Problem with testN_mem_reg0 in register allocation.

Vladimir Kozlov vladimir.kozlov at oracle.com
Mon Aug 19 10:57:37 PDT 2013


Goetz, Martin

I would speculate it is scheduled very early by GCM because of memory 
access anti-dependency. Somewhere there is a store or other changes to 
this memory slice. Yes, matcher should not allow such matching. I am not 
sure we have an anti-dependency check when we match (need to look). The 
method which should do that is Matcher::find_shared().

The easiest fix would be in place where we try to spill flag do bailout 
with recompilation without subsuming loads:

     if (C->subsume_loads() == true && !C->failing()) {
       // Retry with subsume_loads == false
       // If this is the first failure, the sentinel string will "stick"
       // to the Compile object, and the C2Compiler will see it and retry.
       C->record_failure(C2Compiler::retry_no_subsuming_loads());

Regards,
Vladimir

On 8/19/13 8:04 AM, Lindenmaier, Goetz wrote:
> Hi,
>
> we are currently analyzing a bug in our jdk7 VM, which is based on
> HS23.  It happens on linux x86_64.
>
> Register allocation tries to spill a RefFlags register, and, as to
> expect, fails on this leading to a SIGSEGV.
>
> I suspect this is a strange interdependency between gcm and
> register allocation
>
> Gcm produces something as the following pattern (I simplified
> to get the essentials).
>
>            Block 35
>              Call
>              209 testN_mem_reg0
>              Catch
>         /              \
>        /                \
>      |/_                _\|
> Block 36             Block 146
>    ...                 ...
>                        159 testP_reg
>                        158 jmpCon(212)
>       \                   /
>        \                 /
>        _\|             |/_
>          Block 39
>            ...
>         /              \
>        /                \
>      |/_                _\|
> Block 140              ...
>    208 jmpCon(209)
>
> Then call_catch_cleanup() repairs the position of 209.
> It adds 1088, 1089 and 1090.
>
>            Block 35
>              Call
>              Catch
>         /              \
>        /                \
>      |/_                _\|
> Block 36               Block 146
>    1089 testN_mem_reg0    1088 testN_mem_reg0
>    ...                    ...
>                           159 testP_reg
>                           158 jmpCon(212)
>       \                   /
>        \                 /
>        _\|             |/_
>          Block 39
>            1090 Phi(1089, 1088)
>            ...
>         /              \
>        /                \
>      |/_                _\|
> Block 140              ...
>    208 jmpCon(1090)
>
> Register allocation now wants to spill the register of 1088.
> This is necessary as 159 needs the flag register.
> Have you seen such a problem before?
>
> We could envision that one the following 3 behaviors is expected and
> should get fixed:
>
> 1. gcm should place node 209 in Block 140.
> 2. Register allocation should be able to properly rematerialize the
> testN_mem_reg0 node (which does allow rematerialization).
>     This would require that it recognizes that the Phi merges twice the
> same value.
> 3. The matcher should not match this node (which matches on a Load and
> Cmp)?
>
> Best reagrds,
> Martin & Goetz.
>


More information about the hotspot-compiler-dev mailing list