# HG changeset patch # User Thomas Wuerthinger # Date 1362584238 -3600 # Node ID 3d41998c30de809bffd52daf6efb78c5ea478a7d # Parent 0026a2e70695afcc3ecbdbbc0e36794eed17632d Create new way of handling unwind that recalculates rbp from rsp. Remove unused instanceof slow path stub. diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.compiler.ptx/src/com/oracle/graal/compiler/ptx/PTXLIRGenerator.java --- a/graal/com.oracle.graal.compiler.ptx/src/com/oracle/graal/compiler/ptx/PTXLIRGenerator.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.compiler.ptx/src/com/oracle/graal/compiler/ptx/PTXLIRGenerator.java Wed Mar 06 16:37:18 2013 +0100 @@ -466,4 +466,10 @@ public void visitSafepointNode(SafepointNode i) { throw new InternalError("NYI"); } + + @Override + public void emitUnwind(Value operand) { + // TODO Auto-generated method stub + + } } diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.compiler.sparc/src/com/oracle/graal/compiler/sparc/SPARCLIRGenerator.java --- a/graal/com.oracle.graal.compiler.sparc/src/com/oracle/graal/compiler/sparc/SPARCLIRGenerator.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.compiler.sparc/src/com/oracle/graal/compiler/sparc/SPARCLIRGenerator.java Wed Mar 06 16:37:18 2013 +0100 @@ -368,4 +368,10 @@ // SPARC: Auto-generated method stub } + + @Override + public void emitUnwind(Value operand) { + // TODO Auto-generated method stub + + } } diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackend.java --- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackend.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackend.java Wed Mar 06 16:37:18 2013 +0100 @@ -165,6 +165,13 @@ emitMove(targetAddress, operand(callTarget.computedAddress())); append(new AMD64IndirectCallOp(callTarget.target(), result, parameters, temps, metaspaceMethod, targetAddress, callState)); } + + @Override + public void emitUnwind(Value exception) { + RegisterValue exceptionParameter = AMD64.rax.asValue(); + emitMove(exceptionParameter, exception); + append(new AMD64HotSpotUnwindOp(exceptionParameter)); + } } /** diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRegisterConfig.java --- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRegisterConfig.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRegisterConfig.java Wed Mar 06 16:37:18 2013 +0100 @@ -37,9 +37,8 @@ // @formatter:off public class AMD64HotSpotRegisterConfig implements RegisterConfig { - // be careful - the contents of this array are duplicated in graal_CodeInstaller.cpp private final Register[] allocatable = { - rax, rbx, rcx, rdx, rsi, rdi, r8, r9, /* r10, */r11, r12, r13, r14, /*r15*/ + rax, rbx, rcx, rdx, /*rsp, rbp, */rsi, rdi, r8, r9, /* r10, */r11, r12, r13, r14, /*r15, */ xmm0, xmm1, xmm2, xmm3, xmm4, xmm5, xmm6, xmm7, xmm8, xmm9, xmm10, xmm11, xmm12, xmm13, xmm14, xmm15 }; diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRuntime.java --- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRuntime.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRuntime.java Wed Mar 06 16:37:18 2013 +0100 @@ -54,6 +54,10 @@ Kind word = graalRuntime.getTarget().wordKind; // @formatter:off + addRuntimeCall(AMD64HotSpotUnwindOp.UNWIND_EXCEPTION, config.unwindExceptionStub, + /* temps */ null, + /* ret */ ret(Kind.Void), + /* arg0: exception */ javaCallingConvention(Kind.Object)); addRuntimeCall(DEOPTIMIZE, config.deoptimizeStub, /* temps */ null, diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotUnwindOp.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotUnwindOp.java Wed Mar 06 16:37:18 2013 +0100 @@ -0,0 +1,64 @@ +/* + * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.graal.hotspot.amd64; + +import static com.oracle.graal.amd64.AMD64.*; +import static com.oracle.graal.lir.LIRInstruction.OperandFlag.*; + +import com.oracle.graal.amd64.*; +import com.oracle.graal.api.code.*; +import com.oracle.graal.api.code.RuntimeCallTarget.*; +import com.oracle.graal.asm.amd64.*; +import com.oracle.graal.lir.LIRInstruction.Opcode; +import com.oracle.graal.lir.amd64.*; +import com.oracle.graal.lir.asm.*; + +/** + * Performs an unwind to throw an exception. + */ +@Opcode("CALL_INDIRECT") +final class AMD64HotSpotUnwindOp extends AMD64LIRInstruction { + + public static final Descriptor UNWIND_EXCEPTION = new Descriptor("unwindException", true, void.class, Object.class); + + /** + * Vtable stubs expect the metaspace Method in RBX. + */ + public static final Register METHOD = AMD64.rbx; + + @Use({REG}) protected AllocatableValue exception; + @Temp private RegisterValue framePointer; + + AMD64HotSpotUnwindOp(AllocatableValue exception) { + this.exception = exception; + assert exception == AMD64.rax.asValue(); + framePointer = AMD64.rbp.asValue(); + } + + @Override + public void emitCode(TargetMethodAssembler tasm, AMD64MacroAssembler masm) { + masm.movq(framePointer.getRegister(), rsp); + masm.incrementq(framePointer.getRegister(), tasm.frameMap.frameSize() - 8); + AMD64Call.directCall(tasm, masm, tasm.runtime.lookupRuntimeCall(UNWIND_EXCEPTION), null); + } +} diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java Wed Mar 06 16:37:18 2013 +0100 @@ -304,7 +304,6 @@ public int typeProfileWidth; // runtime stubs - public long instanceofStub; public long newInstanceStub; public long newArrayStub; public long newMultiArrayStub; diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotRuntime.java --- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotRuntime.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotRuntime.java Wed Mar 06 16:37:18 2013 +0100 @@ -32,7 +32,6 @@ import static com.oracle.graal.hotspot.HotSpotGraalRuntime.*; import static com.oracle.graal.hotspot.snippets.SystemSubstitutions.*; import static com.oracle.graal.java.GraphBuilderPhase.RuntimeCalls.*; -import static com.oracle.graal.nodes.UnwindNode.*; import static com.oracle.graal.nodes.java.RegisterFinalizerNode.*; import static com.oracle.graal.snippets.Log.*; import static com.oracle.graal.snippets.MathSubstitutionsX86.*; @@ -204,11 +203,6 @@ // @formatter:off - addRuntimeCall(UNWIND_EXCEPTION, config.unwindExceptionStub, - /* temps */ null, - /* ret */ ret(Kind.Void), - /* arg0: exception */ javaCallingConvention(Kind.Object)); - addRuntimeCall(OnStackReplacementPhase.OSR_MIGRATION_END, config.osrMigrationEndStub, /* temps */ null, /* ret */ ret(Kind.Void), diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/UnwindNode.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/UnwindNode.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/UnwindNode.java Wed Mar 06 16:37:18 2013 +0100 @@ -22,8 +22,6 @@ */ package com.oracle.graal.nodes; -import com.oracle.graal.api.code.*; -import com.oracle.graal.api.code.RuntimeCallTarget.Descriptor; import com.oracle.graal.api.meta.*; import com.oracle.graal.graph.*; import com.oracle.graal.nodes.spi.*; @@ -35,8 +33,6 @@ */ public final class UnwindNode extends FixedNode implements LIRLowerable, Node.IterableNodeType { - public static final Descriptor UNWIND_EXCEPTION = new Descriptor("unwindException", true, void.class, Object.class); - @Input private ValueNode exception; public ValueNode exception() { @@ -51,7 +47,6 @@ @Override public void generate(LIRGeneratorTool gen) { - RuntimeCallTarget call = gen.getRuntime().lookupRuntimeCall(UNWIND_EXCEPTION); - gen.emitCall(call, call.getCallingConvention(), false, gen.operand(exception())); + gen.emitUnwind(gen.operand(exception())); } } diff -r 0026a2e70695 -r 3d41998c30de graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/spi/LIRGeneratorTool.java --- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/spi/LIRGeneratorTool.java Tue Mar 05 23:58:57 2013 +0100 +++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/spi/LIRGeneratorTool.java Wed Mar 06 16:37:18 2013 +0100 @@ -132,4 +132,6 @@ public abstract void visitSafepointNode(SafepointNode i); public abstract void visitBreakpointNode(BreakpointNode i); + + public abstract void emitUnwind(Value operand); } diff -r 0026a2e70695 -r 3d41998c30de src/cpu/x86/vm/graalRuntime_x86.cpp --- a/src/cpu/x86/vm/graalRuntime_x86.cpp Tue Mar 05 23:58:57 2013 +0100 +++ b/src/cpu/x86/vm/graalRuntime_x86.cpp Wed Mar 06 16:37:18 2013 +0100 @@ -46,12 +46,6 @@ assert(!(oop_result1->is_valid() || metadata_result->is_valid()) || oop_result1 != metadata_result, "registers must be different"); assert(oop_result1 != thread && metadata_result != thread, "registers must be different"); assert(args_size >= 0, "illegal args_size"); - bool align_stack = false; -#ifdef _LP64 - // At a method handle call, the stack may not be properly aligned - // when returning with an exception. - align_stack = (stub_id() == false /*GraalRuntime::handle_exception_from_callee_id*/); -#endif #ifdef _LP64 mov(c_rarg0, thread); @@ -65,20 +59,11 @@ #endif // _LP64 int call_offset; - if (!align_stack) { - set_last_Java_frame(thread, noreg, rbp, NULL); - } else { - address the_pc = pc(); - call_offset = offset(); - set_last_Java_frame(thread, noreg, rbp, the_pc); - andptr(rsp, -(StackAlignmentInBytes)); // Align stack - } + set_last_Java_frame(thread, rsp, noreg, NULL); // do the call call(RuntimeAddress(entry)); - if (!align_stack) { - call_offset = offset(); - } + call_offset = offset(); // verify callee-saved register #ifdef ASSERT guarantee(thread != rax, "change this code"); @@ -93,7 +78,7 @@ } pop(rax); #endif - reset_last_Java_frame(thread, true, align_stack); + reset_last_Java_frame(thread, true, false); // discard thread and arguments NOT_LP64(addptr(rsp, num_rt_args()*BytesPerWord)); @@ -356,6 +341,7 @@ map->set_callee_saved(VMRegImpl::stack2reg(rcx_off + num_rt_args), rcx->as_VMReg()); map->set_callee_saved(VMRegImpl::stack2reg(rdx_off + num_rt_args), rdx->as_VMReg()); map->set_callee_saved(VMRegImpl::stack2reg(rbx_off + num_rt_args), rbx->as_VMReg()); + map->set_callee_saved(VMRegImpl::stack2reg(rbp_off + num_rt_args), rbp->as_VMReg()); map->set_callee_saved(VMRegImpl::stack2reg(rsi_off + num_rt_args), rsi->as_VMReg()); map->set_callee_saved(VMRegImpl::stack2reg(rdi_off + num_rt_args), rdi->as_VMReg()); #ifdef _LP64 @@ -373,6 +359,7 @@ map->set_callee_saved(VMRegImpl::stack2reg(rcxH_off + num_rt_args), rcx->as_VMReg()->next()); map->set_callee_saved(VMRegImpl::stack2reg(rdxH_off + num_rt_args), rdx->as_VMReg()->next()); map->set_callee_saved(VMRegImpl::stack2reg(rbxH_off + num_rt_args), rbx->as_VMReg()->next()); + map->set_callee_saved(VMRegImpl::stack2reg(rbpH_off + num_rt_args), rbp->as_VMReg()->next()); map->set_callee_saved(VMRegImpl::stack2reg(rsiH_off + num_rt_args), rsi->as_VMReg()->next()); map->set_callee_saved(VMRegImpl::stack2reg(rdiH_off + num_rt_args), rdi->as_VMReg()->next()); @@ -933,69 +920,10 @@ } break; - case slow_subtype_check_id: - { - // Typical calling sequence: - // __ push(klass_RInfo); // object klass or other subclass - // __ push(sup_k_RInfo); // array element klass or other superclass - // __ call(slow_subtype_check); - // Note that the subclass is pushed first, and is therefore deepest. - // Previous versions of this code reversed the names 'sub' and 'super'. - // This was operationally harmless but made the code unreadable. - enum layout { - rax_off, SLOT2(raxH_off) - rcx_off, SLOT2(rcxH_off) - rsi_off, SLOT2(rsiH_off) - rdi_off, SLOT2(rdiH_off) - // saved_rbp_off, SLOT2(saved_rbpH_off) - return_off, SLOT2(returnH_off) - sup_k_off, SLOT2(sup_kH_off) - klass_off, SLOT2(superH_off) - framesize, - result_off = klass_off // deepest argument is also the return value - }; - - __ set_info("slow_subtype_check", dont_gc_arguments); - __ push(rdi); - __ push(rsi); - __ push(rcx); - __ push(rax); - - // This is called by pushing args and not with C abi - __ movptr(rsi, Address(rsp, (klass_off) * VMRegImpl::stack_slot_size)); // subclass - __ movptr(rax, Address(rsp, (sup_k_off) * VMRegImpl::stack_slot_size)); // superclass - - Label miss; - Label success; - __ check_klass_subtype_fast_path(rsi, rax, rcx, &success, &miss, NULL); - - __ check_klass_subtype_slow_path(rsi, rax, rcx, rdi, NULL, &miss); - - // fallthrough on success: - __ bind(success); - __ movptr(Address(rsp, (result_off) * VMRegImpl::stack_slot_size), 1); // result - __ pop(rax); - __ pop(rcx); - __ pop(rsi); - __ pop(rdi); - __ ret(0); - - __ bind(miss); - __ movptr(Address(rsp, (result_off) * VMRegImpl::stack_slot_size), NULL_WORD); // result - __ pop(rax); - __ pop(rcx); - __ pop(rsi); - __ pop(rdi); - __ ret(0); - } - break; - case unwind_exception_call_id: { // remove the frame from the stack __ movptr(rsp, rbp); __ pop(rbp); - // exception_oop is passed using ordinary java calling conventions - __ movptr(rax, j_rarg0); Label nonNullExceptionOop; __ testptr(rax, rax); diff -r 0026a2e70695 -r 3d41998c30de src/share/vm/graal/graalCompilerToVM.cpp --- a/src/share/vm/graal/graalCompilerToVM.cpp Tue Mar 05 23:58:57 2013 +0100 +++ b/src/share/vm/graal/graalCompilerToVM.cpp Wed Mar 06 16:37:18 2013 +0100 @@ -702,7 +702,6 @@ set_int("layoutHelperHeaderSizeMask", Klass::_lh_header_size_mask); set_int("layoutHelperOffset", in_bytes(Klass::layout_helper_offset())); - set_stub("instanceofStub", GraalRuntime::entry_for(GraalRuntime::slow_subtype_check_id)); set_stub("newInstanceStub", GraalRuntime::entry_for(GraalRuntime::new_instance_id)); set_stub("newArrayStub", GraalRuntime::entry_for(GraalRuntime::new_array_id)); set_stub("newMultiArrayStub", GraalRuntime::entry_for(GraalRuntime::new_multi_array_id)); diff -r 0026a2e70695 -r 3d41998c30de src/share/vm/graal/graalRuntime.cpp --- a/src/share/vm/graal/graalRuntime.cpp Tue Mar 05 23:58:57 2013 +0100 +++ b/src/share/vm/graal/graalRuntime.cpp Wed Mar 06 16:37:18 2013 +0100 @@ -127,7 +127,6 @@ // Make sure that stubs that need oopmaps have them switch (id) { // These stubs don't need to have an oopmap - case slow_subtype_check_id: #if defined(SPARC) || defined(PPC) case handle_exception_nofpu_id: // Unused on sparc #endif diff -r 0026a2e70695 -r 3d41998c30de src/share/vm/graal/graalRuntime.hpp --- a/src/share/vm/graal/graalRuntime.hpp Tue Mar 05 23:58:57 2013 +0100 +++ b/src/share/vm/graal/graalRuntime.hpp Wed Mar 06 16:37:18 2013 +0100 @@ -86,7 +86,6 @@ stub(new_array) \ stub(new_multi_array) \ stub(handle_exception_nofpu) /* optimized version that does not preserve fpu registers */ \ - stub(slow_subtype_check) \ stub(unwind_exception_call) \ stub(OSR_migration_end) \ stub(arithmetic_frem) \