17 *
18 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
19 * or visit www.oracle.com if you need additional information or have any
20 * questions.
21 *
22 */
23
24 #include "precompiled.hpp"
25 #include "c1/c1_Compilation.hpp"
26 #include "c1/c1_Defs.hpp"
27 #include "c1/c1_FrameMap.hpp"
28 #include "c1/c1_Instruction.hpp"
29 #include "c1/c1_LIRAssembler.hpp"
30 #include "c1/c1_LIRGenerator.hpp"
31 #include "c1/c1_ValueStack.hpp"
32 #include "ci/ciArrayKlass.hpp"
33 #include "ci/ciInstance.hpp"
34 #include "ci/ciObjArray.hpp"
35 #include "ci/ciUtilities.hpp"
36 #include "gc/shared/cardTable.hpp"
37 #include "gc/shared/cardTableModRefBS.hpp"
38 #include "runtime/arguments.hpp"
39 #include "runtime/sharedRuntime.hpp"
40 #include "runtime/stubRoutines.hpp"
41 #include "runtime/vm_version.hpp"
42 #include "utilities/bitMap.inline.hpp"
43 #include "utilities/macros.hpp"
44 #if INCLUDE_ALL_GCS
45 #include "gc/g1/heapRegion.hpp"
46 #endif // INCLUDE_ALL_GCS
47 #ifdef TRACE_HAVE_INTRINSICS
48 #include "trace/traceMacros.hpp"
49 #endif
50
51 #ifdef ASSERT
52 #define __ gen()->lir(__FILE__, __LINE__)->
53 #else
54 #define __ gen()->lir()->
55 #endif
56
|
17 *
18 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
19 * or visit www.oracle.com if you need additional information or have any
20 * questions.
21 *
22 */
23
24 #include "precompiled.hpp"
25 #include "c1/c1_Compilation.hpp"
26 #include "c1/c1_Defs.hpp"
27 #include "c1/c1_FrameMap.hpp"
28 #include "c1/c1_Instruction.hpp"
29 #include "c1/c1_LIRAssembler.hpp"
30 #include "c1/c1_LIRGenerator.hpp"
31 #include "c1/c1_ValueStack.hpp"
32 #include "ci/ciArrayKlass.hpp"
33 #include "ci/ciInstance.hpp"
34 #include "ci/ciObjArray.hpp"
35 #include "ci/ciUtilities.hpp"
36 #include "gc/shared/cardTable.hpp"
37 #include "gc/shared/cardTableBarrierSet.hpp"
38 #include "runtime/arguments.hpp"
39 #include "runtime/sharedRuntime.hpp"
40 #include "runtime/stubRoutines.hpp"
41 #include "runtime/vm_version.hpp"
42 #include "utilities/bitMap.inline.hpp"
43 #include "utilities/macros.hpp"
44 #if INCLUDE_ALL_GCS
45 #include "gc/g1/heapRegion.hpp"
46 #endif // INCLUDE_ALL_GCS
47 #ifdef TRACE_HAVE_INTRINSICS
48 #include "trace/traceMacros.hpp"
49 #endif
50
51 #ifdef ASSERT
52 #define __ gen()->lir(__FILE__, __LINE__)->
53 #else
54 #define __ gen()->lir()->
55 #endif
56
|
1442 }
1443 return _reg_for_constants.at(i);
1444 }
1445 }
1446
1447 LIR_Opr result = new_register(t);
1448 __ move((LIR_Opr)c, result);
1449 _constants.append(c);
1450 _reg_for_constants.append(result);
1451 return result;
1452 }
1453
1454 // Various barriers
1455
1456 void LIRGenerator::pre_barrier(LIR_Opr addr_opr, LIR_Opr pre_val,
1457 bool do_load, bool patch, CodeEmitInfo* info) {
1458 // Do the pre-write barrier, if any.
1459 switch (_bs->kind()) {
1460 #if INCLUDE_ALL_GCS
1461 case BarrierSet::G1BarrierSet:
1462 G1SATBCardTableModRef_pre_barrier(addr_opr, pre_val, do_load, patch, info);
1463 break;
1464 #endif // INCLUDE_ALL_GCS
1465 case BarrierSet::CardTableModRef:
1466 // No pre barriers
1467 break;
1468 default :
1469 ShouldNotReachHere();
1470
1471 }
1472 }
1473
1474 void LIRGenerator::post_barrier(LIR_OprDesc* addr, LIR_OprDesc* new_val) {
1475 switch (_bs->kind()) {
1476 #if INCLUDE_ALL_GCS
1477 case BarrierSet::G1BarrierSet:
1478 G1SATBCardTableModRef_post_barrier(addr, new_val);
1479 break;
1480 #endif // INCLUDE_ALL_GCS
1481 case BarrierSet::CardTableModRef:
1482 CardTableModRef_post_barrier(addr, new_val);
1483 break;
1484 default :
1485 ShouldNotReachHere();
1486 }
1487 }
1488
1489 ////////////////////////////////////////////////////////////////////////
1490 #if INCLUDE_ALL_GCS
1491
1492 void LIRGenerator::G1SATBCardTableModRef_pre_barrier(LIR_Opr addr_opr, LIR_Opr pre_val,
1493 bool do_load, bool patch, CodeEmitInfo* info) {
1494 // First we test whether marking is in progress.
1495 BasicType flag_type;
1496 if (in_bytes(SATBMarkQueue::byte_width_of_active()) == 4) {
1497 flag_type = T_INT;
1498 } else {
1499 guarantee(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1,
1500 "Assumption");
1501 // Use unsigned type T_BOOLEAN here rather than signed T_BYTE since some platforms, eg. ARM,
1502 // need to use unsigned instructions to use the large offset to load the satb_mark_queue.
1503 flag_type = T_BOOLEAN;
1504 }
1505 LIR_Opr thrd = getThreadPointer();
1506 LIR_Address* mark_active_flag_addr =
1507 new LIR_Address(thrd,
1508 in_bytes(JavaThread::satb_mark_queue_offset() +
1509 SATBMarkQueue::byte_offset_of_active()),
1510 flag_type);
1511 // Read the marking-in-progress flag.
1512 LIR_Opr flag_val = new_register(T_INT);
|
1442 }
1443 return _reg_for_constants.at(i);
1444 }
1445 }
1446
1447 LIR_Opr result = new_register(t);
1448 __ move((LIR_Opr)c, result);
1449 _constants.append(c);
1450 _reg_for_constants.append(result);
1451 return result;
1452 }
1453
1454 // Various barriers
1455
1456 void LIRGenerator::pre_barrier(LIR_Opr addr_opr, LIR_Opr pre_val,
1457 bool do_load, bool patch, CodeEmitInfo* info) {
1458 // Do the pre-write barrier, if any.
1459 switch (_bs->kind()) {
1460 #if INCLUDE_ALL_GCS
1461 case BarrierSet::G1BarrierSet:
1462 G1BarrierSet_pre_barrier(addr_opr, pre_val, do_load, patch, info);
1463 break;
1464 #endif // INCLUDE_ALL_GCS
1465 case BarrierSet::CardTableBarrierSet:
1466 // No pre barriers
1467 break;
1468 default :
1469 ShouldNotReachHere();
1470
1471 }
1472 }
1473
1474 void LIRGenerator::post_barrier(LIR_OprDesc* addr, LIR_OprDesc* new_val) {
1475 switch (_bs->kind()) {
1476 #if INCLUDE_ALL_GCS
1477 case BarrierSet::G1BarrierSet:
1478 G1BarrierSet_post_barrier(addr, new_val);
1479 break;
1480 #endif // INCLUDE_ALL_GCS
1481 case BarrierSet::CardTableBarrierSet:
1482 CardTableBarrierSet_post_barrier(addr, new_val);
1483 break;
1484 default :
1485 ShouldNotReachHere();
1486 }
1487 }
1488
1489 ////////////////////////////////////////////////////////////////////////
1490 #if INCLUDE_ALL_GCS
1491
1492 void LIRGenerator::G1BarrierSet_pre_barrier(LIR_Opr addr_opr, LIR_Opr pre_val,
1493 bool do_load, bool patch, CodeEmitInfo* info) {
1494 // First we test whether marking is in progress.
1495 BasicType flag_type;
1496 if (in_bytes(SATBMarkQueue::byte_width_of_active()) == 4) {
1497 flag_type = T_INT;
1498 } else {
1499 guarantee(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1,
1500 "Assumption");
1501 // Use unsigned type T_BOOLEAN here rather than signed T_BYTE since some platforms, eg. ARM,
1502 // need to use unsigned instructions to use the large offset to load the satb_mark_queue.
1503 flag_type = T_BOOLEAN;
1504 }
1505 LIR_Opr thrd = getThreadPointer();
1506 LIR_Address* mark_active_flag_addr =
1507 new LIR_Address(thrd,
1508 in_bytes(JavaThread::satb_mark_queue_offset() +
1509 SATBMarkQueue::byte_offset_of_active()),
1510 flag_type);
1511 // Read the marking-in-progress flag.
1512 LIR_Opr flag_val = new_register(T_INT);
|
1527 pre_val = new_register(T_OBJECT);
1528
1529 if (!addr_opr->is_address()) {
1530 assert(addr_opr->is_register(), "must be");
1531 addr_opr = LIR_OprFact::address(new LIR_Address(addr_opr, T_OBJECT));
1532 }
1533 slow = new G1PreBarrierStub(addr_opr, pre_val, pre_val_patch_code, info);
1534 } else {
1535 assert(addr_opr == LIR_OprFact::illegalOpr, "sanity");
1536 assert(pre_val->is_register(), "must be");
1537 assert(pre_val->type() == T_OBJECT, "must be an object");
1538 assert(info == NULL, "sanity");
1539
1540 slow = new G1PreBarrierStub(pre_val);
1541 }
1542
1543 __ branch(lir_cond_notEqual, T_INT, slow);
1544 __ branch_destination(slow->continuation());
1545 }
1546
1547 void LIRGenerator::G1SATBCardTableModRef_post_barrier(LIR_OprDesc* addr, LIR_OprDesc* new_val) {
1548 // If the "new_val" is a constant NULL, no barrier is necessary.
1549 if (new_val->is_constant() &&
1550 new_val->as_constant_ptr()->as_jobject() == NULL) return;
1551
1552 if (!new_val->is_register()) {
1553 LIR_Opr new_val_reg = new_register(T_OBJECT);
1554 if (new_val->is_constant()) {
1555 __ move(new_val, new_val_reg);
1556 } else {
1557 __ leal(new_val, new_val_reg);
1558 }
1559 new_val = new_val_reg;
1560 }
1561 assert(new_val->is_register(), "must be a register at this point");
1562
1563 if (addr->is_address()) {
1564 LIR_Address* address = addr->as_address_ptr();
1565 LIR_Opr ptr = new_pointer_register();
1566 if (!address->index()->is_valid() && address->disp() == 0) {
|
1527 pre_val = new_register(T_OBJECT);
1528
1529 if (!addr_opr->is_address()) {
1530 assert(addr_opr->is_register(), "must be");
1531 addr_opr = LIR_OprFact::address(new LIR_Address(addr_opr, T_OBJECT));
1532 }
1533 slow = new G1PreBarrierStub(addr_opr, pre_val, pre_val_patch_code, info);
1534 } else {
1535 assert(addr_opr == LIR_OprFact::illegalOpr, "sanity");
1536 assert(pre_val->is_register(), "must be");
1537 assert(pre_val->type() == T_OBJECT, "must be an object");
1538 assert(info == NULL, "sanity");
1539
1540 slow = new G1PreBarrierStub(pre_val);
1541 }
1542
1543 __ branch(lir_cond_notEqual, T_INT, slow);
1544 __ branch_destination(slow->continuation());
1545 }
1546
1547 void LIRGenerator::G1BarrierSet_post_barrier(LIR_OprDesc* addr, LIR_OprDesc* new_val) {
1548 // If the "new_val" is a constant NULL, no barrier is necessary.
1549 if (new_val->is_constant() &&
1550 new_val->as_constant_ptr()->as_jobject() == NULL) return;
1551
1552 if (!new_val->is_register()) {
1553 LIR_Opr new_val_reg = new_register(T_OBJECT);
1554 if (new_val->is_constant()) {
1555 __ move(new_val, new_val_reg);
1556 } else {
1557 __ leal(new_val, new_val_reg);
1558 }
1559 new_val = new_val_reg;
1560 }
1561 assert(new_val->is_register(), "must be a register at this point");
1562
1563 if (addr->is_address()) {
1564 LIR_Address* address = addr->as_address_ptr();
1565 LIR_Opr ptr = new_pointer_register();
1566 if (!address->index()->is_valid() && address->disp() == 0) {
|
1591 LIR_OprDesc::illegalOpr());
1592 }
1593
1594 if (!new_val->is_register()) {
1595 LIR_Opr new_val_reg = new_register(T_OBJECT);
1596 __ leal(new_val, new_val_reg);
1597 new_val = new_val_reg;
1598 }
1599 assert(new_val->is_register(), "must be a register at this point");
1600
1601 __ cmp(lir_cond_notEqual, xor_shift_res, LIR_OprFact::intptrConst(NULL_WORD));
1602
1603 CodeStub* slow = new G1PostBarrierStub(addr, new_val);
1604 __ branch(lir_cond_notEqual, LP64_ONLY(T_LONG) NOT_LP64(T_INT), slow);
1605 __ branch_destination(slow->continuation());
1606 }
1607
1608 #endif // INCLUDE_ALL_GCS
1609 ////////////////////////////////////////////////////////////////////////
1610
1611 void LIRGenerator::CardTableModRef_post_barrier(LIR_OprDesc* addr, LIR_OprDesc* new_val) {
1612 LIR_Const* card_table_base = new LIR_Const(ci_card_table_address());
1613 if (addr->is_address()) {
1614 LIR_Address* address = addr->as_address_ptr();
1615 // ptr cannot be an object because we use this barrier for array card marks
1616 // and addr can point in the middle of an array.
1617 LIR_Opr ptr = new_pointer_register();
1618 if (!address->index()->is_valid() && address->disp() == 0) {
1619 __ move(address->base(), ptr);
1620 } else {
1621 assert(address->disp() != max_jint, "lea doesn't support patched addresses!");
1622 __ leal(addr, ptr);
1623 }
1624 addr = ptr;
1625 }
1626 assert(addr->is_register(), "must be a register at this point");
1627
1628 #ifdef CARDTABLEMODREF_POST_BARRIER_HELPER
1629 CardTableModRef_post_barrier_helper(addr, card_table_base);
1630 #else
1631 LIR_Opr tmp = new_pointer_register();
1632 if (TwoOperandLIRForm) {
1633 __ move(addr, tmp);
1634 __ unsigned_shift_right(tmp, CardTable::card_shift, tmp);
1635 } else {
1636 __ unsigned_shift_right(addr, CardTable::card_shift, tmp);
1637 }
1638
1639 LIR_Address* card_addr;
1640 if (can_inline_as_constant(card_table_base)) {
1641 card_addr = new LIR_Address(tmp, card_table_base->as_jint(), T_BYTE);
1642 } else {
1643 card_addr = new LIR_Address(tmp, load_constant(card_table_base), T_BYTE);
1644 }
1645
1646 LIR_Opr dirty = LIR_OprFact::intConst(CardTable::dirty_card_val());
1647 if (UseCondCardMark) {
1648 LIR_Opr cur_value = new_register(T_INT);
|
1591 LIR_OprDesc::illegalOpr());
1592 }
1593
1594 if (!new_val->is_register()) {
1595 LIR_Opr new_val_reg = new_register(T_OBJECT);
1596 __ leal(new_val, new_val_reg);
1597 new_val = new_val_reg;
1598 }
1599 assert(new_val->is_register(), "must be a register at this point");
1600
1601 __ cmp(lir_cond_notEqual, xor_shift_res, LIR_OprFact::intptrConst(NULL_WORD));
1602
1603 CodeStub* slow = new G1PostBarrierStub(addr, new_val);
1604 __ branch(lir_cond_notEqual, LP64_ONLY(T_LONG) NOT_LP64(T_INT), slow);
1605 __ branch_destination(slow->continuation());
1606 }
1607
1608 #endif // INCLUDE_ALL_GCS
1609 ////////////////////////////////////////////////////////////////////////
1610
1611 void LIRGenerator::CardTableBarrierSet_post_barrier(LIR_OprDesc* addr, LIR_OprDesc* new_val) {
1612 LIR_Const* card_table_base = new LIR_Const(ci_card_table_address());
1613 if (addr->is_address()) {
1614 LIR_Address* address = addr->as_address_ptr();
1615 // ptr cannot be an object because we use this barrier for array card marks
1616 // and addr can point in the middle of an array.
1617 LIR_Opr ptr = new_pointer_register();
1618 if (!address->index()->is_valid() && address->disp() == 0) {
1619 __ move(address->base(), ptr);
1620 } else {
1621 assert(address->disp() != max_jint, "lea doesn't support patched addresses!");
1622 __ leal(addr, ptr);
1623 }
1624 addr = ptr;
1625 }
1626 assert(addr->is_register(), "must be a register at this point");
1627
1628 #ifdef CARDTABLEBARRIERSET_POST_BARRIER_HELPER
1629 CardTableBarrierSet_post_barrier_helper(addr, card_table_base);
1630 #else
1631 LIR_Opr tmp = new_pointer_register();
1632 if (TwoOperandLIRForm) {
1633 __ move(addr, tmp);
1634 __ unsigned_shift_right(tmp, CardTable::card_shift, tmp);
1635 } else {
1636 __ unsigned_shift_right(addr, CardTable::card_shift, tmp);
1637 }
1638
1639 LIR_Address* card_addr;
1640 if (can_inline_as_constant(card_table_base)) {
1641 card_addr = new LIR_Address(tmp, card_table_base->as_jint(), T_BYTE);
1642 } else {
1643 card_addr = new LIR_Address(tmp, load_constant(card_table_base), T_BYTE);
1644 }
1645
1646 LIR_Opr dirty = LIR_OprFact::intConst(CardTable::dirty_card_val());
1647 if (UseCondCardMark) {
1648 LIR_Opr cur_value = new_register(T_INT);
|