Skip to content

Commit 7bcfee1

Browse files
authored
JIT: Handle possibility of late optimized out async calls (#121502)
If we optimize an async call away after the suspension/resumption code has been created then the emit locations used for resumption info and diagnostic info will not be valid. Handle this rare case by just storing 0. The value should not matter as we will never suspend here. Suspension blocks can be removed in this case, but resumption blocks cannot as they are referenced by the resumption switch. Ideally we would model things so that resumption blocks could too be removed in these cases, but that's not so simple. Fixes issue reported in #121298 (comment)
1 parent 83496bf commit 7bcfee1

File tree

2 files changed

+8
-3
lines changed

2 files changed

+8
-3
lines changed

src/coreclr/jit/codegencommon.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6774,7 +6774,7 @@ void CodeGen::genReportAsyncDebugInfo()
67746774
for (size_t i = 0; i < suspPoints->size(); i++)
67756775
{
67766776
emitLocation& emitLoc = ((emitLocation*)genAsyncResumeInfoTable->dsCont)[i];
6777-
(*suspPoints)[i].DiagnosticNativeOffset = emitLoc.CodeOffset(GetEmitter());
6777+
(*suspPoints)[i].DiagnosticNativeOffset = emitLoc.Valid() ? emitLoc.CodeOffset(GetEmitter()) : 0;
67786778
}
67796779

67806780
ICorDebugInfo::AsyncInfo asyncInfo;

src/coreclr/jit/emit.cpp

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8553,14 +8553,19 @@ void emitter::emitOutputDataSec(dataSecDsc* sec, BYTE* dst)
85538553
{
85548554
emitLocation* emitLoc = &((emitLocation*)dsc->dsCont)[i];
85558555

8556-
BYTE* target = emitOffsetToPtr(emitLoc->CodeOffset(this));
8556+
// Async call may have been removed very late, after we have introduced suspension/resumption.
8557+
// In those cases just encode null.
8558+
BYTE* target = emitLoc->Valid() ? emitOffsetToPtr(emitLoc->CodeOffset(this)) : nullptr;
85578559
aDstRW[i].Resume = (target_size_t)(uintptr_t)emitAsyncResumeStubEntryPoint;
85588560
aDstRW[i].DiagnosticIP = (target_size_t)(uintptr_t)target;
85598561
if (emitComp->opts.compReloc)
85608562
{
85618563
uint16_t relocType = TARGET_POINTER_SIZE == 8 ? IMAGE_REL_BASED_DIR64 : IMAGE_REL_BASED_HIGHLOW;
85628564
emitRecordRelocation(&aDstRW[i].Resume, emitAsyncResumeStubEntryPoint, relocType);
8563-
emitRecordRelocation(&aDstRW[i].DiagnosticIP, target, relocType);
8565+
if (target != nullptr)
8566+
{
8567+
emitRecordRelocation(&aDstRW[i].DiagnosticIP, target, relocType);
8568+
}
85648569
}
85658570

85668571
JITDUMP(" Resume=%p, FinalResumeIP=%p\n", emitAsyncResumeStubEntryPoint, (void*)target);

0 commit comments

Comments
 (0)