On Fri, 21 Nov 2025 15:27:46 GMT, Marc Chevalier <[email protected]> wrote:

>> We are on aarch64.
>> 
>> When a function needs stack extension, we build a stack that has this shape:
>> 
>> https://github.com/openjdk/valhalla/blob/b1d14c658511cced2a860d9e2741ae89827e25ba/src/hotspot/cpu/aarch64/macroAssembler_aarch64.cpp#L6040-L6073
>> 
>> Currently, when leaving the frame, we use LR §1 (I use § not to mess with 
>> github rendering that interpret `#` as PR references) as return address 
>> (because it can be patched for deoptimization), and FP §2 to restore x29 
>> (because when it contains an oop, the GC is only aware of this copy).
>> 
>> In our failing case, we have a C2-compiled frame that is being deoptimized 
>> when returning from a call to an interpreted method. During deoptimization, 
>> the function `frame::sender_for_compiled_frame(RegisterMap*) const` is used 
>> to locate the location on the stack where rfp (x29) is saved.
>> 
>> https://github.com/openjdk/valhalla/blob/b1d14c658511cced2a860d9e2741ae89827e25ba/src/hotspot/cpu/aarch64/frame_aarch64.inline.hpp#L446
>> 
>> Actually this function is a bit more general: it computes the sender frame 
>> of a compiled frame, and build the `RegisterMap`. The problem is that during 
>> deoptimization, this function locates the wrong save of rfp (FP §1) because 
>> the C2 frame is being modified by the deoptimization process and it's not 
>> anymore recognized as a C2-compiled method that needs stack repairs. In this 
>> modified frame the sender's sp is correctly known (or the deoptimization 
>> mechanism would not work), and the saved FP is taken just 2 words above: 
>> that is FP §1. On top of that, if rfp contained an oop and the GC moved the 
>> pointed object during the call we are returning from, the value we get for 
>> rfp is not valid anymore.
>> 
>> The good and bad news is that the GC also locates the saved location of rfp 
>> thanks to the same function. The bad news is that GC sees the C2 frame 
>> correctly, and so `sender_for_compiled_frame` can locate FP §2. We can 
>> follow a few ideas:
>> - make the deoptimized frame bottom under FP/LR §2. This is not possible, 
>> for many reasons: we need LR §1, we need to remove the whole frame to find 
>> the sender's frame...
>> - make `sender_for_compiled_frame` detects when the deoptimized frame is the 
>> one of a C2 compiled method that needs stack repair. No idea how to do that! 
>> Also, it seems brittle, and more complicated than the next solution.
>> - always pick FP §1: since the deoptimized frame will pick FP §1, in case 
>> it's a regular C2 frame, we can also make sure to use FP §1. It is the 
>> simplest solution and t...
>
> Marc Chevalier has updated the pull request with a new target base due to a 
> merge or a rebase. The pull request now contains six commits:
> 
>  - Merge remote-tracking branch 'origin/lworld' into JDK-8367151
>  - Address comments
>  - Actually use compiled_frame_details
>  - ProblemList and comment
>  - Factor compiled frame pointers computation
>  - First fix

Marked as reviewed by thartmann (Committer).

-------------

PR Review: 
https://git.openjdk.org/valhalla/pull/1751#pullrequestreview-3493287822

Reply via email to