source: branches/v4/softs/soft_transpose_giet/main.c @ 466

Last change on this file since 466 was 248, checked in by meunier, 12 years ago

Updates in the soft_filter application (bug corrections, formatting, and adaptation to the architecture generic_mmu)

File size: 12.2 KB
Line 
1
2#include "stdio.h"
3#include "limits.h"
4#include "../giet_tsar/block_device.h"
5
6#define NL              512
7#define NP              512
8#define NB_IMAGES       1
9#define NB_CLUSTER_MAX  256
10
11#define PRINTF(...)      ({ if (proc_id == 0) { tty_printf(__VA_ARGS__); } })
12
13//#define DISPLAY_ONLY
14
15///////////////////////////////////////////
16// tricks to read parameters from ldscript
17///////////////////////////////////////////
18
19struct plaf;
20
21extern struct plouf seg_ioc_base;
22extern struct plaf seg_heap_base;
23extern struct plaf NB_PROCS;
24extern struct plaf NB_CLUSTERS;
25
26/////////////
27void main(){
28   unsigned int frame = 0;
29   unsigned int date  = 0;
30
31   unsigned int c; // cluster index for loops
32   unsigned int l; // line index for loops
33   unsigned int p; // pixel index for loops
34
35   unsigned int proc_id       = procid();                      // processor id
36   unsigned int nlocal_procs  = (unsigned int) &NB_PROCS;      // number of processors per cluster
37   unsigned int nclusters     = (unsigned int) &NB_CLUSTERS;   // number of clusters
38   unsigned int local_id      = proc_id % nlocal_procs;        // local processor id
39   unsigned int cluster_id    = proc_id / nlocal_procs;        // cluster id
40   unsigned int base          = (unsigned int) &seg_heap_base; // base address for shared buffers
41   unsigned int increment     = 0x80000000 / nclusters * 2;    // cluster increment
42   unsigned int nglobal_procs = nclusters * nlocal_procs;      // number of tasks
43   unsigned int npixels       = NP * NL;                       // number of pixel per frame
44   
45   unsigned int * ioc_address = (unsigned int *) &seg_ioc_base;
46   unsigned int block_size    = ioc_address[BLOCK_DEVICE_BLOCK_SIZE];
47   unsigned int nblocks       = npixels / block_size;   // number of blocks per frame
48
49   PRINTF("\n *** Entering main at cycle %d ***\n\n", proctime());
50
51   //  parameters checking
52   if ((nlocal_procs != 1) && (nlocal_procs != 2) && (nlocal_procs != 4)){
53      PRINTF("NB_PROCS must be 1, 2 or 4\n");
54      exit(1);
55   }
56   if ((nclusters != 1) && (nclusters != 2) && (nclusters != 4) && (nclusters != 8) &&
57         (nclusters != 16) && (nclusters != 32) && (nclusters != 64) && (nclusters != 128) &&
58         (nclusters != 256)){
59      PRINTF("NB_CLUSTERS must be a power of 1 between 1 and 256\n");
60      exit(1);
61   }
62   if (nglobal_procs > 1024){
63      PRINTF("NB_PROCS * NB_CLUSTERS cannot be larger than 1024\n");
64      exit(1);
65   }
66   if (proc_id >= nglobal_procs){
67      PRINTF("processor id %d larger than NB_CLUSTERS*NB_PROCS\n", proc_id);
68      exit(1);
69   }
70
71   // Arrays of pointers on the shared, distributed buffers containing the frames
72   // These arrays are indexed by the cluster index (sized for the worst case : 256 clusters)
73   unsigned char * A[NB_CLUSTER_MAX];
74   unsigned char * B[NB_CLUSTER_MAX];
75
76   // Arrays of pointers on the instrumentation arrays
77   // These arrays are indexed by the cluster index (sized for the worst case : 256 clusters)
78   // each pointer points on the base adress of an array of NPROCS unsigned int
79   unsigned int * LOAD_START[NB_CLUSTER_MAX];
80   unsigned int * LOAD_END[NB_CLUSTER_MAX];
81   unsigned int * TRSP_START[NB_CLUSTER_MAX];
82   unsigned int * TRSP_END[NB_CLUSTER_MAX];
83   unsigned int * DISP_START[NB_CLUSTER_MAX];
84   unsigned int * DISP_END[NB_CLUSTER_MAX];
85
86   // shared buffers address definition
87   // from the seg_heap_base and increment depending on the cluster index
88   // These arrays of pointers are identical and replicated in the stack of each task
89   for (c = 0; c < nclusters; c++){
90      A[c]          = (unsigned char *) (base                                  + increment * c);
91      B[c]          = (unsigned char *) (base +     npixels                    + increment * c);
92      LOAD_START[c] = (unsigned int *)  (base + 2 * npixels                    + increment * c);
93      LOAD_END[c]   = (unsigned int *)  (base + 2 * npixels +     nlocal_procs + increment * c);
94      TRSP_START[c] = (unsigned int *)  (base + 2 * npixels + 2 * nlocal_procs + increment * c);
95      TRSP_END[c]   = (unsigned int *)  (base + 2 * npixels + 3 * nlocal_procs + increment * c);
96      DISP_START[c] = (unsigned int *)  (base + 2 * npixels + 4 * nlocal_procs + increment * c);
97      DISP_END[c]   = (unsigned int *)  (base + 2 * npixels + 5 * nlocal_procs + increment * c);
98   }
99
100   PRINTF("NB_CLUSTERS     = %d\n", nclusters); 
101   PRINTF("NB_LOCAL_PROCS  = %d\n", nlocal_procs); 
102   PRINTF("NB_GLOBAL_PROCS = %d\n", nglobal_procs);
103   PRINTF("NB_PIXELS       = %d\n", npixels);
104   PRINTF("BLOCK_SIZE      = %d\n", block_size);
105   PRINTF("NB_BLOCKS       = %d\n\n", nblocks);
106
107
108   PRINTF("*** Starting barrier init at cycle %d ***\n", proctime());
109
110   //  barriers initialization
111   barrier_init(0, nglobal_procs);
112   barrier_init(1, nglobal_procs);
113   barrier_init(2, nglobal_procs);
114
115   PRINTF("*** Completing barrier init at cycle %d ***\n", proctime());
116
117   // Main loop (on frames)
118   while (frame < NB_IMAGES){
119      // pseudo parallel load from disk to A[c] buffer : nblocks/nclusters blocks
120      // only task running on processor with (local_id == 0) does it
121
122      if (local_id == 0){
123         int p;
124
125         date = proctime();
126         PRINTF("\n*** Starting load for frame %d at cycle %d\n", frame, date);
127         
128         for (p = 0; p < nlocal_procs; p++){
129            LOAD_START[cluster_id][p] = date;
130         }
131         if (ioc_read(frame * nblocks + nblocks * cluster_id / nclusters, A[cluster_id], nblocks / nclusters)){
132            PRINTF("echec ioc_read\n");
133            exit();
134         }
135         if (ioc_completed()){
136            PRINTF("echec ioc_completed\n");
137            exit();
138         }
139
140         date = proctime();
141         PRINTF("*** Completing load for frame %d at cycle %d\n", frame, date);
142         for (p = 0; p < nlocal_procs; p++){
143            LOAD_END[cluster_id][p] = date;
144         }
145      }
146
147      barrier_wait(0);
148
149      // parallel transpose from A to B buffers
150      // each processor makes the transposition for (NL/nglobal_procs) lines
151      // (p,l) are the (x,y) pixel coordinates in the source frame
152
153#ifndef DISPLAY_ONLY
154      date = proctime();
155      PRINTF("\n*** Starting transpose for frame %d at cycle %d\n", frame, date);
156      TRSP_START[cluster_id][local_id] = date;
157
158      unsigned int nlt   = NL / nglobal_procs; // Nombre de ligne à traiter par processeur
159      unsigned int first = proc_id * nlt;      // Index de la premiÚre ligne à traiter pour le proc courant (celui qui exécute le code)
160      unsigned int last  = first + nlt;        // Index de la derniÚre ligne
161      unsigned int nlines_clusters = NL / nclusters; // Nombre de lignes à traiter par cluster
162      unsigned int npix_clusters   = NP / nclusters; // Nombre de pixels par ligne à traiter par cluster
163
164      for (l = first; l < last; l++){
165         PRINTF("    - processing line %d\n", l);
166         for (p = 0; p < NP; p++){
167            unsigned int source_index   = (l % nlines_clusters) * NP + p;
168            unsigned int dest_cluster   = p / npix_clusters;
169            unsigned int dest_index     = (p % npix_clusters) * NL + l;
170            B[dest_cluster][dest_index] = A[cluster_id][source_index];
171         }
172      }
173
174      date = proctime();
175      PRINTF("*** Completing transpose for frame %d at cycle %d\n", frame, date);
176      TRSP_END[cluster_id][local_id] = date;
177      barrier_wait(1);
178#endif
179
180      // parallel display from B[c] to frame buffer
181      // each processor uses its private dma to display NL*NP/nglobal_procs pixels
182
183      date = proctime();
184      PRINTF("\n*** Starting display for frame %d at cycle %d\n", frame, date);
185      DISP_START[cluster_id][local_id] = date;
186
187      unsigned int npxt = npixels / nglobal_procs;   // number of pixels per proc
188
189#ifndef DISPLAY_ONLY
190      if (fb_write(npxt * proc_id, B[cluster_id] + npxt * local_id, npxt)){
191         PRINTF("[%d]: echec fb_sync_write\n", proc_id);
192         exit();
193      }
194#else
195      if (fb_write(npxt * proc_id, A[cluster_id] + npxt * local_id, npxt)){
196         PRINTF("[%d]: echec fb_sync_write\n", proc_id);
197         exit();
198      }
199#endif
200
201      if (fb_completed()){
202         PRINTF("[%d]: echec fb_completed\n", proc_id);
203         exit();
204      }
205
206      date = proctime();
207      PRINTF("*** Completing display for frame %d at cycle %d\n", frame, date);
208      DISP_END[cluster_id][local_id] = date;
209
210      barrier_wait(2);
211
212      // Instrumentation (done by processor 0 in cluster 0)
213      if (local_id == 0){ 
214         date = proctime();
215         PRINTF("\n*** Starting Instrumentation for frame %d at cycle %d\n\n", frame, date);
216
217         int cc, pp;
218         unsigned int min_load_start = INT_MAX;
219         unsigned int max_load_start = 0;
220         unsigned int min_load_ended = INT_MAX;
221         unsigned int max_load_ended = 0;
222         unsigned int min_trsp_start = INT_MAX;
223         unsigned int max_trsp_start = 0;
224         unsigned int min_trsp_ended = INT_MAX;
225         unsigned int max_trsp_ended = 0;
226         unsigned int min_disp_start = INT_MAX;
227         unsigned int max_disp_start = 0;
228         unsigned int min_disp_ended = INT_MAX;
229         unsigned int max_disp_ended = 0;
230
231         for (cc = 0; cc < nclusters; cc++){
232            for (pp = 0; pp < nlocal_procs; pp++){
233               if (LOAD_START[cc][pp] < min_load_start){
234                  min_load_start = LOAD_START[cc][pp];
235               }
236               if (LOAD_START[cc][pp] > max_load_start){
237                  max_load_start = LOAD_START[cc][pp];
238               }
239               if (LOAD_END[cc][pp] < min_load_ended){
240                  min_load_ended = LOAD_END[cc][pp];
241               }
242               if (LOAD_END[cc][pp] > max_load_ended){
243                  max_load_ended = LOAD_END[cc][pp];
244               }
245
246               if (TRSP_START[cc][pp] < min_trsp_start){
247                  min_trsp_start = TRSP_START[cc][pp];
248               }
249               if (TRSP_START[cc][pp] > max_trsp_start){
250                  max_trsp_start = TRSP_START[cc][pp];
251               }
252               if (TRSP_END[cc][pp] < min_trsp_ended){
253                  min_trsp_ended = TRSP_END[cc][pp];
254               }
255               if (TRSP_END[cc][pp] > max_trsp_ended){
256                  max_trsp_ended = TRSP_END[cc][pp];
257               }
258
259               if (DISP_START[cc][pp] < min_disp_start){
260                  min_disp_start = DISP_START[cc][pp];
261               }
262               if (DISP_START[cc][pp] > max_disp_start){
263                  max_disp_start = DISP_START[cc][pp];
264               }
265               if (DISP_END[cc][pp] < min_disp_ended){
266                  min_disp_ended = DISP_END[cc][pp];
267               }
268               if (DISP_END[cc][pp] > max_disp_ended){
269                  max_disp_ended = DISP_END[cc][pp];
270               }
271            }
272         }
273
274         PRINTF(" - LOAD_START : min = %d / max = %d / med = %d / delta = %d\n",
275               min_load_start, max_load_start, (min_load_start+max_load_start)/2, max_load_start-min_load_start); 
276         PRINTF(" - LOAD_END   : min = %d / max = %d / med = %d / delta = %d\n",
277               min_load_ended, max_load_ended, (min_load_ended+max_load_ended)/2, max_load_ended-min_load_ended); 
278
279         PRINTF(" - TRSP_START : min = %d / max = %d / med = %d / delta = %d\n",
280               min_trsp_start, max_trsp_start, (min_trsp_start+max_trsp_start)/2, max_trsp_start-min_trsp_start); 
281         PRINTF(" - TRSP_END   : min = %d / max = %d / med = %d / delta = %d\n",
282               min_trsp_ended, max_trsp_ended, (min_trsp_ended+max_trsp_ended)/2, max_trsp_ended-min_trsp_ended); 
283
284         PRINTF(" - DISP_START : min = %d / max = %d / med = %d / delta = %d\n",
285               min_disp_start, max_disp_start, (min_disp_start+max_disp_start)/2, max_disp_start-min_disp_start); 
286         PRINTF(" - DISP_END   : min = %d / max = %d / med = %d / delta = %d\n",
287               min_disp_ended, max_disp_ended, (min_disp_ended+max_disp_ended)/2, max_disp_ended-min_disp_ended); 
288
289         PRINTF(" - BARRIER TRSP/DISP = %d\n", min_disp_start - max_trsp_ended);
290      }
291      frame++;
292
293   } // end while frame     
294
295   PRINTF("*** End of main ***\n");
296
297   while(1);
298} // end main()
299
300// Local Variables:
301// tab-width: 3
302// c-basic-offset: 3
303// c-file-offsets:((innamespace . 0)(inline-open . 0))
304// indent-tabs-mode: nil
305// End:
306
307// vim: filetype=cpp:expandtab:shiftwidth=3:tabstop=3:softtabstop=3
308
309
310
Note: See TracBrowser for help on using the repository browser.