1 /*
   2  * Copyright (c) 2018, Oracle and/or its affiliates. All rights reserved.
   3  * Copyright (c) 2018, SAP SE. 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.
  23  *
  24  */
  25 
  26 #include "precompiled.hpp"
  27 #include "asm/macroAssembler.inline.hpp"
  28 #include "registerSaver_s390.hpp"
  29 #include "gc/g1/g1CardTable.hpp"
  30 #include "gc/g1/g1BarrierSet.hpp"
  31 #include "gc/g1/g1BarrierSetAssembler.hpp"
  32 #include "gc/g1/g1ThreadLocalData.hpp"
  33 #include "gc/g1/heapRegion.hpp"
  34 #include "gc/shared/collectedHeap.hpp"
  35 #include "interpreter/interp_masm.hpp"
  36 
  37 #define __ masm->
  38 
  39 #define BLOCK_COMMENT(str) if (PrintAssembly) __ block_comment(str)
  40 
  41 void G1BarrierSetAssembler::gen_write_ref_array_pre_barrier(MacroAssembler* masm, DecoratorSet decorators,
  42                                                             Register addr, Register count) {
  43   bool dest_uninitialized = (decorators & AS_DEST_NOT_INITIALIZED) != 0;
  44 
  45   // With G1, don't generate the call if we statically know that the target is uninitialized.
  46   if (!dest_uninitialized) {
  47     // Is marking active?
  48     Label filtered;
  49     assert_different_registers(addr,  Z_R0_scratch);  // would be destroyed by push_frame()
  50     assert_different_registers(count, Z_R0_scratch);  // would be destroyed by push_frame()
  51     Register Rtmp1 = Z_R0_scratch;
  52     const int active_offset = in_bytes(G1ThreadLocalData::satb_mark_queue_active_offset());
  53     if (in_bytes(SATBMarkQueue::byte_width_of_active()) == 4) {
  54       __ load_and_test_int(Rtmp1, Address(Z_thread, active_offset));
  55     } else {
  56       guarantee(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1, "Assumption");
  57       __ load_and_test_byte(Rtmp1, Address(Z_thread, active_offset));
  58     }
  59     __ z_bre(filtered); // Activity indicator is zero, so there is no marking going on currently.
  60 
  61     RegisterSaver::save_live_registers(masm, RegisterSaver::arg_registers); // Creates frame.
  62 
  63     if (UseCompressedOops) {
  64       __ call_VM_leaf(CAST_FROM_FN_PTR(address, G1BarrierSet::write_ref_array_pre_narrow_oop_entry), addr, count);
  65     } else {
  66       __ call_VM_leaf(CAST_FROM_FN_PTR(address, G1BarrierSet::write_ref_array_pre_oop_entry), addr, count);
  67     }
  68 
  69     RegisterSaver::restore_live_registers(masm, RegisterSaver::arg_registers);
  70 
  71     __ bind(filtered);
  72   }
  73 }
  74 
  75 void G1BarrierSetAssembler::gen_write_ref_array_post_barrier(MacroAssembler* masm, DecoratorSet decorators,
  76                                                              Register addr, Register count, bool do_return) {
  77   address entry_point = CAST_FROM_FN_PTR(address, G1BarrierSet::write_ref_array_post_entry);
  78   if (!do_return) {
  79     assert_different_registers(addr,  Z_R0_scratch);  // would be destroyed by push_frame()
  80     assert_different_registers(count, Z_R0_scratch);  // would be destroyed by push_frame()
  81     RegisterSaver::save_live_registers(masm, RegisterSaver::arg_registers); // Creates frame.
  82     __ call_VM_leaf(entry_point, addr, count);
  83     RegisterSaver::restore_live_registers(masm, RegisterSaver::arg_registers);
  84   } else {
  85     // Tail call: call c and return to stub caller.
  86     __ lgr_if_needed(Z_ARG1, addr);
  87     __ lgr_if_needed(Z_ARG2, count);
  88     __ load_const(Z_R1, entry_point);
  89     __ z_br(Z_R1); // Branch without linking, callee will return to stub caller.
  90   }
  91 }
  92 
  93 void G1BarrierSetAssembler::load_at(MacroAssembler* masm, DecoratorSet decorators, BasicType type,
  94                                     const Address& src, Register dst, Register tmp1, Register tmp2, Label *is_null) {
  95   bool on_oop = type == T_OBJECT || type == T_ARRAY;
  96   bool on_weak = (decorators & ON_WEAK_OOP_REF) != 0;
  97   bool on_phantom = (decorators & ON_PHANTOM_OOP_REF) != 0;
  98   bool on_reference = on_weak || on_phantom;
  99   Label done;
 100   if (on_oop && on_reference && is_null == NULL) { is_null = &done; }
 101   ModRefBarrierSetAssembler::load_at(masm, decorators, type, src, dst, tmp1, tmp2, is_null);
 102   if (on_oop && on_reference) {
 103     // Generate the G1 pre-barrier code to log the value of
 104     // the referent field in an SATB buffer.
 105     g1_write_barrier_pre(masm, decorators | OOP_NOT_NULL,
 106                          NULL /* obj */,
 107                          dst  /* pre_val */,
 108                          noreg/* preserve */ ,
 109                          tmp1, tmp2 /* tmp */,
 110                          true /* pre_val_needed */);
 111   }
 112   __ bind(done);
 113 }
 114 
 115 void G1BarrierSetAssembler::g1_write_barrier_pre(MacroAssembler* masm, DecoratorSet decorators,
 116                                                  const Address*  obj,
 117                                                  Register        Rpre_val,      // Ideally, this is a non-volatile register.
 118                                                  Register        Rval,          // Will be preserved.
 119                                                  Register        Rtmp1,         // If Rpre_val is volatile, either Rtmp1
 120                                                  Register        Rtmp2,         // or Rtmp2 has to be non-volatile.
 121                                                  bool            pre_val_needed // Save Rpre_val across runtime call, caller uses it.
 122                                                  ) {
 123 
 124   bool not_null  = (decorators & OOP_NOT_NULL) != 0,
 125        preloaded = obj == NULL;
 126 
 127   const Register Robj = obj ? obj->base() : noreg,
 128                  Roff = obj ? obj->index() : noreg;
 129   const int active_offset = in_bytes(G1ThreadLocalData::satb_mark_queue_active_offset());
 130   const int buffer_offset = in_bytes(G1ThreadLocalData::satb_mark_queue_buffer_offset());
 131   const int index_offset  = in_bytes(G1ThreadLocalData::satb_mark_queue_index_offset());
 132   assert_different_registers(Rtmp1, Rtmp2, Z_R0_scratch); // None of the Rtmp<i> must be Z_R0!!
 133   assert_different_registers(Robj, Z_R0_scratch);         // Used for addressing. Furthermore, push_frame destroys Z_R0!!
 134   assert_different_registers(Rval, Z_R0_scratch);         // push_frame destroys Z_R0!!
 135 
 136   Label callRuntime, filtered;
 137 
 138   BLOCK_COMMENT("g1_write_barrier_pre {");
 139 
 140   // Is marking active?
 141   // Note: value is loaded for test purposes only. No further use here.
 142   if (in_bytes(SATBMarkQueue::byte_width_of_active()) == 4) {
 143     __ load_and_test_int(Rtmp1, Address(Z_thread, active_offset));
 144   } else {
 145     guarantee(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1, "Assumption");
 146     __ load_and_test_byte(Rtmp1, Address(Z_thread, active_offset));
 147   }
 148   __ z_bre(filtered); // Activity indicator is zero, so there is no marking going on currently.
 149 
 150   assert(Rpre_val != noreg, "must have a real register");
 151 
 152 
 153   // If an object is given, we need to load the previous value into Rpre_val.
 154   if (obj) {
 155     // Load the previous value...
 156     if (UseCompressedOops) {
 157       __ z_llgf(Rpre_val, *obj);
 158     } else {
 159       __ z_lg(Rpre_val, *obj);
 160     }
 161   }
 162 
 163   // Is the previous value NULL?
 164   // If so, we don't need to record it and we're done.
 165   // Note: pre_val is loaded, decompressed and stored (directly or via runtime call).
 166   //       Register contents is preserved across runtime call if caller requests to do so.
 167   if (preloaded && not_null) {
 168 #ifdef ASSERT
 169     __ z_ltgr(Rpre_val, Rpre_val);
 170     __ asm_assert_ne("null oop not allowed (G1 pre)", 0x321); // Checked by caller.
 171 #endif
 172   } else {
 173     __ z_ltgr(Rpre_val, Rpre_val);
 174     __ z_bre(filtered); // previous value is NULL, so we don't need to record it.
 175   }
 176 
 177   // Decode the oop now. We know it's not NULL.
 178   if (Robj != noreg && UseCompressedOops) {
 179     __ oop_decoder(Rpre_val, Rpre_val, /*maybeNULL=*/false);
 180   }
 181 
 182   // OK, it's not filtered, so we'll need to call enqueue.
 183 
 184   // We can store the original value in the thread's buffer
 185   // only if index > 0. Otherwise, we need runtime to handle.
 186   // (The index field is typed as size_t.)
 187   Register Rbuffer = Rtmp1, Rindex = Rtmp2;
 188   assert_different_registers(Rbuffer, Rindex, Rpre_val);
 189 
 190   __ z_lg(Rbuffer, buffer_offset, Z_thread);
 191 
 192   __ load_and_test_long(Rindex, Address(Z_thread, index_offset));
 193   __ z_bre(callRuntime); // If index == 0, goto runtime.
 194 
 195   __ add2reg(Rindex, -wordSize); // Decrement index.
 196   __ z_stg(Rindex, index_offset, Z_thread);
 197 
 198   // Record the previous value.
 199   __ z_stg(Rpre_val, 0, Rbuffer, Rindex);
 200   __ z_bru(filtered);  // We are done.
 201 
 202   Rbuffer = noreg;  // end of life
 203   Rindex  = noreg;  // end of life
 204 
 205   __ bind(callRuntime);
 206 
 207   // Save some registers (inputs and result) over runtime call
 208   // by spilling them into the top frame.
 209   if (Robj != noreg && Robj->is_volatile()) {
 210     __ z_stg(Robj, Robj->encoding()*BytesPerWord, Z_SP);
 211   }
 212   if (Roff != noreg && Roff->is_volatile()) {
 213     __ z_stg(Roff, Roff->encoding()*BytesPerWord, Z_SP);
 214   }
 215   if (Rval != noreg && Rval->is_volatile()) {
 216     __ z_stg(Rval, Rval->encoding()*BytesPerWord, Z_SP);
 217   }
 218 
 219   // Save Rpre_val (result) over runtime call.
 220   Register Rpre_save = Rpre_val;
 221   if ((Rpre_val == Z_R0_scratch) || (pre_val_needed && Rpre_val->is_volatile())) {
 222     guarantee(!Rtmp1->is_volatile() || !Rtmp2->is_volatile(), "oops!");
 223     Rpre_save = !Rtmp1->is_volatile() ? Rtmp1 : Rtmp2;
 224   }
 225   __ lgr_if_needed(Rpre_save, Rpre_val);
 226 
 227   // Push frame to protect top frame with return pc and spilled register values.
 228   __ save_return_pc();
 229   __ push_frame_abi160(0); // Will use Z_R0 as tmp.
 230 
 231   // Rpre_val may be destroyed by push_frame().
 232   __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_pre), Rpre_save, Z_thread);
 233 
 234   __ pop_frame();
 235   __ restore_return_pc();
 236 
 237   // Restore spilled values.
 238   if (Robj != noreg && Robj->is_volatile()) {
 239     __ z_lg(Robj, Robj->encoding()*BytesPerWord, Z_SP);
 240   }
 241   if (Roff != noreg && Roff->is_volatile()) {
 242     __ z_lg(Roff, Roff->encoding()*BytesPerWord, Z_SP);
 243   }
 244   if (Rval != noreg && Rval->is_volatile()) {
 245     __ z_lg(Rval, Rval->encoding()*BytesPerWord, Z_SP);
 246   }
 247   if (pre_val_needed && Rpre_val->is_volatile()) {
 248     __ lgr_if_needed(Rpre_val, Rpre_save);
 249   }
 250 
 251   __ bind(filtered);
 252   BLOCK_COMMENT("} g1_write_barrier_pre");
 253 }
 254 
 255 void G1BarrierSetAssembler::g1_write_barrier_post(MacroAssembler* masm, DecoratorSet decorators, Register Rstore_addr, Register Rnew_val,
 256                                                   Register Rtmp1, Register Rtmp2, Register Rtmp3) {
 257   bool not_null = (decorators & OOP_NOT_NULL) != 0;
 258 
 259   assert_different_registers(Rstore_addr, Rnew_val, Rtmp1, Rtmp2); // Most probably, Rnew_val == Rtmp3.
 260 
 261   Label callRuntime, filtered;
 262 
 263   CardTableBarrierSet* ct = barrier_set_cast<CardTableBarrierSet>(Universe::heap()->barrier_set());
 264   assert(sizeof(*ct->card_table()->byte_map_base()) == sizeof(jbyte), "adjust this code");
 265 
 266   BLOCK_COMMENT("g1_write_barrier_post {");
 267 
 268   // Does store cross heap regions?
 269   // It does if the two addresses specify different grain addresses.
 270   if (G1RSBarrierRegionFilter) {
 271     if (VM_Version::has_DistinctOpnds()) {
 272       __ z_xgrk(Rtmp1, Rstore_addr, Rnew_val);
 273     } else {
 274       __ z_lgr(Rtmp1, Rstore_addr);
 275       __ z_xgr(Rtmp1, Rnew_val);
 276     }
 277     __ z_srag(Rtmp1, Rtmp1, HeapRegion::LogOfHRGrainBytes);
 278     __ z_bre(filtered);
 279   }
 280 
 281   // Crosses regions, storing NULL?
 282   if (not_null) {
 283 #ifdef ASSERT
 284     __ z_ltgr(Rnew_val, Rnew_val);
 285     __ asm_assert_ne("null oop not allowed (G1 post)", 0x322); // Checked by caller.
 286 #endif
 287   } else {
 288     __ z_ltgr(Rnew_val, Rnew_val);
 289     __ z_bre(filtered);
 290   }
 291 
 292   Rnew_val = noreg; // end of lifetime
 293 
 294   // Storing region crossing non-NULL, is card already dirty?
 295   assert(sizeof(*ct->card_table()->byte_map_base()) == sizeof(jbyte), "adjust this code");
 296   assert_different_registers(Rtmp1, Rtmp2, Rtmp3);
 297   // Make sure not to use Z_R0 for any of these registers.
 298   Register Rcard_addr = (Rtmp1 != Z_R0_scratch) ? Rtmp1 : Rtmp3;
 299   Register Rbase      = (Rtmp2 != Z_R0_scratch) ? Rtmp2 : Rtmp3;
 300 
 301   // calculate address of card
 302   __ load_const_optimized(Rbase, (address)ct->card_table()->byte_map_base());      // Card table base.
 303   __ z_srlg(Rcard_addr, Rstore_addr, CardTable::card_shift);         // Index into card table.
 304   __ z_algr(Rcard_addr, Rbase);                                      // Explicit calculation needed for cli.
 305   Rbase = noreg; // end of lifetime
 306 
 307   // Filter young.
 308   assert((unsigned int)G1CardTable::g1_young_card_val() <= 255, "otherwise check this code");
 309   __ z_cli(0, Rcard_addr, G1CardTable::g1_young_card_val());
 310   __ z_bre(filtered);
 311 
 312   // Check the card value. If dirty, we're done.
 313   // This also avoids false sharing of the (already dirty) card.
 314   __ z_sync(); // Required to support concurrent cleaning.
 315   assert((unsigned int)G1CardTable::dirty_card_val() <= 255, "otherwise check this code");
 316   __ z_cli(0, Rcard_addr, G1CardTable::dirty_card_val()); // Reload after membar.
 317   __ z_bre(filtered);
 318 
 319   // Storing a region crossing, non-NULL oop, card is clean.
 320   // Dirty card and log.
 321   __ z_mvi(0, Rcard_addr, G1CardTable::dirty_card_val());
 322 
 323   Register Rcard_addr_x = Rcard_addr;
 324   Register Rqueue_index = (Rtmp2 != Z_R0_scratch) ? Rtmp2 : Rtmp1;
 325   Register Rqueue_buf   = (Rtmp3 != Z_R0_scratch) ? Rtmp3 : Rtmp1;
 326   const int qidx_off    = in_bytes(G1ThreadLocalData::dirty_card_queue_index_offset());
 327   const int qbuf_off    = in_bytes(G1ThreadLocalData::dirty_card_queue_buffer_offset());
 328   if ((Rcard_addr == Rqueue_buf) || (Rcard_addr == Rqueue_index)) {
 329     Rcard_addr_x = Z_R0_scratch;  // Register shortage. We have to use Z_R0.
 330   }
 331   __ lgr_if_needed(Rcard_addr_x, Rcard_addr);
 332 
 333   __ load_and_test_long(Rqueue_index, Address(Z_thread, qidx_off));
 334   __ z_bre(callRuntime); // Index == 0 then jump to runtime.
 335 
 336   __ z_lg(Rqueue_buf, qbuf_off, Z_thread);
 337 
 338   __ add2reg(Rqueue_index, -wordSize); // Decrement index.
 339   __ z_stg(Rqueue_index, qidx_off, Z_thread);
 340 
 341   __ z_stg(Rcard_addr_x, 0, Rqueue_index, Rqueue_buf); // Store card.
 342   __ z_bru(filtered);
 343 
 344   __ bind(callRuntime);
 345 
 346   // TODO: do we need a frame? Introduced to be on the safe side.
 347   bool needs_frame = true;
 348   __ lgr_if_needed(Rcard_addr, Rcard_addr_x); // copy back asap. push_frame will destroy Z_R0_scratch!
 349 
 350   // VM call need frame to access(write) O register.
 351   if (needs_frame) {
 352     __ save_return_pc();
 353     __ push_frame_abi160(0); // Will use Z_R0 as tmp on old CPUs.
 354   }
 355 
 356   // Save the live input values.
 357   __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_post), Rcard_addr, Z_thread);
 358 
 359   if (needs_frame) {
 360     __ pop_frame();
 361     __ restore_return_pc();
 362   }
 363 
 364   __ bind(filtered);
 365 
 366   BLOCK_COMMENT("} g1_write_barrier_post");
 367 }
 368 
 369 void G1BarrierSetAssembler::oop_store_at(MacroAssembler* masm, DecoratorSet decorators, BasicType type,
 370                                          const Address& dst, Register val, Register tmp1, Register tmp2, Register tmp3) {
 371   bool on_array = (decorators & IN_HEAP_ARRAY) != 0;
 372   bool on_anonymous = (decorators & ON_UNKNOWN_OOP_REF) != 0;
 373   bool precise = on_array || on_anonymous;
 374   // Load and record the previous value.
 375   g1_write_barrier_pre(masm, decorators, &dst, tmp3, val, tmp1, tmp2, false);
 376 
 377   BarrierSetAssembler::store_at(masm, decorators, type, dst, val, tmp1, tmp2, tmp3);
 378 
 379   // No need for post barrier if storing NULL
 380   if (val != noreg) {
 381     const Register base = dst.base(),
 382                    idx  = dst.index();
 383     const intptr_t disp = dst.disp();
 384     if (precise && (disp != 0 || idx != noreg)) {
 385       __ add2reg_with_index(base, disp, idx, base);
 386     }
 387     g1_write_barrier_post(masm, decorators, base, val, tmp1, tmp2, tmp3);
 388   }
 389 }
 390 
 391 void G1BarrierSetAssembler::resolve_jobject(MacroAssembler* masm, Register value, Register tmp1, Register tmp2) {
 392   NearLabel Ldone, Lnot_weak;
 393   __ z_ltgr(tmp1, value);
 394   __ z_bre(Ldone);          // Use NULL result as-is.
 395 
 396   __ z_nill(value, ~JNIHandles::weak_tag_mask);
 397   __ z_lg(value, 0, value); // Resolve (untagged) jobject.
 398 
 399   __ z_tmll(tmp1, JNIHandles::weak_tag_mask); // Test for jweak tag.
 400   __ z_braz(Lnot_weak);
 401   __ verify_oop(value);
 402   DecoratorSet decorators = IN_ROOT | ON_PHANTOM_OOP_REF;
 403   g1_write_barrier_pre(masm, decorators, (const Address*)NULL, value, noreg, tmp1, tmp2, true);
 404   __ bind(Lnot_weak);
 405   __ verify_oop(value);
 406   __ bind(Ldone);
 407 }
 408 
 409 #undef __