JDK-8150186 : Folding mismatched accesses with @Stable is incorrect
  • Type: Bug
  • Component: hotspot
  • Sub-Component: compiler
  • Affected Version: 9
  • Priority: P1
  • Status: Closed
  • Resolution: Fixed
  • Submitted: 2016-02-18
  • Updated: 2020-09-01
  • Resolved: 2016-02-26
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 9
9 b110Fixed
Related Reports
Duplicate :  
Duplicate :  
Relates :  
Relates :  
Relates :  
Relates :  
Description
This seems to reproduce only with String code, when @Stable is placed over String.value field with JDK-8150180:

 public final class String
     implements java.io.Serializable, Comparable<String>, CharSequence {
 
+    @Stable
     private final byte[] value;

Then after we compile charAt() over a constant String, we are cut out higher bytes. 

Steps to reproduce:  
  1. Get the test: http://cr.openjdk.java.net/~shade/8150186/TestStableStrings.java
  2. Run, get:

java.lang.IllegalStateException: Failed, got = 45, but needed 1069
	at TestStableStrings.main(TestStableStrings.java:15)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:520)
	at com.sun.javatest.regtest.agent.MainWrapper$MainThread.run(MainWrapper.java:92)
	at java.lang.Thread.run(Thread.java:804)

1069 is 100_00101101b, while 45 is 101101b, so we cut out half of the char.

Test passes with -XX:+UnlockDiagnosticVMOptions -XX:DisableIntrinsic=_getCharStringU, which indicates the potential trouble with intrinsic.
Test passes with -XX:-FoldStableValues, which may indicate that intrinsic generates an access that @Stable machinery then misoptimizes.

AFAIU, StringUTF16.getChar produces a "char" load over byte[] array. LoadNode::Value code that folds stable array elements ignores that load type, and reads the constant off the array with the array type, e.g. "byte" -- see memnode.cpp::fold_stable_ary_elem. Everything goes downhill from there. This seems to be a generic problem with @Stable folding over mismatched accesses.

We avoid this with JDK-8150180 by special-casing the constant values in intrinsic. However, some other code shapes may expose the same problem, see JDK-8150517. The compiler code should really assert the mismatched loads when folding @Stable, and bail on mismatch.
Comments
verified by nightly testing
26-07-2017

Integration blocker -> P1
24-02-2016