< prev index next >

src/hotspot/cpu/aarch64/c1_LIRAssembler_aarch64.cpp

Print this page

        

*** 32,41 **** --- 32,42 ---- #include "c1/c1_MacroAssembler.hpp" #include "c1/c1_Runtime1.hpp" #include "c1/c1_ValueStack.hpp" #include "ci/ciArrayKlass.hpp" #include "ci/ciInstance.hpp" + #include "ci/ciValueKlass.hpp" #include "code/compiledIC.hpp" #include "gc/shared/barrierSet.hpp" #include "gc/shared/cardTableBarrierSet.hpp" #include "gc/shared/collectedHeap.hpp" #include "nativeInst_aarch64.hpp"
*** 503,512 **** --- 504,528 ---- void LIR_Assembler::return_op(LIR_Opr result) { assert(result->is_illegal() || !result->is_single_cpu() || result->as_register() == r0, "word returns are in r0,"); ciMethod* method = compilation()->method(); + + if (ValueTypeReturnedAsFields && method->signature()->returns_never_null()) { + ciType* return_type = method->return_type(); + if (return_type->is_valuetype()) { + ciValueKlass* vk = return_type->as_value_klass(); + if (vk->can_be_returned_as_fields()) { + address unpack_handler = vk->unpack_handler(); + assert(unpack_handler != NULL, "must be"); + __ far_call(RuntimeAddress(unpack_handler)); + // At this point, rax points to the value object (for interpreter or C1 caller). + // The fields of the object are copied into registers (for C2 caller). + } + } + } + // Pop the stack before the safepoint code __ remove_frame(initial_frame_size_in_bytes(), needs_stack_repair()); if (StackReservedPages > 0 && compilation()->has_reserved_stack_access()) { __ reserved_stack_check();
*** 515,526 **** address polling_page(os::get_polling_page()); __ read_polling_page(rscratch1, polling_page, relocInfo::poll_return_type); __ ret(lr); } ! void LIR_Assembler::store_value_type_fields_to_buf(ciValueKlass* vk) { ! __ store_value_type_fields_to_buf(vk); } int LIR_Assembler::safepoint_poll(LIR_Opr tmp, CodeEmitInfo* info) { address polling_page(os::get_polling_page()); guarantee(info != NULL, "Shouldn't be NULL"); --- 531,542 ---- address polling_page(os::get_polling_page()); __ read_polling_page(rscratch1, polling_page, relocInfo::poll_return_type); __ ret(lr); } ! int LIR_Assembler::store_value_type_fields_to_buf(ciValueKlass* vk) { ! return (__ store_value_type_fields_to_buf(vk, false)); } int LIR_Assembler::safepoint_poll(LIR_Opr tmp, CodeEmitInfo* info) { address polling_page(os::get_polling_page()); guarantee(info != NULL, "Shouldn't be NULL");
*** 680,692 **** break; case T_INT: assert(c->as_jint() == 0, "should be"); insn = &Assembler::strw; break; ! case T_VALUETYPE: // DMS CHECK: the code is significantly differ from x86 case T_OBJECT: case T_ARRAY: assert(c->as_jobject() == 0, "should be"); if (UseCompressedOops && !wide) { insn = &Assembler::strw; } else { insn = &Assembler::str; --- 696,710 ---- break; case T_INT: assert(c->as_jint() == 0, "should be"); insn = &Assembler::strw; break; ! case T_VALUETYPE: case T_OBJECT: case T_ARRAY: + // Non-null case is not handled on aarch64 but handled on x86 + // FIXME: do we need to add it here? assert(c->as_jobject() == 0, "should be"); if (UseCompressedOops && !wide) { insn = &Assembler::strw; } else { insn = &Assembler::str;
*** 1638,1651 **** __ b(*op->stub()->entry()); } else { Register left_klass_op = op->left_klass_op()->as_register(); Register right_klass_op = op->right_klass_op()->as_register(); ! // DMS CHECK, likely x86 bug, make aarch64 implementation correct ! __ load_klass(left_klass_op, left); ! __ load_klass(right_klass_op, right); __ cmp(left_klass_op, right_klass_op); __ br(Assembler::EQ, *op->stub()->entry()); // same klass -> do slow check // fall through to L_oops_not_equal } __ bind(L_oops_not_equal); --- 1656,1675 ---- __ b(*op->stub()->entry()); } else { Register left_klass_op = op->left_klass_op()->as_register(); Register right_klass_op = op->right_klass_op()->as_register(); ! if (UseCompressedOops) { ! __ ldrw(left_klass_op, Address(left, oopDesc::klass_offset_in_bytes())); ! __ ldrw(right_klass_op, Address(right, oopDesc::klass_offset_in_bytes())); ! __ cmpw(left_klass_op, right_klass_op); ! } else { ! __ ldr(left_klass_op, Address(left, oopDesc::klass_offset_in_bytes())); ! __ ldr(right_klass_op, Address(right, oopDesc::klass_offset_in_bytes())); __ cmp(left_klass_op, right_klass_op); + } + __ br(Assembler::EQ, *op->stub()->entry()); // same klass -> do slow check // fall through to L_oops_not_equal } __ bind(L_oops_not_equal);
< prev index next >