1 #include "barrier.h" 2 #include "util.h" 3 #include "mce.h" 4 mce_barrier_init(struct mce_softirq_barrier * bar)5void mce_barrier_init(struct mce_softirq_barrier *bar) 6 { 7 atomic_set(&bar->val, 0); 8 atomic_set(&bar->ingen, 0); 9 atomic_set(&bar->outgen, 0); 10 } 11 mce_barrier_dec(struct mce_softirq_barrier * bar)12void mce_barrier_dec(struct mce_softirq_barrier *bar) 13 { 14 atomic_inc(&bar->outgen); 15 wmb(); 16 atomic_dec(&bar->val); 17 } 18 mce_barrier_enter(struct mce_softirq_barrier * bar,bool wait)19void mce_barrier_enter(struct mce_softirq_barrier *bar, bool wait) 20 { 21 int gen; 22 23 if ( !wait ) 24 return; 25 atomic_inc(&bar->ingen); 26 gen = atomic_read(&bar->outgen); 27 mb(); 28 atomic_inc(&bar->val); 29 while ( atomic_read(&bar->val) != num_online_cpus() && 30 atomic_read(&bar->outgen) == gen ) 31 { 32 mb(); 33 mce_panic_check(); 34 } 35 } 36 mce_barrier_exit(struct mce_softirq_barrier * bar,bool wait)37void mce_barrier_exit(struct mce_softirq_barrier *bar, bool wait) 38 { 39 int gen; 40 41 if ( !wait ) 42 return; 43 atomic_inc(&bar->outgen); 44 gen = atomic_read(&bar->ingen); 45 mb(); 46 atomic_dec(&bar->val); 47 while ( atomic_read(&bar->val) != 0 && 48 atomic_read(&bar->ingen) == gen ) 49 { 50 mb(); 51 mce_panic_check(); 52 } 53 } 54 mce_barrier(struct mce_softirq_barrier * bar)55void mce_barrier(struct mce_softirq_barrier *bar) 56 { 57 mce_barrier_enter(bar, mce_broadcast); 58 mce_barrier_exit(bar, mce_broadcast); 59 } 60