diff --git a/eng/native/sanitizer-ignorelist.txt b/eng/native/sanitizer-ignorelist.txt index ecc8bef9bf688..8e89d3ca960dc 100644 --- a/eng/native/sanitizer-ignorelist.txt +++ b/eng/native/sanitizer-ignorelist.txt @@ -10,5 +10,5 @@ fun:_ZN11CMiniMdBase19UsesAllocatedMemoryEP11CMiniColDef # 2 0x4e8051 in __ubsan_handle_dynamic_type_cache_miss # 3 0x7f02ce676cd8 in JIT_InitPInvokeFrame(InlinedCallFrame*, void*) /home/steveharter/git/dotnet_coreclr/vm/jithelpers.cpp:6491:9 # 4 0x7f0252bbceb2 () -fun:_Z20JIT_InitPInvokeFrameP16InlinedCallFramePv +fun:_Z20JIT_InitPInvokeFrameP16InlinedCallFrame diff --git a/src/coreclr/inc/corinfo.h b/src/coreclr/inc/corinfo.h index 2d526105164b6..db5499b81fd33 100644 --- a/src/coreclr/inc/corinfo.h +++ b/src/coreclr/inc/corinfo.h @@ -1754,6 +1754,9 @@ struct CORINFO_EE_INFO // Size of the Frame structure unsigned size; + // Size of the Frame structure when it also contains the secret stub arg + unsigned sizeWithSecretStubArg; + unsigned offsetOfGSCookie; unsigned offsetOfFrameVptr; unsigned offsetOfFrameLink; @@ -1761,6 +1764,7 @@ struct CORINFO_EE_INFO unsigned offsetOfCalleeSavedFP; unsigned offsetOfCallTarget; unsigned offsetOfReturnAddress; + unsigned offsetOfSecretStubArg; // This offset is used only for ARM unsigned offsetOfSPAfterProlog; } diff --git a/src/coreclr/inc/jiteeversionguid.h b/src/coreclr/inc/jiteeversionguid.h index 762656a3dbbcf..46b50f5410ce4 100644 --- a/src/coreclr/inc/jiteeversionguid.h +++ b/src/coreclr/inc/jiteeversionguid.h @@ -43,11 +43,11 @@ typedef const GUID *LPCGUID; #define GUID_DEFINED #endif // !GUID_DEFINED -constexpr GUID JITEEVersionIdentifier = { /* 43854594-cd60-45df-a89f-5b7697586f46 */ - 0x43854594, - 0xcd60, - 0x45df, - {0xa8, 0x9f, 0x5b, 0x76, 0x97, 0x58, 0x6f, 0x46} +constexpr GUID JITEEVersionIdentifier = { /* 227e46fa-1be3-4770-b613-4a239e7c28aa */ + 0x227e46fa, + 0x1be3, + 0x4770, + {0xb6, 0x13, 0x4a, 0x23, 0x9e, 0x7c, 0x28, 0xaa} }; ////////////////////////////////////////////////////////////////////////////////////////////////////////// diff --git a/src/coreclr/jit/codegen.h b/src/coreclr/jit/codegen.h index af324ce6e8ba3..ed1e4be7cf43e 100644 --- a/src/coreclr/jit/codegen.h +++ b/src/coreclr/jit/codegen.h @@ -277,6 +277,7 @@ class CodeGen final : public CodeGenInterface var_types genParamStackStoreType(LclVarDsc* dsc, const ABIPassingSegment& seg); void genSpillOrAddRegisterParam(unsigned lclNum, class RegGraph* graph); + void genSpillOrAddNonStandardRegisterParam(unsigned lclNum, regNumber sourceReg, class RegGraph* graph); void genEnregisterIncomingStackArgs(); #if defined(TARGET_ARM64) || defined(TARGET_LOONGARCH64) || defined(TARGET_RISCV64) void genEnregisterOSRArgsAndLocals(regNumber initReg, bool* pInitRegZeroed); diff --git a/src/coreclr/jit/codegencommon.cpp b/src/coreclr/jit/codegencommon.cpp index 428f030571499..070ecc71f9078 100644 --- a/src/coreclr/jit/codegencommon.cpp +++ b/src/coreclr/jit/codegencommon.cpp @@ -3246,6 +3246,31 @@ void CodeGen::genSpillOrAddRegisterParam(unsigned lclNum, RegGraph* graph) } } +// ----------------------------------------------------------------------------- +// genSpillOrAddNonStandardRegisterParam: Handle a non-standard register parameter either +// by homing it to stack immediately, or by adding it to the register graph. +// +// Parameters: +// lclNum - Local that represents the non-standard parameter +// sourceReg - Register that the non-standard parameter is in on entry to the function +// graph - The register graph to add to +// +void CodeGen::genSpillOrAddNonStandardRegisterParam(unsigned lclNum, regNumber sourceReg, RegGraph* graph) +{ + LclVarDsc* varDsc = compiler->lvaGetDesc(lclNum); + if (varDsc->lvOnFrame && (!varDsc->lvIsInReg() || varDsc->lvLiveInOutOfHndlr)) + { + GetEmitter()->emitIns_S_R(ins_Store(varDsc->TypeGet()), emitActualTypeSize(varDsc), sourceReg, lclNum, 0); + } + + if (varDsc->lvIsInReg()) + { + RegNode* sourceRegNode = graph->GetOrAdd(sourceReg); + RegNode* destRegNode = graph->GetOrAdd(varDsc->GetRegNum()); + graph->AddEdge(sourceRegNode, destRegNode, TYP_I_IMPL, 0); + } +} + // ----------------------------------------------------------------------------- // genHomeRegisterParams: Move all register parameters to their initial // assigned location. @@ -3289,6 +3314,12 @@ void CodeGen::genHomeRegisterParams(regNumber initReg, bool* initRegStillZeroed) } } + if (compiler->info.compPublishStubParam && ((paramRegs & RBM_SECRET_STUB_PARAM) != RBM_NONE)) + { + GetEmitter()->emitIns_S_R(ins_Store(TYP_I_IMPL), EA_PTRSIZE, REG_SECRET_STUB_PARAM, + compiler->lvaStubArgumentVar, 0); + } + return; } @@ -3321,6 +3352,11 @@ void CodeGen::genHomeRegisterParams(regNumber initReg, bool* initRegStillZeroed) } } + if (compiler->info.compPublishStubParam && ((paramRegs & RBM_SECRET_STUB_PARAM) != RBM_NONE)) + { + genSpillOrAddNonStandardRegisterParam(compiler->lvaStubArgumentVar, REG_SECRET_STUB_PARAM, &graph); + } + DBEXEC(VERBOSE, graph.Dump()); regMaskTP busyRegs = intRegState.rsCalleeRegArgMaskLiveIn | floatRegState.rsCalleeRegArgMaskLiveIn; @@ -3784,13 +3820,6 @@ void CodeGen::genCheckUseBlockInit() { regMaskTP maskCalleeRegArgMask = intRegState.rsCalleeRegArgMaskLiveIn; - // If there is a secret stub param, don't count it, as it will no longer - // be live when we do block init. - if (compiler->info.compPublishStubParam) - { - maskCalleeRegArgMask &= ~RBM_SECRET_STUB_PARAM; - } - #ifdef TARGET_ARM // // On the Arm if we are using a block init to initialize, then we @@ -5572,16 +5601,6 @@ void CodeGen::genFnProlog() } #endif // TARGET_ARM - if (compiler->info.compPublishStubParam) - { - GetEmitter()->emitIns_S_R(ins_Store(TYP_I_IMPL), EA_PTRSIZE, REG_SECRET_STUB_PARAM, - compiler->lvaStubArgumentVar, 0); - assert(intRegState.rsCalleeRegArgMaskLiveIn & RBM_SECRET_STUB_PARAM); - - // It's no longer live; clear it out so it can be used after this in the prolog - intRegState.rsCalleeRegArgMaskLiveIn &= ~RBM_SECRET_STUB_PARAM; - } - // // Zero out the frame as needed // diff --git a/src/coreclr/jit/compiler.cpp b/src/coreclr/jit/compiler.cpp index 6a16fa4e0d7f7..515976a96f507 100644 --- a/src/coreclr/jit/compiler.cpp +++ b/src/coreclr/jit/compiler.cpp @@ -4602,11 +4602,6 @@ void Compiler::compCompile(void** methodCodePtr, uint32_t* methodCodeSize, JitFl assert(lvaStubArgumentVar == BAD_VAR_NUM); lvaStubArgumentVar = lvaGrabTempWithImplicitUse(false DEBUGARG("stub argument")); lvaGetDesc(lvaStubArgumentVar)->lvType = TYP_I_IMPL; - // TODO-CQ: there is no need to mark it as doNotEnreg. There are no stores for this local - // before codegen so liveness and LSRA mark it as "liveIn" and always allocate a stack slot for it. - // However, it would be better to process it like other argument locals and keep it in - // a reg for the whole method without spilling to the stack when possible. - lvaSetVarDoNotEnregister(lvaStubArgumentVar DEBUGARG(DoNotEnregisterReason::VMNeedsStackAddr)); } }; DoPhase(this, PHASE_PRE_IMPORT, preImportPhase); diff --git a/src/coreclr/jit/compiler.h b/src/coreclr/jit/compiler.h index 080274dfb9d1b..b17ee58465b89 100644 --- a/src/coreclr/jit/compiler.h +++ b/src/coreclr/jit/compiler.h @@ -4243,7 +4243,7 @@ class Compiler return lvaGetDesc(lclNum)->lvInSsa; } - unsigned lvaStubArgumentVar; // variable representing the secret stub argument coming in EAX + unsigned lvaStubArgumentVar; // variable representing the secret stub argument unsigned lvaPSPSym; // variable representing the PSPSym diff --git a/src/coreclr/jit/flowgraph.cpp b/src/coreclr/jit/flowgraph.cpp index 151729b095051..b319fa2be3941 100644 --- a/src/coreclr/jit/flowgraph.cpp +++ b/src/coreclr/jit/flowgraph.cpp @@ -2438,7 +2438,10 @@ PhaseStatus Compiler::fgAddInternal() LclVarDsc* varDsc = lvaGetDesc(lvaInlinedPInvokeFrameVar); // Make room for the inlined frame. - lvaSetStruct(lvaInlinedPInvokeFrameVar, typGetBlkLayout(eeGetEEInfo()->inlinedCallFrameInfo.size), false); + const CORINFO_EE_INFO* eeInfo = eeGetEEInfo(); + unsigned frameSize = info.compPublishStubParam ? eeInfo->inlinedCallFrameInfo.sizeWithSecretStubArg + : eeInfo->inlinedCallFrameInfo.size; + lvaSetStruct(lvaInlinedPInvokeFrameVar, typGetBlkLayout(frameSize), false); } // Do we need to insert a "JustMyCode" callback? diff --git a/src/coreclr/jit/gentree.cpp b/src/coreclr/jit/gentree.cpp index 94124b0c1778b..1b52178682da5 100644 --- a/src/coreclr/jit/gentree.cpp +++ b/src/coreclr/jit/gentree.cpp @@ -13136,8 +13136,6 @@ const char* Compiler::gtGetWellKnownArgNameForArgMsg(WellKnownArg arg) return "retbuf"; case WellKnownArg::PInvokeFrame: return "pinv frame"; - case WellKnownArg::SecretStubParam: - return "stub param"; case WellKnownArg::WrapperDelegateCell: return "wrap cell"; case WellKnownArg::ShiftLow: diff --git a/src/coreclr/jit/gentree.h b/src/coreclr/jit/gentree.h index 7dbfef174994e..79e103423af7d 100644 --- a/src/coreclr/jit/gentree.h +++ b/src/coreclr/jit/gentree.h @@ -4465,7 +4465,6 @@ enum class WellKnownArg : unsigned InstParam, RetBuffer, PInvokeFrame, - SecretStubParam, WrapperDelegateCell, ShiftLow, ShiftHigh, diff --git a/src/coreclr/jit/lclvars.cpp b/src/coreclr/jit/lclvars.cpp index 5aa1e488b4ef5..0510611d8d488 100644 --- a/src/coreclr/jit/lclvars.cpp +++ b/src/coreclr/jit/lclvars.cpp @@ -6694,22 +6694,6 @@ void Compiler::lvaAssignVirtualFrameOffsetsToLocals() continue; } - // This should be low on the stack. Hence, it will be assigned later. - if (lclNum == lvaStubArgumentVar) - { -#ifdef JIT32_GCENCODER - noway_assert(codeGen->isFramePointerUsed()); -#endif - continue; - } - - // This should be low on the stack. Hence, it will be assigned later. - if (lclNum == lvaInlinedPInvokeFrameVar) - { - noway_assert(codeGen->isFramePointerUsed()); - continue; - } - if (varDsc->lvIsParam) { #ifdef TARGET_ARM64 @@ -6852,25 +6836,6 @@ void Compiler::lvaAssignVirtualFrameOffsetsToLocals() *------------------------------------------------------------------------- */ - // lvaInlinedPInvokeFrameVar and lvaStubArgumentVar need to be assigned last - // Important: The stack walker depends on lvaStubArgumentVar immediately - // following lvaInlinedPInvokeFrameVar in the frame. - - if (lvaStubArgumentVar != BAD_VAR_NUM) - { -#ifdef JIT32_GCENCODER - noway_assert(codeGen->isFramePointerUsed()); -#endif - stkOffs = lvaAllocLocalAndSetVirtualOffset(lvaStubArgumentVar, lvaLclSize(lvaStubArgumentVar), stkOffs); - } - - if (lvaInlinedPInvokeFrameVar != BAD_VAR_NUM) - { - noway_assert(codeGen->isFramePointerUsed()); - stkOffs = - lvaAllocLocalAndSetVirtualOffset(lvaInlinedPInvokeFrameVar, lvaLclSize(lvaInlinedPInvokeFrameVar), stkOffs); - } - #ifdef JIT32_GCENCODER // JIT32 encoder cannot handle GS cookie at fp+0 since NO_GS_COOKIE == 0. // Add some padding if it is the last allocated local. diff --git a/src/coreclr/jit/lower.cpp b/src/coreclr/jit/lower.cpp index 28538fc2b9053..e5261b04fe77d 100644 --- a/src/coreclr/jit/lower.cpp +++ b/src/coreclr/jit/lower.cpp @@ -5515,7 +5515,7 @@ GenTree* Lowering::CreateFrameLinkUpdate(FrameLinkAction action) const CORINFO_EE_INFO* pInfo = comp->eeGetEEInfo(); const CORINFO_EE_INFO::InlinedCallFrameInfo& callFrameInfo = pInfo->inlinedCallFrameInfo; - GenTree* TCB = new (comp, GT_LCL_VAR) GenTreeLclVar(GT_LCL_VAR, TYP_I_IMPL, comp->info.compLvFrameListRoot); + GenTree* TCB = comp->gtNewLclVarNode(comp->info.compLvFrameListRoot, TYP_I_IMPL); // Thread->m_pFrame GenTree* addr = new (comp, GT_LEA) GenTreeAddrMode(TYP_I_IMPL, TCB, nullptr, 1, pInfo->offsetOfThreadFrame); @@ -5525,18 +5525,17 @@ GenTree* Lowering::CreateFrameLinkUpdate(FrameLinkAction action) if (action == PushFrame) { // Thread->m_pFrame = &inlinedCallFrame; - data = new (comp, GT_LCL_ADDR) - GenTreeLclFld(GT_LCL_ADDR, TYP_BYREF, comp->lvaInlinedPInvokeFrameVar, callFrameInfo.offsetOfFrameVptr); + data = comp->gtNewLclAddrNode(comp->lvaInlinedPInvokeFrameVar, callFrameInfo.offsetOfFrameVptr); } else { assert(action == PopFrame); // Thread->m_pFrame = inlinedCallFrame.m_pNext; - data = new (comp, GT_LCL_FLD) GenTreeLclFld(GT_LCL_FLD, TYP_BYREF, comp->lvaInlinedPInvokeFrameVar, - pInfo->inlinedCallFrameInfo.offsetOfFrameLink); + data = comp->gtNewLclFldNode(comp->lvaInlinedPInvokeFrameVar, TYP_I_IMPL, + pInfo->inlinedCallFrameInfo.offsetOfFrameLink); } - GenTree* storeInd = new (comp, GT_STOREIND) GenTreeStoreInd(TYP_I_IMPL, addr, data); + GenTree* storeInd = comp->gtNewStoreIndNode(TYP_I_IMPL, addr, data); return storeInd; } @@ -5558,28 +5557,22 @@ GenTree* Lowering::CreateFrameLinkUpdate(FrameLinkAction action) // +08h +04h vptr for class InlinedCallFrame offsetOfFrameVptr method prolog // +10h +08h m_Next offsetOfFrameLink method prolog // +18h +0Ch m_Datum offsetOfCallTarget call site -// +20h n/a m_StubSecretArg not set by JIT -// +28h +10h m_pCallSiteSP offsetOfCallSiteSP x86: call site, and zeroed in method +// +20h +10h m_pCallSiteSP offsetOfCallSiteSP x86: call site, and zeroed in method // prolog; // non-x86: method prolog (SP remains // constant in function, after prolog: no // localloc and PInvoke in same function) -// +30h +14h m_pCallerReturnAddress offsetOfReturnAddress call site -// +38h +18h m_pCalleeSavedFP offsetOfCalleeSavedFP not set by JIT -// +1Ch m_pThread +// +28h +14h m_pCallerReturnAddress offsetOfReturnAddress call site +// +30h +18h m_pCalleeSavedFP offsetOfCalleeSavedFP not set by JIT +// +38h +1Ch m_pThread // +20h m_pSPAfterProlog offsetOfSPAfterProlog arm only -// +20/24h JIT retval spill area (int) before call_gc ??? -// +24/28h JIT retval spill area (long) before call_gc ??? -// +28/2Ch Saved value of EBP method prolog ??? +// +40h +20/24h m_StubSecretArg offsetOfSecretStubArg method prolog of IL stubs with secret arg // // Note that in the VM, InlinedCallFrame is a C++ class whose objects have a 'this' pointer that points // to the InlinedCallFrame vptr (the 2nd field listed above), and the GS cookie is stored *before* // the object. When we link the InlinedCallFrame onto the Frame chain, we must point at this location, // and not at the beginning of the InlinedCallFrame local, which is actually the GS cookie. // -// Return Value: -// none -// // See the usages for USE_PER_FRAME_PINVOKE_INIT for more information. void Lowering::InsertPInvokeMethodProlog() { @@ -5601,34 +5594,30 @@ void Lowering::InsertPInvokeMethodProlog() const CORINFO_EE_INFO* pInfo = comp->eeGetEEInfo(); const CORINFO_EE_INFO::InlinedCallFrameInfo& callFrameInfo = pInfo->inlinedCallFrameInfo; -// First arg: &compiler->lvaInlinedPInvokeFrameVar + callFrameInfo.offsetOfFrameVptr -#if defined(DEBUG) - const LclVarDsc* inlinedPInvokeDsc = comp->lvaGetDesc(comp->lvaInlinedPInvokeFrameVar); - assert(inlinedPInvokeDsc->IsAddressExposed()); -#endif // DEBUG - GenTree* frameAddr = new (comp, GT_LCL_ADDR) - GenTreeLclFld(GT_LCL_ADDR, TYP_BYREF, comp->lvaInlinedPInvokeFrameVar, callFrameInfo.offsetOfFrameVptr); + assert(comp->lvaGetDesc(comp->lvaInlinedPInvokeFrameVar)->IsAddressExposed()); - // Call runtime helper to fill in our InlinedCallFrame and push it on the Frame list: - // TCB = CORINFO_HELP_INIT_PINVOKE_FRAME(&symFrameStart, secretArg); - GenTreeCall* call = comp->gtNewHelperCallNode(CORINFO_HELP_INIT_PINVOKE_FRAME, TYP_I_IMPL); + GenTree* const insertionPoint = firstBlockRange.FirstNonCatchArgNode(); - NewCallArg frameAddrArg = NewCallArg::Primitive(frameAddr).WellKnown(WellKnownArg::PInvokeFrame); - call->gtArgs.PushBack(comp, frameAddrArg); -// for x86/arm32 don't pass the secretArg. -#if !defined(TARGET_X86) && !defined(TARGET_ARM) - GenTree* argNode; + // Store the stub secret arg if necessary. This has to be done before the + // call to the init helper below, which links the frame into the thread + // list on 32-bit platforms. + // InlinedCallFrame.m_StubSecretArg = stubSecretArg; if (comp->info.compPublishStubParam) { - argNode = comp->gtNewLclvNode(comp->lvaStubArgumentVar, TYP_I_IMPL); + GenTree* value = comp->gtNewLclvNode(comp->lvaStubArgumentVar, TYP_I_IMPL); + GenTree* store = comp->gtNewStoreLclFldNode(comp->lvaInlinedPInvokeFrameVar, TYP_I_IMPL, + callFrameInfo.offsetOfSecretStubArg, value); + firstBlockRange.InsertBefore(insertionPoint, LIR::SeqTree(comp, store)); + DISPTREERANGE(firstBlockRange, store); } - else - { - argNode = comp->gtNewIconNode(0, TYP_I_IMPL); - } - NewCallArg stubParamArg = NewCallArg::Primitive(argNode).WellKnown(WellKnownArg::SecretStubParam); - call->gtArgs.PushBack(comp, stubParamArg); -#endif + + // Call runtime helper to fill in our InlinedCallFrame and push it on the Frame list: + // TCB = CORINFO_HELP_INIT_PINVOKE_FRAME(&symFrameStart); + GenTree* frameAddr = comp->gtNewLclAddrNode(comp->lvaInlinedPInvokeFrameVar, callFrameInfo.offsetOfFrameVptr); + NewCallArg frameAddrArg = NewCallArg::Primitive(frameAddr).WellKnown(WellKnownArg::PInvokeFrame); + + GenTreeCall* call = comp->gtNewHelperCallNode(CORINFO_HELP_INIT_PINVOKE_FRAME, TYP_I_IMPL); + call->gtArgs.PushBack(comp, frameAddrArg); // some sanity checks on the frame list root vardsc const unsigned lclNum = comp->info.compLvFrameListRoot; @@ -5636,12 +5625,7 @@ void Lowering::InsertPInvokeMethodProlog() noway_assert(!varDsc->lvIsParam); noway_assert(varDsc->lvType == TYP_I_IMPL); - GenTree* store = new (comp, GT_STORE_LCL_VAR) GenTreeLclVar(GT_STORE_LCL_VAR, TYP_I_IMPL, lclNum); - store->AsOp()->gtOp1 = call; - store->gtFlags |= GTF_VAR_DEF; - - GenTree* const insertionPoint = firstBlockRange.FirstNonCatchArgNode(); - + GenTree* store = comp->gtNewStoreLclVarNode(lclNum, call); comp->fgMorphTree(store); firstBlockRange.InsertBefore(insertionPoint, LIR::SeqTree(comp, store)); DISPTREERANGE(firstBlockRange, store); @@ -5656,7 +5640,6 @@ void Lowering::InsertPInvokeMethodProlog() GenTree* spValue = PhysReg(REG_SPBASE); GenTreeLclFld* storeSP = comp->gtNewStoreLclFldNode(comp->lvaInlinedPInvokeFrameVar, TYP_I_IMPL, callFrameInfo.offsetOfCallSiteSP, spValue); - assert(inlinedPInvokeDsc->lvDoNotEnregister); firstBlockRange.InsertBefore(insertionPoint, LIR::SeqTree(comp, storeSP)); DISPTREERANGE(firstBlockRange, storeSP); @@ -5672,7 +5655,6 @@ void Lowering::InsertPInvokeMethodProlog() GenTree* fpValue = PhysReg(REG_FPBASE); GenTreeLclFld* storeFP = comp->gtNewStoreLclFldNode(comp->lvaInlinedPInvokeFrameVar, TYP_I_IMPL, callFrameInfo.offsetOfCalleeSavedFP, fpValue); - assert(inlinedPInvokeDsc->lvDoNotEnregister); firstBlockRange.InsertBefore(insertionPoint, LIR::SeqTree(comp, storeFP)); DISPTREERANGE(firstBlockRange, storeFP); diff --git a/src/coreclr/jit/lsra.h b/src/coreclr/jit/lsra.h index 51ab3dcc65a67..a80bf94c770be 100644 --- a/src/coreclr/jit/lsra.h +++ b/src/coreclr/jit/lsra.h @@ -644,6 +644,8 @@ class LinearScan : public LinearScanInterface template void buildIntervals(); + void buildInitialParamDef(const LclVarDsc* varDsc, regNumber paramReg); + // This is where the actual assignment is done for scenarios where // no local var enregistration is done. void allocateRegistersMinimal(); diff --git a/src/coreclr/jit/lsrabuild.cpp b/src/coreclr/jit/lsrabuild.cpp index b36695280809f..43c75a118b218 100644 --- a/src/coreclr/jit/lsrabuild.cpp +++ b/src/coreclr/jit/lsrabuild.cpp @@ -2327,20 +2327,7 @@ void LinearScan::buildIntervals() if (isCandidateVar(argDsc)) { - Interval* interval = getIntervalForLocalVar(varIndex); - const var_types regType = argDsc->GetRegisterType(); - regMaskTP mask = allRegs(regType); - if (argDsc->lvIsRegArg && !stressInitialParamReg()) - { - // Set this interval as currently assigned to that register - regNumber inArgReg = argDsc->GetArgReg(); - assert(inArgReg < REG_COUNT); - mask = genRegMask(inArgReg); - assignPhysReg(inArgReg, interval); - INDEBUG(registersToDump |= getRegMask(inArgReg, interval->registerType)); - } - RefPosition* pos = newRefPosition(interval, MinLocation, RefTypeParamDef, nullptr, mask); - pos->setRegOptional(true); + buildInitialParamDef(argDsc, argDsc->lvIsRegArg ? argDsc->GetArgReg() : REG_NA); } else if (argDsc->lvPromoted) { @@ -2351,10 +2338,7 @@ void LinearScan::buildIntervals() if (fieldVarDsc->lvLRACandidate) { assert(fieldVarDsc->lvTracked); - Interval* interval = getIntervalForLocalVar(fieldVarDsc->lvVarIndex); - RefPosition* pos = - newRefPosition(interval, MinLocation, RefTypeParamDef, nullptr, allRegs(TypeGet(fieldVarDsc))); - pos->setRegOptional(true); + buildInitialParamDef(fieldVarDsc, REG_NA); } } } @@ -2401,6 +2385,12 @@ void LinearScan::buildIntervals() if (compiler->info.compPublishStubParam) { intRegState->rsCalleeRegArgMaskLiveIn |= RBM_SECRET_STUB_PARAM; + + LclVarDsc* stubParamDsc = compiler->lvaGetDesc(compiler->lvaStubArgumentVar); + if (isCandidateVar(stubParamDsc)) + { + buildInitialParamDef(stubParamDsc, REG_SECRET_STUB_PARAM); + } } #ifdef DEBUG @@ -2858,6 +2848,32 @@ void LinearScan::buildIntervals() #endif // DEBUG } +//------------------------------------------------------------------------ +// buildInitialParamDef: Build the initial definition for a parameter. +// +// Parameters: +// varDsc - LclVarDsc* for parameter +// paramReg - Register that parameter is in +// +void LinearScan::buildInitialParamDef(const LclVarDsc* varDsc, regNumber paramReg) +{ + assert(isCandidateVar(varDsc)); + + Interval* interval = getIntervalForLocalVar(varDsc->lvVarIndex); + const var_types regType = varDsc->GetRegisterType(); + regMaskTP mask = allRegs(regType); + if ((paramReg != REG_NA) && !stressInitialParamReg()) + { + // Set this interval as currently assigned to that register + assert(paramReg < REG_COUNT); + mask = genRegMask(paramReg); + assignPhysReg(paramReg, interval); + INDEBUG(registersToDump |= getRegMask(paramReg, interval->registerType)); + } + RefPosition* pos = newRefPosition(interval, MinLocation, RefTypeParamDef, nullptr, mask); + pos->setRegOptional(true); +} + #ifdef DEBUG //------------------------------------------------------------------------ diff --git a/src/coreclr/jit/morph.cpp b/src/coreclr/jit/morph.cpp index 7b76a74b5f4c8..9e18a38281baf 100644 --- a/src/coreclr/jit/morph.cpp +++ b/src/coreclr/jit/morph.cpp @@ -765,8 +765,6 @@ const char* getWellKnownArgName(WellKnownArg arg) return "RetBuffer"; case WellKnownArg::PInvokeFrame: return "PInvokeFrame"; - case WellKnownArg::SecretStubParam: - return "SecretStubParam"; case WellKnownArg::WrapperDelegateCell: return "WrapperDelegateCell"; case WellKnownArg::ShiftLow: diff --git a/src/coreclr/tools/Common/JitInterface/CorInfoImpl.cs b/src/coreclr/tools/Common/JitInterface/CorInfoImpl.cs index 31a5dd68927bd..8adbb56aaa070 100644 --- a/src/coreclr/tools/Common/JitInterface/CorInfoImpl.cs +++ b/src/coreclr/tools/Common/JitInterface/CorInfoImpl.cs @@ -3283,7 +3283,7 @@ private void getEEInfo(ref CORINFO_EE_INFO pEEInfoOut) // In debug, write some bogus data to the struct to ensure we have filled everything // properly. fixed (CORINFO_EE_INFO* tmp = &pEEInfoOut) - MemoryHelper.FillMemory((byte*)tmp, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(tmp, (nuint)sizeof(CORINFO_EE_INFO), 0xcc); #endif int pointerSize = this.PointerSize; diff --git a/src/coreclr/tools/Common/JitInterface/CorInfoTypes.cs b/src/coreclr/tools/Common/JitInterface/CorInfoTypes.cs index 960b2e8e8113b..3eba98954c1c5 100644 --- a/src/coreclr/tools/Common/JitInterface/CorInfoTypes.cs +++ b/src/coreclr/tools/Common/JitInterface/CorInfoTypes.cs @@ -836,6 +836,9 @@ public struct InlinedCallFrameInfo // Size of the Frame structure public uint size; + // Size of the Frame structure inside IL stubs that include secret stub arg in the frame + public uint sizeWithSecretStubArg; + public uint offsetOfGSCookie; public uint offsetOfFrameVptr; public uint offsetOfFrameLink; @@ -843,6 +846,7 @@ public struct InlinedCallFrameInfo public uint offsetOfCalleeSavedFP; public uint offsetOfCallTarget; public uint offsetOfReturnAddress; + public uint offsetOfSecretStubArg; public uint offsetOfSPAfterProlog; } public InlinedCallFrameInfo inlinedCallFrameInfo; diff --git a/src/coreclr/tools/Common/JitInterface/MemoryHelper.cs b/src/coreclr/tools/Common/JitInterface/MemoryHelper.cs deleted file mode 100644 index ac009bcd17da1..0000000000000 --- a/src/coreclr/tools/Common/JitInterface/MemoryHelper.cs +++ /dev/null @@ -1,17 +0,0 @@ -// Licensed to the .NET Foundation under one or more agreements. -// The .NET Foundation licenses this file to you under the MIT license. - -namespace Internal.JitInterface -{ - internal static unsafe class MemoryHelper - { - public static void FillMemory(byte* dest, byte fill, int count) - { - for (; count > 0; count--) - { - *dest = fill; - dest++; - } - } - } -} diff --git a/src/coreclr/tools/aot/ILCompiler.Compiler/ILCompiler.Compiler.csproj b/src/coreclr/tools/aot/ILCompiler.Compiler/ILCompiler.Compiler.csproj index eb9db7165be26..e81340150e769 100644 --- a/src/coreclr/tools/aot/ILCompiler.Compiler/ILCompiler.Compiler.csproj +++ b/src/coreclr/tools/aot/ILCompiler.Compiler/ILCompiler.Compiler.csproj @@ -729,9 +729,6 @@ JitInterface\CorInfoTypes.VarInfo.cs - - JitInterface\MemoryHelper.cs - TypeSystem\TypesDebugInfoWriter\TypesDebugInfoWriter.cs diff --git a/src/coreclr/tools/aot/ILCompiler.ReadyToRun/ILCompiler.ReadyToRun.csproj b/src/coreclr/tools/aot/ILCompiler.ReadyToRun/ILCompiler.ReadyToRun.csproj index 04fb0838bee7d..96e6df9805eb0 100644 --- a/src/coreclr/tools/aot/ILCompiler.ReadyToRun/ILCompiler.ReadyToRun.csproj +++ b/src/coreclr/tools/aot/ILCompiler.ReadyToRun/ILCompiler.ReadyToRun.csproj @@ -332,9 +332,6 @@ JitInterface\JitConfigProvider.cs - - JitInterface\MemoryHelper.cs - JitInterface\UnboxingMethodDesc.cs diff --git a/src/coreclr/tools/aot/ILCompiler.ReadyToRun/JitInterface/CorInfoImpl.ReadyToRun.cs b/src/coreclr/tools/aot/ILCompiler.ReadyToRun/JitInterface/CorInfoImpl.ReadyToRun.cs index 7f702fd6b764a..8e3eb3a3d9257 100644 --- a/src/coreclr/tools/aot/ILCompiler.ReadyToRun/JitInterface/CorInfoImpl.ReadyToRun.cs +++ b/src/coreclr/tools/aot/ILCompiler.ReadyToRun/JitInterface/CorInfoImpl.ReadyToRun.cs @@ -934,7 +934,7 @@ private void getReadyToRunDelegateCtorHelper(ref CORINFO_RESOLVED_TOKEN pTargetM // In debug, write some bogus data to the struct to ensure we have filled everything // properly. fixed (CORINFO_LOOKUP* tmp = &pLookup) - MemoryHelper.FillMemory((byte*)tmp, 0xcc, sizeof(CORINFO_LOOKUP)); + NativeMemory.Fill(tmp, (nuint)sizeof(CORINFO_LOOKUP), 0xcc); #endif TypeDesc delegateTypeDesc = HandleToObject(delegateType); @@ -1663,7 +1663,7 @@ private void getFieldInfo(ref CORINFO_RESOLVED_TOKEN pResolvedToken, CORINFO_MET #if DEBUG // In debug, write some bogus data to the struct to ensure we have filled everything // properly. - MemoryHelper.FillMemory((byte*)pResult, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(pResult, (nuint)sizeof(CORINFO_FIELD_INFO), 0xcc); #endif Debug.Assert(((int)flags & ((int)CORINFO_ACCESS_FLAGS.CORINFO_ACCESS_GET | @@ -1847,7 +1847,7 @@ private void ceeInfoGetCallInfo( #if DEBUG // In debug, write some bogus data to the struct to ensure we have filled everything // properly. - MemoryHelper.FillMemory((byte*)pResult, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(pResult, (nuint)sizeof(CORINFO_CALL_INFO), 0xcc); #endif pResult->codePointerOrStubLookup.lookupKind.needsRuntimeLookup = false; @@ -2648,7 +2648,7 @@ private void ceeInfoEmbedGenericHandle(ref CORINFO_RESOLVED_TOKEN pResolvedToken // In debug, write some bogus data to the struct to ensure we have filled everything // properly. fixed (CORINFO_GENERICHANDLE_RESULT* tmp = &pResult) - MemoryHelper.FillMemory((byte*)tmp, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(tmp, (nuint)sizeof(CORINFO_GENERICHANDLE_RESULT), 0xcc); #endif bool runtimeLookup = false; diff --git a/src/coreclr/tools/aot/ILCompiler.RyuJit/ILCompiler.RyuJit.csproj b/src/coreclr/tools/aot/ILCompiler.RyuJit/ILCompiler.RyuJit.csproj index e785f9b427190..3ddf3e46a13cb 100644 --- a/src/coreclr/tools/aot/ILCompiler.RyuJit/ILCompiler.RyuJit.csproj +++ b/src/coreclr/tools/aot/ILCompiler.RyuJit/ILCompiler.RyuJit.csproj @@ -73,9 +73,6 @@ JitInterface\CorInfoImpl.cs - - JitInterface\MemoryHelper.cs - JitInterface\UnboxingMethodDesc.cs diff --git a/src/coreclr/tools/aot/ILCompiler.RyuJit/JitInterface/CorInfoImpl.RyuJit.cs b/src/coreclr/tools/aot/ILCompiler.RyuJit/JitInterface/CorInfoImpl.RyuJit.cs index d344dd431fb55..2e4013c9081bb 100644 --- a/src/coreclr/tools/aot/ILCompiler.RyuJit/JitInterface/CorInfoImpl.RyuJit.cs +++ b/src/coreclr/tools/aot/ILCompiler.RyuJit/JitInterface/CorInfoImpl.RyuJit.cs @@ -363,7 +363,7 @@ private void getReadyToRunDelegateCtorHelper(ref CORINFO_RESOLVED_TOKEN pTargetM // In debug, write some bogus data to the struct to ensure we have filled everything // properly. fixed (CORINFO_LOOKUP* tmp = &pLookup) - MemoryHelper.FillMemory((byte*)tmp, 0xcc, sizeof(CORINFO_LOOKUP)); + NativeMemory.Fill(tmp, (nuint)sizeof(CORINFO_LOOKUP), 0xcc); #endif MethodDesc expectedTargetMethod = HandleToObject(pTargetMethod.hMethod); @@ -1193,7 +1193,7 @@ private void getCallInfo(ref CORINFO_RESOLVED_TOKEN pResolvedToken, CORINFO_RESO #if DEBUG // In debug, write some bogus data to the struct to ensure we have filled everything // properly. - MemoryHelper.FillMemory((byte*)pResult, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(pResult, (nuint)sizeof(CORINFO_CALL_INFO), 0xcc); #endif MethodDesc method = HandleToObject(pResolvedToken.hMethod); @@ -1701,7 +1701,7 @@ private void embedGenericHandle(ref CORINFO_RESOLVED_TOKEN pResolvedToken, bool // In debug, write some bogus data to the struct to ensure we have filled everything // properly. fixed (CORINFO_GENERICHANDLE_RESULT* tmp = &pResult) - MemoryHelper.FillMemory((byte*)tmp, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(tmp, (nuint)sizeof(CORINFO_GENERICHANDLE_RESULT), 0xcc); #endif ReadyToRunHelperId helperId = ReadyToRunHelperId.Invalid; object target = null; @@ -2060,7 +2060,7 @@ private void getFieldInfo(ref CORINFO_RESOLVED_TOKEN pResolvedToken, CORINFO_MET #if DEBUG // In debug, write some bogus data to the struct to ensure we have filled everything // properly. - MemoryHelper.FillMemory((byte*)pResult, 0xcc, Marshal.SizeOf()); + NativeMemory.Fill(pResult, (nuint)sizeof(CORINFO_FIELD_INFO), 0xcc); #endif Debug.Assert(((int)flags & ((int)CORINFO_ACCESS_FLAGS.CORINFO_ACCESS_GET | diff --git a/src/coreclr/tools/superpmi/superpmi-shared/agnostic.h b/src/coreclr/tools/superpmi/superpmi-shared/agnostic.h index 4e34350894ec7..7f382f4d967b4 100644 --- a/src/coreclr/tools/superpmi/superpmi-shared/agnostic.h +++ b/src/coreclr/tools/superpmi/superpmi-shared/agnostic.h @@ -172,6 +172,7 @@ struct Agnostic_CORINFO_EE_INFO struct Agnostic_InlinedCallFrameInfo { DWORD size; + DWORD sizeWithSecretStubArg; DWORD offsetOfGSCookie; DWORD offsetOfFrameVptr; DWORD offsetOfFrameLink; @@ -179,6 +180,8 @@ struct Agnostic_CORINFO_EE_INFO DWORD offsetOfCalleeSavedFP; DWORD offsetOfCallTarget; DWORD offsetOfReturnAddress; + DWORD offsetOfSecretStubArg; + DWORD offsetOfSPAfterProlog; } inlinedCallFrameInfo; DWORD offsetOfThreadFrame; DWORD offsetOfGCState; diff --git a/src/coreclr/tools/superpmi/superpmi-shared/methodcontext.cpp b/src/coreclr/tools/superpmi/superpmi-shared/methodcontext.cpp index 25e3b1c774415..b3ffb7e7edf85 100644 --- a/src/coreclr/tools/superpmi/superpmi-shared/methodcontext.cpp +++ b/src/coreclr/tools/superpmi/superpmi-shared/methodcontext.cpp @@ -4305,6 +4305,7 @@ void MethodContext::recGetEEInfo(CORINFO_EE_INFO* pEEInfoOut) Agnostic_CORINFO_EE_INFO value; value.inlinedCallFrameInfo.size = (DWORD)pEEInfoOut->inlinedCallFrameInfo.size; + value.inlinedCallFrameInfo.sizeWithSecretStubArg = (DWORD)pEEInfoOut->inlinedCallFrameInfo.sizeWithSecretStubArg; value.inlinedCallFrameInfo.offsetOfGSCookie = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfGSCookie; value.inlinedCallFrameInfo.offsetOfFrameVptr = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameVptr; value.inlinedCallFrameInfo.offsetOfFrameLink = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameLink; @@ -4312,6 +4313,8 @@ void MethodContext::recGetEEInfo(CORINFO_EE_INFO* pEEInfoOut) value.inlinedCallFrameInfo.offsetOfCalleeSavedFP = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfCalleeSavedFP; value.inlinedCallFrameInfo.offsetOfCallTarget = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfCallTarget; value.inlinedCallFrameInfo.offsetOfReturnAddress = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfReturnAddress; + value.inlinedCallFrameInfo.offsetOfSecretStubArg = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfSecretStubArg; + value.inlinedCallFrameInfo.offsetOfSPAfterProlog = (DWORD)pEEInfoOut->inlinedCallFrameInfo.offsetOfSPAfterProlog; value.offsetOfThreadFrame = (DWORD)pEEInfoOut->offsetOfThreadFrame; value.offsetOfGCState = (DWORD)pEEInfoOut->offsetOfGCState; value.offsetOfDelegateInstance = (DWORD)pEEInfoOut->offsetOfDelegateInstance; @@ -4328,12 +4331,14 @@ void MethodContext::recGetEEInfo(CORINFO_EE_INFO* pEEInfoOut) } void MethodContext::dmpGetEEInfo(DWORD key, const Agnostic_CORINFO_EE_INFO& value) { - printf("GetEEInfo key %u, value icfi{sz-%u ogs-%u ofv-%u ofl-%u ocsp-%u ocsfp-%u oct-%u ora-%u} " + printf("GetEEInfo key %u, value icfi{sz-%u sz-witharg-%u ogs-%u ofv-%u ofl-%u ocsp-%u ocsfp-%u oct-%u ora-%u ossa-%u osap-%u} " "otf-%u ogcs-%u odi-%u odft-%u osdic-%u srpf-%u osps-%u muono-%u tabi-%u osType-%u", - key, value.inlinedCallFrameInfo.size, value.inlinedCallFrameInfo.offsetOfGSCookie, + key, value.inlinedCallFrameInfo.size, value.inlinedCallFrameInfo.sizeWithSecretStubArg, + value.inlinedCallFrameInfo.offsetOfGSCookie, value.inlinedCallFrameInfo.offsetOfFrameVptr, value.inlinedCallFrameInfo.offsetOfFrameLink, value.inlinedCallFrameInfo.offsetOfCallSiteSP, value.inlinedCallFrameInfo.offsetOfCalleeSavedFP, value.inlinedCallFrameInfo.offsetOfCallTarget, value.inlinedCallFrameInfo.offsetOfReturnAddress, + value.inlinedCallFrameInfo.offsetOfSecretStubArg, value.inlinedCallFrameInfo.offsetOfSPAfterProlog, value.offsetOfThreadFrame, value.offsetOfGCState, value.offsetOfDelegateInstance, value.offsetOfDelegateFirstTarget, value.offsetOfWrapperDelegateIndirectCell, value.sizeOfReversePInvokeFrame, value.osPageSize, value.maxUncheckedOffsetForNullObject, value.targetAbi, @@ -4341,64 +4346,33 @@ void MethodContext::dmpGetEEInfo(DWORD key, const Agnostic_CORINFO_EE_INFO& valu } void MethodContext::repGetEEInfo(CORINFO_EE_INFO* pEEInfoOut) { - Agnostic_CORINFO_EE_INFO value; - - int index = -1; - if (GetEEInfo != nullptr) - index = GetEEInfo->GetIndex((DWORD)0); - if (index >= 0) - { - value = GetEEInfo->Get(0); - DEBUG_REP(dmpGetEEInfo(0, value)); - - pEEInfoOut->inlinedCallFrameInfo.size = (unsigned)value.inlinedCallFrameInfo.size; - pEEInfoOut->inlinedCallFrameInfo.offsetOfGSCookie = (unsigned)value.inlinedCallFrameInfo.offsetOfGSCookie; - pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameVptr = (unsigned)value.inlinedCallFrameInfo.offsetOfFrameVptr; - pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameLink = (unsigned)value.inlinedCallFrameInfo.offsetOfFrameLink; - pEEInfoOut->inlinedCallFrameInfo.offsetOfCallSiteSP = (unsigned)value.inlinedCallFrameInfo.offsetOfCallSiteSP; - pEEInfoOut->inlinedCallFrameInfo.offsetOfCalleeSavedFP = - (unsigned)value.inlinedCallFrameInfo.offsetOfCalleeSavedFP; - pEEInfoOut->inlinedCallFrameInfo.offsetOfCallTarget = (unsigned)value.inlinedCallFrameInfo.offsetOfCallTarget; - pEEInfoOut->inlinedCallFrameInfo.offsetOfReturnAddress = - (unsigned)value.inlinedCallFrameInfo.offsetOfReturnAddress; - pEEInfoOut->offsetOfThreadFrame = (unsigned)value.offsetOfThreadFrame; - pEEInfoOut->offsetOfGCState = (unsigned)value.offsetOfGCState; - pEEInfoOut->offsetOfDelegateInstance = (unsigned)value.offsetOfDelegateInstance; - pEEInfoOut->offsetOfDelegateFirstTarget = (unsigned)value.offsetOfDelegateFirstTarget; - pEEInfoOut->offsetOfWrapperDelegateIndirectCell= (unsigned)value.offsetOfWrapperDelegateIndirectCell; - pEEInfoOut->sizeOfReversePInvokeFrame = (unsigned)value.sizeOfReversePInvokeFrame; - pEEInfoOut->osPageSize = (size_t)value.osPageSize; - pEEInfoOut->maxUncheckedOffsetForNullObject = (size_t)value.maxUncheckedOffsetForNullObject; - pEEInfoOut->targetAbi = (CORINFO_RUNTIME_ABI)value.targetAbi; - pEEInfoOut->osType = (CORINFO_OS)value.osType; - } - else - { - pEEInfoOut->inlinedCallFrameInfo.size = (unsigned)0x40; - pEEInfoOut->inlinedCallFrameInfo.offsetOfGSCookie = (unsigned)0; - pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameVptr = (unsigned)0x8; - pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameLink = (unsigned)0x10; - pEEInfoOut->inlinedCallFrameInfo.offsetOfCallSiteSP = (unsigned)0x28; - pEEInfoOut->inlinedCallFrameInfo.offsetOfCalleeSavedFP = (unsigned)0x38; - pEEInfoOut->inlinedCallFrameInfo.offsetOfCallTarget = (unsigned)0x18; - pEEInfoOut->inlinedCallFrameInfo.offsetOfReturnAddress = (unsigned)0x30; - pEEInfoOut->offsetOfThreadFrame = (unsigned)0x10; - pEEInfoOut->offsetOfGCState = (unsigned)0xc; - pEEInfoOut->offsetOfDelegateInstance = (unsigned)0x8; - pEEInfoOut->offsetOfDelegateFirstTarget = (unsigned)0x18; - pEEInfoOut->offsetOfWrapperDelegateIndirectCell = (unsigned)0x40; - pEEInfoOut->sizeOfReversePInvokeFrame = (unsigned)0x8; - pEEInfoOut->osPageSize = (size_t)0x1000; - pEEInfoOut->maxUncheckedOffsetForNullObject = (size_t)((32 * 1024) - 1); - pEEInfoOut->targetAbi = CORINFO_CORECLR_ABI; -#ifdef TARGET_OSX - pEEInfoOut->osType = CORINFO_APPLE; -#elif defined(TARGET_UNIX) - pEEInfoOut->osType = CORINFO_UNIX; -#else - pEEInfoOut->osType = CORINFO_WINNT; -#endif - } + Agnostic_CORINFO_EE_INFO value = LookupByKeyOrMissNoMessage(GetEEInfo, 0); + + DEBUG_REP(dmpGetEEInfo(0, value)); + + pEEInfoOut->inlinedCallFrameInfo.size = (unsigned)value.inlinedCallFrameInfo.size; + pEEInfoOut->inlinedCallFrameInfo.sizeWithSecretStubArg = (unsigned)value.inlinedCallFrameInfo.sizeWithSecretStubArg; + pEEInfoOut->inlinedCallFrameInfo.offsetOfGSCookie = (unsigned)value.inlinedCallFrameInfo.offsetOfGSCookie; + pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameVptr = (unsigned)value.inlinedCallFrameInfo.offsetOfFrameVptr; + pEEInfoOut->inlinedCallFrameInfo.offsetOfFrameLink = (unsigned)value.inlinedCallFrameInfo.offsetOfFrameLink; + pEEInfoOut->inlinedCallFrameInfo.offsetOfCallSiteSP = (unsigned)value.inlinedCallFrameInfo.offsetOfCallSiteSP; + pEEInfoOut->inlinedCallFrameInfo.offsetOfCalleeSavedFP = + (unsigned)value.inlinedCallFrameInfo.offsetOfCalleeSavedFP; + pEEInfoOut->inlinedCallFrameInfo.offsetOfCallTarget = (unsigned)value.inlinedCallFrameInfo.offsetOfCallTarget; + pEEInfoOut->inlinedCallFrameInfo.offsetOfReturnAddress = + (unsigned)value.inlinedCallFrameInfo.offsetOfReturnAddress; + pEEInfoOut->inlinedCallFrameInfo.offsetOfSecretStubArg = (unsigned)value.inlinedCallFrameInfo.offsetOfSecretStubArg; + pEEInfoOut->inlinedCallFrameInfo.offsetOfSPAfterProlog = (unsigned)value.inlinedCallFrameInfo.offsetOfSPAfterProlog; + pEEInfoOut->offsetOfThreadFrame = (unsigned)value.offsetOfThreadFrame; + pEEInfoOut->offsetOfGCState = (unsigned)value.offsetOfGCState; + pEEInfoOut->offsetOfDelegateInstance = (unsigned)value.offsetOfDelegateInstance; + pEEInfoOut->offsetOfDelegateFirstTarget = (unsigned)value.offsetOfDelegateFirstTarget; + pEEInfoOut->offsetOfWrapperDelegateIndirectCell= (unsigned)value.offsetOfWrapperDelegateIndirectCell; + pEEInfoOut->sizeOfReversePInvokeFrame = (unsigned)value.sizeOfReversePInvokeFrame; + pEEInfoOut->osPageSize = (size_t)value.osPageSize; + pEEInfoOut->maxUncheckedOffsetForNullObject = (size_t)value.maxUncheckedOffsetForNullObject; + pEEInfoOut->targetAbi = (CORINFO_RUNTIME_ABI)value.targetAbi; + pEEInfoOut->osType = (CORINFO_OS)value.osType; } void MethodContext::recGetGSCookie(GSCookie* pCookieVal, GSCookie** ppCookieVal) diff --git a/src/coreclr/vm/amd64/asmconstants.h b/src/coreclr/vm/amd64/asmconstants.h index f51f3b00836b7..627938c445c46 100644 --- a/src/coreclr/vm/amd64/asmconstants.h +++ b/src/coreclr/vm/amd64/asmconstants.h @@ -501,19 +501,19 @@ ASMCONSTANTS_C_ASSERT(OFFSETOF__StringObject__m_StringLength ASMCONSTANTS_C_ASSERT(OFFSETOF__InlinedCallFrame__m_Datum == offsetof(InlinedCallFrame, m_Datum)); -#define OFFSETOF__InlinedCallFrame__m_pCallSiteSP 0x20 +#define OFFSETOF__InlinedCallFrame__m_pCallSiteSP 0x18 ASMCONSTANTS_C_ASSERT(OFFSETOF__InlinedCallFrame__m_pCallSiteSP == offsetof(InlinedCallFrame, m_pCallSiteSP)); -#define OFFSETOF__InlinedCallFrame__m_pCallerReturnAddress 0x28 +#define OFFSETOF__InlinedCallFrame__m_pCallerReturnAddress 0x20 ASMCONSTANTS_C_ASSERT(OFFSETOF__InlinedCallFrame__m_pCallerReturnAddress == offsetof(InlinedCallFrame, m_pCallerReturnAddress)); -#define OFFSETOF__InlinedCallFrame__m_pCalleeSavedFP 0x30 +#define OFFSETOF__InlinedCallFrame__m_pCalleeSavedFP 0x28 ASMCONSTANTS_C_ASSERT(OFFSETOF__InlinedCallFrame__m_pCalleeSavedFP == offsetof(InlinedCallFrame, m_pCalleeSavedFP)); -#define OFFSETOF__InlinedCallFrame__m_pThread 0x38 +#define OFFSETOF__InlinedCallFrame__m_pThread 0x30 ASMCONSTANTS_C_ASSERT(OFFSETOF__InlinedCallFrame__m_pThread == offsetof(InlinedCallFrame, m_pThread)); diff --git a/src/coreclr/vm/arm64/asmconstants.h b/src/coreclr/vm/arm64/asmconstants.h index c002916963f42..c0d6012aab9ec 100644 --- a/src/coreclr/vm/arm64/asmconstants.h +++ b/src/coreclr/vm/arm64/asmconstants.h @@ -204,16 +204,16 @@ ASMCONSTANTS_C_ASSERT(Frame__m_Next == offsetof(Frame, m_Next)) #define InlinedCallFrame__m_Datum 0x10 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_Datum == offsetof(InlinedCallFrame, m_Datum)) -#define InlinedCallFrame__m_pCallSiteSP 0x20 +#define InlinedCallFrame__m_pCallSiteSP 0x18 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCallSiteSP == offsetof(InlinedCallFrame, m_pCallSiteSP)) -#define InlinedCallFrame__m_pCallerReturnAddress 0x28 +#define InlinedCallFrame__m_pCallerReturnAddress 0x20 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCallerReturnAddress == offsetof(InlinedCallFrame, m_pCallerReturnAddress)) -#define InlinedCallFrame__m_pCalleeSavedFP 0x30 +#define InlinedCallFrame__m_pCalleeSavedFP 0x28 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCalleeSavedFP == offsetof(InlinedCallFrame, m_pCalleeSavedFP)) -#define InlinedCallFrame__m_pThread 0x38 +#define InlinedCallFrame__m_pThread 0x30 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pThread == offsetof(InlinedCallFrame, m_pThread)) #define FixupPrecodeData__Target 0x00 diff --git a/src/coreclr/vm/frames.h b/src/coreclr/vm/frames.h index 3d3fe177bcbb8..68706cd52304d 100644 --- a/src/coreclr/vm/frames.h +++ b/src/coreclr/vm/frames.h @@ -730,7 +730,7 @@ class Frame : public FrameBase friend LONG WINAPI CLRVectoredExceptionHandlerShim(PEXCEPTION_POINTERS pExceptionInfo); #endif #ifdef HOST_64BIT - friend Thread * __stdcall JIT_InitPInvokeFrame(InlinedCallFrame *pFrame, PTR_VOID StubSecretArg); + friend Thread * JIT_InitPInvokeFrame(InlinedCallFrame *pFrame); #endif #ifdef FEATURE_EH_FUNCLETS friend class ExceptionTracker; @@ -2852,31 +2852,10 @@ class InlinedCallFrame : public Frame // method if the current InlinedCallFrame is inactive. PTR_MethodDesc GetActualInteropMethodDesc() { -#if defined(TARGET_X86) || defined(TARGET_ARM) - // Important: This code relies on the way JIT lays out frames. Keep it in sync - // with code:Compiler.lvaAssignFrameOffsets. - // - // | ... | - // +--------------------+ - // | lvaStubArgumentVar | <= filled with EAX in prolog | - // +--------------------+ | - // | | | - // | InlinedCallFrame | | - // | | <= m_pCrawl.pFrame | to lower addresses - // +--------------------+ V - // | ... | - // - // Extract the actual MethodDesc to report from the InlinedCallFrame. + // The VM instructs the JIT to publish the secret stub arg at the end + // of the InlinedCallFrame structure when it exists. TADDR addr = dac_cast(this) + sizeof(InlinedCallFrame); return PTR_MethodDesc(*PTR_TADDR(addr)); -#elif defined(HOST_64BIT) - // On 64bit, the actual interop MethodDesc is saved off in a field off the InlinedCrawlFrame - // which is populated by the JIT. Refer to JIT_InitPInvokeFrame for details. - return PTR_MethodDesc(m_StubSecretArg); -#else - _ASSERTE(!"NYI - Interop method reporting for this architecture!"); - return NULL; -#endif // defined(TARGET_X86) || defined(TARGET_ARM) } virtual void UpdateRegDisplay(const PREGDISPLAY, bool updateFloats = false); @@ -2890,13 +2869,6 @@ class InlinedCallFrame : public Frame // See code:HasFunction. PTR_NDirectMethodDesc m_Datum; -#ifdef HOST_64BIT - // IL stubs fill this field with the incoming secret argument when they erect - // InlinedCallFrame so we know which interop method was invoked even if the frame - // is not active at the moment. - PTR_VOID m_StubSecretArg; -#endif // HOST_64BIT - // X86: ESP after pushing the outgoing arguments, and just before calling // out to unmanaged code. // Other platforms: the field stays set throughout the declaring method. diff --git a/src/coreclr/vm/jithelpers.cpp b/src/coreclr/vm/jithelpers.cpp index 33caff53a66e9..157e34c3a1a1f 100644 --- a/src/coreclr/vm/jithelpers.cpp +++ b/src/coreclr/vm/jithelpers.cpp @@ -6040,7 +6040,7 @@ HCIMPLEND /* Fills out portions of an InlinedCallFrame for JIT64 */ /* The idea here is to allocate and initialize the frame to only once, */ /* regardless of how many PInvokes there are in the method */ -Thread * __stdcall JIT_InitPInvokeFrame(InlinedCallFrame *pFrame, PTR_VOID StubSecretArg) +Thread * JIT_InitPInvokeFrame(InlinedCallFrame *pFrame) { CONTRACTL { @@ -6054,7 +6054,6 @@ Thread * __stdcall JIT_InitPInvokeFrame(InlinedCallFrame *pFrame, PTR_VOID StubS _ASSERTE(pFrame != pThread->GetFrame()); pFrame->Init(); - pFrame->m_StubSecretArg = StubSecretArg; pFrame->m_Next = pThread->GetFrame(); return pThread; diff --git a/src/coreclr/vm/jitinterface.cpp b/src/coreclr/vm/jitinterface.cpp index 0324a02c2c750..1f86c561e7354 100644 --- a/src/coreclr/vm/jitinterface.cpp +++ b/src/coreclr/vm/jitinterface.cpp @@ -10078,6 +10078,7 @@ void InlinedCallFrame::GetEEInfo(CORINFO_EE_INFO::InlinedCallFrameInfo *pInfo) LIMITED_METHOD_CONTRACT; pInfo->size = sizeof(GSCookie) + sizeof(InlinedCallFrame); + pInfo->sizeWithSecretStubArg = sizeof(GSCookie) + sizeof(InlinedCallFrame) + sizeof(PTR_VOID); pInfo->offsetOfGSCookie = 0; pInfo->offsetOfFrameVptr = sizeof(GSCookie); @@ -10086,6 +10087,7 @@ void InlinedCallFrame::GetEEInfo(CORINFO_EE_INFO::InlinedCallFrameInfo *pInfo) pInfo->offsetOfCalleeSavedFP = sizeof(GSCookie) + offsetof(InlinedCallFrame, m_pCalleeSavedFP); pInfo->offsetOfCallTarget = sizeof(GSCookie) + offsetof(InlinedCallFrame, m_Datum); pInfo->offsetOfReturnAddress = sizeof(GSCookie) + offsetof(InlinedCallFrame, m_pCallerReturnAddress); + pInfo->offsetOfSecretStubArg = sizeof(GSCookie) + sizeof(InlinedCallFrame); #ifdef TARGET_ARM pInfo->offsetOfSPAfterProlog = sizeof(GSCookie) + offsetof(InlinedCallFrame, m_pSPAfterProlog); #endif // TARGET_ARM diff --git a/src/coreclr/vm/jitinterface.h b/src/coreclr/vm/jitinterface.h index a8266d6b79b27..51e2b959d6f69 100644 --- a/src/coreclr/vm/jitinterface.h +++ b/src/coreclr/vm/jitinterface.h @@ -1083,7 +1083,7 @@ EXTERN_C TypeHandle::CastResult STDCALL ObjIsInstanceOfCached(Object *pObject, T #ifdef HOST_64BIT class InlinedCallFrame; -Thread * __stdcall JIT_InitPInvokeFrame(InlinedCallFrame *pFrame, PTR_VOID StubSecretArg); +Thread * JIT_InitPInvokeFrame(InlinedCallFrame *pFrame); #endif #ifdef _DEBUG diff --git a/src/coreclr/vm/loongarch64/asmconstants.h b/src/coreclr/vm/loongarch64/asmconstants.h index 6828eec7505e1..8d53c8c3173a9 100644 --- a/src/coreclr/vm/loongarch64/asmconstants.h +++ b/src/coreclr/vm/loongarch64/asmconstants.h @@ -218,16 +218,16 @@ ASMCONSTANTS_C_ASSERT(Frame__m_Next == offsetof(Frame, m_Next)) #define InlinedCallFrame__m_Datum 0x10 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_Datum == offsetof(InlinedCallFrame, m_Datum)) -#define InlinedCallFrame__m_pCallSiteSP 0x20 +#define InlinedCallFrame__m_pCallSiteSP 0x18 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCallSiteSP == offsetof(InlinedCallFrame, m_pCallSiteSP)) -#define InlinedCallFrame__m_pCallerReturnAddress 0x28 +#define InlinedCallFrame__m_pCallerReturnAddress 0x20 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCallerReturnAddress == offsetof(InlinedCallFrame, m_pCallerReturnAddress)) -#define InlinedCallFrame__m_pCalleeSavedFP 0x30 +#define InlinedCallFrame__m_pCalleeSavedFP 0x28 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCalleeSavedFP == offsetof(InlinedCallFrame, m_pCalleeSavedFP)) -#define InlinedCallFrame__m_pThread 0x38 +#define InlinedCallFrame__m_pThread 0x30 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pThread == offsetof(InlinedCallFrame, m_pThread)) #define FixupPrecodeData__Target 0x00 diff --git a/src/coreclr/vm/riscv64/asmconstants.h b/src/coreclr/vm/riscv64/asmconstants.h index 8076ee94f2130..d10d2d4dabc96 100644 --- a/src/coreclr/vm/riscv64/asmconstants.h +++ b/src/coreclr/vm/riscv64/asmconstants.h @@ -214,16 +214,16 @@ ASMCONSTANTS_C_ASSERT(Frame__m_Next == offsetof(Frame, m_Next)) #define InlinedCallFrame__m_Datum 0x10 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_Datum == offsetof(InlinedCallFrame, m_Datum)) -#define InlinedCallFrame__m_pCallSiteSP 0x20 +#define InlinedCallFrame__m_pCallSiteSP 0x18 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCallSiteSP == offsetof(InlinedCallFrame, m_pCallSiteSP)) -#define InlinedCallFrame__m_pCallerReturnAddress 0x28 +#define InlinedCallFrame__m_pCallerReturnAddress 0x20 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCallerReturnAddress == offsetof(InlinedCallFrame, m_pCallerReturnAddress)) -#define InlinedCallFrame__m_pCalleeSavedFP 0x30 +#define InlinedCallFrame__m_pCalleeSavedFP 0x28 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pCalleeSavedFP == offsetof(InlinedCallFrame, m_pCalleeSavedFP)) -#define InlinedCallFrame__m_pThread 0x38 +#define InlinedCallFrame__m_pThread 0x30 ASMCONSTANTS_C_ASSERT(InlinedCallFrame__m_pThread == offsetof(InlinedCallFrame, m_pThread)) #define FixupPrecodeData__Target 0x00