G1BarrierSet_merge
615 __ blrt(rscratch1, 3, 0, 1);
616
617 return start;
618 }
619
620 void array_overlap_test(Label& L_no_overlap, Address::sxtw sf) { __ b(L_no_overlap); }
621
622 // Generate code for an array write pre barrier
623 //
624 // addr - starting address
625 // count - element count
626 // tmp - scratch register
627 // saved_regs - registers to be saved before calling static_write_ref_array_pre
628 //
629 // Callers must specify which registers to preserve in saved_regs.
630 // Clobbers: r0-r18, v0-v7, v16-v31, except saved_regs.
631 //
632 void gen_write_ref_array_pre_barrier(Register addr, Register count, bool dest_uninitialized, RegSet saved_regs) {
633 BarrierSet* bs = Universe::heap()->barrier_set();
634 switch (bs->kind()) {
635 case BarrierSet::G1SATBCTLogging:
636 // With G1, don't generate the call if we statically know that the target in uninitialized
637 if (!dest_uninitialized) {
638 __ push(saved_regs, sp);
639 if (count == c_rarg0) {
640 if (addr == c_rarg1) {
641 // exactly backwards!!
642 __ mov(rscratch1, c_rarg0);
643 __ mov(c_rarg0, c_rarg1);
644 __ mov(c_rarg1, rscratch1);
645 } else {
646 __ mov(c_rarg1, count);
647 __ mov(c_rarg0, addr);
648 }
649 } else {
650 __ mov(c_rarg0, addr);
651 __ mov(c_rarg1, count);
652 }
653 __ call_VM_leaf(CAST_FROM_FN_PTR(address, BarrierSet::static_write_ref_array_pre), 2);
654 __ pop(saved_regs, sp);
|
615 __ blrt(rscratch1, 3, 0, 1);
616
617 return start;
618 }
619
620 void array_overlap_test(Label& L_no_overlap, Address::sxtw sf) { __ b(L_no_overlap); }
621
622 // Generate code for an array write pre barrier
623 //
624 // addr - starting address
625 // count - element count
626 // tmp - scratch register
627 // saved_regs - registers to be saved before calling static_write_ref_array_pre
628 //
629 // Callers must specify which registers to preserve in saved_regs.
630 // Clobbers: r0-r18, v0-v7, v16-v31, except saved_regs.
631 //
632 void gen_write_ref_array_pre_barrier(Register addr, Register count, bool dest_uninitialized, RegSet saved_regs) {
633 BarrierSet* bs = Universe::heap()->barrier_set();
634 switch (bs->kind()) {
635 case BarrierSet::G1BarrierSet:
636 // With G1, don't generate the call if we statically know that the target in uninitialized
637 if (!dest_uninitialized) {
638 __ push(saved_regs, sp);
639 if (count == c_rarg0) {
640 if (addr == c_rarg1) {
641 // exactly backwards!!
642 __ mov(rscratch1, c_rarg0);
643 __ mov(c_rarg0, c_rarg1);
644 __ mov(c_rarg1, rscratch1);
645 } else {
646 __ mov(c_rarg1, count);
647 __ mov(c_rarg0, addr);
648 }
649 } else {
650 __ mov(c_rarg0, addr);
651 __ mov(c_rarg1, count);
652 }
653 __ call_VM_leaf(CAST_FROM_FN_PTR(address, BarrierSet::static_write_ref_array_pre), 2);
654 __ pop(saved_regs, sp);
|
662 }
663 }
664
665 //
666 // Generate code for an array write post barrier
667 //
668 // Input:
669 // start - register containing starting address of destination array
670 // end - register containing ending address of destination array
671 // scratch - scratch register
672 // saved_regs - registers to be saved before calling static_write_ref_array_post
673 //
674 // The input registers are overwritten.
675 // The ending address is inclusive.
676 // Callers must specify which registers to preserve in saved_regs.
677 // Clobbers: r0-r18, v0-v7, v16-v31, except saved_regs.
678 void gen_write_ref_array_post_barrier(Register start, Register end, Register scratch, RegSet saved_regs) {
679 assert_different_registers(start, end, scratch);
680 BarrierSet* bs = Universe::heap()->barrier_set();
681 switch (bs->kind()) {
682 case BarrierSet::G1SATBCTLogging:
683
684 {
685 __ push(saved_regs, sp);
686 // must compute element count unless barrier set interface is changed (other platforms supply count)
687 assert_different_registers(start, end, scratch);
688 __ lea(scratch, Address(end, BytesPerHeapOop));
689 __ sub(scratch, scratch, start); // subtract start to get #bytes
690 __ lsr(scratch, scratch, LogBytesPerHeapOop); // convert to element count
691 __ mov(c_rarg0, start);
692 __ mov(c_rarg1, scratch);
693 __ call_VM_leaf(CAST_FROM_FN_PTR(address, BarrierSet::static_write_ref_array_post), 2);
694 __ pop(saved_regs, sp);
695 }
696 break;
697 case BarrierSet::CardTableModRef:
698 {
699 CardTableModRefBS* ctbs = barrier_set_cast<CardTableModRefBS>(bs);
700 CardTable* ct = ctbs->card_table();
701 assert(sizeof(*ct->byte_map_base()) == sizeof(jbyte), "adjust this code");
|
662 }
663 }
664
665 //
666 // Generate code for an array write post barrier
667 //
668 // Input:
669 // start - register containing starting address of destination array
670 // end - register containing ending address of destination array
671 // scratch - scratch register
672 // saved_regs - registers to be saved before calling static_write_ref_array_post
673 //
674 // The input registers are overwritten.
675 // The ending address is inclusive.
676 // Callers must specify which registers to preserve in saved_regs.
677 // Clobbers: r0-r18, v0-v7, v16-v31, except saved_regs.
678 void gen_write_ref_array_post_barrier(Register start, Register end, Register scratch, RegSet saved_regs) {
679 assert_different_registers(start, end, scratch);
680 BarrierSet* bs = Universe::heap()->barrier_set();
681 switch (bs->kind()) {
682 case BarrierSet::G1BarrierSet:
683
684 {
685 __ push(saved_regs, sp);
686 // must compute element count unless barrier set interface is changed (other platforms supply count)
687 assert_different_registers(start, end, scratch);
688 __ lea(scratch, Address(end, BytesPerHeapOop));
689 __ sub(scratch, scratch, start); // subtract start to get #bytes
690 __ lsr(scratch, scratch, LogBytesPerHeapOop); // convert to element count
691 __ mov(c_rarg0, start);
692 __ mov(c_rarg1, scratch);
693 __ call_VM_leaf(CAST_FROM_FN_PTR(address, BarrierSet::static_write_ref_array_post), 2);
694 __ pop(saved_regs, sp);
695 }
696 break;
697 case BarrierSet::CardTableModRef:
698 {
699 CardTableModRefBS* ctbs = barrier_set_cast<CardTableModRefBS>(bs);
700 CardTable* ct = ctbs->card_table();
701 assert(sizeof(*ct->byte_map_base()) == sizeof(jbyte), "adjust this code");
|