diff options
author | Dave Chinner <dchinner@redhat.com> | 2010-03-22 19:11:05 -0400 |
---|---|---|
committer | Alex Elder <aelder@sgi.com> | 2010-05-19 10:58:09 -0400 |
commit | b1c1b5b6108ad8e5991a614514f41da436c659d6 (patch) | |
tree | fea56bd29b112eb18985c22745d99063ed19cd0e /fs/xfs/xfs_trans.c | |
parent | 8e646a55ac69fe620b9e84034c03dd1e8e16a36b (diff) |
xfs: Clean up xfs_trans_committed code after factoring
Now that the code has been factored, clean up all the remaining
style cruft, simplify the code and re-order functions so that it
doesn't need forward declarations.
Also move the remaining functions that require forward declarations
(xfs_trans_uncommit, xfs_trans_free) so that all the forward
declarations can be removed from the file.
Signed-off-by: Dave Chinner <dchinner@redhat.com>
Reviewed-by: Christoph Hellwig <hch@lst.de>
Diffstat (limited to 'fs/xfs/xfs_trans.c')
-rw-r--r-- | fs/xfs/xfs_trans.c | 356 |
1 files changed, 166 insertions, 190 deletions
diff --git a/fs/xfs/xfs_trans.c b/fs/xfs/xfs_trans.c index 084bd3a13184..be578ecb4af2 100644 --- a/fs/xfs/xfs_trans.c +++ b/fs/xfs/xfs_trans.c | |||
@@ -45,20 +45,12 @@ | |||
45 | #include "xfs_trans_space.h" | 45 | #include "xfs_trans_space.h" |
46 | #include "xfs_inode_item.h" | 46 | #include "xfs_inode_item.h" |
47 | 47 | ||
48 | |||
49 | STATIC void xfs_trans_apply_sb_deltas(xfs_trans_t *); | ||
50 | STATIC void xfs_trans_uncommit(xfs_trans_t *, uint); | ||
51 | STATIC void xfs_trans_committed(xfs_trans_t *, int); | ||
52 | STATIC void xfs_trans_free(xfs_trans_t *); | ||
53 | |||
54 | kmem_zone_t *xfs_trans_zone; | 48 | kmem_zone_t *xfs_trans_zone; |
55 | 49 | ||
56 | |||
57 | /* | 50 | /* |
58 | * Reservation functions here avoid a huge stack in xfs_trans_init | 51 | * Reservation functions here avoid a huge stack in xfs_trans_init |
59 | * due to register overflow from temporaries in the calculations. | 52 | * due to register overflow from temporaries in the calculations. |
60 | */ | 53 | */ |
61 | |||
62 | STATIC uint | 54 | STATIC uint |
63 | xfs_calc_write_reservation(xfs_mount_t *mp) | 55 | xfs_calc_write_reservation(xfs_mount_t *mp) |
64 | { | 56 | { |
@@ -258,6 +250,19 @@ _xfs_trans_alloc( | |||
258 | } | 250 | } |
259 | 251 | ||
260 | /* | 252 | /* |
253 | * Free the transaction structure. If there is more clean up | ||
254 | * to do when the structure is freed, add it here. | ||
255 | */ | ||
256 | STATIC void | ||
257 | xfs_trans_free( | ||
258 | xfs_trans_t *tp) | ||
259 | { | ||
260 | atomic_dec(&tp->t_mountp->m_active_trans); | ||
261 | xfs_trans_free_dqinfo(tp); | ||
262 | kmem_zone_free(xfs_trans_zone, tp); | ||
263 | } | ||
264 | |||
265 | /* | ||
261 | * This is called to create a new transaction which will share the | 266 | * This is called to create a new transaction which will share the |
262 | * permanent log reservation of the given transaction. The remaining | 267 | * permanent log reservation of the given transaction. The remaining |
263 | * unused block and rt extent reservations are also inherited. This | 268 | * unused block and rt extent reservations are also inherited. This |
@@ -769,7 +774,7 @@ xfs_trans_unreserve_and_mod_sb( | |||
769 | */ | 774 | */ |
770 | static uint | 775 | static uint |
771 | xfs_trans_count_vecs( | 776 | xfs_trans_count_vecs( |
772 | xfs_trans_t *tp) | 777 | struct xfs_trans *tp) |
773 | { | 778 | { |
774 | int nvecs; | 779 | int nvecs; |
775 | xfs_log_item_desc_t *lidp; | 780 | xfs_log_item_desc_t *lidp; |
@@ -861,6 +866,158 @@ xfs_trans_fill_vecs( | |||
861 | } | 866 | } |
862 | 867 | ||
863 | /* | 868 | /* |
869 | * The committed item processing consists of calling the committed routine of | ||
870 | * each logged item, updating the item's position in the AIL if necessary, and | ||
871 | * unpinning each item. If the committed routine returns -1, then do nothing | ||
872 | * further with the item because it may have been freed. | ||
873 | * | ||
874 | * Since items are unlocked when they are copied to the incore log, it is | ||
875 | * possible for two transactions to be completing and manipulating the same | ||
876 | * item simultaneously. The AIL lock will protect the lsn field of each item. | ||
877 | * The value of this field can never go backwards. | ||
878 | * | ||
879 | * We unpin the items after repositioning them in the AIL, because otherwise | ||
880 | * they could be immediately flushed and we'd have to race with the flusher | ||
881 | * trying to pull the item from the AIL as we add it. | ||
882 | */ | ||
883 | static void | ||
884 | xfs_trans_item_committed( | ||
885 | struct xfs_log_item *lip, | ||
886 | xfs_lsn_t commit_lsn, | ||
887 | int aborted) | ||
888 | { | ||
889 | xfs_lsn_t item_lsn; | ||
890 | struct xfs_ail *ailp; | ||
891 | |||
892 | if (aborted) | ||
893 | lip->li_flags |= XFS_LI_ABORTED; | ||
894 | item_lsn = IOP_COMMITTED(lip, commit_lsn); | ||
895 | |||
896 | /* If the committed routine returns -1, item has been freed. */ | ||
897 | if (XFS_LSN_CMP(item_lsn, (xfs_lsn_t)-1) == 0) | ||
898 | return; | ||
899 | |||
900 | /* | ||
901 | * If the returned lsn is greater than what it contained before, update | ||
902 | * the location of the item in the AIL. If it is not, then do nothing. | ||
903 | * Items can never move backwards in the AIL. | ||
904 | * | ||
905 | * While the new lsn should usually be greater, it is possible that a | ||
906 | * later transaction completing simultaneously with an earlier one | ||
907 | * using the same item could complete first with a higher lsn. This | ||
908 | * would cause the earlier transaction to fail the test below. | ||
909 | */ | ||
910 | ailp = lip->li_ailp; | ||
911 | spin_lock(&ailp->xa_lock); | ||
912 | if (XFS_LSN_CMP(item_lsn, lip->li_lsn) > 0) { | ||
913 | /* | ||
914 | * This will set the item's lsn to item_lsn and update the | ||
915 | * position of the item in the AIL. | ||
916 | * | ||
917 | * xfs_trans_ail_update() drops the AIL lock. | ||
918 | */ | ||
919 | xfs_trans_ail_update(ailp, lip, item_lsn); | ||
920 | } else { | ||
921 | spin_unlock(&ailp->xa_lock); | ||
922 | } | ||
923 | |||
924 | /* | ||
925 | * Now that we've repositioned the item in the AIL, unpin it so it can | ||
926 | * be flushed. Pass information about buffer stale state down from the | ||
927 | * log item flags, if anyone else stales the buffer we do not want to | ||
928 | * pay any attention to it. | ||
929 | */ | ||
930 | IOP_UNPIN(lip); | ||
931 | } | ||
932 | |||
933 | /* Clear all the per-AG busy list items listed in this transaction */ | ||
934 | static void | ||
935 | xfs_trans_clear_busy_extents( | ||
936 | struct xfs_trans *tp) | ||
937 | { | ||
938 | xfs_log_busy_chunk_t *lbcp; | ||
939 | xfs_log_busy_slot_t *lbsp; | ||
940 | int i; | ||
941 | |||
942 | for (lbcp = &tp->t_busy; lbcp != NULL; lbcp = lbcp->lbc_next) { | ||
943 | i = 0; | ||
944 | for (lbsp = lbcp->lbc_busy; i < lbcp->lbc_unused; i++, lbsp++) { | ||
945 | if (XFS_LBC_ISFREE(lbcp, i)) | ||
946 | continue; | ||
947 | xfs_alloc_clear_busy(tp, lbsp->lbc_ag, lbsp->lbc_idx); | ||
948 | } | ||
949 | } | ||
950 | xfs_trans_free_busy(tp); | ||
951 | } | ||
952 | |||
953 | /* | ||
954 | * This is typically called by the LM when a transaction has been fully | ||
955 | * committed to disk. It needs to unpin the items which have | ||
956 | * been logged by the transaction and update their positions | ||
957 | * in the AIL if necessary. | ||
958 | * | ||
959 | * This also gets called when the transactions didn't get written out | ||
960 | * because of an I/O error. Abortflag & XFS_LI_ABORTED is set then. | ||
961 | */ | ||
962 | STATIC void | ||
963 | xfs_trans_committed( | ||
964 | struct xfs_trans *tp, | ||
965 | int abortflag) | ||
966 | { | ||
967 | xfs_log_item_desc_t *lidp; | ||
968 | xfs_log_item_chunk_t *licp; | ||
969 | xfs_log_item_chunk_t *next_licp; | ||
970 | |||
971 | /* Call the transaction's completion callback if there is one. */ | ||
972 | if (tp->t_callback != NULL) | ||
973 | tp->t_callback(tp, tp->t_callarg); | ||
974 | |||
975 | for (lidp = xfs_trans_first_item(tp); | ||
976 | lidp != NULL; | ||
977 | lidp = xfs_trans_next_item(tp, lidp)) { | ||
978 | xfs_trans_item_committed(lidp->lid_item, tp->t_lsn, abortflag); | ||
979 | } | ||
980 | |||
981 | /* free the item chunks, ignoring the embedded chunk */ | ||
982 | for (licp = tp->t_items.lic_next; licp != NULL; licp = next_licp) { | ||
983 | next_licp = licp->lic_next; | ||
984 | kmem_free(licp); | ||
985 | } | ||
986 | |||
987 | xfs_trans_clear_busy_extents(tp); | ||
988 | xfs_trans_free(tp); | ||
989 | } | ||
990 | |||
991 | /* | ||
992 | * Called from the trans_commit code when we notice that | ||
993 | * the filesystem is in the middle of a forced shutdown. | ||
994 | */ | ||
995 | STATIC void | ||
996 | xfs_trans_uncommit( | ||
997 | struct xfs_trans *tp, | ||
998 | uint flags) | ||
999 | { | ||
1000 | xfs_log_item_desc_t *lidp; | ||
1001 | |||
1002 | for (lidp = xfs_trans_first_item(tp); | ||
1003 | lidp != NULL; | ||
1004 | lidp = xfs_trans_next_item(tp, lidp)) { | ||
1005 | /* | ||
1006 | * Unpin all but those that aren't dirty. | ||
1007 | */ | ||
1008 | if (lidp->lid_flags & XFS_LID_DIRTY) | ||
1009 | IOP_UNPIN_REMOVE(lidp->lid_item, tp); | ||
1010 | } | ||
1011 | |||
1012 | xfs_trans_unreserve_and_mod_sb(tp); | ||
1013 | xfs_trans_unreserve_and_mod_dquots(tp); | ||
1014 | |||
1015 | xfs_trans_free_items(tp, flags); | ||
1016 | xfs_trans_free_busy(tp); | ||
1017 | xfs_trans_free(tp); | ||
1018 | } | ||
1019 | |||
1020 | /* | ||
864 | * Format the transaction direct to the iclog. This isolates the physical | 1021 | * Format the transaction direct to the iclog. This isolates the physical |
865 | * transaction commit operation from the logical operation and hence allows | 1022 | * transaction commit operation from the logical operation and hence allows |
866 | * other methods to be introduced without affecting the existing commit path. | 1023 | * other methods to be introduced without affecting the existing commit path. |
@@ -1111,35 +1268,6 @@ out_unreserve: | |||
1111 | } | 1268 | } |
1112 | 1269 | ||
1113 | /* | 1270 | /* |
1114 | * Called from the trans_commit code when we notice that | ||
1115 | * the filesystem is in the middle of a forced shutdown. | ||
1116 | */ | ||
1117 | STATIC void | ||
1118 | xfs_trans_uncommit( | ||
1119 | xfs_trans_t *tp, | ||
1120 | uint flags) | ||
1121 | { | ||
1122 | xfs_log_item_desc_t *lidp; | ||
1123 | |||
1124 | for (lidp = xfs_trans_first_item(tp); | ||
1125 | lidp != NULL; | ||
1126 | lidp = xfs_trans_next_item(tp, lidp)) { | ||
1127 | /* | ||
1128 | * Unpin all but those that aren't dirty. | ||
1129 | */ | ||
1130 | if (lidp->lid_flags & XFS_LID_DIRTY) | ||
1131 | IOP_UNPIN_REMOVE(lidp->lid_item, tp); | ||
1132 | } | ||
1133 | |||
1134 | xfs_trans_unreserve_and_mod_sb(tp); | ||
1135 | xfs_trans_unreserve_and_mod_dquots(tp); | ||
1136 | |||
1137 | xfs_trans_free_items(tp, flags); | ||
1138 | xfs_trans_free_busy(tp); | ||
1139 | xfs_trans_free(tp); | ||
1140 | } | ||
1141 | |||
1142 | /* | ||
1143 | * Unlock all of the transaction's items and free the transaction. | 1271 | * Unlock all of the transaction's items and free the transaction. |
1144 | * The transaction must not have modified any of its items, because | 1272 | * The transaction must not have modified any of its items, because |
1145 | * there is no way to restore them to their previous state. | 1273 | * there is no way to restore them to their previous state. |
@@ -1215,20 +1343,6 @@ xfs_trans_cancel( | |||
1215 | xfs_trans_free(tp); | 1343 | xfs_trans_free(tp); |
1216 | } | 1344 | } |
1217 | 1345 | ||
1218 | |||
1219 | /* | ||
1220 | * Free the transaction structure. If there is more clean up | ||
1221 | * to do when the structure is freed, add it here. | ||
1222 | */ | ||
1223 | STATIC void | ||
1224 | xfs_trans_free( | ||
1225 | xfs_trans_t *tp) | ||
1226 | { | ||
1227 | atomic_dec(&tp->t_mountp->m_active_trans); | ||
1228 | xfs_trans_free_dqinfo(tp); | ||
1229 | kmem_zone_free(xfs_trans_zone, tp); | ||
1230 | } | ||
1231 | |||
1232 | /* | 1346 | /* |
1233 | * Roll from one trans in the sequence of PERMANENT transactions to | 1347 | * Roll from one trans in the sequence of PERMANENT transactions to |
1234 | * the next: permanent transactions are only flushed out when | 1348 | * the next: permanent transactions are only flushed out when |
@@ -1298,141 +1412,3 @@ xfs_trans_roll( | |||
1298 | xfs_trans_ihold(trans, dp); | 1412 | xfs_trans_ihold(trans, dp); |
1299 | return 0; | 1413 | return 0; |
1300 | } | 1414 | } |
1301 | |||
1302 | /* | ||
1303 | * The committed item processing consists of calling the committed routine of | ||
1304 | * each logged item, updating the item's position in the AIL if necessary, and | ||
1305 | * unpinning each item. If the committed routine returns -1, then do nothing | ||
1306 | * further with the item because it may have been freed. | ||
1307 | * | ||
1308 | * Since items are unlocked when they are copied to the incore log, it is | ||
1309 | * possible for two transactions to be completing and manipulating the same | ||
1310 | * item simultaneously. The AIL lock will protect the lsn field of each item. | ||
1311 | * The value of this field can never go backwards. | ||
1312 | * | ||
1313 | * We unpin the items after repositioning them in the AIL, because otherwise | ||
1314 | * they could be immediately flushed and we'd have to race with the flusher | ||
1315 | * trying to pull the item from the AIL as we add it. | ||
1316 | */ | ||
1317 | static void | ||
1318 | xfs_trans_item_committed( | ||
1319 | xfs_log_item_t *lip, | ||
1320 | xfs_lsn_t commit_lsn, | ||
1321 | int aborted) | ||
1322 | { | ||
1323 | xfs_lsn_t item_lsn; | ||
1324 | struct xfs_ail *ailp; | ||
1325 | |||
1326 | if (aborted) | ||
1327 | lip->li_flags |= XFS_LI_ABORTED; | ||
1328 | |||
1329 | /* | ||
1330 | * Send in the ABORTED flag to the COMMITTED routine so that it knows | ||
1331 | * whether the transaction was aborted or not. | ||
1332 | */ | ||
1333 | item_lsn = IOP_COMMITTED(lip, commit_lsn); | ||
1334 | |||
1335 | /* | ||
1336 | * If the committed routine returns -1, item has been freed. | ||
1337 | */ | ||
1338 | if (XFS_LSN_CMP(item_lsn, (xfs_lsn_t)-1) == 0) | ||
1339 | return; | ||
1340 | |||
1341 | /* | ||
1342 | * If the returned lsn is greater than what it contained before, update | ||
1343 | * the location of the item in the AIL. If it is not, then do nothing. | ||
1344 | * Items can never move backwards in the AIL. | ||
1345 | * | ||
1346 | * While the new lsn should usually be greater, it is possible that a | ||
1347 | * later transaction completing simultaneously with an earlier one | ||
1348 | * using the same item could complete first with a higher lsn. This | ||
1349 | * would cause the earlier transaction to fail the test below. | ||
1350 | */ | ||
1351 | ailp = lip->li_ailp; | ||
1352 | spin_lock(&ailp->xa_lock); | ||
1353 | if (XFS_LSN_CMP(item_lsn, lip->li_lsn) > 0) { | ||
1354 | /* | ||
1355 | * This will set the item's lsn to item_lsn and update the | ||
1356 | * position of the item in the AIL. | ||
1357 | * | ||
1358 | * xfs_trans_ail_update() drops the AIL lock. | ||
1359 | */ | ||
1360 | xfs_trans_ail_update(ailp, lip, item_lsn); | ||
1361 | } else { | ||
1362 | spin_unlock(&ailp->xa_lock); | ||
1363 | } | ||
1364 | |||
1365 | /* | ||
1366 | * Now that we've repositioned the item in the AIL, unpin it so it can | ||
1367 | * be flushed. Pass information about buffer stale state down from the | ||
1368 | * log item flags, if anyone else stales the buffer we do not want to | ||
1369 | * pay any attention to it. | ||
1370 | */ | ||
1371 | IOP_UNPIN(lip); | ||
1372 | } | ||
1373 | |||
1374 | /* Clear all the per-AG busy list items listed in this transaction */ | ||
1375 | static void | ||
1376 | xfs_trans_clear_busy_extents( | ||
1377 | struct xfs_trans *tp) | ||
1378 | { | ||
1379 | xfs_log_busy_chunk_t *lbcp; | ||
1380 | xfs_log_busy_slot_t *lbsp; | ||
1381 | int i; | ||
1382 | |||
1383 | lbcp = &tp->t_busy; | ||
1384 | while (lbcp != NULL) { | ||
1385 | for (i = 0, lbsp = lbcp->lbc_busy; i < lbcp->lbc_unused; i++, lbsp++) { | ||
1386 | if (!XFS_LBC_ISFREE(lbcp, i)) { | ||
1387 | xfs_alloc_clear_busy(tp, lbsp->lbc_ag, | ||
1388 | lbsp->lbc_idx); | ||
1389 | } | ||
1390 | } | ||
1391 | lbcp = lbcp->lbc_next; | ||
1392 | } | ||
1393 | xfs_trans_free_busy(tp); | ||
1394 | } | ||
1395 | |||
1396 | /* | ||
1397 | * This is typically called by the LM when a transaction has been fully | ||
1398 | * committed to disk. It needs to unpin the items which have | ||
1399 | * been logged by the transaction and update their positions | ||
1400 | * in the AIL if necessary. | ||
1401 | * | ||
1402 | * This also gets called when the transactions didn't get written out | ||
1403 | * because of an I/O error. Abortflag & XFS_LI_ABORTED is set then. | ||
1404 | */ | ||
1405 | STATIC void | ||
1406 | xfs_trans_committed( | ||
1407 | xfs_trans_t *tp, | ||
1408 | int abortflag) | ||
1409 | { | ||
1410 | xfs_log_item_desc_t *lidp; | ||
1411 | xfs_log_item_chunk_t *licp; | ||
1412 | xfs_log_item_chunk_t *next_licp; | ||
1413 | |||
1414 | /* | ||
1415 | * Call the transaction's completion callback if there | ||
1416 | * is one. | ||
1417 | */ | ||
1418 | if (tp->t_callback != NULL) { | ||
1419 | tp->t_callback(tp, tp->t_callarg); | ||
1420 | } | ||
1421 | |||
1422 | for (lidp = xfs_trans_first_item(tp); | ||
1423 | lidp != NULL; | ||
1424 | lidp = xfs_trans_next_item(tp, lidp)) { | ||
1425 | xfs_trans_item_committed(lidp->lid_item, tp->t_lsn, abortflag); | ||
1426 | } | ||
1427 | |||
1428 | /* free the item chunks, ignoring the embedded chunk */ | ||
1429 | licp = tp->t_items.lic_next; | ||
1430 | while (licp != NULL) { | ||
1431 | next_licp = licp->lic_next; | ||
1432 | kmem_free(licp); | ||
1433 | licp = next_licp; | ||
1434 | } | ||
1435 | |||
1436 | xfs_trans_clear_busy_extents(tp); | ||
1437 | xfs_trans_free(tp); | ||
1438 | } | ||