Skip to content

Commit 253f491

Browse files
Christoph Hellwigdchinner
authored andcommitted
xfs: better xfs_trans_alloc interface
Merge xfs_trans_reserve and xfs_trans_alloc into a single function call that returns a transaction with all the required log and block reservations, and which allows passing transaction flags directly to avoid the cumbersome _xfs_trans_alloc interface. While we're at it we also get rid of the transaction type argument that has been superflous since we stopped supporting the non-CIL logging mode. The guts of it will be removed in another patch. [dchinner: fixed transaction leak in error path in xfs_setattr_nonsize] Signed-off-by: Christoph Hellwig <[email protected]> Reviewed-by: Dave Chinner <[email protected]> Signed-off-by: Dave Chinner <[email protected]>
1 parent f55532a commit 253f491

22 files changed

+191
-347
lines changed

fs/xfs/libxfs/xfs_attr.c

Lines changed: 13 additions & 45 deletions
Original file line numberDiff line numberDiff line change
@@ -242,37 +242,21 @@ xfs_attr_set(
242242
return error;
243243
}
244244

245-
/*
246-
* Start our first transaction of the day.
247-
*
248-
* All future transactions during this code must be "chained" off
249-
* this one via the trans_dup() call. All transactions will contain
250-
* the inode, and the inode will always be marked with trans_ihold().
251-
* Since the inode will be locked in all transactions, we must log
252-
* the inode in every transaction to let it float upward through
253-
* the log.
254-
*/
255-
args.trans = xfs_trans_alloc(mp, XFS_TRANS_ATTR_SET);
245+
tres.tr_logres = M_RES(mp)->tr_attrsetm.tr_logres +
246+
M_RES(mp)->tr_attrsetrt.tr_logres * args.total;
247+
tres.tr_logcount = XFS_ATTRSET_LOG_COUNT;
248+
tres.tr_logflags = XFS_TRANS_PERM_LOG_RES;
256249

257250
/*
258251
* Root fork attributes can use reserved data blocks for this
259252
* operation if necessary
260253
*/
261-
262-
if (rsvd)
263-
args.trans->t_flags |= XFS_TRANS_RESERVE;
264-
265-
tres.tr_logres = M_RES(mp)->tr_attrsetm.tr_logres +
266-
M_RES(mp)->tr_attrsetrt.tr_logres * args.total;
267-
tres.tr_logcount = XFS_ATTRSET_LOG_COUNT;
268-
tres.tr_logflags = XFS_TRANS_PERM_LOG_RES;
269-
error = xfs_trans_reserve(args.trans, &tres, args.total, 0);
270-
if (error) {
271-
xfs_trans_cancel(args.trans);
254+
error = xfs_trans_alloc(mp, &tres, args.total, 0,
255+
rsvd ? XFS_TRANS_RESERVE : 0, &args.trans);
256+
if (error)
272257
return error;
273-
}
274-
xfs_ilock(dp, XFS_ILOCK_EXCL);
275258

259+
xfs_ilock(dp, XFS_ILOCK_EXCL);
276260
error = xfs_trans_reserve_quota_nblks(args.trans, dp, args.total, 0,
277261
rsvd ? XFS_QMOPT_RES_REGBLKS | XFS_QMOPT_FORCE_RES :
278262
XFS_QMOPT_RES_REGBLKS);
@@ -428,32 +412,16 @@ xfs_attr_remove(
428412
if (error)
429413
return error;
430414

431-
/*
432-
* Start our first transaction of the day.
433-
*
434-
* All future transactions during this code must be "chained" off
435-
* this one via the trans_dup() call. All transactions will contain
436-
* the inode, and the inode will always be marked with trans_ihold().
437-
* Since the inode will be locked in all transactions, we must log
438-
* the inode in every transaction to let it float upward through
439-
* the log.
440-
*/
441-
args.trans = xfs_trans_alloc(mp, XFS_TRANS_ATTR_RM);
442-
443415
/*
444416
* Root fork attributes can use reserved data blocks for this
445417
* operation if necessary
446418
*/
447-
448-
if (flags & ATTR_ROOT)
449-
args.trans->t_flags |= XFS_TRANS_RESERVE;
450-
451-
error = xfs_trans_reserve(args.trans, &M_RES(mp)->tr_attrrm,
452-
XFS_ATTRRM_SPACE_RES(mp), 0);
453-
if (error) {
454-
xfs_trans_cancel(args.trans);
419+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_attrrm,
420+
XFS_ATTRRM_SPACE_RES(mp), 0,
421+
(flags & ATTR_ROOT) ? XFS_TRANS_RESERVE : 0,
422+
&args.trans);
423+
if (error)
455424
return error;
456-
}
457425

458426
xfs_ilock(dp, XFS_ILOCK_EXCL);
459427
/*

fs/xfs/libxfs/xfs_bmap.c

Lines changed: 9 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1121,15 +1121,14 @@ xfs_bmap_add_attrfork(
11211121

11221122
mp = ip->i_mount;
11231123
ASSERT(!XFS_NOT_DQATTACHED(mp, ip));
1124-
tp = xfs_trans_alloc(mp, XFS_TRANS_ADDAFORK);
1124+
11251125
blks = XFS_ADDAFORK_SPACE_RES(mp);
1126-
if (rsvd)
1127-
tp->t_flags |= XFS_TRANS_RESERVE;
1128-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_addafork, blks, 0);
1129-
if (error) {
1130-
xfs_trans_cancel(tp);
1126+
1127+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_addafork, blks, 0,
1128+
rsvd ? XFS_TRANS_RESERVE : 0, &tp);
1129+
if (error)
11311130
return error;
1132-
}
1131+
11331132
xfs_ilock(ip, XFS_ILOCK_EXCL);
11341133
error = xfs_trans_reserve_quota_nblks(tp, ip, blks, 0, rsvd ?
11351134
XFS_QMOPT_RES_REGBLKS | XFS_QMOPT_FORCE_RES :
@@ -6026,13 +6025,10 @@ xfs_bmap_split_extent(
60266025
xfs_fsblock_t firstfsb;
60276026
int error;
60286027

6029-
tp = xfs_trans_alloc(mp, XFS_TRANS_DIOSTRAT);
6030-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_write,
6031-
XFS_DIOSTRAT_SPACE_RES(mp, 0), 0);
6032-
if (error) {
6033-
xfs_trans_cancel(tp);
6028+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_write,
6029+
XFS_DIOSTRAT_SPACE_RES(mp, 0), 0, 0, &tp);
6030+
if (error)
60346031
return error;
6035-
}
60366032

60376033
xfs_ilock(ip, XFS_ILOCK_EXCL);
60386034
xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL);

fs/xfs/libxfs/xfs_sb.c

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -838,12 +838,10 @@ xfs_sync_sb(
838838
struct xfs_trans *tp;
839839
int error;
840840

841-
tp = _xfs_trans_alloc(mp, XFS_TRANS_SB_CHANGE, KM_SLEEP);
842-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_sb, 0, 0);
843-
if (error) {
844-
xfs_trans_cancel(tp);
841+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_sb, 0, 0,
842+
XFS_TRANS_NO_WRITECOUNT, &tp);
843+
if (error)
845844
return error;
846-
}
847845

848846
xfs_log_sb(tp);
849847
if (wait)

fs/xfs/libxfs/xfs_shared.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -181,8 +181,9 @@ int xfs_log_calc_minimum_size(struct xfs_mount *);
181181
#define XFS_TRANS_SYNC 0x08 /* make commit synchronous */
182182
#define XFS_TRANS_DQ_DIRTY 0x10 /* at least one dquot in trx dirty */
183183
#define XFS_TRANS_RESERVE 0x20 /* OK to use reserved data blocks */
184-
#define XFS_TRANS_FREEZE_PROT 0x40 /* Transaction has elevated writer
185-
count in superblock */
184+
#define XFS_TRANS_NO_WRITECOUNT 0x40 /* do not elevate SB writecount */
185+
#define XFS_TRANS_NOFS 0x80 /* pass KM_NOFS to kmem_alloc */
186+
186187
/*
187188
* Field values for xfs_trans_mod_sb.
188189
*/

fs/xfs/xfs_aops.c

Lines changed: 6 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -120,13 +120,9 @@ xfs_setfilesize_trans_alloc(
120120
struct xfs_trans *tp;
121121
int error;
122122

123-
tp = xfs_trans_alloc(mp, XFS_TRANS_FSYNC_TS);
124-
125-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_fsyncts, 0, 0);
126-
if (error) {
127-
xfs_trans_cancel(tp);
123+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_fsyncts, 0, 0, 0, &tp);
124+
if (error)
128125
return error;
129-
}
130126

131127
ioend->io_append_trans = tp;
132128

@@ -1391,13 +1387,10 @@ xfs_end_io_direct_write(
13911387

13921388
trace_xfs_end_io_direct_write_append(ip, offset, size);
13931389

1394-
tp = xfs_trans_alloc(mp, XFS_TRANS_FSYNC_TS);
1395-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_fsyncts, 0, 0);
1396-
if (error) {
1397-
xfs_trans_cancel(tp);
1398-
return error;
1399-
}
1400-
error = xfs_setfilesize(ip, tp, offset, size);
1390+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_fsyncts, 0, 0, 0,
1391+
&tp);
1392+
if (!error)
1393+
error = xfs_setfilesize(ip, tp, offset, size);
14011394
}
14021395

14031396
return error;

fs/xfs/xfs_attr_inactive.c

Lines changed: 3 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -405,21 +405,11 @@ xfs_attr_inactive(
405405
goto out_destroy_fork;
406406
xfs_iunlock(dp, lock_mode);
407407

408-
/*
409-
* Start our first transaction of the day.
410-
*
411-
* All future transactions during this code must be "chained" off
412-
* this one via the trans_dup() call. All transactions will contain
413-
* the inode, and the inode will always be marked with trans_ihold().
414-
* Since the inode will be locked in all transactions, we must log
415-
* the inode in every transaction to let it float upward through
416-
* the log.
417-
*/
418408
lock_mode = 0;
419-
trans = xfs_trans_alloc(mp, XFS_TRANS_ATTRINVAL);
420-
error = xfs_trans_reserve(trans, &M_RES(mp)->tr_attrinval, 0, 0);
409+
410+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_attrinval, 0, 0, 0, &trans);
421411
if (error)
422-
goto out_cancel;
412+
goto out_destroy_fork;
423413

424414
lock_mode = XFS_ILOCK_EXCL;
425415
xfs_ilock(dp, lock_mode);

fs/xfs/xfs_bmap_util.c

Lines changed: 13 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -900,19 +900,15 @@ xfs_free_eofblocks(
900900
* Free them up now by truncating the file to
901901
* its current size.
902902
*/
903-
tp = xfs_trans_alloc(mp, XFS_TRANS_INACTIVE);
904-
905903
if (need_iolock) {
906-
if (!xfs_ilock_nowait(ip, XFS_IOLOCK_EXCL)) {
907-
xfs_trans_cancel(tp);
904+
if (!xfs_ilock_nowait(ip, XFS_IOLOCK_EXCL))
908905
return -EAGAIN;
909-
}
910906
}
911907

912-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_itruncate, 0, 0);
908+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_itruncate, 0, 0, 0,
909+
&tp);
913910
if (error) {
914911
ASSERT(XFS_FORCED_SHUTDOWN(mp));
915-
xfs_trans_cancel(tp);
916912
if (need_iolock)
917913
xfs_iunlock(ip, XFS_IOLOCK_EXCL);
918914
return error;
@@ -1037,9 +1033,9 @@ xfs_alloc_file_space(
10371033
/*
10381034
* Allocate and setup the transaction.
10391035
*/
1040-
tp = xfs_trans_alloc(mp, XFS_TRANS_DIOSTRAT);
1041-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_write,
1042-
resblks, resrtextents);
1036+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_write, resblks,
1037+
resrtextents, 0, &tp);
1038+
10431039
/*
10441040
* Check for running out of space
10451041
*/
@@ -1048,7 +1044,6 @@ xfs_alloc_file_space(
10481044
* Free the transaction structure.
10491045
*/
10501046
ASSERT(error == -ENOSPC || XFS_FORCED_SHUTDOWN(mp));
1051-
xfs_trans_cancel(tp);
10521047
break;
10531048
}
10541049
xfs_ilock(ip, XFS_ILOCK_EXCL);
@@ -1311,18 +1306,10 @@ xfs_free_file_space(
13111306
* transaction to dip into the reserve blocks to ensure
13121307
* the freeing of the space succeeds at ENOSPC.
13131308
*/
1314-
tp = xfs_trans_alloc(mp, XFS_TRANS_DIOSTRAT);
1315-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_write, resblks, 0);
1316-
1317-
/*
1318-
* check for running out of space
1319-
*/
1309+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_write, resblks, 0, 0,
1310+
&tp);
13201311
if (error) {
1321-
/*
1322-
* Free the transaction structure.
1323-
*/
13241312
ASSERT(error == -ENOSPC || XFS_FORCED_SHUTDOWN(mp));
1325-
xfs_trans_cancel(tp);
13261313
break;
13271314
}
13281315
xfs_ilock(ip, XFS_ILOCK_EXCL);
@@ -1482,19 +1469,16 @@ xfs_shift_file_space(
14821469
}
14831470

14841471
while (!error && !done) {
1485-
tp = xfs_trans_alloc(mp, XFS_TRANS_DIOSTRAT);
14861472
/*
14871473
* We would need to reserve permanent block for transaction.
14881474
* This will come into picture when after shifting extent into
14891475
* hole we found that adjacent extents can be merged which
14901476
* may lead to freeing of a block during record update.
14911477
*/
1492-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_write,
1493-
XFS_DIOSTRAT_SPACE_RES(mp, 0), 0);
1494-
if (error) {
1495-
xfs_trans_cancel(tp);
1478+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_write,
1479+
XFS_DIOSTRAT_SPACE_RES(mp, 0), 0, 0, &tp);
1480+
if (error)
14961481
break;
1497-
}
14981482

14991483
xfs_ilock(ip, XFS_ILOCK_EXCL);
15001484
error = xfs_trans_reserve_quota(tp, mp, ip->i_udquot,
@@ -1747,12 +1731,9 @@ xfs_swap_extents(
17471731
if (error)
17481732
goto out_unlock;
17491733

1750-
tp = xfs_trans_alloc(mp, XFS_TRANS_SWAPEXT);
1751-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_ichange, 0, 0);
1752-
if (error) {
1753-
xfs_trans_cancel(tp);
1734+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_ichange, 0, 0, 0, &tp);
1735+
if (error)
17541736
goto out_unlock;
1755-
}
17561737

17571738
/*
17581739
* Lock and join the inodes to the tansaction so that transaction commit

fs/xfs/xfs_dquot.c

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -614,11 +614,10 @@ xfs_qm_dqread(
614614
trace_xfs_dqread(dqp);
615615

616616
if (flags & XFS_QMOPT_DQALLOC) {
617-
tp = xfs_trans_alloc(mp, XFS_TRANS_QM_DQALLOC);
618-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_qm_dqalloc,
619-
XFS_QM_DQALLOC_SPACE_RES(mp), 0);
617+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_qm_dqalloc,
618+
XFS_QM_DQALLOC_SPACE_RES(mp), 0, 0, &tp);
620619
if (error)
621-
goto error1;
620+
goto error0;
622621
}
623622

624623
/*

fs/xfs/xfs_file.c

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -145,12 +145,10 @@ xfs_update_prealloc_flags(
145145
struct xfs_trans *tp;
146146
int error;
147147

148-
tp = xfs_trans_alloc(ip->i_mount, XFS_TRANS_WRITEID);
149-
error = xfs_trans_reserve(tp, &M_RES(ip->i_mount)->tr_writeid, 0, 0);
150-
if (error) {
151-
xfs_trans_cancel(tp);
148+
error = xfs_trans_alloc(ip->i_mount, &M_RES(ip->i_mount)->tr_writeid,
149+
0, 0, 0, &tp);
150+
if (error)
152151
return error;
153-
}
154152

155153
xfs_ilock(ip, XFS_ILOCK_EXCL);
156154
xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL);

fs/xfs/xfs_fsops.c

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -198,14 +198,10 @@ xfs_growfs_data_private(
198198
return error;
199199
}
200200

201-
tp = xfs_trans_alloc(mp, XFS_TRANS_GROWFS);
202-
tp->t_flags |= XFS_TRANS_RESERVE;
203-
error = xfs_trans_reserve(tp, &M_RES(mp)->tr_growdata,
204-
XFS_GROWFS_SPACE_RES(mp), 0);
205-
if (error) {
206-
xfs_trans_cancel(tp);
201+
error = xfs_trans_alloc(mp, &M_RES(mp)->tr_growdata,
202+
XFS_GROWFS_SPACE_RES(mp), 0, XFS_TRANS_RESERVE, &tp);
203+
if (error)
207204
return error;
208-
}
209205

210206
/*
211207
* Write new AG headers to disk. Non-transactional, but written

0 commit comments

Comments
 (0)