895 }
896 }
897
898 ShenandoahBarrierStubC2* ShenandoahBarrierStubC2::create(const MachNode* node, Register obj, Address addr, Register tmp1, Register tmp2, bool narrow, bool do_load) {
899 auto* stub = new (Compile::current()->comp_arena()) ShenandoahBarrierStubC2(node, obj, addr, tmp1, tmp2, narrow, do_load);
900 register_stub(stub);
901 return stub;
902 }
903
904 void ShenandoahBarrierStubC2::load_post(MacroAssembler* masm, const MachNode* node, Register obj, Address addr, Register tmp1, Register tmp2, bool narrow) {
905 // Load post-barrier:
906 // a. Satisfies the need for LRB for normal loads
907 // b. Passes a weak load through LRB-weak
908 // c. Keep-alives a weak load
909 if (needs_slow_barrier(node)) {
910 ShenandoahBarrierStubC2* const stub = create(node, obj, addr, tmp1, tmp2, narrow, /* do_load = */ false);
911 char check = 0;
912 check |= needs_keep_alive_barrier(node) ? ShenandoahHeap::MARKING : 0;
913 check |= needs_load_ref_barrier(node) ? ShenandoahHeap::HAS_FORWARDED : 0;
914 check |= needs_load_ref_barrier_weak(node) ? ShenandoahHeap::WEAK_ROOTS : 0;
915 stub->enter_if_gc_state(*masm, check, tmp1);
916 }
917 }
918
919 void ShenandoahBarrierStubC2::store_pre(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2, Register tmp3, bool narrow) {
920 // Store pre-barrier: SATB, keep-alive the current memory value.
921 if (needs_slow_barrier(node)) {
922 assert(!needs_load_ref_barrier(node), "Should not be required for stores");
923 ShenandoahBarrierStubC2* const stub = create(node, tmp1, addr, tmp2, tmp3, narrow, /* do_load = */ true);
924 stub->enter_if_gc_state(*masm, ShenandoahHeap::MARKING, tmp1);
925 }
926 }
927
928 void ShenandoahBarrierStubC2::load_store_pre(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2, Register tmp3, bool narrow) {
929 // Load/Store pre-barrier:
930 // a. Avoids false positives from CAS encountering to-space memory values.
931 // b. Satisfies the need for LRB for the CAE result.
932 // c. Records old value for the sake of SATB.
933 //
934 // (a) and (b) are covered because load barrier does memory location fixup.
935 // (c) is covered by KA on the current memory value.
936 if (needs_slow_barrier(node)) {
937 ShenandoahBarrierStubC2* const stub = create(node, tmp1, addr, tmp2, tmp3, narrow, /* do_load = */ true);
938 char check = 0;
939 check |= needs_keep_alive_barrier(node) ? ShenandoahHeap::MARKING : 0;
940 check |= needs_load_ref_barrier(node) ? ShenandoahHeap::HAS_FORWARDED : 0;
941 assert(!needs_load_ref_barrier_weak(node), "Not supported for Load/Stores");
942 stub->enter_if_gc_state(*masm, check, tmp1);
943 }
944 }
945
946 void ShenandoahBarrierStubC2::store_post(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2) {
947 if (needs_card_barrier(node)) {
948 cardtable(*masm, addr, tmp1, tmp2);
949 }
950 }
951
952 void ShenandoahBarrierStubC2::load_store_post(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2) {
953 store_post(masm, node, addr, tmp1, tmp2);
954 }
955
956 bool ShenandoahBarrierStubC2::is_live_register(Register reg) {
957 return preserve_set().member(OptoReg::as_OptoReg(reg->as_VMReg()));
958 }
959
960 Register ShenandoahBarrierStubC2::select_temp_register(bool& selected_live, Register skip_reg1, Register skip_reg2) {
961 Register tmp = noreg;
962 Register fallback_live = noreg;
|
895 }
896 }
897
898 ShenandoahBarrierStubC2* ShenandoahBarrierStubC2::create(const MachNode* node, Register obj, Address addr, Register tmp1, Register tmp2, bool narrow, bool do_load) {
899 auto* stub = new (Compile::current()->comp_arena()) ShenandoahBarrierStubC2(node, obj, addr, tmp1, tmp2, narrow, do_load);
900 register_stub(stub);
901 return stub;
902 }
903
904 void ShenandoahBarrierStubC2::load_post(MacroAssembler* masm, const MachNode* node, Register obj, Address addr, Register tmp1, Register tmp2, bool narrow) {
905 // Load post-barrier:
906 // a. Satisfies the need for LRB for normal loads
907 // b. Passes a weak load through LRB-weak
908 // c. Keep-alives a weak load
909 if (needs_slow_barrier(node)) {
910 ShenandoahBarrierStubC2* const stub = create(node, obj, addr, tmp1, tmp2, narrow, /* do_load = */ false);
911 char check = 0;
912 check |= needs_keep_alive_barrier(node) ? ShenandoahHeap::MARKING : 0;
913 check |= needs_load_ref_barrier(node) ? ShenandoahHeap::HAS_FORWARDED : 0;
914 check |= needs_load_ref_barrier_weak(node) ? ShenandoahHeap::WEAK_ROOTS : 0;
915 stub->enter_if_gc_state(*masm, check, tmp1, tmp2);
916 }
917 }
918
919 void ShenandoahBarrierStubC2::store_pre(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2, Register tmp3, bool narrow) {
920 // Store pre-barrier: SATB, keep-alive the current memory value.
921 if (needs_slow_barrier(node)) {
922 assert(!needs_load_ref_barrier(node), "Should not be required for stores");
923 ShenandoahBarrierStubC2* const stub = create(node, tmp1, addr, tmp2, tmp3, narrow, /* do_load = */ true);
924 stub->enter_if_gc_state(*masm, ShenandoahHeap::MARKING, tmp1, tmp2);
925 }
926 }
927
928 void ShenandoahBarrierStubC2::load_store_pre(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2, Register tmp3, bool narrow) {
929 // Load/Store pre-barrier:
930 // a. Avoids false positives from CAS encountering to-space memory values.
931 // b. Satisfies the need for LRB for the CAE result.
932 // c. Records old value for the sake of SATB.
933 //
934 // (a) and (b) are covered because load barrier does memory location fixup.
935 // (c) is covered by KA on the current memory value.
936 if (needs_slow_barrier(node)) {
937 ShenandoahBarrierStubC2* const stub = create(node, tmp1, addr, tmp2, tmp3, narrow, /* do_load = */ true);
938 char check = 0;
939 check |= needs_keep_alive_barrier(node) ? ShenandoahHeap::MARKING : 0;
940 check |= needs_load_ref_barrier(node) ? ShenandoahHeap::HAS_FORWARDED : 0;
941 assert(!needs_load_ref_barrier_weak(node), "Not supported for Load/Stores");
942 stub->enter_if_gc_state(*masm, check, tmp1, tmp2);
943 }
944 }
945
946 void ShenandoahBarrierStubC2::store_post(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2) {
947 if (needs_card_barrier(node)) {
948 cardtable(*masm, addr, tmp1, tmp2);
949 }
950 }
951
952 void ShenandoahBarrierStubC2::load_store_post(MacroAssembler* masm, const MachNode* node, Address addr, Register tmp1, Register tmp2) {
953 store_post(masm, node, addr, tmp1, tmp2);
954 }
955
956 bool ShenandoahBarrierStubC2::is_live_register(Register reg) {
957 return preserve_set().member(OptoReg::as_OptoReg(reg->as_VMReg()));
958 }
959
960 Register ShenandoahBarrierStubC2::select_temp_register(bool& selected_live, Register skip_reg1, Register skip_reg2) {
961 Register tmp = noreg;
962 Register fallback_live = noreg;
|