On Tue, Jun 10, 2008 at 12:14:27PM +0200, Louis Rilling wrote:
Nope, because you may have live objects below you - the rmdir
should fail, and nothing should change. Sure, you could put it back,
but in the middle there is a period where another process tries to look
at the tree and gets ENOENT. That's not right.
But blocking lookup another way might work. If we keep that
rename process out of looking up its targets (blocked on a lock we hold)
it might work.
Note, btw, that the create side (populate_groups) is safe,
because we hold the creating parent's i_mutex throughout the entire
process.
Hey, can we use d_revalidate? Here's the issue. rename, when
going to lookup the objects it wants to lock, is getting them out of
cached_lookup - there dcache locking is all that protects it. I was
first thinking we could take the dentry locks to block this out. But
rather, why not fail d_revalidate and force a locked lookup? So, when
we go to lock one of these groups for detaching, we also set a flag on
the configfs_dirent. We add a configfs_d_revalidate function that
returns based on that flag - if set, revalidation is needed. Thus, when
another process comes in to look at the object we've already locked, it
blocks waiting to find it.
See, in do_rename, it does do_path_lookup() before actually
calling lock_rename(). It would block there waiting for our speculative
removal. We'd either fail rmdir, and those lookups would succeed, or
we'd succeed rmdir, and the lookup fails.
The only concern is, can the reverse happen? We get past the
lookups in do_rename(), and then another process comes into rmdir() -
will they deadlock there?
Joel
--
Life's Little Instruction Book #267
"Lie on your back and look at the stars."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
--