diff --git a/BUILD.gn b/BUILD.gn index e35c304bf09575c1743a64166a5ae68588a02c9a..fca908c868b08738a836d47a064c648a674cdd50 100644 --- a/BUILD.gn +++ b/BUILD.gn @@ -18,3 +18,12 @@ group("mapleall") { "${MAPLEALL_ROOT}:mapleall" ] } + +group("js2mpl") { + deps = [] + if(IS_JS2MPL_EXISTS == "1"){ + deps = [ + "${JS2MPL_ROOT}:js2mpl" + ] + } +} diff --git a/Makefile b/Makefile index 3b75bb82bbbd1652a9f43b539b41e72371a47884..958d153d24044fc76eb955f6b70e1cff6ab01a8d 100644 --- a/Makefile +++ b/Makefile @@ -71,6 +71,14 @@ default: mapleall mapleall: $(call build_gn, ${GN_OPTIONS}, irbuild maple mplcg) +.PHONY: js2mpl +js2mpl: + $(call build_gn, ${GN_OPTIONS}, js2mpl) + +.PHONY: mplbe +mplbe: + $(call build_gn, ${GN_OPTIONS}, mplbe) + .PHONY: install install: mapleall $(shell mkdir -p ${MAPLE_ROOT}/bin; \ diff --git a/build/config/BUILDCONFIG.gn b/build/config/BUILDCONFIG.gn index bbed5bee8dbbf44785f2414eb94f57525d299082..b36b4e4e8330fd77c885c1c5d1e06f5965075666 100644 --- a/build/config/BUILDCONFIG.gn +++ b/build/config/BUILDCONFIG.gn @@ -39,6 +39,7 @@ declare_args() { # Define global args MAPLE_ROOT = getenv("MAPLE_ROOT") +IS_JS2MPL_EXISTS = getenv("IS_JS2MPL_EXISTS") DYNAMICLANG = true RC_V2 = true if (X86_ARK == 1) { @@ -66,6 +67,7 @@ MAPLEALL_ROOT = "${MAPLE_ROOT}/mapleall" MAPLE_RE_ROOT = "${MAPLE_ROOT}/maple_engine" HUAWEI_SECURE_C_ROOT = "${MAPLE_ROOT}/huawei_secure_c" DWARF_ROOT = "${MAPLE_ROOT}/tools/dwarf" +JS2MPL_ROOT = "${MAPLE_ROOT}/js2mpl" # Toolchain setup if (USE_CLANG == 1) { diff --git a/maple_engine/include/mre_opcodes.def b/maple_engine/include/mre_opcodes.def index ea5bae16f5f039fb3485baa75a2d854750f92d38..804fc5711e15d1bc9f801b8abef614175b0cea26 100644 --- a/maple_engine/include/mre_opcodes.def +++ b/maple_engine/include/mre_opcodes.def @@ -22,3 +22,6 @@ OPCODE(brtrue32, none, none, none) OPCODE(brfalse32, none, none, none) OPCODE(goto32, none, none, none) + OPCODE(ireadfpoff32, none, none, none) + OPCODE(iassignfpoff32, none, none, none) + diff --git a/mapleall/maple_be/include/be/be_common.h b/mapleall/maple_be/include/be/be_common.h index 2fdb4cc6e81fb6239aa40535c68e180ad415f8c1..927c5384782d4cba0feacd807f5144d7e2dfda43 100644 --- a/mapleall/maple_be/include/be/be_common.h +++ b/mapleall/maple_be/include/be/be_common.h @@ -31,10 +31,10 @@ namespace maplebe { -#if TARGX86_64 || TARGAARCH64 || TARGARK || TARGRISCV64 +#if TARGX86_64 || TARGAARCH64 || TARGARK || TARGRISCV64 || TARGVM #define LOWERED_PTR_TYPE PTY_a64 #define SIZEOFPTR 8 -#elif TARGX86 || TARGARM || TARGVM +#elif TARGX86 || TARGARM #define LOWERED_PTR_TYPE PTY_a32 #define SIZEOFPTR 4 #else diff --git a/mapleall/maple_be/include/cg/ark/ark_mir_emit.h b/mapleall/maple_be/include/cg/ark/ark_mir_emit.h index d07de81f69c341e2e37000a2539c8c52a6e80ceb..4cf4445356f803f8f0d08c352c022e6a5c443b54 100644 --- a/mapleall/maple_be/include/cg/ark/ark_mir_emit.h +++ b/mapleall/maple_be/include/cg/ark/ark_mir_emit.h @@ -353,7 +353,8 @@ class MirGenerator : public CmplGenerator { void EmitAsmCall(CallNode *fstmt); void EmitAsmComment(CommentNode *comment); void EmitBytes(uint8 *b, int count); - void EmitBytesComment(uint8 *b, int count, string &comment); + void EmitBytesComment(uint8 *b, int count, const string &comment); + void EmitBytesCommentOffset(uint8 *b, int count, const string &comment, int offset); void EmitAsmShort(uint16 s); void EmitAsmWord(uint32 word); void EmitAsmWord(uint32 word, string comment); @@ -370,6 +371,9 @@ class MirGenerator : public CmplGenerator { void EmitString(const std::string &str, int bytes); void EmitStringNoTab(const std::string &str, int bytes); void EmitYieldPoint(void); + void EmitModuleInfo(void); + void EmitGlobalDecl(void); + void EmitOpCodes(void); void CheckYieldPointInsert(StmtNode *fstmt); int GetFormalsInfo(MIRFunction *func); int GetLocalsInfo(MIRFunction *func); @@ -377,6 +381,7 @@ class MirGenerator : public CmplGenerator { uint32 GetFieldOffsetType(TyIdx tyidx, FieldID fieldid, MIRType *&); RE_Opcode MapEHOpcode(RE_Opcode op); void CheckInsertOpCvt(Opcode expr, PrimType exprType, PrimType insnType); + std::string BuildLabelString(LabelIdx lbidx); int GetFuncOffset(void) { return funcOffset; diff --git a/mapleall/maple_be/src/be/be_lowerer.cpp b/mapleall/maple_be/src/be/be_lowerer.cpp index c241da712f2e88a2815fff72ff3d41f02aeae580..c7da9bb70a52df3468a0e5ed0af09a1fc5ae90bc 100644 --- a/mapleall/maple_be/src/be/be_lowerer.cpp +++ b/mapleall/maple_be/src/be/be_lowerer.cpp @@ -1419,9 +1419,7 @@ BlockNode *BELowerer::LowerBlock(BlockNode *block) { } // Do not leave comment stmt to mmpl. case OP_comment: - if (!IsTargetMMPL()) { - newblk->AddStatement(stmt); - } + newblk->AddStatement(stmt); break; case OP_try: case OP_javatry: diff --git a/mapleall/maple_be/src/be/mmpl/mmpl_lowerer.cpp b/mapleall/maple_be/src/be/mmpl/mmpl_lowerer.cpp index c91631ba1f48fe32ff8982ce052e763fe0b7a532..aba6a98c7fec3bb3006c0e108826db36e13b75b4 100644 --- a/mapleall/maple_be/src/be/mmpl/mmpl_lowerer.cpp +++ b/mapleall/maple_be/src/be/mmpl/mmpl_lowerer.cpp @@ -62,7 +62,7 @@ PregIdx MmplLowerer::GetSpecialRegFromSt(const MIRSymbol *sym) { } BaseNode *MmplLowerer::ReadregNodeForSymbol(MIRSymbol *sym) { - return mirModule.mirBuilder->CreateExprRegread(PTY_a32, GetSpecialRegFromSt(sym)); + return mirModule.mirBuilder->CreateExprRegread(LOWERED_PTR_TYPE, GetSpecialRegFromSt(sym)); } BaseNode *MmplLowerer::LowerAddrof(AddrofNode *expr) { @@ -80,7 +80,7 @@ BaseNode *MmplLowerer::LowerAddrof(AddrofNode *expr) { offset += symbol->IsLocal() ? memlayout->sym_alloc_table[symbol->GetStIndex()].offset : globmemlayout->sym_alloc_table[symbol->GetStIndex()].offset; return (offset == 0) ? rrn - : mirModule.mirBuilder->CreateExprBinary(OP_add, GlobalTables::GetTypeTable().GetTypeFromTyIdx((TyIdx)PTY_a32), rrn, + : mirModule.mirBuilder->CreateExprBinary(OP_add, GlobalTables::GetTypeTable().GetTypeFromTyIdx((TyIdx)LOWERED_PTR_TYPE), rrn, mirModule.mirBuilder->GetConstInt(offset)); } @@ -103,7 +103,7 @@ BaseNode *MmplLowerer::LowerDread(AddrofNode *expr) { symty, memlayout->sym_alloc_table[symbol->GetStIndex()].offset + offset); return ireadoff; } else { - BaseNode *rrn = mirModule.mirBuilder->CreateExprRegread(PTY_a32, spcreg); + BaseNode *rrn = mirModule.mirBuilder->CreateExprRegread(LOWERED_PTR_TYPE, spcreg); SymbolAlloc &symalloc = symbol->IsLocal() ? memlayout->sym_alloc_table[symbol->GetStIndex()] : globmemlayout->sym_alloc_table[symbol->GetStIndex()]; IreadoffNode *ireadoff = mirModule.mirBuilder->CreateExprIreadoff(symty, symalloc.offset + offset, rrn); diff --git a/mapleall/maple_be/src/cg/ark/ark_emit.cpp b/mapleall/maple_be/src/cg/ark/ark_emit.cpp index 93f62d641b6e70fa8771f9096206f576cbedafbc..905a119b3ca328b2df5ad0cb77f04bef59691b3c 100644 --- a/mapleall/maple_be/src/cg/ark/ark_emit.cpp +++ b/mapleall/maple_be/src/cg/ark/ark_emit.cpp @@ -195,7 +195,9 @@ void ArkCGFunc::Emit() { // nothing } else { emitter.Emit("\t.globl\t").Emit(funcSt->GetName()).Emit("\n"); - emitter.Emit("\t.hidden\t").Emit(funcSt->GetName()).Emit("\n"); + if (!func->module->IsJsModule()) { + emitter.Emit("\t.hidden\t").Emit(funcSt->GetName()).Emit("\n"); + } } emitter.Emit("\t.type\t").Emit(funcSt->GetName()).Emit(", %function\n"); @@ -207,7 +209,9 @@ void ArkCGFunc::Emit() { emitter.Emit("\t// mir2bin func begin: ========================\n"); emitter.Emit("\t.cfi_startproc\n"); - emitter.Emit("\t.cfi_personality 155, DW.ref.__mpl_personality_v0\n"); + if (!func->module->IsJsModule()) { + emitter.Emit("\t.cfi_personality 155, DW.ref.__mpl_personality_v0\n"); + } emitter.mirg_->EmitFunc(cg->curCgFunc->func); emitter.Emit("\t.cfi_endproc\n"); emitter.Emit(".label.end."+funcSt->GetName()+":\n"); diff --git a/mapleall/maple_be/src/cg/ark/ark_mir_emit.cpp b/mapleall/maple_be/src/cg/ark/ark_mir_emit.cpp index be2da39629e520cc03617730b461a41b3b7e410d..6384687547e33f55e148c02595b1586acb05475d 100644 --- a/mapleall/maple_be/src/cg/ark/ark_mir_emit.cpp +++ b/mapleall/maple_be/src/cg/ark/ark_mir_emit.cpp @@ -30,6 +30,8 @@ #include #define CLANG (mmodule.IsCModule()) +#define JAVALANG (mmodule.IsJavaModule()) +#define JAVASCRIPT (mmodule.IsJsModule()) using std::hex; @@ -119,13 +121,13 @@ std::set PreDefClassInfo = { // TODO: add memcmpMpl to list when we have x86 replacement. // NOTE: IntrinsicList is moved to special_func.cpp -inline void MirGenerator::EmitString(const std::string &str, int bytes) { +inline void MirGenerator::EmitString(const std::string &str, int bytes=0) { int offset = GetFuncOffset(); os << "\t" << str << "\n"; SetFuncOffset(offset + bytes); } -inline void MirGenerator::EmitStringNoTab(const std::string &str, int bytes) { +inline void MirGenerator::EmitStringNoTab(const std::string &str, int bytes=0) { int offset = GetFuncOffset(); os << str << "\n"; SetFuncOffset(offset + bytes); @@ -282,7 +284,11 @@ void MirGenerator::EmitExpr(Opcode curOp, PrimType curPrimType, BaseNode *fexpr) ASSERT(preg, "preg is null"); regName.append("%"); regName.append(std::to_string(preg->pregNo)); - expr.param.frameIdx = curFunc.EncodePreg(preg->pregNo); + if (JAVASCRIPT) { + expr.param.frameIdx = preg->pregNo; + } else { + expr.param.frameIdx = curFunc.EncodePreg(preg->pregNo); + } EmitAsmBaseNode(expr, regName); // check for regread of less than 4 bytes CheckInsertOpCvt(curOp, curPrimType, fexpr->primType); @@ -302,6 +308,20 @@ void MirGenerator::EmitExpr(Opcode curOp, PrimType curPrimType, BaseNode *fexpr) } break; } + case OP_ireadfpoff: { + ASSERT(JAVASCRIPT, "OP_ireadfpoff in non Maple JS input"); + int32 offset = static_cast(fexpr)->offset; + // generate 4 byte instr if offset fits in 16 bits else generate 8 byte instr + if (offset <= 32767 && offset >= -32768) { + expr.param.offset = offset; + EmitAsmBaseNode(expr); + } else { + expr.op = RE_ireadfpoff32; + EmitAsmBaseNode(expr); + EmitAsmWord(offset); + } + break; + } case OP_select: FlattenExpr(fexpr); // no extra fields to handle @@ -415,6 +435,13 @@ void MirGenerator::EmitExpr(Opcode curOp, PrimType curPrimType, BaseNode *fexpr) EmitAsmBaseNode(expr); EmitAsmConststr(reinterpret_cast(fexpr)->strIdx); break; + case OP_intrinsicop: { + IntrinsicopNode *intrinsicop = (IntrinsicopNode *)fexpr; + expr.param.intrinsic.intrinsicId = intrinsicop->intrinsic; + FlattenExpr(fexpr); + EmitAsmBaseNode(expr, GetIntrinsicName(intrinsicop->intrinsic)); + break; + } default: MIR_FATAL("unknown expression opcode: [%d]:(%s)\n", fexpr->op, kOpcodeInfo.GetName(fexpr->op)); } @@ -473,6 +500,21 @@ void MirGenerator::EmitStmt(StmtNode *fstmt) { } break; } + case OP_iassignfpoff: { + ASSERT(JAVASCRIPT, "OP_iassignfpoff in non Maple JS input"); + int32 offset = static_cast(fstmt)->offset; + FlattenExpr(fstmt); + // generate 4 byte instr if offset fits in 16 bits else generate 8 byte instr + if (offset <= 32767 && offset >= -32768) { + stmt.param.offset = offset; + EmitAsmBaseNode(stmt); + } else { + stmt.op = RE_iassignfpoff32; + EmitAsmBaseNode(stmt); + EmitAsmWord(offset); + } + break; + } case OP_regassign: { string regName; FlattenExpr(fstmt); @@ -480,7 +522,11 @@ void MirGenerator::EmitStmt(StmtNode *fstmt) { ASSERT(preg, "preg is null"); regName.append("%"); regName.append(std::to_string(preg->pregNo)); - stmt.param.frameIdx = curFunc.EncodePreg(preg->pregNo); + if (JAVASCRIPT) { + stmt.param.frameIdx = preg->pregNo; + } else { + stmt.param.frameIdx = curFunc.EncodePreg(preg->pregNo); + } EmitAsmBaseNode(stmt, regName); break; } @@ -512,6 +558,11 @@ void MirGenerator::EmitStmt(StmtNode *fstmt) { EmitAsmBaseNode(stmt); EmitAsmLabel(((GotoNode *)fstmt)->offset, true); break; + case OP_gosub: + stmt.op = RE_gosub; + EmitAsmBaseNode(stmt); + EmitAsmLabel(((GotoNode *)fstmt)->offset, true); + break; case OP_rangegoto: { RangegotoNode *rNode = static_cast(fstmt); SmallCaseVector &rTable = rNode->rangegotoTable; @@ -522,9 +573,7 @@ void MirGenerator::EmitStmt(StmtNode *fstmt) { EmitAsmBaseNode(stmt); // emit base instr with num jump table entry EmitAsmWord(rNode->tagOffset); // emit tagOffset for (int i = 0; i < numCases; i++) { // emit jump table - MIRFunction *func = GetCurFunction(); - string label = "mirbin_label_"+to_string(func->puIdxOrigin)+"_"+to_string(rTable[i].second); - EmitString(".4byte "+label+"-. "+"\t// jmptbl["+to_string(rTable[i].first)+"]", 2); + EmitString(".4byte "+BuildLabelString(rTable[i].second)+"-. "+"\t// jmptbl["+to_string(rTable[i].first)+"]", 4); } break; } @@ -669,6 +718,30 @@ void MirGenerator::EmitStmt(StmtNode *fstmt) { EmitAsmBaseNode(stmt); curFunc.currentTry = nullptr; break; + case OP_cleanuptry: + case OP_finally: + case OP_retsub: + EmitAsmBaseNode(stmt); + break; + case OP_jstry: { + JsTryNode *jstry = static_cast(fstmt); + EmitAsmBaseNode(stmt); + if (jstry->catchOffset) { + EmitAsmLabel(jstry->catchOffset, true); + } else { + EmitString(".long 0", 4); + } + if (jstry->finallyOffset) { + EmitAsmLabel(jstry->finallyOffset, true); + } else { + EmitString(".long 0", 4); + } + break; + } + case OP_jscatch: { + EmitAsmBaseNode(stmt); + break; + } default: MIR_FATAL("unknown statement opcode: [%d]:(%s)\n", fstmt->op, kOpcodeInfo.GetName(fstmt->op)); } @@ -1079,46 +1152,96 @@ void MirGenerator::EmitAsmFuncInfo(MIRFunction *func) { //printf("func %d \n", func->puIdxOrigin); curFunc.Init(func); - curFunc.numFormalArgs = GetFormalsInfo(func); - curFunc.numAutoVars = GetLocalsInfo(func) + 2; // incl. %%retval0 and %%thrownval + if (!JAVASCRIPT) { + curFunc.numFormalArgs = GetFormalsInfo(func); + curFunc.numAutoVars = GetLocalsInfo(func) + 2; // incl. %%retval0 and %%thrownval + if (func->IsWeak()) curFunc.SetWeakAttr(); + if (func->IsStatic()) curFunc.SetStaticAttr(); + if (func->IsConstructor()) curFunc.SetConstructorAttr(); + if (GlobalTables::GetStrTable().GetStringFromStrIdx(func->GetBaseFuncNameStridx()) == "finalize") curFunc.SetFinalizeAttr(); + } curFunc.evalStackDepth = MaxEvalStack(func); + // insert interpreter shim and signature + if (JAVASCRIPT) { + os << "\t.ascii \"MPJS\"\n"; + os << infoLabel << ":\n"; + os << "\t" << ".long " << codeLabel << " - .\n"; + + int formalsBlkBitVectBytes = BlkSize2BitvectorSize(func->upFormalSize); + int localsBlkBitVectBytes = BlkSize2BitvectorSize(func->frameSize); + os << "\t" << ".word " << func->upFormalSize << ", " << func->frameSize << ", " << curFunc.evalStackDepth << ", " << 0 << "\t// upFormalSize, frameSize, evalStackDepth\n"; + os << "\t" << ".word " << formalsBlkBitVectBytes << ", " << localsBlkBitVectBytes << "\t\t// formalWords bit vector byte count, localWords bit vector byte count\n"; + if (formalsBlkBitVectBytes) { + EmitBytesCommentOffset(func->formalWordsTypeTagged, formalsBlkBitVectBytes, "// formalWordsTypeTagged", 0); + EmitBytesCommentOffset(func->formalWordsRefCounted, formalsBlkBitVectBytes, "// formalWordsRefCounted", 0); + } + if (localsBlkBitVectBytes) { + EmitBytesCommentOffset(func->localWordsTypeTagged, localsBlkBitVectBytes, "// localWordsTypeTagged", 0); + EmitBytesCommentOffset(func->localWordsRefCounted, localsBlkBitVectBytes, "// localWordsRefCounted", 0); + } + } else { + os << "\t.ascii \"MPLI\"\n"; + os << infoLabel << ":\n"; + os << "\t" << ".long " << codeLabel << " - .\n"; + os << "\t" << ".word " << curFunc.numFormalArgs << ", " << curFunc.numAutoVars << ", " << curFunc.evalStackDepth << ", " << curFunc.funcAttrs << " // func storage info\n"; - if (func->IsWeak()) curFunc.SetWeakAttr(); - if (func->IsStatic()) curFunc.SetStaticAttr(); - if (func->IsConstructor()) curFunc.SetConstructorAttr(); - if (GlobalTables::GetStrTable().GetStringFromStrIdx(func->GetBaseFuncNameStridx()) == "finalize") curFunc.SetFinalizeAttr(); + if (curFunc.numFormalArgs) { + os << "\t" << "// PrimType of formal arguments\n"; + } + EmitAsmFormalArgInfo(func); + if (curFunc.numAutoVars) { + os << "\t" << "// PrimType of automatic variables\n"; + } + EmitAsmAutoVarsInfo(func); - // insert interpreter shim and signature - os << "\t.ascii \"MPLI\"\n"; - os << infoLabel << ":\n"; - os << "\t" << ".long " << codeLabel << " - .\n"; - os << "\t" << ".word " << curFunc.numFormalArgs << ", " << curFunc.numAutoVars << ", " << curFunc.evalStackDepth << ", " << curFunc.funcAttrs << " // func storage info\n"; + if (curFunc.numFormalArgs) { + os << "\t" << "// Name of formal arguments\n"; + } + EmitAsmFormalArgNameInfo(func); + if (curFunc.numAutoVars) { + os << "\t" << "// Name of automatic variables\n"; + } + EmitAsmAutoVarsNameInfo(func); - if (curFunc.numFormalArgs) { - os << "\t" << "// PrimType of formal arguments\n"; - } - EmitAsmFormalArgInfo(func); - if (curFunc.numAutoVars) { - os << "\t" << "// PrimType of automatic variables\n"; + for (std::pair it : curFunc.func->aliasVarMap) { + os << "\t// ALIAS %" << GlobalTables::GetStrTable().GetStringFromStrIdx(it.first) << " %" + << GlobalTables::GetStrTable().GetStringFromStrIdx(it.second.memPoolStrIdx) << "\n"; + } } - EmitAsmAutoVarsInfo(func); - if (curFunc.numFormalArgs) { - os << "\t" << "// Name of formal arguments\n"; - } - EmitAsmFormalArgNameInfo(func); - if (curFunc.numAutoVars) { - os << "\t" << "// Name of automatic variables\n"; + os << "\t.p2align 1\n"; + os << codeLabel << ":\n"; +} + +void MirGenerator::EmitModuleInfo(void) { + EmitOpCodes(); + if (JAVASCRIPT) { + EmitGlobalDecl(); } - EmitAsmAutoVarsNameInfo(func); +} - for (std::pair it : curFunc.func->aliasVarMap) { - os << "\t// ALIAS %" << GlobalTables::GetStrTable().GetStringFromStrIdx(it.first) << " %" - << GlobalTables::GetStrTable().GetStringFromStrIdx(it.second.memPoolStrIdx) << "\n"; +void MirGenerator::EmitOpCodes(void) { + // gen opcodes - skip entry 0 (kOpUndef) and handle duplicate name (OP_dassign, OP_maydassign) + EmitStringNoTab("\nOP_dassign = 1"); + EmitStringNoTab("OP_maydassign = 2"); + for (int i = 3; i < kREOpLast; ++i) { + EmitStringNoTab(string("OP_")+RE_OpName[i]+" = "+to_string(i)); } + EmitStringNoTab(""); +} - os << "\t.p2align 1\n"; - os << codeLabel << ":\n"; +void MirGenerator::EmitGlobalDecl(void) { + os << "\t.section\t.rodata\n"; + os << "\t.p2align 3\n"; + os << "\t.global __mpljs_module_decl__\n"; + os << "__mpljs_module_decl__:\n"; + os << "\t.word " << mmodule.globalMemSize << "\t// globalMemSize byte count\n"; + if (mmodule.globalMemSize) { + EmitBytesCommentOffset(mmodule.globalBlkMap, mmodule.globalMemSize, "\t// globalMemMap", 0);; + os << "\t.word " << BlkSize2BitvectorSize(mmodule.globalMemSize) << "\t// globalwordstypetagged/refcounted byte count\n"; + EmitBytesCommentOffset(mmodule.globalWordsTypeTagged, BlkSize2BitvectorSize(mmodule.globalMemSize), "\t// globalwordstypetagged", 0); + EmitBytesCommentOffset(mmodule.globalWordsRefCounted, BlkSize2BitvectorSize(mmodule.globalMemSize), "\t// globalwordsrefcounted", 0); + } } void MirGenerator::EmitAsmBaseNode(mre_instr_t &m) { @@ -1158,7 +1281,7 @@ void MirGenerator::EmitBytes(uint8 *b, int count) { EmitString(ss.str(), count); } -void MirGenerator::EmitBytesComment(uint8 *b, int count, string &comment) { +void MirGenerator::EmitBytesCommentOffset(uint8 *b, int count, const string &comment, int offset=0) { stringstream ss; ss << ".byte "; for (int i=0; icomment.c_str() && stmt->comment.c_str()[stmt->comment.length()-1] == '\\') { + // remove trailing slash in comment line otherwuse gnu g++-5 treats next line as + // continuation of comment and skips compiling it + stmt->comment.c_str()[stmt->comment.length()-1] = 0; + } os << "\t// " << stmt->comment.data << "\n"; } @@ -1324,15 +1456,36 @@ void MirGenerator::EmitYieldPoint(void) { EmitAsmBaseNode(node); } +std::string MirGenerator::BuildLabelString(LabelIdx lbidx) { + MIRFunction *func = GetCurFunction(); + string label; + + // Many strangeness with labels if we generate labels into .s + // by the label's name in string table: + // - we get @ and | characters in name string that the assembler complains + // - duplicate name strings across different label idx in the same function + // - duplicate label idx in same function if all of CG's phases are run. + if (JAVASCRIPT){ + string labelName = func->GetLabelName(lbidx); + replace(labelName.begin(), labelName.end(), '@', '_'); + replace(labelName.begin(), labelName.end(), '|', '_'); + // cannot use puIdxOrigin because they are all 0 in js2mpl generated mpl + MIRSymbol *fnSt = GlobalTables::GetGsymTable().GetSymbolFromStIdx(func->stIdx.Idx()); + label = "mirbin_label_"+fnSt->GetName()+"_"+labelName; + } else { + label = "mirbin_label_"+ to_string(func->puIdxOrigin)+"_"+to_string(lbidx); + } + return label; +} + void MirGenerator::EmitAsmLabel(LabelIdx lbidx, bool genOffset) { MIRFunction *func = GetCurFunction(); - string label = "mirbin_label_"+to_string(func->puIdxOrigin)+"_"+to_string(lbidx); // TODO: fix issue - currently have to disable fpm->run in CG to avoid duplicate labels if (genOffset) { - EmitString(".long "+label+"-.", 4); + EmitString(".long "+BuildLabelString(lbidx)+"-.", 4); } else { - os << label+":\n"; + os << BuildLabelString(lbidx)+":\n"; } } @@ -1352,14 +1505,13 @@ void MirGenerator::EmitAsmConststr(UStrIdx strIdx) { } RE_Opcode MirGenerator::MapEHOpcode(RE_Opcode op) { - MIRModule *module = GetCurFunction()->module; - if (module->IsCModule()) { + if (CLANG) { if (op == RE_catch) { op = RE_cppcatch; } else if (op == RE_try) { op = RE_cpptry; } - } else if (module->IsJavaModule()) { + } else if (JAVALANG) { if (op == RE_catch) { op = RE_javacatch; } else if (op == RE_try) { diff --git a/mapleall/maple_be/src/cg/cg_driver.cpp b/mapleall/maple_be/src/cg/cg_driver.cpp index b5d83f3c52116d46341f2b631ff9850675961361..4cff699a0f992a16ba696a444ad533b6f41c795a 100644 --- a/mapleall/maple_be/src/cg/cg_driver.cpp +++ b/mapleall/maple_be/src/cg/cg_driver.cpp @@ -177,9 +177,14 @@ int main(int argc, char **argv) { } if (cgoption.run_cg_flag) { - // 1. LowerIR. - thecg.LowerIR(); +#if TARGARK + if (!themodule->IsJsModule()) { +#endif + thecg.LowerIR(); +#if TARGARK + } +#endif // 2. Generate the output file BECommon &becommon = *g->becommon; @@ -194,13 +199,10 @@ int main(int argc, char **argv) { mirGen->OutputMIR(cgoption.genMirMpl); thecg.emitter_->mirg_ = mirGen; - // gen opcodes - skip entry 0 (kOpUndef) and handle duplicate name (OP_dassign, OP_maydassign) - thecg.emitter_->Emit("\nOP_dassign = 1\n"); - thecg.emitter_->Emit("OP_maydassign = 2\n"); - for (int i = 3; i < kREOpLast; ++i) { - thecg.emitter_->Emit(string("OP_")+RE_OpName[i]+" = "+to_string(i)+"\n"); + mirGen->EmitOpCodes(); + if (themodule->IsJsModule()) { + mirGen->EmitGlobalDecl(); } - // load profile info for class meta data - uses same binary metadata profile (meta.list) as mpl2mpl uint32 javaNameIdx = themodule->GetFileinfo(GlobalTables::GetStrTable().GetOrCreateStrIdxFromName("INFO_filename")); const std::string &javaName = GlobalTables::GetStrTable().GetStringFromStrIdx(GStrIdx(javaNameIdx)); diff --git a/mapleall/maple_ir/include/intrinsics.def b/mapleall/maple_ir/include/intrinsics.def index 91d027ef1d83ed5edfe656b478b4ffac45d75d60..18889bb75a6bfb759be6961a20a2d83e282bb99e 100644 --- a/mapleall/maple_ir/include/intrinsics.def +++ b/mapleall/maple_ir/include/intrinsics.def @@ -192,6 +192,7 @@ DEF_MIR_INTRINSIC(MCCNewPermanentArray,\ #include "intrinsic_misc.def" #include "intrinsic_c.def" +#include "js2mpl/jsintrinsic_eng.def" DEF_MIR_INTRINSIC(LAST,\ nullptr, kIntrnUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) diff --git a/mapleall/maple_ir/include/js2mpl/jsintrinsic.def b/mapleall/maple_ir/include/js2mpl/jsintrinsic.def index 7d5650cb339bab285f610982201d2ce775bd3cca..1c42c3d4ea6ceec35048de41802e96e71061be46 100644 --- a/mapleall/maple_ir/include/js2mpl/jsintrinsic.def +++ b/mapleall/maple_ir/include/js2mpl/jsintrinsic.def @@ -116,3 +116,4 @@ DEF_MIR_INTRINSIC(JSOP_MORE_ITERATOR,\ __jsop_more_iterator, INTRNISJS, kArgTyU32, kArgTyPtr, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) DEF_MIR_INTRINSIC(JS_ADDSYSEVENTLISTENER,\ __js_add_sysevent_listener, INTRNISJS, kArgTyU32, kArgTyDynany, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) + diff --git a/mapleall/maple_ir/include/js2mpl/jsintrinsic_eng.def b/mapleall/maple_ir/include/js2mpl/jsintrinsic_eng.def new file mode 100644 index 0000000000000000000000000000000000000000..aed902742f6e4a95a41b964a1639ca996df91948 --- /dev/null +++ b/mapleall/maple_ir/include/js2mpl/jsintrinsic_eng.def @@ -0,0 +1,34 @@ +/* + * Copyright (c) [2020] Huawei Technologies Co., Ltd. All rights reserved. + * + * OpenArkCompiler is licensed under the Mulan Permissive Software License v2. + * You can use this software according to the terms and conditions of the MulanPSL - 2.0. + * You may obtain a copy of MulanPSL - 2.0 at: + * + * https://opensource.org/licenses/MulanPSL-2.0 + * + * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR + * FIT FOR A PARTICULAR PURPOSE. + * See the MulanPSL - 2.0 for more details. + */ + +// DEF_MIR_INTRINSIC(STR, NAME, INTRN_CLASS, RETURN_TYPE, ARG0, ARG1, ARG2, ARG3, ARG4, ARG5) +DEF_MIR_INTRINSIC(JS_GET_ARGUMENTOBJECT,\ + __jsobj_get_or_create_argument, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_ERROR_OBJECT,\ + __jsobj_get_or_create_error, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_EVALERROR_OBJECT,\ + __jsobj_get_or_create_evalError, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_RANGEERROR_OBJECT,\ + __jsobj_get_or_create_rangeError, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_REFERENCEERROR_OBJECT,\ + __jsobj_get_or_create_referenceError, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_SYNTAXERROR_OBJECT,\ + __jsobj_get_or_create_syntaxError, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_TYPEERROR_OBJECT,\ + __jsobj_get_or_create_typeError, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JS_GET_URIERROR_OBJECT,\ + __jsobj_get_or_create_uriError, INTRNISJS | INTRNISPURE, kArgTySimpleobj, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) +DEF_MIR_INTRINSIC(JSOP_ASSERTVALUE, + __jsop_assert_value, INTRNISJS, kArgTyDynany, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef, kArgTyUndef) diff --git a/mapleall/maple_ir/include/mir_module.h b/mapleall/maple_ir/include/mir_module.h index 90016499451ebf3c911bb7c96264d8151d7eb7b7..1f5dd23b94091dd390859499be14554bea234849 100644 --- a/mapleall/maple_ir/include/mir_module.h +++ b/mapleall/maple_ir/include/mir_module.h @@ -240,6 +240,10 @@ class MIRModule : public mir_module_t { return srcLang == kSrcLangC || srcLang == kSrcLangCPlusPlus; } + bool IsJsModule() const { + return srcLang == kSrcLangJs; + } + void ReleaseCurFuncMpTmp(); inline void SetUseFuncCodeMpTmp() { useFuncCodeMpTmp = true; diff --git a/mapleall/maple_ir/src/lexer.cpp b/mapleall/maple_ir/src/lexer.cpp index 58074f34275a367782799345469a1a05f891a5e0..4bb6e2f5e8fca35ade10d5a812ec0998fc961e85 100644 --- a/mapleall/maple_ir/src/lexer.cpp +++ b/mapleall/maple_ir/src/lexer.cpp @@ -360,7 +360,7 @@ TokenKind MIRLexer::GetTokenWithPrefixPercent() { TokenKind MIRLexer::GetTokenWithPrefixAmpersand() { // token with prefix '&' char c = GetCurrentCharWithUpperCheck(); - if (isalpha(c) || c == '_') { + if (isalpha(c) || c == '_' || c == '$') { GenName(); return TK_fname; } else { diff --git a/mapleall/maple_ir/src/mir_parser_expr.cpp b/mapleall/maple_ir/src/mir_parser_expr.cpp index bb615588f0ccca12c4d90b5d105b82f875032bd6..df46f743b50a0231d883cfbfe931e6552caf21b1 100644 --- a/mapleall/maple_ir/src/mir_parser_expr.cpp +++ b/mapleall/maple_ir/src/mir_parser_expr.cpp @@ -1159,11 +1159,14 @@ bool MIRParser::ParseExprIntrinsicopwithtype(BaseNode *&expr) { bool MIRParser::ParseScalarValue(MIRConst *&stype, MIRType *type) { PrimType ptp = type->primType; if (IsPrimitiveInteger(ptp) || IsPrimitiveDynType(ptp) || ptp == PTY_gen) { - if (lexer.GetTokenKind() != TK_intconst) { + if (lexer.GetTokenKind() == TK_intconst) { + stype = mod.memPool->New(lexer.GetTheIntVal(), type); + } else if (lexer.GetTokenKind() == TK_doubleconst) { + stype = mod.memPool->New(lexer.GetTheDoubleVal(), type); + } else { Error("constant value incompatible with integer type at "); return false; } - stype = mod.memPool->New(lexer.GetTheIntVal(), type); } else if (ptp == PTY_f32) { if (lexer.GetTokenKind() != TK_floatconst) { Error("constant value incompatible with single-precision float type at "); diff --git a/mapleall/maple_ir/src/mir_type.cpp b/mapleall/maple_ir/src/mir_type.cpp index 17e91d477b86b79f9f85c7c23b2948ecd6cc28e9..fb2cab4d6baf20b48367738ea15f566892a9a530 100644 --- a/mapleall/maple_ir/src/mir_type.cpp +++ b/mapleall/maple_ir/src/mir_type.cpp @@ -163,9 +163,10 @@ uint32 GetPrimTypeSize(PrimType pty) { case PTY_f32: case PTY_i32: case PTY_u32: + return 4; case PTY_simplestr: case PTY_simpleobj: - return 4; + return 8; case PTY_a64: case PTY_c64: case PTY_f64: