Bug fixes and add some code for easy debugging
[IRC.git] / Robust / src / Runtime / bamboo / multicoremem.c
1 #ifdef MULTICORE
2 #include "runtime_arch.h"
3 #include "multicoreruntime.h"
4
5 extern int corenum;
6
7 #ifdef MULTICORE_GC
8 #include "multicorehelper.h"
9
10 #ifdef SMEMF
11 #define NUM_CORES2TEST 5
12 #ifdef GC_1
13 int core2test[1][NUM_CORES2TEST] = {
14   {0, -1, -1, -1, -1}
15 };
16 #elif defined GC_56
17 int core2test[56][NUM_CORES2TEST] = {
18   { 0, -1,  7, -1,  1}, { 1, -1,  8,  0,  2}, { 2, -1,  9,  1,  3},
19   { 3, -1, 10,  2,  4}, { 4, -1, 11,  3,  5}, { 5, -1, 12,  4,  6},
20   { 6, -1, 13,  5, -1}, { 7,  0, 14, -1,  8}, { 8,  1, 15,  7,  9},
21   { 9,  2, 16,  8, 10}, {10,  3, 17,  9, 11}, {11,  4, 18, 10, 12},
22   {12,  5, 19, 11, 13}, {13,  6, 20, 12, -1}, {14,  7, 21, -1, 15},
23   {15,  8, 22, 14, 16}, {16,  9, 23, 15, 17}, {17, 10, 24, 16, 18},
24   {18, 11, 25, 17, 19}, {19, 12, 26, 18, 20}, {20, 13, 27, 19, -1},
25   {21, 14, 28, -1, 22}, {22, 15, 29, 21, 23}, {23, 16, 30, 22, 24},
26   {24, 17, 31, 23, 25}, {25, 18, 32, 24, 26}, {26, 19, 33, 25, 27},
27   {27, 20, 34, 26, -1}, {28, 21, 35, -1, 29}, {29, 22, 36, 28, 30},
28   {30, 23, 37, 29, 31}, {31, 24, 38, 30, 32}, {32, 25, 39, 31, 33},
29   {33, 26, 40, 32, 34}, {34, 27, 41, 33, -1}, {35, 28, 42, -1, 36},
30   {36, 29, 43, 35, 37}, {37, 30, 44, 36, 38}, {38, 31, 45, 37, 39},
31   {39, 32, 46, 38, 40}, {40, 33, 47, 39, 41}, {41, 34, 48, 40, -1},
32   {42, 35, 49, -1, 43}, {43, 36, 50, 42, 44}, {44, 37, 51, 43, 45},
33   {45, 38, 52, 44, 46}, {46, 39, 53, 45, 47}, {47, 40, 54, 46, 48},
34   {48, 41, 55, 47, -1}, {49, 42, -1, -1, 50}, {50, 43, -1, 49, 51},
35   {51, 44, -1, 50, 52}, {52, 45, -1, 51, 53}, {53, 46, -1, 52, 54},
36   {54, 47, -1, 53, 55}, {55, 48, -1, 54, -1}
37 };
38 #elif defined GC_62
39 int core2test[62][NUM_CORES2TEST] = {
40   { 0, -1,  6, -1,  1}, { 1, -1,  7,  0,  2}, { 2, -1,  8,  1,  3},
41   { 3, -1,  9,  2,  4}, { 4, -1, 10,  3,  5}, { 5, -1, 11,  4, -1},
42   { 6,  0, 14, -1,  7}, { 7,  1, 15,  6,  8}, { 8,  2, 16,  7,  9},
43   { 9,  3, 17,  8, 10}, {10,  4, 18,  9, 11}, {11,  5, 19, 10, 12},
44   {12, -1, 20, 11, 13}, {13, -1, 21, 12, -1}, {14,  6, 22, -1, 15},
45   {15,  7, 23, 14, 16}, {16,  8, 24, 15, 17}, {17,  9, 25, 16, 18},
46   {18, 10, 26, 17, 19}, {19, 11, 27, 18, 20}, {20, 12, 28, 19, 21},
47   {21, 13, 29, 28, -1}, {22, 14, 30, -1, 23}, {23, 15, 31, 22, 24},
48   {24, 16, 32, 23, 25}, {25, 17, 33, 24, 26}, {26, 18, 34, 25, 27},
49   {27, 19, 35, 26, 28}, {28, 20, 36, 27, 29}, {29, 21, 37, 28, -1},
50   {30, 22, 38, -1, 31}, {31, 23, 39, 30, 32}, {32, 24, 40, 31, 33},
51   {33, 25, 41, 32, 34}, {34, 26, 42, 33, 35}, {35, 27, 43, 34, 36},
52   {36, 28, 44, 35, 37}, {37, 29, 45, 36, -1}, {38, 30, 46, -1, 39},
53   {39, 31, 47, 38, 40}, {40, 32, 48, 39, 41}, {41, 33, 49, 40, 42},
54   {42, 34, 50, 41, 43}, {43, 35, 51, 42, 44}, {44, 36, 52, 43, 45},
55   {45, 37, 53, 44, -1}, {46, 38, 54, -1, 47}, {47, 39, 55, 46, 48},
56   {48, 40, 56, 47, 49}, {49, 41, 57, 48, 50}, {50, 42, 58, 49, 51},
57   {51, 43, 59, 50, 52}, {52, 44, 60, 51, 53}, {53, 45, 61, 52, -1},
58   {54, 46, -1, -1, 55}, {55, 47, -1, 54, 56}, {56, 48, -1, 55, 57},
59   {57, 49, -1, 56, 59}, {58, 50, -1, 57, 59}, {59, 51, -1, 58, 60},
60   {60, 52, -1, 59, 61}, {61, 53, -1, 60, -1}
61 };
62 #endif // GC_1
63 #elif defined SMEMM
64 unsigned int gcmem_mixed_threshold = 0;
65 unsigned int gcmem_mixed_usedmem = 0;
66 #define NUM_CORES2TEST 13
67 #ifdef GC_1
68 int core2test[1][NUM_CORES2TEST] = {
69   {0, -1, -1, -1, -1, -1, -1, -1, -1}
70 };
71 #elif defined GC_56
72 int core2test[56][NUM_CORES2TEST] = {
73   { 0, -1, -1,  7,  1, -1, -1, -1, -1, 14,  8,  2, -1}, 
74   { 1, -1,  0,  8,  2, -1, -1, -1,  7, 15,  9,  3, -1}, 
75   { 2, -1,  1,  9,  3, -1, -1,  0,  8, 16, 10,  4, -1}, 
76   { 3, -1,  2, 10,  4, -1, -1,  1,  9, 17, 11,  5, -1}, 
77   { 4, -1,  3, 11,  5, -1, -1,  2, 10, 18, 12,  6, -1}, 
78   { 5, -1,  4, 12,  6, -1, -1,  3, 11, 19, 13, -1, -1},
79   { 6, -1,  5, 13, -1, -1, -1,  4, 12, 20, -1, -1, -1}, 
80   { 7,  0, -1, 14,  8, -1, -1, -1, -1, 21, 15,  9,  1}, 
81   { 8,  1,  7, 15,  9, -1,  0, -1, 14, 22, 16, 10,  2}, 
82   { 9,  2,  8, 16, 10, -1,  1,  7, 15, 23, 17, 11,  3}, 
83   {10,  3,  9, 17, 11, -1,  2,  8, 16, 24, 18, 12,  4}, 
84   {11,  4, 10, 18, 12, -1,  3,  9, 17, 25, 19, 13,  5},
85   {12,  5, 11, 19, 13, -1,  4, 10, 18, 26, 20, -1,  6}, 
86   {13,  6, 12, 20, -1, -1,  5, 11, 19, 27, -1, -1, -1}, 
87   {14,  7, -1, 21, 15,  0, -1, -1, -1, 28, 22, 16,  8}, 
88   {15,  8, 14, 22, 16,  1,  7, -1, 21, 29, 23, 17,  9}, 
89   {16,  9, 15, 23, 17,  2,  8, 14, 22, 30, 24, 18, 10}, 
90   {17, 10, 16, 24, 18,  3,  9, 15, 23, 31, 25, 19, 11},
91   {18, 11, 17, 25, 19,  4, 10, 16, 24, 32, 26, 20, 12}, 
92   {19, 12, 18, 26, 20,  5, 11, 17, 25, 33, 27, -1, 13}, 
93   {20, 13, 19, 27, -1,  6, 12, 18, 26, 34, -1, -1, -1}, 
94   {21, 14, -1, 28, 22,  7, -1, -1, -1, 35, 29, 23, 15}, 
95   {22, 15, 21, 29, 23,  8, 14, -1, 28, 36, 30, 24, 16}, 
96   {23, 16, 22, 30, 24,  9, 15, 21, 29, 37, 31, 25, 17},
97   {24, 17, 23, 31, 25, 10, 16, 22, 40, 38, 32, 26, 18}, 
98   {25, 18, 24, 32, 26, 11, 17, 23, 31, 39, 33, 27, 19}, 
99   {26, 19, 25, 33, 27, 12, 18, 24, 32, 40, 34, -1, 20}, 
100   {27, 20, 26, 34, -1, 13, 19, 25, 33, 41, -1, -1, -1}, 
101   {28, 21, -1, 35, 29, 14, -1, -1, -1, 42, 36, 30, 22}, 
102   {29, 22, 28, 36, 30, 15, 21, -1, 35, 43, 37, 31, 23},
103   {30, 23, 29, 37, 31, 16, 22, 28, 36, 44, 38, 32, 24}, 
104   {31, 24, 30, 38, 32, 17, 23, 29, 37, 45, 39, 33, 25}, 
105   {32, 25, 31, 39, 33, 18, 24, 30, 38, 46, 40, 34, 26}, 
106   {33, 26, 32, 40, 34, 19, 25, 31, 39, 47, 41, -1, 27}, 
107   {34, 27, 33, 41, -1, 20, 26, 32, 40, 48, -1, -1, -1}, 
108   {35, 28, -1, 42, 36, 21, -1, -1, -1, 49, 43, 37, 29},
109   {36, 29, 35, 43, 37, 22, 28, -1, 42, 50, 44, 38, 30}, 
110   {37, 30, 36, 44, 38, 23, 29, 35, 43, 51, 45, 39, 31}, 
111   {38, 31, 37, 45, 39, 24, 30, 36, 44, 52, 46, 40, 32}, 
112   {39, 32, 38, 46, 40, 25, 31, 37, 45, 53, 47, 41, 33}, 
113   {40, 33, 39, 47, 41, 26, 32, 38, 46, 54, 48, -1, 34}, 
114   {41, 34, 40, 48, -1, 27, 33, 39, 47, 55, -1, -1, -1},
115   {42, 35, -1, 49, 43, 28, -1, -1, -1, -1, 50, 44, 36}, 
116   {43, 36, 42, 50, 44, 29, 35, -1, 49, -1, 51, 45, 37}, 
117   {44, 37, 43, 51, 45, 30, 36, 42, 50, -1, 52, 46, 38}, 
118   {45, 38, 44, 52, 46, 31, 37, 43, 51, -1, 53, 47, 39}, 
119   {46, 39, 45, 53, 47, 32, 38, 44, 52, -1, 54, 48, 40}, 
120   {47, 40, 46, 54, 48, 33, 39, 45, 53, -1, 55, -1, 41},
121   {48, 41, 47, 55, -1, 34, 40, 46, 54, -1, -1, -1, -1}, 
122   {49, 42, -1, -1, 50, 35, -1, -1, -1, -1, -1, 51, 43}, 
123   {50, 43, 49, -1, 51, 36, 42, -1, -1, -1, -1, 52, 44}, 
124   {51, 44, 50, -1, 52, 37, 43, 49, -1, -1, -1, 53, 45}, 
125   {52, 45, 51, -1, 53, 38, 44, 50, -1, -1, -1, 54, 46}, 
126   {53, 46, 52, -1, 54, 39, 45, 51, -1, -1, -1, 55, 47},
127   {54, 47, 53, -1, 55, 40, 46, 52, -1, -1, -1, -1, 48}, 
128   {55, 48, 54, -1, -1, 41, 47, 53, -1, -1, -1, -1, -1}
129 };
130 #elif defined GC_62
131 int core2test[62][NUM_CORES2TEST] = {
132   { 0, -1, -1,  6,  1, -1, -1, -1, -1, 14,  7,  2, -1}, 
133   { 1, -1,  0,  7,  2, -1, -1, -1,  6, 15,  8,  3, -1}, 
134   { 2, -1,  1,  8,  3, -1, -1,  0,  7, 16,  9,  4, -1}, 
135   { 3, -1,  2,  9,  4, -1, -1,  1,  8, 17, 10,  5, -1}, 
136   { 4, -1,  3, 10,  5, -1, -1,  2,  9, 18,  11, -1, -1}, 
137   { 5, -1,  4, 11, -1, -1, -1,  3, 10, 19, 12, -1, -1},
138   { 6,  0, -1, 14,  7, -1, -1, -1, -1, 22, 15,  8,  1}, 
139   { 7,  1,  6, 15,  8, -1,  0, -1, 14, 23, 16,  9,  2}, 
140   { 8,  2,  7, 16,  9, -1,  1,  6, 15, 24, 17, 10,  3}, 
141   { 9,  3,  8, 17, 10, -1,  2,  7, 16, 25, 18, 11,  4}, 
142   {10,  4,  9, 18, 11, -1,  3,  8, 17, 26, 19, 12,  5}, 
143   {11,  5, 10, 19, 12, -1,  4,  9, 18, 27, 20, 13, -1},
144   {12, -1, 11, 20, 13, -1,  5, 10, 19, 28, 21, -1, -1}, 
145   {13, -1,  12, 21, -1, -1, -1, 11, 20, 29, -1, -1, -1}, 
146   {14,  6, -1, 22, 15,  0, -1, -1, -1, 30, 23, 16,  7}, 
147   {15,  7, 14, 23, 16,  1,  6, -1, 22, 31, 24, 17,  8}, 
148   {16,  8, 15, 24, 17,  2,  7, 14, 23, 32, 25, 18,  9}, 
149   {17,  9, 16, 25, 18,  3,  8, 15, 24, 33, 26, 19, 10},
150   {18, 10, 17, 26, 19,  4,   9, 16, 25, 34, 27, 20, 11}, 
151   {19, 11, 18, 27, 20,  5, 10, 17, 26, 35, 28, 21, 12}, 
152   {20, 12, 19, 28, 21, -1, 11, 18, 27, 36, 29, -1, 13}, 
153   {21, 13, 28, 29, -1, -1, 12, 19, 28, 37, -1, -1, -1}, 
154   {22, 14, -1, 30, 23,  6, -1, -1, -1, 38, 31, 24, 15}, 
155   {23, 15, 22, 31, 24,  7, 14, -1, 30, 39, 32, 25, 16},
156   {24, 16, 23, 32, 25,  8, 15, 22, 31, 40, 33, 26, 17}, 
157   {25, 17, 24, 33, 26,  9, 16, 23, 32, 41, 34, 27, 18}, 
158   {26, 18, 25, 34, 27, 10, 17, 24, 33, 42, 35, 28, 19}, 
159   {27, 19, 26, 35, 28, 11, 18, 25, 34, 43, 36, 29, 20}, 
160   {28, 20, 27, 36, 29, 12, 19, 26, 35, 44, 37, -1, 21}, 
161   {29, 21, 28, 37, -1, 13, 20, 27, 36, 45, -1, -1, -1},
162   {30, 22, -1, 38, 31, 14, -1, -1, -1, 46, 39, 32, 23}, 
163   {31, 23, 30, 39, 32, 15, 22, -1, 38, 47, 40, 33, 24}, 
164   {32, 24, 31, 40, 33, 16, 23, 30, 39, 48, 41, 34, 25}, 
165   {33, 25, 32, 41, 34, 17, 24, 31, 40, 49, 42, 35, 26}, 
166   {34, 26, 33, 42, 35, 18, 25, 32, 41, 50, 43, 36, 27}, 
167   {35, 27, 34, 43, 36, 19, 26, 33, 42, 51, 44, 37, 28},
168   {36, 28, 35, 44, 37, 20, 27, 34, 43, 52, 45, -1, 29}, 
169   {37, 29, 36, 45, -1, 21, 28, 35, 44, 53, -1, -1, -1}, 
170   {38, 30, -1, 46, 39, 22, -1, -1, -1, 54, 47, 40, 31}, 
171   {39, 31, 38, 47, 40, 23, 30, -1, 46, 55, 48, 41, 32}, 
172   {40, 32, 39, 48, 41, 24, 31, 38, 47, 56, 49, 42, 33}, 
173   {41, 33, 40, 49, 42, 25, 32, 39, 48, 57, 50, 43, 34},
174   {42, 34, 41, 50, 43, 26, 33, 40, 49, 58, 51, 44, 35}, 
175   {43, 35, 42, 51, 44, 27, 34, 41, 50, 59, 52, 45, 36}, 
176   {44, 36, 43, 52, 45, 28, 35, 42, 51, 60, 53, -1, 37}, 
177   {45, 37, 44, 53, -1, 29, 36, 43, 52, 61, -1, -1}, 
178   {46, 38, -1, 54, 47, 30, -1, -1, -1, -1, 55, 48, 39}, 
179   {47, 39, 46, 55, 48, 31, 38, -1, 54, -1, 56, 49, 40},
180   {48, 40, 47, 56, 49, 32, 39, 46, 55 -1, 57, 50, 41}, 
181   {49, 41, 48, 57, 50, 33, 40, 47, 56, -1, 58, 51, 42}, 
182   {50, 42, 49, 58, 51, 34, 41, 48, 57, -1, 59, 52, 43}, 
183   {51, 43, 50, 59, 52, 35, 42, 49, 58, -1, 60, 53, 44}, 
184   {52, 44, 51, 60, 53, 36, 43, 50, 59, -1, 61, -1, 45}, 
185   {53, 45, 52, 61, -1, 37, 44, 51, 60, -1, -1, -1, -1},
186   {54, 46, -1, -1, 55, 38, -1, -1, -1, -1, -1, 56, 47}, 
187   {55, 47, 54, -1, 56, 39, 46, -1, -1, -1, -1, 57, 48}, 
188   {56, 48, 55, -1, 57, 40, 47, 54, -1, -1, -1, 58, 49}, 
189   {57, 49, 56, -1, 58, 41, 48, 55, -1, -1, -1, 59, 50}, 
190   {58, 50, 57, -1, 59, 42, 49, 56, -1, -1, -1, 60, 51}, 
191   {59, 51, 58, -1, 60, 43, 50, 57, -1, -1, -1, 61, 52},
192   {60, 52, 59, -1, 61, 44, 51, 58, -1, -1, -1, -1, 53}, 
193   {61, 53, 60, -1, -1, 45, 52, 59, -1, -1, -1, -1, -1}
194 };
195 #endif // GC_1
196 #endif // SMEMF
197
198 INLINE void setupsmemmode(void) {
199 #ifdef SMEML
200   // Only allocate local mem chunks to each core.
201   // If a core has used up its local shared memory, start gc.
202   bamboo_smem_mode = SMEMLOCAL;
203 #elif defined SMEMF
204   // Allocate the local shared memory to each core with the highest priority,
205   // if a core has used up its local shared memory, try to allocate the 
206   // shared memory that belong to its neighbours, if also failed, start gc.
207   bamboo_smem_mode = SMEMFIXED;
208 #elif defined SMEMM
209   // Allocate the local shared memory to each core with the highest priority,
210   // if a core has used up its local shared memory, try to allocate the 
211   // shared memory that belong to its neighbours first, if failed, check 
212   // current memory allocation rate, if it has already reached the threshold,
213   // start gc, otherwise, allocate the shared memory globally.  If all the 
214   // shared memory has been used up, start gc.
215   bamboo_smem_mode = SMEMMIXED;
216 #elif defined SMEMG
217   // Allocate all the memory chunks globally, do not consider the host cores
218   // When all the shared memory are used up, start gc.
219   bamboo_smem_mode = SMEMGLOBAL;
220 #else
221   // defaultly using local mode
222   bamboo_smem_mode = SMEMLOCAL;
223 #endif // SMEML
224 } // void setupsmemmode(void)
225
226 // Only allocate local mem chunks to each core.
227 // If a core has used up its local shared memory, start gc.
228 void * localmalloc_I(int coren,
229                      int isize,
230                      int * allocsize) {
231   void * mem = NULL;
232   int gccorenum = (coren < NUMCORES4GC) ? (coren) : (coren % NUMCORES4GC);
233   int i = 0;
234   int j = 0;
235   int tofindb = gc_core2block[2*gccorenum+i]+(NUMCORES4GC*2)*j;
236   int totest = tofindb;
237   int bound = BAMBOO_SMEM_SIZE_L;
238   int foundsmem = 0;
239   int size = 0;
240   do {
241     bound = (totest < NUMCORES4GC) ? BAMBOO_SMEM_SIZE_L : BAMBOO_SMEM_SIZE;
242     int nsize = bamboo_smemtbl[totest];
243     bool islocal = true;
244     if(nsize < bound) {
245       bool tocheck = true;
246       // have some space in the block
247       if(totest == tofindb) {
248                 // the first partition
249                 size = bound - nsize;
250       } else if(nsize == 0) {
251                 // an empty partition, can be appended
252                 size += bound;
253       } else {
254                 // not an empty partition, can not be appended
255                 // the last continuous block is not big enough, go to check the next
256                 // local block
257                 islocal = true;
258                 tocheck = false;
259       } // if(totest == tofindb) else if(nsize == 0) else ...
260       if(tocheck) {
261                 if(size >= isize) {
262                   // have enough space in the block, malloc
263                   foundsmem = 1;
264                   break;
265                 } else {
266                   // no enough space yet, try to append next continuous block
267                   islocal = false;
268                 }  // if(size > isize) else ...
269       }  // if(tocheck)
270     } // if(nsize < bound)
271     if(islocal) {
272       // no space in the block, go to check the next block
273       i++;
274       if(2==i) {
275                 i = 0;
276                 j++;
277       }
278       tofindb = totest = gc_core2block[2*gccorenum+i]+(NUMCORES4GC*2)*j;
279     } else {
280       totest += 1;
281     }  // if(islocal) else ...
282     if(totest > gcnumblock-1-bamboo_reserved_smem) {
283       // no more local mem, do not find suitable block
284       foundsmem = 2;
285       break;
286     }  // if(totest > gcnumblock-1-bamboo_reserved_smem) ...
287   } while(true);
288
289   if(foundsmem == 1) {
290     // find suitable block
291     mem = gcbaseva+bamboo_smemtbl[tofindb]+((tofindb<NUMCORES4GC) ?
292           (BAMBOO_SMEM_SIZE_L*tofindb) : (BAMBOO_LARGE_SMEM_BOUND+
293           (tofindb-NUMCORES4GC)*BAMBOO_SMEM_SIZE));
294     *allocsize = size;
295     // set bamboo_smemtbl
296     for(i = tofindb; i <= totest; i++) {
297       bamboo_smemtbl[i]=(i<NUMCORES4GC)?BAMBOO_SMEM_SIZE_L:BAMBOO_SMEM_SIZE;
298     }
299   } else if(foundsmem == 2) {
300     // no suitable block
301     *allocsize = 0;
302   }
303
304   return mem;
305 } // void * localmalloc_I(int, int, int *)
306
307 #ifdef SMEMF
308 // Allocate the local shared memory to each core with the highest priority,
309 // if a core has used up its local shared memory, try to allocate the 
310 // shared memory that belong to its neighbours, if also failed, start gc.
311 void * fixedmalloc_I(int coren,
312                      int isize,
313                      int * allocsize) {
314   void * mem = NULL;
315   int i = 0;
316   int j = 0;
317   int k = 0;
318   int gccorenum = (coren < NUMCORES4GC) ? (coren) : (coren % NUMCORES4GC);
319   int ii = 1;
320   int tofindb = gc_core2block[2*core2test[gccorenum][k]+i]+(NUMCORES4GC*2)*j;
321   int totest = tofindb;
322   int bound = BAMBOO_SMEM_SIZE_L;
323   int foundsmem = 0;
324   int size = 0;
325   do {
326     bound = (totest < NUMCORES4GC) ? BAMBOO_SMEM_SIZE_L : BAMBOO_SMEM_SIZE;
327     int nsize = bamboo_smemtbl[totest];
328     bool islocal = true;
329     if(nsize < bound) {
330       bool tocheck = true;
331       // have some space in the block
332       if(totest == tofindb) {
333                 // the first partition
334                 size = bound - nsize;
335       } else if(nsize == 0) {
336                 // an empty partition, can be appended
337                 size += bound;
338       } else {
339                 // not an empty partition, can not be appended
340                 // the last continuous block is not big enough, go to check the next
341                 // local block
342                 islocal = true;
343                 tocheck = false;
344       } // if(totest == tofindb) else if(nsize == 0) else ...
345       if(tocheck) {
346                 if(size >= isize) {
347                   // have enough space in the block, malloc
348                   foundsmem = 1;
349                   break;
350                 } else {
351                   // no enough space yet, try to append next continuous block
352                   // TODO may consider to go to next local block?
353                   islocal = false;
354                 }  // if(size > isize) else ...
355       }  // if(tocheck)
356     } // if(nsize < bound)
357     if(islocal) {
358       // no space in the block, go to check the next block
359       i++;
360       if(2==i) {
361                 i = 0;
362                 j++;
363       }
364       tofindb=totest=
365                 gc_core2block[2*core2test[gccorenum][k]+i]+(NUMCORES4GC*2)*j;
366     } else {
367       totest += 1;
368     }  // if(islocal) else ...
369     if(totest > gcnumblock-1-bamboo_reserved_smem) {
370       // no more local mem, do not find suitable block on local mem
371           // try to malloc shared memory assigned to the neighbour cores
372           do{
373                 k++;
374                 if(k >= NUM_CORES2TEST) {
375                   // no more memory available on either coren or its neighbour cores
376                   foundsmem = 2;
377                   goto memsearchresult;
378                 }
379           } while(core2test[gccorenum][k] == -1);
380           i = 0;
381           j = 0;
382           tofindb=totest=
383                 gc_core2block[2*core2test[gccorenum][k]+i]+(NUMCORES4GC*2)*j;
384     }  // if(totest > gcnumblock-1-bamboo_reserved_smem) ...
385   } while(true);
386
387 memsearchresult:
388   if(foundsmem == 1) {
389     // find suitable block
390     mem = gcbaseva+bamboo_smemtbl[tofindb]+((tofindb<NUMCORES4GC) ?
391           (BAMBOO_SMEM_SIZE_L*tofindb) : (BAMBOO_LARGE_SMEM_BOUND+
392           (tofindb-NUMCORES4GC)*BAMBOO_SMEM_SIZE));
393     *allocsize = size;
394     // set bamboo_smemtbl
395     for(i = tofindb; i <= totest; i++) {
396       bamboo_smemtbl[i]=(i<NUMCORES4GC)?BAMBOO_SMEM_SIZE_L:BAMBOO_SMEM_SIZE;
397     }
398   } else if(foundsmem == 2) {
399     // no suitable block
400     *allocsize = 0;
401   }
402
403   return mem;
404 } // void * fixedmalloc_I(int, int, int *)
405 #endif // #ifdef SMEMF
406
407 #ifdef SMEMM
408 // Allocate the local shared memory to each core with the highest priority,
409 // if a core has used up its local shared memory, try to allocate the 
410 // shared memory that belong to its neighbours first, if failed, check 
411 // current memory allocation rate, if it has already reached the threshold,
412 // start gc, otherwise, allocate the shared memory globally.  If all the 
413 // shared memory has been used up, start gc.
414 void * mixedmalloc_I(int coren,
415                      int isize,
416                      int * allocsize) {
417   void * mem = NULL;
418   int i = 0;
419   int j = 0;
420   int k = 0;
421   int gccorenum = (coren < NUMCORES4GC) ? (coren) : (coren % NUMCORES4GC);
422   int ii = 1;
423   int tofindb = gc_core2block[2*core2test[gccorenum][k]+i]+(NUMCORES4GC*2)*j;
424   int totest = tofindb;
425   int bound = BAMBOO_SMEM_SIZE_L;
426   int foundsmem = 0;
427   int size = 0;
428   do {
429     bound = (totest < NUMCORES4GC) ? BAMBOO_SMEM_SIZE_L : BAMBOO_SMEM_SIZE;
430     int nsize = bamboo_smemtbl[totest];
431     bool islocal = true;
432     if(nsize < bound) {
433       bool tocheck = true;
434       // have some space in the block
435       if(totest == tofindb) {
436                 // the first partition
437                 size = bound - nsize;
438       } else if(nsize == 0) {
439                 // an empty partition, can be appended
440                 size += bound;
441       } else {
442                 // not an empty partition, can not be appended
443                 // the last continuous block is not big enough, go to check the next
444                 // local block
445                 islocal = true;
446                 tocheck = false;
447       } // if(totest == tofindb) else if(nsize == 0) else ...
448       if(tocheck) {
449                 if(size >= isize) {
450                   // have enough space in the block, malloc
451                   foundsmem = 1;
452                   break;
453                 } else {
454                   // no enough space yet, try to append next continuous block
455                   // TODO may consider to go to next local block?
456                   islocal = false;
457                 }  // if(size > isize) else ...
458       }  // if(tocheck)
459     } // if(nsize < bound)
460     if(islocal) {
461       // no space in the block, go to check the next block
462       i++;
463       if(2==i) {
464                 i = 0;
465                 j++;
466       }
467       tofindb=totest=
468                 gc_core2block[2*core2test[gccorenum][k]+i]+(NUMCORES4GC*2)*j;
469     } else {
470       totest += 1;
471     }  // if(islocal) else ...
472     if(totest > gcnumblock-1-bamboo_reserved_smem) {
473       // no more local mem, do not find suitable block on local mem
474           // try to malloc shared memory assigned to the neighbour cores
475           do{
476                 k++;
477                 if(k >= NUM_CORES2TEST) {
478                   if(gcmem_mixed_usedmem >= gcmem_mixed_threshold) {
479                         // no more memory available on either coren or its neighbour cores
480                         foundsmem = 2;
481                         goto memmixedsearchresult;
482                   } else {
483                         // try allocate globally
484                         mem = globalmalloc_I(coren, isize, allocsize);
485                         return mem;
486                   }
487                 }
488           } while(core2test[gccorenum][k] == -1);
489           i = 0;
490           j = 0;
491           tofindb=totest=
492                 gc_core2block[2*core2test[gccorenum][k]+i]+(NUMCORES4GC*2)*j;
493     }  // if(totest > gcnumblock-1-bamboo_reserved_smem) ...
494   } while(true);
495
496 memmixedsearchresult:
497   if(foundsmem == 1) {
498     // find suitable block
499     mem = gcbaseva+bamboo_smemtbl[tofindb]+((tofindb<NUMCORES4GC) ?
500           (BAMBOO_SMEM_SIZE_L*tofindb) : (BAMBOO_LARGE_SMEM_BOUND+
501           (tofindb-NUMCORES4GC)*BAMBOO_SMEM_SIZE));
502     *allocsize = size;
503     // set bamboo_smemtbl
504     for(i = tofindb; i <= totest; i++) {
505       bamboo_smemtbl[i]=(i<NUMCORES4GC)?BAMBOO_SMEM_SIZE_L:BAMBOO_SMEM_SIZE;
506     }
507         gcmem_mixed_usedmem += size;
508         if(tofindb == bamboo_free_block) {
509       bamboo_free_block = totest+1;
510     }
511   } else if(foundsmem == 2) {
512     // no suitable block
513     *allocsize = 0;
514   }
515
516   return mem;
517 } // void * mixedmalloc_I(int, int, int *)
518 #endif // #ifdef SMEMM
519
520 // Allocate all the memory chunks globally, do not consider the host cores
521 // When all the shared memory are used up, start gc.
522 void * globalmalloc_I(int coren,
523                       int isize,
524                       int * allocsize) {
525   void * mem = NULL;
526   int tofindb = bamboo_free_block;       //0;
527   int totest = tofindb;
528   int bound = BAMBOO_SMEM_SIZE_L;
529   int foundsmem = 0;
530   int size = 0;
531   if(tofindb > gcnumblock-1-bamboo_reserved_smem) {
532         // Out of shared memory
533     *allocsize = 0;
534     return NULL;
535   }
536   do {
537     bound = (totest < NUMCORES4GC) ? BAMBOO_SMEM_SIZE_L : BAMBOO_SMEM_SIZE;
538     int nsize = bamboo_smemtbl[totest];
539     bool isnext = false;
540     if(nsize < bound) {
541       bool tocheck = true;
542       // have some space in the block
543       if(totest == tofindb) {
544                 // the first partition
545                 size = bound - nsize;
546       } else if(nsize == 0) {
547                 // an empty partition, can be appended
548                 size += bound;
549       } else {
550                 // not an empty partition, can not be appended
551                 // the last continuous block is not big enough, start another block
552                 isnext = true;
553                 tocheck = false;
554       }  // if(totest == tofindb) else if(nsize == 0) else ...
555       if(tocheck) {
556                 if(size >= isize) {
557                   // have enough space in the block, malloc
558                   foundsmem = 1;
559                   break;
560                 }  // if(size > isize)
561       }   // if(tocheck)
562     } else {
563       isnext = true;
564     }  // if(nsize < bound) else ...
565     totest += 1;
566     if(totest > gcnumblock-1-bamboo_reserved_smem) {
567       // no more local mem, do not find suitable block
568       foundsmem = 2;
569       break;
570     }  // if(totest > gcnumblock-1-bamboo_reserved_smem) ...
571     if(isnext) {
572       // start another block
573       tofindb = totest;
574     } // if(islocal)
575   } while(true);
576
577   if(foundsmem == 1) {
578     // find suitable block
579     mem = gcbaseva+bamboo_smemtbl[tofindb]+((tofindb<NUMCORES4GC) ?
580           (BAMBOO_SMEM_SIZE_L*tofindb) : (BAMBOO_LARGE_SMEM_BOUND+
581           (tofindb-NUMCORES4GC)*BAMBOO_SMEM_SIZE));
582     *allocsize = size;
583     // set bamboo_smemtbl
584     for(int i = tofindb; i <= totest; i++) {
585       bamboo_smemtbl[i]=(i<NUMCORES4GC)?BAMBOO_SMEM_SIZE_L:BAMBOO_SMEM_SIZE;
586     }
587     if(tofindb == bamboo_free_block) {
588       bamboo_free_block = totest+1;
589     }
590   } else if(foundsmem == 2) {
591     // no suitable block
592     *allocsize = 0;
593     mem = NULL;
594   }
595
596   return mem;
597 } // void * globalmalloc_I(int, int, int *)
598 #endif // MULTICORE_GC
599
600 // malloc from the shared memory
601 void * smemalloc_I(int coren,
602                    int size,
603                    int * allocsize) {
604   void * mem = NULL;
605 #ifdef MULTICORE_GC
606   int isize = size+(BAMBOO_CACHE_LINE_SIZE);
607
608   // go through the bamboo_smemtbl for suitable partitions
609   switch(bamboo_smem_mode) {
610   case SMEMLOCAL: {
611     mem = localmalloc_I(coren, isize, allocsize);
612     break;
613   }
614
615   case SMEMFIXED: {
616 #ifdef SMEMF
617         mem = fixedmalloc_I(coren, isize, allocsize);
618 #else
619         // not supported yet
620         BAMBOO_EXIT(0xe001);
621 #endif
622     break;
623   }
624
625   case SMEMMIXED: {
626 #ifdef SMEMM
627         mem = mixedmalloc_I(coren, isize, allocsize);
628 #else
629         // not supported yet
630     BAMBOO_EXIT(0xe002);
631 #endif
632     break;
633   }
634
635   case SMEMGLOBAL: {
636     mem = globalmalloc_I(coren, isize, allocsize);
637     break;
638   }
639
640   default:
641     break;
642   }
643
644   if(mem == NULL) {
645 #else 
646   int toallocate = (size>(BAMBOO_SMEM_SIZE)) ? (size) : (BAMBOO_SMEM_SIZE);
647   if(toallocate > bamboo_free_smem_size) {
648         // no enough mem
649         mem = NULL;
650   } else {
651         mem = (void *)bamboo_free_smemp;
652         bamboo_free_smemp = ((void*)bamboo_free_smemp) + toallocate;
653         bamboo_free_smem_size -= toallocate;
654   }
655   *allocsize = toallocate;
656   if(mem == NULL) {
657 #endif // MULTICORE_GC
658     // no enough shared global memory
659     *allocsize = 0;
660 #ifdef MULTICORE_GC
661         if(!gcflag) {
662           gcflag = true;
663           // inform other cores to stop and wait for gc
664           gcprecheck = true;
665           for(int i = 0; i < NUMCORESACTIVE; i++) {
666                 // reuse the gcnumsendobjs & gcnumreceiveobjs
667                 gccorestatus[i] = 1;
668                 gcnumsendobjs[0][i] = 0;
669                 gcnumreceiveobjs[0][i] = 0;
670           }
671           for(int i = 0; i < NUMCORESACTIVE; i++) {
672                 if(i != BAMBOO_NUM_OF_CORE) {
673                   if(BAMBOO_CHECK_SEND_MODE()) {
674                         cache_msg_1(i, GCSTARTPRE);
675                   } else {
676                         send_msg_1(i, GCSTARTPRE, true);
677                   }
678                 }
679           }
680         }
681         return NULL;
682 #else
683     BAMBOO_EXIT(0xe003);
684 #endif
685   }
686   return mem;
687 }  // void * smemalloc_I(int, int, int)
688
689 #endif // MULTICORE