bzr branch
http://darksoft.org/webbzr/perf/fdk
1
by Suren A. Chilingaryan
Initial |
1 |
#define _POSIX_C_SOURCE 200112L
|
2 |
#define _XOPEN_SOURCE 600
|
|
3 |
||
4 |
#include <stdio.h> |
|
5 |
#include <stdlib.h> |
|
6 |
#include <malloc.h> |
|
2
by Suren A. Chilingaryan
Intel compiler |
7 |
#include <errno.h> |
1
by Suren A. Chilingaryan
Initial |
8 |
#include <sys/time.h> |
2
by Suren A. Chilingaryan
Intel compiler |
9 |
#include <ctype.h> |
10 |
#include <stdarg.h> |
|
1
by Suren A. Chilingaryan
Initial |
11 |
|
12 |
#include <math.h> |
|
13 |
#include <pthread.h> |
|
14 |
#include <stdint.h> |
|
15 |
#include <string.h> |
|
16 |
#include <limits.h> |
|
17 |
||
2
by Suren A. Chilingaryan
Intel compiler |
18 |
#include <getopt.h> |
19 |
||
1
by Suren A. Chilingaryan
Initial |
20 |
#include "process.h" |
21 |
||
2
by Suren A. Chilingaryan
Intel compiler |
22 |
extern int counter; |
23 |
||
24 |
||
25 |
enum { |
|
26 |
OPT_SLICE = 's', |
|
27 |
OPT_HELP
|
|
28 |
};
|
|
29 |
||
30 |
static struct option long_options[] = { |
|
31 |
{"help", no_argument, 0, OPT_HELP }, |
|
32 |
{"slice", required_argument, 0, OPT_SLICE }, |
|
33 |
{ 0, 0, 0, 0 } |
|
34 |
};
|
|
35 |
||
36 |
static void Usage(int argc, char *argv[], const char *format, ...) { |
|
37 |
if (format) { |
|
38 |
va_list ap; |
|
39 |
||
40 |
va_start(ap, format); |
|
41 |
printf("Error %i: ", errno); |
|
42 |
vprintf(format, ap); |
|
43 |
printf("\n"); |
|
44 |
va_end(ap); |
|
45 |
||
46 |
printf("\n"); |
|
47 |
}
|
|
48 |
||
49 |
printf( |
|
50 |
"Usage:\n" |
|
51 |
" %s [options]\n" |
|
52 |
"\n" |
|
53 |
"Options:\n" |
|
54 |
" -s [slice] - slice number\n" |
|
55 |
"\n\n", |
|
56 |
argv[0]); |
|
57 |
||
58 |
exit(0); |
|
59 |
}
|
|
60 |
||
61 |
||
62 |
static int isnumber(const char *str) { |
|
63 |
int i = 0; |
|
64 |
for (i = 0; str[i]; i++) |
|
65 |
if (!isdigit(str[i])) return 0; |
|
66 |
return 1; |
|
67 |
}
|
|
68 |
||
69 |
||
70 |
void main(int argc, char *argv[]) { |
|
1
by Suren A. Chilingaryan
Initial |
71 |
|
72 |
int n_threads = 1; |
|
73 |
int alignment = 256; |
|
74 |
||
75 |
long n_proj = 3600; |
|
76 |
long n_elements = 2000; |
|
77 |
float cor = 1060. / 16; |
|
78 |
float d = 1060; |
|
79 |
float detector_size = 400; |
|
80 |
float pixel_size = 400. / 2000; |
|
81 |
float cor_offset = 0; |
|
82 |
float detector_offset_u = 0, detector_offset_v = 0, detector_offset_z = 0; |
|
83 |
float source[] = {0, 0, 0}; |
|
84 |
float u_detector[] = {1, 0, 0}; |
|
85 |
float v_detector[] = {0, 1, 0}; |
|
86 |
float n_detector[] = {0, 0, 1}; |
|
87 |
||
88 |
float *out_volume, *projections, *slice_x, *slice_y, *slice_coord_z; |
|
89 |
||
90 |
int err; |
|
91 |
int i, j; |
|
92 |
int tnum, m; |
|
93 |
struct thread_info *t_info; |
|
94 |
void *res; |
|
95 |
||
96 |
struct timeval start, end; |
|
97 |
long duration; |
|
98 |
||
99 |
err = posix_memalign((void**)&out_volume, alignment, n_elements * n_elements * n_elements * sizeof(float)); |
|
100 |
if (!err) err = posix_memalign((void**)&projections, alignment, n_elements * n_elements * n_proj * sizeof(float)); |
|
101 |
if (!err) err = posix_memalign((void**)&slice_x, alignment, n_elements * n_elements * sizeof(float)); |
|
102 |
if (!err) err = posix_memalign((void**)&slice_y, alignment, n_elements * n_elements * sizeof(float)); |
|
103 |
if (!err) err = posix_memalign((void**)&slice_coord_z, alignment, n_elements * sizeof(float)); |
|
104 |
||
105 |
if (err) { |
|
106 |
printf("Can not allocate memory"); |
|
107 |
exit(-1); |
|
108 |
}
|
|
109 |
||
110 |
for (i = 0; i < n_elements; i++) { |
|
2
by Suren A. Chilingaryan
Intel compiler |
111 |
slice_coord_z[i] = (pixel_size / 16) * ((i + 1) - (n_elements + 1.) / 2); |
1
by Suren A. Chilingaryan
Initial |
112 |
for (j = 0; j < n_elements; j++) { |
113 |
slice_x[i * n_elements + j] = (pixel_size / 16) * ((i + 1) - (n_elements + 1.)/2); |
|
114 |
slice_y[i * n_elements + j] = (pixel_size / 16) * ((n_elements - j) - (n_elements + 1.)/2); |
|
115 |
}
|
|
116 |
}
|
|
117 |
||
118 |
/* allocate memory for threads */
|
|
119 |
t_info = (struct thread_info*) calloc(n_threads, sizeof(struct thread_info)); |
|
120 |
||
121 |
if (t_info == NULL) |
|
122 |
{
|
|
123 |
printf("Structure t_info memory allocation error\n"); |
|
124 |
exit(-1); |
|
125 |
}
|
|
126 |
||
127 |
/* fill tread_info structure and create threads */
|
|
128 |
||
2
by Suren A. Chilingaryan
Intel compiler |
129 |
|
130 |
counter = n_elements / 2; |
|
131 |
||
132 |
unsigned char c; |
|
133 |
while ((c = getopt_long(argc, argv, "s:", long_options, NULL)) != (unsigned char)-1) { |
|
134 |
extern int optind; |
|
135 |
switch (c) { |
|
136 |
case OPT_HELP: |
|
137 |
Usage(argc, argv, NULL); |
|
138 |
break; |
|
139 |
case OPT_SLICE: |
|
140 |
if ((!isnumber(optarg))||(sscanf(optarg, "%i", &counter) != 1)||(counter < 0)||(counter >= n_elements)) { |
|
141 |
Usage(argc, argv, "Invalid slice is specified (%s)", optarg); |
|
142 |
}
|
|
143 |
break; |
|
144 |
default: |
|
145 |
Usage(argc, argv, "Unknown option (%s) with argument (%s)", optarg?argv[optind-2]:argv[optind-1], optarg?optarg:"(null)"); |
|
146 |
}
|
|
147 |
}
|
|
148 |
||
149 |
||
1
by Suren A. Chilingaryan
Initial |
150 |
gettimeofday(&start, NULL); |
151 |
||
152 |
for (tnum = 0; tnum < n_threads; tnum++) |
|
153 |
{
|
|
154 |
t_info[tnum].thread_num = tnum; /* Application-defined thread # */ |
|
155 |
t_info[tnum].n_elements = n_elements; |
|
156 |
t_info[tnum].n_proj = n_proj; |
|
157 |
t_info[tnum].cor = cor; |
|
158 |
t_info[tnum].d = d; |
|
159 |
t_info[tnum].detector_size = detector_size; |
|
160 |
t_info[tnum].pixel_size = pixel_size; |
|
161 |
t_info[tnum].cor_offset = cor_offset; |
|
162 |
t_info[tnum].detector_offset_u = detector_offset_u; |
|
163 |
t_info[tnum].detector_offset_v = detector_offset_v; |
|
164 |
t_info[tnum].detector_offset_z = detector_offset_z; |
|
165 |
t_info[tnum].source = source; |
|
166 |
t_info[tnum].u_detector = u_detector; |
|
167 |
t_info[tnum].v_detector = v_detector; |
|
168 |
t_info[tnum].n_detector = n_detector; |
|
169 |
t_info[tnum].projections = projections; |
|
170 |
t_info[tnum].slice_x = slice_x; |
|
171 |
t_info[tnum].slice_y = slice_y; |
|
172 |
t_info[tnum].slice_coord_z = slice_coord_z; |
|
173 |
t_info[tnum].out_volume = out_volume; |
|
2
by Suren A. Chilingaryan
Intel compiler |
174 |
t_info[tnum].slices_per_iter = n_elements; |
1
by Suren A. Chilingaryan
Initial |
175 |
|
176 |
if (n_threads > 1) { |
|
177 |
m = pthread_create(&t_info[tnum].thread_id, NULL, &process, &t_info[tnum]); |
|
178 |
||
179 |
if (m != 0) |
|
180 |
{
|
|
181 |
printf("Cannot create thread with error %i\n", m); |
|
182 |
exit(-1); |
|
183 |
}
|
|
184 |
} else { |
|
185 |
process(&t_info[tnum]); |
|
186 |
}
|
|
187 |
}
|
|
188 |
||
189 |
if (n_threads > 1) { |
|
190 |
/* join threads */
|
|
191 |
for (tnum = 0; tnum < n_threads; tnum++) |
|
192 |
{
|
|
193 |
m = pthread_join(t_info[tnum].thread_id, &res); |
|
194 |
||
195 |
if (m != 0) |
|
196 |
{
|
|
197 |
printf("Cannot join threads with error %i\n", m); |
|
198 |
exit(-1); |
|
199 |
}
|
|
200 |
}
|
|
201 |
}
|
|
202 |
||
203 |
gettimeofday(&end, NULL); |
|
204 |
duration = (end.tv_sec - start.tv_sec) * 1000000 + end.tv_usec - start.tv_usec; |
|
2
by Suren A. Chilingaryan
Intel compiler |
205 |
printf("Time: %2u:%2u:%2u (%6u)\n", duration/3600000000, (duration%3600000000)/60000000, (duration%60000000)/1000000, (duration%1000000)); |
1
by Suren A. Chilingaryan
Initial |
206 |
|
207 |
||
208 |
free(t_info); |
|
209 |
free(slice_coord_z); |
|
210 |
free(slice_y); |
|
211 |
free(slice_x); |
|
212 |
free(projections); |
|
213 |
free(out_volume); |
|
214 |
}
|