RFR (L) 8154580: Save mirror in interpreter frame to enable cleanups of CLDClosure
Coleen Phillimore
coleen.phillimore at oracle.com
Wed Apr 20 21:49:03 UTC 2016
Thanks Chris!
Coleen
On 4/20/16 5:43 PM, Christian Thalinger wrote:
>
>> On Apr 19, 2016, at 4:29 PM, Coleen Phillimore
>> <coleen.phillimore at oracle.com <mailto:coleen.phillimore at oracle.com>>
>> wrote:
>>
>>
>> Chris, thank you for reviewing this.
>>
>> On 4/19/16 4:35 PM, Christian Thalinger wrote:
>>>> On Apr 19, 2016, at 9:50 AM, Coleen Phillimore
>>>> <coleen.phillimore at oracle.com
>>>> <mailto:coleen.phillimore at oracle.com>> wrote:
>>>>
>>>> Summary: GC walks the mirror using OopClosure rather than using
>>>> CLDClosure in oops_interpreted_do()
>>>>
>>>> See bug for more description and justification. The changes are
>>>> large but very redundant. The main change is in
>>>> TemplateInterpreterGenerator::generate_fixed_frame().
>>> + // Save oop Mirror (with padding)
>>> + __ load_mirror(rscratch1, rmethod);
>>>
>>> + // get mirror and store it in the frame so that this Method* is never
>>> + // reclaimed while it's running.
>>> + Register mirror = LcpoolCache;
>>> + __ load_mirror(mirror, Method);
>>>
>>> + // Push the mirror so this method isn't collected
>>> + __ load_mirror(rdx, rbi);
>>>
>>> Please use the same comment on all platforms.
>>
>> Yes, that's inconsistent. I changed all platforms to have this comment:
>>
>> // Get mirror and store it in the frame as GC root for this Method*
>>
>>>> open webrev at
>>>> http://cr.openjdk.java.net/~coleenp/8154580.01/webrev
>>>> <http://cr.openjdk.java.net/%7Ecoleenp/8154580.01/webrev>
>>>> bug link https://bugs.openjdk.java.net/browse/JDK-8154580
>>> src/share/vm/runtime/frame.cpp
>>>
>>> // The method pointer in the frame might be the only path to
>>> the method's
>>> // klass, and the klass needs to be kept alive while executing.
>>> The GCs
>>> // don't trace through method pointers, so typically in similar
>>> situations
>>> // the mirror or the class loader of the klass are installed as
>>> a GC root.
>>>
>>> - // To minimize the overhead of doing that here, we ask the GC
>>> to pass down a
>>> - // closure that knows how to keep klasses alive given a
>>> ClassLoaderData.
>>> - cld_f->do_cld(m->method_holder()->class_loader_data());
>>> - }
>>> -
>>> - if (m->is_native() PPC32_ONLY(&& m->is_static())) {
>>> - f->do_oop(interpreter_frame_temp_oop_addr());
>>> - }
>>> + // And it is here too.
>>> + f->do_oop(interpreter_frame_mirror_addr());
>>>
>>> That comment is kinda funny now. It still hints at the old-way of
>>> doing things but “it is here too”.
>>
>> I reworded it as:
>>
>> // The method pointer in the frame might be the only path to the
>> method's
>> // klass, and the klass needs to be kept alive while executing. The GCs
>> // don't trace through method pointers, so the mirror of the
>> method's klass
>> // is installed as a GC root.
>> f->do_oop(interpreter_frame_mirror_addr());
>
> Excellent.
>
>>
>>>> Tested with hotspot-runtime-nightly and gc-nightly tests.
>>>>
>>>> Need testing with ppc and aarch64 open code. I implemented the
>>>> changes but I can't test them.
>>> One obvious bug is that you copied the __ as well:
>>>
>>> +void MacroAssembler::load_mirror(Register dst, Register method) {
>>> + const int mirror_offset = in_bytes(Klass::java_mirror_offset());
>>> + __ ldr(dst, Address(rmethod, Method::const_offset()));
>>> + __ ldr(dst, Address(dst, ConstMethod::constants_offset()));
>>> + __ ldr(dst, Address(dst,
>>> ConstantPool::pool_holder_offset_in_bytes()));
>>> + __ ldr(dst, Address(dst, mirror_offset));
>>> +}
>>>
>>> Other than that it looks fine to me. Nothing obvious stood out.
>>
>> Oh, yes, this was wrong on both ppc and aarch64. I hope someone
>> that has access to this platforms can test this patch.
>>
>> Thank you!
>> Coleen
>>
>>>
>>>> Thanks,
>>>> Coleen
>
More information about the hotspot-dev
mailing list