JDK-8153357 : C2 creates incorrect cast after eliminating phi with unique input
  • Type: Bug
  • Component: hotspot
  • Sub-Component: compiler
  • Affected Version: 8u112,9
  • Priority: P3
  • Status: Resolved
  • Resolution: Fixed
  • Submitted: 2016-04-04
  • Updated: 2016-11-23
  • Resolved: 2016-04-18
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 b120Fixed
Related Reports
Relates :  
Description
The test java/lang/invoke/VarargsArrayTest.java fails in the compiler nightlies of 2016-04-01 due to the following assert:

#
# A fatal error has been detected by the Java Runtime Environment:
#
#  Internal Error (C:\jprt\T\P1\153346.dmitrij\s\hotspot\src\share\vm\opto\castnode.cpp:333), pid=62836, tid=64164
#  Error: assert(jptr) failed
#
# JRE version: Java(TM) SE Runtime Environment (9.0) (fastdebug build 9-internal+0-2016-04-01-153346.dmitrij.hs-comp)
# Java VM: Java HotSpot(TM) Server VM (fastdebug 9-internal+0-2016-04-01-153346.dmitrij.hs-comp, compiled mode, tiered, g1 gc, windows-x86)
# Core dump will be written. Default location: C:\Users\aurora\sandbox\results\workDir\java\lang\invoke\VarargsArrayTest\hs_err_pid62836.mdmp
Comments
Needs to be backported if JDK-8139771 is backported as well.
23-11-2016

Here is the updated webrev: http://cr.openjdk.java.net/~zmajo/8153357/webrev.01/
15-04-2016

The failure appears during the first round of loop optimizations performed after CCP. Here is the sequence of optimizations that lead to the crash: PhaseCCP IterGVN2 Loop optimization Beaufity loops Split-if IterGVN -> Crash Before the split-if optimization, '3090 Phi' of type 'klass' has two inputs: - '1612 Conp' of type 'klass' (precise klass java/lang/String) - '44 LoadKlass' of type 'klass' (rawptr:BotPTR) '3090 Phi' has one output, '3087 CastPP', that changes the type of '3090 Phi' to 'klass java/lang/Object'. During the split-if optimization, the chain '2476 CmpP' -> '2475 Bool' -> '3091 If' -> '3092 IfTrue' is split through '2774 Phi'. As a result, several nodes are cloned in the graph and new merge points appear. One of these new merge points is produced from the chain previously described (the chain ending in '3087 CastPP'). The new merge point ('3732 Phi') is shown in the attached picture. '3732 Phi' has two CastPP inputs (3713 and 3714). Both CastPPs have the same type (klass java/lang/Object) and they also have the same input, '1612 ConP'. As a result, after the split-if optimization, IterGVN determines that '3732 Phi' has a unique input. The CastPPs (3713 and 3714) are removed and a CheckCastPP ('3757 CheckCastPP') is added instead. Then, PhaseIterGVN::transform is invoked on '3757 CheckCastPP'. Here is the state of the graph when the failure appears: 1612 ConP === 0 [[ 2873 3714 3713 3757 ]] #precise klass java/lang/String: 0x007cbfb8:Constant:exact * Klass:precise klass java/lang/String: 0x007cbfb8:Constant:exact * 3727 Region === 3727 3728 3729 [[ 3727 3687 3730 3732 3733 3734 3736 3757 ]] !orig=[3688],[3092],811 !jvms: VarargsArrayTest::makeTestArray @ bci:75 3757 CheckCastPP === 3727 1612 [[]] #klass java/lang/Object: 0x007cbf60 * carry dependency Klass:klass java/lang/Object: 0x007cbf60 * The failure appears because CheckCastPPNode::Value() assumes that if the input of a CheckCastPP is constant, the input must be an oop. Howver, in our case the input is a klass pointer. The solution I propose is to replace the phi with the unique input with a CastPP node (if both the Phi and its unique input is a klass pointer). I've checked and we seem to always use CastPPs for casting between klass pointers. The attached the IGV output (graph.191.out1.xml) illustrates what I've described above. The two phases that provide additional information to what I've described above are the last "Before Split-If" and "After Split-If".
14-04-2016

webrev.00: http://cr.openjdk.java.net/~zmajo/8153357/webrev.00/
14-04-2016

No, the problem is not related to JDK-8146792: I've managed to reproduce failure with a build that backs out JDK-8146792.
06-04-2016

Issue likely to be related to JDK-8146792.
05-04-2016

This bug not an integration blocker as it has appeared already in the "Def" compiler nightlies of 2016-01-13.
05-04-2016

Here is the stack trace: V [jvm.dll+00836fd9] = 00835be0+1017 static void VMError::report_and_die(int,char const *,char const *,char *,class Thread *,unsigned char *,void *,void *,char const *,int,unsigned int) 08836be0 f vmEr\ ror.obj V [jvm.dll+008374a7] = 00836480+ 39 static void VMError::report_and_die(class Thread *,char const *,int,char const *,char const *,char *) 08837480 f vmError.obj V [jvm.dll+0035dfc8] = 0035cf80+ 72 void report_vm_error(char const *,int,char const *,char const *,...) 0835df80 f debug.obj V [jvm.dll+0028bfa9] = 0028ae80+ 297 virtual class Type const * CheckCastPPNode::Value(class PhaseGVN *)const 0828be80 f castnode.obj V [jvm.dll+007258d4] = 00724650+ 644 virtual class Node * PhaseIterGVN::transform_old(class Node *) 08725650 f phaseX.obj V [jvm.dll+00725354] = 007242c0+ 148 virtual class Node * PhaseIterGVN::transform(class Node *) 087252c0 f phaseX.obj V [jvm.dll+0028d452] = 0028c050+1026 virtual class Node * PhiNode::Ideal(class PhaseGVN *,bool) 0828d050 f cfgnode.obj V [jvm.dll+007256ee] = 00724650+ 158 virtual class Node * PhaseIterGVN::transform_old(class Node *) 08725650 f phaseX.obj V [jvm.dll+00723e07] = 00722ca0+ 359 void PhaseIterGVN::optimize(void) 08723ca0 f phaseX.obj V [jvm.dll+00608627] = 00606b70+2743 void PhaseIdealLoop::build_and_optimize(bool,bool) 08607b70 f loopnode.obj V [jvm.dll+0031c745] = 0031b6a0+ 165 PhaseIdealLoop::PhaseIdealLoop(class PhaseIterGVN &,bool,bool) 0831c6a0 f i compile.obj V [jvm.dll+0031e745] = 0031cfe0+1893 void Compile::Optimize(void) 0831dfe0 f compile.obj V [jvm.dll+0031be27] = 0031a1b0+3191 Compile::Compile(class ciEnv *,class C2Compiler *,class ciMethod *,int,bool,bool,bool,class DirectiveSet *) 0831b1b0 f compile.obj V [jvm.dll+00279bbc] = 00278ae0+ 220 virtual void C2Compiler::compile_method(class ciEnv *,class ciMethod *,int,class DirectiveSet *) 08279ae0 f c2compiler.obj V [jvm.dll+0032c717] = 0032b1c0+1367 static void CompileBroker::invoke_compiler_on_method(class CompileTask *) 0832c1c0 f compileBroker.obj V [jvm.dll+0032b68c] = 0032a420+ 620 static void CompileBroker::compiler_thread_loop(void) 0832b420 f compileBroker.obj V [jvm.dll+007fd83c] = 007fc740+ 252 void JavaThread::thread_main_inner(void) 087fd740 f thread.obj V [jvm.dll+007fcbb7] = 007fba20+ 407 virtual void JavaThread::run(void) 087fca20 f thread.obj V [jvm.dll+006ead7c] = 006e9c80+ 252 unsigned int __stdcall java_start(class Thread *) 086eac80 f os_windows.obj C [msvcr120.dll+0x2c01d] C [msvcr120.dll+0x2c001] C [KERNEL32.DLL+0x17c04] C [ntdll.dll+0x5ad6f] C [ntdll.dll+0x5ad3a]
04-04-2016