On Mon, Sep 02, 2019 at 11:51:34PM -0500, Eric W. Biederman wrote: > > Add a count of the number of rcu users (currently 1) of the task > struct so that we can later add the scheduler case and get rid of the > very subtle task_rcu_dereference, and just use rcu_dereference. > > As suggested by Oleg have the count overlap rcu_head so that no > additional space in task_struct is required. > > Inspired-by: Linus Torvalds <torva...@linux-foundation.org> > Inspired-by: Oleg Nesterov <o...@redhat.com> > Signed-off-by: "Eric W. Biederman" <ebied...@xmission.com> > --- > include/linux/sched.h | 5 ++++- > include/linux/sched/task.h | 1 + > kernel/exit.c | 7 ++++++- > kernel/fork.c | 7 +++---- > 4 files changed, 14 insertions(+), 6 deletions(-) > > diff --git a/include/linux/sched.h b/include/linux/sched.h > index 9f51932bd543..99a4518b9b17 100644 > --- a/include/linux/sched.h > +++ b/include/linux/sched.h > @@ -1142,7 +1142,10 @@ struct task_struct { > > struct tlbflush_unmap_batch tlb_ubc; > > - struct rcu_head rcu; > + union { > + refcount_t rcu_users; > + struct rcu_head rcu;
So what happens if, say: CPU 1 CPU 2 -------------------------------------------------------------- rcu_read_lock() p = rcu_dereference(rq->task) if (refcount_inc_not_zero(p->rcu_users)) { ..... release_task() { put_task_struct_rcu_user() { call_rcu() { queue rcu_head } } } put_task_struct_rcu_user(); //here rcu_users has been overwritten Thanks.