< prev index next >

src/hotspot/cpu/riscv/gc/g1/g1_riscv.ad

Print this page

  1 //
  2 // Copyright (c) 2024, 2025, Oracle and/or its affiliates. All rights reserved.
  3 // Copyright (c) 2024, Huawei Technologies Co., Ltd. All rights reserved.
  4 // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  5 //
  6 // This code is free software; you can redistribute it and/or modify it
  7 // under the terms of the GNU General Public License version 2 only, as
  8 // published by the Free Software Foundation.
  9 //
 10 // This code is distributed in the hope that it will be useful, but WITHOUT
 11 // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 12 // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 13 // version 2 for more details (a copy is included in the LICENSE file that
 14 // accompanied this code).
 15 //
 16 // You should have received a copy of the GNU General Public License version
 17 // 2 along with this work; if not, write to the Free Software Foundation,
 18 // Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 19 //
 20 // Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 21 // or visit www.oracle.com if you need additional information or have any
 22 // questions.

 57   g1_asm->g1_write_barrier_pre_c2(masm, obj, pre_val, xthread, tmp1, tmp2, stub);
 58 }
 59 
 60 static void write_barrier_post(MacroAssembler* masm,
 61                                const MachNode* node,
 62                                Register store_addr,
 63                                Register new_val,
 64                                Register tmp1,
 65                                Register tmp2) {
 66   if (!G1BarrierStubC2::needs_post_barrier(node)) {
 67     return;
 68   }
 69   Assembler::InlineSkippedInstructionsCounter skip_counter(masm);
 70   G1BarrierSetAssembler* g1_asm = static_cast<G1BarrierSetAssembler*>(BarrierSet::barrier_set()->barrier_set_assembler());
 71   bool new_val_may_be_null = G1BarrierStubC2::post_new_val_may_be_null(node);
 72   g1_asm->g1_write_barrier_post_c2(masm, store_addr, new_val, xthread, tmp1, tmp2, new_val_may_be_null);
 73 }
 74 
 75 %}
 76 
























































































































 77 instruct g1StoreP(indirect mem, iRegP src, iRegPNoSp tmp1, iRegPNoSp tmp2, iRegPNoSp tmp3, rFlagsReg cr)
 78 %{
 79   predicate(UseG1GC && n->as_Store()->barrier_data() != 0);
 80   match(Set mem (StoreP mem src));
 81   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, KILL cr);
 82   ins_cost(STORE_COST);
 83   format %{ "sd  $src, $mem\t# ptr" %}
 84   ins_encode %{
 85     guarantee($mem$$disp == 0, "impossible encoding");
 86     write_barrier_pre(masm, this,
 87                       $mem$$Register  /* obj */,
 88                       $tmp1$$Register /* pre_val */,
 89                       $tmp2$$Register /* tmp1 */,
 90                       $tmp3$$Register /* tmp2 */,
 91                       RegSet::of($mem$$Register, $src$$Register) /* preserve */);
 92     __ sd($src$$Register, Address($mem$$Register));
 93     write_barrier_post(masm, this,
 94                        $mem$$Register  /* store_addr */,
 95                        $src$$Register  /* new_val */,
 96                        $tmp2$$Register /* tmp1 */,

  1 //
  2 // Copyright (c) 2024, 2026, Oracle and/or its affiliates. All rights reserved.
  3 // Copyright (c) 2024, Huawei Technologies Co., Ltd. All rights reserved.
  4 // DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  5 //
  6 // This code is free software; you can redistribute it and/or modify it
  7 // under the terms of the GNU General Public License version 2 only, as
  8 // published by the Free Software Foundation.
  9 //
 10 // This code is distributed in the hope that it will be useful, but WITHOUT
 11 // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 12 // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 13 // version 2 for more details (a copy is included in the LICENSE file that
 14 // accompanied this code).
 15 //
 16 // You should have received a copy of the GNU General Public License version
 17 // 2 along with this work; if not, write to the Free Software Foundation,
 18 // Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 19 //
 20 // Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 21 // or visit www.oracle.com if you need additional information or have any
 22 // questions.

 57   g1_asm->g1_write_barrier_pre_c2(masm, obj, pre_val, xthread, tmp1, tmp2, stub);
 58 }
 59 
 60 static void write_barrier_post(MacroAssembler* masm,
 61                                const MachNode* node,
 62                                Register store_addr,
 63                                Register new_val,
 64                                Register tmp1,
 65                                Register tmp2) {
 66   if (!G1BarrierStubC2::needs_post_barrier(node)) {
 67     return;
 68   }
 69   Assembler::InlineSkippedInstructionsCounter skip_counter(masm);
 70   G1BarrierSetAssembler* g1_asm = static_cast<G1BarrierSetAssembler*>(BarrierSet::barrier_set()->barrier_set_assembler());
 71   bool new_val_may_be_null = G1BarrierStubC2::post_new_val_may_be_null(node);
 72   g1_asm->g1_write_barrier_post_c2(masm, store_addr, new_val, xthread, tmp1, tmp2, new_val_may_be_null);
 73 }
 74 
 75 %}
 76 
 77 
 78 // TODO 8350865 (same applies to g1StoreLSpecialTwoOops)
 79 // - Do not set/overwrite barrier data here, also handle G1C2BarrierPostNotNull
 80 
 81 instruct g1StoreLSpecialOneOopOff0(indirect mem, iRegLNoSp src, immI0 off, iRegPNoSp tmp1, iRegPNoSp tmp2, iRegPNoSp tmp3, rFlagsReg cr)
 82 %{
 83   predicate(UseG1GC);
 84   match(Set mem (StoreLSpecial mem (Binary src off)));
 85   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, KILL cr);
 86   ins_cost(STORE_COST);
 87   format %{ "sd  $src, $mem\t# g1StoreLSpecialOneOopOff0" %}
 88   ins_encode %{
 89     guarantee($mem$$disp == 0, "impossible encoding");
 90     ((MachNode*)this)->set_barrier_data(G1C2BarrierPre | G1C2BarrierPost);
 91 
 92     write_barrier_pre(masm, this,
 93                       $mem$$Register /* obj */,
 94                       $tmp1$$Register /* pre_val */,
 95                       $tmp2$$Register /* tmp1 */,
 96                       $tmp3$$Register /* tmp2 */,
 97                       RegSet::of($mem$$Register, $src$$Register) /* preserve */);
 98 
 99     __ sd($src$$Register, Address($mem$$Register));
100 
101     // Extract the narrow oop field value
102     __ zext($tmp1$$Register, $src$$Register, 32);
103     __ decode_heap_oop($tmp1$$Register, $tmp1$$Register);
104     write_barrier_post(masm, this,
105                        $mem$$Register /* store_addr */,
106                        $tmp1$$Register /* new_val */,
107                        $tmp2$$Register /* tmp1 */,
108                        $tmp3$$Register /* tmp2 */);
109   %}
110   ins_pipe(istore_reg_mem);
111 %}
112 
113 instruct g1StoreLSpecialOneOopOff4(indirect mem, iRegLNoSp src, immI_4 off, iRegPNoSp tmp1, iRegPNoSp tmp2, iRegPNoSp tmp3, iRegPNoSp tmp4, rFlagsReg cr)
114 %{
115   predicate(UseG1GC);
116   match(Set mem (StoreLSpecial mem (Binary src off)));
117   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
118   ins_cost(STORE_COST);
119   format %{ "sd  $src, $mem\t# g1StoreLSpecialOneOopOff4" %}
120   ins_encode %{
121     guarantee($mem$$disp == 0, "impossible encoding");
122     ((MachNode*)this)->set_barrier_data(G1C2BarrierPre | G1C2BarrierPost);
123 
124     // Adjust address to point to narrow oop
125     __ add($tmp4$$Register, $mem$$Register, 4);
126     write_barrier_pre(masm, this,
127                       $tmp4$$Register /* obj */,
128                       $tmp1$$Register /* pre_val */,
129                       $tmp2$$Register /* tmp1 */,
130                       $tmp3$$Register /* tmp2 */,
131                       RegSet::of($mem$$Register, $src$$Register, $tmp4$$Register) /* preserve */);
132 
133     __ sd($src$$Register, Address($mem$$Register));
134 
135     // Shift long value to extract the narrow oop field value and zero-extend it
136     __ srli($tmp1$$Register, $src$$Register, 32);
137     __ decode_heap_oop($tmp1$$Register, $tmp1$$Register);
138     write_barrier_post(masm, this,
139                        $tmp4$$Register /* store_addr */,
140                        $tmp1$$Register /* new_val */,
141                        $tmp2$$Register /* tmp1 */,
142                        $tmp3$$Register /* tmp2 */);
143   %}
144   ins_pipe(istore_reg_mem);
145 %}
146 
147 instruct g1StoreLSpecialTwoOops(indirect mem, iRegLNoSp src, iRegPNoSp tmp1, iRegPNoSp tmp2, iRegPNoSp tmp3, iRegPNoSp tmp4, rFlagsReg cr)
148 %{
149   predicate(UseG1GC);
150   match(Set mem (StoreLSpecial mem src));
151   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, TEMP tmp4, KILL cr);
152   ins_cost(STORE_COST);
153   format %{ "sd  $src, $mem\t# g1StoreLSpecialTwoOops" %}
154   ins_encode %{
155     guarantee($mem$$disp == 0, "impossible encoding");
156     ((MachNode*)this)->set_barrier_data(G1C2BarrierPre | G1C2BarrierPost);
157 
158     write_barrier_pre(masm, this,
159                       $mem$$Register /* obj */,
160                       $tmp1$$Register /* pre_val */,
161                       $tmp2$$Register /* tmp1 */,
162                       $tmp3$$Register /* tmp2 */,
163                       RegSet::of($mem$$Register, $src$$Register) /* preserve */);
164     // Adjust address to point to the second narrow oop in the long value
165     __ add($tmp4$$Register, $mem$$Register, 4);
166     write_barrier_pre(masm, this,
167                       $tmp4$$Register /* obj */,
168                       $tmp1$$Register /* pre_val */,
169                       $tmp2$$Register /* tmp1 */,
170                       $tmp3$$Register /* tmp2 */,
171                       RegSet::of($mem$$Register, $src$$Register, $tmp4$$Register) /* preserve */);
172 
173     __ sd($src$$Register, Address($mem$$Register));
174 
175     // Zero-extend first narrow oop to long
176     __ zext($tmp1$$Register, $src$$Register, 32);
177     __ decode_heap_oop($tmp1$$Register, $tmp1$$Register);
178     write_barrier_post(masm, this,
179                        $mem$$Register /* store_addr */,
180                        $tmp1$$Register /* new_val */,
181                        $tmp2$$Register /* tmp1 */,
182                        $tmp3$$Register /* tmp2 */);
183 
184     // Shift long value to extract the second narrow oop field value
185     __ srli($tmp1$$Register, $src$$Register, 32);
186     __ decode_heap_oop($tmp1$$Register, $tmp1$$Register);
187     write_barrier_post(masm, this,
188                        $tmp4$$Register /* store_addr */,
189                        $tmp1$$Register /* new_val */,
190                        $tmp2$$Register /* tmp1 */,
191                        $tmp3$$Register /* tmp2 */);
192   %}
193   ins_pipe(istore_reg_mem);
194 %}
195 
196 
197 instruct g1StoreP(indirect mem, iRegP src, iRegPNoSp tmp1, iRegPNoSp tmp2, iRegPNoSp tmp3, rFlagsReg cr)
198 %{
199   predicate(UseG1GC && n->as_Store()->barrier_data() != 0);
200   match(Set mem (StoreP mem src));
201   effect(TEMP tmp1, TEMP tmp2, TEMP tmp3, KILL cr);
202   ins_cost(STORE_COST);
203   format %{ "sd  $src, $mem\t# ptr" %}
204   ins_encode %{
205     guarantee($mem$$disp == 0, "impossible encoding");
206     write_barrier_pre(masm, this,
207                       $mem$$Register  /* obj */,
208                       $tmp1$$Register /* pre_val */,
209                       $tmp2$$Register /* tmp1 */,
210                       $tmp3$$Register /* tmp2 */,
211                       RegSet::of($mem$$Register, $src$$Register) /* preserve */);
212     __ sd($src$$Register, Address($mem$$Register));
213     write_barrier_post(masm, this,
214                        $mem$$Register  /* store_addr */,
215                        $src$$Register  /* new_val */,
216                        $tmp2$$Register /* tmp1 */,
< prev index next >