* Xfs fails in xfstests 013 @ 2013-01-31 8:19 Lukáš Czerner 2013-01-31 19:08 ` Ben Myers 2013-02-01 0:29 ` Dave Chinner 0 siblings, 2 replies; 8+ messages in thread From: Lukáš Czerner @ 2013-01-31 8:19 UTC (permalink / raw) To: xfs Hi. I've just run xfstest 013 on xfs and it fails with this backtrace Jan 31 03:09:07 rhel6_vm1 kernel: ffff88020b6d1000: 78 78 78 78 78 78 78 78 78 78 2f 78 78 78 78 78 xxxxxxxxxx/xxxxx Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa025486e Jan 31 03:09:07 rhel6_vm1 kernel: Jan 31 03:09:07 rhel6_vm1 kernel: Pid: 8909, comm: xfsaild/sda Tainted: GF 3.8.0-rc5-orig+ #8 Jan 31 03:09:07 rhel6_vm1 kernel: Call Trace: Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa022877f>] xfs_error_report+0x3f/0x50 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa025486e>] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02287ee>] xfs_corruption_error+0x5e/0x90 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0254710>] xfs_bmbt_verify+0x80/0x1d0 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa025486e>] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa025486e>] xfs_bmbt_write_verify+0xe/0x10 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02269a5>] _xfs_buf_ioapply+0x65/0x150 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff8108d170>] ? try_to_wake_up+0x2b0/0x2b0 Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02270a5>] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0226fef>] xfs_buf_iorequest+0x4f/0xa0 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02270a5>] xfs_bdstrat_cb+0x65/0xd0 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0227218>] __xfs_buf_delwri_submit+0x108/0x200 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02273c0>] ? xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02273c0>] xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0282376>] xfsaild_push+0x1b6/0x520 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0282778>] xfsaild+0x98/0x130 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02826e0>] ? xfsaild_push+0x520/0x520 [xfs] Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff8107968e>] kthread+0xce/0xe0 Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff810795c0>] ? kthread_freezable_should_stop+0x70/0x70 Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff8155cdec>] ret_from_fork+0x7c/0xb0 Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff810795c0>] ? kthread_freezable_should_stop+0x70/0x70 Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Corruption detected. Unmount and run xfs_repair Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): xfs_do_force_shutdown(0x8) called from line 1358 of file fs/xfs/xfs_buf.c. Return address = 0xffffffffa0226a85 Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Corruption of in-memory data detected. Shutting down filesystem Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Please umount the filesystem and rectify the problem(s) Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): xfs_log_force: error 5 returned. I can reproduce it every time with xfstest 013 on 3.8.0-rc5. -Lukas _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-01-31 8:19 Xfs fails in xfstests 013 Lukáš Czerner @ 2013-01-31 19:08 ` Ben Myers 2013-02-01 0:29 ` Dave Chinner 1 sibling, 0 replies; 8+ messages in thread From: Ben Myers @ 2013-01-31 19:08 UTC (permalink / raw) To: Lukáš Czerner; +Cc: xfs Hey Lukas, On Thu, Jan 31, 2013 at 09:19:23AM +0100, Lukáš Czerner wrote: > I've just run xfstest 013 on xfs and it fails with this backtrace > > > Jan 31 03:09:07 rhel6_vm1 kernel: ffff88020b6d1000: 78 78 78 78 78 78 78 78 78 78 2f 78 78 78 78 78 xxxxxxxxxx/xxxxx > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa025486e > Jan 31 03:09:07 rhel6_vm1 kernel: > Jan 31 03:09:07 rhel6_vm1 kernel: Pid: 8909, comm: xfsaild/sda Tainted: GF 3.8.0-rc5-orig+ #8 > Jan 31 03:09:07 rhel6_vm1 kernel: Call Trace: > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa022877f>] xfs_error_report+0x3f/0x50 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa025486e>] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02287ee>] xfs_corruption_error+0x5e/0x90 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0254710>] xfs_bmbt_verify+0x80/0x1d0 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa025486e>] ? xfs_bmbt_write_verify+0xe/0x10 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa025486e>] xfs_bmbt_write_verify+0xe/0x10 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02269a5>] _xfs_buf_ioapply+0x65/0x150 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff8108d170>] ? try_to_wake_up+0x2b0/0x2b0 > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02270a5>] ? xfs_bdstrat_cb+0x65/0xd0 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0226fef>] xfs_buf_iorequest+0x4f/0xa0 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02270a5>] xfs_bdstrat_cb+0x65/0xd0 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0227218>] __xfs_buf_delwri_submit+0x108/0x200 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02273c0>] ? xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02273c0>] xfs_buf_delwri_submit_nowait+0x20/0x30 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0282376>] xfsaild_push+0x1b6/0x520 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa0282778>] xfsaild+0x98/0x130 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffffa02826e0>] ? xfsaild_push+0x520/0x520 [xfs] > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff8107968e>] kthread+0xce/0xe0 > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff810795c0>] ? kthread_freezable_should_stop+0x70/0x70 > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff8155cdec>] ret_from_fork+0x7c/0xb0 > Jan 31 03:09:07 rhel6_vm1 kernel: [<ffffffff810795c0>] ? kthread_freezable_should_stop+0x70/0x70 > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Corruption detected. Unmount and run xfs_repair > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): xfs_do_force_shutdown(0x8) called from line 1358 of file fs/xfs/xfs_buf.c. Return address = 0xffffffffa0226a85 > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Corruption of in-memory data detected. Shutting down filesystem > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Please umount the filesystem and rectify the problem(s) > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): xfs_log_force: error 5 returned. > > > I can reproduce it every time with xfstest 013 on 3.8.0-rc5. I haven't been able to reproduce this with test 013. Could you grab a metadump? Thanks, Ben _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-01-31 8:19 Xfs fails in xfstests 013 Lukáš Czerner 2013-01-31 19:08 ` Ben Myers @ 2013-02-01 0:29 ` Dave Chinner 2013-02-01 10:58 ` Lukáš Czerner 1 sibling, 1 reply; 8+ messages in thread From: Dave Chinner @ 2013-02-01 0:29 UTC (permalink / raw) To: Lukáš Czerner; +Cc: xfs On Thu, Jan 31, 2013 at 09:19:23AM +0100, Lukáš Czerner wrote: > Hi. > > I've just run xfstest 013 on xfs and it fails with this backtrace > > > Jan 31 03:09:07 rhel6_vm1 kernel: ffff88020b6d1000: 78 78 78 78 78 78 78 78 78 78 2f 78 78 78 78 78 xxxxxxxxxx/xxxxx > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa025486e Same problem Cai Qian just reported - a remote symlink with a bmbt verifier attached to it. > I can reproduce it every time with xfstest 013 on 3.8.0-rc5. And the configuration you are testing? I'd suggest that you add an: ASSERT(bp->b_ops == NULL); into xfs_symlink() after the xfs_trans_get_buf() call in the remote symlink crate loop, because the problem occurring implies that the code is getting a new buffer with a stale ops structure on it (though I can't see how that is possible right now). You should probably put the same assert into xfs_inactive_symlink_rmt() between the get buf and the xfs_trans_binval() call, and into xfs_readlink_bmap() after the contents of a symlink are read from disk. Cheers, Dave. -- Dave Chinner david@fromorbit.com _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-02-01 0:29 ` Dave Chinner @ 2013-02-01 10:58 ` Lukáš Czerner 2013-02-01 14:33 ` Lukáš Czerner 0 siblings, 1 reply; 8+ messages in thread From: Lukáš Czerner @ 2013-02-01 10:58 UTC (permalink / raw) To: Dave Chinner; +Cc: Lukáš Czerner, xfs [-- Attachment #1: Type: TEXT/PLAIN, Size: 1832 bytes --] On Fri, 1 Feb 2013, Dave Chinner wrote: > Date: Fri, 1 Feb 2013 11:29:27 +1100 > From: Dave Chinner <david@fromorbit.com> > To: Lukáš Czerner <lczerner@redhat.com> > Cc: xfs@oss.sgi.com > Subject: Re: Xfs fails in xfstests 013 > > On Thu, Jan 31, 2013 at 09:19:23AM +0100, Lukáš Czerner wrote: > > Hi. > > > > I've just run xfstest 013 on xfs and it fails with this backtrace > > > > > > Jan 31 03:09:07 rhel6_vm1 kernel: ffff88020b6d1000: 78 78 78 78 78 78 78 78 78 78 2f 78 78 78 78 78 xxxxxxxxxx/xxxxx > > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa025486e > > Same problem Cai Qian just reported - a remote symlink with a bmbt > verifier attached to it. > > > I can reproduce it every time with xfstest 013 on 3.8.0-rc5. > > And the configuration you are testing? The system is x86_64 KVM guest and I am using the following config export TEST_DEV=/dev/sda export TEST_DIR=/mnt/test export SCRATCH_DEV=/dev/sdb export SCRATCH_MNT=/mnt/test1 export MKFS_OPTIONS="-f " export FSTYP=xfs Where /dev/sda and /dev/sdb are 50GB in size and those are exported from the host linear logical volumes. > > I'd suggest that you add an: > > ASSERT(bp->b_ops == NULL); > > into xfs_symlink() after the xfs_trans_get_buf() call in the remote > symlink crate loop, because the problem occurring implies that the > code is getting a new buffer with a stale ops structure on it > (though I can't see how that is possible right now). > > You should probably put the same assert into > xfs_inactive_symlink_rmt() between the get buf and the > xfs_trans_binval() call, and into xfs_readlink_bmap() after the > contents of a symlink are read from disk. Ok, I'll try that and let you know. Thanks! -Lukas > > Cheers, > > Dave. > [-- Attachment #2: Type: text/plain, Size: 121 bytes --] _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-02-01 10:58 ` Lukáš Czerner @ 2013-02-01 14:33 ` Lukáš Czerner 2013-02-03 23:00 ` Dave Chinner 0 siblings, 1 reply; 8+ messages in thread From: Lukáš Czerner @ 2013-02-01 14:33 UTC (permalink / raw) To: Lukáš Czerner; +Cc: xfs [-- Attachment #1: Type: TEXT/PLAIN, Size: 3481 bytes --] On Fri, 1 Feb 2013, Lukáš Czerner wrote: > Date: Fri, 1 Feb 2013 11:58:04 +0100 (CET) > From: Lukáš Czerner <lczerner@redhat.com> > To: Dave Chinner <david@fromorbit.com> > Cc: Lukáš Czerner <lczerner@redhat.com>, xfs@oss.sgi.com > Subject: Re: Xfs fails in xfstests 013 > > On Fri, 1 Feb 2013, Dave Chinner wrote: > > > Date: Fri, 1 Feb 2013 11:29:27 +1100 > > From: Dave Chinner <david@fromorbit.com> > > To: Lukáš Czerner <lczerner@redhat.com> > > Cc: xfs@oss.sgi.com > > Subject: Re: Xfs fails in xfstests 013 > > > > On Thu, Jan 31, 2013 at 09:19:23AM +0100, Lukáš Czerner wrote: > > > Hi. > > > > > > I've just run xfstest 013 on xfs and it fails with this backtrace > > > > > > > > > Jan 31 03:09:07 rhel6_vm1 kernel: ffff88020b6d1000: 78 78 78 78 78 78 78 78 78 78 2f 78 78 78 78 78 xxxxxxxxxx/xxxxx > > > Jan 31 03:09:07 rhel6_vm1 kernel: XFS (sda): Internal error xfs_bmbt_verify at line 747 of file fs/xfs/xfs_bmap_btree.c. Caller 0xffffffffa025486e > > > > Same problem Cai Qian just reported - a remote symlink with a bmbt > > verifier attached to it. > > > > > I can reproduce it every time with xfstest 013 on 3.8.0-rc5. > > > > And the configuration you are testing? > > The system is x86_64 KVM guest and I am using the following config > > export TEST_DEV=/dev/sda > export TEST_DIR=/mnt/test > export SCRATCH_DEV=/dev/sdb > export SCRATCH_MNT=/mnt/test1 > export MKFS_OPTIONS="-f " > export FSTYP=xfs > > Where /dev/sda and /dev/sdb are 50GB in size and those are exported > from the host linear logical volumes. > > > > > I'd suggest that you add an: > > > > ASSERT(bp->b_ops == NULL); > > > > into xfs_symlink() after the xfs_trans_get_buf() call in the remote > > symlink crate loop, because the problem occurring implies that the > > code is getting a new buffer with a stale ops structure on it > > (though I can't see how that is possible right now). > > > > You should probably put the same assert into > > xfs_inactive_symlink_rmt() between the get buf and the > > xfs_trans_binval() call, and into xfs_readlink_bmap() after the > > contents of a symlink are read from disk. > > Ok, I'll try that and let you know. This is what I've done: diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c index d95f565..22590ef 100644 --- a/fs/xfs/xfs_vnodeops.c +++ b/fs/xfs/xfs_vnodeops.c @@ -89,6 +89,7 @@ xfs_readlink_bmap( xfs_buf_relse(bp); goto out; } + ASSERT(bp->b_ops == NULL); if (pathlen < byte_cnt) byte_cnt = pathlen; pathlen -= byte_cnt; @@ -313,6 +314,7 @@ xfs_inactive_symlink_rmt( error = ENOMEM; goto error1; } + ASSERT(bp->b_ops == NULL); xfs_trans_binval(tp, bp); } /* @@ -1535,6 +1537,7 @@ xfs_symlink( error = ENOMEM; goto error2; } + ASSERT(bp->b_ops == NULL); if (pathlen < byte_cnt) { byte_cnt = pathlen; } and I have not hit the assert. However I think that I know what's going on. The verifier is obviously not attached when the symlink is created, however it is attached when security attributes are created for the symlink by xfs_init_security(). Thanks! -Lukas [-- Attachment #2: Type: text/plain, Size: 121 bytes --] _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply related [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-02-01 14:33 ` Lukáš Czerner @ 2013-02-03 23:00 ` Dave Chinner 2013-02-10 22:16 ` Dave Chinner 0 siblings, 1 reply; 8+ messages in thread From: Dave Chinner @ 2013-02-03 23:00 UTC (permalink / raw) To: Lukáš Czerner; +Cc: xfs On Fri, Feb 01, 2013 at 03:33:06PM +0100, Lukáš Czerner wrote: > On Fri, 1 Feb 2013, Lukáš Czerner wrote: > and I have not hit the assert. However I think that I know what's > going on. The verifier is obviously not attached when the symlink is > created, however it is attached when security attributes are created > for the symlink by xfs_init_security(). Which means the bug is in xfs_bmap_add_attrfork_local() in calling xfs_bmap_local_to_extents(). i.e it assumes that the local data is either directory data or extent data, and is attaching extent tree verifiers to the buffer that contains a remote symlink. Thinking time now needed, as this affects the symlink CRC changes as well. Thanks for the debug help, Lukas. Cheers, Dave. -- Dave Chinner david@fromorbit.com _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-02-03 23:00 ` Dave Chinner @ 2013-02-10 22:16 ` Dave Chinner 2013-02-11 12:08 ` Lukáš Czerner 0 siblings, 1 reply; 8+ messages in thread From: Dave Chinner @ 2013-02-10 22:16 UTC (permalink / raw) To: Lukáš Czerner; +Cc: xfs On Mon, Feb 04, 2013 at 10:00:13AM +1100, Dave Chinner wrote: > On Fri, Feb 01, 2013 at 03:33:06PM +0100, Lukáš Czerner wrote: > > On Fri, 1 Feb 2013, Lukáš Czerner wrote: > > and I have not hit the assert. However I think that I know what's > > going on. The verifier is obviously not attached when the symlink is > > created, however it is attached when security attributes are created > > for the symlink by xfs_init_security(). > > Which means the bug is in xfs_bmap_add_attrfork_local() in calling > xfs_bmap_local_to_extents(). i.e it assumes that the local data is > either directory data or extent data, and is attaching extent tree > verifiers to the buffer that contains a remote symlink. Thinking > time now needed, as this affects the symlink CRC changes as well. > > Thanks for the debug help, Lukas. Lukas, can you check whether the patch below fixes the problem you saw? Cheers, Dave. -- Dave Chinner david@fromorbit.com xfs: xfs_bmap_add_attrfork_local is too generic From: Dave Chinner <dchinner@redhat.com> When we are converting local data to an extent format as a result of adding an attribute, the type of data contained in the local fork determines the behaviour that needs to occur. xfs_bmap_add_attrfork_local() already handles the directory data case specially by using S_ISDIR() and calling out to xfs_dir2_sf_to_block(), but with verifiers we now need to handle each different type of metadata specially and different metadata formats require different verifiers (and eventually block header initialisation). There is only a single place that we add and attribute fork to the inode, but that is in the attribute code and it knows nothing about the specific contents of the data fork. It is only the case of local data that is the issue here, so adding code to hadnle this case in the attribute specific code is wrong. Hence we are really stuck trying to detect the data fork contents in xfs_bmap_add_attrfork_local() and performing the correct callout there. Luckily the current cases can be determined by S_IS* macros, and we can push the work off to data specific callouts, but each of those callouts does a lot of work in common with xfs_bmap_local_to_extents(). The only reason that this fails for symlinks right now is is that xfs_bmap_local_to_extents() assumes the data fork contains extent data, and so attaches a a bmap extent data verifier to the buffer and simply copies the data fork information straight into it. To fix this, allow us to pass a "formatting" callback into xfs_bmap_local_to_extents() which is responsible for setting the buffer type, initialising it and copying the data fork contents over to the new buffer. This allows callers to specify how they want to format the new buffer (which is necessary for the upcoming CRC enabled metadata blocks) and hence make xfs_bmap_local_to_extents() useful for any type of data fork content. Signed-off-by: Dave Chinner <dchinner@redhat.com> --- fs/xfs/xfs_bmap.c | 114 +++++++++++++++++++++++++++++++++++++++++++---------- 1 file changed, 93 insertions(+), 21 deletions(-) diff --git a/fs/xfs/xfs_bmap.c b/fs/xfs/xfs_bmap.c index 491f35e..b44af92 100644 --- a/fs/xfs/xfs_bmap.c +++ b/fs/xfs/xfs_bmap.c @@ -147,7 +147,10 @@ xfs_bmap_local_to_extents( xfs_fsblock_t *firstblock, /* first block allocated in xaction */ xfs_extlen_t total, /* total blocks needed by transaction */ int *logflagsp, /* inode logging flags */ - int whichfork); /* data or attr fork */ + int whichfork, /* data or attr fork */ + void (*init_fn)(struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp)); /* * Search the extents list for the inode, for the extent containing bno. @@ -357,7 +360,42 @@ xfs_bmap_add_attrfork_extents( } /* - * Called from xfs_bmap_add_attrfork to handle local format files. + * Block initialisation functions for local to extent format conversion. + * As these get more complex, they will be moved to the relevant files, + * but for now they are too simple to worry about. + */ +STATIC void +xfs_bmap_local_to_extents_init_fn( + struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp) +{ + bp->b_ops = &xfs_bmbt_buf_ops; + memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); +} + +STATIC void +xfs_symlink_local_to_remote( + struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp) +{ + /* remote symlink blocks are not verifiable until CRCs come along */ + bp->b_ops = NULL; + memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); +} + +/* + * Called from xfs_bmap_add_attrfork to handle local format files. Each + * different data fork content type needs a different callout to do the + * conversion. Some are basic and only require special block initialisation + * callouts for the data formating, others (directories) are so specialised they + * handle everything themselves. + * + * XXX (dgc): investigate whether directory conversion can use the generic + * formatting callout. It should be possible - it's just a very complex + * formatter. it would also require passing the transaction through to the init + * function. */ STATIC int /* error */ xfs_bmap_add_attrfork_local( @@ -368,25 +406,29 @@ xfs_bmap_add_attrfork_local( int *flags) /* inode logging flags */ { xfs_da_args_t dargs; /* args for dir/attr code */ - int error; /* error return value */ - xfs_mount_t *mp; /* mount structure pointer */ if (ip->i_df.if_bytes <= XFS_IFORK_DSIZE(ip)) return 0; + if (S_ISDIR(ip->i_d.di_mode)) { - mp = ip->i_mount; memset(&dargs, 0, sizeof(dargs)); dargs.dp = ip; dargs.firstblock = firstblock; dargs.flist = flist; - dargs.total = mp->m_dirblkfsbs; + dargs.total = ip->i_mount->m_dirblkfsbs; dargs.whichfork = XFS_DATA_FORK; dargs.trans = tp; - error = xfs_dir2_sf_to_block(&dargs); - } else - error = xfs_bmap_local_to_extents(tp, ip, firstblock, 1, flags, - XFS_DATA_FORK); - return error; + return xfs_dir2_sf_to_block(&dargs); + } + + if (S_ISLNK(ip->i_d.di_mode)) + return xfs_bmap_local_to_extents(tp, ip, firstblock, 1, + flags, XFS_DATA_FORK, + xfs_symlink_local_to_remote); + + return xfs_bmap_local_to_extents(tp, ip, firstblock, 1, flags, + XFS_DATA_FORK, + xfs_bmap_local_to_extents_init_fn); } /* @@ -3219,7 +3261,10 @@ xfs_bmap_local_to_extents( xfs_fsblock_t *firstblock, /* first block allocated in xaction */ xfs_extlen_t total, /* total blocks needed by transaction */ int *logflagsp, /* inode logging flags */ - int whichfork) /* data or attr fork */ + int whichfork, + void (*init_fn)(struct xfs_buf *bp, + struct xfs_inode *ip, + struct xfs_ifork *ifp)) { int error; /* error return value */ int flags; /* logging flags returned */ @@ -3239,12 +3284,12 @@ xfs_bmap_local_to_extents( xfs_buf_t *bp; /* buffer for extent block */ xfs_bmbt_rec_host_t *ep;/* extent record pointer */ + ASSERT((ifp->if_flags & + (XFS_IFINLINE|XFS_IFEXTENTS|XFS_IFEXTIREC)) == XFS_IFINLINE); memset(&args, 0, sizeof(args)); args.tp = tp; args.mp = ip->i_mount; args.firstblock = *firstblock; - ASSERT((ifp->if_flags & - (XFS_IFINLINE|XFS_IFEXTENTS|XFS_IFEXTIREC)) == XFS_IFINLINE); /* * Allocate a block. We know we need only one, since the * file currently fits in an inode. @@ -3258,17 +3303,20 @@ xfs_bmap_local_to_extents( } args.total = total; args.minlen = args.maxlen = args.prod = 1; - if ((error = xfs_alloc_vextent(&args))) + error = xfs_alloc_vextent(&args); + if (error) goto done; - /* - * Can't fail, the space was reserved. - */ + + /* Can't fail, the space was reserved. */ ASSERT(args.fsbno != NULLFSBLOCK); ASSERT(args.len == 1); *firstblock = args.fsbno; bp = xfs_btree_get_bufl(args.mp, tp, args.fsbno, 0); - bp->b_ops = &xfs_bmbt_buf_ops; - memcpy(bp->b_addr, ifp->if_u1.if_data, ifp->if_bytes); + + /* initialise the block and copy the data */ + init_fn(bp, ip, ifp); + + /* account for the change in fork size and log everything */ xfs_trans_log_buf(tp, bp, 0, ifp->if_bytes - 1); xfs_bmap_forkoff_reset(args.mp, ip, whichfork); xfs_idata_realloc(ip, -ifp->if_bytes, whichfork); @@ -4915,8 +4963,32 @@ xfs_bmapi_write( XFS_STATS_INC(xs_blk_mapw); if (XFS_IFORK_FORMAT(ip, whichfork) == XFS_DINODE_FMT_LOCAL) { + /* + * XXX (dgc): This assumes we are only called for inodes that + * contain content neutral data in local format. Anything that + * contains caller-specific data in local format that needs + * transformation to move to a block format needs to do the + * conversion to extent format itself. + * + * Directory data forks and attribute forks handle this + * themselves, but with the addition of metadata verifiers every + * data fork in local format now contains caller specific data + * and as such conversion through this function is likely to be + * broken. + * + * The only likely user of this branch is for remote symlinks, + * but we cannot overwrite the data fork contents of the symlink + * (EEXIST occurs higher up the stack) and so it will never go + * from local format to extent format here. Hence I don't think + * this branch is ever executed intentionally and we should + * consider removing it and asserting that xfs_bmapi_write() + * cannot be called directly on local format forks. i.e. callers + * are completely responsible for local to extent format + * conversion, not xfs_bmapi_write(). + */ error = xfs_bmap_local_to_extents(tp, ip, firstblock, total, - &bma.logflags, whichfork); + &bma.logflags, whichfork, + xfs_bmap_local_to_extents_init_fn); if (error) goto error0; } _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply related [flat|nested] 8+ messages in thread
* Re: Xfs fails in xfstests 013 2013-02-10 22:16 ` Dave Chinner @ 2013-02-11 12:08 ` Lukáš Czerner 0 siblings, 0 replies; 8+ messages in thread From: Lukáš Czerner @ 2013-02-11 12:08 UTC (permalink / raw) To: Dave Chinner; +Cc: Lukáš Czerner, xfs [-- Attachment #1: Type: TEXT/PLAIN, Size: 1323 bytes --] On Mon, 11 Feb 2013, Dave Chinner wrote: > Date: Mon, 11 Feb 2013 09:16:00 +1100 > From: Dave Chinner <david@fromorbit.com> > To: Lukáš Czerner <lczerner@redhat.com> > Cc: xfs@oss.sgi.com > Subject: Re: Xfs fails in xfstests 013 > > On Mon, Feb 04, 2013 at 10:00:13AM +1100, Dave Chinner wrote: > > On Fri, Feb 01, 2013 at 03:33:06PM +0100, Lukáš Czerner wrote: > > > On Fri, 1 Feb 2013, Lukáš Czerner wrote: > > > and I have not hit the assert. However I think that I know what's > > > going on. The verifier is obviously not attached when the symlink is > > > created, however it is attached when security attributes are created > > > for the symlink by xfs_init_security(). > > > > Which means the bug is in xfs_bmap_add_attrfork_local() in calling > > xfs_bmap_local_to_extents(). i.e it assumes that the local data is > > either directory data or extent data, and is attaching extent tree > > verifiers to the buffer that contains a remote symlink. Thinking > > time now needed, as this affects the symlink CRC changes as well. > > > > Thanks for the debug help, Lukas. > > Lukas, can you check whether the patch below fixes the problem you > saw? Hi Dave, from my testing it seems that ti fixes the problem. Can not reproduce it anymore with the patch applied. Thanks! -Lukas > > Cheers, > > Dave. > [-- Attachment #2: Type: text/plain, Size: 121 bytes --] _______________________________________________ xfs mailing list xfs@oss.sgi.com http://oss.sgi.com/mailman/listinfo/xfs ^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2013-02-11 12:12 UTC | newest] Thread overview: 8+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2013-01-31 8:19 Xfs fails in xfstests 013 Lukáš Czerner 2013-01-31 19:08 ` Ben Myers 2013-02-01 0:29 ` Dave Chinner 2013-02-01 10:58 ` Lukáš Czerner 2013-02-01 14:33 ` Lukáš Czerner 2013-02-03 23:00 ` Dave Chinner 2013-02-10 22:16 ` Dave Chinner 2013-02-11 12:08 ` Lukáš Czerner
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox