[PATCH V2 2/2] Btrfs: make __merge_refs() return type be void
__merge_refs() always return 0, it is unnecessary for the caller to check the return value. Signed-off-by: Wang Shilong wangsl-f...@cn.fujitsu.com --- Changelog v1-v2: - don't make __add_missing_keys() return type to be void so that makes people aware of unhandled BUG_ON() from read_tree block(). - rename title to be more accurate --- fs/btrfs/backref.c | 11 +++ 1 files changed, 3 insertions(+), 8 deletions(-) diff --git a/fs/btrfs/backref.c b/fs/btrfs/backref.c index dc200f6..13720d4 100644 --- a/fs/btrfs/backref.c +++ b/fs/btrfs/backref.c @@ -443,7 +443,7 @@ static int __add_missing_keys(struct btrfs_fs_info *fs_info, * having a parent). * mode = 2: merge identical parents */ -static int __merge_refs(struct list_head *head, int mode) +static void __merge_refs(struct list_head *head, int mode) { struct list_head *pos1; @@ -489,7 +489,6 @@ static int __merge_refs(struct list_head *head, int mode) } } - return 0; } /* @@ -884,18 +883,14 @@ again: if (ret) goto out; - ret = __merge_refs(prefs, 1); - if (ret) - goto out; + __merge_refs(prefs, 1); ret = __resolve_indirect_refs(fs_info, search_commit_root, time_seq, prefs, extent_item_pos); if (ret) goto out; - ret = __merge_refs(prefs, 2); - if (ret) - goto out; + __merge_refs(prefs, 2); while (!list_empty(prefs)) { ref = list_first_entry(prefs, struct __prelim_ref, list); -- 1.7.7.6 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] Btrfs: make some functions return type be void in backref.c
Hello, David Patch V2 has been sent out,many thanks for your review ^_^ Thanks, Wang On Wed, Apr 10, 2013 at 07:22:51PM +0800, Wang Shilong wrote: From: Wang Shilong wangsl-f...@cn.fujitsu.com __merge_refs() and __add_missing_keys() always return 0, it is unnecessary for the caller to check the return value. ok for __merge_refs, nak for __add_missing_keys: there's unhandled BUG_ON from read_tree_block 422 eb = read_tree_block(fs_info-tree_root, ref-wanted_disk_byte, 423 fs_info-tree_root-leafsize, 0); 424 BUG_ON(!eb); this should become a proper error handling someday and use the int return value. Keep the callers aware of that. david -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [obsoleted] [PATCH 1/5 v5] btrfs-progs: make btrfs dev scan multi path aware
This patch is replaced By: btrfs-progs: avoid ioctl for multipath-dev with its non-multipath path which is also sent to this mailing list. thanks, Anand On 03/27/2013 06:07 PM, Anand Jain wrote: We should avoid using non multi-path (mp) path for mp disks As of now there is no good way (like api) to check that. A workaround way is to check if the O_EXCL open is unsuccessful. This is safe since otherwise the BTRFS_IOC_SCAN_DEV ioctl would fail if the disk-path can not be opened with the flag O_EXCL set. This patch also includes some (error) print format changes related to the btrfs dev scan.. Signed-off-by: Anand Jain anand.j...@oracle.com --- cmds-device.c | 53 +++-- utils.c | 31 --- 2 files changed, 63 insertions(+), 21 deletions(-) diff --git a/cmds-device.c b/cmds-device.c index 41e79d3..b8d05fd 100644 --- a/cmds-device.c +++ b/cmds-device.c @@ -185,7 +185,7 @@ static const char * const cmd_scan_dev_usage[] = { static int cmd_scan_dev(int argc, char **argv) { - int i, fd, e; + int i, fd, e, ret = 0; int checklist = 1; int devstart = 1; @@ -197,6 +197,21 @@ static int cmd_scan_dev(int argc, char **argv) devstart += 1; } + fd = open(/dev/btrfs-control, O_RDWR); + e = errno; + if (fd 0) { + FILE *mfd = popen(lsmod | grep btrfs, r); + char buf[16]; + + if (fread (buf, 1, sizeof (buf), mfd) 0) + fprintf(stderr, ERROR: failed to open \ + /dev/btrfs-control - %s\n, strerror(e)); + else + fprintf(stderr, ERROR: btrfs kernel module \ + is not loaded\n); + return 10; + } + if(argc=devstart){ int ret; @@ -210,20 +225,30 @@ static int cmd_scan_dev(int argc, char **argv) fprintf(stderr, ERROR: error %d while scanning\n, ret); return 18; } + printf(done\n); return 0; } - fd = open(/dev/btrfs-control, O_RDWR); - if (fd 0) { - perror(failed to open /dev/btrfs-control); - return 10; - } - + printf(Scanning for Btrfs in\n); for( i = devstart ; i argc ; i++ ){ + int fdt; struct btrfs_ioctl_vol_args args; - int ret; + printf( %s , argv[i]); + fflush(stdout); - printf(Scanning for Btrfs filesystems in '%s'\n, argv[i]); + /* +* If for a multipath (mp) disk user provides the +* non-mp path then open with flag O_EXCL will fail, +* (also ioctl opens with O_EXCL), So test it before +* calling ioctl. +*/ + fdt = open(argv[i], O_RDONLY|O_EXCL); + if (fdt 0) { + perror(ERROR); + ret = -1; + continue; + } + close(fdt); strncpy_null(args.name, argv[i]); /* @@ -235,15 +260,15 @@ static int cmd_scan_dev(int argc, char **argv) e = errno; if( ret 0 ){ - close(fd); - fprintf(stderr, ERROR: unable to scan the device '%s' - %s\n, - argv[i], strerror(e)); - return 11; + fprintf(stderr, ERROR: unable to scan - %s\n, + strerror(e)); + ret = -1; } + printf(found\n); } close(fd); - return 0; + return ret; } static const char * const cmd_ready_dev_usage[] = { diff --git a/utils.c b/utils.c index a4f7b06..3a0d444 100644 --- a/utils.c +++ b/utils.c @@ -1105,25 +1105,32 @@ again: if (!S_ISBLK(st.st_mode)) { continue; } - fd = open(fullpath, O_RDONLY); + fd = open(fullpath, O_RDONLY|O_EXCL); if (fd 0) { /* ignore the following errors: ENXIO (device don't exists) ENOMEDIUM (No medium found - like a cd tray empty) + EBUSY (when mp disk is opened + using non-mp path). */ - if(errno != ENXIO errno != ENOMEDIUM) + if(errno != ENXIO errno != ENOMEDIUM + errno != EBUSY) fprintf(stderr, failed to read %s: %s\n, fullpath,
[PATCH] btrfs-progs: avoid ioctl for multipath-dev with its non-multipath path
We should avoid using non multi-path (mp) path for mp disks As of now there is no good way (like api) to check that. A workaround way is to check if the O_EXCL open is unsuccessful. This is safe since otherwise the BTRFS_IOC_SCAN_DEV ioctl would fail if the disk-path can not be opened with the flag O_EXCL set. Signed-off-by: Anand Jain anand.j...@oracle.com --- utils.c | 30 +- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/utils.c b/utils.c index 3308668..0231677 100644 --- a/utils.c +++ b/utils.c @@ -1105,6 +1105,13 @@ again: if (!S_ISBLK(st.st_mode)) { continue; } + + /* Do not test for O_EXCL here since btrfs when + * mounted will open with O_EXCL, and if we don't + * allow btrfs_scan_one_device pass thru + * btrfs fi show will not show the btrfs fs which + * are mounted + */ fd = open(fullpath, O_RDONLY); if (fd 0) { /* ignore the following errors: @@ -1122,10 +1129,18 @@ again: num_devices, BTRFS_SUPER_INFO_OFFSET, 0ull); + close(fd); + if (ret == 0 flags BTRFS_SCAN_REGISTER) { + /* Test if the dev is already opened with O_EXCL flag + * if yes then no need to call ioctl since the + * ioctl will anyway fail. + */ + fd = open(fullpath, O_RDONLY|O_EXCL); + if (fd 0) continue; + close(fd); btrfs_register_one_device(fullpath); } - close(fd); } if (!list_empty(pending_list)) { free(pending); @@ -1444,6 +1459,12 @@ scan_again: continue; } + /* Do not test for O_EXCL here since btrfs when + * mounted will open with O_EXCL, and if we don't + * allow btrfs_scan_one_device pass thru + * btrfs fi show will not show the btrfs fs which + * are mounted + */ fd = open(fullpath, O_RDONLY); if (fd 0) { fprintf(stderr, failed to open %s: %s\n, @@ -1455,6 +1476,13 @@ scan_again: BTRFS_SUPER_INFO_OFFSET, 0ull); if (ret == 0 flags BTRFS_SCAN_REGISTER) { + /* Test if the dev is already opened with O_EXCL flag + * if yes then no need to call ioctl since the + * ioctl will anyway fail. + */ + fd = open(fullpath, O_RDONLY|O_EXCL); + if (fd 0) continue; + close(fd); btrfs_register_one_device(fullpath); } close(fd); -- 1.8.1.227.g44fe835 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 1/2] Btrfs: fix unblocked autodefraggers when remount
The new mount option is set after parsing the remount arguments, so it is wrong that checking the autodefrag is close or not at btrfs_remount_prepare(). Fix it. Signed-off-by: Miao Xie mi...@cn.fujitsu.com --- fs/btrfs/super.c | 10 +++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c index 68a29a1..0f03569 100644 --- a/fs/btrfs/super.c +++ b/fs/btrfs/super.c @@ -1202,11 +1202,14 @@ static void btrfs_resize_thread_pool(struct btrfs_fs_info *fs_info, new_pool_size); } -static inline void btrfs_remount_prepare(struct btrfs_fs_info *fs_info, -unsigned long old_opts, int flags) +static inline void btrfs_remount_prepare(struct btrfs_fs_info *fs_info) { set_bit(BTRFS_FS_STATE_REMOUNTING, fs_info-fs_state); +} +static inline void btrfs_remount_begin(struct btrfs_fs_info *fs_info, + unsigned long old_opts, int flags) +{ if (btrfs_raw_test_opt(old_opts, AUTO_DEFRAG) (!btrfs_raw_test_opt(fs_info-mount_opt, AUTO_DEFRAG) || (flags MS_RDONLY))) { @@ -1247,7 +1250,7 @@ static int btrfs_remount(struct super_block *sb, int *flags, char *data) unsigned int old_metadata_ratio = fs_info-metadata_ratio; int ret; - btrfs_remount_prepare(fs_info, old_opts, *flags); + btrfs_remount_prepare(fs_info); ret = btrfs_parse_options(root, data); if (ret) { @@ -1255,6 +1258,7 @@ static int btrfs_remount(struct super_block *sb, int *flags, char *data) goto restore; } + btrfs_remount_begin(fs_info, old_opts, *flags); btrfs_resize_thread_pool(fs_info, fs_info-thread_pool_size, old_thread_pool_size); -- 1.8.0.1 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 2/2] Btrfs: use a lock to protect incompat/compat flag of the super block
The following case will make the incompat/compat flag of the super block be recovered. Task1 |Task2 flags = btrfs_super_incompat_flags(); | |flags = btrfs_super_incompat_flags(); flags |= new_flag1;| |flags |= new_flag2; btrfs_set_super_incompat_flags(flags); | |btrfs_set_super_incompat_flags(flags); the new_flag1 is recovered. In order to avoid this problem, we introduce a lock named super_lock into the btrfs_fs_info structure. If we want to update incompat/compat flags of the super block, we must hold it. Signed-off-by: Miao Xie mi...@cn.fujitsu.com --- fs/btrfs/ctree.h | 22 -- fs/btrfs/disk-io.c | 5 + fs/btrfs/volumes.c | 10 +- 3 files changed, 26 insertions(+), 11 deletions(-) diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h index 0d82922..a883e47 100644 --- a/fs/btrfs/ctree.h +++ b/fs/btrfs/ctree.h @@ -1360,6 +1360,17 @@ struct btrfs_fs_info { wait_queue_head_t transaction_blocked_wait; wait_queue_head_t async_submit_wait; + /* +* Used to protect the incompat_flags, compat_flags, compat_ro_flags +* when they are updated. +* +* Because we do not clear the flags for ever, so we needn't use +* the lock on the read side. +* +* We also needn't use the lock when we mount the fs, because +* there is no other task which will update the flag. +*/ + spinlock_t super_lock; struct btrfs_super_block *super_copy; struct btrfs_super_block *super_for_commit; struct block_device *__bdev; @@ -3663,8 +3674,15 @@ static inline void __btrfs_set_fs_incompat(struct btrfs_fs_info *fs_info, disk_super = fs_info-super_copy; features = btrfs_super_incompat_flags(disk_super); if (!(features flag)) { - features |= flag; - btrfs_set_super_incompat_flags(disk_super, features); + spin_lock(fs_info-super_lock); + features = btrfs_super_incompat_flags(disk_super); + if (!(features flag)) { + features |= flag; + btrfs_set_super_incompat_flags(disk_super, features); + printk(KERN_INFO btrfs: setting %llu feature flag\n, +flag); + } + spin_unlock(fs_info-super_lock); } } diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index 6d19a0a..ab8ef37 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c @@ -2060,6 +2060,7 @@ int open_ctree(struct super_block *sb, spin_lock_init(fs_info-defrag_inodes_lock); spin_lock_init(fs_info-free_chunk_lock); spin_lock_init(fs_info-tree_mod_seq_lock); + spin_lock_init(fs_info-super_lock); rwlock_init(fs_info-tree_mod_log_lock); mutex_init(fs_info-reloc_mutex); seqlock_init(fs_info-profiles_lock); @@ -2319,6 +2320,10 @@ int open_ctree(struct super_block *sb, goto fail_alloc; } + /* +* Needn't use the lock because there is no other task which will +* update the flag. +*/ btrfs_set_super_incompat_flags(disk_super, features); features = btrfs_super_compat_ro_flags(disk_super) diff --git a/fs/btrfs/volumes.c b/fs/btrfs/volumes.c index 2854c82..e710db4 100644 --- a/fs/btrfs/volumes.c +++ b/fs/btrfs/volumes.c @@ -3674,18 +3674,10 @@ static u32 find_raid56_stripe_len(u32 data_devices, u32 dev_stripe_target) static void check_raid56_incompat_flag(struct btrfs_fs_info *info, u64 type) { - u64 features; - if (!(type (BTRFS_BLOCK_GROUP_RAID5 | BTRFS_BLOCK_GROUP_RAID6))) return; - features = btrfs_super_incompat_flags(info-super_copy); - if (features BTRFS_FEATURE_INCOMPAT_RAID56) - return; - - features |= BTRFS_FEATURE_INCOMPAT_RAID56; - btrfs_set_super_incompat_flags(info-super_copy, features); - printk(KERN_INFO btrfs: setting RAID5/6 feature flag\n); + btrfs_set_fs_incompat(info, RAID56); } static int __btrfs_alloc_chunk(struct btrfs_trans_handle *trans, -- 1.8.0.1 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 0/2] do not open the extend inode reference at the beginning
In most cases, we do not insert so many inode references, so it is better that we don't set incompat flag -- EXTEND_IREF -- when we make a fs. Otherwise we can not mount the fs on the old kernel though there is no extend iref in fact. And some users may not hope to inserting the extend inode reference because of the incompatible problem. In this case, we introduce a mount option named noextiref. Note, if the extend inode reference function is enabled, we will fail to mount a fs with this option because there might be some extend irefs in the fs, we should not close this function. This patchset is against: [PATCH 1/2] Btrfs: fix unblocked autodefraggers when remount [PATCH 2/2] Btrfs: use a lock to protect incompat/compat flag of the super block Miao Xie (2): Btrfs: set the INCOMPAT_EXTENDED_IREF when the extended iref is inserted Btrfs: introduce noextiref mount option fs/btrfs/ctree.h | 1 + fs/btrfs/disk-io.c| 9 + fs/btrfs/inode-item.c | 20 ++-- fs/btrfs/super.c | 41 - 4 files changed, 60 insertions(+), 11 deletions(-) -- 1.8.0.1 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 1/2] Btrfs: set the INCOMPAT_EXTENDED_IREF when the extended iref is inserted
We needn't set the INCOMAT_EXTENDED_IREF when making a new fs, just do it after we insert a extended iref successfully. Otherwise, we can not mount the fs in which there is no extended iref in fact on the old kernel, it is not so flexible for the users. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- fs/btrfs/inode-item.c | 18 +- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/fs/btrfs/inode-item.c b/fs/btrfs/inode-item.c index 48b8fda..f07eb45 100644 --- a/fs/btrfs/inode-item.c +++ b/fs/btrfs/inode-item.c @@ -443,15 +443,15 @@ out: btrfs_free_path(path); if (ret == -EMLINK) { - struct btrfs_super_block *disk_super = root-fs_info-super_copy; - /* We ran out of space in the ref array. Need to -* add an extended ref. */ - if (btrfs_super_incompat_flags(disk_super) -BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF) - ret = btrfs_insert_inode_extref(trans, root, name, - name_len, - inode_objectid, - ref_objectid, index); + /* +* We ran out of space in the ref array. Need to add an +* extended ref. +*/ + ret = btrfs_insert_inode_extref(trans, root, name, name_len, + inode_objectid, ref_objectid, + index); + if (!ret) + btrfs_set_fs_incompat(root-fs_info, EXTENDED_IREF); } return ret; -- 1.8.0.1 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 2/2] Btrfs: introduce noextiref mount option
Now, we set incompat flag EXTEND_IREF when we actually need insert a extend inode reference, not when making a fs. But some users may hope that the fs still can be mounted on the old kernel, and don't hope we insert any extend inode references. So we introduce noextiref mount option to close this function. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- fs/btrfs/ctree.h | 1 + fs/btrfs/disk-io.c| 9 + fs/btrfs/inode-item.c | 2 +- fs/btrfs/super.c | 41 - 4 files changed, 51 insertions(+), 2 deletions(-) diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h index a883e47..db88963 100644 --- a/fs/btrfs/ctree.h +++ b/fs/btrfs/ctree.h @@ -1911,6 +1911,7 @@ struct btrfs_ioctl_defrag_range_args { #define BTRFS_MOUNT_CHECK_INTEGRITY(1 20) #define BTRFS_MOUNT_CHECK_INTEGRITY_INCLUDING_EXTENT_DATA (1 21) #define BTRFS_MOUNT_PANIC_ON_FATAL_ERROR (1 22) +#define BTRFS_MOUNT_NOEXTIREF (1 23) #define btrfs_clear_opt(o, opt)((o) = ~BTRFS_MOUNT_##opt) #define btrfs_set_opt(o, opt) ((o) |= BTRFS_MOUNT_##opt) diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index ab8ef37..ee00448 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c @@ -2269,6 +2269,15 @@ int open_ctree(struct super_block *sb, goto fail_alloc; } + if ((btrfs_super_incompat_flags(disk_super) +BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF) + btrfs_test_opt(tree_root, NOEXTIREF)) { + printk(KERN_ERR BTRFS: couldn't mount because the extend iref + can not be close.\n); + err = -EINVAL; + goto fail_alloc; + } + if (btrfs_super_leafsize(disk_super) != btrfs_super_nodesize(disk_super)) { printk(KERN_ERR BTRFS: couldn't mount because metadata diff --git a/fs/btrfs/inode-item.c b/fs/btrfs/inode-item.c index f07eb45..7c4f880 100644 --- a/fs/btrfs/inode-item.c +++ b/fs/btrfs/inode-item.c @@ -442,7 +442,7 @@ int btrfs_insert_inode_ref(struct btrfs_trans_handle *trans, out: btrfs_free_path(path); - if (ret == -EMLINK) { + if (ret == -EMLINK !btrfs_test_opt(root, NOEXTIREF)) { /* * We ran out of space in the ref array. Need to add an * extended ref. diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c index 0f03569..fd375b3 100644 --- a/fs/btrfs/super.c +++ b/fs/btrfs/super.c @@ -315,7 +315,7 @@ enum { Opt_nodatacow, Opt_max_inline, Opt_alloc_start, Opt_nobarrier, Opt_ssd, Opt_nossd, Opt_ssd_spread, Opt_thread_pool, Opt_noacl, Opt_compress, Opt_compress_type, Opt_compress_force, Opt_compress_force_type, - Opt_notreelog, Opt_ratio, Opt_flushoncommit, Opt_discard, + Opt_notreelog, Opt_noextiref, Opt_ratio, Opt_flushoncommit, Opt_discard, Opt_space_cache, Opt_clear_cache, Opt_user_subvol_rm_allowed, Opt_enospc_debug, Opt_subvolrootid, Opt_defrag, Opt_inode_cache, Opt_no_space_cache, Opt_recovery, Opt_skip_balance, @@ -344,6 +344,7 @@ static match_table_t tokens = { {Opt_nossd, nossd}, {Opt_noacl, noacl}, {Opt_notreelog, notreelog}, + {Opt_noextiref, noextiref}, {Opt_flushoncommit, flushoncommit}, {Opt_ratio, metadata_ratio=%d}, {Opt_discard, discard}, @@ -535,6 +536,10 @@ int btrfs_parse_options(struct btrfs_root *root, char *options) printk(KERN_INFO btrfs: disabling tree log\n); btrfs_set_opt(info-mount_opt, NOTREELOG); break; + case Opt_noextiref: + printk(KERN_INFO btrfs: disabling extend inode ref\n); + btrfs_set_opt(info-mount_opt, NOEXTIREF); + break; case Opt_flushoncommit: printk(KERN_INFO btrfs: turning on flush-on-commit\n); btrfs_set_opt(info-mount_opt, FLUSHONCOMMIT); @@ -1202,6 +1207,35 @@ static void btrfs_resize_thread_pool(struct btrfs_fs_info *fs_info, new_pool_size); } +static int btrfs_close_extend_iref(struct btrfs_fs_info *fs_info, + unsigned long old_opts) +{ + struct btrfs_trans_handle *trans; + int ret; + + if (btrfs_raw_test_opt(old_opts, NOEXTIREF) || + !btrfs_raw_test_opt(fs_info-mount_opt, NOEXTIREF)) + return 0; + + trans = btrfs_attach_transaction(fs_info-tree_root); + if (IS_ERR(trans)) { + if (PTR_ERR(trans) != -ENOENT) + return PTR_ERR(trans); + } else { + ret = btrfs_commit_transaction(trans, fs_info-tree_root); + if (ret) + return ret; + } + + if (btrfs_super_incompat_flags(fs_info-super_copy) +
[PATCH] Btrfs-progs: don't set INCOMPAT_EXTENDED_IREF flag when making a new fs
There is no extended irefs in the new fs, and we can mount it on the old kernel without extended iref function safely. So we needn't set INCOMPAT_EXTENDED_IREF flag when making a new fs, and just set it when we actually insert a extended iref. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- mkfs.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/mkfs.c b/mkfs.c index c8cb395..aca6e46 100644 --- a/mkfs.c +++ b/mkfs.c @@ -1654,8 +1654,6 @@ raid_groups: super = root-fs_info-super_copy; flags = btrfs_super_incompat_flags(super); - flags |= BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF; - if (mixed) flags |= BTRFS_FEATURE_INCOMPAT_MIXED_GROUPS; -- 1.8.0.1 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: lvm volume like support
On Mon, Apr 08, 2013 at 02:01:09PM +0200, David Sterba wrote: problem 1: size of 'file' was 77 GB problem 2: umount was fine, remounted again and now size of 'file' is 0 Works fine with a recent kernel (3.9). -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] Btrfs: add a rb_tree to improve performance of ulist search
On Thu, April 11, 2013 at 07:25 (+0200), Wang Shilong wrote: Walking backref tree and btrfs quota rely on ulist very much. This patch tries to use rb_tree to speed up search time. The original code always checks whether an element exists before adding a new element, however it costs O(n). I try to add a rb_tree in the ulist,this is only used to speed up search. I also do some measurements with quota enabled. fsstress -p 4 -n 1 Without this path: real0m51.058s 2m4.745s1m28.222s 1m5.137s user0m0.035s0m0.041s0m0.105s0m0.100s sys 0m12.009s 0m11.246s 0m10.901s 0m10.999s 0m11.287s With this path: real0m55.295s 0m50.960s 1m2.214s0m48.273s user0m0.053s0m0.095s0m0.135s0m0.107s sys 0m7.766s0m6.013s0m6.319s0m6.030s 0m6.532s After applying the patch,the execute time is down by ~42%.(11.287s-6.532s) Signed-off-by: Wang Shilong wangsl-f...@cn.fujitsu.com Reviewed-by: Miao Xie mi...@cn.fujitsu.com --- fs/btrfs/ulist.c | 58 ++--- fs/btrfs/ulist.h |6 + 2 files changed, 56 insertions(+), 8 deletions(-) diff --git a/fs/btrfs/ulist.c b/fs/btrfs/ulist.c index ddc61ca..7b417e2 100644 --- a/fs/btrfs/ulist.c +++ b/fs/btrfs/ulist.c @@ -53,6 +53,7 @@ void ulist_init(struct ulist *ulist) ulist-nnodes = 0; ulist-nodes = ulist-int_nodes; ulist-nodes_alloced = ULIST_SIZE; + ulist-root = RB_ROOT; } EXPORT_SYMBOL(ulist_init); @@ -72,6 +73,7 @@ void ulist_fini(struct ulist *ulist) if (ulist-nodes_alloced ULIST_SIZE) kfree(ulist-nodes); ulist-nodes_alloced = 0; /* in case ulist_fini is called twice */ + ulist-root = RB_ROOT; } EXPORT_SYMBOL(ulist_fini); @@ -123,6 +125,45 @@ void ulist_free(struct ulist *ulist) } EXPORT_SYMBOL(ulist_free); +static struct ulist_node *ulist_rbtree_search(struct ulist *ulist, u64 val) +{ + struct rb_node *n = ulist-root.rb_node; + struct ulist_node *u = NULL; + + while (n) { + u = rb_entry(n, struct ulist_node, rb_node); + if (u-val val) + n = n-rb_right; + else if (u-val val) + n = n-rb_left; + else + return u; + } + return NULL; +} + +static int ulist_rbtree_insert(struct ulist *ulist, struct ulist_node *ins) +{ + struct rb_node **p = ulist-root.rb_node; + struct rb_node *parent = NULL; + struct ulist_node *cur = NULL; + + while (*p) { + parent = *p; + cur = rb_entry(parent, struct ulist_node, rb_node); + + if (cur-val ins-val) + p = (*p)-rb_right; + else if (cur-val ins-val) + p = (*p)-rb_left; + else + return -EEXIST; + } + rb_link_node(ins-rb_node, parent, p); + rb_insert_color(ins-rb_node, ulist-root); + return 0; +} + /** * ulist_add - add an element to the ulist * @ulist: ulist to add the element to @@ -151,14 +192,13 @@ int ulist_add(struct ulist *ulist, u64 val, u64 aux, gfp_t gfp_mask) int ulist_add_merge(struct ulist *ulist, u64 val, u64 aux, u64 *old_aux, gfp_t gfp_mask) { - int i; - - for (i = 0; i ulist-nnodes; ++i) { - if (ulist-nodes[i].val == val) { - if (old_aux) - *old_aux = ulist-nodes[i].aux; - return 0; - } + int ret = 0; + struct ulist_node *node = NULL; + node = ulist_rbtree_search(ulist, val); + if (node) { + if (old_aux) + *old_aux = node-aux; + return 0; } if (ulist-nnodes = ulist-nodes_alloced) { @@ -187,6 +227,8 @@ int ulist_add_merge(struct ulist *ulist, u64 val, u64 aux, } ulist-nodes[ulist-nnodes].val = val; ulist-nodes[ulist-nnodes].aux = aux; + ret = ulist_rbtree_insert(ulist, ulist-nodes[ulist-nnodes]); + BUG_ON(ret); ++ulist-nnodes; return 1; diff --git a/fs/btrfs/ulist.h b/fs/btrfs/ulist.h index 21a1963..cb5f89d 100644 --- a/fs/btrfs/ulist.h +++ b/fs/btrfs/ulist.h @@ -8,6 +8,9 @@ #ifndef __ULIST__ #define __ULIST__ +#includelinux/list.h +#includelinux/rbtree.h I didn't expect the space after #include being optional. If it compiles, I'm fine with it. With a space, it would look more familiar, though. + /* * ulist is a generic data structure to hold a collection of unique u64 * values. The only operations it supports is adding to the list and @@ -34,6 +37,7 @@ struct ulist_iterator { struct ulist_node { u64 val;/* value to store */ u64 aux;/*
Re: [PATCH] Btrfs: add a rb_tree to improve performance of ulist search
Hello, Jan [snip] +#includelinux/list.h +#includelinux/rbtree.h I didn't expect the space after #include being optional. If it compiles, I'm fine with it. With a space, it would look more familiar, though. I am happy to send V2 to correct this coding style problem. Thanks very much for reviewing it so carefully! Thanks, Wang + /* * ulist is a generic data structure to hold a collection of unique u64 * values. The only operations it supports is adding to the list and @@ -34,6 +37,7 @@ struct ulist_iterator { struct ulist_node { u64 val;/* value to store */ u64 aux;/* auxiliary value saved along with the val */ +struct rb_node rb_node; /* used to speed up search */ }; struct ulist { @@ -54,6 +58,8 @@ struct ulist { */ struct ulist_node *nodes; +struct rb_root root; + /* * inline storage space for the first ULIST_SIZE entries */ Makes a lot of sense. Thanks! Reviewed-by: Jan Schmidt list.bt...@jan-o-sch.net -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] Btrfs-progs: don't set INCOMPAT_EXTENDED_IREF flag when making a new fs
On Thu, April 11, 2013 at 12:28 (+0200), Miao Xie wrote: There is no extended irefs in the new fs, and we can mount it on the old kernel without extended iref function safely. So we needn't set INCOMPAT_EXTENDED_IREF flag when making a new fs, and just set it when we actually insert a extended iref. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- mkfs.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/mkfs.c b/mkfs.c index c8cb395..aca6e46 100644 --- a/mkfs.c +++ b/mkfs.c @@ -1654,8 +1654,6 @@ raid_groups: super = root-fs_info-super_copy; flags = btrfs_super_incompat_flags(super); - flags |= BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF; - if (mixed) flags |= BTRFS_FEATURE_INCOMPAT_MIXED_GROUPS; This one should have a large *** do not apply until kernel patches from [PATCH 0/2] do not open the extend *** inode reference at the beginning have been merged. tag. Otherwise, extended irefs are disabled entirely for all new file systems in environments where they have been working so far. -Jan -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 2/2] Btrfs: introduce noextiref mount option
On Thu, April 11, 2013 at 12:35 (+0200), Miao Xie wrote: Now, we set incompat flag EXTEND_IREF when we actually need insert a extend inode reference, not when making a fs. But some users may hope that the fs still can be mounted on the old kernel, and don't hope we insert any extend inode references. So we introduce noextiref mount option to close this function. That's a much better approach compared to setting the flag on mkfs, I agree. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- fs/btrfs/ctree.h | 1 + fs/btrfs/disk-io.c| 9 + fs/btrfs/inode-item.c | 2 +- fs/btrfs/super.c | 41 - 4 files changed, 51 insertions(+), 2 deletions(-) diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h index a883e47..db88963 100644 --- a/fs/btrfs/ctree.h +++ b/fs/btrfs/ctree.h @@ -1911,6 +1911,7 @@ struct btrfs_ioctl_defrag_range_args { #define BTRFS_MOUNT_CHECK_INTEGRITY (1 20) #define BTRFS_MOUNT_CHECK_INTEGRITY_INCLUDING_EXTENT_DATA (1 21) #define BTRFS_MOUNT_PANIC_ON_FATAL_ERROR (1 22) +#define BTRFS_MOUNT_NOEXTIREF(1 23) #define btrfs_clear_opt(o, opt) ((o) = ~BTRFS_MOUNT_##opt) #define btrfs_set_opt(o, opt)((o) |= BTRFS_MOUNT_##opt) diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index ab8ef37..ee00448 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c @@ -2269,6 +2269,15 @@ int open_ctree(struct super_block *sb, goto fail_alloc; } + if ((btrfs_super_incompat_flags(disk_super) + BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF) + btrfs_test_opt(tree_root, NOEXTIREF)) { + printk(KERN_ERR BTRFS: couldn't mount because the extend iref +can not be close.\n); + err = -EINVAL; + goto fail_alloc; + } + if (btrfs_super_leafsize(disk_super) != btrfs_super_nodesize(disk_super)) { printk(KERN_ERR BTRFS: couldn't mount because metadata diff --git a/fs/btrfs/inode-item.c b/fs/btrfs/inode-item.c index f07eb45..7c4f880 100644 --- a/fs/btrfs/inode-item.c +++ b/fs/btrfs/inode-item.c @@ -442,7 +442,7 @@ int btrfs_insert_inode_ref(struct btrfs_trans_handle *trans, out: btrfs_free_path(path); - if (ret == -EMLINK) { + if (ret == -EMLINK !btrfs_test_opt(root, NOEXTIREF)) { /* * We ran out of space in the ref array. Need to add an * extended ref. diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c index 0f03569..fd375b3 100644 --- a/fs/btrfs/super.c +++ b/fs/btrfs/super.c @@ -315,7 +315,7 @@ enum { Opt_nodatacow, Opt_max_inline, Opt_alloc_start, Opt_nobarrier, Opt_ssd, Opt_nossd, Opt_ssd_spread, Opt_thread_pool, Opt_noacl, Opt_compress, Opt_compress_type, Opt_compress_force, Opt_compress_force_type, - Opt_notreelog, Opt_ratio, Opt_flushoncommit, Opt_discard, + Opt_notreelog, Opt_noextiref, Opt_ratio, Opt_flushoncommit, Opt_discard, Opt_space_cache, Opt_clear_cache, Opt_user_subvol_rm_allowed, Opt_enospc_debug, Opt_subvolrootid, Opt_defrag, Opt_inode_cache, Opt_no_space_cache, Opt_recovery, Opt_skip_balance, @@ -344,6 +344,7 @@ static match_table_t tokens = { {Opt_nossd, nossd}, {Opt_noacl, noacl}, {Opt_notreelog, notreelog}, + {Opt_noextiref, noextiref}, {Opt_flushoncommit, flushoncommit}, {Opt_ratio, metadata_ratio=%d}, {Opt_discard, discard}, @@ -535,6 +536,10 @@ int btrfs_parse_options(struct btrfs_root *root, char *options) printk(KERN_INFO btrfs: disabling tree log\n); btrfs_set_opt(info-mount_opt, NOTREELOG); break; + case Opt_noextiref: + printk(KERN_INFO btrfs: disabling extend inode ref\n); + btrfs_set_opt(info-mount_opt, NOEXTIREF); + break; case Opt_flushoncommit: printk(KERN_INFO btrfs: turning on flush-on-commit\n); btrfs_set_opt(info-mount_opt, FLUSHONCOMMIT); @@ -1202,6 +1207,35 @@ static void btrfs_resize_thread_pool(struct btrfs_fs_info *fs_info, new_pool_size); } +static int btrfs_close_extend_iref(struct btrfs_fs_info *fs_info, +unsigned long old_opts) The name irritated me, it's more like unset instead of close, isn't it? +{ + struct btrfs_trans_handle *trans; + int ret; + + if (btrfs_raw_test_opt(old_opts, NOEXTIREF) || + !btrfs_raw_test_opt(fs_info-mount_opt, NOEXTIREF)) + return 0; + + trans = btrfs_attach_transaction(fs_info-tree_root); + if (IS_ERR(trans)) { + if (PTR_ERR(trans) != -ENOENT) + return PTR_ERR(trans); + } else { +
[PATCH] Btrfs-progs: enhance 'btrfs subvolume list'
btrfs subvolume list gets a new option --fields=... which allows to specify which pieces of information about subvolumes shall be printed. This is necessary because this commit also adds all the so far missing items from the root_item like the received UUID, all generation values and all time values. The parameters to the --fields option is a list of items to print: --fields=gen,dirid,uuid,puuid,ruuid,cgen,ogen,sgen,rgen,ctime,otime, stime,rtime,path,rootid,parent,topid,all Signed-off-by: Stefan Behrens sbehr...@giantdisaster.de --- btrfs-list.c | 418 --- btrfs-list.h | 40 +- cmds-subvolume.c | 57 +++- man/btrfs.8.in | 19 +-- 4 files changed, 339 insertions(+), 195 deletions(-) diff --git a/btrfs-list.c b/btrfs-list.c index 1246a25..b0d8d13 100644 --- a/btrfs-list.c +++ b/btrfs-list.c @@ -50,62 +50,151 @@ struct { char*name; char*column_name; int need_print; + int width; } btrfs_list_columns[] = { { .name = ID, .column_name= ID, .need_print = 0, + .width = 6, }, { .name = gen, .column_name= Gen, .need_print = 0, + .width = 6, }, { .name = cgen, .column_name= CGen, .need_print = 0, + .width = 6, + }, + { + .name = ogen, + .column_name= OGen, + .need_print = 0, + .width = 6, + }, + { + .name = sgen, + .column_name= SGen, + .need_print = 0, + .width = 6, + }, + { + .name = rgen, + .column_name= RGen, + .need_print = 0, + .width = 6, }, { .name = parent, .column_name= Parent, .need_print = 0, + .width = 7, }, { .name = top level, .column_name= Top Level, .need_print = 0, + .width = 10, + }, + { + .name = ctime, + .column_name= CTime, + .need_print = 0, + .width = 21, }, { .name = otime, .column_name= OTime, .need_print = 0, + .width = 21, + }, + { + .name = stime, + .column_name= STime, + .need_print = 0, + .width = 21, }, { - .name = parent_uuid, - .column_name= Parent UUID, + .name = rtime, + .column_name= RTime, .need_print = 0, + .width = 21, }, { .name = uuid, .column_name= UUID, .need_print = 0, + .width = 38, + }, + { + .name = puuid, + .column_name= PUUID, + .need_print = 0, + .width = 38, + }, + { + .name = ruuid, + .column_name= RUUID, + .need_print = 0, + .width = 38, + }, + { + .name = dirid, + .column_name= DirID, + .need_print = 0, + .width = 6, }, { .name = path, .column_name= Path, .need_print = 0, + .width = 0, }, { .name = NULL, .column_name= NULL, .need_print = 0, + .width = 0, }, }; +static char *all_field_items[] = { + [BTRFS_LIST_OBJECTID] = rootid, + [BTRFS_LIST_GENERATION] = gen, + [BTRFS_LIST_CGENERATION]= cgen, + [BTRFS_LIST_OGENERATION]= ogen, + [BTRFS_LIST_SGENERATION]= sgen, + [BTRFS_LIST_RGENERATION]= rgen, + [BTRFS_LIST_PARENT] = parent, + [BTRFS_LIST_TOP_LEVEL] = topid, + [BTRFS_LIST_CTIME] = ctime, + [BTRFS_LIST_OTIME] = otime, + [BTRFS_LIST_STIME] = stime, + [BTRFS_LIST_RTIME] = rtime, + [BTRFS_LIST_UUID] = uuid, +
[PATCH 1/2] btrfs-progs: replace blkid_probe_get_wholedisk_devno
blkid_probe_get_wholedisk_devno() isn't available in some older versions of libblkid. It was used to work around an old bug in blkid_devno_to_wholedisk(), but that has been fixed since 5cd0823 libblkid: fix blkid_devno_to_wholedisk(), present in util-linux 2.17 and beyond. If we happen to be missing that fix, the worst that happens is that we'd fail to detect that a device is an ssd; the upside is that this code compiles on older systems. Signed-off-by: Eric Sandeen sand...@redhat.com --- diff --git a/mkfs.c b/mkfs.c index c8cb395..7df78fc 100644 --- a/mkfs.c +++ b/mkfs.c @@ -1215,9 +1215,8 @@ static int check_leaf_or_node_size(u32 size, u32 sectorsize) static int is_ssd(const char *file) { - char *devname; blkid_probe probe; - char *dev; + char dev[32]; char path[PATH_MAX]; dev_t disk; int fd; @@ -1227,24 +1226,16 @@ static int is_ssd(const char *file) if (!probe) return 0; - /* -* We want to use blkid_devno_to_wholedisk() but it's broken for some -* reason on F17 at least so we'll do this trickery -*/ - disk = blkid_probe_get_wholedisk_devno(probe); + /* Device number of this disk (possibly a partition) */ + disk = blkid_probe_get_devno(probe); if (!disk) return 0; - devname = blkid_devno_to_devname(disk); - if (!devname) - return 0; - - dev = strrchr(devname, '/'); - dev++; + /* Get whole disk name (not full path) for this devno */ + blkid_devno_to_wholedisk(disk, dev, sizeof(dev), NULL); snprintf(path, PATH_MAX, /sys/block/%s/queue/rotational, dev); - free(devname); blkid_free_probe(probe); fd = open(path, O_RDONLY); -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v2 1/4] Btrfs-progs: cleanup in btrfs-list.c
Since someone modified the code to initialize all need_print with zero, these lines can be removed entirely. Signed-off-by: Stefan Behrens sbehr...@giantdisaster.de --- btrfs-list.c | 12 +--- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/btrfs-list.c b/btrfs-list.c index 1246a25..a5d6e9b 100644 --- a/btrfs-list.c +++ b/btrfs-list.c @@ -46,7 +46,7 @@ struct root_lookup { struct rb_root root; }; -struct { +static struct { char*name; char*column_name; int need_print; @@ -54,52 +54,42 @@ struct { { .name = ID, .column_name= ID, - .need_print = 0, }, { .name = gen, .column_name= Gen, - .need_print = 0, }, { .name = cgen, .column_name= CGen, - .need_print = 0, }, { .name = parent, .column_name= Parent, - .need_print = 0, }, { .name = top level, .column_name= Top Level, - .need_print = 0, }, { .name = otime, .column_name= OTime, - .need_print = 0, }, { .name = parent_uuid, .column_name= Parent UUID, - .need_print = 0, }, { .name = uuid, .column_name= UUID, - .need_print = 0, }, { .name = path, .column_name= Path, - .need_print = 0, }, { .name = NULL, .column_name= NULL, - .need_print = 0, }, }; -- 1.8.2.1 -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH v2 3/4] Btrfs-progs: add more subvol fields to btrfs-list
The parent UUID, all generation values and all timestamps that are available in the root_item are added. Signed-off-by: Stefan Behrens sbehr...@giantdisaster.de --- btrfs-list.c | 273 +++ btrfs-list.h | 39 - 2 files changed, 197 insertions(+), 115 deletions(-) diff --git a/btrfs-list.c b/btrfs-list.c index 70da9a3..2d53290 100644 --- a/btrfs-list.c +++ b/btrfs-list.c @@ -68,6 +68,21 @@ static struct { .width = 6, }, { + .name = ogen, + .column_name= OGen, + .width = 6, + }, + { + .name = sgen, + .column_name= SGen, + .width = 6, + }, + { + .name = rgen, + .column_name= RGen, + .width = 6, + }, + { .name = parent, .column_name= Parent, .width = 7, @@ -78,13 +93,24 @@ static struct { .width = 10, }, { + .name = ctime, + .column_name= CTime, + .width = 21, + }, + { .name = otime, .column_name= OTime, .width = 21, }, { - .name = parent_uuid, - .column_name= Parent UUID, + .name = stime, + .column_name= STime, + .width = 21, + }, + { + .name = rtime, + .column_name= RTime, + .width = 21, }, { .name = uuid, @@ -92,6 +118,21 @@ static struct { .width = 38, }, { + .name = puuid, + .column_name= PUUID, + .width = 38, + }, + { + .name = ruuid, + .column_name= RUUID, + .width = 38, + }, + { + .name = dirid, + .column_name= DirID, + .width = 6, + }, + { .name = path, .column_name= Path, .width = 0, @@ -391,52 +432,70 @@ static struct root_info *root_tree_search(struct root_lookup *root_tree, return NULL; } -static int update_root(struct root_lookup *root_lookup, - u64 root_id, u64 ref_tree, u64 root_offset, u64 flags, - u64 dir_id, char *name, int name_len, u64 ogen, u64 gen, - time_t ot, void *uuid, void *puuid) +static int set_root_info(struct root_info *rinfo, u64 ref_tree, u64 root_offset, +u64 dir_id, char *name, int name_len, +struct btrfs_root_item *ritem, u32 ritem_len) { - struct root_info *ri; + int is_v0 = (ritem_len = sizeof(struct btrfs_root_item_v0)); - ri = root_tree_search(root_lookup, root_id); - if (!ri || ri-root_id != root_id) - return -ENOENT; - if (name name_len 0) { - if (ri-name) - free(ri-name); + if (root_offset) + rinfo-root_offset = root_offset; + if (ref_tree) + rinfo-ref_tree = ref_tree; + if (dir_id) + rinfo-dir_id = dir_id; + + if (ritem) { + rinfo-gen = btrfs_root_generation(ritem); + rinfo-flags = btrfs_root_flags(ritem); + } - ri-name = malloc(name_len + 1); - if (!ri-name) { + if (ritem !is_v0) { + rinfo-cgen = btrfs_root_ctransid(ritem); + rinfo-ogen = btrfs_root_otransid(ritem); + rinfo-sgen = btrfs_root_stransid(ritem); + rinfo-rgen = btrfs_root_rtransid(ritem); + rinfo-ctime = btrfs_stack_timespec_sec(ritem-ctime); + rinfo-otime = btrfs_stack_timespec_sec(ritem-otime); + rinfo-stime = btrfs_stack_timespec_sec(ritem-stime); + rinfo-rtime = btrfs_stack_timespec_sec(ritem-rtime); + memcpy(rinfo-uuid, ritem-uuid, BTRFS_UUID_SIZE); + memcpy(rinfo-puuid, ritem-parent_uuid, BTRFS_UUID_SIZE); + memcpy(rinfo-ruuid, ritem-received_uuid, BTRFS_UUID_SIZE); + } + + /* TODO: this is copied from the old code, what is it good for? */ + if ((!ritem || !btrfs_root_otransid(ritem)) root_offset) + rinfo-ogen = root_offset; + + if (name name_len 0) { + rinfo-name = malloc(name_len + 1); + if (!rinfo-name) { fprintf(stderr, memory allocation failed\n); -
[PATCH v2 2/4] Btrfs-progs: make the btrfs-list output more compact
The following commit will add many additional columns to the output. Therefore the current commit adds a width for each column. It replaces to uncondionally add a TAB after each column which makes the output much wider than necessary. Signed-off-by: Stefan Behrens sbehr...@giantdisaster.de --- btrfs-list.c | 79 +++- 1 file changed, 46 insertions(+), 33 deletions(-) diff --git a/btrfs-list.c b/btrfs-list.c index a5d6e9b..70da9a3 100644 --- a/btrfs-list.c +++ b/btrfs-list.c @@ -50,30 +50,37 @@ static struct { char*name; char*column_name; int need_print; + int width; } btrfs_list_columns[] = { { .name = ID, .column_name= ID, + .width = 6, }, { .name = gen, .column_name= Gen, + .width = 6, }, { .name = cgen, .column_name= CGen, + .width = 6, }, { .name = parent, .column_name= Parent, + .width = 7, }, { .name = top level, .column_name= Top Level, + .width = 10, }, { .name = otime, .column_name= OTime, + .width = 21, }, { .name = parent_uuid, @@ -82,14 +89,17 @@ static struct { { .name = uuid, .column_name= UUID, + .width = 38, }, { .name = path, .column_name= Path, + .width = 0, }, { .name = NULL, .column_name= NULL, + .width = 0, }, }; @@ -1309,29 +1319,30 @@ static int __list_subvol_fill_paths(int fd, struct root_lookup *root_lookup) return 0; } -static void print_subvolume_column(struct root_info *subv, - enum btrfs_list_column_enum column) +static int print_subvolume_column(struct root_info *subv, + enum btrfs_list_column_enum column) { char tstr[256]; char uuidparse[37]; + int width; BUG_ON(column = BTRFS_LIST_ALL || column 0); switch (column) { case BTRFS_LIST_OBJECTID: - printf(%llu, subv-root_id); + width = printf(%llu, subv-root_id); break; case BTRFS_LIST_GENERATION: - printf(%llu, subv-gen); + width = printf(%llu, subv-gen); break; case BTRFS_LIST_OGENERATION: - printf(%llu, subv-ogen); + width = printf(%llu, subv-ogen); break; case BTRFS_LIST_PARENT: - printf(%llu, subv-ref_tree); + width = printf(%llu, subv-ref_tree); break; case BTRFS_LIST_TOP_LEVEL: - printf(%llu, subv-top_id); + width = printf(%llu, subv-top_id); break; case BTRFS_LIST_OTIME: if (subv-otime) @@ -1339,29 +1350,34 @@ static void print_subvolume_column(struct root_info *subv, localtime(subv-otime)); else strcpy(tstr, -); - printf(%s, tstr); + width = printf(%s, tstr); break; case BTRFS_LIST_UUID: if (uuid_is_null(subv-uuid)) strcpy(uuidparse, -); else uuid_unparse(subv-uuid, uuidparse); - printf(%s, uuidparse); + width = printf(%s, uuidparse); break; case BTRFS_LIST_PUUID: if (uuid_is_null(subv-puuid)) strcpy(uuidparse, -); else uuid_unparse(subv-puuid, uuidparse); - printf(%s, uuidparse); + width = printf(%s, uuidparse); break; case BTRFS_LIST_PATH: BUG_ON(!subv-full_path); - printf(%s, subv-full_path); + width = printf(%s, subv-full_path); break; default: + width = 0; break; } + + if (width 0) + width = 0; + return width; } static void print_single_volume_info_raw(struct root_info *subv, char *raw_prefix) @@ -1383,18 +1399,15 @@ static void print_single_volume_info_raw(struct root_info *subv, char *raw_prefi static void print_single_volume_info_table(struct root_info *subv) { int i; + int width;
[PATCH v2 4/4] Btrfs-progs: enhance 'btrfs subvolume list'
btrfs subvolume list gets a new option --fields=... which allows to specify which pieces of information about subvolumes shall be printed. This is necessary because this commit also adds all the so far missing items from the root_item like the received UUID, all generation values and all time values. The parameters to the --fields option is a list of items to print: --fields=gen,dirid,uuid,puuid,ruuid,cgen,ogen,sgen,rgen,ctime,otime, stime,rtime,path,rootid,parent,topid,all Signed-off-by: Stefan Behrens sbehr...@giantdisaster.de --- btrfs-list.c | 58 btrfs-list.h | 1 + cmds-subvolume.c | 57 +-- man/btrfs.8.in | 19 +++ 4 files changed, 88 insertions(+), 47 deletions(-) diff --git a/btrfs-list.c b/btrfs-list.c index 2d53290..5f69922 100644 --- a/btrfs-list.c +++ b/btrfs-list.c @@ -144,9 +144,39 @@ static struct { }, }; +static char *all_field_items[] = { + [BTRFS_LIST_OBJECTID] = rootid, + [BTRFS_LIST_GENERATION] = gen, + [BTRFS_LIST_CGENERATION]= cgen, + [BTRFS_LIST_OGENERATION]= ogen, + [BTRFS_LIST_SGENERATION]= sgen, + [BTRFS_LIST_RGENERATION]= rgen, + [BTRFS_LIST_PARENT] = parent, + [BTRFS_LIST_TOP_LEVEL] = topid, + [BTRFS_LIST_CTIME] = ctime, + [BTRFS_LIST_OTIME] = otime, + [BTRFS_LIST_STIME] = stime, + [BTRFS_LIST_RTIME] = rtime, + [BTRFS_LIST_UUID] = uuid, + [BTRFS_LIST_PUUID] = puuid, + [BTRFS_LIST_RUUID] = ruuid, + [BTRFS_LIST_DIRID] = dirid, + [BTRFS_LIST_PATH] = path, + [BTRFS_LIST_ALL]= all, + [BTRFS_LIST_MAX]= NULL, +}; + static btrfs_list_filter_func all_filter_funcs[]; static btrfs_list_comp_func all_comp_funcs[]; +void btrfs_list_clear_all_print_columns(void) +{ + int i; + + for (i = 0; i BTRFS_LIST_ALL; i++) + btrfs_list_columns[i].need_print = 0; +} + void btrfs_list_setup_print_column(enum btrfs_list_column_enum column) { int i; @@ -257,6 +287,16 @@ static int btrfs_list_get_sort_item(char *sort_name) return -1; } +static int btrfs_list_get_field_item(char *field_name) +{ + int i; + + for (i = 0; i BTRFS_LIST_MAX; i++) + if (strcmp(field_name, all_field_items[i]) == 0) + return i; + return -1; +} + struct btrfs_list_comparer_set *btrfs_list_alloc_comparer_set(void) { struct btrfs_list_comparer_set *set; @@ -1897,6 +1937,24 @@ int btrfs_list_parse_sort_string(char *optarg, return 0; } +int btrfs_list_parse_fields_string(char *optarg) +{ + char *p; + int column; + + btrfs_list_clear_all_print_columns(); + + while ((p = strtok(optarg, ,)) != NULL) { + column = btrfs_list_get_field_item(p); + if (column 0) + return -1; + btrfs_list_setup_print_column(column); + optarg = NULL; + } + + return 0; +} + /* * This function is used to parse the argument of filter condition. * diff --git a/btrfs-list.h b/btrfs-list.h index 27be3b1..7e03948 100644 --- a/btrfs-list.h +++ b/btrfs-list.h @@ -173,6 +173,7 @@ enum btrfs_list_comp_enum { int btrfs_list_parse_sort_string(char *optarg, struct btrfs_list_comparer_set **comps); +int btrfs_list_parse_fields_string(char *optarg); int btrfs_list_parse_filter_string(char *optarg, struct btrfs_list_filter_set **filters, enum btrfs_list_filter_enum type); diff --git a/cmds-subvolume.c b/cmds-subvolume.c index e97297a..add655e 100644 --- a/cmds-subvolume.c +++ b/cmds-subvolume.c @@ -282,19 +282,16 @@ out: * - lowercase for enabling specific items in the output */ static const char * const cmd_subvol_list_usage[] = { - btrfs subvolume list [-agopurts] [-G [+|-]value] [-C [+|-]value] - [--sort=gen,ogen,rootid,path] path, + btrfs subvolume list [-roast] [-G [+|-]value] [-C [+|-]value] + [--sort=gen,ogen,rootid,path] + [--fields=gen,dirid,uuid,puuid,ruuid,cgen,ogen,sgen,rgen,ctime, + otime,stime,rtime,path,rootid,parent,topid,all] path, List subvolumes (and snapshots), , - -p print parent ID, -a print all the subvolumes in the filesystem and, distinguish absolute and relative path with respect, to the given path, - -c print the ogeneration of the subvolume, - -g print the generation of the subvolume, -o print only subvolumes bellow specified path, -
Re: btrfs prof compile error on debian squeeze.
I agree with you. Debian package are out of date. I've chosen to change distribution, I switched to ArchLinux and everything is fine. And finally I don't like the way debian works anymore. Thanks for your help. Le 11 avr. 2013 à 03:41, Eric Sandeen sand...@redhat.com a écrit : On 4/10/13 7:28 PM, Mitch Harder wrote: We had a discussion on this topic in another thread. I'd be happy to be corrected, but I think the conclusion was that you probably need to be on a really modern version of Linux to work with the latest version of btrfs-progs that is in the kernel git repository. The mkfs.btrfs version in the kernel git tree won't even work correctly on a kernel = 3.7, and only partially works on the 3.8 kernel. Well, that needs to be fixed too, IMHO, and I think that's the plan? For userspace, if we used autoconf, we could pretty easily turn off the ssd code in btrfs for older systems. We could probably use the older blkid interfaces to do the same thing as well, but nobody's made it a priority yet. -Eric On 4/10/13, Wang Shilong wangshilong1...@gmail.com wrote: Hello, Maybe this url will help you. https://btrfs.wiki.kernel.org/index.php/Btrfs_source_repositories Thanks, Wang Hello, I'm trying to build btrfs-prog on debian squeeze but when I'm trying to use make, I have an error : pc@debian:~/b/btrfs-progs$ make [LD] mkfs.btrfs mkfs.o: In function `is_ssd': /home/pc/b/btrfs-progs/mkfs.c:1234: undefined reference to `blkid_probe_get_wholedisk_devno' collect2: ld returned 1 exit status make: *** [mkfs.btrfs] Erreur 1 After a few searches over the internet, it seems that my blkid library is out of date. How can I compile btrfs prog on debian squeeze ? Thanks ! Olivier.-- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: btrfs prof compile error on debian squeeze.
On 4/11/13 11:26 AM, Olivier BATARD wrote: I agree with you. Debian package are out of date. I've chosen to change distribution, I switched to ArchLinux and everything is fine. And finally I don't like the way debian works anymore. Thanks for your help. FWIW, I did just send patches to the list to work w/ older util-linux blkid, with the caveat that they may fail to detect an SSD on an older, buggy blkid. -Eric Le 11 avr. 2013 à 03:41, Eric Sandeen sand...@redhat.com a écrit : On 4/10/13 7:28 PM, Mitch Harder wrote: We had a discussion on this topic in another thread. I'd be happy to be corrected, but I think the conclusion was that you probably need to be on a really modern version of Linux to work with the latest version of btrfs-progs that is in the kernel git repository. The mkfs.btrfs version in the kernel git tree won't even work correctly on a kernel = 3.7, and only partially works on the 3.8 kernel. Well, that needs to be fixed too, IMHO, and I think that's the plan? For userspace, if we used autoconf, we could pretty easily turn off the ssd code in btrfs for older systems. We could probably use the older blkid interfaces to do the same thing as well, but nobody's made it a priority yet. -Eric On 4/10/13, Wang Shilong wangshilong1...@gmail.com wrote: Hello, Maybe this url will help you. https://btrfs.wiki.kernel.org/index.php/Btrfs_source_repositories Thanks, Wang Hello, I'm trying to build btrfs-prog on debian squeeze but when I'm trying to use make, I have an error : pc@debian:~/b/btrfs-progs$ make [LD] mkfs.btrfs mkfs.o: In function `is_ssd': /home/pc/b/btrfs-progs/mkfs.c:1234: undefined reference to `blkid_probe_get_wholedisk_devno' collect2: ld returned 1 exit status make: *** [mkfs.btrfs] Erreur 1 After a few searches over the internet, it seems that my blkid library is out of date. How can I compile btrfs prog on debian squeeze ? Thanks ! Olivier.-- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Restriper documentation
-BEGIN PGP SIGNED MESSAGE- Hash: SHA1 It looks like the restriper patches got merged last year, but never documented in the man page. Could you do that? -BEGIN PGP SIGNATURE- Version: GnuPG v2.0.17 (MingW32) Comment: Using GnuPG with Thunderbird - http://www.enigmail.net/ iQEcBAEBAgAGBQJRZwZYAAoJEJrBOlT6nu75sAYIAKdXp17gP1dmbSu2yImzaRDK VAFX6RkeMknjkTU9/GtmaDeCM/JEHNNqH7EKLHGzJIomMJSbZq34iTbkgDNXxikh uyhXpNXz0ghqJP+AmQ8GHw27LZ2Gi7T1o1AYed9JcCqxRRyRB2+822HQWWVzA30M LYUQOMyy4Rq1RR1vOnVs1XPLsb4gc7yQtwXlvIU9yi4euWaQYbmEr29nSLTYi5+m CBE686XgMzbDZB84VjUwGCnHzYeXofARUN1xjfeEy6g4n/NRbUJgiDyR/iG3gMqU FeqHO1j1+A8i6ljxTEzxZAKwIi0DOaFbgN/8kx8vIsjL3NzP79WlSex/LMUjMPU= =ncMQ -END PGP SIGNATURE- -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH] Btrfs-progs: don't set INCOMPAT_EXTENDED_IREF flag when making a new fs
On Thu, 11 Apr 2013 16:28:11 +0200, Jan Schmidt wrote: On Thu, April 11, 2013 at 12:28 (+0200), Miao Xie wrote: There is no extended irefs in the new fs, and we can mount it on the old kernel without extended iref function safely. So we needn't set INCOMPAT_EXTENDED_IREF flag when making a new fs, and just set it when we actually insert a extended iref. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- mkfs.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/mkfs.c b/mkfs.c index c8cb395..aca6e46 100644 --- a/mkfs.c +++ b/mkfs.c @@ -1654,8 +1654,6 @@ raid_groups: super = root-fs_info-super_copy; flags = btrfs_super_incompat_flags(super); -flags |= BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF; - if (mixed) flags |= BTRFS_FEATURE_INCOMPAT_MIXED_GROUPS; This one should have a large *** do not apply until kernel patches from [PATCH 0/2] do not open the extend *** inode reference at the beginning have been merged. tag. Otherwise, extended irefs are disabled entirely for all new file systems in environments where they have been working so far. Yes, thanks to point it out. Miao -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v2 3/4] Btrfs-progs: add more subvol fields to btrfs-list
Hello, ... [snip] -static int update_root(struct root_lookup *root_lookup, -u64 root_id, u64 ref_tree, u64 root_offset, u64 flags, -u64 dir_id, char *name, int name_len, u64 ogen, u64 gen, -time_t ot, void *uuid, void *puuid) +static int set_root_info(struct root_info *rinfo, u64 ref_tree, u64 root_offset, + u64 dir_id, char *name, int name_len, + struct btrfs_root_item *ritem, u32 ritem_len) { - struct root_info *ri; + int is_v0 = (ritem_len = sizeof(struct btrfs_root_item_v0)); - ri = root_tree_search(root_lookup, root_id); - if (!ri || ri-root_id != root_id) - return -ENOENT; - if (name name_len 0) { - if (ri-name) - free(ri-name); + if (root_offset) + rinfo-root_offset = root_offset; + if (ref_tree) + rinfo-ref_tree = ref_tree; + if (dir_id) + rinfo-dir_id = dir_id; + + if (ritem) { + rinfo-gen = btrfs_root_generation(ritem); + rinfo-flags = btrfs_root_flags(ritem); + } - ri-name = malloc(name_len + 1); - if (!ri-name) { + if (ritem !is_v0) { + rinfo-cgen = btrfs_root_ctransid(ritem); + rinfo-ogen = btrfs_root_otransid(ritem); + rinfo-sgen = btrfs_root_stransid(ritem); + rinfo-rgen = btrfs_root_rtransid(ritem); + rinfo-ctime = btrfs_stack_timespec_sec(ritem-ctime); + rinfo-otime = btrfs_stack_timespec_sec(ritem-otime); + rinfo-stime = btrfs_stack_timespec_sec(ritem-stime); + rinfo-rtime = btrfs_stack_timespec_sec(ritem-rtime); + memcpy(rinfo-uuid, ritem-uuid, BTRFS_UUID_SIZE); + memcpy(rinfo-puuid, ritem-parent_uuid, BTRFS_UUID_SIZE); + memcpy(rinfo-ruuid, ritem-received_uuid, BTRFS_UUID_SIZE); + } + + /* TODO: this is copied from the old code, what is it good for? */ + if ((!ritem || !btrfs_root_otransid(ritem)) root_offset) + rinfo-ogen = root_offset; For the older kernel: subvolume's original generation is always 0, but for snapshot, root_offset equals to its original generation. so we set it here. Thanks, Wang + + if (name name_len 0) { + rinfo-name = malloc(name_len + 1); + if (!rinfo-name) { fprintf(stderr, memory allocation failed\n); - exit(1); + return -1; } - strncpy(ri-name, name, name_len); - ri-name[name_len] = 0; + strncpy(rinfo-name, name, name_len); + rinfo-name[name_len] = 0; } - if (ref_tree) - ri-ref_tree = ref_tree; - if (root_offset) - ri-root_offset = root_offset; - if (flags) - ri-flags = flags; - if (dir_id) - ri-dir_id = dir_id; - if (gen) - ri-gen = gen; - if (ogen) - ri-ogen = ogen; - if (!ri-ogen root_offset) - ri-ogen = root_offset; - if (ot) - ri-otime = ot; - if (uuid) - memcpy(ri-uuid, uuid, BTRFS_UUID_SIZE); - if (puuid) - memcpy(ri-puuid, puuid, BTRFS_UUID_SIZE); return 0; } ... [snip] ... -- To unsubscribe from this list: send the line unsubscribe linux-btrfs in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH v2 3/4] Btrfs-progs: add more subvol fields to btrfs-list
Hello, The parent UUID, all generation values and all timestamps that are available in the root_item are added. Signed-off-by: Stefan Behrens sbehr...@giantdisaster.de --- btrfs-list.c | 273 +++ btrfs-list.h | 39 - 2 files changed, 197 insertions(+), 115 deletions(-) diff --git a/btrfs-list.c b/btrfs-list.c index 70da9a3..2d53290 100644 --- a/btrfs-list.c +++ b/btrfs-list.c @@ -68,6 +68,21 @@ static struct { .width = 6, }, { + .name = ogen, + .column_name= OGen, + .width = 6, + }, + { + .name = sgen, + .column_name= SGen, + .width = 6, + }, + { + .name = rgen, + .column_name= RGen, + .width = 6, + }, + { .name = parent, .column_name= Parent, .width = 7, @@ -78,13 +93,24 @@ static struct { .width = 10, }, { + .name = ctime, + .column_name= CTime, + .width = 21, + }, + { .name = otime, .column_name= OTime, .width = 21, }, { - .name = parent_uuid, - .column_name= Parent UUID, + .name = stime, + .column_name= STime, + .width = 21, + }, + { + .name = rtime, + .column_name= RTime, + .width = 21, }, { .name = uuid, @@ -92,6 +118,21 @@ static struct { .width = 38, }, { + .name = puuid, + .column_name= PUUID, + .width = 38, + }, + { + .name = ruuid, + .column_name= RUUID, + .width = 38, + }, + { + .name = dirid, + .column_name= DirID, + .width = 6, + }, + { .name = path, .column_name= Path, .width = 0, @@ -391,52 +432,70 @@ static struct root_info *root_tree_search(struct root_lookup *root_tree, return NULL; } -static int update_root(struct root_lookup *root_lookup, -u64 root_id, u64 ref_tree, u64 root_offset, u64 flags, -u64 dir_id, char *name, int name_len, u64 ogen, u64 gen, -time_t ot, void *uuid, void *puuid) +static int set_root_info(struct root_info *rinfo, u64 ref_tree, u64 root_offset, + u64 dir_id, char *name, int name_len, + struct btrfs_root_item *ritem, u32 ritem_len) { - struct root_info *ri; + int is_v0 = (ritem_len = sizeof(struct btrfs_root_item_v0)); - ri = root_tree_search(root_lookup, root_id); - if (!ri || ri-root_id != root_id) - return -ENOENT; - if (name name_len 0) { - if (ri-name) - free(ri-name); + if (root_offset) + rinfo-root_offset = root_offset; + if (ref_tree) + rinfo-ref_tree = ref_tree; + if (dir_id) + rinfo-dir_id = dir_id; + + if (ritem) { + rinfo-gen = btrfs_root_generation(ritem); + rinfo-flags = btrfs_root_flags(ritem); + } - ri-name = malloc(name_len + 1); - if (!ri-name) { + if (ritem !is_v0) { + rinfo-cgen = btrfs_root_ctransid(ritem); + rinfo-ogen = btrfs_root_otransid(ritem); + rinfo-sgen = btrfs_root_stransid(ritem); + rinfo-rgen = btrfs_root_rtransid(ritem); + rinfo-ctime = btrfs_stack_timespec_sec(ritem-ctime); + rinfo-otime = btrfs_stack_timespec_sec(ritem-otime); + rinfo-stime = btrfs_stack_timespec_sec(ritem-stime); + rinfo-rtime = btrfs_stack_timespec_sec(ritem-rtime); + memcpy(rinfo-uuid, ritem-uuid, BTRFS_UUID_SIZE); + memcpy(rinfo-puuid, ritem-parent_uuid, BTRFS_UUID_SIZE); + memcpy(rinfo-ruuid, ritem-received_uuid, BTRFS_UUID_SIZE); + } + + /* TODO: this is copied from the old code, what is it good for? */ + if ((!ritem || !btrfs_root_otransid(ritem)) root_offset) + rinfo-ogen = root_offset; For the older kernel: subvolume's original generation is always 0, but for snapshot, root_offset equals to its original generation. so we set it here. Thanks, Wang + + if (name name_len 0) { +
Re: [PATCH 2/2] Btrfs: introduce noextiref mount option
On thu, 11 Apr 2013 16:29:48 +0200, Jan Schmidt wrote: On Thu, April 11, 2013 at 12:35 (+0200), Miao Xie wrote: Now, we set incompat flag EXTEND_IREF when we actually need insert a extend inode reference, not when making a fs. But some users may hope that the fs still can be mounted on the old kernel, and don't hope we insert any extend inode references. So we introduce noextiref mount option to close this function. That's a much better approach compared to setting the flag on mkfs, I agree. Signed-off-by: Miao Xie mi...@cn.fujitsu.com Cc: Mark Fasheh mfas...@suse.de --- fs/btrfs/ctree.h | 1 + fs/btrfs/disk-io.c| 9 + fs/btrfs/inode-item.c | 2 +- fs/btrfs/super.c | 41 - 4 files changed, 51 insertions(+), 2 deletions(-) diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h index a883e47..db88963 100644 --- a/fs/btrfs/ctree.h +++ b/fs/btrfs/ctree.h @@ -1911,6 +1911,7 @@ struct btrfs_ioctl_defrag_range_args { #define BTRFS_MOUNT_CHECK_INTEGRITY (1 20) #define BTRFS_MOUNT_CHECK_INTEGRITY_INCLUDING_EXTENT_DATA (1 21) #define BTRFS_MOUNT_PANIC_ON_FATAL_ERROR(1 22) +#define BTRFS_MOUNT_NOEXTIREF (1 23) #define btrfs_clear_opt(o, opt) ((o) = ~BTRFS_MOUNT_##opt) #define btrfs_set_opt(o, opt) ((o) |= BTRFS_MOUNT_##opt) diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index ab8ef37..ee00448 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c @@ -2269,6 +2269,15 @@ int open_ctree(struct super_block *sb, goto fail_alloc; } +if ((btrfs_super_incompat_flags(disk_super) + BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF) +btrfs_test_opt(tree_root, NOEXTIREF)) { +printk(KERN_ERR BTRFS: couldn't mount because the extend iref + can not be close.\n); +err = -EINVAL; +goto fail_alloc; +} + if (btrfs_super_leafsize(disk_super) != btrfs_super_nodesize(disk_super)) { printk(KERN_ERR BTRFS: couldn't mount because metadata diff --git a/fs/btrfs/inode-item.c b/fs/btrfs/inode-item.c index f07eb45..7c4f880 100644 --- a/fs/btrfs/inode-item.c +++ b/fs/btrfs/inode-item.c @@ -442,7 +442,7 @@ int btrfs_insert_inode_ref(struct btrfs_trans_handle *trans, out: btrfs_free_path(path); -if (ret == -EMLINK) { +if (ret == -EMLINK !btrfs_test_opt(root, NOEXTIREF)) { /* * We ran out of space in the ref array. Need to add an * extended ref. diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c index 0f03569..fd375b3 100644 --- a/fs/btrfs/super.c +++ b/fs/btrfs/super.c @@ -315,7 +315,7 @@ enum { Opt_nodatacow, Opt_max_inline, Opt_alloc_start, Opt_nobarrier, Opt_ssd, Opt_nossd, Opt_ssd_spread, Opt_thread_pool, Opt_noacl, Opt_compress, Opt_compress_type, Opt_compress_force, Opt_compress_force_type, -Opt_notreelog, Opt_ratio, Opt_flushoncommit, Opt_discard, +Opt_notreelog, Opt_noextiref, Opt_ratio, Opt_flushoncommit, Opt_discard, Opt_space_cache, Opt_clear_cache, Opt_user_subvol_rm_allowed, Opt_enospc_debug, Opt_subvolrootid, Opt_defrag, Opt_inode_cache, Opt_no_space_cache, Opt_recovery, Opt_skip_balance, @@ -344,6 +344,7 @@ static match_table_t tokens = { {Opt_nossd, nossd}, {Opt_noacl, noacl}, {Opt_notreelog, notreelog}, +{Opt_noextiref, noextiref}, {Opt_flushoncommit, flushoncommit}, {Opt_ratio, metadata_ratio=%d}, {Opt_discard, discard}, @@ -535,6 +536,10 @@ int btrfs_parse_options(struct btrfs_root *root, char *options) printk(KERN_INFO btrfs: disabling tree log\n); btrfs_set_opt(info-mount_opt, NOTREELOG); break; +case Opt_noextiref: +printk(KERN_INFO btrfs: disabling extend inode ref\n); +btrfs_set_opt(info-mount_opt, NOEXTIREF); +break; case Opt_flushoncommit: printk(KERN_INFO btrfs: turning on flush-on-commit\n); btrfs_set_opt(info-mount_opt, FLUSHONCOMMIT); @@ -1202,6 +1207,35 @@ static void btrfs_resize_thread_pool(struct btrfs_fs_info *fs_info, new_pool_size); } +static int btrfs_close_extend_iref(struct btrfs_fs_info *fs_info, + unsigned long old_opts) The name irritated me, it's more like unset instead of close, isn't it? Maybe btrfs_set_no_extend_iref() is better, the other developers might think we will clear BTRFS_FEATURE_INCOMPAT_EXTENDED_IREF. +{ +struct btrfs_trans_handle *trans; +int ret; + +if (btrfs_raw_test_opt(old_opts, NOEXTIREF) || +!btrfs_raw_test_opt(fs_info-mount_opt, NOEXTIREF)) +return 0; + +trans = btrfs_attach_transaction(fs_info-tree_root); +if