Andrew Morton wrote: > On Tue, 18 Sep 2007 13:17:28 +0400 Alexey Dobriyan wrote: > > >>I'm getting tons of this, and X fails to start >> >>CONFIG_SYSVIPC=y >>CONFIG_SYSVIPC_SYSCTL=y >># CONFIG_PREEMPT_NONE is not set >># CONFIG_PREEMPT_VOLUNTARY is not set >>CONFIG_PREEMPT=y >>CONFIG_PREEMPT_BKL=y >>CONFIG_DEBUG_PREEMPT=y >> >>BUG: sleeping function called from invalid context at kernel/rwsem.c:47 >>in_atomic():1, irqs_disabled():0 > > > OK, this fixes the locking here: > > --- a/ipc/util.c~ipc-integrate-ipc_checkid-into-ipc_lock-fix-2 > +++ a/ipc/util.c > @@ -295,7 +295,6 @@ int ipc_addid(struct ipc_ids* ids, struc > > spin_lock_init(&new->lock); > new->deleted = 0; > - rcu_read_lock(); > spin_lock(&new->lock); > return id; > } > @@ -691,7 +690,7 @@ struct kern_ipc_perm *ipc_lock(struct ip > rcu_read_unlock(); > return ERR_PTR(-EINVAL); > } > - > + rcu_read_unlock(); > return out; > } > Well, reviewing the code I found another place where the rcu_read_unlock() was missing. I'm so sorry for the inconvenience. It's true that I should have tested with CONFIG_PREEMPT=y :-( Now, the ltp tests pass even with this option set... In attachment you'll find a patch thhat 1) adds the missing rcu_read_unlock() 2) replaces Andrew's fix with a new one: the rcu_read_lock() is now taken in ipc_lock() / ipc_lock_by_ptr() and released in ipc_unlock(), exactly as it was done in the ref code. Regards, Nadia