aboutsummaryrefslogtreecommitdiffstats
path: root/fs/btrfs/delayed-inode.c
diff options
context:
space:
mode:
authorJeff Mahoney <jeffm@suse.com>2012-03-12 11:03:00 -0400
committerDavid Sterba <dsterba@suse.cz>2012-03-22 06:52:54 -0400
commit79787eaab46121d4713ed03c8fc63b9ec3eaec76 (patch)
treeee6b17d0811ee54ab74a03aa4e0bb92769d2f12a /fs/btrfs/delayed-inode.c
parent49b25e0540904be0bf558b84475c69d72e4de66e (diff)
btrfs: replace many BUG_ONs with proper error handling
btrfs currently handles most errors with BUG_ON. This patch is a work-in- progress but aims to handle most errors other than internal logic errors and ENOMEM more gracefully. This iteration prevents most crashes but can run into lockups with the page lock on occasion when the timing "works out." Signed-off-by: Jeff Mahoney <jeffm@suse.com>
Diffstat (limited to 'fs/btrfs/delayed-inode.c')
-rw-r--r--fs/btrfs/delayed-inode.c27
1 files changed, 20 insertions, 7 deletions
diff --git a/fs/btrfs/delayed-inode.c b/fs/btrfs/delayed-inode.c
index 6829590d0fbb..03e3748d84d0 100644
--- a/fs/btrfs/delayed-inode.c
+++ b/fs/btrfs/delayed-inode.c
@@ -115,6 +115,7 @@ static struct btrfs_delayed_node *btrfs_get_delayed_node(struct inode *inode)
115 return NULL; 115 return NULL;
116} 116}
117 117
118/* Will return either the node or PTR_ERR(-ENOMEM) */
118static struct btrfs_delayed_node *btrfs_get_or_create_delayed_node( 119static struct btrfs_delayed_node *btrfs_get_or_create_delayed_node(
119 struct inode *inode) 120 struct inode *inode)
120{ 121{
@@ -1106,16 +1107,25 @@ static int btrfs_update_delayed_inode(struct btrfs_trans_handle *trans,
1106 return 0; 1107 return 0;
1107} 1108}
1108 1109
1109/* Called when committing the transaction. */ 1110/*
1111 * Called when committing the transaction.
1112 * Returns 0 on success.
1113 * Returns < 0 on error and returns with an aborted transaction with any
1114 * outstanding delayed items cleaned up.
1115 */
1110int btrfs_run_delayed_items(struct btrfs_trans_handle *trans, 1116int btrfs_run_delayed_items(struct btrfs_trans_handle *trans,
1111 struct btrfs_root *root) 1117 struct btrfs_root *root)
1112{ 1118{
1119 struct btrfs_root *curr_root = root;
1113 struct btrfs_delayed_root *delayed_root; 1120 struct btrfs_delayed_root *delayed_root;
1114 struct btrfs_delayed_node *curr_node, *prev_node; 1121 struct btrfs_delayed_node *curr_node, *prev_node;
1115 struct btrfs_path *path; 1122 struct btrfs_path *path;
1116 struct btrfs_block_rsv *block_rsv; 1123 struct btrfs_block_rsv *block_rsv;
1117 int ret = 0; 1124 int ret = 0;
1118 1125
1126 if (trans->aborted)
1127 return -EIO;
1128
1119 path = btrfs_alloc_path(); 1129 path = btrfs_alloc_path();
1120 if (!path) 1130 if (!path)
1121 return -ENOMEM; 1131 return -ENOMEM;
@@ -1128,17 +1138,18 @@ int btrfs_run_delayed_items(struct btrfs_trans_handle *trans,
1128 1138
1129 curr_node = btrfs_first_delayed_node(delayed_root); 1139 curr_node = btrfs_first_delayed_node(delayed_root);
1130 while (curr_node) { 1140 while (curr_node) {
1131 root = curr_node->root; 1141 curr_root = curr_node->root;
1132 ret = btrfs_insert_delayed_items(trans, path, root, 1142 ret = btrfs_insert_delayed_items(trans, path, curr_root,
1133 curr_node); 1143 curr_node);
1134 if (!ret) 1144 if (!ret)
1135 ret = btrfs_delete_delayed_items(trans, path, root, 1145 ret = btrfs_delete_delayed_items(trans, path,
1136 curr_node); 1146 curr_root, curr_node);
1137 if (!ret) 1147 if (!ret)
1138 ret = btrfs_update_delayed_inode(trans, root, path, 1148 ret = btrfs_update_delayed_inode(trans, curr_root,
1139 curr_node); 1149 path, curr_node);
1140 if (ret) { 1150 if (ret) {
1141 btrfs_release_delayed_node(curr_node); 1151 btrfs_release_delayed_node(curr_node);
1152 btrfs_abort_transaction(trans, root, ret);
1142 break; 1153 break;
1143 } 1154 }
1144 1155
@@ -1149,6 +1160,7 @@ int btrfs_run_delayed_items(struct btrfs_trans_handle *trans,
1149 1160
1150 btrfs_free_path(path); 1161 btrfs_free_path(path);
1151 trans->block_rsv = block_rsv; 1162 trans->block_rsv = block_rsv;
1163
1152 return ret; 1164 return ret;
1153} 1165}
1154 1166
@@ -1369,6 +1381,7 @@ void btrfs_balance_delayed_items(struct btrfs_root *root)
1369 btrfs_wq_run_delayed_node(delayed_root, root, 0); 1381 btrfs_wq_run_delayed_node(delayed_root, root, 0);
1370} 1382}
1371 1383
1384/* Will return 0 or -ENOMEM */
1372int btrfs_insert_delayed_dir_index(struct btrfs_trans_handle *trans, 1385int btrfs_insert_delayed_dir_index(struct btrfs_trans_handle *trans,
1373 struct btrfs_root *root, const char *name, 1386 struct btrfs_root *root, const char *name,
1374 int name_len, struct inode *dir, 1387 int name_len, struct inode *dir,