Whamcloud - gitweb
b=20298 (Merge head ldiskfs and b1_8 ldiskfs)
[fs/lustre-release.git] / ldiskfs / kernel_patches / patches / ext3-nlinks-2.6.9.patch
1 Index: linux-2.6.12/fs/ext3/namei.c
2 ===================================================================
3 --- linux-2.6.12.orig/fs/ext3/namei.c
4 +++ linux-2.6.12/fs/ext3/namei.c
5 @@ -1600,11 +1600,17 @@ static int ext3_delete_entry (handle_t *
6  static inline void ext3_inc_count(handle_t *handle, struct inode *inode)
7  {
8         inode->i_nlink++;
9 +       if (is_dx(inode) && inode->i_nlink > 1) {
10 +               /* limit is 16-bit i_links_count */
11 +               if (inode->i_nlink >= EXT3_LINK_MAX || inode->i_nlink == 2)
12 +                       inode->i_nlink = 1;
13 +       }
14  }
15  
16  static inline void ext3_dec_count(handle_t *handle, struct inode *inode)
17  {
18 -       inode->i_nlink--;
19 +       if (!S_ISDIR(inode->i_mode) || inode->i_nlink > 2)
20 +               inode->i_nlink--;
21  }
22  
23  static int ext3_add_nondir(handle_t *handle,
24 @@ -1703,7 +1709,7 @@ static int ext3_mkdir(struct inode * dir
25         struct ext3_dir_entry_2 * de;
26         int err, retries = 0;
27  
28 -       if (dir->i_nlink >= EXT3_LINK_MAX)
29 +       if (EXT3_DIR_LINK_MAX(dir))
30                 return -EMLINK;
31  
32  retry:
33 @@ -1782,7 +1793,7 @@ retry:
34         inode->i_size = EXT3_I(inode)->i_disksize = inode->i_sb->s_blocksize;
35         dir_block = ext3_bread (handle, inode, 0, 1, &err);
36         if (!dir_block) {
37 -               inode->i_nlink--; /* is this nlink == 0? */
38 +               drop_nlink(inode); /* is this nlink == 0? */
39                 ext3_mark_inode_dirty(handle, inode);
40                 iput (inode);
41                 goto out_stop;
42 @@ -1758,7 +1764,7 @@ retry:
43                 iput (inode);
44                 goto out_stop;
45         }
46 -       dir->i_nlink++;
47 +       ext3_inc_count(handle, dir);
48         ext3_update_dx_flag(dir);
49         ext3_mark_inode_dirty(handle, dir);
50         d_instantiate(dentry, inode);
51 @@ -2023,10 +2029,10 @@ static int ext3_rmdir (struct inode * di
52         retval = ext3_delete_entry(handle, dir, de, bh);
53         if (retval)
54                 goto end_rmdir;
55 -       if (inode->i_nlink != 2)
56 -               ext3_warning (inode->i_sb, "ext3_rmdir",
57 -                             "empty directory has nlink!=2 (%d)",
58 -                             inode->i_nlink);
59 +       if (!EXT3_DIR_LINK_EMPTY(inode))
60 +               ext3_warning(inode->i_sb, "ext3_rmdir",
61 +                            "empty directory has too many links (%d)",
62 +                            inode->i_nlink);
63         inode->i_version++;
64         inode->i_nlink = 0;
65         /* There's no need to set i_disksize: the fact that i_nlink is
66 @@ -2036,7 +2042,7 @@ static int ext3_rmdir (struct inode * di
67         ext3_orphan_add(handle, inode);
68         inode->i_ctime = dir->i_ctime = dir->i_mtime = CURRENT_TIME_SEC;
69         ext3_mark_inode_dirty(handle, inode);
70 -       dir->i_nlink--;
71 +       ext3_dec_count(handle, dir);
72         ext3_update_dx_flag(dir);
73         ext3_mark_inode_dirty(handle, dir);
74  
75 @@ -2087,7 +2093,7 @@ static int ext3_unlink(struct inode * di
76         dir->i_ctime = dir->i_mtime = CURRENT_TIME_SEC;
77         ext3_update_dx_flag(dir);
78         ext3_mark_inode_dirty(handle, dir);
79 -       inode->i_nlink--;
80 +       ext3_dec_count(handle, inode);
81         if (!inode->i_nlink)
82                 ext3_orphan_add(handle, inode);
83         inode->i_ctime = dir->i_ctime;
84 @@ -2162,7 +2168,7 @@ static int ext3_link (struct dentry * ol
85         struct inode *inode = old_dentry->d_inode;
86         int err, retries = 0;
87  
88 -       if (inode->i_nlink >= EXT3_LINK_MAX)
89 +       if (EXT3_DIR_LINK_MAX(inode))
90                 return -EMLINK;
91  
92  retry:
93 @@ -2249,8 +2255,8 @@ static int ext3_rename (struct inode * o
94                 if (le32_to_cpu(PARENT_INO(dir_bh->b_data)) != old_dir->i_ino)
95                         goto end_rename;
96                 retval = -EMLINK;
97 -               if (!new_inode && new_dir!=old_dir &&
98 -                               new_dir->i_nlink >= EXT3_LINK_MAX)
99 +               if (!new_inode && new_dir != old_dir &&
100 +                   EXT3_DIR_LINK_MAX(new_dir))
101                         goto end_rename;
102         }
103         if (!new_bh) {
104 @@ -2307,7 +2313,7 @@ static int ext3_rename (struct inode * o
105         }
106  
107         if (new_inode) {
108 -               new_inode->i_nlink--;
109 +               ext3_dec_count(handle, new_inode);
110                 new_inode->i_ctime = CURRENT_TIME_SEC;
111         }
112         old_dir->i_ctime = old_dir->i_mtime = CURRENT_TIME_SEC;
113 @@ -2318,11 +2324,13 @@ static int ext3_rename (struct inode * o
114                 PARENT_INO(dir_bh->b_data) = cpu_to_le32(new_dir->i_ino);
115                 BUFFER_TRACE(dir_bh, "call ext3_journal_dirty_metadata");
116                 ext3_journal_dirty_metadata(handle, dir_bh);
117 -               old_dir->i_nlink--;
118 +               ext3_dec_count(handle, old_dir);
119                 if (new_inode) {
120 -                       new_inode->i_nlink--;
121 +                       /* checked empty_dir above, can't have another parent,
122 +                        * ext3_dec_count() won't work for many-linked dirs */
123 +                       new_inode->i_nlink = 0;
124                 } else {
125 -                       new_dir->i_nlink++;
126 +                       ext3_inc_count(handle, new_dir);
127                         ext3_update_dx_flag(new_dir);
128                         ext3_mark_inode_dirty(handle, new_dir);
129                 }
130 Index: linux-2.6.12/include/linux/ext3_fs.h
131 ===================================================================
132 --- linux-2.6.12.orig/include/linux/ext3_fs.h
133 +++ linux-2.6.12/include/linux/ext3_fs.h
134 @@ -78,7 +78,7 @@ struct statfs;
135  /*
136   * Maximal count of links to a file
137   */
138 -#define EXT3_LINK_MAX          32000
139 +#define EXT3_LINK_MAX          65000
140  
141  /*
142   * Macro-instructions used to manage several block sizes
143 @@ -539,6 +539,7 @@ static inline struct ext3_inode_info *EX
144  #define EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER    0x0001
145  #define EXT3_FEATURE_RO_COMPAT_LARGE_FILE      0x0002
146  #define EXT3_FEATURE_RO_COMPAT_BTREE_DIR       0x0004
147 +#define EXT4_FEATURE_RO_COMPAT_DIR_NLINK       0x0020
148  
149  #define EXT3_FEATURE_INCOMPAT_COMPRESSION      0x0001
150  #define EXT3_FEATURE_INCOMPAT_FILETYPE         0x0002
151 @@ -552,6 +553,7 @@ static inline struct ext3_inode_info *EX
152                                          EXT3_FEATURE_INCOMPAT_META_BG)
153  #define EXT3_FEATURE_RO_COMPAT_SUPP    (EXT3_FEATURE_RO_COMPAT_SPARSE_SUPER| \
154                                          EXT3_FEATURE_RO_COMPAT_LARGE_FILE| \
155 +                                        EXT4_FEATURE_RO_COMPAT_DIR_NLINK| \
156                                          EXT3_FEATURE_RO_COMPAT_BTREE_DIR)
157  
158  /*