-
Notifications
You must be signed in to change notification settings - Fork 4.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
JIT: refactor to allow OSR to switch to optimized #61851
Conversation
When OSR is enabled, the jit may still need to switch to optimized codegen if there is something in the method that OSR cannot handle. Examples include: * localloc * tail. prefixes * loops in handlers * reverse pinvoke (currently bypasses Tiering so somewhat moot) When OSR is enabled, rework the "switch to optimize logic" in the jit to check for these cases up front before we start importing code. When both QuickJitForLoops and OnStackReplacement are enabled, this should ensure that if we can't transition out of long-running Tier0 code (via OSR) then we will instead optimize the method. Very few methods overall should opt-out of Tier0. Note some of these unhandled constructs can eventually be handled by OSR, with additional work.
Tagging subscribers to this area: @JulieLeeMSFT Issue DetailsWhen OSR is enabled, the jit may still need to switch to optimized codegen if
When OSR is enabled, rework the "switch to optimize logic" in the jit to check When both QuickJitForLoops and OnStackReplacement are enabled, this should ensure Note some of these unhandled constructs can eventually be handled by OSR, with
|
cc @dotnet/jit-contrib This is the last "prereq" before we can consider turning OSR on by default for x64. Note partial compilation doesn't have quite the same level of restriction -- it is opportunistic. If we can't support patchpoints in a method we can just bail out for each partial compilation candidate block, rather than forcing the method to be optimized. |
/azp run runtime-jit-experimental |
Azure Pipelines successfully started running 1 pipeline(s). |
src/coreclr/jit/compiler.cpp
Outdated
// | ||
const char* reason = nullptr; | ||
|
||
if ((info.compFlags & CORINFO_FLG_DISABLE_TIER0_FOR_LOOPS) == 0) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Isn't this the wrong way around?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ooops, yes. I should verify this is a no-diff change.
Also I'm changing what happens with BBINSTR -- formerly it would prevent switching to optimized -- as a result we'll have slightly fewer methods with PGO. Maybe I should rethink this.
We may need to distinguish the case where we we trap everything in Tier0 to gather static data from dynamic PGO. Right now we can't tell which is which. If we're trying to gather for static PGO we don't want to switch; if we're trying to minimize downside of Tier0 we do...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I should verify this is a no-diff change.
On further thought, it may not be no-diff because of the BBINSTR change, but there should be minimal diffs, and only in the ASP.NET cases where we see instrumentation.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is all in the context of #58632, so perhaps I can refine this down to not switching to optimized for BBINSTR'd methods with explicit tail calls.
OSR doesn't support explicit tail calls yet but presumably if we don't optimize recursive tail calls to loops then eventually normal tiering swaps all this over.
/azp run runtime-jit-experimental |
Azure Pipelines successfully started running 1 pipeline(s). |
This should replicate the current logic where we alwatys optimize methods with explicit tail calls unless we're instrumenting them. To make this work with OSR we simply won't put patchpoints in methods with explicit tail calls, instead trusting that Tiering can get us to optimized versions.
The interplay of QJFL, OSR, BBINSTR, and explicit tail calls is a bit messier than I'd like -- hopefully the latest commit here gets us to a reasonable point. |
/azp run runtime-jit-experimental |
Azure Pipelines successfully started running 1 pipeline(s). |
One unexpected failure in osr_stress to investigate
|
This is from the new handling for alignment. We scan blocks for labels:
and notably decide
and then assert because In this case
There is no reason to have |
/azp run runtime-jit-experimental |
Azure Pipelines successfully started running 1 pipeline(s). |
Experimental CI failures are down to the "expected ones". |
When OSR is enabled, the jit may still need to switch to optimized codegen if
there is something in the method that OSR cannot handle. Examples include:
When OSR is enabled, rework the "switch to optimize logic" in the jit to check
for these cases up front before we start importing code.
When both QuickJitForLoops and OnStackReplacement are enabled, this should ensure
that if we can't transition out of long-running Tier0 code (via OSR) then we will
instead optimize the method. Very few methods overall should opt-out of Tier0.
Note some of these unhandled constructs can eventually be handled by OSR, with
additional work.