diff options
Diffstat (limited to 'fs/xfs/xfs_trans_inode.c')
-rw-r--r-- | fs/xfs/xfs_trans_inode.c | 86 |
1 files changed, 5 insertions, 81 deletions
diff --git a/fs/xfs/xfs_trans_inode.c b/fs/xfs/xfs_trans_inode.c index 23d276af2e0c..785ff101da0a 100644 --- a/fs/xfs/xfs_trans_inode.c +++ b/fs/xfs/xfs_trans_inode.c | |||
@@ -49,30 +49,7 @@ xfs_trans_inode_broot_debug( | |||
49 | 49 | ||
50 | 50 | ||
51 | /* | 51 | /* |
52 | * Get and lock the inode for the caller if it is not already | 52 | * Get an inode and join it to the transaction. |
53 | * locked within the given transaction. If it is already locked | ||
54 | * within the transaction, just increment its lock recursion count | ||
55 | * and return a pointer to it. | ||
56 | * | ||
57 | * For an inode to be locked in a transaction, the inode lock, as | ||
58 | * opposed to the io lock, must be taken exclusively. This ensures | ||
59 | * that the inode can be involved in only 1 transaction at a time. | ||
60 | * Lock recursion is handled on the io lock, but only for lock modes | ||
61 | * of equal or lesser strength. That is, you can recur on the io lock | ||
62 | * held EXCL with a SHARED request but not vice versa. Also, if | ||
63 | * the inode is already a part of the transaction then you cannot | ||
64 | * go from not holding the io lock to having it EXCL or SHARED. | ||
65 | * | ||
66 | * Use the inode cache routine xfs_inode_incore() to find the inode | ||
67 | * if it is already owned by this transaction. | ||
68 | * | ||
69 | * If we don't already own the inode, use xfs_iget() to get it. | ||
70 | * Since the inode log item structure is embedded in the incore | ||
71 | * inode structure and is initialized when the inode is brought | ||
72 | * into memory, there is nothing to do with it here. | ||
73 | * | ||
74 | * If the given transaction pointer is NULL, just call xfs_iget(). | ||
75 | * This simplifies code which must handle both cases. | ||
76 | */ | 53 | */ |
77 | int | 54 | int |
78 | xfs_trans_iget( | 55 | xfs_trans_iget( |
@@ -84,62 +61,11 @@ xfs_trans_iget( | |||
84 | xfs_inode_t **ipp) | 61 | xfs_inode_t **ipp) |
85 | { | 62 | { |
86 | int error; | 63 | int error; |
87 | xfs_inode_t *ip; | ||
88 | |||
89 | /* | ||
90 | * If the transaction pointer is NULL, just call the normal | ||
91 | * xfs_iget(). | ||
92 | */ | ||
93 | if (tp == NULL) | ||
94 | return xfs_iget(mp, NULL, ino, flags, lock_flags, ipp, 0); | ||
95 | |||
96 | /* | ||
97 | * If we find the inode in core with this transaction | ||
98 | * pointer in its i_transp field, then we know we already | ||
99 | * have it locked. In this case we just increment the lock | ||
100 | * recursion count and return the inode to the caller. | ||
101 | * Assert that the inode is already locked in the mode requested | ||
102 | * by the caller. We cannot do lock promotions yet, so | ||
103 | * die if someone gets this wrong. | ||
104 | */ | ||
105 | if ((ip = xfs_inode_incore(tp->t_mountp, ino, tp)) != NULL) { | ||
106 | /* | ||
107 | * Make sure that the inode lock is held EXCL and | ||
108 | * that the io lock is never upgraded when the inode | ||
109 | * is already a part of the transaction. | ||
110 | */ | ||
111 | ASSERT(ip->i_itemp != NULL); | ||
112 | ASSERT(lock_flags & XFS_ILOCK_EXCL); | ||
113 | ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL)); | ||
114 | ASSERT((!(lock_flags & XFS_IOLOCK_EXCL)) || | ||
115 | xfs_isilocked(ip, XFS_IOLOCK_EXCL)); | ||
116 | ASSERT((!(lock_flags & XFS_IOLOCK_EXCL)) || | ||
117 | (ip->i_itemp->ili_flags & XFS_ILI_IOLOCKED_EXCL)); | ||
118 | ASSERT((!(lock_flags & XFS_IOLOCK_SHARED)) || | ||
119 | xfs_isilocked(ip, XFS_IOLOCK_EXCL|XFS_IOLOCK_SHARED)); | ||
120 | ASSERT((!(lock_flags & XFS_IOLOCK_SHARED)) || | ||
121 | (ip->i_itemp->ili_flags & XFS_ILI_IOLOCKED_ANY)); | ||
122 | |||
123 | if (lock_flags & (XFS_IOLOCK_SHARED | XFS_IOLOCK_EXCL)) { | ||
124 | ip->i_itemp->ili_iolock_recur++; | ||
125 | } | ||
126 | if (lock_flags & XFS_ILOCK_EXCL) { | ||
127 | ip->i_itemp->ili_ilock_recur++; | ||
128 | } | ||
129 | *ipp = ip; | ||
130 | return 0; | ||
131 | } | ||
132 | |||
133 | ASSERT(lock_flags & XFS_ILOCK_EXCL); | ||
134 | error = xfs_iget(tp->t_mountp, tp, ino, flags, lock_flags, &ip, 0); | ||
135 | if (error) { | ||
136 | return error; | ||
137 | } | ||
138 | ASSERT(ip != NULL); | ||
139 | 64 | ||
140 | xfs_trans_ijoin(tp, ip, lock_flags); | 65 | error = xfs_iget(mp, tp, ino, flags, lock_flags, ipp, 0); |
141 | *ipp = ip; | 66 | if (!error && tp) |
142 | return 0; | 67 | xfs_trans_ijoin(tp, *ipp, lock_flags); |
68 | return error; | ||
143 | } | 69 | } |
144 | 70 | ||
145 | /* | 71 | /* |
@@ -163,8 +89,6 @@ xfs_trans_ijoin( | |||
163 | xfs_inode_item_init(ip, ip->i_mount); | 89 | xfs_inode_item_init(ip, ip->i_mount); |
164 | iip = ip->i_itemp; | 90 | iip = ip->i_itemp; |
165 | ASSERT(iip->ili_flags == 0); | 91 | ASSERT(iip->ili_flags == 0); |
166 | ASSERT(iip->ili_ilock_recur == 0); | ||
167 | ASSERT(iip->ili_iolock_recur == 0); | ||
168 | 92 | ||
169 | /* | 93 | /* |
170 | * Get a log_item_desc to point at the new item. | 94 | * Get a log_item_desc to point at the new item. |