comparison example/many_task/sort.cc @ 935:e54842e4d97b

-a option for sort
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Sat, 31 Jul 2010 03:13:24 +0900
parents da657af64afd
children 14fb1c888931
comparison
equal deleted inserted replaced
934:da657af64afd 935:e54842e4d97b
8 extern void check_data(); 8 extern void check_data();
9 9
10 static DataPtr data; 10 static DataPtr data;
11 static int data_length; 11 static int data_length;
12 static int cpuNum; 12 static int cpuNum;
13
14 extern int all;
13 15
14 /** 16 /**
15 * 一つの block にある data の数が MAX_BLOCK_SIZE 超えないような 17 * 一つの block にある data の数が MAX_BLOCK_SIZE 超えないような
16 * len の分割数を返す 18 * len の分割数を返す
17 * 19 *
35 } 37 }
36 38
37 39
38 HTaskPtr *fsort; 40 HTaskPtr *fsort;
39 HTaskPtr *bsort; 41 HTaskPtr *bsort;
40 42 int split_num;
41 #define ALL_TASK 43
42
43 #ifdef ALL_TASK
44
45 static void
46 sort_start(SchedTask *manager)
47 {
48 int split_num = get_split_num(data_length, cpuNum); // data の分割数
49 int half_num = split_num-1;
50 static int sort_count = split_num; // sort 完了に必要な回数
51
52 // 一つのタスクで sort する data 数
53 int block_num = (data_length + split_num -1)/split_num;
54 int half_block_num = block_num/2;
55
56 int last_block_num = data_length - (split_num-1)*block_num;
57 int last_half_block_num = half_block_num+(last_block_num/2);
58
59 while (--sort_count > 0) {
60
61 for (int i = 0; i < split_num-1; i++) {
62 fsort[i] = manager->create_task(QUICK_SORT,
63 (memaddr)&data[i*block_num], sizeof(Data)*block_num,
64 (memaddr)&data[i*block_num], sizeof(Data)*block_num);
65 if (i>0 && bsort[i-1]) {
66 fsort[i]->wait_for(bsort[i-1]);
67 }
68 if (i<split_num-2 && bsort[i]) {
69 fsort[i]->wait_for(bsort[i]);
70 }
71 fsort[i]->set_cpu(SPE_ANY);
72 }
73
74 // 最後の block は端数なので last_block_num を使う
75 {
76 int i = split_num-1;
77
78 fsort[i] = manager->create_task(QUICK_SORT,
79 (memaddr)&data[i*block_num], sizeof(Data)*last_block_num,
80 (memaddr)&data[i*block_num], sizeof(Data)*last_block_num);
81 if (i>0 && bsort[i-1]) {
82 fsort[i]->wait_for(bsort[i-1]);
83 }
84 fsort[i]->set_cpu(SPE_ANY);
85 }
86
87 if (split_num > 1) {
88
89 for (int i = 0; i < half_num-1; i++) {
90 bsort[i] = manager->create_task(QUICK_SORT,
91 (memaddr)&data[i*block_num+half_block_num], sizeof(Data)*block_num,
92 (memaddr)&data[i*block_num+half_block_num], sizeof(Data)*block_num);
93 bsort[i]->set_cpu(SPE_ANY);
94 }
95
96 {
97 int i = half_num-1;
98
99 bsort[i] = manager->create_task(QUICK_SORT,
100 (memaddr)&data[i*block_num+half_block_num], sizeof(Data)*last_half_block_num,
101 (memaddr)&data[i*block_num+half_block_num], sizeof(Data)*last_half_block_num);
102 bsort[i]->set_cpu(SPE_ANY);
103 }
104
105 for (int i = 0; i < half_num; i++) {
106 bsort[i]->wait_for(fsort[i]);
107 bsort[i]->wait_for(fsort[i+1]);
108 bsort[i]->spawn();
109 }
110 }
111
112 for (int i = 0; i < split_num; i++) {
113 fsort[i]->spawn();
114 }
115 }
116 }
117
118 #else
119 44
120 /** 45 /**
121 * btask が全て終了したら、再び sort_start を実行する 46 * btask が全て終了したら、再び sort_start を実行する
122 * @param d 生成された btask の数 47 * @param d 生成された btask の数
123 */ 48 */
124 static void 49
50 SchedDefineTask1(RESTART, sort_restart );
51
52 static int
125 sort_restart(SchedTask *s, void *d, void *e) 53 sort_restart(SchedTask *s, void *d, void *e)
126 { 54 {
127 static int cnt = 0;
128 static int ccc = 0; 55 static int ccc = 0;
129 long max = (long)d; 56
130 57 printf("restarted %d %% %d\n",ccc++,split_num);
131 if (++cnt == max) { 58 sort_start(s);
132 printf("restarted %d %% %ld\n",ccc++,max); 59 return 0;
133 cnt = 0;
134 sort_start(s);
135 }
136 } 60 }
137 #ifdef USE_SIMPLE_TASK 61 #ifdef USE_SIMPLE_TASK
138 62
139 static void 63 static void
140 sort_start(SchedTask *manager) 64 sort_start(SchedTask *manager)
141 { 65 {
142 int split_num = get_split_num(data_length, cpuNum); // data の分割数
143 int half_num = split_num-1; 66 int half_num = split_num-1;
144 static int sort_count = split_num; // sort 完了に必要な回数 67 static int sort_count = split_num; // sort 完了に必要な回数
145 68
146 // 一つのタスクで sort する data 数 69 // 一つのタスクで sort する data 数
147 int block_num = (data_length + split_num -1)/split_num; 70 int block_num = (data_length + split_num -1)/split_num;
205 bsort[i]->wait_for(fsort[i+1]); 128 bsort[i]->wait_for(fsort[i+1]);
206 bsort[i]->spawn(); 129 bsort[i]->spawn();
207 } 130 }
208 } 131 }
209 132
133 HTaskPtr restart = manager->create_task(RESTART,0,0,0,0);
210 for (int i = 0; i < split_num; i++) { 134 for (int i = 0; i < split_num; i++) {
211 fsort[i]->set_post(sort_restart, (void*)(half_num),(void*)manager); 135 if (!all) restart->wait_for(fsort[i]);
212 fsort[i]->spawn(); 136 fsort[i]->spawn();
213 } 137 }
138 restart->spawn();
214 } 139 }
215 140
216 #else 141 #else
217 142
218 static void 143 static void
219 sort_start(SchedTask *manager) 144 sort_start(SchedTask *manager)
220 { 145 {
221 int split_num = get_split_num(data_length, cpuNum); // data の分割数
222 int half_num = split_num-1; 146 int half_num = split_num-1;
223 static int sort_count = split_num; // sort 完了に必要な回数 147 static int sort_count = split_num; // sort 完了に必要な回数
224 148
225 // 一つのタスクで sort する data 数 149 // 一つのタスクで sort する data 数
226 int block_num = (data_length + split_num -1)/split_num; 150 int block_num = (data_length + split_num -1)/split_num;
294 bsort[i]->wait_for(fsort[i+1]); 218 bsort[i]->wait_for(fsort[i+1]);
295 bsort[i]->spawn(); 219 bsort[i]->spawn();
296 } 220 }
297 } 221 }
298 222
223 HTask restart = create_task(RESTART,0,0,0,0);
299 for (int i = 0; i < split_num; i++) { 224 for (int i = 0; i < split_num; i++) {
300 fsort[i]->set_post(sort_restart, (void*)(half_num),(void*)manager); 225 if (!all) restart->wait_for(fsort[i]);
301 fsort[i]->spawn(); 226 fsort[i]->spawn();
302 } 227 }
303 } 228 restart->spawn();
304 #endif 229
230 }
305 #endif 231 #endif
306 232
307 void check_data() 233 void check_data()
308 { 234 {
309 int flag = 1; 235 int flag = 1;
315 } 241 }
316 } 242 }
317 if (flag) printf("Data are sorted\n"); 243 if (flag) printf("Data are sorted\n");
318 } 244 }
319 245
246
320 void 247 void
321 sort_init(SchedTask *manager, void *a, void *b) 248 sort_init(SchedTask *manager, void *a, void *b)
322 { 249 {
323 cpuNum = (int)a; 250 cpuNum = (int)a;
324 int length = (int)b; 251 int length = (int)b;
325 252
326 data = (DataPtr)manager->allocate(sizeof(Data)*length); 253 data = (DataPtr)manager->allocate(sizeof(Data)*length);
327 data_length = length; 254 data_length = length;
328 255
329 int split_num = get_split_num(data_length, cpuNum); // data の分割数 256 split_num = get_split_num(data_length, cpuNum); // data の分割数
330 int half_num = split_num-1; 257 int half_num = split_num-1;
331 fsort = (HTaskPtr*)manager->allocate(sizeof(HTaskPtr)*split_num); 258 fsort = (HTaskPtr*)manager->allocate(sizeof(HTaskPtr)*split_num);
332 bsort = (HTaskPtr*)manager->allocate(sizeof(HTaskPtr)*half_num); 259 bsort = (HTaskPtr*)manager->allocate(sizeof(HTaskPtr)*half_num);
333 memset((void*)bsort,0, sizeof(HTaskPtr)*half_num); 260 memset((void*)bsort,0, sizeof(HTaskPtr)*half_num);
334 261