Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Add copy buttons to all
 blocks\n(function() {\n function addCopyButtons() {\n document.querySelectorAll('pre code').forEach(function(codeBlock) {\n if (codeBlock.parentElement.hasAttribute('data-copy-added')) return;\n codeBlock.parentElement.setAttribute('data-copy-added', 'true');\n \n var btn = document.createElement('button');\n btn.textContent = 'Copy';\n btn.style.cssText = 'position:absolute;top:4px;right:4px;padding:2px 8px;font-size:11px;background:#4ecdc4;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;opacity:0.7;transition:opacity 0.2s;';\n btn.onmouseover = function() { this.style.opacity = '1'; };\n btn.onmouseout = function() { this.style.opacity = '0.7'; };\n btn.onclick = function() {\n navigator.clipboard.writeText(codeBlock.textContent).then(function() {\n btn.textContent = 'Copied!';\n setTimeout(function() { btn.textContent = 'Copy'; }, 1500);\n });\n };\n codeBlock.parentElement.style.position = 'relative';\n codeBlock.parentElement.appendChild(btn);\n });\n }\n \n addCopyButtons();\n \n // Re-run on dynamic content\n var observer = new MutationObserver(addCopyButtons);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Add Copy Buttons to Code Blocks");
}
} catch(__e) { console.warn('[Userscript:Add Copy Buttons to Code Blocks]', __e); }
})();
(function(){
try {
var __m = "github.com";
var __re = new RegExp('^' + "github\\.com" + '
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Force GitHub README to respect dark mode\n(function() {\n var style = document.createElement('style');\n style.textContent = '\n .markdown-body {\n color-scheme: dark light;\n }\n .markdown-body pre { background: #161b22 !important; }\n .markdown-body code { background: rgba(110, 118, 129, 0.4) !important; }\n .markdown-body table th, .markdown-body table td { border-color: #30363d !important; }\n .markdown-body img { background: #0d1117; }\n .markdown-body blockquote { border-left-color: #8b949e; }\n .markdown-body hr { border-color: #30363d; }\n ';\n document.head.appendChild(style);\n})();", "GitHub Dark Mode README Fix"); } } catch(__e) { console.warn('[Userscript:GitHub Dark Mode README Fix]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Highlight search terms from Google/DuckDuckGo/Bing referrer\n(function() {\n var ref = document.referrer;\n var terms = [];\n \n if (ref.includes('google.com') || ref.includes('duckduckgo.com') || ref.includes('bing.com')) {\n var url = new URL(ref);\n var q = url.searchParams.get('q') || url.searchParams.get('p');\n if (q) {\n terms = q.split(/\\s+/).filter(function(t) { return t.length > 2; });\n }\n }\n \n if (terms.length === 0) return;\n \n var style = document.createElement('style');\n style.textContent = '.userscript-highlight { background: #fbbf24; color: #1a1a2e; padding: 1px 3px; border-radius: 2px; }';\n document.head.appendChild(style);\n \n function highlight(node) {\n if (node.nodeType === 3) { // text node\n var text = node.textContent;\n var found = false;\n terms.forEach(function(term) {\n var regex = new RegExp('(' + term.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\') + ')', 'gi');\n if (regex.test(text)) {\n found = true;\n var frag = document.createDocumentFragment();\n var parts = text.split(regex);\n parts.forEach(function(part, i) {\n if (i % 2 === 0) {\n frag.appendChild(document.createTextNode(part));\n } else {\n var span = document.createElement('span');\n span.className = 'userscript-highlight';\n span.textContent = part;\n frag.appendChild(span);\n }\n });\n node.parentNode.replaceChild(frag, node);\n }\n });\n } else if (node.nodeType === 1 && node.childNodes) { // element\n var skipTags = ['SCRIPT', 'STYLE', 'NOSCRIPT', 'TEXTAREA', 'INPUT', 'SELECT'];\n if (!skipTags.includes(node.tagName)) {\n Array.from(node.childNodes).forEach(highlight);\n }\n }\n }\n \n highlight(document.body);\n \n // Re-highlight on dynamic content\n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1 || node.nodeType === 3) highlight(node);\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Highlight Search Terms"); } } catch(__e) { console.warn('[Userscript:Highlight Search Terms]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Strip utm_, fbclid, gclid, etc. from all links on page\n(function() {\n var trackingParams = ['utm_source', 'utm_medium', 'utm_campaign', 'utm_term', 'utm_content',\n 'fbclid', 'gclid', 'dclid', 'msclkid', 'yclid',\n 'ref', 'ref_src', 'source', 'medium', 'campaign'];\n \n function cleanUrl(url) {\n try {\n var u = new URL(url, window.location.origin);\n var changed = false;\n trackingParams.forEach(function(p) {\n if (u.searchParams.has(p)) {\n u.searchParams.delete(p);\n changed = true;\n }\n });\n return changed ? u.toString() : url;\n } catch (e) {\n return url;\n }\n }\n \n function cleanLinks() {\n document.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n \n cleanLinks();\n \n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1) {\n if (node.tagName === 'A') cleanLinks();\n node.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Remove Tracking Parameters from Links"); } } catch(__e) { console.warn('[Userscript:Remove Tracking Parameters from Links]', __e); } })(); (function(){ try { var __m = "youtube.com"; var __re = new RegExp('^' + "youtube\\.com" + '
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Auto-enable theater mode on YouTube\n(function() {\n function tryTheater() {\n var btn = document.querySelector('button[aria-label=\"Theater mode\"], ytd-player #player button[title=\"Theater mode\"]');\n if (btn && !btn.classList.contains('activated')) {\n btn.click();\n }\n }\n \n // Try immediately\n tryTheater();\n \n // Try after navigation (SPA)\n var lastUrl = location.href;\n setInterval(function() {\n if (location.href !== lastUrl) {\n lastUrl = location.href;\n setTimeout(tryTheater, 500);\n }\n }, 1000);\n \n // Also try on player load\n var observer = new MutationObserver(tryTheater);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "YouTube Theater Mode Default"); } } catch(__e) { console.warn('[Userscript:YouTube Theater Mode Default]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Remove or un-stick sticky/fixed headers that block content\n(function() {\n function unstick() {\n document.querySelectorAll('header, nav, [role=\"banner\"], .header, .navbar, .sticky, .fixed-top, [style*=\"position: fixed\"], [style*=\"position:sticky\"]').forEach(function(el) {\n if (el.style.position === 'fixed' || el.style.position === 'sticky' || \n getComputedStyle(el).position === 'fixed' || getComputedStyle(el).position === 'sticky') {\n el.style.position = 'static';\n el.style.top = 'auto';\n el.style.zIndex = 'auto';\n }\n });\n }\n \n unstick();\n \n var observer = new MutationObserver(unstick);\n observer.observe(document.body, { childList: true, subtree: true, attributes: true, attributeFilter: ['style', 'class'] });\n})();", "Kill Sticky Headers"); } } catch(__e) { console.warn('[Userscript:Kill Sticky Headers]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Universal Dark Mode - works on any site\n(function() {\n var enabled = true;\n \n function applyDarkMode() {\n if (!enabled) return;\n \n // Create style element if it doesn't exist\n var style = document.getElementById('universal-dark-mode-style');\n if (!style) {\n style = document.createElement('style');\n style.id = 'universal-dark-mode-style';\n document.head.appendChild(style);\n }\n \n // Dark mode CSS - inverts colors but preserves images/video\n style.textContent = '\n /* Invert everything except media */\n html {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #1a1a2e !important;\n }\n \n /* Restore images, videos, iframes, canvas */\n img, video, iframe, canvas, svg, picture, [style*=\"background-image\"] {\n filter: invert(1) hue-rotate(180deg) !important;\n }\n \n /* Preserve specific elements that should not be inverted */\n .no-dark-mode, .no-dark-mode *,\n [data-theme=\"light\"], [data-theme=\"light\"],\n .ace_editor, .ace_editor *,\n .CodeMirror, .CodeMirror *,\n .monaco-editor, .monaco-editor *,\n .markdown-body pre, .markdown-body pre *,\n .highlight, .highlight *,\n pre code, pre code * {\n filter: none !important;\n }\n \n /* Fix common UI elements */\n .modal, .popup, .dropdown-menu, .tooltip, .popover {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #2d2d44 !important;\n border-color: #444 !important;\n }\n \n /* Scrollbars */\n ::-webkit-scrollbar { background: #1a1a2e !important; }\n ::-webkit-scrollbar-thumb { background: #444 !important; }\n ::-webkit-scrollbar-thumb:hover { background: #555 !important; }\n \n /* Selection */\n ::selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ::-moz-selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ';\n }\n \n function removeDarkMode() {\n var style = document.getElementById('universal-dark-mode-style');\n if (style) style.remove();\n }\n \n // Toggle with Alt+Shift+D\n document.addEventListener('keydown', function(e) {\n if (e.altKey && e.shiftKey && e.key === 'D') {\n e.preventDefault();\n enabled = !enabled;\n if (enabled) {\n applyDarkMode();\n console.log('[Universal Dark Mode] Enabled');\n } else {\n removeDarkMode();\n console.log('[Universal Dark Mode] Disabled');\n }\n }\n });\n \n // Apply on load\n applyDarkMode();\n \n // Re-apply on dynamic content\n var observer = new MutationObserver(function(mutations) {\n if (enabled && !document.getElementById('universal-dark-mode-style')) {\n applyDarkMode();\n }\n });\n observer.observe(document.head, { childList: true });\n \n console.log('[Universal Dark Mode] Loaded - Press Alt+Shift+D to toggle');\n})();", "Universal Dark Mode"); } } catch(__e) { console.warn('[Userscript:Universal Dark Mode]', __e); } })(); })();
Skip to content

Fix nonvolatile context restoration - #101709

Merged
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration
Apr 30, 2024
Merged

Fix nonvolatile context restoration#101709
janvorli merged 2 commits into
dotnet:mainfrom
janvorli:fix-nonvolatile-context-restoration

Conversation

@janvorli

@janvorlijanvorli commented Apr 30, 2024

Copy link
Copy Markdown
Member

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like the one we use for runtime suspension). If the signal kicks in after we've loaded Rsp, but before we jumped to the target address, the context we are loading the registers from could get overwritten by the signal handler stack. So the ClrRestoreNonVolatileContext would end up jumping into a wrong target address.

The fix is to load the target address into a register before loading the Rsp and then jumping using the register.

Close#101060, #98292

There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
@janvorlijanvorli added this to the 9.0.0 milestone Apr 30, 2024
@janvorlijanvorli self-assigned this Apr 30, 2024
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @mangod9
See info in area-owners.md if you want to be subscribed.

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM! This seems like the most plausible explanation.
Is only x64 affected?

@janvorli

Copy link
Copy Markdown
MemberAuthor

Actually, the other targets use RtlRestoreContext in PAL and it also has this issue on some targets (arm, x86, most likely riscv64 and loongarch64, not sure about s390x and ppc64le). Arm64 is ok. Let me add fixes for more architectures here.

@AndyAyersMS

Copy link
Copy Markdown
Member

We expect this to fix #98292 and #101060, right?

Seems like a very small race window, which jives with the fact that these are very hard to repro.

@janvorli

Copy link
Copy Markdown
MemberAuthor

We expect this to fix #98292 and #101060, right?

I think so as they both seem to be OSR related.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli

Copy link
Copy Markdown
MemberAuthor

@jakobbotsch can you please take a look again? I have added arm and x86 fixes. Arm64 was already ok. I will leave possible fixes for the other architectures on the external people who have added support for those.

@janvorli

Copy link
Copy Markdown
MemberAuthor

The CI failure is a known issue.

Comment on lines +165 to +167
str r2, [r1, #-4]
ldr r2, [r0, #(CONTEXT_R12)]
str r2, [r1, #-8]

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any possibility that these stores accidentally overwrite some of the registers in the context that we are going to use later, if the context happens to be at this location in the stack? Or does the context not end with the GPR registers?

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The context contains GPR registers first, then all the NEON ones, debug registers and two DWORDS of padding at the end. So worst case scenario, if we ever overwritten anything from the context, it could only be the padding.

Copy link
Copy Markdown
MemberAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

See here:

typedefstructDECLSPEC_ALIGN(8) _CONTEXT {
//
// Control flags.
//
DWORD ContextFlags;
//
// Integer registers
//
DWORDR0;
DWORDR1;
DWORDR2;
DWORDR3;
DWORDR4;
DWORDR5;
DWORDR6;
DWORDR7;
DWORDR8;
DWORDR9;
DWORDR10;
DWORDR11;
DWORDR12;
//
// Control Registers
//
DWORD Sp;
DWORD Lr;
DWORD Pc;
DWORD Cpsr;
//
// Floating Point/NEON Registers
//
DWORD Fpscr;
DWORD Padding;
union {
NEON128 Q[16];
ULONGLONG D[32];
DWORD S[32];
};
//
// Debug registers
//
DWORD Bvr[ARM_MAX_BREAKPOINTS];
DWORD Bcr[ARM_MAX_BREAKPOINTS];
DWORD Wvr[ARM_MAX_WATCHPOINTS];
DWORD Wcr[ARM_MAX_WATCHPOINTS];
DWORD Padding2[2];
} CONTEXT, *PCONTEXT, *LPCONTEXT;

@jakobbotschjakobbotsch left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks good to me, just one hypothetical wondering.

@janvorli
janvorli merged commit 7aefd27 into dotnet:mainApr 30, 2024
@janvorli
janvorli deleted the fix-nonvolatile-context-restoration branch April 30, 2024 22:47
@t-mustafin

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

@janvorli thanks for notification. Are this changes needed on release/8.0 branch?

cc @dotnet/samsung

uweigand added a commit to uweigand/runtime that referenced this pull request May 3, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@uweigand

Copy link
Copy Markdown
Contributor

@t-mustafin, @shushanhf, @vikasgupta8, @uweigand can you please check if the architectures you have added support for also need a fix like this? It seems to me that RISCV64 and LoongArch64 do need to be fixed, I have no idea about the S390x and PPC64LE.

Thanks for the heads-up! The s390x patch is here: #101854

michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
michaelgsharp pushed a commit to michaelgsharp/runtime that referenced this pull request May 9, 2024
Fix s390x context restoration along the lines of
dotnet#101709
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
* Fix nonvolatile context restoration
There is a possibility of a race between the
ClrRestoreNonVolatileContext and an async signal handling (like
the one we use for runtime suspension). If the signal kicks in after
we've loaded Rsp, but before we jumped to the target address, the
context we are loading the registers from could get overwritten by the
signal handler stack. So the ClrRestoreNonVolatileContext would end up
jumping into a wrong target address.
The fix is to load the target address into a register before loading the
Rsp and then jumping using the register.
* Fix arm and x86
Ruihan-Yin pushed a commit to Ruihan-Yin/runtime that referenced this pull request May 30, 2024
Fix s390x context restoration along the lines of
dotnet#101709
@github-actionsgithub-actionsBot locked and limited conversation to collaborators Jun 4, 2024
Sign up for freeto subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Test failure: readytorun/coreroot_determinism/coreroot_determinism/coreroot_determinism.cmd [libraries-pgo] segfault in System.Linq.Tests

5 participants

@janvorli@AndyAyersMS@t-mustafin@uweigand@jakobbotsch