Skip to content

JIT: revise may/must point to stack analysis #115080

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

Merged
merged 2 commits into from
Apr 27, 2025

Conversation

AndyAyersMS
Copy link
Member

Keep track of locals that may point to the heap as well as locals that may point to the stack.

The set of definitely stack-pointing locals is then the difference in these two sets. This handles the "cyclic" case where stack pointing locals are assigned to one another.

Fixes #115017

Keep track of locals that may point to the heap as well as locals that
may point to the stack.

The set of definitely stack-pointing locals is then the difference in
these two sets. This handles the "cyclic" case where stack pointing locals
are assigned to one another.

Fixes dotnet#115017
@Copilot Copilot AI review requested due to automatic review settings April 26, 2025 15:10
@dotnet-issue-labeler dotnet-issue-labeler bot added the area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI label Apr 26, 2025
Copy link
Contributor

@Copilot Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull Request Overview

This PR improves JIT analysis by tracking locals that may point to both the heap and the stack to better compute the set of definitely stack-pointing locals, addressing an issue with cyclic assignments.

  • Added a new test case to verify the updated connection cycles behavior.
  • Updated object allocation logic in objectalloc.cpp to compute stack-pointing locals based on the difference with heap-pointing locals and added corresponding logging.
  • Enhanced logging in assertionprop.cpp for better cross-block table insights.

Reviewed Changes

Copilot reviewed 3 out of 4 changed files in this pull request and generated 1 comment.

File Description
src/tests/JIT/opt/ObjectStackAllocation/ConnectionCycles.cs Added tests for verifying connection cycles via local pointer assignments.
src/coreclr/jit/objectalloc.cpp Updated logic to distinguish stack- and heap-pointing locals with new logging messages.
src/coreclr/jit/assertionprop.cpp Added a logging statement to report cross-block table size details.
Files not reviewed (1)
  • src/tests/JIT/opt/ObjectStackAllocation/ConnectionCycles.csproj: Language not supported
Comments suppressed due to low confidence (1)

src/tests/JIT/opt/ObjectStackAllocation/ConnectionCycles.cs:20

  • [nitpick] Consider renaming the test method 'Problem' to a more descriptive name that reflects the scenario under test, improving clarity for future readers.
public static int Problem()


// If a local is possibly stack pointing and not possibly heap pointing, then it is definitely stack pointing.
//
BitVec newDefinitelyStackPointingPointers = BitVecOps::UninitVal();
Copy link
Preview

Copilot AI Apr 26, 2025

Choose a reason for hiding this comment

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

Consider adding an inline comment to clarify that subtracting the possibly heap-pointing pointers from the possibly stack-pointing pointers isolates the definitely stack-pointing locals, especially to support future maintenance.

Copilot uses AI. Check for mistakes.

Copy link
Contributor

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

@AndyAyersMS
Copy link
Member Author

@jakobbotsch PTAL
cc @dotnet/jit-contrib

This reduces the number of ambient byrefs, and can also improve code quality.

Two bad diffs in x64 windows libraries SPMI (System.MemoryTests) where we now fill up the local AP table and so drop a couple of useful assertions.

@AndyAyersMS
Copy link
Member Author

arm failure is related, there are diffs in VerifyUriNormalizationForEscapedCharacters

    System.PrivateUri.Tests.IriTest.Iri_UnicodePlane3_13 [FAIL]
      System.ArgumentNullException : Value cannot be null. (Parameter 'value')
      Stack Trace:
        /_/src/libraries/System.Private.CoreLib/src/System/ArgumentNullException.cs(97,0): at System.ArgumentNullException.Throw(String paramName)
        /_/src/libraries/System.Private.CoreLib/src/System/Globalization/CultureInfo.cs(374,0): at System.Globalization.CultureInfo.set_CurrentCulture(CultureInfo value)
        /_/src/libraries/System.Private.Uri/tests/FunctionalTests/IriTest.cs(331,0): at System.PrivateUri.Tests.IriTest.VerifyUriNormalizationForEscapedCharacters(String uriInput)
        /_/src/libraries/System.Private.Uri/tests/FunctionalTests/IriTest.cs(265,0): at System.PrivateUri.Tests.IriTest.EscapeUnescapeTestUnicodePlane(Int32 start, Int32 end, Int32 step)
        /_/src/libraries/System.Private.Uri/tests/FunctionalTests/IriTest.cs(246,0): at System.PrivateUri.Tests.IriTest.Iri_UnicodePlane3_13()
        /_/src/coreclr/System.Private.CoreLib/src/System/Reflection/MethodBaseInvoker.CoreCLR.cs(36,0): at System.Reflection.MethodBaseInvoker.InterpretedInvoke_Method(Object obj, IntPtr* args)
        /_/src/libraries/System.Private.CoreLib/src/System/Reflection/MethodBaseInvoker.cs(57,0): at System.Reflection.MethodBaseInvoker.InvokeWithNoArgs(Object obj, BindingFlags invokeAttr)
Fatal error.
System.AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
   at System.Threading.AsyncLocal`1[[System.__Canon, System.Private.CoreLib, Version=10.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].System.Threading.IAsyncLocal.OnValueChanged(System.Object, System.Object, Boolean)
   at System.Threading.ExecutionContext.SetLocalValue(System.Threading.IAsyncLocal, System.Object, Boolean)
   at System.Threading.AsyncLocal`1[[System.__Canon, System.Private.CoreLib, Version=10.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]].set_Value(System.__Canon)
   at System.Globalization.CultureInfo.set_CurrentCulture(System.Globalization.CultureInfo)
   at System.PrivateUri.Tests.IriTest.VerifyUriNormalizationForEscapedCharacters(System.String)

@AndyAyersMS
Copy link
Member Author

We are missing a connection graph edge for the case where a local doesn't escape but we decide not to stack allocate it (say because the allocation site is in a loop).

Comment on lines +890 to +892
BitVec newDefinitelyStackPointingPointers = BitVecOps::UninitVal();
BitVecOps::Assign(bitVecTraits, newDefinitelyStackPointingPointers, m_PossiblyStackPointingPointers);
BitVecOps::DiffD(bitVecTraits, newDefinitelyStackPointingPointers, possiblyHeapPointingPointers);
Copy link
Member

Choose a reason for hiding this comment

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

I think you can use BitVecOps::Diff directly here to avoid manually writing the copy.

Copy link
Member Author

Choose a reason for hiding this comment

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

Good point. Will clean this up in a future escape PR.

@AndyAyersMS AndyAyersMS merged commit 4158fca into dotnet:main Apr 27, 2025
112 of 114 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI
Projects
None yet
Development

Successfully merging this pull request may close these issues.

JIT: cycles in connection graph lead to non-minimal fix point retypings
2 participants