On Tue, 2 Dec 2025 10:30:46 GMT, Quan Anh Mai <[email protected]> wrote:

> Hi,
> 
> This PR fixes the issue of the compiler crashing with "not enough operands 
> for reexecution". The issue here is that during 
> `Parse::catch_inline_exceptions`, the old stack is gone, and we cannot 
> reexecute the current bytecode anymore. However, there are some places where 
> we try to insert safepoints into the graph, such as if the handler is a 
> backward jump, or if one of the exceptions in the handlers is not loaded. 
> Since the `_reexecute` state of the current jvms is "undefined", it is 
> inferred automatically that it should reexecute for some bytecodes such as 
> `putfield`. The solution then is to explicitly set `_reexecute` to false.
> 
> I can manage to write a unit test for the case of a backward handler, for the 
> other cases, since the exceptions that can be thrown for a bytecode that is 
> inferred to reexecute are `NullPointerException`, 
> `ArrayIndexOutOfBoundsException`, and `ArrayStoreException`. I find it hard 
> to construct such a test in which one of them is not loaded.
> 
> Please kindly review, thanks a lot.

It seems to be very difficult to force the back-edge safepoint to deoptimize.  
I tried creating a thread that calls System.gc(), but so far no crash.  Still, 
I think the state is incorrect if reexecute=false.  Setting reexecute to false 
means it will skip the current instruction.  To correctly handle a 
deoptimization on the backwards branch, the debug state, bci, and exception 
location should match.  I think we have 3 choices to prepare for 
maybe_add_safepoint():
1. preserve stack inputs, use original bci, do not push exception oop, let 
interpreter reexecute and throw the exception (reexecute=true)
  This might be as simple as reversing the order of calls to push_ex_oop and 
maybe_add_safepoint.
2. trim stack, push exception object, use bci of exception handler 
(reexecute=true)
  This would require temporarily changing the bci for the maybe_add_safepoint 
call.
3. trim stack, throw exception (move to Thread) (reexecute=true)
  This requires extra unconditional overhead even though safepoint rarely 
happens.

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

PR Comment: https://git.openjdk.org/jdk/pull/28597#issuecomment-3609883724

Reply via email to