[PATCH][RFC] Btrfs: Treat -EDQUOT like -ENOSPC during unlink

2015-06-03 Thread jmaggard10
From: Justin Maggard jmaggar...@gmail.com

Error messages saying, basically, you don't have enough
free space to free up space make people angry.

Sure, there are workarounds like truncating a file before
removing it; but it's certainly not obvious.  Unlink has a
special case if we cannot make our reservations the normal
way to try and see if there is enough slack room in the
global reserve to migrate.  Use the same retry for -EDQUOT.

There are certainly other (probably more proper) ways to
address this, but this is the least intrusive way that I
could think of.
---
 fs/btrfs/inode.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c
index 742f65d..d247c2d 100644
--- a/fs/btrfs/inode.c
+++ b/fs/btrfs/inode.c
@@ -4000,10 +4000,10 @@ static struct btrfs_trans_handle 
*__unlink_start_trans(struct inode *dir)
 * 1 for the inode
 */
trans = btrfs_start_transaction(root, 5);
-   if (!IS_ERR(trans) || PTR_ERR(trans) != -ENOSPC)
+   if (!IS_ERR(trans) || (PTR_ERR(trans) != -ENOSPC  PTR_ERR(trans) != 
-EDQUOT))
return trans;
 
-   if (PTR_ERR(trans) == -ENOSPC) {
+   if (PTR_ERR(trans) == -ENOSPC || PTR_ERR(trans) == -EDQUOT) {
u64 num_bytes = btrfs_calc_trans_metadata_size(root, 5);
 
trans = btrfs_start_transaction(root, 0);
-- 
2.4.2

--
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: btrfs_defrag_file: Fix calculation of max_to_defrag.

2015-06-03 Thread David Sterba
On Wed, Jun 03, 2015 at 02:59:54PM +0530, Chandan Rajendra wrote:
 max_to_defrag represents the number of pages to defrag rather than the last
 page of the file range to be defragged. Fix this.

Please update the changelog and describe the buggy behaviour. From a
brief look I think that the defrag batch will be much higher than
desired. Elsewhere the defrag batch is 1024, the page indexes used here
are always large numbers. I guess this could (partially) explain high
load during defrag that people report.

ACK for the fix, I'll stick a reviewed-by to v2.

 
 Signed-off-by: Chandan Rajendra chan...@linux.vnet.ibm.com
 ---
  fs/btrfs/ioctl.c | 2 +-
  1 file changed, 1 insertion(+), 1 deletion(-)
 
 diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c
 index ca5d968..2a45026 100644
 --- a/fs/btrfs/ioctl.c
 +++ b/fs/btrfs/ioctl.c
 @@ -1318,7 +1318,7 @@ int btrfs_defrag_file(struct inode *inode, struct file 
 *file,
   i = range-start  PAGE_CACHE_SHIFT;
   }
   if (!max_to_defrag)
 - max_to_defrag = last_index + 1;
 + max_to_defrag = last_index - i + 1;
  
   /*
* make writeback starts from i, so the defrag range can be
 -- 
 2.1.0
 
 --
 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: don't invalidate root dentry when subvolume deletion fails

2015-06-03 Thread David Sterba
On Tue, Jun 02, 2015 at 05:19:14PM -0700, Omar Sandoval wrote:
 I also can't figure out what that shrink_dcache_sb() is doing there.
 d_invalidate() already prunes the dentry cache under the deleted
 subvolume, but this clears the dcache for the whole filesystem, which
 could incur unnecessary overhead.

Correct analysis and the penalty is noticeable. In a directory where the
new/deleted subvolume flux is high. A 'ls' can take very long because all
the cached dentries are forcibly dropped and the metadata blocks have to be
read again.

 The call was added by efefb1438be2
 (Btrfs: remove negative dentry when deleting subvolumne), which fixes
 a problem in btrfs_dentry_delete(), but the commit message doesn't
 explain what shrink_dcache_sb() had to do with it. I'll send in an
 updated version with d_invalidate() moved and shrink_dcache_sb() removed
 and see if anyone can enlighten me.

I think it's a material for a separate patch.
--
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: qgroup: allow user to clear the limitation on qgroup

2015-06-03 Thread Tsutomu Itoh
On 2015/06/03 15:57, Dongsheng Yang wrote:
 Currently, we can only set a limitation on a qgroup, but we
 can not clear it.
 
 This patch provide a choice to user to clear a limitation on
 qgroup by passing a value of CLEAR_VALUE(-1) to kernel.
 
 Reported-by: Tsutomu Itoh t-i...@jp.fujitsu.com
 Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com

Tested-by: Tsutomu Itoh t-i...@jp.fujitsu.com

 ---
   fs/btrfs/qgroup.c | 49 +
   1 file changed, 41 insertions(+), 8 deletions(-)
 
 diff --git a/fs/btrfs/qgroup.c b/fs/btrfs/qgroup.c
 index 3d65465..0412d5b 100644
 --- a/fs/btrfs/qgroup.c
 +++ b/fs/btrfs/qgroup.c
 @@ -1317,6 +1317,11 @@ int btrfs_limit_qgroup(struct btrfs_trans_handle 
 *trans,
   struct btrfs_root *quota_root;
   struct btrfs_qgroup *qgroup;
   int ret = 0;
 + /* Sometimes we would want to clear the limit on this qgroup.
 +  * To meet this requirement, we treat the -1 as a special value
 +  * which tell kernel to clear the limit on this qgroup.
 +  */
 + const u64 CLEAR_VALUE = -1;
   
   mutex_lock(fs_info-qgroup_ioctl_lock);
   quota_root = fs_info-quota_root;
 @@ -1332,14 +1337,42 @@ int btrfs_limit_qgroup(struct btrfs_trans_handle 
 *trans,
   }
   
   spin_lock(fs_info-qgroup_lock);
 - if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_RFER)
 - qgroup-max_rfer = limit-max_rfer;
 - if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_EXCL)
 - qgroup-max_excl = limit-max_excl;
 - if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_RFER)
 - qgroup-rsv_rfer = limit-rsv_rfer;
 - if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_EXCL)
 - qgroup-rsv_excl = limit-rsv_excl;
 + if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_RFER) {
 + if (limit-max_rfer == CLEAR_VALUE) {
 + qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_MAX_RFER;
 + limit-flags = ~BTRFS_QGROUP_LIMIT_MAX_RFER;
 + qgroup-max_rfer = 0;
 + } else {
 + qgroup-max_rfer = limit-max_rfer;
 + }
 + }
 + if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_EXCL) {
 + if (limit-max_excl == CLEAR_VALUE) {
 + qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_MAX_EXCL;
 + limit-flags = ~BTRFS_QGROUP_LIMIT_MAX_EXCL;
 + qgroup-max_excl = 0;
 + } else {
 + qgroup-max_excl = limit-max_excl;
 + }
 + }
 + if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_RFER) {
 + if (limit-rsv_rfer == CLEAR_VALUE) {
 + qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_RSV_RFER;
 + limit-flags = ~BTRFS_QGROUP_LIMIT_RSV_RFER;
 + qgroup-rsv_rfer = 0;
 + } else {
 + qgroup-rsv_rfer = limit-rsv_rfer;
 + }
 + }
 + if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_EXCL) {
 + if (limit-rsv_excl == CLEAR_VALUE) {
 + qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_RSV_EXCL;
 + limit-flags = ~BTRFS_QGROUP_LIMIT_RSV_EXCL;
 + qgroup-rsv_excl = 0;
 + } else {
 + qgroup-rsv_excl = limit-rsv_excl;
 + }
 + }
   qgroup-lim_flags |= limit-flags;
   
   spin_unlock(fs_info-qgroup_lock);
 


--
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-progs: qgroup: allow user to clear some limitation on qgroup.

2015-06-03 Thread Tsutomu Itoh
On 2015/06/03 15:57, Dongsheng Yang wrote:
 Currently, we can not clear a limitation on a qgroup. Although
 there is a 'none' choice provided to user to do it, it does not
 work well.
 
 It does not set the flag which user want to clear, then kernel
 will never know what the user want to do at all.
 
 *Without this commit*
   # ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB  5.00GiB none
 0/257   100.02MiB100.02MiB none none
   # ./btrfs qgroup limit none /mnt
   # ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB  5.00GiB none
 0/257   100.02MiB100.02MiB none none
 
 This patch will set the flag user want to clear and pass a
 size=-1 to kernel. Then kernel will clear it correctly.
 
 *With this commit*
   # ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB  5.00GiB none
 0/257   100.02MiB100.02MiB none none
   # ./btrfs qgroup limit none /mnt
   # ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB none none
 0/257   100.02MiB100.02MiB none none
 
 Reported-by: Tsutomu Itoh t-i...@jp.fujitsu.com
 Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
 ---
   cmds-qgroup.c | 23 +++
   1 file changed, 11 insertions(+), 12 deletions(-)
 
 diff --git a/cmds-qgroup.c b/cmds-qgroup.c
 index b073250..00cc089 100644
 --- a/cmds-qgroup.c
 +++ b/cmds-qgroup.c
 @@ -110,9 +110,10 @@ static int parse_limit(const char *p, unsigned long long 
 *s)
   {
   char *endptr;
   unsigned long long size;
 + unsigned long long CLEAR_VALUE = -1;

Even if a negative value is specified, it doesn't become an error...
So, it doesn't make an error of the following command.

# btrfs qg lim -- -1 sub1
# btrfs qg show -prce /test1
qgroupid rfer excl max_rfer max_excl parent  child
     --  -
0/5  16.00KiB 16.00KiB none none --- ---
0/259 8.86GiB  7.88GiB none none --- ---
# btrfs qg lim -- -2 sub1
# btrfs qg show -prce /test1
qgroupid rfer excl max_rfer max_excl parent  child
     --  -
0/5  16.00KiB 16.00KiB none none --- ---
0/259 8.86GiB  7.88GiB 16.00EiB none --- ---

Otherwise OK,

Tested-by: Tsutomu Itoh t-i...@jp.fujitsu.com


   
   if (strcasecmp(p, none) == 0) {
 - *s = 0;
 + *s = CLEAR_VALUE;
   return 1;
   }
   size = strtoull(p, endptr, 10);
 @@ -406,17 +407,15 @@ static int cmd_qgroup_limit(int argc, char **argv)
   }
   
   memset(args, 0, sizeof(args));
 - if (size) {
 - if (compressed)
 - args.lim.flags |= BTRFS_QGROUP_LIMIT_RFER_CMPR |
 -   BTRFS_QGROUP_LIMIT_EXCL_CMPR;
 - if (exclusive) {
 - args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_EXCL;
 - args.lim.max_exclusive = size;
 - } else {
 - args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_RFER;
 - args.lim.max_referenced = size;
 - }
 + if (compressed)
 + args.lim.flags |= BTRFS_QGROUP_LIMIT_RFER_CMPR |
 +   BTRFS_QGROUP_LIMIT_EXCL_CMPR;
 + if (exclusive) {
 + args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_EXCL;
 + args.lim.max_exclusive = size;
 + } else {
 + args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_RFER;
 + args.lim.max_referenced = size;
   }
   
   if (argc - optind == 2) {
 


--
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-progs: qgroup limit: add a check for invalid input of 'T/G/M/K'

2015-06-03 Thread Dongsheng Yang
Add a check to error out in the following case:

 # ./btrfs qgroup limit  T /mnt/
Invalid size argument given

Without this patch, btrfs-progs would parse the input as 0
and continue.

Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
 cmds-qgroup.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/cmds-qgroup.c b/cmds-qgroup.c
index 5ea4021..9545a20 100644
--- a/cmds-qgroup.c
+++ b/cmds-qgroup.c
@@ -121,6 +121,9 @@ static int parse_limit(const char *p, unsigned long long *s)
return 0;
 
size = strtoull(p, endptr, 10);
+   if (p == endptr)
+   return 0;
+
switch (*endptr) {
case 'T':
case 't':
-- 
1.8.4.2

--
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-progs: qgroup: show 'none' when we did not limit it on this qgroup

2015-06-03 Thread Dongsheng Yang
There are two understanding of the '0' value in btrfs qgroup show.
(1) is no-limitation on this qgroup. (2) is the max-limitation is 0.

This patch make it showing in different way.

(1). max-limitation for 0 is still showing '0'.
(2). no-limitation will show 'none'.

qgroupid rfer excl max_rfer max_excl parent
     --
0/5   2.19GiB  2.19GiB none none ---
0/257   100.02MiB100.02MiB none none ---

Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
 qgroup.c | 10 --
 1 file changed, 8 insertions(+), 2 deletions(-)

diff --git a/qgroup.c b/qgroup.c
index 53815b5..dc04b03 100644
--- a/qgroup.c
+++ b/qgroup.c
@@ -237,10 +237,16 @@ static void print_qgroup_column(struct btrfs_qgroup 
*qgroup,
print_qgroup_column_add_blank(BTRFS_QGROUP_PARENT, len);
break;
case BTRFS_QGROUP_MAX_RFER:
-   len = printf(%*s, max_len, pretty_size_mode(qgroup-max_rfer, 
unit_mode));
+   if (qgroup-flags  BTRFS_QGROUP_LIMIT_MAX_RFER)
+   len = printf(%*s, max_len, 
pretty_size_mode(qgroup-max_rfer, unit_mode));
+   else
+   len = printf(%*s, max_len, none);
break;
case BTRFS_QGROUP_MAX_EXCL:
-   len = printf(%*s, max_len, pretty_size_mode(qgroup-max_excl, 
unit_mode));
+   if (qgroup-flags  BTRFS_QGROUP_LIMIT_MAX_EXCL)
+   len = printf(%*s, max_len, 
pretty_size_mode(qgroup-max_excl, unit_mode));
+   else
+   len = printf(%*s, max_len, none);
break;
case BTRFS_QGROUP_CHILD:
len = print_child_column(qgroup);
-- 
1.8.4.2

--
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-progs: qgroup: allow user to clear some limitation on qgroup.

2015-06-03 Thread Dongsheng Yang
Currently, we can not clear a limitation on a qgroup. Although
there is a 'none' choice provided to user to do it, it does not
work well.

It does not set the flag which user want to clear, then kernel
will never know what the user want to do at all.

*Without this commit*
 # ./btrfs qgroup show -re /mnt
qgroupid rfer excl max_rfer max_excl
    
0/5   2.19GiB  2.19GiB  5.00GiB none
0/257   100.02MiB100.02MiB none none
 # ./btrfs qgroup limit none /mnt
 # ./btrfs qgroup show -re /mnt
qgroupid rfer excl max_rfer max_excl
    
0/5   2.19GiB  2.19GiB  5.00GiB none
0/257   100.02MiB100.02MiB none none

This patch will set the flag user want to clear and pass a
size=-1 to kernel. Then kernel will clear it correctly.

*With this commit*
 # ./btrfs qgroup show -re /mnt
qgroupid rfer excl max_rfer max_excl
    
0/5   2.19GiB  2.19GiB  5.00GiB none
0/257   100.02MiB100.02MiB none none
 # ./btrfs qgroup limit none /mnt
 # ./btrfs qgroup show -re /mnt
qgroupid rfer excl max_rfer max_excl
    
0/5   2.19GiB  2.19GiB none none
0/257   100.02MiB100.02MiB none none

Reported-by: Tsutomu Itoh t-i...@jp.fujitsu.com
Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
 cmds-qgroup.c | 23 +++
 1 file changed, 11 insertions(+), 12 deletions(-)

diff --git a/cmds-qgroup.c b/cmds-qgroup.c
index b073250..00cc089 100644
--- a/cmds-qgroup.c
+++ b/cmds-qgroup.c
@@ -110,9 +110,10 @@ static int parse_limit(const char *p, unsigned long long 
*s)
 {
char *endptr;
unsigned long long size;
+   unsigned long long CLEAR_VALUE = -1;
 
if (strcasecmp(p, none) == 0) {
-   *s = 0;
+   *s = CLEAR_VALUE;
return 1;
}
size = strtoull(p, endptr, 10);
@@ -406,17 +407,15 @@ static int cmd_qgroup_limit(int argc, char **argv)
}
 
memset(args, 0, sizeof(args));
-   if (size) {
-   if (compressed)
-   args.lim.flags |= BTRFS_QGROUP_LIMIT_RFER_CMPR |
- BTRFS_QGROUP_LIMIT_EXCL_CMPR;
-   if (exclusive) {
-   args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_EXCL;
-   args.lim.max_exclusive = size;
-   } else {
-   args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_RFER;
-   args.lim.max_referenced = size;
-   }
+   if (compressed)
+   args.lim.flags |= BTRFS_QGROUP_LIMIT_RFER_CMPR |
+ BTRFS_QGROUP_LIMIT_EXCL_CMPR;
+   if (exclusive) {
+   args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_EXCL;
+   args.lim.max_exclusive = size;
+   } else {
+   args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_RFER;
+   args.lim.max_referenced = size;
}
 
if (argc - optind == 2) {
-- 
1.8.4.2

--
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] btrfs: qgroup: allow user to clear the limitation on qgroup

2015-06-03 Thread Dongsheng Yang
Currently, we can only set a limitation on a qgroup, but we
can not clear it.

This patch provide a choice to user to clear a limitation on
qgroup by passing a value of CLEAR_VALUE(-1) to kernel.

Reported-by: Tsutomu Itoh t-i...@jp.fujitsu.com
Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
 fs/btrfs/qgroup.c | 49 +
 1 file changed, 41 insertions(+), 8 deletions(-)

diff --git a/fs/btrfs/qgroup.c b/fs/btrfs/qgroup.c
index 3d65465..0412d5b 100644
--- a/fs/btrfs/qgroup.c
+++ b/fs/btrfs/qgroup.c
@@ -1317,6 +1317,11 @@ int btrfs_limit_qgroup(struct btrfs_trans_handle *trans,
struct btrfs_root *quota_root;
struct btrfs_qgroup *qgroup;
int ret = 0;
+   /* Sometimes we would want to clear the limit on this qgroup.
+* To meet this requirement, we treat the -1 as a special value
+* which tell kernel to clear the limit on this qgroup.
+*/
+   const u64 CLEAR_VALUE = -1;
 
mutex_lock(fs_info-qgroup_ioctl_lock);
quota_root = fs_info-quota_root;
@@ -1332,14 +1337,42 @@ int btrfs_limit_qgroup(struct btrfs_trans_handle *trans,
}
 
spin_lock(fs_info-qgroup_lock);
-   if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_RFER)
-   qgroup-max_rfer = limit-max_rfer;
-   if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_EXCL)
-   qgroup-max_excl = limit-max_excl;
-   if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_RFER)
-   qgroup-rsv_rfer = limit-rsv_rfer;
-   if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_EXCL)
-   qgroup-rsv_excl = limit-rsv_excl;
+   if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_RFER) {
+   if (limit-max_rfer == CLEAR_VALUE) {
+   qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_MAX_RFER;
+   limit-flags = ~BTRFS_QGROUP_LIMIT_MAX_RFER;
+   qgroup-max_rfer = 0;
+   } else {
+   qgroup-max_rfer = limit-max_rfer;
+   }
+   }
+   if (limit-flags  BTRFS_QGROUP_LIMIT_MAX_EXCL) {
+   if (limit-max_excl == CLEAR_VALUE) {
+   qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_MAX_EXCL;
+   limit-flags = ~BTRFS_QGROUP_LIMIT_MAX_EXCL;
+   qgroup-max_excl = 0;
+   } else {
+   qgroup-max_excl = limit-max_excl;
+   }
+   }
+   if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_RFER) {
+   if (limit-rsv_rfer == CLEAR_VALUE) {
+   qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_RSV_RFER;
+   limit-flags = ~BTRFS_QGROUP_LIMIT_RSV_RFER;
+   qgroup-rsv_rfer = 0;
+   } else {
+   qgroup-rsv_rfer = limit-rsv_rfer;
+   }
+   }
+   if (limit-flags  BTRFS_QGROUP_LIMIT_RSV_EXCL) {
+   if (limit-rsv_excl == CLEAR_VALUE) {
+   qgroup-lim_flags = ~BTRFS_QGROUP_LIMIT_RSV_EXCL;
+   limit-flags = ~BTRFS_QGROUP_LIMIT_RSV_EXCL;
+   qgroup-rsv_excl = 0;
+   } else {
+   qgroup-rsv_excl = limit-rsv_excl;
+   }
+   }
qgroup-lim_flags |= limit-flags;
 
spin_unlock(fs_info-qgroup_lock);
-- 
1.8.4.2

--
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 1/2] btrfs-progs: avoid duplicate checks on user provided devid

2015-06-03 Thread Anand Jain


On 06/02/2015 11:12 PM, David Sterba wrote:

On Mon, Jun 01, 2015 at 02:25:17PM +0800, Anand Jain wrote:

kernel is already checking it (rightly), we don't need to check that in the 
user land.


Sometimes it's useful to duplicate the checks in userspace because we
can fail early and return the error message directly, compared to
messages in syslog or a simple errno.


 right. But here what do you feel about the gain obtained vs additional
 code thats required ?

 My take: get_fs_info() calls check_mounted_where() which in turn calls
 btrfs_scan_lblkid(), which is system wide scan of all block devices,
 thats heavy weight.

 My past tests showed visible delay/jitter in the output of
 'btrfs fi show -d' when btrfs scrub is running. The main culprit
 is check_mounted_where calling btrfs_scan_lblkid. so its recommend
 to run get_fs_info() only if required.


Have you observed that the userspace checks were problematic?


 Nope. Just a cleanup. With this patch cmd_start_replace() would
 should match with cmd_rm_dev().
 As both 'btrfs dev del devid ..' and 'btrfs replace start devid ..
 intentions are same, so theoretically up to certain extent their codes
 should match.


@@ -214,33 +213,7 @@ static int cmd_start_replace(int argc, char **argv)
}

if (is_numerical(srcdev)) {
-   struct btrfs_ioctl_fs_info_args fi_args;
-   struct btrfs_ioctl_dev_info_args *di_args = NULL;
-
start_args.start.srcdevid = arg_strtou64(srcdev);
-
-   ret = get_fs_info(path, fi_args, di_args);


This does additional checks, like checking where it's mounted.


 in this part of the if statement srcdev is num and is devid.
 get_fs_info check does not help.

 What did I miss ?

Thanks Anand


--
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


[PATCH 1/2] btrfs-progs: qgroup limit: error out if input value is negative

2015-06-03 Thread Dongsheng Yang
If we pass a negative value to command qgroup limit, btrfs-progs
would convert it to unsigned long long silently. That's a little
confusing to user, why I can limit my quota to a negative value.

This patch add a check in parse_limit, if the input value is negative,
error out to user.

Reported-by: Tsutomu Itoh t-i...@jp.fujitsu.com
Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
 cmds-qgroup.c | 4 
 1 file changed, 4 insertions(+)

diff --git a/cmds-qgroup.c b/cmds-qgroup.c
index 00cc089..5ea4021 100644
--- a/cmds-qgroup.c
+++ b/cmds-qgroup.c
@@ -116,6 +116,10 @@ static int parse_limit(const char *p, unsigned long long 
*s)
*s = CLEAR_VALUE;
return 1;
}
+
+   if (p[0] == '-')
+   return 0;
+
size = strtoull(p, endptr, 10);
switch (*endptr) {
case 'T':
-- 
1.8.4.2

--
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] xfstests: btrfs: 022: add a quota rescan -w to wait rescan finished.

2015-06-03 Thread Dongsheng Yang
When we enable quota, btrfs will rescan quota numbers. We need
to wait the rescan finished before any more operations on btrfs
qgroups. Otherwith, the new btrfs-progs would WARN out:

WARNING: Rescan is running, qgroup data may be incorrect.

It would make btrfs/022 failed.

Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
 tests/btrfs/022 | 1 +
 1 file changed, 1 insertion(+)

diff --git a/tests/btrfs/022 b/tests/btrfs/022
index 5c1a82d..56d4f3d 100755
--- a/tests/btrfs/022
+++ b/tests/btrfs/022
@@ -51,6 +51,7 @@ _basic_test()
 {
_run_btrfs_util_prog subvolume create $SCRATCH_MNT/a
_run_btrfs_util_prog quota enable $SCRATCH_MNT/a
+   _run_btrfs_util_prog quota rescan -w $SCRATCH_MNT
subvolid=$(_btrfs_get_subvolid $SCRATCH_MNT a)
$BTRFS_UTIL_PROG qgroup show $units $SCRATCH_MNT | grep $subvolid  \
$seqres.full 21
-- 
1.8.4.2

--
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 1/2] btrfs-progs: qgroup: show 'none' when we did not limit it on this qgroup

2015-06-03 Thread Tsutomu Itoh
On 2015/06/03 15:57, Dongsheng Yang wrote:
 There are two understanding of the '0' value in btrfs qgroup show.
 (1) is no-limitation on this qgroup. (2) is the max-limitation is 0.
 
 This patch make it showing in different way.
 
 (1). max-limitation for 0 is still showing '0'.
 (2). no-limitation will show 'none'.
 
 qgroupid rfer excl max_rfer max_excl parent
      --
 0/5   2.19GiB  2.19GiB none none ---
 0/257   100.02MiB100.02MiB none none ---
 
 Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com

Tested-by: Tsutomu Itoh t-i...@jp.fujitsu.com

 ---
   qgroup.c | 10 --
   1 file changed, 8 insertions(+), 2 deletions(-)
 
 diff --git a/qgroup.c b/qgroup.c
 index 53815b5..dc04b03 100644
 --- a/qgroup.c
 +++ b/qgroup.c
 @@ -237,10 +237,16 @@ static void print_qgroup_column(struct btrfs_qgroup 
 *qgroup,
   print_qgroup_column_add_blank(BTRFS_QGROUP_PARENT, len);
   break;
   case BTRFS_QGROUP_MAX_RFER:
 - len = printf(%*s, max_len, pretty_size_mode(qgroup-max_rfer, 
 unit_mode));
 + if (qgroup-flags  BTRFS_QGROUP_LIMIT_MAX_RFER)
 + len = printf(%*s, max_len, 
 pretty_size_mode(qgroup-max_rfer, unit_mode));
 + else
 + len = printf(%*s, max_len, none);
   break;
   case BTRFS_QGROUP_MAX_EXCL:
 - len = printf(%*s, max_len, pretty_size_mode(qgroup-max_excl, 
 unit_mode));
 + if (qgroup-flags  BTRFS_QGROUP_LIMIT_MAX_EXCL)
 + len = printf(%*s, max_len, 
 pretty_size_mode(qgroup-max_excl, unit_mode));
 + else
 + len = printf(%*s, max_len, none);
   break;
   case BTRFS_QGROUP_CHILD:
   len = print_child_column(qgroup);
 


--
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] xfstests: btrfs: 022: add a quota rescan -w to wait rescan finished.

2015-06-03 Thread Dongsheng Yang

Hi Filip,

Qu is off duty this week, would you please try this patch here?

Thanx
Yang

On 06/03/2015 03:10 PM, Dongsheng Yang wrote:

When we enable quota, btrfs will rescan quota numbers. We need
to wait the rescan finished before any more operations on btrfs
qgroups. Otherwith, the new btrfs-progs would WARN out:

WARNING: Rescan is running, qgroup data may be incorrect.

It would make btrfs/022 failed.

Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
---
  tests/btrfs/022 | 1 +
  1 file changed, 1 insertion(+)

diff --git a/tests/btrfs/022 b/tests/btrfs/022
index 5c1a82d..56d4f3d 100755
--- a/tests/btrfs/022
+++ b/tests/btrfs/022
@@ -51,6 +51,7 @@ _basic_test()
  {
_run_btrfs_util_prog subvolume create $SCRATCH_MNT/a
_run_btrfs_util_prog quota enable $SCRATCH_MNT/a
+   _run_btrfs_util_prog quota rescan -w $SCRATCH_MNT
subvolid=$(_btrfs_get_subvolid $SCRATCH_MNT a)
$BTRFS_UTIL_PROG qgroup show $units $SCRATCH_MNT | grep $subvolid  \
$seqres.full 21



--
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-progs: qgroup: allow user to clear some limitation on qgroup.

2015-06-03 Thread Dongsheng Yang
On 06/03/2015 04:40 PM, Tsutomu Itoh wrote:
 On 2015/06/03 15:57, Dongsheng Yang wrote:
 Currently, we can not clear a limitation on a qgroup. Although
 there is a 'none' choice provided to user to do it, it does not
 work well.

 It does not set the flag which user want to clear, then kernel
 will never know what the user want to do at all.

 *Without this commit*
# ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB  5.00GiB none
 0/257   100.02MiB100.02MiB none none
# ./btrfs qgroup limit none /mnt
# ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB  5.00GiB none
 0/257   100.02MiB100.02MiB none none

 This patch will set the flag user want to clear and pass a
 size=-1 to kernel. Then kernel will clear it correctly.

 *With this commit*
# ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB  5.00GiB none
 0/257   100.02MiB100.02MiB none none
# ./btrfs qgroup limit none /mnt
# ./btrfs qgroup show -re /mnt
 qgroupid rfer excl max_rfer max_excl
     
 0/5   2.19GiB  2.19GiB none none
 0/257   100.02MiB100.02MiB none none

 Reported-by: Tsutomu Itoh t-i...@jp.fujitsu.com
 Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
 ---
cmds-qgroup.c | 23 +++
1 file changed, 11 insertions(+), 12 deletions(-)

 diff --git a/cmds-qgroup.c b/cmds-qgroup.c
 index b073250..00cc089 100644
 --- a/cmds-qgroup.c
 +++ b/cmds-qgroup.c
 @@ -110,9 +110,10 @@ static int parse_limit(const char *p, unsigned long 
 long *s)
{
  char *endptr;
  unsigned long long size;
 +unsigned long long CLEAR_VALUE = -1;
 
 Even if a negative value is specified, it doesn't become an error...
 So, it doesn't make an error of the following command.
 
 # btrfs qg lim -- -1 sub1
 # btrfs qg show -prce /test1
 qgroupid rfer excl max_rfer max_excl parent  child
      --  -
 0/5  16.00KiB 16.00KiB none none --- ---
 0/259 8.86GiB  7.88GiB none none --- ---
 # btrfs qg lim -- -2 sub1
 # btrfs qg show -prce /test1
 qgroupid rfer excl max_rfer max_excl parent  child
      --  -
 0/5  16.00KiB 16.00KiB none none --- ---
 0/259 8.86GiB  7.88GiB 16.00EiB none --- ---

Agreed, I understand your point here.

If we pass a negative value to limit command, we should Error out. But
currently, btrfs-progs are treating it as a unsigned value in parsing
it. Yes, that's a bit of confusing.

We need to cover it in parsing steps with another patch I think.
 
 Otherwise OK,
 
 Tested-by: Tsutomu Itoh t-i...@jp.fujitsu.com

Thanx


Yang
 
 

  if (strcasecmp(p, none) == 0) {
 -*s = 0;
 +*s = CLEAR_VALUE;
  return 1;
  }
  size = strtoull(p, endptr, 10);
 @@ -406,17 +407,15 @@ static int cmd_qgroup_limit(int argc, char **argv)
  }

  memset(args, 0, sizeof(args));
 -if (size) {
 -if (compressed)
 -args.lim.flags |= BTRFS_QGROUP_LIMIT_RFER_CMPR |
 -  BTRFS_QGROUP_LIMIT_EXCL_CMPR;
 -if (exclusive) {
 -args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_EXCL;
 -args.lim.max_exclusive = size;
 -} else {
 -args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_RFER;
 -args.lim.max_referenced = size;
 -}
 +if (compressed)
 +args.lim.flags |= BTRFS_QGROUP_LIMIT_RFER_CMPR |
 +  BTRFS_QGROUP_LIMIT_EXCL_CMPR;
 +if (exclusive) {
 +args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_EXCL;
 +args.lim.max_exclusive = size;
 +} else {
 +args.lim.flags |= BTRFS_QGROUP_LIMIT_MAX_RFER;
 +args.lim.max_referenced = size;
  }

  if (argc - optind == 2) {

 
 
 .
 

--
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] Btrfs: btrfs_defrag_file: Fix calculation of max_to_defrag.

2015-06-03 Thread Chandan Rajendra
max_to_defrag represents the number of pages to defrag rather than the last
page of the file range to be defragged. Fix this.

Signed-off-by: Chandan Rajendra chan...@linux.vnet.ibm.com
---
 fs/btrfs/ioctl.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c
index ca5d968..2a45026 100644
--- a/fs/btrfs/ioctl.c
+++ b/fs/btrfs/ioctl.c
@@ -1318,7 +1318,7 @@ int btrfs_defrag_file(struct inode *inode, struct file 
*file,
i = range-start  PAGE_CACHE_SHIFT;
}
if (!max_to_defrag)
-   max_to_defrag = last_index + 1;
+   max_to_defrag = last_index - i + 1;
 
/*
 * make writeback starts from i, so the defrag range can be
-- 
2.1.0

--
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] btrfs: cleanup, stop casting for extent_map-lookup everywhere

2015-06-03 Thread jeffm
From: Jeff Mahoney je...@suse.com

Overloading extent_map-bdev to struct map_lookup * might have started out
as a means to an end, but it's a pattern that's used all over the place
now. Let's get rid of the casting and just add a union instead.

Signed-off-by: Jeff Mahoney je...@suse.com
---
 fs/btrfs/dev-replace.c |  2 +-
 fs/btrfs/extent_map.c  |  2 +-
 fs/btrfs/extent_map.h  | 10 +-
 fs/btrfs/scrub.c   |  2 +-
 fs/btrfs/volumes.c | 24 
 5 files changed, 24 insertions(+), 16 deletions(-)

diff --git a/fs/btrfs/dev-replace.c b/fs/btrfs/dev-replace.c
index 0573848..2ad3289 100644
--- a/fs/btrfs/dev-replace.c
+++ b/fs/btrfs/dev-replace.c
@@ -613,7 +613,7 @@ static void btrfs_dev_replace_update_device_in_mapping_tree(
em = lookup_extent_mapping(em_tree, start, (u64)-1);
if (!em)
break;
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
for (i = 0; i  map-num_stripes; i++)
if (srcdev == map-stripes[i].dev)
map-stripes[i].dev = tgtdev;
diff --git a/fs/btrfs/extent_map.c b/fs/btrfs/extent_map.c
index 6a98bdd..84fb56d 100644
--- a/fs/btrfs/extent_map.c
+++ b/fs/btrfs/extent_map.c
@@ -76,7 +76,7 @@ void free_extent_map(struct extent_map *em)
WARN_ON(extent_map_in_tree(em));
WARN_ON(!list_empty(em-list));
if (test_bit(EXTENT_FLAG_FS_MAPPING, em-flags))
-   kfree(em-bdev);
+   kfree(em-map_lookup);
kmem_cache_free(extent_map_cache, em);
}
 }
diff --git a/fs/btrfs/extent_map.h b/fs/btrfs/extent_map.h
index b2991fd..eb8b8fa 100644
--- a/fs/btrfs/extent_map.h
+++ b/fs/btrfs/extent_map.h
@@ -32,7 +32,15 @@ struct extent_map {
u64 block_len;
u64 generation;
unsigned long flags;
-   struct block_device *bdev;
+   union {
+   struct block_device *bdev;
+
+   /*
+* used for chunk mappings
+* flags  EXTENT_FLAG_FS_MAPPING must be set
+*/
+   struct map_lookup *map_lookup;
+   };
atomic_t refs;
unsigned int compress_type;
struct list_head list;
diff --git a/fs/btrfs/scrub.c b/fs/btrfs/scrub.c
index ab58115..19f7241d 100644
--- a/fs/btrfs/scrub.c
+++ b/fs/btrfs/scrub.c
@@ -3339,7 +3339,7 @@ static noinline_for_stack int scrub_chunk(struct 
scrub_ctx *sctx,
if (!em)
return -EINVAL;
 
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
if (em-start != chunk_offset)
goto out;
 
diff --git a/fs/btrfs/volumes.c b/fs/btrfs/volumes.c
index 7fdde31..9f48ae5 100644
--- a/fs/btrfs/volumes.c
+++ b/fs/btrfs/volumes.c
@@ -1068,7 +1068,7 @@ again:
struct map_lookup *map;
int i;
 
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
for (i = 0; i  map-num_stripes; i++) {
if (map-stripes[i].dev != device)
continue;
@@ -2622,7 +2622,7 @@ int btrfs_remove_chunk(struct btrfs_trans_handle *trans,
free_extent_map(em);
return -EINVAL;
}
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
 
for (i = 0; i  map-num_stripes; i++) {
struct btrfs_device *device = map-stripes[i].dev;
@@ -4465,7 +4465,7 @@ static int __btrfs_alloc_chunk(struct btrfs_trans_handle 
*trans,
goto error;
}
set_bit(EXTENT_FLAG_FS_MAPPING, em-flags);
-   em-bdev = (struct block_device *)map;
+   em-map_lookup = map;
em-start = start;
em-len = num_bytes;
em-block_start = 0;
@@ -4560,7 +4560,7 @@ int btrfs_finish_chunk_alloc(struct btrfs_trans_handle 
*trans,
return -EINVAL;
}
 
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
item_size = btrfs_chunk_item_size(map-num_stripes);
stripe_size = em-orig_block_len;
 
@@ -4702,7 +4702,7 @@ int btrfs_chunk_readonly(struct btrfs_root *root, u64 
chunk_offset)
if (!em)
return 1;
 
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
for (i = 0; i  map-num_stripes; i++) {
if (map-stripes[i].dev-missing) {
miss_ndevs++;
@@ -4782,7 +4782,7 @@ int btrfs_num_copies(struct btrfs_fs_info *fs_info, u64 
logical, u64 len)
return 1;
}
 
-   map = (struct map_lookup *)em-bdev;
+   map = em-map_lookup;
if (map-type  (BTRFS_BLOCK_GROUP_DUP | BTRFS_BLOCK_GROUP_RAID1))
ret = map-num_stripes;
else if (map-type  BTRFS_BLOCK_GROUP_RAID10)
@@ -4818,7 +4818,7 @@ unsigned long btrfs_full_stripe_len(struct btrfs_root 
*root,

[PATCH 3/3] btrfs: add missing discards when unpinning extents with -o discard

2015-06-03 Thread jeffm
From: Jeff Mahoney je...@suse.com

When we clear the dirty bits in btrfs_delete_unused_bgs for extents
in the empty block group, it results in btrfs_finish_extent_commit being
unable to discard the freed extents.

The block group removal patch added an alternate path to forget extents
other than btrfs_finish_extent_commit.  As a result, any extents that
would be freed when the block group is removed aren't discarded.  In my
test run, with a large copy of mixed sized files followed by removal, it
left nearly 2/3 of extents undiscarded.

To clean up the block groups, we add the removed block group onto a list
that will be discarded after transaction commit.

v1-v2:
- Fix ordering to ensure that we don't discard extents freed in an
  uncommitted transaction.

v2-v3:
- Factor out get/put block_group-trimming to ensure that cleanup always
  happens at the last reference drop.
- Cleanup the free space cache on the last reference drop.
- Use list_move instead of list_add in case of multiple adds.  We still
  issue a warning, but we shouldn't fall over.

Signed-off-by: Jeff Mahoney je...@suse.com
---
 fs/btrfs/ctree.h|  3 ++
 fs/btrfs/extent-tree.c  | 69 ++---
 fs/btrfs/free-space-cache.c | 57 +
 fs/btrfs/super.c|  2 +-
 fs/btrfs/transaction.c  |  2 ++
 fs/btrfs/transaction.h  |  2 ++
 6 files changed, 106 insertions(+), 29 deletions(-)

diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h
index 6f364e1..780acf1 100644
--- a/fs/btrfs/ctree.h
+++ b/fs/btrfs/ctree.h
@@ -3438,6 +3438,8 @@ int btrfs_remove_block_group(struct btrfs_trans_handle 
*trans,
 struct btrfs_root *root, u64 group_start,
 struct extent_map *em);
 void btrfs_delete_unused_bgs(struct btrfs_fs_info *fs_info);
+void btrfs_get_block_group_trimming(struct btrfs_block_group_cache *cache);
+void btrfs_put_block_group_trimming(struct btrfs_block_group_cache *cache);
 void btrfs_create_pending_block_groups(struct btrfs_trans_handle *trans,
   struct btrfs_root *root);
 u64 btrfs_get_alloc_profile(struct btrfs_root *root, int data);
@@ -4068,6 +4070,7 @@ __printf(5, 6)
 void __btrfs_std_error(struct btrfs_fs_info *fs_info, const char *function,
 unsigned int line, int errno, const char *fmt, ...);
 
+const char *btrfs_decode_error(int errno);
 
 void __btrfs_abort_transaction(struct btrfs_trans_handle *trans,
   struct btrfs_root *root, const char *function,
diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c
index fb4dbfc..e53dbe9 100644
--- a/fs/btrfs/extent-tree.c
+++ b/fs/btrfs/extent-tree.c
@@ -6034,20 +6034,19 @@ int btrfs_finish_extent_commit(struct 
btrfs_trans_handle *trans,
   struct btrfs_root *root)
 {
struct btrfs_fs_info *fs_info = root-fs_info;
+   struct btrfs_block_group_cache *block_group, *tmp;
+   struct list_head *deleted_bgs;
struct extent_io_tree *unpin;
u64 start;
u64 end;
int ret;
 
-   if (trans-aborted)
-   return 0;
-
if (fs_info-pinned_extents == fs_info-freed_extents[0])
unpin = fs_info-freed_extents[1];
else
unpin = fs_info-freed_extents[0];
 
-   while (1) {
+   while (!trans-aborted) {
mutex_lock(fs_info-unused_bg_unpin_mutex);
ret = find_first_extent_bit(unpin, 0, start, end,
EXTENT_DIRTY, NULL);
@@ -6066,6 +6065,34 @@ int btrfs_finish_extent_commit(struct btrfs_trans_handle 
*trans,
cond_resched();
}
 
+   /*
+* Transaction is finished.  We don't need the lock anymore.  We
+* do need to clean up the block groups in case of a transaction
+* abort.
+*/
+   deleted_bgs = trans-transaction-deleted_bgs;
+   list_for_each_entry_safe(block_group, tmp, deleted_bgs, bg_list) {
+   u64 trimmed = 0;
+
+   ret = -EROFS;
+   if (!trans-aborted)
+   ret = btrfs_discard_extent(root,
+  block_group-key.objectid,
+  block_group-key.offset,
+  trimmed);
+
+   list_del_init(block_group-bg_list);
+   btrfs_put_block_group_trimming(block_group);
+   btrfs_put_block_group(block_group);
+
+   if (ret) {
+   const char *errstr = btrfs_decode_error(ret);
+   btrfs_warn(fs_info,
+  Discard failed while removing blockgroup: 
errno=%d %s\n,
+  ret, errstr);
+   }
+   }
+
return 0;
 }
 
@@ -9845,6 +9872,11 @@ int 

[PATCH v3] btrfs: fix automatic blockgroup remove + discard

2015-06-03 Thread jeffm
The automatic block group removal patch introduced some regressions
in how discards are handled.

1/ FITRIM only iterates over block groups on disk - removed block groups
   won't be trimmed.
2/ Clearing the dirty bit from extents in removed block groups means that
   those extents won't be discarded when the block group is removed.
3/ More of a UI wart: We don't wait on block groups to be removed during
   read-only remount or fs umount. This results in block groups that
   /should/ have been discarded on thin provisioned storage hanging around
   until the file system is mounted read-write again.

The following patches address these problems by:
1/ Iterating over block groups on disk and then iterating over free space.
   This is consistent with how other file systems handle FITRIM.
2/ Putting removed block groups on a list so that they are automatically
   discarded during btrfs_finish_extent_commit after transaction commit.
   Note: This may still leave undiscarded space on disk if the system
   crashes after transaction commit but before discard. The file system
   itself will be compeltely consistent, but the user will need to trim
   manually.
3/ Simple: We call btrfs_delete_unused_bgs explicitly during ro-remount
   and umount.

Changelog:
v1-v2
- -odiscard
 - Fix ordering to ensure that we dont' discard extents freed in an
uncommitted transaction.
- FITRIM
  - Don't start a transaction so the entire run is transactionless
  - The loop can be interrupted while waiting on the chunk mutex and
after the discard has completed.
  - The only lock held for the duration is the device_list_mutex.  The
chunk mutex is take per loop iteration so normal operations should
continue while we're running, even on large file systems.

v2-v3
- -odiscard
 - Factor out get/put block_group-trimming to ensure that cleanup always
   happens at the last reference drop.
 - Cleanup the free space cache on the last reference drop.
 - Use list_move instead of list_add in case of multiple adds.  We still
   issue a warning but we shouldn't fall over.
 - Explicitly delete unused block groups in close_ctree and ro-remount.
- FITRIM
 - Cleaned up pointer tricks that abused NULL-member.
 - Take the commit_root_sem across loop iteration to protect against
   transaction commit moving the commit root.

Please apply.

Thanks,

-Jeff

--
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/3] btrfs: explictly delete unused block groups in close_ctree and ro-remount

2015-06-03 Thread jeffm
From: Jeff Mahoney je...@suse.com

The cleaner thread may already be sleeping by the time we enter
close_ctree.  If that's the case, we'll skip removing any unused
block groups queued for removal, even during a normal umount.
They'll be cleaned up automatically at next mount, but users
expect a umount to be a clean synchronization point, especially
when used on thin-provisioned storage with -odiscard.  We also
explicitly remove unused block groups in the ro-remount path
for the same reason.

Signed-off-by: Jeff Mahoney je...@suse.com
---
 fs/btrfs/disk-io.c |  9 +
 fs/btrfs/super.c   | 11 +++
 2 files changed, 20 insertions(+)

diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c
index 2ef9a4b..2e47fef 100644
--- a/fs/btrfs/disk-io.c
+++ b/fs/btrfs/disk-io.c
@@ -3710,6 +3710,15 @@ void close_ctree(struct btrfs_root *root)
cancel_work_sync(fs_info-async_reclaim_work);
 
if (!(fs_info-sb-s_flags  MS_RDONLY)) {
+   /*
+* If the cleaner thread is stopped and there are
+* block groups queued for removal, the deletion will be
+* skipped when we quit the cleaner thread.
+*/
+   mutex_lock(root-fs_info-cleaner_mutex);
+   btrfs_delete_unused_bgs(root-fs_info);
+   mutex_unlock(root-fs_info-cleaner_mutex);
+
ret = btrfs_commit_super(root);
if (ret)
btrfs_err(fs_info, commit super ret %d, ret);
diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c
index 9e66f5e..2ccd8d4 100644
--- a/fs/btrfs/super.c
+++ b/fs/btrfs/super.c
@@ -1539,6 +1539,17 @@ static int btrfs_remount(struct super_block *sb, int 
*flags, char *data)
 
sb-s_flags |= MS_RDONLY;
 
+   /*
+* Setting MS_RDONLY will put the cleaner thread to
+* sleep at the next loop if it's already active.
+* If it's already asleep, we'll leave unused block
+* groups on disk until we're mounted read-write again
+* unless we clean them up here.
+*/
+   mutex_lock(root-fs_info-cleaner_mutex);
+   btrfs_delete_unused_bgs(fs_info);
+   mutex_unlock(root-fs_info-cleaner_mutex);
+
btrfs_dev_replace_suspend_for_unmount(fs_info);
btrfs_scrub_cancel(fs_info);
btrfs_pause_balance(fs_info);
-- 
1.8.4.5

--
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


[RFC] add a bi_error field

2015-06-03 Thread Christoph Hellwig
Bio error reporting has been a mess for a while, and the increasing
use of chained bios makes it worse.

This series attempts to add a proper error field to struct bio
to sort this out.  It's working fine for me, but MD and btrfs were
doing pretty nasty things with the BIO_UPTODATE flag, so I would
appreciate some detailed review there.

--
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: btrfs_defrag_file: Fix calculation of max_to_defrag.

2015-06-03 Thread Chandan Rajendra
On Wednesday 03 Jun 2015 12:41:02 David Sterba wrote:
 On Wed, Jun 03, 2015 at 02:59:54PM +0530, Chandan Rajendra wrote:
  max_to_defrag represents the number of pages to defrag rather than the
  last
  page of the file range to be defragged. Fix this.
 
 Please update the changelog and describe the buggy behaviour. From a
 brief look I think that the defrag batch will be much higher than
 desired. Elsewhere the defrag batch is 1024, the page indexes used here
 are always large numbers. I guess this could (partially) explain high
 load during defrag that people report.
 
 ACK for the fix, I'll stick a reviewed-by to v2.

Hello Dave,

Consider a file having 10 4k blocks (i.e. blocks in the range [0 - 9]). If the
defrag ioctl was invoked for the block range [3 - 6], then max_to_defrag
should actually have the value 4. Instead in the current code we end up
setting it to 6.

Now, this does not (yet) cause an issue since the first part of the while loop
condition in btrfs_defrag_file() (i.e. i = last_index) causes the control
to flow out of the while loop before any buggy behavior is actually caused. So
the patch just makes sure that max_to_defrag ends up having the right value
rather than fixing a bug. I did run the xfstests suite to make sure that no
new regressions were introduced by this patch.

-- 
chandan

--
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


btrfs refuses to mount rw, access yields ESTALE on ro mount

2015-06-03 Thread fuz
Hello!

I'm experiencing a problem with a btrfs partition on my system. It
refuses to mount rw, dmesg contains this message and a stack trace [0]
when I try:

BTRFS info (device sdb1): disk space caching is enabled

I can mount the fs as readonly but then I get a bunch of these errors on
file access:

[121618.400230] BTRFS info (device sdb1): no csum found for inode 3357352 start 0
[121618.400398] BTRFS info (device sdb1): no csum found for inode 3357352 start 
4096
[121618.400501] BTRFS info (device sdb1): no csum found for inode 3357352 start 
8192
[121618.400603] BTRFS info (device sdb1): no csum found for inode 3357352 start 
12288

Here are the results of btrfs checks with two different versions of the
btrfs(8) utility: [1] [2]. I was then advised to run btrfs check --repair
on the file system by users on the #btrfs IRC channel. The log of this
execution and an execution of btrfs check --readonly immediately after
that can be found here: [3] [4]. What's interesting is that the error
count did not went down to 0 and neiher was the problem alleviated.

Before all of this, I performed btrfs-zero-log as suggested in various
articles on the internet.

Meta data from the file system pulled with btrfs-image(8) is available
on request only due to privacy concerns.

Yours sincerely,
Robert Clausecker

[0]: http://fuz.su/~fuz/txt/btrfs.trace
[1]: http://fuz.su/~fuz/txt/btrfs.check
[2]: http://fuz.su/~fuz/txt/btrfs.check2
[3]: http://fuz.su/~fuz/txt/btrfs.check3
[4]: http://fuz.su/~fuz/txt/btrfs.check4

-- 
()  ascii ribbon campaign - for an 8-bit clean world 
/\  - against html email  - against proprietary attachments
--
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] xfstests: btrfs: 022: add a quota rescan -w to wait rescan finished.

2015-06-03 Thread Filipe David Manana
On Wed, Jun 3, 2015 at 8:10 AM, Dongsheng Yang
yangds.f...@cn.fujitsu.com wrote:
 When we enable quota, btrfs will rescan quota numbers. We need
 to wait the rescan finished before any more operations on btrfs
 qgroups. Otherwith, the new btrfs-progs would WARN out:

 WARNING: Rescan is running, qgroup data may be incorrect.

 It would make btrfs/022 failed.

 Signed-off-by: Dongsheng Yang yangds.f...@cn.fujitsu.com
Reviewed-by: Filipe Manana fdman...@suse.com

Thanks, it works and it makes sense.

 ---
  tests/btrfs/022 | 1 +
  1 file changed, 1 insertion(+)

 diff --git a/tests/btrfs/022 b/tests/btrfs/022
 index 5c1a82d..56d4f3d 100755
 --- a/tests/btrfs/022
 +++ b/tests/btrfs/022
 @@ -51,6 +51,7 @@ _basic_test()
  {
 _run_btrfs_util_prog subvolume create $SCRATCH_MNT/a
 _run_btrfs_util_prog quota enable $SCRATCH_MNT/a
 +   _run_btrfs_util_prog quota rescan -w $SCRATCH_MNT
 subvolid=$(_btrfs_get_subvolid $SCRATCH_MNT a)
 $BTRFS_UTIL_PROG qgroup show $units $SCRATCH_MNT | grep $subvolid  \
 $seqres.full 21
 --
 1.8.4.2




-- 
Filipe David Manana,

Reasonable men adapt themselves to the world.
 Unreasonable men adapt the world to themselves.
 That's why all progress depends on unreasonable men.
--
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 RESEND] Btrfs: incremental send, check if orphanized dir inode needs delayed rename

2015-06-03 Thread Filipe Manana
If a directory inode is orphanized, because some inode previously
processed has a new name that collides with the old name of the current
inode, we need to check if it needs its rename operation delayed too,
as its ancestor-descendent relationship with some other inode might
have been reversed between the parent and send snapshots and therefore
its rename operation needs to happen after that other inode is renamed.

For example, for the following reproducer where this is needed (provided
by Robbie Ko):

  $ mkfs.btrfs -f /dev/sdb
  $ mount /dev/sdb /mnt
  $ mkfs.btrfs -f /dev/sdc
  $ mount /dev/sdc /mnt2

  $ mkdir -p /mnt/data/n1/n2
  $ mkdir /mnt/data/n4
  $ mkdir -p /mnt/data/t6/t7
  $ mkdir /mnt/data/t5
  $ mkdir /mnt/data/t7
  $ mkdir /mnt/data/n4/t2
  $ mkdir /mnt/data/t4
  $ mkdir /mnt/data/t3
  $ mv /mnt/data/t7 /mnt/data/n4/t2
  $ mv /mnt/data/t4 /mnt/data/n4/t2/t7
  $ mv /mnt/data/t5 /mnt/data/n4/t2/t7/t4
  $ mv /mnt/data/t6 /mnt/data/n4/t2/t7/t4/t5
  $ mv /mnt/data/n1/n2 /mnt/data/n4/t2/t7/t4/t5/t6
  $ mv /mnt/data/n1 /mnt/data/n4/t2/t7/t4/t5/t6
  $ mv /mnt/data/n4/t2/t7/t4/t5/t6/t7 /mnt/data/n4/t2/t7/t4/t5/t6/n2
  $ mv /mnt/data/t3 /mnt/data/n4/t2/t7/t4/t5/t6/n2/t7

  $ btrfs subvolume snapshot -r /mnt /mnt/snap1

  $ mv /mnt/data/n4/t2/t7/t4/t5/t6/n1 /mnt/data/n4
  $ mv /mnt/data/n4/t2 /mnt/data/n4/n1
  $ mv /mnt/data/n4/n1/t2/t7/t4/t5/t6/n2 /mnt/data/n4/n1/t2
  $ mv /mnt/data/n4/n1/t2/n2/t7/t3 /mnt/data/n4/n1/t2
  $ mv /mnt/data/n4/n1/t2/t7/t4/t5/t6 /mnt/data/n4/n1/t2
  $ mv /mnt/data/n4/n1/t2/t7/t4 /mnt/data/n4/n1/t2/t6
  $ mv /mnt/data/n4/n1/t2/t7 /mnt/data/n4/n1/t2/t3
  $ mv /mnt/data/n4/n1/t2/n2/t7 /mnt/data/n4/n1/t2

  $ btrfs subvolume snapshot -r /mnt /mnt/snap2

  $ btrfs send /mnt/snap1 | btrfs receive /mnt2
  $ btrfs send -p /mnt/snap1 /mnt/snap2 | btrfs receive /mnt2
  ERROR: send ioctl failed with -12: Cannot allocate memory

Where the parent snapshot directory hierarchy is the following:

  .(ino 256)
  |-- data/(ino 257)
|-- n4/(ino 260)
 |-- t2/   (ino 265)
  |-- t7/  (ino 264)
   |-- t4/ (ino 266)
|-- t5/(ino 263)
 |-- t6/   (ino 261)
  |-- n1/  (ino 258)
  |-- n2/  (ino 259)
   |-- t7/ (ino 262)
|-- t3/(ino 267)

And the send snapshot's directory hierarchy is the following:

  .(ino 256)
  |-- data/(ino 257)
|-- n4/(ino 260)
 |-- n1/   (ino 258)
  |-- t2/  (ino 265)
   |-- n2/ (ino 259)
   |-- t3/ (ino 267)
   ||-- t7 (ino 264)
   |
   |-- t6/ (ino 261)
   ||-- t4/(ino 266)
   | |-- t5/   (ino 263)
   |
   |-- t7/ (ino 262)

While processing inode 262 we orphanize inode 264 and later attempt
to rename inode 264 to its new name/location, which resulted in building
an incorrect destination path string for the rename operation with the
value data/n4/t2/t7/t4/t5/t6/n2/t7/t3/t7. This rename operation must
have been done only after inode 267 is processed and renamed, as the
ancestor-descendent relationship between inodes 264 and 267 was reversed
between both snapshots, because otherwise it results in an infinite loop
when building the path string for inode 264 when we are processing an
inode with a number larger than 264. That loop is the following:

  start inode 264, send progress of 265 for example
  parent of 264 - 267
  parent of 267 - 262
  parent of 262 - 259
  parent of 259 - 261
  parent of 261 - 263
  parent of 263 - 266
  parent of 266 - 264
|-- back to first iteration while current path string length
 is = PATH_MAX, and fail with -ENOMEM otherwise

So fix this by making the check if we need to delay a directory rename
regardless of the current inode having been orphanized or not.

A test case for fstests follows soon.

Thanks to Robbie Ko for providing a reproducer for this problem.

Reported-by: Robbie Ko robbi...@synology.com
Signed-off-by: Filipe Manana 

[GIT PULL] Send fixes for 4.2

2015-06-03 Thread Filipe Manana
Hi Chris,

Please pull 2 fixes for the send feature from my branch send_fixes_4.2.
Both have been around in the mailing list/patchwork before the 4.1 merge
window opened but were not picked for 4.1. They both have tests merged
in xfstests (btrfs/087 and btrfs/092), which as expected, fail without
this fixes applied and pass with them applied.

The following changes since commit c65b99f046843d2455aa231747b5a07a999a9f3d:

  Linux 4.1-rc6 (2015-05-31 19:01:07 -0700)

are available in the git repository at:

  git://git.kernel.org/pub/scm/linux/kernel/git/fdmanana/linux.git 
send_fixes_4.2

for you to fetch changes up to 8b191a684968e24b34c9894024b37532c68e6ae8:

  Btrfs: incremental send, check if orphanized dir inode needs delayed rename 
(2015-06-03 03:10:40 +0100)


Filipe Manana (2):
  Btrfs: incremental send, don't delay directory renames unnecessarily
  Btrfs: incremental send, check if orphanized dir inode needs delayed 
rename

 fs/btrfs/send.c | 104 
+++-
 1 file changed, 83 insertions(+), 21 deletions(-)

-- 
2.1.3

--
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 RESEND] Btrfs: incremental send, don't delay directory renames unnecessarily

2015-06-03 Thread Filipe Manana
Even though we delay the rename of directories when they become
descendents of other directories that were also renamed in the send
root to prevent infinite path build loops, we were doing it in cases
where this was not needed and was actually harmful resulting in
infinite path build loops as we ended up with a circular dependency
of delayed directory renames.

Consider the following reproducer:

  $ mkfs.btrfs -f /dev/sdb
  $ mount /dev/sdb /mnt
  $ mkfs.btrfs -f /dev/sdc
  $ mount /dev/sdc /mnt2

  $ mkdir /mnt/data
  $ mkdir /mnt/data/n1
  $ mkdir /mnt/data/n1/n2
  $ mkdir /mnt/data/n4
  $ mkdir /mnt/data/n1/n2/p1
  $ mkdir /mnt/data/n1/n2/p1/p2
  $ mkdir /mnt/data/t6
  $ mkdir /mnt/data/t7
  $ mkdir -p /mnt/data/t5/t7
  $ mkdir /mnt/data/t2
  $ mkdir /mnt/data/t4
  $ mkdir -p /mnt/data/t1/t3
  $ mkdir /mnt/data/p1
  $ mv /mnt/data/t1 /mnt/data/p1
  $ mkdir -p /mnt/data/p1/p2
  $ mv /mnt/data/t4 /mnt/data/p1/p2/t1
  $ mv /mnt/data/t5 /mnt/data/n4/t5
  $ mv /mnt/data/n1/n2/p1/p2 /mnt/data/n4/t5/p2
  $ mv /mnt/data/t7 /mnt/data/n4/t5/p2/t7
  $ mv /mnt/data/t2 /mnt/data/n4/t1
  $ mv /mnt/data/p1 /mnt/data/n4/t5/p2/p1
  $ mv /mnt/data/n1/n2 /mnt/data/n4/t5/p2/p1/p2/n2
  $ mv /mnt/data/n4/t5/p2/p1/p2/t1 /mnt/data/n4/t5/p2/p1/p2/n2/t1
  $ mv /mnt/data/n4/t5/t7 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t7
  $ mv /mnt/data/n4/t5/p2/p1/t1/t3 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t3
  $ mv /mnt/data/n4/t5/p2/p1/p2/n2/p1 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t7/p1
  $ mv /mnt/data/t6 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t3/t5
  $ mv /mnt/data/n4/t5/p2/p1/t1 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t3/t1
  $ mv /mnt/data/n1 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t7/p1/n1

  $ btrfs subvolume snapshot -r /mnt /mnt/snap1

  $ mv /mnt/data/n4/t1 /mnt/data/n4/t5/p2/p1/p2/n2/t1/t7/p1/t1
  $ mv /mnt/data/n4/t5/p2/p1/p2/n2/t1 /mnt/data/n4/
  $ mv /mnt/data/n4/t5/p2/p1/p2/n2 /mnt/data/n4/t1/n2
  $ mv /mnt/data/n4/t1/t7/p1 /mnt/data/n4/t1/n2/p1
  $ mv /mnt/data/n4/t1/t3/t1 /mnt/data/n4/t1/n2/t1
  $ mv /mnt/data/n4/t1/t3 /mnt/data/n4/t1/n2/t1/t3
  $ mv /mnt/data/n4/t5/p2/p1/p2 /mnt/data/n4/t1/n2/p1/p2
  $ mv /mnt/data/n4/t1/t7 /mnt/data/n4/t1/n2/p1/t7
  $ mv /mnt/data/n4/t5/p2/p1 /mnt/data/n4/t1/n2/p1/p2/p1
  $ mv /mnt/data/n4/t1/n2/t1/t3/t5 /mnt/data/n4/t1/n2/p1/p2/t5
  $ mv /mnt/data/n4/t5 /mnt/data/n4/t1/n2/p1/p2/p1/t5
  $ mv /mnt/data/n4/t1/n2/p1/p2/p1/t5/p2 /mnt/data/n4/t1/n2/p1/p2/p1/p2
  $ mv /mnt/data/n4/t1/n2/p1/p2/p1/p2/t7 /mnt/data/n4/t1/t7

  $ btrfs subvolume snapshot -r /mnt /mnt/snap2

  $ btrfs send /mnt/snap1 | btrfs receive /mnt2
  $ btrfs send -p /mnt/snap1 /mnt/snap2 | btrfs receive -vv /mnt2
  ERROR: send ioctl failed with -12: Cannot allocate memory

This reproducer resulted in an infinite path build loop when building the
path for inode 266 because the following circular dependency of delayed
directory renames was created:

   ino 272 - ino 261 - ino 259 - ino 268 - ino 267 - ino 261

Where the notation X - Y means the rename of inode X is delayed by the
rename of inode Y (X will be renamed after Y is renamed). This resulted
in an infinite path build loop of inode 266 because that inode has inode
261 as an ancestor in the send root and inode 261 is in the circular
dependency of delayed renames listed above.

Fix this by not delaying the rename of a directory inode if an ancestor of
the inode in the send root, which has a delayed rename operation, is not
also a descendent of the inode in the parent root.

Thanks to Robbie Ko for sending the reproducer example.
A test case for xfstests follows soon.

Reported-by: Robbie Ko robbi...@synology.com
Signed-off-by: Filipe Manana fdman...@suse.com
---
 fs/btrfs/send.c | 48 ++--
 1 file changed, 46 insertions(+), 2 deletions(-)

diff --git a/fs/btrfs/send.c b/fs/btrfs/send.c
index a1216f9..2ed36af 100644
--- a/fs/btrfs/send.c
+++ b/fs/btrfs/send.c
@@ -3353,6 +3353,37 @@ out:
return ret;
 }
 
+/*
+ * Check if ino ino1 is an ancestor of inode ino2 in the given root.
+ * Return 1 if true, 0 if false and  0 on error.
+ */
+static int is_ancestor(struct btrfs_root *root,
+  const u64 ino1,
+  const u64 ino1_gen,
+  const u64 ino2,
+  struct fs_path *fs_path)
+{
+   u64 ino = ino2;
+
+   while (ino  BTRFS_FIRST_FREE_OBJECTID) {
+   int ret;
+   u64 parent;
+   u64 parent_gen;
+
+   fs_path_reset(fs_path);
+   ret = get_first_ref(root, ino, parent, parent_gen, fs_path);
+   if (ret  0) {
+   if (ret == -ENOENT  ino == ino2)
+   ret = 0;
+   return ret;
+   }
+   if (parent == ino1)
+   return parent_gen == ino1_gen ? 1 : 0;
+   ino = parent;
+   }
+   return 0;
+}
+
 static int wait_for_parent_move(struct send_ctx *sctx,
struct recorded_ref 

(no subject)

2015-06-03 Thread Irena A.

Hello

My name is Irena .A, I am sending this brief letter to solicit your 
partnership to transfer €22,500,000.00 Euros,if interested kindly write 
back for more information.


irenageorgia...@qq.com

Irena .A.
--
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] btrfs: test premature submount unmounting when deleting default subvolume

2015-06-03 Thread Eryu Guan
On Tue, Jun 02, 2015 at 10:05:30PM -0700, Omar Sandoval wrote:
 Add a regression test for a problem where attempting to delete the
 default subvolume would fail (as expected), but not until after all
 submounts under the subvolume were unmounted.
 
 Signed-off-by: Omar Sandoval osan...@osandov.com
 ---
 v1-v2:
 - Simpler test: just depends on umount of the bind mount succeeding
   instead of running find. Without the patch applied, the bind mount
   will disappear so umount will fail.
 - Fix Eryu's comments (better subject, copyright, use
   _btrfs_get_subvolid)
 
  tests/btrfs/089 | 81 
 +
  tests/btrfs/089.out |  2 ++
  tests/btrfs/group   |  1 +
  3 files changed, 84 insertions(+)
  create mode 100755 tests/btrfs/089
  create mode 100644 tests/btrfs/089.out
 
 diff --git a/tests/btrfs/089 b/tests/btrfs/089
 new file mode 100755
 index ..c81df2a3b225
 --- /dev/null
 +++ b/tests/btrfs/089
 @@ -0,0 +1,81 @@
 +#! /bin/bash
 +# FS QA Test 089
 +#
 +# Test deleting the default subvolume, making sure that it fails and that

Here says to make sure the deletion of default subvol fails, but...

 +# submounts under it are not unmounted prematurely. This is a regression test
 +# for Linux commit Btrfs: don't invalidate root dentry when subvolume 
 deletion
 +# fails.
 +#
 +#---
 +# Copyright (c) 2015 Omar Sandoval.  All Rights Reserved.
 +#
 +# This program is free software; you can redistribute it and/or
 +# modify it under the terms of the GNU General Public License as
 +# published by the Free Software Foundation.
 +#
 +# This program is distributed in the hope that it would be useful,
 +# but WITHOUT ANY WARRANTY; without even the implied warranty of
 +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 +# GNU General Public License for more details.
 +#
 +# You should have received a copy of the GNU General Public License
 +# along with this program; if not, write the Free Software Foundation,
 +# Inc.,  51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 +#---
 +#
 +
 +seq=`basename $0`
 +seqres=$RESULT_DIR/$seq
 +echo QA output created by $seq
 +
 +here=`pwd`
 +tmp=/tmp/$$
 +status=1 # failure is the default!
 +trap _cleanup; exit \$status 0 1 2 3 15
 +
 +_cleanup()
 +{
 + cd /
 + rm -f $tmp.*
 +}
 +
 +# get standard environment, filters and checks
 +. ./common/rc
 +. ./common/filter
 +. ./common/filter.btrfs
 +
 +# real QA test starts here
 +
 +# Modify as appropriate.
 +_need_to_be_root
 +_supported_fs btrfs
 +_supported_os Linux
 +_require_scratch
 +
 +rm -f $seqres.full
 +
 +_scratch_mkfs $seqres.full 21
 +_scratch_mount
 +
 +# Create a new subvolume and make it the default subvolume.
 +$BTRFS_UTIL_PROG subvolume create $SCRATCH_MNT/testvol  $seqres.full 
 21 \
 + || _fail couldn't create subvol
 +testvol_id=$(_btrfs_get_subvolid $SCRATCH_MNT testvol)
 +$BTRFS_UTIL_PROG subvolume set-default $testvol_id $SCRATCH_MNT  
 $seqres.full 21 \
 + || _fail couldn't set default
 +
 +# Bind-mount a directory under the default subvolume.
 +mkdir $SCRATCH_MNT/testvol/testdir
 +touch $SCRATCH_MNT/testvol/testdir/testfile
 +mkdir $SCRATCH_MNT/testvol/mnt
 +mount --bind $SCRATCH_MNT/testvol/testdir $SCRATCH_MNT/testvol/mnt
 +
 +# Now attempt to delete the default subvolume, which should fail.
 +$BTRFS_UTIL_PROG subvolume delete $SCRATCH_MNT/testvol  $seqres.full 21

the result of deletion of default subvol is not checked and ignored
here. The description should match the test.

Otherwise looks good to me.

Reviewed-by: Eryu Guan eg...@redhat.com

Thanks,
Eryu
 +
 +# Unmount the bind mount, which should still be alive.
 +$UMOUNT_PROG $SCRATCH_MNT/testvol/mnt
 +
 +echo Silence is golden
 +status=0
 +exit
 diff --git a/tests/btrfs/089.out b/tests/btrfs/089.out
 new file mode 100644
 index ..a7fcdee9b767
 --- /dev/null
 +++ b/tests/btrfs/089.out
 @@ -0,0 +1,2 @@
 +QA output created by 089
 +Silence is golden
 diff --git a/tests/btrfs/group b/tests/btrfs/group
 index ffe18bff0d21..616d060758c1 100644
 --- a/tests/btrfs/group
 +++ b/tests/btrfs/group
 @@ -91,6 +91,7 @@
  086 auto quick clone
  087 auto quick send
  088 auto quick metadata
 +089 auto quick subvol
  090 auto quick metadata
  091 auto quick qgroup
  092 auto quick send
 -- 
 2.4.2
 
 --
 To unsubscribe from this list: send the line unsubscribe fstests 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


[PATCH] btrfs: tweak key advancing condition

2015-06-03 Thread Naohiro Aota
The key advancing condition used in copy_to_sk() is loose. It can
advance the key even if it reaches sk-max_*: e.g. when the max key = (512,
1024, -1) and the current key = (512, 1025, 10), it increments the
offset by 1, continues hopeless search from (512, 1025, 11). This issue
make ioctl() to take a lot of time scanning all the leaf a blocks one by
one.

This commit fix the problem using standard way of key comparison:
btrfs_comp_cpu_keys()

Signed-off-by: Naohiro Aota na...@elisp.net
---
 fs/btrfs/ioctl.c | 12 +---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c
index 1c22c65..07dc01d 100644
--- a/fs/btrfs/ioctl.c
+++ b/fs/btrfs/ioctl.c
@@ -1932,6 +1932,7 @@ static noinline int copy_to_sk(struct btrfs_root *root,
u64 found_transid;
struct extent_buffer *leaf;
struct btrfs_ioctl_search_header sh;
+   struct btrfs_key test;
unsigned long item_off;
unsigned long item_len;
int nritems;
@@ -2015,12 +2016,17 @@ static noinline int copy_to_sk(struct btrfs_root *root,
}
 advance_key:
ret = 0;
-   if (key-offset  (u64)-1  key-offset  sk-max_offset)
+   test.objectid = sk-max_objectid;
+   test.type = sk-max_type;
+   test.offset = sk-max_offset;
+   if (btrfs_comp_cpu_keys(key, test) = 0)
+   ret = 1;
+   else if (key-offset  (u64)-1)
key-offset++;
-   else if (key-type  (u8)-1  key-type  sk-max_type) {
+   else if (key-type  (u8)-1) {
key-offset = 0;
key-type++;
-   } else if (key-objectid  (u64)-1  key-objectid  sk-max_objectid) 
{
+   } else if (key-objectid  (u64)-1) {
key-offset = 0;
key-type = 0;
key-objectid++;
-- 
2.4.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: [PATCH 1/2] btrfs-progs: avoid duplicate checks on user provided devid

2015-06-03 Thread Anand Jain


David,

 Kindly do not integrated this patch as of now.
 As I have just found that, the error reporting when
 the default background option is used is not completely
 transparent. I need to fix this before this patch.

Thanks, Anand


On 06/03/2015 03:49 PM, Anand Jain wrote:


On 06/02/2015 11:12 PM, David Sterba wrote:

On Mon, Jun 01, 2015 at 02:25:17PM +0800, Anand Jain wrote:

kernel is already checking it (rightly), we don't need to check that
in the user land.


Sometimes it's useful to duplicate the checks in userspace because we
can fail early and return the error message directly, compared to
messages in syslog or a simple errno.


  right. But here what do you feel about the gain obtained vs additional
  code thats required ?

  My take: get_fs_info() calls check_mounted_where() which in turn calls
  btrfs_scan_lblkid(), which is system wide scan of all block devices,
  thats heavy weight.

  My past tests showed visible delay/jitter in the output of
  'btrfs fi show -d' when btrfs scrub is running. The main culprit
  is check_mounted_where calling btrfs_scan_lblkid. so its recommend
  to run get_fs_info() only if required.


Have you observed that the userspace checks were problematic?


  Nope. Just a cleanup. With this patch cmd_start_replace() would
  should match with cmd_rm_dev().
  As both 'btrfs dev del devid ..' and 'btrfs replace start devid ..
  intentions are same, so theoretically up to certain extent their codes
  should match.


@@ -214,33 +213,7 @@ static int cmd_start_replace(int argc, char **argv)
  }

  if (is_numerical(srcdev)) {
-struct btrfs_ioctl_fs_info_args fi_args;
-struct btrfs_ioctl_dev_info_args *di_args = NULL;
-
  start_args.start.srcdevid = arg_strtou64(srcdev);
-
-ret = get_fs_info(path, fi_args, di_args);


This does additional checks, like checking where it's mounted.


  in this part of the if statement srcdev is num and is devid.
  get_fs_info check does not help.

  What did I miss ?

Thanks Anand


--
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: [GIT PULL] Send fixes for 4.2

2015-06-03 Thread Chris Mason
On 06/02/2015 11:15 PM, Filipe Manana wrote:
 Hi Chris,
 
 Please pull 2 fixes for the send feature from my branch send_fixes_4.2.
 Both have been around in the mailing list/patchwork before the 4.1 merge
 window opened but were not picked for 4.1. They both have tests merged
 in xfstests (btrfs/087 and btrfs/092), which as expected, fail without
 this fixes applied and pass with them applied.
 

Thanks, pulled.

-chris

--
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