572 #ifndef PRODUCT |
572 #ifndef PRODUCT |
573 virtual void print_name(outputStream* out) const { out->print("G1PreBarrierStub"); } |
573 virtual void print_name(outputStream* out) const { out->print("G1PreBarrierStub"); } |
574 #endif // PRODUCT |
574 #endif // PRODUCT |
575 }; |
575 }; |
576 |
576 |
577 // This G1 barrier code stub is used in Unsafe.getObject. |
|
578 // It generates a sequence of guards around the SATB |
|
579 // barrier code that are used to detect when we have |
|
580 // the referent field of a Reference object. |
|
581 // The first check is assumed to have been generated |
|
582 // in the code generated for Unsafe.getObject(). |
|
583 |
|
584 class G1UnsafeGetObjSATBBarrierStub: public CodeStub { |
|
585 private: |
|
586 LIR_Opr _val; |
|
587 LIR_Opr _src; |
|
588 |
|
589 LIR_Opr _tmp; |
|
590 LIR_Opr _thread; |
|
591 |
|
592 bool _gen_src_check; |
|
593 |
|
594 public: |
|
595 // A G1 barrier that is guarded by generated guards that determine whether |
|
596 // val (which is the result of Unsafe.getObject() should be recorded in an |
|
597 // SATB log buffer. We could be reading the referent field of a Reference object |
|
598 // using Unsafe.getObject() and we need to record the referent. |
|
599 // |
|
600 // * val is the operand returned by the unsafe.getObject routine. |
|
601 // * src is the base object |
|
602 // * tmp is a temp used to load the klass of src, and then reference type |
|
603 // * thread is the thread object. |
|
604 |
|
605 G1UnsafeGetObjSATBBarrierStub(LIR_Opr val, LIR_Opr src, |
|
606 LIR_Opr tmp, LIR_Opr thread, |
|
607 bool gen_src_check) : |
|
608 _val(val), _src(src), |
|
609 _tmp(tmp), _thread(thread), |
|
610 _gen_src_check(gen_src_check) |
|
611 { |
|
612 assert(_val->is_register(), "should have already been loaded"); |
|
613 assert(_src->is_register(), "should have already been loaded"); |
|
614 |
|
615 assert(_tmp->is_register(), "should be a temporary register"); |
|
616 } |
|
617 |
|
618 LIR_Opr val() const { return _val; } |
|
619 LIR_Opr src() const { return _src; } |
|
620 |
|
621 LIR_Opr tmp() const { return _tmp; } |
|
622 LIR_Opr thread() const { return _thread; } |
|
623 |
|
624 bool gen_src_check() const { return _gen_src_check; } |
|
625 |
|
626 virtual void emit_code(LIR_Assembler* e); |
|
627 |
|
628 virtual void visit(LIR_OpVisitState* visitor) { |
|
629 visitor->do_slow_case(); |
|
630 visitor->do_input(_val); |
|
631 visitor->do_input(_src); |
|
632 visitor->do_input(_thread); |
|
633 |
|
634 visitor->do_temp(_tmp); |
|
635 } |
|
636 |
|
637 #ifndef PRODUCT |
|
638 virtual void print_name(outputStream* out) const { out->print("G1UnsafeGetObjSATBBarrierStub"); } |
|
639 #endif // PRODUCT |
|
640 }; |
|
641 |
|
642 class G1PostBarrierStub: public CodeStub { |
577 class G1PostBarrierStub: public CodeStub { |
643 private: |
578 private: |
644 LIR_Opr _addr; |
579 LIR_Opr _addr; |
645 LIR_Opr _new_val; |
580 LIR_Opr _new_val; |
646 |
581 |