diff options
author | Christoph Hellwig <hch@infradead.org> | 2008-12-09 04:47:31 -0500 |
---|---|---|
committer | Lachlan McIlroy <lachlan@redback.melbourne.sgi.com> | 2008-12-10 21:13:52 -0500 |
commit | 2175dd95741bda5f438e4efe388a8c1bb5abf1cc (patch) | |
tree | cf861111885ed094b64d0680d4aa901c8e30cbcf | |
parent | 15ac08a8b2c129abccf1be47b6ab09491e013db2 (diff) |
[XFS] simplify projid check in xfs_rename
Check for the project ID after attaching all inodes to the transaction.
That way the unlock in the error case is done by the transaction subsystem,
which guaratees that is uses the right flags (which was wrong from day one
of this check), and avoids having special code unlocking an array of inodes
with potential duplicates. Attaching the inode first is the method used
by xfs_rename and the other namespace methods all other error that require
multiple locked inodes.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Reviewed-by: Dave Chinner <david@fromorbit.com>
Signed-off-by: Lachlan McIlroy <lachlan@sgi.com>
-rw-r--r-- | fs/xfs/xfs_rename.c | 49 |
1 files changed, 11 insertions, 38 deletions
diff --git a/fs/xfs/xfs_rename.c b/fs/xfs/xfs_rename.c index 10642fcbb1f7..86471bb40fd4 100644 --- a/fs/xfs/xfs_rename.c +++ b/fs/xfs/xfs_rename.c | |||
@@ -42,31 +42,6 @@ | |||
42 | 42 | ||
43 | 43 | ||
44 | /* | 44 | /* |
45 | * Given an array of up to 4 inode pointers, unlock the pointed to inodes. | ||
46 | * If there are fewer than 4 entries in the array, the empty entries will | ||
47 | * be at the end and will have NULL pointers in them. | ||
48 | */ | ||
49 | STATIC void | ||
50 | xfs_rename_unlock4( | ||
51 | xfs_inode_t **i_tab, | ||
52 | uint lock_mode) | ||
53 | { | ||
54 | int i; | ||
55 | |||
56 | xfs_iunlock(i_tab[0], lock_mode); | ||
57 | for (i = 1; i < 4; i++) { | ||
58 | if (i_tab[i] == NULL) | ||
59 | break; | ||
60 | |||
61 | /* | ||
62 | * Watch out for duplicate entries in the table. | ||
63 | */ | ||
64 | if (i_tab[i] != i_tab[i-1]) | ||
65 | xfs_iunlock(i_tab[i], lock_mode); | ||
66 | } | ||
67 | } | ||
68 | |||
69 | /* | ||
70 | * Enter all inodes for a rename transaction into a sorted array. | 45 | * Enter all inodes for a rename transaction into a sorted array. |
71 | */ | 46 | */ |
72 | STATIC void | 47 | STATIC void |
@@ -205,19 +180,6 @@ xfs_rename( | |||
205 | xfs_lock_inodes(inodes, num_inodes, XFS_ILOCK_EXCL); | 180 | xfs_lock_inodes(inodes, num_inodes, XFS_ILOCK_EXCL); |
206 | 181 | ||
207 | /* | 182 | /* |
208 | * If we are using project inheritance, we only allow renames | ||
209 | * into our tree when the project IDs are the same; else the | ||
210 | * tree quota mechanism would be circumvented. | ||
211 | */ | ||
212 | if (unlikely((target_dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) && | ||
213 | (target_dp->i_d.di_projid != src_ip->i_d.di_projid))) { | ||
214 | error = XFS_ERROR(EXDEV); | ||
215 | xfs_rename_unlock4(inodes, XFS_ILOCK_EXCL); | ||
216 | xfs_trans_cancel(tp, cancel_flags); | ||
217 | goto std_return; | ||
218 | } | ||
219 | |||
220 | /* | ||
221 | * Join all the inodes to the transaction. From this point on, | 183 | * Join all the inodes to the transaction. From this point on, |
222 | * we can rely on either trans_commit or trans_cancel to unlock | 184 | * we can rely on either trans_commit or trans_cancel to unlock |
223 | * them. Note that we need to add a vnode reference to the | 185 | * them. Note that we need to add a vnode reference to the |
@@ -242,6 +204,17 @@ xfs_rename( | |||
242 | } | 204 | } |
243 | 205 | ||
244 | /* | 206 | /* |
207 | * If we are using project inheritance, we only allow renames | ||
208 | * into our tree when the project IDs are the same; else the | ||
209 | * tree quota mechanism would be circumvented. | ||
210 | */ | ||
211 | if (unlikely((target_dp->i_d.di_flags & XFS_DIFLAG_PROJINHERIT) && | ||
212 | (target_dp->i_d.di_projid != src_ip->i_d.di_projid))) { | ||
213 | error = XFS_ERROR(EXDEV); | ||
214 | goto error_return; | ||
215 | } | ||
216 | |||
217 | /* | ||
245 | * Set up the target. | 218 | * Set up the target. |
246 | */ | 219 | */ |
247 | if (target_ip == NULL) { | 220 | if (target_ip == NULL) { |