1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
|
# Copyright(c) 1986 Association of Universities for Research in Astronomy Inc.
include <imhdr.h>
include "cogetr.h"
# COGETR -- Get a real column vector from a 2D image.
#
# This procedure is designed to be efficient when:
# 1. The columns are accessed sequentially.
# 2. The number of lines does not change.
# 3. The first and last lines change slowly with column.
# One such case is when the entire column of an image is required. Then
# the first and last lines do not change at all. Another type of use
# occurs when dealing with features which are aligned nearly
# with the image lines. For example objects in a long slit spectrum or
# Echelle orders.
#
# As the columns are accessed sequentially new lines are added to a
# scrolled buffer only when the first and last lines fall outside the
# buffer. If the buffer size is insufficient to hold the all the columns
# then the buffer is set to contain a block of columns. When the desired
# column is outside the block of columns then a new block is read.
# The buffer is created and initialized when the buffer pointer
# is null or when the number of lines requested is changed. Both the
# buffer and the column data pointer are allocated in this procedure.
# The user must free the buffers with the procedure COUNMAP.
pointer procedure cogetr (co, col, line1, line2)
pointer co # COIO pointer
int col # Column
int line1 # First image line of column vector
int line2 # Last image line of column vector
int ncols, nlines, lastc1, lastl1, lastl2
int i, imlen1, imlen2, col1, nc
pointer im, coldata, buffer, buf, data
pointer imgl2r()
begin
# Dereference the structure elements to improve the readability of
# the code and reduce the Mem index arithmetic.
im = CO_IM(co)
coldata = CO_DATA(co)
buffer = CO_BUF(co)
ncols = CO_NCOLS(co)
nlines = CO_NLINES(co)
lastc1 = CO_COL1(co)
lastl1 = CO_LINE1(co)
lastl2 = CO_LINE2(co)
imlen1 = IM_LEN (im, 1)
imlen2 = IM_LEN (im, 2)
# If memory has not been allocated then allocate it.
# If the number of lines changes reallocate the buffer and
# initialize lastc1 to zero to force a full buffer read.
i = min (imlen2, (line2 - line1 + 1) + 2 * EXTRA)
if ((buffer == NULL) || (nlines != i)) {
nlines = i
ncols = min (imlen1, CO_MAXBUF(co) / nlines)
lastc1 = 0
call mfree (coldata, TY_REAL)
call mfree (buffer, TY_REAL)
call malloc (coldata, line2 - line1 + 1, TY_REAL)
call malloc (buffer, ncols * nlines, TY_REAL)
CO_DATA(co) = coldata
CO_BUF(co) = buffer
CO_NCOLS(co) = ncols
CO_NLINES(co) = nlines
}
# Determine the starting column and the number of columns per line.
col1 = ((col - 1) / ncols) * ncols + 1
nc = min (ncols, imlen1 - col1 + 1)
# If there is no overlap with the last buffer then read all the
# requested lines. Otherwise read only the image lines with are
# different from the last buffer.
if ((col1 != lastc1) || (line1 > lastl2) || (line2 < lastl1)) {
lastc1 = col1
lastl1 = max (1, line1 - EXTRA)
lastl2 = min (imlen2, line2 + EXTRA)
do i = lastl1, lastl2 {
buf = buffer + mod (i, nlines) * ncols
call amovr (Memr[imgl2r(im, i)+col1-1], Memr[buf], nc)
}
CO_COL1(co) = lastc1
CO_LINE1(co) = lastl1
CO_LINE2(co) = lastl2
} else if (line1 < lastl1) {
do i = max (1, line1 - EXTRA), min (imlen2, lastl1 - 1) {
buf = buffer + mod (i, nlines) * ncols
call amovr (Memr[imgl2r(im, i)+col1-1], Memr[buf], nc)
}
lastl1 = max (1, line1 - EXTRA)
lastl2 = min (imlen2, line2 + EXTRA)
CO_LINE1(co) = lastl1
CO_LINE2(co) = lastl2
} else if (line2 > lastl2) {
do i = max (1, lastl2 + 1), min (imlen2, line2 + EXTRA) {
buf = buffer + mod (i, nlines) * ncols
call amovr (Memr[imgl2r(im, i)+col1-1], Memr[buf], nc)
}
lastl1 = max (1, line1 - EXTRA)
lastl2 = min (imlen2, line2 + EXTRA)
CO_LINE1(co) = lastl1
CO_LINE2(co) = lastl2
}
# Set the column data vector.
data = coldata
do i = line1, line2 {
buf = buffer + mod (i, nlines) * ncols
Memr[data] = Memr[buf+col-col1]
data = data + 1
}
return (coldata)
end
# COMAP -- Map the column access
pointer procedure comap (im, maxbuf)
pointer im # IMIO pointer
int maxbuf # Maximum buffer size
pointer co # Returned pointer
begin
call malloc (co, LEN_CO, TY_LONG)
CO_IM(co) = im
CO_MAXBUF(co) = maxbuf
CO_DATA(co) = NULL
CO_BUF(co) = NULL
return (co)
end
# COUMAP -- Unmap the column access
procedure counmap (co)
pointer co # Pointer to buffer structure
begin
call mfree (CO_DATA(co), TY_REAL)
call mfree (CO_BUF(co), TY_REAL)
call mfree (co, TY_LONG)
end
|