< prev index next >

src/cpu/x86/vm/c1_LIRGenerator_x86.cpp

Print this page

        

*** 298,316 **** CodeEmitInfo* null_check_info = NULL; if (x->needs_null_check()) { null_check_info = new CodeEmitInfo(range_check_info); } // emit array address setup early so it schedules better ! LIR_Address* array_addr = emit_array_address(array.result(), index.result(), x->elt_type(), obj_store); if (GenerateRangeChecks && needs_range_check) { if (use_length) { __ cmp(lir_cond_belowEqual, length.result(), index.result()); __ branch(lir_cond_belowEqual, T_INT, new RangeCheckStub(range_check_info, index.result())); } else { ! array_range_check(array.result(), index.result(), null_check_info, range_check_info); // range_check also does the null check null_check_info = NULL; } } --- 298,327 ---- CodeEmitInfo* null_check_info = NULL; if (x->needs_null_check()) { null_check_info = new CodeEmitInfo(range_check_info); } + LIR_Opr ary = array.result(); + ary = shenandoah_write_barrier(ary, null_check_info, x->needs_null_check()); + LIR_Opr val = value.result(); + if (obj_store && UseShenandoahGC) { + if (! val->is_register()) { + assert(val->is_constant(), "expect constant"); + } else { + val = shenandoah_read_barrier(val, NULL, true); + } + } + // emit array address setup early so it schedules better ! LIR_Address* array_addr = emit_array_address(ary, index.result(), x->elt_type(), obj_store); if (GenerateRangeChecks && needs_range_check) { if (use_length) { __ cmp(lir_cond_belowEqual, length.result(), index.result()); __ branch(lir_cond_belowEqual, T_INT, new RangeCheckStub(range_check_info, index.result())); } else { ! array_range_check(ary, index.result(), null_check_info, range_check_info); // range_check also does the null check null_check_info = NULL; } }
*** 318,339 **** LIR_Opr tmp1 = new_register(objectType); LIR_Opr tmp2 = new_register(objectType); LIR_Opr tmp3 = new_register(objectType); CodeEmitInfo* store_check_info = new CodeEmitInfo(range_check_info); ! __ store_check(value.result(), array.result(), tmp1, tmp2, tmp3, store_check_info, x->profiled_method(), x->profiled_bci()); } if (obj_store) { // Needs GC write barriers. pre_barrier(LIR_OprFact::address(array_addr), LIR_OprFact::illegalOpr /* pre_val */, true /* do_load */, false /* patch */, NULL); ! __ move(value.result(), array_addr, null_check_info); // Seems to be a precise post_barrier(LIR_OprFact::address(array_addr), value.result()); } else { ! __ move(value.result(), array_addr, null_check_info); } } void LIRGenerator::do_MonitorEnter(MonitorEnter* x) { --- 329,350 ---- LIR_Opr tmp1 = new_register(objectType); LIR_Opr tmp2 = new_register(objectType); LIR_Opr tmp3 = new_register(objectType); CodeEmitInfo* store_check_info = new CodeEmitInfo(range_check_info); ! __ store_check(val, ary, tmp1, tmp2, tmp3, store_check_info, x->profiled_method(), x->profiled_bci()); } if (obj_store) { // Needs GC write barriers. pre_barrier(LIR_OprFact::address(array_addr), LIR_OprFact::illegalOpr /* pre_val */, true /* do_load */, false /* patch */, NULL); ! __ move(val, array_addr, null_check_info); // Seems to be a precise post_barrier(LIR_OprFact::address(array_addr), value.result()); } else { ! __ move(val, array_addr, null_check_info); } } void LIRGenerator::do_MonitorEnter(MonitorEnter* x) {
*** 356,366 **** info_for_exception = state_for(x); } // this CodeEmitInfo must not have the xhandlers because here the // object is already locked (xhandlers expect object to be unlocked) CodeEmitInfo* info = state_for(x, x->state(), true); ! monitor_enter(obj.result(), lock, syncTempOpr(), scratch, x->monitor_no(), info_for_exception, info); } void LIRGenerator::do_MonitorExit(MonitorExit* x) { --- 367,379 ---- info_for_exception = state_for(x); } // this CodeEmitInfo must not have the xhandlers because here the // object is already locked (xhandlers expect object to be unlocked) CodeEmitInfo* info = state_for(x, x->state(), true); ! LIR_Opr obj_opr = obj.result(); ! obj_opr = shenandoah_write_barrier(obj_opr, state_for(x), x->needs_null_check()); ! monitor_enter(obj_opr, lock, syncTempOpr(), scratch, x->monitor_no(), info_for_exception, info); } void LIRGenerator::do_MonitorExit(MonitorExit* x) {
*** 748,778 **** ShouldNotReachHere(); } LIR_Opr addr = new_pointer_register(); LIR_Address* a; if(offset.result()->is_constant()) { #ifdef _LP64 jlong c = offset.result()->as_jlong(); if ((jlong)((jint)c) == c) { ! a = new LIR_Address(obj.result(), (jint)c, as_BasicType(type)); } else { LIR_Opr tmp = new_register(T_LONG); __ move(offset.result(), tmp); ! a = new LIR_Address(obj.result(), tmp, as_BasicType(type)); } #else ! a = new LIR_Address(obj.result(), offset.result()->as_jint(), as_BasicType(type)); #endif } else { ! a = new LIR_Address(obj.result(), offset.result(), LIR_Address::times_1, 0, as_BasicType(type)); } --- 761,795 ---- ShouldNotReachHere(); } LIR_Opr addr = new_pointer_register(); LIR_Address* a; + + LIR_Opr obj_op = obj.result(); + obj_op = shenandoah_write_barrier(obj_op, NULL, false); + if(offset.result()->is_constant()) { #ifdef _LP64 jlong c = offset.result()->as_jlong(); if ((jlong)((jint)c) == c) { ! a = new LIR_Address(obj_op, (jint)c, as_BasicType(type)); } else { LIR_Opr tmp = new_register(T_LONG); __ move(offset.result(), tmp); ! a = new LIR_Address(obj_op, tmp, as_BasicType(type)); } #else ! a = new LIR_Address(obj_op, offset.result()->as_jint(), as_BasicType(type)); #endif } else { ! a = new LIR_Address(obj_op, offset.result(), LIR_Address::times_1, 0, as_BasicType(type)); }
*** 783,809 **** pre_barrier(addr, LIR_OprFact::illegalOpr /* pre_val */, true /* do_load */, false /* patch */, NULL); } LIR_Opr ill = LIR_OprFact::illegalOpr; // for convenience ! if (type == objectType) ! __ cas_obj(addr, cmp.result(), val.result(), ill, ill); else if (type == intType) ! __ cas_int(addr, cmp.result(), val.result(), ill, ill); else if (type == longType) ! __ cas_long(addr, cmp.result(), val.result(), ill, ill); else { ShouldNotReachHere(); } // generate conditional move of boolean result LIR_Opr result = rlock_result(x); __ cmove(lir_cond_equal, LIR_OprFact::intConst(1), LIR_OprFact::intConst(0), result, as_BasicType(type)); if (type == objectType) { // Write-barrier needed for Object fields. // Seems to be precise ! post_barrier(addr, val.result()); } } void LIRGenerator::do_MathIntrinsic(Intrinsic* x) { --- 800,831 ---- pre_barrier(addr, LIR_OprFact::illegalOpr /* pre_val */, true /* do_load */, false /* patch */, NULL); } LIR_Opr ill = LIR_OprFact::illegalOpr; // for convenience ! ! LIR_Opr val_op = val.result(); ! ! if (type == objectType) { ! val_op = shenandoah_read_barrier(val_op, NULL, true); ! __ cas_obj(addr, cmp.result(), val_op, new_register(T_OBJECT), new_register(T_OBJECT)); ! } else if (type == intType) ! __ cas_int(addr, cmp.result(), val_op, ill, ill); else if (type == longType) ! __ cas_long(addr, cmp.result(), val_op, ill, ill); else { ShouldNotReachHere(); } // generate conditional move of boolean result LIR_Opr result = rlock_result(x); __ cmove(lir_cond_equal, LIR_OprFact::intConst(1), LIR_OprFact::intConst(0), result, as_BasicType(type)); if (type == objectType) { // Write-barrier needed for Object fields. // Seems to be precise ! post_barrier(addr, val_op); } } void LIRGenerator::do_MathIntrinsic(Intrinsic* x) {
*** 891,908 **** LIRItem src_pos(x->argument_at(1), this); LIRItem dst(x->argument_at(2), this); LIRItem dst_pos(x->argument_at(3), this); LIRItem length(x->argument_at(4), this); // operands for arraycopy must use fixed registers, otherwise // LinearScan will fail allocation (because arraycopy always needs a // call) #ifndef _LP64 ! src.load_item_force (FrameMap::rcx_oop_opr); src_pos.load_item_force (FrameMap::rdx_opr); ! dst.load_item_force (FrameMap::rax_oop_opr); dst_pos.load_item_force (FrameMap::rbx_opr); length.load_item_force (FrameMap::rdi_opr); LIR_Opr tmp = (FrameMap::rsi_opr); #else --- 913,935 ---- LIRItem src_pos(x->argument_at(1), this); LIRItem dst(x->argument_at(2), this); LIRItem dst_pos(x->argument_at(3), this); LIRItem length(x->argument_at(4), this); + LIR_Opr dst_op = dst.result(); + dst_op = shenandoah_write_barrier(dst_op, info, x->arg_needs_null_check(2)); + LIR_Opr src_op = src.result(); + src_op = shenandoah_read_barrier(src_op, info, x->arg_needs_null_check(0)); + // operands for arraycopy must use fixed registers, otherwise // LinearScan will fail allocation (because arraycopy always needs a // call) #ifndef _LP64 ! src_op = force_opr_to(src_op, FrameMap::rcx_oop_opr); src_pos.load_item_force (FrameMap::rdx_opr); ! dst_op = force_opr_to(dst_op, FrameMap::rax_oop_opr); dst_pos.load_item_force (FrameMap::rbx_opr); length.load_item_force (FrameMap::rdi_opr); LIR_Opr tmp = (FrameMap::rsi_opr); #else
*** 912,924 **** // positions are not similar enough to pick one as the best. // Also because the java calling convention is a "shifted" version // of the C convention we can process the java args trivially into C // args without worry of overwriting during the xfer ! src.load_item_force (FrameMap::as_oop_opr(j_rarg0)); src_pos.load_item_force (FrameMap::as_opr(j_rarg1)); ! dst.load_item_force (FrameMap::as_oop_opr(j_rarg2)); dst_pos.load_item_force (FrameMap::as_opr(j_rarg3)); length.load_item_force (FrameMap::as_opr(j_rarg4)); LIR_Opr tmp = FrameMap::as_opr(j_rarg5); #endif // LP64 --- 939,951 ---- // positions are not similar enough to pick one as the best. // Also because the java calling convention is a "shifted" version // of the C convention we can process the java args trivially into C // args without worry of overwriting during the xfer ! src_op = force_opr_to(src_op, FrameMap::as_oop_opr(j_rarg0)); src_pos.load_item_force (FrameMap::as_opr(j_rarg1)); ! dst_op = force_opr_to(dst_op, FrameMap::as_oop_opr(j_rarg2)); dst_pos.load_item_force (FrameMap::as_opr(j_rarg3)); length.load_item_force (FrameMap::as_opr(j_rarg4)); LIR_Opr tmp = FrameMap::as_opr(j_rarg5); #endif // LP64
*** 927,937 **** int flags; ciArrayKlass* expected_type; arraycopy_helper(x, &flags, &expected_type); ! __ arraycopy(src.result(), src_pos.result(), dst.result(), dst_pos.result(), length.result(), tmp, expected_type, flags, info); // does add_safepoint } void LIRGenerator::do_update_CRC32(Intrinsic* x) { assert(UseCRC32Intrinsics, "need AVX and LCMUL instructions support"); // Make all state_for calls early since they can emit code --- 954,964 ---- int flags; ciArrayKlass* expected_type; arraycopy_helper(x, &flags, &expected_type); ! __ arraycopy(src_op, src_pos.result(), dst_op, dst_pos.result(), length.result(), tmp, expected_type, flags, info); // does add_safepoint } void LIRGenerator::do_update_CRC32(Intrinsic* x) { assert(UseCRC32Intrinsics, "need AVX and LCMUL instructions support"); // Make all state_for calls early since they can emit code
*** 978,987 **** --- 1005,1018 ---- __ convert(Bytecodes::_i2l, index, tmp); index = tmp; } #endif + if (is_updateBytes) { + base_op = shenandoah_read_barrier(base_op, NULL, false); + } + LIR_Address* a = new LIR_Address(base_op, index, LIR_Address::times_1, offset, T_BYTE);
*** 1310,1319 **** --- 1341,1354 ---- } set_no_result(x); LIR_Opr left = xin->result(); LIR_Opr right = yin->result(); + if (tag == objectTag && UseShenandoahGC && x->y()->type() != objectNull) { // Don't need to resolve for ifnull. + left = shenandoah_write_barrier(left, NULL, true); + right = shenandoah_read_barrier(right, NULL, true); + } __ cmp(lir_cond(cond), left, right); // Generate branch profiling. Profiling code doesn't kill flags. profile_branch(x, cond); move_to_phi(x->state()); if (x->x()->type()->is_float_kind()) {
*** 1389,1398 **** --- 1424,1434 ---- } } void LIRGenerator::get_Object_unsafe(LIR_Opr dst, LIR_Opr src, LIR_Opr offset, BasicType type, bool is_volatile) { + src = shenandoah_read_barrier(src, NULL, false); if (is_volatile && type == T_LONG) { LIR_Address* addr = new LIR_Address(src, offset, T_DOUBLE); LIR_Opr tmp = new_register(T_DOUBLE); __ load(addr, tmp); LIR_Opr spill = new_register(T_LONG);
*** 1406,1415 **** --- 1442,1452 ---- } void LIRGenerator::put_Object_unsafe(LIR_Opr src, LIR_Opr offset, LIR_Opr data, BasicType type, bool is_volatile) { + src = shenandoah_write_barrier(src, NULL, false); if (is_volatile && type == T_LONG) { LIR_Address* addr = new LIR_Address(src, offset, T_DOUBLE); LIR_Opr tmp = new_register(T_DOUBLE); LIR_Opr spill = new_register(T_DOUBLE); set_vreg_flag(spill, must_start_in_memory);
*** 1421,1430 **** --- 1458,1468 ---- bool is_obj = (type == T_ARRAY || type == T_OBJECT); if (is_obj) { // Do the pre-write barrier, if any. pre_barrier(LIR_OprFact::address(addr), LIR_OprFact::illegalOpr /* pre_val */, true /* do_load */, false /* patch */, NULL); + data = shenandoah_read_barrier(data, NULL, true); __ move(data, addr); assert(src->is_register(), "must be register"); // Seems to be a precise address post_barrier(LIR_OprFact::address(addr), data); } else {
*** 1447,1472 **** LIR_Opr data = value.result(); bool is_obj = (type == T_ARRAY || type == T_OBJECT); LIR_Opr offset = off.result(); assert (type == T_INT || (!x->is_add() && is_obj) LP64_ONLY( || type == T_LONG ), "unexpected type"); LIR_Address* addr; if (offset->is_constant()) { #ifdef _LP64 jlong c = offset->as_jlong(); if ((jlong)((jint)c) == c) { ! addr = new LIR_Address(src.result(), (jint)c, type); } else { LIR_Opr tmp = new_register(T_LONG); __ move(offset, tmp); ! addr = new LIR_Address(src.result(), tmp, type); } #else ! addr = new LIR_Address(src.result(), offset->as_jint(), type); #endif } else { ! addr = new LIR_Address(src.result(), offset, type); } // Because we want a 2-arg form of xchg and xadd __ move(data, dst); --- 1485,1517 ---- LIR_Opr data = value.result(); bool is_obj = (type == T_ARRAY || type == T_OBJECT); LIR_Opr offset = off.result(); assert (type == T_INT || (!x->is_add() && is_obj) LP64_ONLY( || type == T_LONG ), "unexpected type"); + + LIR_Opr src_op = src.result(); + src_op = shenandoah_write_barrier(src_op, NULL, false); + if (is_obj) { + data = shenandoah_read_barrier(data, NULL, true); + } + LIR_Address* addr; if (offset->is_constant()) { #ifdef _LP64 jlong c = offset->as_jlong(); if ((jlong)((jint)c) == c) { ! addr = new LIR_Address(src_op, (jint)c, type); } else { LIR_Opr tmp = new_register(T_LONG); __ move(offset, tmp); ! addr = new LIR_Address(src_op, tmp, type); } #else ! addr = new LIR_Address(src_op, offset->as_jint(), type); #endif } else { ! addr = new LIR_Address(src_op, offset, type); } // Because we want a 2-arg form of xchg and xadd __ move(data, dst);
< prev index next >