Skip to content
This repository was archived by the owner on Jan 23, 2023. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion src/inc/eetwain.h
Original file line number Diff line number Diff line change
Expand Up @@ -652,7 +652,10 @@ HRESULT FixContextForEnC(PCONTEXT pCtx,
#ifdef WIN64EXCEPTIONS
static void EnsureCallerContextIsValid( PREGDISPLAY pRD, StackwalkCacheEntry* pCacheEntry, EECodeInfo * pCodeInfo = NULL );
static size_t GetCallerSp( PREGDISPLAY pRD );
#endif
#ifdef _TARGET_X86_
static size_t GetResumeSp( PCONTEXT pContext );
#endif // _TARGET_X86_
#endif // WIN64EXCEPTIONS

#ifdef DACCESS_COMPILE
virtual void EnumMemoryRegions(CLRDataEnumMemoryFlags flags);
Expand Down
48 changes: 48 additions & 0 deletions src/vm/eetwain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4033,6 +4033,54 @@ bool UnwindStackFrame(PREGDISPLAY pContext,

#endif // _TARGET_X86_

#ifdef WIN64EXCEPTIONS
#ifdef _TARGET_X86_
size_t EECodeManager::GetResumeSp( PCONTEXT pContext )
{
PCODE currentPc = PCODE(pContext->Eip);

_ASSERTE(ExecutionManager::IsManagedCode(currentPc));

EECodeInfo codeInfo(currentPc);

PTR_CBYTE methodStart = PTR_CBYTE(codeInfo.GetSavedMethodCode());

GCInfoToken gcInfoToken = codeInfo.GetGCInfoToken();
PTR_VOID methodInfoPtr = gcInfoToken.Info;
DWORD curOffs = codeInfo.GetRelOffset();

CodeManStateBuf stateBuf;

stateBuf.hdrInfoSize = (DWORD)DecodeGCHdrInfo(gcInfoToken,
curOffs,
&stateBuf.hdrInfoBody);

PTR_CBYTE table = dac_cast<PTR_CBYTE>(methodInfoPtr) + stateBuf.hdrInfoSize;

hdrInfo *info = &stateBuf.hdrInfoBody;

_ASSERTE(info->epilogOffs == hdrInfo::NOT_IN_EPILOG && info->prologOffs == hdrInfo::NOT_IN_PROLOG);

bool isESPFrame = !info->ebpFrame && !info->doubleAlign;

if (codeInfo.IsFunclet())
{
// Treat funclet's frame as ESP frame
isESPFrame = true;
}

if (isESPFrame)
{
const size_t curESP = (size_t)(pContext->Esp);
return curESP + GetPushedArgSize(info, table, curOffs);
}

const size_t curEBP = (size_t)(pContext->Ebp);
return GetOutermostBaseFP(curEBP, info);
}
#endif // _TARGET_X86_
#endif // WIN64EXCEPTIONS

#ifndef CROSSGEN_COMPILE
#ifndef WIN64EXCEPTIONS

Expand Down
21 changes: 21 additions & 0 deletions src/vm/exceptionhandling.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,24 @@ bool FixNonvolatileRegisters(UINT_PTR uOriginalSP,
bool fAborting
);

void FixContext(PCONTEXT pContextRecord)
{
#define FIXUPREG(reg, value) \
do { \
STRESS_LOG2(LF_GCROOTS, LL_INFO100, "Updating " #reg " %p to %p\n", \
pContextRecord->reg, \
(value)); \
pContextRecord->reg = (value); \
} while (0)

#ifdef _TARGET_X86_
size_t resumeSp = EECodeManager::GetResumeSp(pContextRecord);
FIXUPREG(ResumeEsp, resumeSp);
#endif // _TARGET_X86_

#undef FIXUPREG
}

MethodDesc * GetUserMethodForILStub(Thread * pThread, UINT_PTR uStubSP, MethodDesc * pILStubMD, Frame ** ppFrameOut);

#ifdef FEATURE_PAL
Expand Down Expand Up @@ -441,6 +459,7 @@ void ExceptionTracker::UpdateNonvolatileRegisters(CONTEXT *pContextRecord, REGDI
} \
} while (0)


#if defined(_TARGET_X86_)

UPDATEREG(Ebx);
Expand Down Expand Up @@ -1181,6 +1200,8 @@ ProcessCLRException(IN PEXCEPTION_RECORD pExceptionRecord

pThread->SetFrame(pLimitFrame);

FixContext(pContextRecord);

SetIP(pContextRecord, (PCODE)uResumePC);
}

Expand Down