Occurs on PPC Linux when running the dacapo jython
benchmark and pseudojbb, with a FastAdaptiveMarkSweep
build (and probably others). Looks to be caused by the
latest committed change, as backing this out appears to
fix it.
The stackdump is:
vm: somebody forgot to conditionalize their call to
assert with
vm: if (VM.VerifyAssertions)
vm internal error: assert called when !VM.VerifyAssertions
-- Stack --
Lcom/ibm/JikesRVM/VM;
_assertionFailure(Ljava/lang/String;Ljava/lang/String;)V
at line 573
Lcom/ibm/JikesRVM/VM;
_assert(ZLjava/lang/String;Ljava/lang/String;)V at line 552
Lcom/ibm/JikesRVM/VM; _assert(Z)V at line 534
Lcom/ibm/JikesRVM/opt/OPT_GenericStackManager;
insertSpillCode(Lcom/ibm/JikesRVM/opt/OPT_LinearScan$ActiveSet;)V
at line 1086
Lcom/ibm/JikesRVM/opt/OPT_LinearScan$SpillCode;
perform(Lcom/ibm/JikesRVM/opt/ir/OPT_IR;)V at line 2438
Lcom/ibm/JikesRVM/opt/OPT_CompilerPhase;
performPhase(Lcom/ibm/JikesRVM/opt/ir/OPT_IR;)V at line 129
Lcom/ibm/JikesRVM/opt/OPT_OptimizationPlanAtomicElement;
perform(Lcom/ibm/JikesRVM/opt/ir/OPT_IR;)V at line 80
Lcom/ibm/JikesRVM/opt/OPT_OptimizationPlanCompositeElement;
perform(Lcom/ibm/JikesRVM/opt/ir/OPT_IR;)V at line 141
Lcom/ibm/JikesRVM/opt/OPT_OptimizationPlanCompositeElement;
perform(Lcom/ibm/JikesRVM/opt/ir/OPT_IR;)V at line 141
Lcom/ibm/JikesRVM/opt/OPT_OptimizationPlanCompositeElement;
perform(Lcom/ibm/JikesRVM/opt/ir/OPT_IR;)V at line 141
Lcom/ibm/JikesRVM/opt/OPT_CompilationPlan;
execute()Lcom/ibm/JikesRVM/opt/ir/OPT_IR; at line 105
Lcom/ibm/JikesRVM/opt/OPT_Compiler;
compile(Lcom/ibm/JikesRVM/opt/OPT_CompilationPlan;)Lcom/ibm/JikesRVM/VM_CompiledMethod;
at line 222
Lcom/ibm/JikesRVM/VM_RuntimeCompiler;
optCompile(Lcom/ibm/JikesRVM/classloader/VM_NormalMethod;Lcom/ibm/JikesRVM/opt/OPT_CompilationPlan;)Lcom/ibm/JikesRVM/VM_CompiledMethod;
at line 377
Lcom/ibm/JikesRVM/VM_RuntimeCompiler;
recompileWithOpt(Lcom/ibm/JikesRVM/opt/OPT_CompilationPlan;)I
at line 519
Lcom/ibm/JikesRVM/adaptive/VM_ControllerPlan;
doRecompile()Lcom/ibm/JikesRVM/VM_CompiledMethod; at
line 179
Lcom/ibm/JikesRVM/adaptive/VM_CompilationThread;
run()V at line 54
Lcom/ibm/JikesRVM/VM_Thread; startoff()V at line 781
Logged In: YES
user_id=308843
Hi Robin,
which change did you back out? This is a bug caused by the
changes to the OSR_YieldPoints (I believe) which previously
didn't have their operands renamed during register
allocation. This led to OSR_YieldPoints refering to
registers that were no longer defined on Intel. I removed
the code that stopped renaming being applied to everything
but OSR_YieldPoints (in OPT_GenericStackManager) and that
stopped the problem of undefined registers being referenced
on Intel - so we passed more IR validation than we did
previously. Looking at the PowerPC OPT_StackManager the
needScratch method returns false for a OSR_YieldPoint but
true for everything else (there's a nice comment of "//
PowerPC does not support memory operands"). Reading the
javadoc this means that the OSR_YieldPoint on PowerPC
references memory operands (which the PowerPC doesn't have
and the comment points out). It seems the PowerPC
OPT_StackManager needScratch routine should always return
true regardless of the instruction operator, but this may
have a detrimental effect on register allocation which was
previously choosing to ignore these scratch registers. I
guess this was the cause of the conditional compilation
which was causing the odd behaviour I was seeing on Intel.
We could re-introduce the conditional compilation around the
VM._assert(NOT_REACHED) on line 1086 for PowerPC, but I
don't think this makes the code particularly intelligible.
We should probably make needScratch always return true for
PowerPC and then add a check around the spill register
creation code that says not to do it for PowerPC
YieldPoint_OSR instructions. But we should probably redefine
these operands to something sane to avoid the use with no
definition validation error. I don't understand why PowerPC
OSR_YieldPoint instructions are so special :-).
The whole of the register allocation is due for a (graph
colouring) rethink, but in the mean time the linear scan
algorithm needs patching up. Not fully understanding the
history behing all of the hacks/improvements may be someone
else can write the patch to fix this. For more hacks of the
register allocator see line 999 of OPT_GenericStackManager
whose bug tracking numbers don't appear to make sense when
you follow them through (2642 should be about a bug with the
ECX register but the new reference number 1147274 talks
about a bug with ESP).
Regards, Ian Rogers
Logged In: YES
user_id=308843
I should have read the comments more, the bug tracking on
line 999 do make sense but the dirty fix has been in place
for 3 years - bleugh :-(. This is all unrelated to the yield
point stuff anyway, I just remember not liking it when I was
trying to fix up the validation - primarily on Intel trying
to get to the cause of bug #1363830 so the loop versioning
could be enabled by default.
Ian
Logged In: YES
user_id=1215435
The assert in questions is a VM._assert(NOT_REACHED).
So, yes it should have been guarded by if
VM.VerifyAssertions, but we should never reach that program
point in any case.
Logged In: YES
user_id=1215435
back out change to OPT_GenericStackManager for now.
Have to consider more carefully if this is actually the
right fix.
Logged In: YES
user_id=308843
Why not back it out for the PowerPC, add the verify
assertions line and add some health warnings e.g.
in OPT_StackManager:
// for some reason PowerPC OSR_YieldPoint instructions think
they can have memory operands (?)
in OPT_GenericStackManager:
// ignore the PowerPC stack manager telling us it can have
memory operands here, it can't, so do nothing. HEALTH
WARNING: This will lead to uses of operands that haven't
been defined and will fail certain IR verifications.
It seems a shame to have this PowerPC botch making a mess of
allocation for Intel and regressing us so that we have
instructions referencing undefined operands again (imo).
Ian
Logged In: YES
user_id=1215435
To properly fix this, someone needs to take the time to go
through and understand how OSR_YieldPoint instructions are
being used in the backend to generate OSR maps. Once we
have a better grasp on that, it should be more clear what
the constraints on their operands need to be.