diff options
author | Li Zefan <lizf@cn.fujitsu.com> | 2011-04-19 22:31:50 -0400 |
---|---|---|
committer | Li Zefan <lizf@cn.fujitsu.com> | 2011-04-25 04:46:09 -0400 |
commit | 33345d01522f8152f99dc84a3e7a1a45707f387f (patch) | |
tree | 6a978702dc4421768e63501fa15bc8fedd5bff32 /fs/btrfs/tree-log.c | |
parent | 0414efae7989a2183fb2cc000ab285c4c2836a00 (diff) |
Btrfs: Always use 64bit inode number
There's a potential problem in 32bit system when we exhaust 32bit inode
numbers and start to allocate big inode numbers, because btrfs uses
inode->i_ino in many places.
So here we always use BTRFS_I(inode)->location.objectid, which is an
u64 variable.
There are 2 exceptions that BTRFS_I(inode)->location.objectid !=
inode->i_ino: the btree inode (0 vs 1) and empty subvol dirs (256 vs 2),
and inode->i_ino will be used in those cases.
Another reason to make this change is I'm going to use a special inode
to save free ino cache, and the inode number must be > (u64)-256.
Signed-off-by: Li Zefan <lizf@cn.fujitsu.com>
Diffstat (limited to 'fs/btrfs/tree-log.c')
-rw-r--r-- | fs/btrfs/tree-log.c | 54 |
1 files changed, 27 insertions, 27 deletions
diff --git a/fs/btrfs/tree-log.c b/fs/btrfs/tree-log.c index c50271ad3157..4323dc68d6cd 100644 --- a/fs/btrfs/tree-log.c +++ b/fs/btrfs/tree-log.c | |||
@@ -519,7 +519,7 @@ static noinline int replay_one_extent(struct btrfs_trans_handle *trans, | |||
519 | * file. This must be done before the btrfs_drop_extents run | 519 | * file. This must be done before the btrfs_drop_extents run |
520 | * so we don't try to drop this extent. | 520 | * so we don't try to drop this extent. |
521 | */ | 521 | */ |
522 | ret = btrfs_lookup_file_extent(trans, root, path, inode->i_ino, | 522 | ret = btrfs_lookup_file_extent(trans, root, path, btrfs_ino(inode), |
523 | start, 0); | 523 | start, 0); |
524 | 524 | ||
525 | if (ret == 0 && | 525 | if (ret == 0 && |
@@ -832,7 +832,7 @@ again: | |||
832 | read_extent_buffer(eb, name, (unsigned long)(ref + 1), namelen); | 832 | read_extent_buffer(eb, name, (unsigned long)(ref + 1), namelen); |
833 | 833 | ||
834 | /* if we already have a perfect match, we're done */ | 834 | /* if we already have a perfect match, we're done */ |
835 | if (inode_in_dir(root, path, dir->i_ino, inode->i_ino, | 835 | if (inode_in_dir(root, path, btrfs_ino(dir), btrfs_ino(inode), |
836 | btrfs_inode_ref_index(eb, ref), | 836 | btrfs_inode_ref_index(eb, ref), |
837 | name, namelen)) { | 837 | name, namelen)) { |
838 | goto out; | 838 | goto out; |
@@ -960,8 +960,9 @@ static noinline int fixup_inode_link_count(struct btrfs_trans_handle *trans, | |||
960 | unsigned long ptr; | 960 | unsigned long ptr; |
961 | unsigned long ptr_end; | 961 | unsigned long ptr_end; |
962 | int name_len; | 962 | int name_len; |
963 | u64 ino = btrfs_ino(inode); | ||
963 | 964 | ||
964 | key.objectid = inode->i_ino; | 965 | key.objectid = ino; |
965 | key.type = BTRFS_INODE_REF_KEY; | 966 | key.type = BTRFS_INODE_REF_KEY; |
966 | key.offset = (u64)-1; | 967 | key.offset = (u64)-1; |
967 | 968 | ||
@@ -980,7 +981,7 @@ static noinline int fixup_inode_link_count(struct btrfs_trans_handle *trans, | |||
980 | } | 981 | } |
981 | btrfs_item_key_to_cpu(path->nodes[0], &key, | 982 | btrfs_item_key_to_cpu(path->nodes[0], &key, |
982 | path->slots[0]); | 983 | path->slots[0]); |
983 | if (key.objectid != inode->i_ino || | 984 | if (key.objectid != ino || |
984 | key.type != BTRFS_INODE_REF_KEY) | 985 | key.type != BTRFS_INODE_REF_KEY) |
985 | break; | 986 | break; |
986 | ptr = btrfs_item_ptr_offset(path->nodes[0], path->slots[0]); | 987 | ptr = btrfs_item_ptr_offset(path->nodes[0], path->slots[0]); |
@@ -1011,10 +1012,10 @@ static noinline int fixup_inode_link_count(struct btrfs_trans_handle *trans, | |||
1011 | if (inode->i_nlink == 0) { | 1012 | if (inode->i_nlink == 0) { |
1012 | if (S_ISDIR(inode->i_mode)) { | 1013 | if (S_ISDIR(inode->i_mode)) { |
1013 | ret = replay_dir_deletes(trans, root, NULL, path, | 1014 | ret = replay_dir_deletes(trans, root, NULL, path, |
1014 | inode->i_ino, 1); | 1015 | ino, 1); |
1015 | BUG_ON(ret); | 1016 | BUG_ON(ret); |
1016 | } | 1017 | } |
1017 | ret = insert_orphan_item(trans, root, inode->i_ino); | 1018 | ret = insert_orphan_item(trans, root, ino); |
1018 | BUG_ON(ret); | 1019 | BUG_ON(ret); |
1019 | } | 1020 | } |
1020 | btrfs_free_path(path); | 1021 | btrfs_free_path(path); |
@@ -2197,6 +2198,7 @@ int btrfs_del_dir_entries_in_log(struct btrfs_trans_handle *trans, | |||
2197 | int ret; | 2198 | int ret; |
2198 | int err = 0; | 2199 | int err = 0; |
2199 | int bytes_del = 0; | 2200 | int bytes_del = 0; |
2201 | u64 dir_ino = btrfs_ino(dir); | ||
2200 | 2202 | ||
2201 | if (BTRFS_I(dir)->logged_trans < trans->transid) | 2203 | if (BTRFS_I(dir)->logged_trans < trans->transid) |
2202 | return 0; | 2204 | return 0; |
@@ -2212,7 +2214,7 @@ int btrfs_del_dir_entries_in_log(struct btrfs_trans_handle *trans, | |||
2212 | if (!path) | 2214 | if (!path) |
2213 | return -ENOMEM; | 2215 | return -ENOMEM; |
2214 | 2216 | ||
2215 | di = btrfs_lookup_dir_item(trans, log, path, dir->i_ino, | 2217 | di = btrfs_lookup_dir_item(trans, log, path, dir_ino, |
2216 | name, name_len, -1); | 2218 | name, name_len, -1); |
2217 | if (IS_ERR(di)) { | 2219 | if (IS_ERR(di)) { |
2218 | err = PTR_ERR(di); | 2220 | err = PTR_ERR(di); |
@@ -2224,7 +2226,7 @@ int btrfs_del_dir_entries_in_log(struct btrfs_trans_handle *trans, | |||
2224 | BUG_ON(ret); | 2226 | BUG_ON(ret); |
2225 | } | 2227 | } |
2226 | btrfs_release_path(log, path); | 2228 | btrfs_release_path(log, path); |
2227 | di = btrfs_lookup_dir_index_item(trans, log, path, dir->i_ino, | 2229 | di = btrfs_lookup_dir_index_item(trans, log, path, dir_ino, |
2228 | index, name, name_len, -1); | 2230 | index, name, name_len, -1); |
2229 | if (IS_ERR(di)) { | 2231 | if (IS_ERR(di)) { |
2230 | err = PTR_ERR(di); | 2232 | err = PTR_ERR(di); |
@@ -2242,7 +2244,7 @@ int btrfs_del_dir_entries_in_log(struct btrfs_trans_handle *trans, | |||
2242 | if (bytes_del) { | 2244 | if (bytes_del) { |
2243 | struct btrfs_key key; | 2245 | struct btrfs_key key; |
2244 | 2246 | ||
2245 | key.objectid = dir->i_ino; | 2247 | key.objectid = dir_ino; |
2246 | key.offset = 0; | 2248 | key.offset = 0; |
2247 | key.type = BTRFS_INODE_ITEM_KEY; | 2249 | key.type = BTRFS_INODE_ITEM_KEY; |
2248 | btrfs_release_path(log, path); | 2250 | btrfs_release_path(log, path); |
@@ -2300,7 +2302,7 @@ int btrfs_del_inode_ref_in_log(struct btrfs_trans_handle *trans, | |||
2300 | log = root->log_root; | 2302 | log = root->log_root; |
2301 | mutex_lock(&BTRFS_I(inode)->log_mutex); | 2303 | mutex_lock(&BTRFS_I(inode)->log_mutex); |
2302 | 2304 | ||
2303 | ret = btrfs_del_inode_ref(trans, log, name, name_len, inode->i_ino, | 2305 | ret = btrfs_del_inode_ref(trans, log, name, name_len, btrfs_ino(inode), |
2304 | dirid, &index); | 2306 | dirid, &index); |
2305 | mutex_unlock(&BTRFS_I(inode)->log_mutex); | 2307 | mutex_unlock(&BTRFS_I(inode)->log_mutex); |
2306 | if (ret == -ENOSPC) { | 2308 | if (ret == -ENOSPC) { |
@@ -2366,13 +2368,14 @@ static noinline int log_dir_items(struct btrfs_trans_handle *trans, | |||
2366 | int nritems; | 2368 | int nritems; |
2367 | u64 first_offset = min_offset; | 2369 | u64 first_offset = min_offset; |
2368 | u64 last_offset = (u64)-1; | 2370 | u64 last_offset = (u64)-1; |
2371 | u64 ino = btrfs_ino(inode); | ||
2369 | 2372 | ||
2370 | log = root->log_root; | 2373 | log = root->log_root; |
2371 | max_key.objectid = inode->i_ino; | 2374 | max_key.objectid = ino; |
2372 | max_key.offset = (u64)-1; | 2375 | max_key.offset = (u64)-1; |
2373 | max_key.type = key_type; | 2376 | max_key.type = key_type; |
2374 | 2377 | ||
2375 | min_key.objectid = inode->i_ino; | 2378 | min_key.objectid = ino; |
2376 | min_key.type = key_type; | 2379 | min_key.type = key_type; |
2377 | min_key.offset = min_offset; | 2380 | min_key.offset = min_offset; |
2378 | 2381 | ||
@@ -2385,9 +2388,8 @@ static noinline int log_dir_items(struct btrfs_trans_handle *trans, | |||
2385 | * we didn't find anything from this transaction, see if there | 2388 | * we didn't find anything from this transaction, see if there |
2386 | * is anything at all | 2389 | * is anything at all |
2387 | */ | 2390 | */ |
2388 | if (ret != 0 || min_key.objectid != inode->i_ino || | 2391 | if (ret != 0 || min_key.objectid != ino || min_key.type != key_type) { |
2389 | min_key.type != key_type) { | 2392 | min_key.objectid = ino; |
2390 | min_key.objectid = inode->i_ino; | ||
2391 | min_key.type = key_type; | 2393 | min_key.type = key_type; |
2392 | min_key.offset = (u64)-1; | 2394 | min_key.offset = (u64)-1; |
2393 | btrfs_release_path(root, path); | 2395 | btrfs_release_path(root, path); |
@@ -2396,7 +2398,7 @@ static noinline int log_dir_items(struct btrfs_trans_handle *trans, | |||
2396 | btrfs_release_path(root, path); | 2398 | btrfs_release_path(root, path); |
2397 | return ret; | 2399 | return ret; |
2398 | } | 2400 | } |
2399 | ret = btrfs_previous_item(root, path, inode->i_ino, key_type); | 2401 | ret = btrfs_previous_item(root, path, ino, key_type); |
2400 | 2402 | ||
2401 | /* if ret == 0 there are items for this type, | 2403 | /* if ret == 0 there are items for this type, |
2402 | * create a range to tell us the last key of this type. | 2404 | * create a range to tell us the last key of this type. |
@@ -2414,7 +2416,7 @@ static noinline int log_dir_items(struct btrfs_trans_handle *trans, | |||
2414 | } | 2416 | } |
2415 | 2417 | ||
2416 | /* go backward to find any previous key */ | 2418 | /* go backward to find any previous key */ |
2417 | ret = btrfs_previous_item(root, path, inode->i_ino, key_type); | 2419 | ret = btrfs_previous_item(root, path, ino, key_type); |
2418 | if (ret == 0) { | 2420 | if (ret == 0) { |
2419 | struct btrfs_key tmp; | 2421 | struct btrfs_key tmp; |
2420 | btrfs_item_key_to_cpu(path->nodes[0], &tmp, path->slots[0]); | 2422 | btrfs_item_key_to_cpu(path->nodes[0], &tmp, path->slots[0]); |
@@ -2449,8 +2451,7 @@ static noinline int log_dir_items(struct btrfs_trans_handle *trans, | |||
2449 | for (i = path->slots[0]; i < nritems; i++) { | 2451 | for (i = path->slots[0]; i < nritems; i++) { |
2450 | btrfs_item_key_to_cpu(src, &min_key, i); | 2452 | btrfs_item_key_to_cpu(src, &min_key, i); |
2451 | 2453 | ||
2452 | if (min_key.objectid != inode->i_ino || | 2454 | if (min_key.objectid != ino || min_key.type != key_type) |
2453 | min_key.type != key_type) | ||
2454 | goto done; | 2455 | goto done; |
2455 | ret = overwrite_item(trans, log, dst_path, src, i, | 2456 | ret = overwrite_item(trans, log, dst_path, src, i, |
2456 | &min_key); | 2457 | &min_key); |
@@ -2471,7 +2472,7 @@ static noinline int log_dir_items(struct btrfs_trans_handle *trans, | |||
2471 | goto done; | 2472 | goto done; |
2472 | } | 2473 | } |
2473 | btrfs_item_key_to_cpu(path->nodes[0], &tmp, path->slots[0]); | 2474 | btrfs_item_key_to_cpu(path->nodes[0], &tmp, path->slots[0]); |
2474 | if (tmp.objectid != inode->i_ino || tmp.type != key_type) { | 2475 | if (tmp.objectid != ino || tmp.type != key_type) { |
2475 | last_offset = (u64)-1; | 2476 | last_offset = (u64)-1; |
2476 | goto done; | 2477 | goto done; |
2477 | } | 2478 | } |
@@ -2497,8 +2498,7 @@ done: | |||
2497 | * is valid | 2498 | * is valid |
2498 | */ | 2499 | */ |
2499 | ret = insert_dir_log_key(trans, log, path, key_type, | 2500 | ret = insert_dir_log_key(trans, log, path, key_type, |
2500 | inode->i_ino, first_offset, | 2501 | ino, first_offset, last_offset); |
2501 | last_offset); | ||
2502 | if (ret) | 2502 | if (ret) |
2503 | err = ret; | 2503 | err = ret; |
2504 | } | 2504 | } |
@@ -2742,6 +2742,7 @@ static int btrfs_log_inode(struct btrfs_trans_handle *trans, | |||
2742 | int nritems; | 2742 | int nritems; |
2743 | int ins_start_slot = 0; | 2743 | int ins_start_slot = 0; |
2744 | int ins_nr; | 2744 | int ins_nr; |
2745 | u64 ino = btrfs_ino(inode); | ||
2745 | 2746 | ||
2746 | log = root->log_root; | 2747 | log = root->log_root; |
2747 | 2748 | ||
@@ -2754,11 +2755,11 @@ static int btrfs_log_inode(struct btrfs_trans_handle *trans, | |||
2754 | return -ENOMEM; | 2755 | return -ENOMEM; |
2755 | } | 2756 | } |
2756 | 2757 | ||
2757 | min_key.objectid = inode->i_ino; | 2758 | min_key.objectid = ino; |
2758 | min_key.type = BTRFS_INODE_ITEM_KEY; | 2759 | min_key.type = BTRFS_INODE_ITEM_KEY; |
2759 | min_key.offset = 0; | 2760 | min_key.offset = 0; |
2760 | 2761 | ||
2761 | max_key.objectid = inode->i_ino; | 2762 | max_key.objectid = ino; |
2762 | 2763 | ||
2763 | /* today the code can only do partial logging of directories */ | 2764 | /* today the code can only do partial logging of directories */ |
2764 | if (!S_ISDIR(inode->i_mode)) | 2765 | if (!S_ISDIR(inode->i_mode)) |
@@ -2781,8 +2782,7 @@ static int btrfs_log_inode(struct btrfs_trans_handle *trans, | |||
2781 | 2782 | ||
2782 | if (inode_only == LOG_INODE_EXISTS) | 2783 | if (inode_only == LOG_INODE_EXISTS) |
2783 | max_key_type = BTRFS_XATTR_ITEM_KEY; | 2784 | max_key_type = BTRFS_XATTR_ITEM_KEY; |
2784 | ret = drop_objectid_items(trans, log, path, | 2785 | ret = drop_objectid_items(trans, log, path, ino, max_key_type); |
2785 | inode->i_ino, max_key_type); | ||
2786 | } else { | 2786 | } else { |
2787 | ret = btrfs_truncate_inode_items(trans, log, inode, 0, 0); | 2787 | ret = btrfs_truncate_inode_items(trans, log, inode, 0, 0); |
2788 | } | 2788 | } |
@@ -2800,7 +2800,7 @@ static int btrfs_log_inode(struct btrfs_trans_handle *trans, | |||
2800 | break; | 2800 | break; |
2801 | again: | 2801 | again: |
2802 | /* note, ins_nr might be > 0 here, cleanup outside the loop */ | 2802 | /* note, ins_nr might be > 0 here, cleanup outside the loop */ |
2803 | if (min_key.objectid != inode->i_ino) | 2803 | if (min_key.objectid != ino) |
2804 | break; | 2804 | break; |
2805 | if (min_key.type > max_key.type) | 2805 | if (min_key.type > max_key.type) |
2806 | break; | 2806 | break; |