On Mon, Jul 11, 2011 at 07:03:15AM +0100, Al Viro wrote: > * If there is an ancestor relationship: > * dentry->d_parent->...->d_parent->d_lock > * ... > * dentry->d_parent->d_lock > * dentry->d_lock > * > * If no ancestor relationship: > * if (dentry1 < dentry2) > * dentry1->d_lock > * dentry2->d_lock > > is no good: suppose A is ancestor of B and C is unrelated to either. > With B sitting at lower address than C and A at higher one. We have > A before B, since it's an ancestor; C before A since they are unrelated > and addresses compare that way; B before C (ditto). Loops in lock > ordering are generally bad; we _might_ get away with that in this case > since we serialize d_move() callers to hell and back, but... But it's not enough. Look: getting from rcu pathwalk to normal one involves * grabbing d_lock on parent * grabbing d_lock on child * checking that child hadn't been moved elsewhere in the meanwhile All flakiness of the locking "order" aside, here we simply lock two dentries that might be nowhere near each other by now. Hell, by that point the parent might've been moved under (what used to be) child. Or it might have address greater than that of child and be not an ancestor anymore. Note that no i_mutex, etc. is held at that point, so there's no external serialization to save our arses... -- To unsubscribe from this list: send the line "unsubscribe linux-fsdevel" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html