< prev index next >

src/cpu/ppc/vm/macroAssembler_ppc.cpp

Print this page


   1 /*
   2  * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
   3  * Copyright (c) 2012, 2017 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  *


3016     barrier_set_cast<CardTableModRefBS>(Universe::heap()->barrier_set());
3017   assert(bs->kind() == BarrierSet::CardTableForRS ||
3018          bs->kind() == BarrierSet::CardTableExtension, "wrong barrier");
3019 #ifdef ASSERT
3020   cmpdi(CCR0, Rnew_val, 0);
3021   asm_assert_ne("null oop not allowed", 0x321);
3022 #endif
3023   card_table_write(bs->byte_map_base, Rtmp, Rstore_addr);
3024 }
3025 
3026 // Write the card table byte.
3027 void MacroAssembler::card_table_write(jbyte* byte_map_base, Register Rtmp, Register Robj) {
3028   assert_different_registers(Robj, Rtmp, R0);
3029   load_const_optimized(Rtmp, (address)byte_map_base, R0);
3030   srdi(Robj, Robj, CardTableModRefBS::card_shift);
3031   li(R0, 0); // dirty
3032   if (UseConcMarkSweepGC) membar(Assembler::StoreStore);
3033   stbx(R0, Rtmp, Robj);
3034 }
3035 
3036 // Kills R31 if value is a volatile register.
3037 void MacroAssembler::resolve_jobject(Register value, Register tmp1, Register tmp2, bool needs_frame) {
3038   Label done;
3039   cmpdi(CCR0, value, 0);
3040   beq(CCR0, done);         // Use NULL as-is.
3041 
3042   clrrdi(tmp1, value, JNIHandles::weak_tag_size);
3043 #if INCLUDE_ALL_GCS
3044   if (UseG1GC) { andi_(tmp2, value, JNIHandles::weak_tag_mask); }
3045 #endif
3046   ld(value, 0, tmp1);      // Resolve (untagged) jobject.
3047 
3048 #if INCLUDE_ALL_GCS
3049   if (UseG1GC) {
3050     Label not_weak;
3051     beq(CCR0, not_weak);   // Test for jweak tag.
3052     verify_oop(value);
3053     g1_write_barrier_pre(noreg, // obj
3054                          noreg, // offset
3055                          value, // pre_val
3056                          tmp1, tmp2, needs_frame);
3057     bind(not_weak);
3058   }
3059 #endif // INCLUDE_ALL_GCS
3060   verify_oop(value);
3061   bind(done);
3062 }
3063 
3064 #if INCLUDE_ALL_GCS
3065 // General G1 pre-barrier generator.
3066 // Goal: record the previous value if it is not null.
3067 void MacroAssembler::g1_write_barrier_pre(Register Robj, RegisterOrConstant offset, Register Rpre_val,
3068                                           Register Rtmp1, Register Rtmp2, bool needs_frame) {
3069   Label runtime, filtered;
3070 
3071   // Is marking active?
3072   if (in_bytes(SATBMarkQueue::byte_width_of_active()) == 4) {
3073     lwz(Rtmp1, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_active()), R16_thread);
3074   } else {
3075     guarantee(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1, "Assumption");
3076     lbz(Rtmp1, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_active()), R16_thread);
3077   }
3078   cmpdi(CCR0, Rtmp1, 0);
3079   beq(CCR0, filtered);
3080 
3081   // Do we need to load the previous value?
3082   if (Robj != noreg) {
3083     // Load the previous value...


3105 
3106   // Can we store original value in the thread's buffer?
3107   // Is index == 0?
3108   // (The index field is typed as size_t.)
3109   const Register Rbuffer = Rtmp1, Rindex = Rtmp2;
3110 
3111   ld(Rindex, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_index()), R16_thread);
3112   cmpdi(CCR0, Rindex, 0);
3113   beq(CCR0, runtime); // If index == 0, goto runtime.
3114   ld(Rbuffer, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_buf()), R16_thread);
3115 
3116   addi(Rindex, Rindex, -wordSize); // Decrement index.
3117   std(Rindex, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_index()), R16_thread);
3118 
3119   // Record the previous value.
3120   stdx(Rpre_val, Rbuffer, Rindex);
3121   b(filtered);
3122 
3123   bind(runtime);
3124 
3125   // May need to preserve LR. Also needed if current frame is not compatible with C calling convention.
3126   if (needs_frame) {
3127     save_LR_CR(Rtmp1);
3128     push_frame_reg_args(0, Rtmp2);
3129   }
3130 
3131   if (Rpre_val->is_volatile() && Robj == noreg) mr(R31, Rpre_val); // Save pre_val across C call if it was preloaded.
3132   call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_pre), Rpre_val, R16_thread);
3133   if (Rpre_val->is_volatile() && Robj == noreg) mr(Rpre_val, R31); // restore
3134 
3135   if (needs_frame) {
3136     pop_frame();
3137     restore_LR_CR(Rtmp1);
3138   }
3139 
3140   bind(filtered);
3141 }
3142 
3143 // General G1 post-barrier generator
3144 // Store cross-region card.
3145 void MacroAssembler::g1_write_barrier_post(Register Rstore_addr, Register Rnew_val, Register Rtmp1, Register Rtmp2, Register Rtmp3, Label *filtered_ext) {


   1 /*
   2  * Copyright (c) 1997, 2016, Oracle and/or its affiliates. All rights reserved.
   3  * Copyright (c) 2012, 2016 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  *


3016     barrier_set_cast<CardTableModRefBS>(Universe::heap()->barrier_set());
3017   assert(bs->kind() == BarrierSet::CardTableForRS ||
3018          bs->kind() == BarrierSet::CardTableExtension, "wrong barrier");
3019 #ifdef ASSERT
3020   cmpdi(CCR0, Rnew_val, 0);
3021   asm_assert_ne("null oop not allowed", 0x321);
3022 #endif
3023   card_table_write(bs->byte_map_base, Rtmp, Rstore_addr);
3024 }
3025 
3026 // Write the card table byte.
3027 void MacroAssembler::card_table_write(jbyte* byte_map_base, Register Rtmp, Register Robj) {
3028   assert_different_registers(Robj, Rtmp, R0);
3029   load_const_optimized(Rtmp, (address)byte_map_base, R0);
3030   srdi(Robj, Robj, CardTableModRefBS::card_shift);
3031   li(R0, 0); // dirty
3032   if (UseConcMarkSweepGC) membar(Assembler::StoreStore);
3033   stbx(R0, Rtmp, Robj);
3034 }
3035 




























3036 #if INCLUDE_ALL_GCS
3037 // General G1 pre-barrier generator.
3038 // Goal: record the previous value if it is not null.
3039 void MacroAssembler::g1_write_barrier_pre(Register Robj, RegisterOrConstant offset, Register Rpre_val,
3040                                           Register Rtmp1, Register Rtmp2, bool needs_frame) {
3041   Label runtime, filtered;
3042 
3043   // Is marking active?
3044   if (in_bytes(SATBMarkQueue::byte_width_of_active()) == 4) {
3045     lwz(Rtmp1, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_active()), R16_thread);
3046   } else {
3047     guarantee(in_bytes(SATBMarkQueue::byte_width_of_active()) == 1, "Assumption");
3048     lbz(Rtmp1, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_active()), R16_thread);
3049   }
3050   cmpdi(CCR0, Rtmp1, 0);
3051   beq(CCR0, filtered);
3052 
3053   // Do we need to load the previous value?
3054   if (Robj != noreg) {
3055     // Load the previous value...


3077 
3078   // Can we store original value in the thread's buffer?
3079   // Is index == 0?
3080   // (The index field is typed as size_t.)
3081   const Register Rbuffer = Rtmp1, Rindex = Rtmp2;
3082 
3083   ld(Rindex, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_index()), R16_thread);
3084   cmpdi(CCR0, Rindex, 0);
3085   beq(CCR0, runtime); // If index == 0, goto runtime.
3086   ld(Rbuffer, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_buf()), R16_thread);
3087 
3088   addi(Rindex, Rindex, -wordSize); // Decrement index.
3089   std(Rindex, in_bytes(JavaThread::satb_mark_queue_offset() + SATBMarkQueue::byte_offset_of_index()), R16_thread);
3090 
3091   // Record the previous value.
3092   stdx(Rpre_val, Rbuffer, Rindex);
3093   b(filtered);
3094 
3095   bind(runtime);
3096 
3097   // VM call need frame to access(write) O register.
3098   if (needs_frame) {
3099     save_LR_CR(Rtmp1);
3100     push_frame_reg_args(0, Rtmp2);
3101   }
3102 
3103   if (Rpre_val->is_volatile() && Robj == noreg) mr(R31, Rpre_val); // Save pre_val across C call if it was preloaded.
3104   call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::g1_wb_pre), Rpre_val, R16_thread);
3105   if (Rpre_val->is_volatile() && Robj == noreg) mr(Rpre_val, R31); // restore
3106 
3107   if (needs_frame) {
3108     pop_frame();
3109     restore_LR_CR(Rtmp1);
3110   }
3111 
3112   bind(filtered);
3113 }
3114 
3115 // General G1 post-barrier generator
3116 // Store cross-region card.
3117 void MacroAssembler::g1_write_barrier_post(Register Rstore_addr, Register Rnew_val, Register Rtmp1, Register Rtmp2, Register Rtmp3, Label *filtered_ext) {


< prev index next >