Linux???RCU???????
???????????? ???????[ 2016/11/22 11:04:13 ] ?????????????? Linux
???????
????RCU??Read-Copy Update??????????????????????????Linux????蟹?????????????谩?RCU????????????????????????????????????????效?????????????RCU??????????????????????泻????????????????????????????卸?????????????????????????????????????????????????????????????RCU???????????????????????????????????????????????????????校?????????????位???????????????????????????????RCU???????????????
????Linux???????校?????RCU???????????????????? /Documentation/RCU/ ?????????些?????Paul E. McKenney ???????RCU????????????????写????RCU????????????????些???o??些????RCU?????????????????????
??????RCU?????????校???????????????????
????1???????????校????????????????????????????????????????????????????????????????????????????????械????????????????????????????RCU?邪?????????????????Grace period????
????2???????????校????????????????????????????????????????????????????????????????????????????婕�???????-????????Publish-Subscribe Mechanism????
????3?? ???????????????????????????????????????????卤????????????屑?????????RCU?????????????????????????????????????????
??????????
????????????????????????????????????????Paul???????
struct foo {
int a;
char b;
long c;
};
DEFINE_SPINLOCK(foo_mutex);
struct foo *gbl_foo;
void foo_read (void)
{
foo *fp = gbl_foo;
if ( fp != NULL )
dosomething(fp->a?? fp->b ?? fp->c );
}
void foo_update( foo* new_fp )
{
spin_lock(&foo_mutex);
foo *old_fp = gbl_foo;
gbl_foo = new_fp;
spin_unlock(&foo_mutex);
kfee(old_fp);
}
struct foo {
int a;
char b;
long c;
};
DEFINE_SPINLOCK(foo_mutex);
struct foo *gbl_foo;
void foo_read (void)
{
foo *fp = gbl_foo;
if ( fp != NULL )
dosomething(fp->a?? fp->b ?? fp->c );
}
void foo_update( foo* new_fp )
{
spin_lock(&foo_mutex);
foo *old_fp = gbl_foo;
gbl_foo = new_fp;
spin_unlock(&foo_mutex);
kfee(old_fp);
}
?????????????????????????gbl_foo??????????????3???????????????????? foo_ read??foo_update???????foo_ read???????????????????谢???????????????????foo_update???????伞???foo_ read???械?????谢???????????dosomething ?????fp???????????????????危???????????????????????RCU????????????渭????锌??????Grace period??????????????
?????????写??????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????????些????锌????????????????????械???????????1??2?????????????5???????????????????????????????3??4??6???????????????????????????????????????????????????????RCU?????????????API?????????????
void foo_read(void)
{
rcu_read_lock();
foo *fp = gbl_foo;
if ( fp != NULL )
dosomething(fp->a??fp->b??fp->c);
rcu_read_unlock();
}
void foo_update( foo* new_fp )
{
spin_lock(&foo_mutex);
foo *old_fp = gbl_foo;
gbl_foo = new_fp;
spin_unlock(&foo_mutex);
synchronize_rcu();
kfee(old_fp);
}
void foo_read(void)
{
rcu_read_lock();
foo *fp = gbl_foo;
if ( fp != NULL )
dosomething(fp->a??fp->b??fp->c);
rcu_read_unlock();
}
void foo_update( foo* new_fp )
{
spin_lock(&foo_mutex);
foo *old_fp = gbl_foo;
gbl_foo = new_fp;
spin_unlock(&foo_mutex);
synchronize_rcu();
kfee(old_fp);
}
????????foo_read????????rcu_read_lock??rcu_read_unlock??????????????????????RCU????????????????????????????????????????????foo_update?????????????synchronize_rcu()??????煤?????味?????????????????????????????????煤??????????????????????????????1??2????synchronize_rcu????????????gbl_foo?????foo_update?械?old_fp????????????????薪?????????kfee(old_fp)?????锌????????????????3??4??6??synchronize_rcu??????校???????????????????old_fp????蔚?kfee????????????????
????????????RCU????懈???????????????????????????????????????????????????睢�
????????——????????
??????????????????????????????????????CPU?????????????些????????????????????????效???????????????????????????????????????????
void foo_update( foo* new_fp )
{
spin_lock(&foo_mutex);
foo *old_fp = gbl_foo;
new_fp->a = 1;
new_fp->b = ‘b’;
new_fp->c = 100;
gbl_foo = new_fp;
spin_unlock(&foo_mutex);
synchronize_rcu();
kfee(old_fp);
}
void foo_update( foo* new_fp )
{
spin_lock(&foo_mutex);
foo *old_fp = gbl_foo;
new_fp->a = 1;
new_fp->b = ‘b’;
new_fp->c = 100;
gbl_foo = new_fp;
spin_unlock(&foo_mutex);
synchronize_rcu();
kfee(old_fp);
}
??????未????校?????????????6??7??8?械???????10?写???????小??????????????????????????????????????????锟�???????????????? new_fp????new_fp???????????????伞???????????dosomething(fp->a?? fp->b ?? fp->c ) ?? ????胁?????????????dosomething?????锌???????????????????????????????????????????????????????RCU????????????????????????????API????????????????????胁?????????????????????? :
#define rcu_assign_pointer(p?? v)
__rcu_assign_pointer((p)?? (v)?? __rcu)
#define __rcu_assign_pointer(p?? v?? space)
do {
smp_wmb();
(p) = (typeof(*v) __force space *)(v);
} while (0)
#define rcu_assign_pointer(p?? v)
__rcu_assign_pointer((p)?? (v)?? __rcu)
#define __rcu_assign_pointer(p?? v?? space)
do {
smp_wmb();
(p) = (typeof(*v) __force space *)(v);
} while (0)
????????????????????????????????????????? smp_wmb??????????????????????????????__rcu?????????????????????????????
??????DEC Alpha CPU????????????????????????????????
void foo_read(void)
{
rcu_read_lock();
foo *fp = gbl_foo;
if ( fp != NULL )
dosomething(fp->a?? fp->b ??fp->c);
rcu_read_unlock();
}
void foo_read(void)
{
rcu_read_lock();
foo *fp = gbl_foo;
if ( fp != NULL )
dosomething(fp->a?? fp->b ??fp->c);
rcu_read_unlock();
}
?????????械? fp->a??fp->b??fp->c?????3?谢????械????????卸????校???????foo_update?????械??????????鈥�???dosomething?????????????gbl_foo??????????????渭?????????????薪????????????????????RCU????????????????????
#define rcu_dereference(p) rcu_dereference_check(p?? 0)
#define rcu_dereference_check(p?? c)
__rcu_dereference_check((p)?? rcu_read_lock_held() || (c)?? __rcu)
#define __rcu_dereference_check(p?? c?? space)
({
typeof(*p) *_________p1 = (typeof(*p)*__force )ACCESS_ONCE(p);
rcu_lockdep_assert(c?? "suspicious rcu_dereference_check()"
" usage");
rcu_dereference_sparse(p?? space);
smp_read_barrier_depends();
((typeof(*p) __force __kernel *)(_________p1));
})
static inline int rcu_read_lock_held(void)
{
if (!debug_lockdep_rcu_enabled())
return 1;
if (rcu_is_cpu_idle())
return 0;
if (!rcu_lockdep_current_cpu_online())
return 0;
return lock_is_held(&rcu_lock_map);
}
#define rcu_dereference(p) rcu_dereference_check(p?? 0)
#define rcu_dereference_check(p?? c)
__rcu_dereference_check((p)?? rcu_read_lock_held() || (c)?? __rcu)
#define __rcu_dereference_check(p?? c?? space)
({
typeof(*p) *_________p1 = (typeof(*p)*__force )ACCESS_ONCE(p);
rcu_lockdep_assert(c?? "suspicious rcu_dereference_check()"
" usage");
rcu_dereference_sparse(p?? space);
smp_read_barrier_depends();
((typeof(*p) __force __kernel *)(_________p1));
})
static inline int rcu_read_lock_held(void)
{
if (!debug_lockdep_rcu_enabled())
return 1;
if (rcu_is_cpu_idle())
return 0;
if (!rcu_lockdep_current_cpu_online())
return 0;
return lock_is_held(&rcu_lock_map);
}
??????

???路???
??????????????????
2023/3/23 14:23:39???写?貌??????????
2023/3/22 16:17:39????????????????????些??
2022/6/14 16:14:27??????????????????????????
2021/10/18 15:37:44???????????????
2021/9/17 15:19:29???路???????路
2021/9/14 15:42:25?????????????
2021/5/28 17:25:47??????APP??????????
2021/5/8 17:01:11