< prev index next >

src/hotspot/share/gc/g1/g1BarrierSet.cpp

BarrierSetCodeGen_v2

8198949_arraycopy

6  * published by the Free Software Foundation.                                                                                        
7  *                                                                                                                                   
8  * This code is distributed in the hope that it will be useful, but WITHOUT                                                          
9  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or                                                             
10  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License                                                             
11  * version 2 for more details (a copy is included in the LICENSE file that                                                           
12  * accompanied this code).                                                                                                           
13  *                                                                                                                                   
14  * You should have received a copy of the GNU General Public License version                                                         
15  * 2 along with this work; if not, write to the Free Software Foundation,                                                            
16  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.                                                                     
17  *                                                                                                                                   
18  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA                                                           
19  * or visit www.oracle.com if you need additional information or have any                                                            
20  * questions.                                                                                                                        
21  *                                                                                                                                   
22  */                                                                                                                                  
23 
24 #include "precompiled.hpp"                                                                                                           
25 #include "gc/g1/g1BarrierSet.inline.hpp"                                                                                             
                                                                                                                                     
26 #include "gc/g1/g1CardTable.inline.hpp"                                                                                              
27 #include "gc/g1/g1CollectedHeap.inline.hpp"                                                                                          
28 #include "gc/g1/heapRegion.hpp"                                                                                                      
29 #include "gc/g1/satbMarkQueue.hpp"                                                                                                   
30 #include "logging/log.hpp"                                                                                                           
31 #include "oops/oop.inline.hpp"                                                                                                       
32 #include "runtime/mutexLocker.hpp"                                                                                                   
33 #include "runtime/thread.inline.hpp"                                                                                                 
                                                                                                                                     
34 
35 G1BarrierSet::G1BarrierSet(G1CardTable* card_table) :                                                                                
36   CardTableModRefBS(card_table, BarrierSet::FakeRtti(BarrierSet::G1BarrierSet)),                                                     
                                                                                                                                     
                                                                                                                                     
37   _dcqs(JavaThread::dirty_card_queue_set())                                                                                          
38 { }                                                                                                                                  
39 
40 void G1BarrierSet::enqueue(oop pre_val) {                                                                                            
41   // Nulls should have been already filtered.                                                                                        
42   assert(oopDesc::is_oop(pre_val, true), "Error");                                                                                   
43 
44   if (!JavaThread::satb_mark_queue_set().is_active()) return;                                                                        
45   Thread* thr = Thread::current();                                                                                                   
46   if (thr->is_Java_thread()) {                                                                                                       
47     JavaThread* jt = (JavaThread*)thr;                                                                                               
48     jt->satb_mark_queue().enqueue(pre_val);                                                                                          
49   } else {                                                                                                                           
50     MutexLockerEx x(Shared_SATB_Q_lock, Mutex::_no_safepoint_check_flag);                                                            
51     JavaThread::satb_mark_queue_set().shared_satb_queue()->enqueue(pre_val);                                                         
52   }                                                                                                                                  
53 }                                                                                                                                    
54 
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
                                                                                                                                     
55 template <class T> void                                                                                                              
56 G1BarrierSet::write_ref_array_pre_work(T* dst, int count) {                                                                          
57   if (!JavaThread::satb_mark_queue_set().is_active()) return;                                                                        
58   T* elem_ptr = dst;                                                                                                                 
59   for (int i = 0; i < count; i++, elem_ptr++) {                                                                                      
60     T heap_oop = oopDesc::load_heap_oop(elem_ptr);                                                                                   
61     if (!oopDesc::is_null(heap_oop)) {                                                                                               
62       enqueue(oopDesc::decode_heap_oop_not_null(heap_oop));                                                                          
63     }                                                                                                                                
64   }                                                                                                                                  
65 }                                                                                                                                    
66 
67 void G1BarrierSet::write_ref_array_pre(oop* dst, int count, bool dest_uninitialized) {                                               
68   if (!dest_uninitialized) {                                                                                                         
69     write_ref_array_pre_work(dst, count);                                                                                            
70   }                                                                                                                                  
71 }                                                                                                                                    
72 
73 void G1BarrierSet::write_ref_array_pre(narrowOop* dst, int count, bool dest_uninitialized) {                                         
74   if (!dest_uninitialized) {                                                                                                         
75     write_ref_array_pre_work(dst, count);                                                                                            
76   }                                                                                                                                  
77 }                                                                                                                                    
78 
79 void G1BarrierSet::write_ref_field_post_slow(volatile jbyte* byte) {                                                                 
80   // In the slow path, we know a card is not young                                                                                   
81   assert(*byte != G1CardTable::g1_young_card_val(), "slow path invoked without filtering");                                          
82   OrderAccess::storeload();                                                                                                          
83   if (*byte != G1CardTable::dirty_card_val()) {                                                                                      
84     *byte = G1CardTable::dirty_card_val();                                                                                           
85     Thread* thr = Thread::current();                                                                                                 
86     if (thr->is_Java_thread()) {                                                                                                     
87       JavaThread* jt = (JavaThread*)thr;                                                                                             
88       jt->dirty_card_queue().enqueue(byte);                                                                                          
89     } else {                                                                                                                         
90       MutexLockerEx x(Shared_DirtyCardQ_lock,                                                                                        
91                       Mutex::_no_safepoint_check_flag);                                                                              
92       _dcqs.shared_dirty_card_queue()->enqueue(byte);                                                                                

6  * published by the Free Software Foundation.
7  *
8  * This code is distributed in the hope that it will be useful, but WITHOUT
9  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
11  * version 2 for more details (a copy is included in the LICENSE file that
12  * accompanied this code).
13  *
14  * You should have received a copy of the GNU General Public License version
15  * 2 along with this work; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
17  *
18  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
19  * or visit www.oracle.com if you need additional information or have any
20  * questions.
21  *
22  */
23 
24 #include "precompiled.hpp"
25 #include "gc/g1/g1BarrierSet.inline.hpp"
26 #include "gc/g1/g1BarrierSetCodeGen.hpp"
27 #include "gc/g1/g1CardTable.inline.hpp"
28 #include "gc/g1/g1CollectedHeap.inline.hpp"
29 #include "gc/g1/heapRegion.hpp"
30 #include "gc/g1/satbMarkQueue.hpp"
31 #include "logging/log.hpp"
32 #include "oops/oop.inline.hpp"
33 #include "runtime/mutexLocker.hpp"
34 #include "runtime/thread.inline.hpp"
35 #include "utilities/macros.hpp"
36 
37 G1BarrierSet::G1BarrierSet(G1CardTable* card_table) :
38   CardTableModRefBS(make_code_gen<G1BarrierSetCodeGen>(),
39                     card_table,
40                     BarrierSet::FakeRtti(BarrierSet::G1BarrierSet)),
41   _dcqs(JavaThread::dirty_card_queue_set())
42 { }
43 
44 void G1BarrierSet::enqueue(oop pre_val) {
45   // Nulls should have been already filtered.
46   assert(oopDesc::is_oop(pre_val, true), "Error");
47 
48   if (!JavaThread::satb_mark_queue_set().is_active()) return;
49   Thread* thr = Thread::current();
50   if (thr->is_Java_thread()) {
51     JavaThread* jt = (JavaThread*)thr;
52     jt->satb_mark_queue().enqueue(pre_val);
53   } else {
54     MutexLockerEx x(Shared_SATB_Q_lock, Mutex::_no_safepoint_check_flag);
55     JavaThread::satb_mark_queue_set().shared_satb_queue()->enqueue(pre_val);
56   }
57 }
58 
59 void G1BarrierSet::write_ref_array_pre_oop_entry(oop* dst, size_t length) {
60   G1BarrierSet *bs = barrier_set_cast<G1BarrierSet>(BarrierSet::barrier_set());
61   bs->write_ref_array_pre(dst, length, false);
62 }
63 
64 void G1BarrierSet::write_ref_array_pre_narrow_oop_entry(narrowOop* dst, size_t length) {
65   G1BarrierSet *bs = barrier_set_cast<G1BarrierSet>(BarrierSet::barrier_set());
66   bs->write_ref_array_pre(dst, length, false);
67 }
68 
69 void G1BarrierSet::write_ref_array_post_entry(HeapWord* dst, size_t length) {
70   G1BarrierSet *bs = barrier_set_cast<G1BarrierSet>(BarrierSet::barrier_set());
71   bs->G1BarrierSet::write_ref_array(dst, length);
72 }
73 
74 template <class T> void
75 G1BarrierSet::write_ref_array_pre_work(T* dst, size_t count) {
76   if (!JavaThread::satb_mark_queue_set().is_active()) return;
77   T* elem_ptr = dst;
78   for (size_t i = 0; i < count; i++, elem_ptr++) {
79     T heap_oop = oopDesc::load_heap_oop(elem_ptr);
80     if (!oopDesc::is_null(heap_oop)) {
81       enqueue(oopDesc::decode_heap_oop_not_null(heap_oop));
82     }
83   }
84 }
85 
86 void G1BarrierSet::write_ref_array_pre(oop* dst, size_t count, bool dest_uninitialized) {
87   if (!dest_uninitialized) {
88     write_ref_array_pre_work(dst, count);
89   }
90 }
91 
92 void G1BarrierSet::write_ref_array_pre(narrowOop* dst, size_t count, bool dest_uninitialized) {
93   if (!dest_uninitialized) {
94     write_ref_array_pre_work(dst, count);
95   }
96 }
97 
98 void G1BarrierSet::write_ref_field_post_slow(volatile jbyte* byte) {
99   // In the slow path, we know a card is not young
100   assert(*byte != G1CardTable::g1_young_card_val(), "slow path invoked without filtering");
101   OrderAccess::storeload();
102   if (*byte != G1CardTable::dirty_card_val()) {
103     *byte = G1CardTable::dirty_card_val();
104     Thread* thr = Thread::current();
105     if (thr->is_Java_thread()) {
106       JavaThread* jt = (JavaThread*)thr;
107       jt->dirty_card_queue().enqueue(byte);
108     } else {
109       MutexLockerEx x(Shared_DirtyCardQ_lock,
110                       Mutex::_no_safepoint_check_flag);
111       _dcqs.shared_dirty_card_queue()->enqueue(byte);
< prev index next >