RFR[13]: 8227260: Can't deal with SharedRuntime::handle_wrong_method triggering more than once for interpreter calls

Dmitrij Pochepko dmitrij.pochepko at bell-sw.com
Wed Jul 17 16:57:37 UTC 2019


Hi,

looks fine.

I also ran updated ClassInitBarrier test on aarch64 fastdebug build

Thanks,

Dmitrij

On 17/07/2019 4:06 PM, Vladimir Ivanov wrote:
> Thanks, Erik.
>
> Also, since I touch platform-specific code, I'd like Martin and 
> Dmitrij (implementors of support for s390, ppc, and aarch64) to take a 
> look at the patch as well.
>
> Best regards,
> Vladimir Ivanov
>
> On 17/07/2019 15:25, Erik Österlund wrote:
>> Hi Vladimir,
>>
>> Looks good. Thanks for fixing.
>>
>> /Erik
>>
>> On 2019-07-17 12:26, Vladimir Ivanov wrote:
>>> Revised fix:
>>>    http://cr.openjdk.java.net/~vlivanov/8227260/webrev.00/
>>>
>>> It turned out the problem is not specific to i2c2i: fast class 
>>> initialization barriers on nmethod entry trigger the assert as well.
>>>
>>> JNI upcalls (CallStatic<type>Method) don't have class initialization 
>>> checks, so it's possible to initiate a JNI upcall from a 
>>> non-initializing thread and JVM should let it complete.
>>>
>>> It leads to a busy loop (asserts in debug) between nmethod entry 
>>> barrier & SharedRuntime::handle_wrong_method until holder class is 
>>> initialized (possibly infinite if it blocks class initialization).
>>>
>>> Proposed fix is to keep using c2i, but jump over class 
>>> initialization barrier right to the argument shuffling logic on 
>>> verified entry when coming from SharedRuntime::handle_wrong_method.
>>>
>>> Improved regression test reliably reproduces the problem.
>>>
>>> Testing: regression test, hs-precheckin-comp, tier1-6
>>>
>>> Best regards,
>>> Vladimir Ivanov
>>>
>>> On 04/07/2019 18:02, Erik Österlund wrote:
>>>> Hi,
>>>>
>>>> The i2c adapter sets a thread-local "callee_target" Method*, which 
>>>> is caught (and cleared) by SharedRuntime::handle_wrong_method if 
>>>> the i2c call is "bad" (e.g. not_entrant). This error handler 
>>>> forwards execution to the callee c2i entry. If the 
>>>> SharedRuntime::handle_wrong_method method is called again due to 
>>>> the i2c2i call being still bad, then we will crash the VM in the 
>>>> following guarantee in SharedRuntime::handle_wrong_method:
>>>>
>>>> Method* callee = thread->callee_target();
>>>> guarantee(callee != NULL && callee->is_method(), "bad handshake");
>>>>
>>>> Unfortunately, the c2i entry can indeed fail again if it, e.g., 
>>>> hits the new class initialization entry barrier of the c2i adapter.
>>>> The solution is to simply not clear the thread-local 
>>>> "callee_target" after handling the first failure, as we can't 
>>>> really know there won't be another one. There is no reason to clear 
>>>> this value as nobody else reads it than the 
>>>> SharedRuntime::handle_wrong_method handler (and we really do want 
>>>> it to be able to read the value as many times as it takes until the 
>>>> call goes through). I found some confused clearing of this 
>>>> callee_target in JavaThread::oops_do(), with a comment saying this 
>>>> is a methodOop that we need to clear to make GC happy or something. 
>>>> Seems like old traces of perm gen. So I deleted that too.
>>>>
>>>> I caught this in ZGC where the timing window for hitting this issue 
>>>> seems to be wider due to concurrent code cache unloading. But it is 
>>>> equally problematic for all GCs.
>>>>
>>>> Bug:
>>>> https://bugs.openjdk.java.net/browse/JDK-8227260
>>>>
>>>> Webrev:
>>>> http://cr.openjdk.java.net/~eosterlund/8227260/webrev.00/
>>>>
>>>> Thanks,
>>>> /Erik


More information about the hotspot-dev mailing list