summaryrefslogtreecommitdiffstats
path: root/SD-VBS/benchmarks/sift/src/c/siftlocalmax.c
diff options
context:
space:
mode:
authorLeo Chan <leochanj@live.unc.edu>2020-10-22 01:53:21 -0400
committerJoshua Bakita <jbakita@cs.unc.edu>2020-10-22 01:56:35 -0400
commitd17b33131c14864bd1eae275f49a3f148e21cf29 (patch)
tree0d8f77922e8d193cb0f6edab83018f057aad64a0 /SD-VBS/benchmarks/sift/src/c/siftlocalmax.c
parent601ed25a4c5b66cb75315832c15613a727db2c26 (diff)
Squashed commit of the sb-vbs branch.
Includes the SD-VBS benchmarks modified to: - Use libextra to loop as realtime jobs - Preallocate memory before starting their main computation - Accept input via stdin instead of via argc Does not include the SD-VBS matlab code. Fixes libextra execution in LITMUS^RT.
Diffstat (limited to 'SD-VBS/benchmarks/sift/src/c/siftlocalmax.c')
-rw-r--r--SD-VBS/benchmarks/sift/src/c/siftlocalmax.c247
1 files changed, 247 insertions, 0 deletions
diff --git a/SD-VBS/benchmarks/sift/src/c/siftlocalmax.c b/SD-VBS/benchmarks/sift/src/c/siftlocalmax.c
new file mode 100644
index 0000000..d75bcbd
--- /dev/null
+++ b/SD-VBS/benchmarks/sift/src/c/siftlocalmax.c
@@ -0,0 +1,247 @@
1#include "sift.h"
2
3/**
4 SIFTLOCALMAX Find local maximizers
5 Returns the indexes of the local maximizers of
6 the 3-dimensional array F.
7
8 Say, we have a Q-dimensional array F.
9 A local maximizer is an element whose value is greater than the
10 value of all its neighbors. The neighbors of an element i1...iQ
11 are the subscripts j1...jQ such that iq-1 <= jq <= iq (excluding
12 i1...iQ itself). For example, if Q=1 the neighbors of an element
13 are its predecessor and successor in the linear order; if Q=2, its
14 neighbors are the elements immediately to its north, south, west,
15 est, north-west, north-est, south-west and south-est
16 (8-neighborhood).
17
18 Points on the boundary of F are ignored (and never selected as
19 local maximizers).
20
21 SEL=SIFTLOCALMAX(F,THRESH) accepts an element as a mazimizer only
22 if it is at least THRES greater than all its neighbors.
23
24 SEL=SIFTLOCALMAX(F,THRESH,P) look for neighbors only in the first
25 P dimensions of the Q-dimensional array F. This is useful to
26 process F in ``slices''.
27
28 REMARK. Matrices (2-array) with a singleton dimension are
29 interpreted as vectors (1-array). So for example SIFTLOCALMAX([0 1
30 0]) and SIFTLOCALMAX([0 1 0]') both return 2 as an aswer. However,
31 if [0 1 0] is to be interpreted as a 1x2 matrix, then the correct
32 answer is the empty set, as all elements are on the boundary.
33 Unfortunately MATLAB does not distinguish between vectors and
34 2-matrices with a singleton dimension. To forece the
35 interpretation of all matrices as 2-arrays, use
36 SIFTLOCALMAX(F,TRESH,2) (but note that in this case the result is
37 always empty!).
38**/
39
40#define NDIMS 3
41
42F2D* siftlocalmax(F2D* in, float thresh, int intervals, int M, int N)
43{
44 int ndims, ptoffset=0, maxIter = 0;
45 int offsets[NDIMS];
46 int midx[NDIMS];
47 int dims[NDIMS];
48 I2D* neighbors ;
49 int nneighbors ;
50 F2D* out;
51
52 /**
53 We pass dogss[o], which has >1 intervals
54 If >1 intervals, then the dimensions of in[F] will be 1 x intervals
55 If =1 interval, then the dimensions of in[F] will be the size of the dogss[o] image
56 We will check for this condition.
57 **/
58
59 ndims = NDIMS; /* Since we have intervals number of images of size M x N */
60 dims[0] = M;
61 dims[1] = N;
62 dims[2] = intervals-1;
63
64 /*
65 If there are only two dimensions and if one is singleton, then
66 assume that a vector has been provided as input (and treat this
67 as a COLUMN matrix with p=1). We do this because Matlab does not
68 distinguish between vectors and 1xN or Mx1 matrices and because
69 the cases 1xN and Mx1 are trivial (the result is alway empty).
70 */
71
72
73
74 /* ------------------------------------------------------------------
75 * Do the job
76 * --------------------------------------------------------------- */
77 int maxima_size = M*N ;
78
79 I2D* maxima_start = iMallocHandle(1, maxima_size);
80 int* maxima_iterator = maxima_start->data ;
81 int* maxima_end = maxima_start->data + maxima_size ;
82
83 int i,h,o,j;
84 F2D* pt;
85
86 pt = in;
87
88 /* Compute the offsets between dimensions. */
89 offsets[0] = 1 ;
90 for(i = 1 ; i < ndims ; ++i)
91 {
92 offsets[i] = offsets[i-1]*dims[i-1] ;
93 }
94
95 /* Multi-index. */
96 for(i = 0 ; i < ndims ; ++i)
97 midx[i] = 1 ;
98
99 /* Neighbors. */
100 nneighbors = 1 ;
101 o=0 ;
102 for(i = 0 ; i < ndims ; ++i)
103 {
104 nneighbors *= 3 ;
105 midx[i] = -1 ;
106 o -= offsets[i] ;
107 }
108 nneighbors -= 1 ;
109 neighbors = iMallocHandle(1,nneighbors);
110
111 /* Precompute offsets from offset(-1,...,-1,0,...0) to
112 * offset(+1,...,+1,0,...,0). */
113 i = 0 ;
114
115 while(1)
116 {
117 if(o != 0)
118 {
119 asubsref(neighbors, i) = o ;
120 i++;
121 }
122 h = 0 ;
123 while( o += offsets[h], (++midx[h]) > 1 )
124 {
125 o -= 3*offsets[h] ;
126 midx[h] = -1 ;
127 if(++h >= ndims)
128 goto stop ;
129 }
130 }
131
132 stop: ;
133
134 /* Starts at the corner (1,1,...,1,0,0,...0) */
135 for(h = 0 ; h < ndims ; ++h)
136 {
137 midx[h] = 1 ;
138 ptoffset += offsets[h] ;
139 }
140
141
142 /* ---------------------------------------------------------------
143 * Loop
144 * ------------------------------------------------------------ */
145
146 /*
147 If any dimension in the first P is less than 3 elements wide
148 then just return the empty matrix (if we proceed without doing
149 anything we break the carry reporting algorithm below).
150 */
151
152 for(h=0 ; h < ndims ; ++h)
153 if(dims[h] < 3)
154 goto end ;
155
156 while(1)
157 {
158 /* Propagate carry along multi index midx */
159
160 h = 0 ;
161 while(midx[h] >= dims[h] - 1)
162 {
163 midx[h] = 1 ;
164 if(++h >= ndims)
165 goto next_layer ;
166 ++midx[h] ;
167 }
168
169 /* Scan neighbors */
170 {
171 float v = asubsref(pt, ptoffset); //*pt ;
172 int is_greater = (v>=thresh) ? 1 : 0;
173
174 assert(ptoffset < pt->width*pt->height);
175
176 i = 0 ;
177 while(is_greater && i < nneighbors)
178 {
179 if(v > asubsref(pt, ptoffset + asubsref(neighbors,i)))
180 is_greater *= 1;
181 else
182 is_greater *= 0;
183 i = i+1;
184 }
185
186 /* Add the local maximum */
187 if(is_greater)
188 {
189 /* Need more space? */
<