aboutsummaryrefslogtreecommitdiffstats
path: root/fs
diff options
context:
space:
mode:
authorChristoph Hellwig <hch@infradead.org>2010-06-23 21:36:58 -0400
committerAlex Elder <aelder@sgi.com>2010-07-26 14:16:36 -0400
commit898621d5a72c6799a9a13fce20443b4b6699899c (patch)
tree6cd994bd8d24f4f4f6ac5b5b57e0b99ee02d4ba6 /fs
parent4d16e9246fc3b3cf7bc95609eff66929a39daa06 (diff)
xfs: simplify inode to transaction joining
Currently we need to either call IHOLD or xfs_trans_ihold on an inode when joining it to a transaction via xfs_trans_ijoin. This patches instead makes xfs_trans_ijoin usable on it's own by doing an implicity xfs_trans_ihold, which also allows us to drop the third argument. For the case where we want to hold a reference on the inode a xfs_trans_ijoin_ref wrapper is added which does the IHOLD and marks the inode for needing an xfs_iput. In addition to the cleaner interface to the caller this also simplifies the implementation. Signed-off-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Dave Chinner <dchinner@redhat.com>
Diffstat (limited to 'fs')
-rw-r--r--fs/xfs/linux-2.6/xfs_file.c3
-rw-r--r--fs/xfs/linux-2.6/xfs_ioctl.c3
-rw-r--r--fs/xfs/linux-2.6/xfs_super.c3
-rw-r--r--fs/xfs/linux-2.6/xfs_sync.c3
-rw-r--r--fs/xfs/quota/xfs_dquot.c9
-rw-r--r--fs/xfs/xfs_attr.c75
-rw-r--r--fs/xfs/xfs_bmap.c5
-rw-r--r--fs/xfs/xfs_dfrag.c7
-rw-r--r--fs/xfs/xfs_fsops.c3
-rw-r--r--fs/xfs/xfs_inode.c14
-rw-r--r--fs/xfs/xfs_inode_item.c42
-rw-r--r--fs/xfs/xfs_inode_item.h8
-rw-r--r--fs/xfs/xfs_iomap.c9
-rw-r--r--fs/xfs/xfs_rename.c26
-rw-r--r--fs/xfs/xfs_trans.c3
-rw-r--r--fs/xfs/xfs_trans.h4
-rw-r--r--fs/xfs/xfs_trans_inode.c60
-rw-r--r--fs/xfs/xfs_utils.c4
-rw-r--r--fs/xfs/xfs_vnodeops.c69
19 files changed, 103 insertions, 247 deletions
diff --git a/fs/xfs/linux-2.6/xfs_file.c b/fs/xfs/linux-2.6/xfs_file.c
index 8d26d93648b4..9a9b446a58a7 100644
--- a/fs/xfs/linux-2.6/xfs_file.c
+++ b/fs/xfs/linux-2.6/xfs_file.c
@@ -158,8 +158,7 @@ xfs_file_fsync(
158 * transaction. So we play it safe and fire off the 158 * transaction. So we play it safe and fire off the
159 * transaction anyway. 159 * transaction anyway.
160 */ 160 */
161 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 161 xfs_trans_ijoin(tp, ip);
162 xfs_trans_ihold(tp, ip);
163 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 162 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
164 xfs_trans_set_sync(tp); 163 xfs_trans_set_sync(tp);
165 error = _xfs_trans_commit(tp, 0, &log_flushed); 164 error = _xfs_trans_commit(tp, 0, &log_flushed);
diff --git a/fs/xfs/linux-2.6/xfs_ioctl.c b/fs/xfs/linux-2.6/xfs_ioctl.c
index 8aa54f0eec15..a12dddad126e 100644
--- a/fs/xfs/linux-2.6/xfs_ioctl.c
+++ b/fs/xfs/linux-2.6/xfs_ioctl.c
@@ -1034,8 +1034,7 @@ xfs_ioctl_setattr(
1034 } 1034 }
1035 } 1035 }
1036 1036
1037 xfs_trans_ijoin(tp, ip, lock_flags); 1037 xfs_trans_ijoin(tp, ip);
1038 xfs_trans_ihold(tp, ip);
1039 1038
1040 /* 1039 /*
1041 * Change file ownership. Must be the owner or privileged. 1040 * Change file ownership. Must be the owner or privileged.
diff --git a/fs/xfs/linux-2.6/xfs_super.c b/fs/xfs/linux-2.6/xfs_super.c
index 4b90e4b531b7..b8ad17e730b6 100644
--- a/fs/xfs/linux-2.6/xfs_super.c
+++ b/fs/xfs/linux-2.6/xfs_super.c
@@ -1023,8 +1023,7 @@ xfs_log_inode(
1023 * an inode in another recent transaction. So we play it safe and 1023 * an inode in another recent transaction. So we play it safe and
1024 * fire off the transaction anyway. 1024 * fire off the transaction anyway.
1025 */ 1025 */
1026 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 1026 xfs_trans_ijoin(tp, ip);
1027 xfs_trans_ihold(tp, ip);
1028 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 1027 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
1029 xfs_trans_set_sync(tp); 1028 xfs_trans_set_sync(tp);
1030 error = xfs_trans_commit(tp, 0); 1029 error = xfs_trans_commit(tp, 0);
diff --git a/fs/xfs/linux-2.6/xfs_sync.c b/fs/xfs/linux-2.6/xfs_sync.c
index 850b4198bf60..0283b88bc16c 100644
--- a/fs/xfs/linux-2.6/xfs_sync.c
+++ b/fs/xfs/linux-2.6/xfs_sync.c
@@ -362,8 +362,7 @@ xfs_commit_dummy_trans(
362 362
363 xfs_ilock(ip, XFS_ILOCK_EXCL); 363 xfs_ilock(ip, XFS_ILOCK_EXCL);
364 364
365 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 365 xfs_trans_ijoin(tp, ip);
366 xfs_trans_ihold(tp, ip);
367 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 366 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
368 error = xfs_trans_commit(tp, 0); 367 error = xfs_trans_commit(tp, 0);
369 xfs_iunlock(ip, XFS_ILOCK_EXCL); 368 xfs_iunlock(ip, XFS_ILOCK_EXCL);
diff --git a/fs/xfs/quota/xfs_dquot.c b/fs/xfs/quota/xfs_dquot.c
index 6526e87cade0..56f366e327f3 100644
--- a/fs/xfs/quota/xfs_dquot.c
+++ b/fs/xfs/quota/xfs_dquot.c
@@ -378,14 +378,7 @@ xfs_qm_dqalloc(
378 return (ESRCH); 378 return (ESRCH);
379 } 379 }
380 380
381 /* 381 xfs_trans_ijoin_ref(tp, quotip, XFS_ILOCK_EXCL);
382 * xfs_trans_commit normally decrements the vnode ref count
383 * when it unlocks the inode. Since we want to keep the quota
384 * inode around, we bump the vnode ref count now.
385 */
386 IHOLD(quotip);
387
388 xfs_trans_ijoin(tp, quotip, XFS_ILOCK_EXCL);
389 nmaps = 1; 382 nmaps = 1;
390 if ((error = xfs_bmapi(tp, quotip, 383 if ((error = xfs_bmapi(tp, quotip,
391 offset_fsb, XFS_DQUOT_CLUSTER_SIZE_FSB, 384 offset_fsb, XFS_DQUOT_CLUSTER_SIZE_FSB,
diff --git a/fs/xfs/xfs_attr.c b/fs/xfs/xfs_attr.c
index 8bde79785a75..f3ca7186155a 100644
--- a/fs/xfs/xfs_attr.c
+++ b/fs/xfs/xfs_attr.c
@@ -319,8 +319,7 @@ xfs_attr_set_int(
319 return (error); 319 return (error);
320 } 320 }
321 321
322 xfs_trans_ijoin(args.trans, dp, XFS_ILOCK_EXCL); 322 xfs_trans_ijoin(args.trans, dp);
323 xfs_trans_ihold(args.trans, dp);
324 323
325 /* 324 /*
326 * If the attribute list is non-existent or a shortform list, 325 * If the attribute list is non-existent or a shortform list,
@@ -390,10 +389,8 @@ xfs_attr_set_int(
390 * bmap_finish() may have committed the last trans and started 389 * bmap_finish() may have committed the last trans and started
391 * a new one. We need the inode to be in all transactions. 390 * a new one. We need the inode to be in all transactions.
392 */ 391 */
393 if (committed) { 392 if (committed)
394 xfs_trans_ijoin(args.trans, dp, XFS_ILOCK_EXCL); 393 xfs_trans_ijoin(args.trans, dp);
395 xfs_trans_ihold(args.trans, dp);
396 }
397 394
398 /* 395 /*
399 * Commit the leaf transformation. We'll need another (linked) 396 * Commit the leaf transformation. We'll need another (linked)
@@ -538,8 +535,7 @@ xfs_attr_remove_int(xfs_inode_t *dp, struct xfs_name *name, int flags)
538 * No need to make quota reservations here. We expect to release some 535 * No need to make quota reservations here. We expect to release some
539 * blocks not allocate in the common case. 536 * blocks not allocate in the common case.
540 */ 537 */
541 xfs_trans_ijoin(args.trans, dp, XFS_ILOCK_EXCL); 538 xfs_trans_ijoin(args.trans, dp);
542 xfs_trans_ihold(args.trans, dp);
543 539
544 /* 540 /*
545 * Decide on what work routines to call based on the inode size. 541 * Decide on what work routines to call based on the inode size.
@@ -815,8 +811,7 @@ xfs_attr_inactive(xfs_inode_t *dp)
815 * No need to make quota reservations here. We expect to release some 811 * No need to make quota reservations here. We expect to release some
816 * blocks, not allocate, in the common case. 812 * blocks, not allocate, in the common case.
817 */ 813 */
818 xfs_trans_ijoin(trans, dp, XFS_ILOCK_EXCL); 814 xfs_trans_ijoin(trans, dp);
819 xfs_trans_ihold(trans, dp);
820 815
821 /* 816 /*
822 * Decide on what work routines to call based on the inode size. 817 * Decide on what work routines to call based on the inode size.
@@ -975,10 +970,8 @@ xfs_attr_leaf_addname(xfs_da_args_t *args)
975 * bmap_finish() may have committed the last trans and started 970 * bmap_finish() may have committed the last trans and started
976 * a new one. We need the inode to be in all transactions. 971 * a new one. We need the inode to be in all transactions.
977 */ 972 */
978 if (committed) { 973 if (committed)
979 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 974 xfs_trans_ijoin(args->trans, dp);
980 xfs_trans_ihold(args->trans, dp);
981 }
982 975
983 /* 976 /*
984 * Commit the current trans (including the inode) and start 977 * Commit the current trans (including the inode) and start
@@ -1079,10 +1072,8 @@ xfs_attr_leaf_addname(xfs_da_args_t *args)
1079 * and started a new one. We need the inode to be 1072 * and started a new one. We need the inode to be
1080 * in all transactions. 1073 * in all transactions.
1081 */ 1074 */
1082 if (committed) { 1075 if (committed)
1083 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1076 xfs_trans_ijoin(args->trans, dp);
1084 xfs_trans_ihold(args->trans, dp);
1085 }
1086 } else 1077 } else
1087 xfs_da_buf_done(bp); 1078 xfs_da_buf_done(bp);
1088 1079
@@ -1155,10 +1146,8 @@ xfs_attr_leaf_removename(xfs_da_args_t *args)
1155 * bmap_finish() may have committed the last trans and started 1146 * bmap_finish() may have committed the last trans and started
1156 * a new one. We need the inode to be in all transactions. 1147 * a new one. We need the inode to be in all transactions.
1157 */ 1148 */
1158 if (committed) { 1149 if (committed)
1159 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1150 xfs_trans_ijoin(args->trans, dp);
1160 xfs_trans_ihold(args->trans, dp);
1161 }
1162 } else 1151 } else
1163 xfs_da_buf_done(bp); 1152 xfs_da_buf_done(bp);
1164 return(0); 1153 return(0);
@@ -1311,10 +1300,8 @@ restart:
1311 * and started a new one. We need the inode to be 1300 * and started a new one. We need the inode to be
1312 * in all transactions. 1301 * in all transactions.
1313 */ 1302 */
1314 if (committed) { 1303 if (committed)
1315 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1304 xfs_trans_ijoin(args->trans, dp);
1316 xfs_trans_ihold(args->trans, dp);
1317 }
1318 1305
1319 /* 1306 /*
1320 * Commit the node conversion and start the next 1307 * Commit the node conversion and start the next
@@ -1350,10 +1337,8 @@ restart:
1350 * bmap_finish() may have committed the last trans and started 1337 * bmap_finish() may have committed the last trans and started
1351 * a new one. We need the inode to be in all transactions. 1338 * a new one. We need the inode to be in all transactions.
1352 */ 1339 */
1353 if (committed) { 1340 if (committed)
1354 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1341 xfs_trans_ijoin(args->trans, dp);
1355 xfs_trans_ihold(args->trans, dp);
1356 }
1357 } else { 1342 } else {
1358 /* 1343 /*
1359 * Addition succeeded, update Btree hashvals. 1344 * Addition succeeded, update Btree hashvals.
@@ -1464,10 +1449,8 @@ restart:
1464 * and started a new one. We need the inode to be 1449 * and started a new one. We need the inode to be
1465 * in all transactions. 1450 * in all transactions.
1466 */ 1451 */
1467 if (committed) { 1452 if (committed)
1468 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1453 xfs_trans_ijoin(args->trans, dp);
1469 xfs_trans_ihold(args->trans, dp);
1470 }
1471 } 1454 }
1472 1455
1473 /* 1456 /*
@@ -1598,10 +1581,8 @@ xfs_attr_node_removename(xfs_da_args_t *args)
1598 * bmap_finish() may have committed the last trans and started 1581 * bmap_finish() may have committed the last trans and started
1599 * a new one. We need the inode to be in all transactions. 1582 * a new one. We need the inode to be in all transactions.
1600 */ 1583 */
1601 if (committed) { 1584 if (committed)
1602 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1585 xfs_trans_ijoin(args->trans, dp);
1603 xfs_trans_ihold(args->trans, dp);
1604 }
1605 1586
1606 /* 1587 /*
1607 * Commit the Btree join operation and start a new trans. 1588 * Commit the Btree join operation and start a new trans.
@@ -1652,10 +1633,8 @@ xfs_attr_node_removename(xfs_da_args_t *args)
1652 * and started a new one. We need the inode to be 1633 * and started a new one. We need the inode to be
1653 * in all transactions. 1634 * in all transactions.
1654 */ 1635 */
1655 if (committed) { 1636 if (committed)
1656 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 1637 xfs_trans_ijoin(args->trans, dp);
1657 xfs_trans_ihold(args->trans, dp);
1658 }
1659 } else 1638 } else
1660 xfs_da_brelse(args->trans, bp); 1639 xfs_da_brelse(args->trans, bp);
1661 } 1640 }
@@ -2093,10 +2072,8 @@ xfs_attr_rmtval_set(xfs_da_args_t *args)
2093 * bmap_finish() may have committed the last trans and started 2072 * bmap_finish() may have committed the last trans and started
2094 * a new one. We need the inode to be in all transactions. 2073 * a new one. We need the inode to be in all transactions.
2095 */ 2074 */
2096 if (committed) { 2075 if (committed)
2097 xfs_trans_ijoin(args->trans, dp, XFS_ILOCK_EXCL); 2076 xfs_trans_ijoin(args->trans, dp);
2098 xfs_trans_ihold(args->trans, dp);
2099 }
2100 2077
2101 ASSERT(nmap == 1); 2078 ASSERT(nmap == 1);
2102 ASSERT((map.br_startblock != DELAYSTARTBLOCK) && 2079 ASSERT((map.br_startblock != DELAYSTARTBLOCK) &&
@@ -2249,10 +2226,8 @@ xfs_attr_rmtval_remove(xfs_da_args_t *args)
2249 * bmap_finish() may have committed the last trans and started 2226 * bmap_finish() may have committed the last trans and started
2250 * a new one. We need the inode to be in all transactions. 2227 * a new one. We need the inode to be in all transactions.
2251 */ 2228 */
2252 if (committed) { 2229 if (committed)
2253 xfs_trans_ijoin(args->trans, args->dp, XFS_ILOCK_EXCL); 2230 xfs_trans_ijoin(args->trans, args->dp);
2254 xfs_trans_ihold(args->trans, args->dp);
2255 }
2256 2231
2257 /* 2232 /*
2258 * Close out trans and start the next one in the chain. 2233 * Close out trans and start the next one in the chain.
diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c
index ff8675b41973..e0389656ad2c 100644
--- a/fs/xfs/xfs_bmap.c
+++ b/fs/xfs/xfs_bmap.c
@@ -3751,9 +3751,10 @@ xfs_bmap_add_attrfork(
3751 ip->i_d.di_aformat = XFS_DINODE_FMT_EXTENTS; 3751 ip->i_d.di_aformat = XFS_DINODE_FMT_EXTENTS;
3752 } 3752 }
3753 ASSERT(ip->i_d.di_anextents == 0); 3753 ASSERT(ip->i_d.di_anextents == 0);
3754 IHOLD(ip); 3754
3755 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 3755 xfs_trans_ijoin_ref(tp, ip, XFS_ILOCK_EXCL);
3756 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 3756 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
3757
3757 switch (ip->i_d.di_format) { 3758 switch (ip->i_d.di_format) {
3758 case XFS_DINODE_FMT_DEV: 3759 case XFS_DINODE_FMT_DEV:
3759 ip->i_d.di_forkoff = roundup(sizeof(xfs_dev_t), 8) >> 3; 3760 ip->i_d.di_forkoff = roundup(sizeof(xfs_dev_t), 8) >> 3;
diff --git a/fs/xfs/xfs_dfrag.c b/fs/xfs/xfs_dfrag.c
index 7b11dc0494c2..3b9582c60a22 100644
--- a/fs/xfs/xfs_dfrag.c
+++ b/fs/xfs/xfs_dfrag.c
@@ -416,11 +416,8 @@ xfs_swap_extents(
416 } 416 }
417 417
418 418
419 IHOLD(ip); 419 xfs_trans_ijoin_ref(tp, ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL);
420 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); 420 xfs_trans_ijoin_ref(tp, tip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL);
421
422 IHOLD(tip);
423 xfs_trans_ijoin(tp, tip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL);
424 421
425 xfs_trans_log_inode(tp, ip, ilf_fields); 422 xfs_trans_log_inode(tp, ip, ilf_fields);
426 xfs_trans_log_inode(tp, tip, tilf_fields); 423 xfs_trans_log_inode(tp, tip, tilf_fields);
diff --git a/fs/xfs/xfs_fsops.c b/fs/xfs/xfs_fsops.c
index ade96922fc8c..dbca5f5c37ba 100644
--- a/fs/xfs/xfs_fsops.c
+++ b/fs/xfs/xfs_fsops.c
@@ -622,8 +622,7 @@ xfs_fs_log_dummy(
622 ip = mp->m_rootip; 622 ip = mp->m_rootip;
623 xfs_ilock(ip, XFS_ILOCK_EXCL); 623 xfs_ilock(ip, XFS_ILOCK_EXCL);
624 624
625 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 625 xfs_trans_ijoin(tp, ip);
626 xfs_trans_ihold(tp, ip);
627 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 626 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
628 xfs_trans_set_sync(tp); 627 xfs_trans_set_sync(tp);
629 error = xfs_trans_commit(tp, 0); 628 error = xfs_trans_commit(tp, 0);
diff --git a/fs/xfs/xfs_inode.c b/fs/xfs/xfs_inode.c
index c7c48da97ad4..d22b580162cc 100644
--- a/fs/xfs/xfs_inode.c
+++ b/fs/xfs/xfs_inode.c
@@ -1456,7 +1456,7 @@ xfs_itruncate_finish(
1456 ASSERT((*tp)->t_flags & XFS_TRANS_PERM_LOG_RES); 1456 ASSERT((*tp)->t_flags & XFS_TRANS_PERM_LOG_RES);
1457 ASSERT(ip->i_transp == *tp); 1457 ASSERT(ip->i_transp == *tp);
1458 ASSERT(ip->i_itemp != NULL); 1458 ASSERT(ip->i_itemp != NULL);
1459 ASSERT(ip->i_itemp->ili_flags & XFS_ILI_HOLD); 1459 ASSERT(ip->i_itemp->ili_lock_flags == 0);
1460 1460
1461 1461
1462 ntp = *tp; 1462 ntp = *tp;
@@ -1608,12 +1608,8 @@ xfs_itruncate_finish(
1608 */ 1608 */
1609 error = xfs_bmap_finish(tp, &free_list, &committed); 1609 error = xfs_bmap_finish(tp, &free_list, &committed);
1610 ntp = *tp; 1610 ntp = *tp;
1611 if (committed) { 1611 if (committed)
1612 /* link the inode into the next xact in the chain */ 1612 xfs_trans_ijoin(ntp, ip);
1613 xfs_trans_ijoin(ntp, ip,
1614 XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL);
1615 xfs_trans_ihold(ntp, ip);
1616 }
1617 1613
1618 if (error) { 1614 if (error) {
1619 /* 1615 /*
@@ -1642,9 +1638,7 @@ xfs_itruncate_finish(
1642 error = xfs_trans_commit(*tp, 0); 1638 error = xfs_trans_commit(*tp, 0);
1643 *tp = ntp; 1639 *tp = ntp;
1644 1640
1645 /* link the inode into the next transaction in the chain */ 1641 xfs_trans_ijoin(ntp, ip);
1646 xfs_trans_ijoin(ntp, ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL);
1647 xfs_trans_ihold(ntp, ip);
1648 1642
1649 if (error) 1643 if (error)
1650 return error; 1644 return error;
diff --git a/fs/xfs/xfs_inode_item.c b/fs/xfs/xfs_inode_item.c
index c7e70d708345..ad050c618e62 100644
--- a/fs/xfs/xfs_inode_item.c
+++ b/fs/xfs/xfs_inode_item.c
@@ -628,19 +628,10 @@ xfs_inode_item_unlock(
628{ 628{
629 struct xfs_inode_log_item *iip = INODE_ITEM(lip); 629 struct xfs_inode_log_item *iip = INODE_ITEM(lip);
630 struct xfs_inode *ip = iip->ili_inode; 630 struct xfs_inode *ip = iip->ili_inode;
631 uint hold; 631 unsigned short lock_flags;
632 uint iolocked;
633 uint lock_flags;
634 632
635 ASSERT(iip != NULL);
636 ASSERT(iip->ili_inode->i_itemp != NULL); 633 ASSERT(iip->ili_inode->i_itemp != NULL);
637 ASSERT(xfs_isilocked(iip->ili_inode, XFS_ILOCK_EXCL)); 634 ASSERT(xfs_isilocked(iip->ili_inode, XFS_ILOCK_EXCL));
638 ASSERT((!(iip->ili_inode->i_itemp->ili_flags &
639 XFS_ILI_IOLOCKED_EXCL)) ||
640 xfs_isilocked(iip->ili_inode, XFS_IOLOCK_EXCL));
641 ASSERT((!(iip->ili_inode->i_itemp->ili_flags &
642 XFS_ILI_IOLOCKED_SHARED)) ||
643 xfs_isilocked(iip->ili_inode, XFS_IOLOCK_SHARED));
644 635
645 /* 636 /*
646 * Clear the transaction pointer in the inode. 637 * Clear the transaction pointer in the inode.
@@ -668,35 +659,10 @@ xfs_inode_item_unlock(
668 iip->ili_aextents_buf = NULL; 659 iip->ili_aextents_buf = NULL;
669 } 660 }
670 661
671 /* 662 lock_flags = iip->ili_lock_flags;
672 * Figure out if we should unlock the inode or not. 663 iip->ili_lock_flags = 0;
673 */ 664 if (lock_flags)
674 hold = iip->ili_flags & XFS_ILI_HOLD;
675
676 /*
677 * Before clearing out the flags, remember whether we
678 * are holding the inode's IO lock.
679 */
680 iolocked = iip->ili_flags & XFS_ILI_IOLOCKED_ANY;
681
682 /*
683 * Clear out the fields of the inode log item particular
684 * to the current transaction.
685 */
686 iip->ili_flags = 0;
687
688 /*
689 * Unlock the inode if XFS_ILI_HOLD was not set.
690 */
691 if (!hold) {
692 lock_flags = XFS_ILOCK_EXCL;
693 if (iolocked & XFS_ILI_IOLOCKED_EXCL) {
694 lock_flags |= XFS_IOLOCK_EXCL;
695 } else if (iolocked & XFS_ILI_IOLOCKED_SHARED) {
696 lock_flags |= XFS_IOLOCK_SHARED;
697 }
698 xfs_iput(iip->ili_inode, lock_flags); 665 xfs_iput(iip->ili_inode, lock_flags);
699 }
700} 666}
701 667
702/* 668/*
diff --git a/fs/xfs/xfs_inode_item.h b/fs/xfs/xfs_inode_item.h
index b6a97ff1c3ab..d3dee61e6d91 100644
--- a/fs/xfs/xfs_inode_item.h
+++ b/fs/xfs/xfs_inode_item.h
@@ -103,12 +103,6 @@ typedef struct xfs_inode_log_format_64 {
103 XFS_ILOG_ADATA | XFS_ILOG_AEXT | \ 103 XFS_ILOG_ADATA | XFS_ILOG_AEXT | \
104 XFS_ILOG_ABROOT) 104 XFS_ILOG_ABROOT)
105 105
106#define XFS_ILI_HOLD 0x1
107#define XFS_ILI_IOLOCKED_EXCL 0x2
108#define XFS_ILI_IOLOCKED_SHARED 0x4
109
110#define XFS_ILI_IOLOCKED_ANY (XFS_ILI_IOLOCKED_EXCL | XFS_ILI_IOLOCKED_SHARED)
111
112static inline int xfs_ilog_fbroot(int w) 106static inline int xfs_ilog_fbroot(int w)
113{ 107{
114 return (w == XFS_DATA_FORK ? XFS_ILOG_DBROOT : XFS_ILOG_ABROOT); 108 return (w == XFS_DATA_FORK ? XFS_ILOG_DBROOT : XFS_ILOG_ABROOT);
@@ -137,7 +131,7 @@ typedef struct xfs_inode_log_item {
137 struct xfs_inode *ili_inode; /* inode ptr */ 131 struct xfs_inode *ili_inode; /* inode ptr */
138 xfs_lsn_t ili_flush_lsn; /* lsn at last flush */ 132 xfs_lsn_t ili_flush_lsn; /* lsn at last flush */
139 xfs_lsn_t ili_last_lsn; /* lsn at last transaction */ 133 xfs_lsn_t ili_last_lsn; /* lsn at last transaction */
140 unsigned short ili_flags; /* misc flags */ 134 unsigned short ili_lock_flags; /* lock flags */
141 unsigned short ili_logged; /* flushed logged data */ 135 unsigned short ili_logged; /* flushed logged data */
142 unsigned int ili_last_fields; /* fields when flushed */ 136 unsigned int ili_last_fields; /* fields when flushed */
143 struct xfs_bmbt_rec *ili_extents_buf; /* array of logged 137 struct xfs_bmbt_rec *ili_extents_buf; /* array of logged
diff --git a/fs/xfs/xfs_iomap.c b/fs/xfs/xfs_iomap.c
index 772f3e791ebe..aeac00294a18 100644
--- a/fs/xfs/xfs_iomap.c
+++ b/fs/xfs/xfs_iomap.c
@@ -329,8 +329,7 @@ xfs_iomap_write_direct(
329 if (error) 329 if (error)
330 goto error1; 330 goto error1;
331 331
332 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 332 xfs_trans_ijoin(tp, ip);
333 xfs_trans_ihold(tp, ip);
334 333
335 bmapi_flag = XFS_BMAPI_WRITE; 334 bmapi_flag = XFS_BMAPI_WRITE;
336 if ((flags & BMAPI_DIRECT) && (offset < ip->i_size || extsz)) 335 if ((flags & BMAPI_DIRECT) && (offset < ip->i_size || extsz))
@@ -597,8 +596,7 @@ xfs_iomap_write_allocate(
597 return XFS_ERROR(error); 596 return XFS_ERROR(error);
598 } 597 }
599 xfs_ilock(ip, XFS_ILOCK_EXCL); 598 xfs_ilock(ip, XFS_ILOCK_EXCL);
600 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 599 xfs_trans_ijoin(tp, ip);
601 xfs_trans_ihold(tp, ip);
602 600
603 xfs_bmap_init(&free_list, &first_block); 601 xfs_bmap_init(&free_list, &first_block);
604 602
@@ -761,8 +759,7 @@ xfs_iomap_write_unwritten(
761 } 759 }
762 760
763 xfs_ilock(ip, XFS_ILOCK_EXCL); 761 xfs_ilock(ip, XFS_ILOCK_EXCL);
764 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 762 xfs_trans_ijoin(tp, ip);
765 xfs_trans_ihold(tp, ip);
766 763
767 /* 764 /*
768 * Modify the unwritten extent state of the buffer. 765 * Modify the unwritten extent state of the buffer.
diff --git a/fs/xfs/xfs_rename.c b/fs/xfs/xfs_rename.c
index 8edb1074847a..778c87a8ebfc 100644
--- a/fs/xfs/xfs_rename.c
+++ b/fs/xfs/xfs_rename.c
@@ -169,26 +169,14 @@ xfs_rename(
169 /* 169 /*
170 * Join all the inodes to the transaction. From this point on, 170 * Join all the inodes to the transaction. From this point on,
171 * we can rely on either trans_commit or trans_cancel to unlock 171 * we can rely on either trans_commit or trans_cancel to unlock
172 * them. Note that we need to add a vnode reference to the 172 * them.
173 * directories since trans_commit & trans_cancel will decrement
174 * them when they unlock the inodes. Also, we need to be careful
175 * not to add an inode to the transaction more than once.
176 */ 173 */
177 IHOLD(src_dp); 174 xfs_trans_ijoin_ref(tp, src_dp, XFS_ILOCK_EXCL);
178 xfs_trans_ijoin(tp, src_dp, XFS_ILOCK_EXCL); 175 if (new_parent)
179 176 xfs_trans_ijoin_ref(tp, target_dp, XFS_ILOCK_EXCL);
180 if (new_parent) { 177 xfs_trans_ijoin_ref(tp, src_ip, XFS_ILOCK_EXCL);
181 IHOLD(target_dp); 178 if (target_ip)
182 xfs_trans_ijoin(tp, target_dp, XFS_ILOCK_EXCL); 179 xfs_trans_ijoin_ref(tp, target_ip, XFS_ILOCK_EXCL);
183 }
184
185 IHOLD(src_ip);
186 xfs_trans_ijoin(tp, src_ip, XFS_ILOCK_EXCL);
187
188 if (target_ip) {
189 IHOLD(target_ip);
190 xfs_trans_ijoin(tp, target_ip, XFS_ILOCK_EXCL);
191 }
192 180
193 /* 181 /*
194 * If we are using project inheritance, we only allow renames 182 * If we are using project inheritance, we only allow renames
diff --git a/fs/xfs/xfs_trans.c b/fs/xfs/xfs_trans.c
index 213792e1ad02..f2065ccb6c2d 100644
--- a/fs/xfs/xfs_trans.c
+++ b/fs/xfs/xfs_trans.c
@@ -1892,7 +1892,6 @@ xfs_trans_roll(
1892 if (error) 1892 if (error)
1893 return error; 1893 return error;
1894 1894
1895 xfs_trans_ijoin(trans, dp, XFS_ILOCK_EXCL); 1895 xfs_trans_ijoin(trans, dp);
1896 xfs_trans_ihold(trans, dp);
1897 return 0; 1896 return 0;
1898} 1897}
diff --git a/fs/xfs/xfs_trans.h b/fs/xfs/xfs_trans.h
index 37c0ce1ccd48..aa6f422f0361 100644
--- a/fs/xfs/xfs_trans.h
+++ b/fs/xfs/xfs_trans.h
@@ -475,8 +475,8 @@ void xfs_trans_dquot_buf(xfs_trans_t *, struct xfs_buf *, uint);
475void xfs_trans_inode_alloc_buf(xfs_trans_t *, struct xfs_buf *); 475void xfs_trans_inode_alloc_buf(xfs_trans_t *, struct xfs_buf *);
476int xfs_trans_iget(struct xfs_mount *, xfs_trans_t *, 476int xfs_trans_iget(struct xfs_mount *, xfs_trans_t *,
477 xfs_ino_t , uint, uint, struct xfs_inode **); 477 xfs_ino_t , uint, uint, struct xfs_inode **);
478void xfs_trans_ijoin(xfs_trans_t *, struct xfs_inode *, uint); 478void xfs_trans_ijoin_ref(struct xfs_trans *, struct xfs_inode *, uint);
479void xfs_trans_ihold(xfs_trans_t *, struct xfs_inode *); 479void xfs_trans_ijoin(struct xfs_trans *, struct xfs_inode *);
480void xfs_trans_log_buf(xfs_trans_t *, struct xfs_buf *, uint, uint); 480void xfs_trans_log_buf(xfs_trans_t *, struct xfs_buf *, uint, uint);
481void xfs_trans_log_inode(xfs_trans_t *, struct xfs_inode *, uint); 481void xfs_trans_log_inode(xfs_trans_t *, struct xfs_inode *, uint);
482struct xfs_efi_log_item *xfs_trans_get_efi(xfs_trans_t *, uint); 482struct xfs_efi_log_item *xfs_trans_get_efi(xfs_trans_t *, uint);
diff --git a/fs/xfs/xfs_trans_inode.c b/fs/xfs/xfs_trans_inode.c
index 865eeb63ce16..cdc53a1050c5 100644
--- a/fs/xfs/xfs_trans_inode.c
+++ b/fs/xfs/xfs_trans_inode.c
@@ -33,6 +33,7 @@
33#include "xfs_btree.h" 33#include "xfs_btree.h"
34#include "xfs_trans_priv.h" 34#include "xfs_trans_priv.h"
35#include "xfs_inode_item.h" 35#include "xfs_inode_item.h"
36#include "xfs_trace.h"
36 37
37#ifdef XFS_TRANS_DEBUG 38#ifdef XFS_TRANS_DEBUG
38STATIC void 39STATIC void
@@ -42,7 +43,6 @@ xfs_trans_inode_broot_debug(
42#define xfs_trans_inode_broot_debug(ip) 43#define xfs_trans_inode_broot_debug(ip)
43#endif 44#endif
44 45
45
46/* 46/*
47 * Get an inode and join it to the transaction. 47 * Get an inode and join it to the transaction.
48 */ 48 */
@@ -58,32 +58,31 @@ xfs_trans_iget(
58 int error; 58 int error;
59 59
60 error = xfs_iget(mp, tp, ino, flags, lock_flags, ipp); 60 error = xfs_iget(mp, tp, ino, flags, lock_flags, ipp);
61 if (!error && tp) 61 if (!error && tp) {
62 xfs_trans_ijoin(tp, *ipp, lock_flags); 62 xfs_trans_ijoin(tp, *ipp);
63 (*ipp)->i_itemp->ili_lock_flags = lock_flags;
64 }
63 return error; 65 return error;
64} 66}
65 67
66/* 68/*
67 * Add the locked inode to the transaction. 69 * Add a locked inode to the transaction.
68 * The inode must be locked, and it cannot be associated with any 70 *
69 * transaction. The caller must specify the locks already held 71 * The inode must be locked, and it cannot be associated with any transaction.
70 * on the inode.
71 */ 72 */
72void 73void
73xfs_trans_ijoin( 74xfs_trans_ijoin(
74 xfs_trans_t *tp, 75 struct xfs_trans *tp,
75 xfs_inode_t *ip, 76 struct xfs_inode *ip)
76 uint lock_flags)
77{ 77{
78 xfs_inode_log_item_t *iip; 78 xfs_inode_log_item_t *iip;
79 79
80 ASSERT(ip->i_transp == NULL); 80 ASSERT(ip->i_transp == NULL);
81 ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL)); 81 ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL));
82 ASSERT(lock_flags & XFS_ILOCK_EXCL);
83 if (ip->i_itemp == NULL) 82 if (ip->i_itemp == NULL)
84 xfs_inode_item_init(ip, ip->i_mount); 83 xfs_inode_item_init(ip, ip->i_mount);
85 iip = ip->i_itemp; 84 iip = ip->i_itemp;
86 ASSERT(iip->ili_flags == 0); 85 ASSERT(iip->ili_lock_flags == 0);
87 86
88 /* 87 /*
89 * Get a log_item_desc to point at the new item. 88 * Get a log_item_desc to point at the new item.
@@ -93,42 +92,31 @@ xfs_trans_ijoin(
93 xfs_trans_inode_broot_debug(ip); 92 xfs_trans_inode_broot_debug(ip);
94 93
95 /* 94 /*
96 * If the IO lock is already held, mark that in the inode log item.
97 */
98 if (lock_flags & XFS_IOLOCK_EXCL) {
99 iip->ili_flags |= XFS_ILI_IOLOCKED_EXCL;
100 } else if (lock_flags & XFS_IOLOCK_SHARED) {
101 iip->ili_flags |= XFS_ILI_IOLOCKED_SHARED;
102 }
103
104 /*
105 * Initialize i_transp so we can find it with xfs_inode_incore() 95 * Initialize i_transp so we can find it with xfs_inode_incore()
106 * in xfs_trans_iget() above. 96 * in xfs_trans_iget() above.
107 */ 97 */
108 ip->i_transp = tp; 98 ip->i_transp = tp;
109} 99}
110 100
111
112
113/* 101/*
114 * Mark the inode as not needing to be unlocked when the inode item's 102 * Add a locked inode to the transaction.
115 * IOP_UNLOCK() routine is called. The inode must already be locked 103 *
116 * and associated with the given transaction. 104 *
105 * Grabs a reference to the inode which will be dropped when the transaction
106 * is commited. The inode will also be unlocked at that point. The inode
107 * must be locked, and it cannot be associated with any transaction.
117 */ 108 */
118/*ARGSUSED*/
119void 109void
120xfs_trans_ihold( 110xfs_trans_ijoin_ref(
121 xfs_trans_t *tp, 111 struct xfs_trans *tp,
122 xfs_inode_t *ip) 112 struct xfs_inode *ip,
113 uint lock_flags)
123{ 114{
124 ASSERT(ip->i_transp == tp); 115 xfs_trans_ijoin(tp, ip);
125 ASSERT(ip->i_itemp != NULL); 116 IHOLD(ip);
126 ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL)); 117 ip->i_itemp->ili_lock_flags = lock_flags;
127
128 ip->i_itemp->ili_flags |= XFS_ILI_HOLD;
129} 118}
130 119
131
132/* 120/*
133 * This is called to mark the fields indicated in fieldmask as needing 121 * This is called to mark the fields indicated in fieldmask as needing
134 * to be logged when the transaction is committed. The inode must 122 * to be logged when the transaction is committed. The inode must
diff --git a/fs/xfs/xfs_utils.c b/fs/xfs/xfs_utils.c
index 8965887d26b1..102ce4898ab7 100644
--- a/fs/xfs/xfs_utils.c
+++ b/fs/xfs/xfs_utils.c
@@ -374,8 +374,8 @@ xfs_truncate_file(
374 * of references will stay constant. 374 * of references will stay constant.
375 */ 375 */
376 xfs_ilock(ip, XFS_ILOCK_EXCL); 376 xfs_ilock(ip, XFS_ILOCK_EXCL);
377 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); 377 xfs_trans_ijoin(tp, ip);
378 xfs_trans_ihold(tp, ip); 378
379 /* 379 /*
380 * Signal a sync xaction. The only case where that isn't 380 * Signal a sync xaction. The only case where that isn't
381 * the case is if we're truncating an already unlinked file 381 * the case is if we're truncating an already unlinked file
diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c
index 161444e768b6..130343a5d22d 100644
--- a/fs/xfs/xfs_vnodeops.c
+++ b/fs/xfs/xfs_vnodeops.c
@@ -268,8 +268,7 @@ xfs_setattr(
268 commit_flags = XFS_TRANS_RELEASE_LOG_RES; 268 commit_flags = XFS_TRANS_RELEASE_LOG_RES;
269 xfs_ilock(ip, XFS_ILOCK_EXCL); 269 xfs_ilock(ip, XFS_ILOCK_EXCL);
270 270
271 xfs_trans_ijoin(tp, ip, lock_flags); 271 xfs_trans_ijoin(tp, ip);
272 xfs_trans_ihold(tp, ip);
273 272
274 /* 273 /*
275 * Only change the c/mtime if we are changing the size 274 * Only change the c/mtime if we are changing the size
@@ -319,8 +318,7 @@ xfs_setattr(
319 xfs_iflags_set(ip, XFS_ITRUNCATED); 318 xfs_iflags_set(ip, XFS_ITRUNCATED);
320 } 319 }
321 } else if (tp) { 320 } else if (tp) {
322 xfs_trans_ijoin(tp, ip, lock_flags); 321 xfs_trans_ijoin(tp, ip);
323 xfs_trans_ihold(tp, ip);
324 } 322 }
325 323
326 /* 324 /*
@@ -653,10 +651,7 @@ xfs_free_eofblocks(
653 } 651 }
654 652
655 xfs_ilock(ip, XFS_ILOCK_EXCL); 653 xfs_ilock(ip, XFS_ILOCK_EXCL);
656 xfs_trans_ijoin(tp, ip, 654 xfs_trans_ijoin(tp, ip);
657 XFS_IOLOCK_EXCL |
658 XFS_ILOCK_EXCL);
659 xfs_trans_ihold(tp, ip);
660 655
661 error = xfs_itruncate_finish(&tp, ip, 656 error = xfs_itruncate_finish(&tp, ip,
662 ip->i_size, 657 ip->i_size,
@@ -728,8 +723,7 @@ xfs_inactive_symlink_rmt(
728 xfs_ilock(ip, XFS_IOLOCK_EXCL | XFS_ILOCK_EXCL); 723 xfs_ilock(ip, XFS_IOLOCK_EXCL | XFS_ILOCK_EXCL);
729 size = (int)ip->i_d.di_size; 724 size = (int)ip->i_d.di_size;
730 ip->i_d.di_size = 0; 725 ip->i_d.di_size = 0;
731 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); 726 xfs_trans_ijoin(tp, ip);
732 xfs_trans_ihold(tp, ip);
733 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 727 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
734 /* 728 /*
735 * Find the block(s) so we can inval and unmap them. 729 * Find the block(s) so we can inval and unmap them.
@@ -773,8 +767,7 @@ xfs_inactive_symlink_rmt(
773 * Mark it dirty so it will be logged and moved forward in the log as 767 * Mark it dirty so it will be logged and moved forward in the log as
774 * part of every commit. 768 * part of every commit.
775 */ 769 */
776 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); 770 xfs_trans_ijoin(tp, ip);
777 xfs_trans_ihold(tp, ip);
778 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 771 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
779 /* 772 /*
780 * Get a new, empty transaction to return to our caller. 773 * Get a new, empty transaction to return to our caller.
@@ -907,8 +900,7 @@ xfs_inactive_attrs(
907 goto error_cancel; 900 goto error_cancel;
908 901
909 xfs_ilock(ip, XFS_ILOCK_EXCL); 902 xfs_ilock(ip, XFS_ILOCK_EXCL);
910 xfs_trans_ijoin(tp, ip, XFS_IOLOCK_EXCL | XFS_ILOCK_EXCL); 903 xfs_trans_ijoin(tp, ip);
911 xfs_trans_ihold(tp, ip);
912 xfs_idestroy_fork(ip, XFS_ATTR_FORK); 904 xfs_idestroy_fork(ip, XFS_ATTR_FORK);
913 905
914 ASSERT(ip->i_d.di_anextents == 0); 906 ASSERT(ip->i_d.di_anextents == 0);
@@ -1095,8 +1087,7 @@ xfs_inactive(
1095 } 1087 }
1096 1088
1097 xfs_ilock(ip, XFS_ILOCK_EXCL); 1089 xfs_ilock(ip, XFS_ILOCK_EXCL);
1098 xfs_trans_ijoin(tp, ip, XFS_IOLOCK_EXCL | XFS_ILOCK_EXCL); 1090 xfs_trans_ijoin(tp, ip);
1099 xfs_trans_ihold(tp, ip);
1100 1091
1101 /* 1092 /*
1102 * normally, we have to run xfs_itruncate_finish sync. 1093 * normally, we have to run xfs_itruncate_finish sync.
@@ -1129,8 +1120,7 @@ xfs_inactive(
1129 return VN_INACTIVE_CACHE; 1120 return VN_INACTIVE_CACHE;
1130 } 1121 }
1131 1122
1132 xfs_trans_ijoin(tp, ip, XFS_IOLOCK_EXCL | XFS_ILOCK_EXCL); 1123 xfs_trans_ijoin(tp, ip);
1133 xfs_trans_ihold(tp, ip);
1134 } else { 1124 } else {
1135 error = xfs_trans_reserve(tp, 0, 1125 error = xfs_trans_reserve(tp, 0,
1136 XFS_IFREE_LOG_RES(mp), 1126 XFS_IFREE_LOG_RES(mp),
@@ -1143,8 +1133,7 @@ xfs_inactive(
1143 } 1133 }
1144 1134
1145 xfs_ilock(ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL); 1135 xfs_ilock(ip, XFS_ILOCK_EXCL | XFS_IOLOCK_EXCL);
1146 xfs_trans_ijoin(tp, ip, XFS_IOLOCK_EXCL | XFS_ILOCK_EXCL); 1136 xfs_trans_ijoin(tp, ip);
1147 xfs_trans_ihold(tp, ip);
1148 } 1137 }
1149 1138
1150 /* 1139 /*
@@ -1392,8 +1381,7 @@ xfs_create(
1392 * the transaction cancel unlocking dp so don't do it explicitly in the 1381 * the transaction cancel unlocking dp so don't do it explicitly in the
1393 * error path. 1382 * error path.
1394 */ 1383 */
1395 IHOLD(dp); 1384 xfs_trans_ijoin_ref(tp, dp, XFS_ILOCK_EXCL);
1396 xfs_trans_ijoin(tp, dp, XFS_ILOCK_EXCL);
1397 unlock_dp_on_error = B_FALSE; 1385 unlock_dp_on_error = B_FALSE;
1398 1386
1399 error = xfs_dir_createname(tp, dp, name, ip->i_ino, 1387 error = xfs_dir_createname(tp, dp, name, ip->i_ino,
@@ -1730,15 +1718,8 @@ xfs_remove(
1730 1718
1731 xfs_lock_two_inodes(dp, ip, XFS_ILOCK_EXCL); 1719 xfs_lock_two_inodes(dp, ip, XFS_ILOCK_EXCL);
1732 1720
1733 /* 1721 xfs_trans_ijoin_ref(tp, dp, XFS_ILOCK_EXCL);
1734 * At this point, we've gotten both the directory and the entry 1722 xfs_trans_ijoin_ref(tp, ip, XFS_ILOCK_EXCL);
1735 * inodes locked.
1736 */
1737 IHOLD(ip);
1738 xfs_trans_ijoin(tp, dp, XFS_ILOCK_EXCL);
1739
1740 IHOLD(dp);
1741 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL);
1742 1723
1743 /* 1724 /*
1744 * If we're removing a directory perform some additional validation. 1725 * If we're removing a directory perform some additional validation.
@@ -1884,15 +1865,8 @@ xfs_link(
1884 1865
1885 xfs_lock_two_inodes(sip, tdp, XFS_ILOCK_EXCL); 1866 xfs_lock_two_inodes(sip, tdp, XFS_ILOCK_EXCL);
1886 1867
1887 /* 1868 xfs_trans_ijoin_ref(tp, sip, XFS_ILOCK_EXCL);
1888 * Increment vnode ref counts since xfs_trans_commit & 1869 xfs_trans_ijoin_ref(tp, tdp, XFS_ILOCK_EXCL);
1889 * xfs_trans_cancel will both unlock the inodes and
1890 * decrement the associated ref counts.
1891 */
1892 IHOLD(sip);
1893 IHOLD(tdp);
1894 xfs_trans_ijoin(tp, sip, XFS_ILOCK_EXCL);
1895 xfs_trans_ijoin(tp, tdp, XFS_ILOCK_EXCL);
1896 1870
1897 /* 1871 /*
1898 * If the source has too many links, we can't make any more to it. 1872 * If the source has too many links, we can't make any more to it.
@@ -2087,8 +2061,7 @@ xfs_symlink(
2087 * transaction cancel unlocking dp so don't do it explicitly in the 2061 * transaction cancel unlocking dp so don't do it explicitly in the
2088 * error path. 2062 * error path.
2089 */ 2063 */
2090 IHOLD(dp); 2064 xfs_trans_ijoin_ref(tp, dp, XFS_ILOCK_EXCL);
2091 xfs_trans_ijoin(tp, dp, XFS_ILOCK_EXCL);
2092 unlock_dp_on_error = B_FALSE; 2065 unlock_dp_on_error = B_FALSE;
2093 2066
2094 /* 2067 /*
@@ -2227,13 +2200,12 @@ xfs_set_dmattrs(
2227 return error; 2200 return error;
2228 } 2201 }
2229 xfs_ilock(ip, XFS_ILOCK_EXCL); 2202 xfs_ilock(ip, XFS_ILOCK_EXCL);
2230 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 2203 xfs_trans_ijoin_ref(tp, ip, XFS_ILOCK_EXCL);
2231 2204
2232 ip->i_d.di_dmevmask = evmask; 2205 ip->i_d.di_dmevmask = evmask;
2233 ip->i_d.di_dmstate = state; 2206 ip->i_d.di_dmstate = state;
2234 2207
2235 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE); 2208 xfs_trans_log_inode(tp, ip, XFS_ILOG_CORE);
2236 IHOLD(ip);
2237 error = xfs_trans_commit(tp, 0); 2209 error = xfs_trans_commit(tp, 0);
2238 2210
2239 return error; 2211 return error;
@@ -2366,8 +2338,7 @@ xfs_alloc_file_space(
2366 if (error) 2338 if (error)
2367 goto error1; 2339 goto error1;
2368 2340
2369 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 2341 xfs_trans_ijoin(tp, ip);
2370 xfs_trans_ihold(tp, ip);
2371 2342
2372 /* 2343 /*
2373 * Issue the xfs_bmapi() call to allocate the blocks 2344 * Issue the xfs_bmapi() call to allocate the blocks
@@ -2668,8 +2639,7 @@ xfs_free_file_space(
2668 if (error) 2639 if (error)
2669 goto error1; 2640 goto error1;
2670 2641
2671 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 2642 xfs_trans_ijoin(tp, ip);
2672 xfs_trans_ihold(tp, ip);
2673 2643
2674 /* 2644 /*
2675 * issue the bunmapi() call to free the blocks 2645 * issue the bunmapi() call to free the blocks
@@ -2839,8 +2809,7 @@ xfs_change_file_space(
2839 2809
2840 xfs_ilock(ip, XFS_ILOCK_EXCL); 2810 xfs_ilock(ip, XFS_ILOCK_EXCL);
2841 2811
2842 xfs_trans_ijoin(tp, ip, XFS_ILOCK_EXCL); 2812 xfs_trans_ijoin(tp, ip);
2843 xfs_trans_ihold(tp, ip);
2844 2813
2845 if ((attr_flags & XFS_ATTR_DMI) == 0) { 2814 if ((attr_flags & XFS_ATTR_DMI) == 0) {
2846 ip->i_d.di_mode &= ~S_ISUID; 2815 ip->i_d.di_mode &= ~S_ISUID;