RFR: 8256061: RegisterSaver::save_live_registers() omits upper halves of ZMM0-15 registers

Vladimir Ivanov vlivanov at openjdk.java.net
Mon Nov 9 21:36:59 UTC 2020


On Mon, 9 Nov 2020 21:26:06 GMT, Sandhya Viswanathan <sviswanathan at openjdk.org> wrote:

>> `YMM0-15` registers are handled specially when CPU registers are saved. They are split in 2 parts (128-bit each) and put in different parts of the frame (see `RegisterSaver::layout` for details). AVX512 adds 16 more vector registers (ZMM16-31) and those are saved full-sized in a separate region. But `RegisterSaver::save_live_registers()` doesn't do anything special for `ZMM0-15` and their upper halves are lost (though there's space reserved for them in the frame).
>> 
>> The fix adds missing logic which saves upper halves (256-bit in size) of ZMM0-15 registers. Thus every ZMM0-15 register ends up split into 3 parts which are stored independently in the frame.
>> 
>> Testing (with some other relevant patches):
>> - [x] jdk/incubator/vector w/ -XX:+DeoptimizeALot and -XX:UseAVX=3 on AVX512-capable hardware
>> - [x] hs-precheckin-comp, hs-tier1, hs-tier2
>
> It looks like the upper 256 bits of ZMM0-15 are already being saved as part of the following statements in sharedRuntime_x86_64.cpp:
>  191   if (save_vectors) {
>  192     // Save upper half of YMM registers(0..15)
>  193     int base_addr = XSAVE_AREA_YMM_BEGIN;
>  194     for (int n = 0; n < 16; n++) {
>  195       __ vextractf128_high(Address(rsp, base_addr+n*16), as_XMMRegister(n));
>  196     }
>  197     if (VM_Version::supports_evex()) {
>  198       // Save upper half of ZMM registers(0..15)
>  199       base_addr = XSAVE_AREA_ZMM_BEGIN;
>  200       for (int n = 0; n < 16; n++) {
>  201         __ vextractf64x4_high(Address(rsp, base_addr+n*32), as_XMMRegister(n));
>  202       }
>  203       // Save full ZMM registers(16..num_xmm_regs)
>  204       base_addr = XSAVE_AREA_UPPERBANK;
>  205       off = 0;
>  206       int vector_len = Assembler::AVX_512bit;
>  207       for (int n = 16; n < num_xmm_regs; n++) {
>  208         __ evmovdqul(Address(rsp, base_addr+(off++*64)), as_XMMRegister(n), vector_le
>      n);
>  209       }
>  210     }
>  211   }

Thanks for the correction, Sandhya. 
You are absolutely right that the values are already saved. 
The problem is the `OopMap` doesn't reflect that and the patch fixes that.

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

PR: https://git.openjdk.java.net/jdk/pull/1131


More information about the hotspot-compiler-dev mailing list