1 Index: linux-2.4.21/fs/ext3/namei.c
2 ===================================================================
3 --- linux-2.4.21.orig/fs/ext3/namei.c 2006-04-29 20:48:26.000000000 +0400
4 +++ linux-2.4.21/fs/ext3/namei.c 2006-05-06 01:31:51.000000000 +0400
5 @@ -955,6 +955,38 @@ static struct dentry *ext3_lookup(struct
9 + /* ".." shouldn't go into dcache to preserve dcache hierarchy
10 + * otherwise we'll get parent being a child of actual child.
11 + * see bug 10458 for details -bzzz */
12 + if (inode && (dentry->d_name.name[0] == '.' && (dentry->d_name.len == 1 ||
13 + (dentry->d_name.len == 2 && dentry->d_name.name[1] == '.')))) {
14 + struct dentry *tmp, *goal = NULL;
15 + struct list_head *lp;
17 + /* first, look for an existing dentry - any one is good */
18 + spin_lock(&dcache_lock);
19 + list_for_each(lp, &inode->i_dentry) {
20 + tmp = list_entry(lp, struct dentry, d_alias);
26 + /* there is no alias, we need to make current dentry:
27 + * a) inaccessible for __d_lookup()
28 + * b) inaccessible for iopen */
29 + J_ASSERT(list_empty(&dentry->d_alias));
30 + dentry->d_flags |= DCACHE_NFSFS_RENAMED;
31 + /* this is d_instantiate() ... */
32 + list_add(&dentry->d_alias, &inode->i_dentry);
33 + dentry->d_inode = inode;
35 + spin_unlock(&dcache_lock);
41 return iopen_connect_dentry(dentry, inode, 1);
44 Index: linux-2.4.21/fs/ext3/iopen.c
45 ===================================================================
46 --- linux-2.4.21.orig/fs/ext3/iopen.c 2006-04-29 20:48:23.000000000 +0400
47 +++ linux-2.4.21/fs/ext3/iopen.c 2006-04-29 20:59:50.000000000 +0400
48 @@ -92,9 +92,12 @@ static struct dentry *iopen_lookup(struc
49 assert(!(alternate->d_flags & DCACHE_NFSD_DISCONNECTED));
52 - if (!list_empty(&inode->i_dentry)) {
53 - alternate = list_entry(inode->i_dentry.next,
54 - struct dentry, d_alias);
55 + list_for_each(lp, &inode->i_dentry) {
56 + alternate = list_entry(lp, struct dentry, d_alias);
57 + /* ignore dentries created for ".." to preserve
58 + * proper dcache hierarchy -- bug 10458 */
59 + if (alternate->d_flags & DCACHE_NFSFS_RENAMED)
61 dget_locked(alternate);
62 alternate->d_vfs_flags |= DCACHE_REFERENCED;