#include "../BasicCompiler_Common/common.h" #ifdef _AMD64_ #include "../BasicCompiler64/opcode.h" #else #include "../BasicCompiler32/opcode.h" #endif extern HANDLE hHeap; int GetAlignment(CClass *pobj_c){ int i; int alignment,member_size; if(pobj_c->vtbl_num) alignment=PTR_SIZE; else alignment=0; for(i=0;iiMemberNum;i++){ if(pobj_c->ppobj_Member[i]->TypeInfo.type==DEF_OBJECT){ //メンバクラスのアラインメントを取得 member_size=GetAlignment(pobj_c->ppobj_Member[i]->TypeInfo.u.pobj_Class); } else{ //メンバサイズを取得 member_size=GetTypeSize(pobj_c->ppobj_Member[i]->TypeInfo.type,pobj_c->ppobj_Member[i]->TypeInfo.u.lpIndex); } //アラインメントをセット if(alignmentiAlign) alignment=pobj_c->iAlign; return alignment; } int GetSizeOfClassMember(CClass *pobj_c,char *pMemberName,int *pMemberNum){ int i,i2,offset; //仮想関数が存在する場合は関数リストへのポインタのサイズを追加 if(pobj_c->vtbl_num) offset=PTR_SIZE; else offset=0; int alignment; if(pobj_c->iAlign) alignment=pobj_c->iAlign; else alignment=1; int iMaxAlign=0; for(i=0;iiMemberNum;i++){ //メンバ変数の型サイズを取得 i2=GetTypeSize(pobj_c->ppobj_Member[i]->TypeInfo.type,pobj_c->ppobj_Member[i]->TypeInfo.u.lpIndex); if(i2==-1) return -1; //アラインメントを算出 int member_size; if(pobj_c->ppobj_Member[i]->TypeInfo.type==DEF_OBJECT){ //メンバクラスのアラインメントを取得 member_size=GetAlignment(pobj_c->ppobj_Member[i]->TypeInfo.u.pobj_Class); } else{ //メンバサイズを取得 member_size=i2; } if(iMaxAligniAlign&&pobj_c->iAlignppobj_Member[i]->name,pMemberName)==0){ if(pMemberNum) *pMemberNum=i; return offset; } } //配列を考慮したメンバサイズを取得 member_size=i2 * JumpSubScripts(pobj_c->ppobj_Member[i]->SubScripts); //メンバサイズを加算 offset+= member_size; } if(iMaxAlignname,Parameter); if(!psi){ if(Parameter[0]) SetError(113,pobj_c->name,cp); return; } char temporary[VN_SIZE]; if(SubScripts[0]!=-1){ int ss[MAX_ARRAYDIM]; memset(ss,0,MAX_ARRAYDIM*sizeof(int)); while(1){ int i3; for(i3=0;;i3++){ if(SubScripts[i3]==-1) break; if(ss[i3]>SubScripts[i3]){ ss[i3]=0; ss[i3+1]++; } else break; } if(SubScripts[i3]==-1) break; sprintf(temporary,"%s[%d",ObjectName,ss[0]); for(i3=1;;i3++){ if(SubScripts[i3]==-1) break; sprintf(temporary+lstrlen(temporary),",%d",ss[i3]); } lstrcat(temporary,"]"); LONG_PTR lp; sprintf(temporary+lstrlen(temporary),".%s",pobj_c->name); CallProc(PROC_DEFAULT, psi, temporary, Parameter, &lp); ss[0]++; //ネイティブコードバッファの再確保 extern int obp_AllocSize; if(obp_AllocSizename); CallProc(PROC_DEFAULT, psi, temporary, Parameter, &lp); } } void CallDestrouctorsOfScope(void){ extern BOOL bCompilingGlobal; VARIABLE *pVar; int num; if(bCompilingGlobal){ //グローバルオブジェクトの解放処理 extern VARIABLE *GlobalVar; extern int MaxGlobalVarNum; pVar=GlobalVar; num=MaxGlobalVarNum; } else{ //ローカルオブジェクトの解放処理 extern VARIABLE *LocalVar; extern int MaxLocalVarNum; pVar=LocalVar; num=MaxLocalVarNum; } int i3,i4,i5; int indexSystemGC=-1; for(i3=0;i3DestructorMemberSubIndex; if(i5!=-1) Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,0,pVar[i3].name,DEF_OBJECT); //メモリを解放する #ifdef _AMD64_ //x64ビットコード //mov rcx,qword ptr[rsp+offset] op_mov_RM(sizeof(_int64),REG_RCX,REG_RSP, -pVar[i3].offset, MOD_BASE_DISP32); obp-=sizeof(long); AddLocalVarAddrSchedule(); obp+=sizeof(long); #else //x86コード //mov ecx,dword ptr[ebp+offset] op_mov_RM(sizeof(long),REG_ECX,REG_EBP,-pVar[i3].offset,MOD_BASE_DISP32); obp-=sizeof(long); AddLocalVarAddrSchedule(); obp+=sizeof(long); //push ecx op_push(REG_ECX); #endif //call free extern SUBINFO *pSub_free; op_call(pSub_free); } else if(pVar[i3].type==DEF_OBJECT&&pVar[i3].fRef==0){ //デストラクタの呼び出し i5=pVar[i3].u.pobj_c->DestructorMemberSubIndex; if(i5!=-1){ int ss[MAX_ARRAYDIM]; memset(ss,0,MAX_ARRAYDIM*sizeof(int)); if(pVar[i3].SubScripts[0]!=-1){ while(1){ for(i4=0;;i4++){ if(pVar[i3].SubScripts[i4]==-1) break; if(ss[i4]>pVar[i3].SubScripts[i4]){ ss[i4]=0; ss[i4+1]++; } else break; } if(pVar[i3].SubScripts[i4]==-1) break; char temporary[VN_SIZE]; sprintf(temporary,"%s[%d",pVar[i3].name,ss[0]); for(i4=1;;i4++){ if(pVar[i3].SubScripts[i4]==-1) break; sprintf(temporary+lstrlen(temporary),",%d",ss[i4]); } lstrcat(temporary,"]"); Opcode_CallProc("",pVar[i3].u.pobj_c->ppobj_Method[i5]->psi,0,0,temporary,DEF_OBJECT); ss[0]++; //ネイティブコードバッファの再確保 extern int obp_AllocSize; if(obp_AllocSizeppobj_Method[i5]->psi,0,0,pVar[i3].name,DEF_OBJECT); } } } } if(indexSystemGC!=-1){ //_System_GCオブジェクトのデストラクタの呼び出し処理 i3=pVar[indexSystemGC].u.pobj_c->DestructorMemberSubIndex; if(i3!=-1){ Opcode_CallProc("",pVar[indexSystemGC].u.pobj_c->ppobj_Method[i3]->psi,0,0,pVar[indexSystemGC].name,DEF_OBJECT); } } }