4 #include "multicoreruntime.h"
5 #include "methodheaders.h"
7 #include "runtime_arch.h"
10 extern int classsize[];
11 extern int typearray[];
12 extern int typearray2[];
13 extern int* supertypes[];
16 extern struct genhashtable * activetasks;
24 int instanceofif(int otype, int type) {
31 int num = supertypes[otype][0];
32 for(int i = 1; i < num + 1; i++) {
33 int t = supertypes[otype][i];
34 if(instanceofif(t, type) == 1) {
41 int instanceof(struct ___Object___ *ptr, int type) {
46 if(instanceofif(i, type) == 1) {
53 i=typearray2[i-NUMCLASSES];
59 void initializeexithandler() {
62 /* This function inject failures */
63 void injectinstructionfailure() {
64 // not supported in MULTICORE version
68 #ifdef D___Double______nativeparsedouble____L___String___
69 double CALL01(___Double______nativeparsedouble____L___String___,
70 struct ___String___ * ___str___) {
71 int length=VAR(___str___)->___count___;
72 int maxlength=(length>60) ? 60 : length;
73 char str[maxlength+1];
74 struct ArrayObject * chararray=VAR(___str___)->___value___;
76 int offset=VAR(___str___)->___offset___;
77 for(i=0; i<maxlength; i++) {
79 ((short *)(((char *)&chararray->___length___)+sizeof(int)))[i+offset];
82 double d=0.0; //atof(str); TODO Unimplemented nativeparsedoulbe
87 #ifdef D___Double______nativeparsedouble_____AR_B_I_I
88 double CALL23(___Double______nativeparsedouble_____AR_B_I_I,
93 struct ArrayObject * ___str___) {
94 int maxlength=(length>60)?60:length;
95 char str[maxlength+1];
96 struct ArrayObject * bytearray=VAR(___str___);
98 for(i=0; i<maxlength; i++) {
99 str[i]=(((char *)&bytearray->___length___)+sizeof(int))[i+start];
102 double d=0.0; //atof(str); TODO Unimplemented nativeparsedouble
107 typedef union jvalue {
117 #ifdef D___Double______doubleToRawLongBits____D
118 long long CALL11(___Double______doubleToRawLongBits____D,
120 double ___value___) {
124 #if defined(__IEEE_BYTES_LITTLE_ENDIAN)
125 /* On little endian ARM processors when using FPA, word order of
126 doubles is still big endian. So take that into account here. When
127 using VFP, word order of doubles follows byte order. */
128 #define SWAP_DOUBLE(a) (((a) << 32) | (((a) >> 32) & 0x00000000ffffffff))
129 val.j = SWAP_DOUBLE(val.j);
136 #ifdef D___Double______longBitsToDouble____J
137 double CALL11(___Double______longBitsToDouble____J,
138 long long ___bits___,
139 long long ___bits___) {
143 #if defined(__IEEE_BYTES_LITTLE_ENDIAN)
145 #define SWAP_DOUBLE(a) (((a) << 32) | (((a) >> 32) & 0x00000000ffffffff))
147 val.j = SWAP_DOUBLE(val.j);
154 #ifdef D___String______convertdoubletochar____D__AR_C
155 int CALL12(___String______convertdoubletochar____D__AR_C,
158 struct ArrayObject * ___chararray___) {
159 int length=VAR(___chararray___)->___length___;
162 int num=snprintf(str, length, "%f",___val___);
165 for(i=0; i<length; i++) {
166 ((short *)(((char *)&VAR(___chararray___)->___length___)+sizeof(int)))[i]=
172 int CALL12(___String______convertdoubletochar____D__AR_C,
175 struct ArrayObject ___chararray___) {
180 #ifdef D___System______deepArrayCopy____L___Object____L___Object___
181 void deepArrayCopy(struct ___Object___ * dst,
182 struct ___Object___ * src) {
183 int dsttype=((int *)dst)[0];
184 int srctype=((int *)src)[0];
185 if (dsttype<NUMCLASSES||srctype<NUMCLASSES||srctype!=dsttype)
187 struct ArrayObject *aodst=(struct ArrayObject *)dst;
188 struct ArrayObject *aosrc=(struct ArrayObject *)src;
189 int dstlength=aodst->___length___;
190 int srclength=aosrc->___length___;
191 if (dstlength!=srclength)
193 unsigned INTPTR *pointer=pointerarray[srctype];
195 int elementsize=classsize[srctype];
196 int size=srclength*elementsize;
198 memcpy(((char *)&aodst->___length___)+sizeof(int) ,
199 ((char *)&aosrc->___length___)+sizeof(int), size);
203 for(i=0;i<srclength;i++) {
204 struct ___Object___ * ptr=
205 ((struct ___Object___**)(((char*)&aosrc->___length___)+sizeof(int)))[i];
206 int ptrtype=((int *)ptr)[0];
207 if (ptrtype>=NUMCLASSES) {
208 struct ___Object___ * dstptr=((struct ___Object___**)
209 (((char*)&aodst->___length___)+sizeof(int)))[i];
210 deepArrayCopy(dstptr,ptr);
213 ((struct ___Object___ **)
214 (((char*) &aodst->___length___)+sizeof(int)))[i]=ptr;
220 void CALL02(___System______deepArrayCopy____L___Object____L___Object___,
221 struct ___Object___ * ___dst___,
222 struct ___Object___ * ___src___) {
223 deepArrayCopy(VAR(___dst___), VAR(___src___));
227 #ifdef D___System______arraycopy____L___Object____I_L___Object____I_I
228 void arraycopy(struct ___Object___ *src,
230 struct ___Object___ *dst,
233 int dsttype=((int *)dst)[0];
234 int srctype=((int *)src)[0];
236 //not an array or type mismatch
237 if (dsttype<NUMCLASSES||srctype<NUMCLASSES/*||srctype!=dsttype*/)
240 struct ArrayObject *aodst=(struct ArrayObject *)dst;
241 struct ArrayObject *aosrc=(struct ArrayObject *)src;
242 int dstlength=aodst->___length___;
243 int srclength=aosrc->___length___;
247 if (srcPos+length>srclength)
249 if (destPos+length>dstlength)
252 unsigned INTPTR *pointer=pointerarray[srctype];
254 int elementsize=classsize[srctype];
255 int size=length*elementsize;
257 memcpy(((char *)&aodst->___length___)+sizeof(int)+destPos*elementsize,
258 ((char *)&aosrc->___length___)+sizeof(int)+srcPos*elementsize, size);
262 for(i=0;i<length;i++) {
263 struct ___Object___ * ptr=((struct ___Object___**)
264 (((char*)&aosrc->___length___)+sizeof(int)))[i+srcPos];
265 int ptrtype=((int *)ptr)[0];
267 ((struct ___Object___ **)
268 (((char*) &aodst->___length___)+sizeof(int)))[i+destPos]=ptr;
273 void CALL35(___System______arraycopy____L___Object____I_L___Object____I_I,
277 struct ___Object___ * ___src___,
279 struct ___Object___ * ___dst___,
282 arraycopy(VAR(___src___), ___srcPos___, VAR(___dst___), ___destPos___,
287 void CALL11(___System______exit____I,
290 // gc_profile mode, output gc prfiling data
292 if(STARTUPCORE == BAMBOO_NUM_OF_CORE) {
293 CACHEADAPT_DISABLE_TIMER();
294 GC_OUTPUT_PROFILE_DATA();
297 BAMBOO_EXIT_APP(___status___);
300 #ifdef D___Vector______removeElement_____AR_L___Object____I_I
301 void CALL23(___Vector______removeElement_____AR_L___Object____I_I,
304 struct ArrayObject * ___array___,
307 char* offset=((char *)(&VAR(___array___)->___length___))
308 +sizeof(unsigned int)+sizeof(void *)*___index___;
309 memmove(offset, offset+sizeof(void *),
310 (___size___-___index___-1)*sizeof(void *));
314 void CALL11(___System______printI____I,
317 BAMBOO_PRINT(0x1111);
318 BAMBOO_PRINT_REG(___status___);
321 long long CALL00(___System______currentTimeMillis____) {
322 //TilePro64 is 700mHz
323 return ((unsigned long long)BAMBOO_GET_EXE_TIME())/700000;
326 void CALL00(___System______setgcprofileflag____) {
329 extern volatile bool gc_profile_flag;
330 gc_profile_flag = true;
335 void CALL00(___System______resetgcprofileflag____) {
338 extern volatile bool gc_profile_flag;
339 gc_profile_flag = false;
344 void CALL01(___System______printString____L___String___,
345 struct ___String___ * ___s___) {
348 struct ArrayObject * chararray=VAR(___s___)->___value___;
350 int offset=VAR(___s___)->___offset___;
352 for(i=0; i<VAR(___s___)->___count___; i++) {
354 ((short *)(((char *)&chararray->___length___)+sizeof(int)))[i+offset];
361 /* Object allocation function */
364 void * allocate_new(void * ptr,
366 struct ___Object___ * v=
367 (struct ___Object___*)FREEMALLOC((struct garbagelist*) ptr,classsize[type]);
376 extern unsigned int gc_num_obj;
382 /* Array allocation function */
384 struct ArrayObject * allocate_newarray(void * ptr,
387 struct ArrayObject * v=(struct ArrayObject *)FREEMALLOC(
388 (struct garbagelist*)ptr,
389 sizeof(struct ArrayObject)+length*classsize[type]);
398 v->___length___=length;
401 extern unsigned int gc_num_obj;
408 void * allocate_new(int type) {
409 struct ___Object___ * v=FREEMALLOC(classsize[type]);
419 /* Array allocation function */
421 struct ArrayObject * allocate_newarray(int type,
423 struct ArrayObject * v=FREEMALLOC(
424 sizeof(struct ArrayObject)+length*classsize[type]);
430 v->___length___=length;
436 /* Converts C character arrays into Java strings */
438 __attribute__((malloc)) struct ___String___ * NewStringShort(void * ptr,
442 __attribute__((malloc)) struct ___String___ * NewStringShort(const short *str,
447 struct ArrayObject * chararray=
448 allocate_newarray((struct garbagelist *)ptr, CHARARRAYTYPE, length);
449 INTPTR ptrarray[]={1, (INTPTR) ptr, (INTPTR) chararray};
450 struct ___String___ * strobj=
451 allocate_new((struct garbagelist *) &ptrarray, STRINGTYPE);
452 chararray=(struct ArrayObject *) ptrarray[2];
454 struct ArrayObject * chararray=allocate_newarray(CHARARRAYTYPE, length);
455 struct ___String___ * strobj=allocate_new(STRINGTYPE);
457 strobj->___value___=chararray;
458 strobj->___count___=length;
459 strobj->___offset___=0;
461 for(i=0; i<length; i++) {
462 ((short *)(((char *)&chararray->___length___)+sizeof(int)))[i]=str[i];
467 /* Converts C character arrays into Java strings */
469 struct ___String___ * NewString(void * ptr,
473 struct ___String___ * NewString(const char *str,
478 struct ArrayObject * chararray=
479 allocate_newarray((struct garbagelist *)ptr, CHARARRAYTYPE, length);
480 int ptrarray[]={1, (int) ptr, (int) chararray};
481 struct ___String___ * strobj=
482 allocate_new((struct garbagelist *) &ptrarray, STRINGTYPE);
483 chararray=(struct ArrayObject *) ptrarray[2];
485 struct ArrayObject * chararray=allocate_newarray(CHARARRAYTYPE, length);
486 struct ___String___ * strobj=allocate_new(STRINGTYPE);
488 strobj->___value___=chararray;
489 strobj->___count___=length;
490 strobj->___offset___=0;
492 for(i=0; i<length; i++) {
493 ((short*)(((char*)&chararray->___length___)+sizeof(int)))[i]=(short)str[i];
498 /* Generated code calls this if we fail a bounds check */
500 void failedboundschk(int num) {
502 printf("Array out of bounds\n");
512 printf("Array out of bounds\n");
513 longjmp(error_handler,2);
520 /* Generated code calls this if we fail null ptr chk */
521 void failednullptr(void * ptr) {
524 //print out current stack
527 struct garbagelist * stackptr = (struct garbagelist *)ptr;
528 while(stackptr!=NULL) {
529 tprintf("Stack %d: \n\t", j);
530 for(i=0; i<stackptr->size; i++) {
531 if(stackptr->array[i] != NULL) {
532 tprintf("%x, ", stackptr->array[i]);
538 stackptr=stackptr->next;
543 printf("NULL ptr\n");
553 printf("NULL ptr\n");
554 longjmp(error_handler,2);
561 /* Abort task call */
565 printf("Aborting\n");
566 longjmp(error_handler,4);
569 printf("Aborting\n");
574 INLINE void initruntimedata() {
576 // initialize the arrays
577 if(STARTUPCORE == BAMBOO_NUM_OF_CORE) {
578 // startup core to initialize corestatus[]
579 for(i = 0; i < NUMCORESACTIVE; ++i) {
582 numreceiveobjs[i] = 0;
589 self_numsendobjs = 0;
590 self_numreceiveobjs = 0;
592 for(i = 0; i < BAMBOO_MSG_BUF_LENGTH; ++i) {
597 //msglength = BAMBOO_MSG_BUF_LENGTH;
599 for(i = 0; i < BAMBOO_OUT_BUF_LENGTH; ++i) {
605 isMsgHanging = false;
608 bamboo_cur_msp = NULL;
609 bamboo_smem_size = 0;
614 INITMULTICOREGCDATA();
618 bamboo_current_thread = 0;
624 INLINE void disruntimedata() {
625 DISMULTICOREGCDATA();
627 BAMBOO_LOCAL_MEM_CLOSE();
628 BAMBOO_SHARE_MEM_CLOSE();
631 INLINE void recordtotalexetime() {
633 totalexetime = BAMBOO_GET_EXE_TIME()-bamboo_start_time;
635 BAMBOO_PRINT(BAMBOO_GET_EXE_TIME()-bamboo_start_time);
637 BAMBOO_PRINT_REG(gc_num_flush_dtlb);
639 #ifndef BAMBOO_MEMPROF
640 BAMBOO_PRINT(0xbbbbbbbb);
645 INLINE void getprofiledata_I() {
646 //profile mode, send msgs to other cores to request pouring out progiling data
648 BAMBOO_ENTER_CLIENT_MODE_FROM_RUNTIME();
649 for(i = 1; i < NUMCORESACTIVE; ++i) {
650 // send profile request msg to core i
651 send_msg_2(i, PROFILEOUTPUT, totalexetime);
654 // pour profiling data on startup core
658 BAMBOO_ENTER_RUNTIME_MODE_FROM_CLIENT();
659 profilestatus[BAMBOO_NUM_OF_CORE] = 0;
660 // check the status of all cores
661 for(i = 0; i < NUMCORESACTIVE; ++i) {
662 if(profilestatus[i] != 0) {
666 if(i != NUMCORESACTIVE) {
668 BAMBOO_ENTER_CLIENT_MODE_FROM_RUNTIME();
672 BAMBOO_ENTER_CLIENT_MODE_FROM_RUNTIME();
679 INLINE void checkCoreStatus() {
683 (waitconfirm && (numconfirm == 0))) {
684 BAMBOO_ENTER_RUNTIME_MODE_FROM_CLIENT();
685 corestatus[BAMBOO_NUM_OF_CORE] = 0;
686 numsendobjs[BAMBOO_NUM_OF_CORE] = self_numsendobjs;
687 numreceiveobjs[BAMBOO_NUM_OF_CORE] = self_numreceiveobjs;
688 // check the status of all cores
689 for(i = 0; i < NUMCORESACTIVE; ++i) {
690 if(corestatus[i] != 0) {
694 if(i == NUMCORESACTIVE) {
695 // check if the sum of send objs and receive obj are the same
696 // yes->check if the info is the latest; no->go on executing
698 for(i = 0; i < NUMCORESACTIVE; ++i) {
699 sumsendobj += numsendobjs[i];
701 for(i = 0; i < NUMCORESACTIVE; ++i) {
702 sumsendobj -= numreceiveobjs[i];
704 if(0 == sumsendobj) {
706 // the first time found all cores stall
707 // send out status confirm msg to all other cores
708 // reset the corestatus array too
709 corestatus[BAMBOO_NUM_OF_CORE] = 1;
711 numconfirm = NUMCORESACTIVE - 1;
712 BAMBOO_ENTER_CLIENT_MODE_FROM_RUNTIME();
713 for(i = 1; i < NUMCORESACTIVE; ++i) {
715 // send status confirm msg to core i
716 send_msg_1(i, STATUSCONFIRM);
720 // all the core status info are the latest
721 // terminate; for profiling mode, send request to all
722 // other cores to pour out profiling data
723 recordtotalexetime();
725 CACHEADAPT_DISABLE_TIMER();
726 GC_OUTPUT_PROFILE_DATA();
728 BAMBOO_ENTER_CLIENT_MODE_FROM_RUNTIME();
729 terminate(); // All done.
732 // still some objects on the fly on the network
733 // reset the waitconfirm and numconfirm
738 // not all cores are stall, keep on waiting
742 BAMBOO_ENTER_CLIENT_MODE_FROM_RUNTIME();
746 // main function for each core
747 inline void run(int argc, char** argv) {
749 bool sendStall = false;
751 bool tocontinue = false;
753 corenum = BAMBOO_GET_NUM_OF_CORE();
755 // initialize runtime data structures
758 // other architecture related initialization
762 CACHEADAPT_ENABLE_TIMER();
764 initializeexithandler();
766 // main process of the execution module
767 if(BAMBOO_NUM_OF_CORE > NUMCORESACTIVE - 1) {
769 // non-executing cores, only processing communications
775 /* Create queue of active tasks */
776 activetasks= genallocatehashtable((unsigned int (*)(void *)) &hashCodetpd,
777 (int (*)(void *,void *)) &comparetpd);
779 /* Process task information */
782 if(STARTUPCORE == BAMBOO_NUM_OF_CORE) {
783 /* Create startup object */
784 createstartupobject(argc, argv);
788 if(STARTUPCORE == BAMBOO_NUM_OF_CORE) {
790 // run the initStaticAndGlobal method to initialize the static blocks and
792 initStaticAndGlobal();
794 // run the main method in the specified mainclass
795 mgc_main(argc, argv);
802 // check if there are new active tasks can be executed
808 while(receiveObject_I() != -1) {
811 // check if there are some pending objects,
812 // if yes, enqueue them and executetasks again
813 tocontinue = checkObjQueue();
815 tocontinue = trystartthread();
823 if(STARTUPCORE == BAMBOO_NUM_OF_CORE) {
834 // wait for some time
840 // send StallMsg to startup core
842 send_msg_4(STARTUPCORE,TRANSTALL,BAMBOO_NUM_OF_CORE,self_numsendobjs,self_numreceiveobjs);