RFR 8156073 : 2-slot LiveStackFrame locals (long and double) are incorrect

Brent Christian brent.christian at oracle.com
Wed Aug 17 20:05:38 UTC 2016


Hi,

Please review this StackWalker fix in hotspot for 8156073, "2-slot 
LiveStackFrame locals (long and double) are incorrect"

Bug: https://bugs.openjdk.java.net/browse/JDK-8156073
Webrev: http://cr.openjdk.java.net/~bchristi/8156073/webrev.01/

The experimental LiveStackFrame[1] interface for StackWalker provides 
access to stack frames' local variables, returned in an Object[] from 
LiveStackFrame.getLocals().

Long and double primitives are returned using two array slots (similar 
to JVMS section 2.6.1 [2]).  This works as indicated on 32-bit JDKs, but 
needs some fixing on 64-bit.

AFAICT under 64-bit, StackValueCollection stores the entire
long/double in the 2nd (64-bit) slot:

jlong StackValueCollection::long_at(int slot) const {
#ifdef _LP64
   return at(slot+1)->get_int();
#else
...

The first slot goes unused and contains 0, instead of holding half of 
the long value as stackwalker expects.  So stackwalker needs to take 
care splitting the value between the two slots.

The fix examines StackValueCollection::long_at(i), checks for an 
unexpected 0 value from StackValueCollection::int_at(i), and copies
the needed 32-bits (depending on native byte ordering) into the first 
slot as needed.  (The 2nd slot gets truncated to 32-bits in 
create_primitive_value_instance()).

Here's the fix in action on linux_x64 with the updated 
LocalsAndOperands.java test.  Slots 4+5 contain a long, 6+7 contain a 
double.

Before the fix:
...
   local 3: himom type java.lang.String
   local 4: 0 type I          <--
   local 5: 65535 type I
   local 6: 0 type I          <--
   local 7: 1293080650 type I
   local 8: 0 type I

After the fix:
...
   local 3: himom type java.lang.String
   local 4: 1023 type I       <--
   local 5: 65535 type I
   local 6: 1074340347 type I <--
   local 7: 1293080650 type I
   local 8: 0 type I

This change also fixes 8158879, "Add new test for verifying 2-slot 
locals in LiveStackFrame".  Thanks to Fabio Tudone 
(fabio at paralleluniverse.co) for the test case.  I only test unused 
("dead") local variables with -Xint, because they are removed in 
compiled frames.

An automated build & test run on all platforms looks good.

It would be good to also do more testing of LiveStackFrame.getStack(), 
but right now I want to focus on getting this getLocals() fix in. 
Testing of LiveStackFrame.getStack() will happen in a follow-up issue 
(8163825).

Thanks,
-Brent

1. 
http://hg.openjdk.java.net/jdk9/hs/jdk/file/1efce54b06b7/src/java.base/share/classes/java/lang/LiveStackFrame.java
2. https://docs.oracle.com/javase/specs/jvms/se8/html/jvms-2.html#jvms-2.6.1



More information about the core-libs-dev mailing list