On Fri, Jan 15, 2010 at 3:00 AM, Josef Bacik <josef@xxxxxxxxxx> wrote:
> On Thu, Jan 14, 2010 at 12:03:23PM -0500, Josef Bacik wrote:
>> On Wed, Jan 13, 2010 at 09:11:59PM +0100, Tomas Carnecky wrote:
>> > On 1/13/10 9:13 PM, Josef Bacik wrote:
>> >> On Wed, Jan 13, 2010 at 08:09:17PM +0100, Tomas Carnecky wrote:
>> >>> I was running v2.6.33-rc2-187-g08d869a and everything was ok. Today I
>> >>> decided to update the kernel (to v2.6.33-rc4) and a minute or two after
>> >>> logging into the gnome desktop this kernel bug appeared in dmesg. I then
>> >>> went back to the old kernel but the bug didn't disappear, not even after
>> >>> running btrfsck on the filesystem.
>> >>>
>> >> Ok will you please run with this patch? It shouldn't panic your box, since it
>> >> seems ret is -EEXIST. Just watch your logs for
>> >>
>> >> OH NO, ORPHAN ENTRY ALREADY EXISTS FOR<number>
>> >>
>> >> and then look up and find all occurances of
>> >>
>> >> Btrfs: orphan add<number>
>> >>
>> >> with the stack trace and send it back to me so I can verify that nothing heinous
>> >> is happening. I assume we're just racing with unlink/rename so all that needs
>> >> to be done is to take that BUG_ON out, but it would be nice to know for sure.
>> >
>>
>> Ok will you try this patch? I've not built it, so sorry if it doesn't compile
>> :). Look for the "OH NO" messages again. If they show up then the problem is
>> still there, if they go away the problem is fixed. I tried to reproduce this
>> locally but I can't seem to do it, so you are my only hope :).
>>
>> By the way, this replaces the last patch I sent you, so unapply the previous
>> patch and apply this one instead. Thanks,
>>
>
> Ok here's the final version of the patch I'm going to post. This replaces the
> other patches that I sent you, so un-apply the last one you applied and apply
> this one instead. Run this for a day and let me know if you have any problems.
> If no problems I'll go ahead and post it. Thanks,
>
> Josef
>
>
> diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c
> index 5440bab..24cbf6b 100644
> --- a/fs/btrfs/inode.c
> +++ b/fs/btrfs/inode.c
> @@ -3305,24 +3305,7 @@ static int btrfs_setattr_size(struct inode *inode, struct iattr *attr)
> send_sig(SIGXFSZ, current, 0);
> return -EFBIG;
> }
> - }
> -
> - ret = btrfs_reserve_metadata_space(root, 1);
> - if (ret)
> - return ret;
> -
> - trans = btrfs_start_transaction(root, 1);
> - btrfs_set_trans_block_group(trans, inode);
> -
> - ret = btrfs_orphan_add(trans, inode);
> - BUG_ON(ret);
> -
> - nr = trans->blocks_used;
> - btrfs_end_transaction(trans, root);
> - btrfs_unreserve_metadata_space(root, 1);
> - btrfs_btree_balance_dirty(root, nr);
>
> - if (attr->ia_size > inode->i_size) {
> ret = btrfs_cont_expand(inode, attr->ia_size);
> if (ret) {
> btrfs_truncate(inode);
> @@ -3337,14 +3320,26 @@ static int btrfs_setattr_size(struct inode *inode, struct iattr *attr)
>
> ret = btrfs_update_inode(trans, root, inode);
> BUG_ON(ret);
> - if (inode->i_nlink > 0) {
> - ret = btrfs_orphan_del(trans, inode);
> - BUG_ON(ret);
> - }
> +
> nr = trans->blocks_used;
> btrfs_end_transaction(trans, root);
> btrfs_btree_balance_dirty(root, nr);
> return 0;
> + } else if (attr->ia_size < i_size_read(inode)) {
> + ret = btrfs_reserve_metadata_space(root, 1);
> + if (ret)
> + return ret;
> +
> + trans = btrfs_start_transaction(root, 1);
> + btrfs_set_trans_block_group(trans, inode);
> +
> + ret = btrfs_orphan_add(trans, inode);
> + BUG_ON(ret);
> +
> + nr = trans->blocks_used;
> + btrfs_end_transaction(trans, root);
> + btrfs_unreserve_metadata_space(root, 1);
> + btrfs_btree_balance_dirty(root, nr);
> }
>
> /*
> @@ -3355,10 +3350,6 @@ static int btrfs_setattr_size(struct inode *inode, struct iattr *attr)
> if (attr->ia_size == 0)
> BTRFS_I(inode)->ordered_data_close = 1;
>
> - /* we don't support swapfiles, so vmtruncate shouldn't fail */
> - ret = vmtruncate(inode, attr->ia_size);
> - BUG_ON(ret);
> -
> return 0;
> }
>
> @@ -3376,7 +3367,6 @@ static int btrfs_setattr(struct dentry *dentry, struct iattr *attr)
> if (err)
> return err;
> }
> - attr->ia_valid &= ~ATTR_SIZE;
>
> if (attr->ia_valid)
> err = inode_setattr(inode, attr);
> --
It looks like a ENOSPC related problem, btrfs_truncate doesn't remove the orphan
item if it fails to finish its operation. so I don't think this patch
fixes the problem
Regards
Yan, Zheng
--
To unsubscribe from this list: send the line "unsubscribe linux-btrfs" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html