[PATCH V3] xfs: prevent xfs_bmapi_write() to exceed maximum extent size.

Alain Renaud arenaud at sgi.com
Thu Aug 23 11:52:33 CDT 2012


xfs: prevent xfs_bmapi_write() to exceed maximum extent size.


When trying to do preallocation that exceed the the maximum size of
an extent, the extsize alignment can exceed the MAXEXTLEN.

We are already solving this issue for delay allocation but we
have the same with prealloc. So the Solution is to limit the bma.length
we send to xfs_bmapi_allocate() in xfs_bmapi_write().

We do have a simple test case to confirm that the problem exist.

# mkfs.xfs -f -b size=512 -d agcount=1,size=4294967296  /dev/sdb1
meta-data=/dev/sdb1              isize=256    agcount=1, agsize=8388608 blks
          =                       sectsz=512   attr=2, projid32bit=0
data     =                       bsize=512    blocks=8388608, imaxpct=25
          =                       sunit=0      swidth=0 blks
naming   =version 2              bsize=4096   ascii-ci=0
log      =internal log           bsize=512    blocks=20480, version=2
          =                       sectsz=512   sunit=0 blks, lazy-count=1
realtime =none                   extsz=4096   blocks=0, rtextents=0
# mount /dev/sdb1 /xfs_dir
# cd/xfs_dir/
# xfs_io -c 'extsize 4m' .
# xfs_io -f -c 'resvsp 0 1g' test_file
XFS_IOC_RESVSP64: No space left on device

Signed-off-by: Alain Renaud<arenaud at sgi.com>

---
    This is the 3rd version of the patch. In the previous version we were
making the change in xfs_bmap_extsize_align() but like Dave mention
we were breaking the function definition.

    Limiting the length in xfs_bmapi_write() seem more logical and should
avoid any unexpected side effect.

  fs/xfs/xfs_bmap.c |   27 ++++++++++++++++-----------
  1 file changed, 16 insertions(+), 11 deletions(-)

Index: b/fs/xfs/xfs_bmap.c
===================================================================
--- a/fs/xfs/xfs_bmap.c
+++ b/fs/xfs/xfs_bmap.c
@@ -4915,22 +4915,27 @@ xfs_bmapi_write(
  		 * that we found, if any.
  		 */
  		if (inhole || wasdelay) {
+			xfs_extlen_t	extsz;
  			bma.eof = eof;
  			bma.conv = !!(flags & XFS_BMAPI_CONVERT);
  			bma.wasdel = wasdelay;
  			bma.offset = bno;
  
-			/*
-			 * There's a 32/64 bit type mismatch between the
-			 * allocation length request (which can be 64 bits in
-			 * length) and the bma length request, which is
-			 * xfs_extlen_t and therefore 32 bits. Hence we have to
-			 * check for 32-bit overflows and handle them here.
-			 */
-			if (len > (xfs_filblks_t)MAXEXTLEN)
-				bma.length = MAXEXTLEN;
-			else
-				bma.length = len;
+			/* Figure out the extent size, set bma.length */
+			extsz = xfs_get_extsz_hint(ip);
+			if (extsz) {
+				/*
+				 * Make sure we don't exceed the maximum extent
+				 * length when we align the extent.  Reduce the
+				 * length we are going to allocate by the
+				 * maximum adjustment extent size aligment may
+				 * require.
+				 */
+				bma.length = XFS_FILBLKS_MIN(len,
+					     MAXEXTLEN - (2 * extsz - 1));
+			} else {
+				bma.length = XFS_FILBLKS_MIN(len, MAXEXTLEN);
+			}
  
  			ASSERT(len > 0);
  			ASSERT(bma.length > 0);


Alain Renaud

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://oss.sgi.com/pipermail/xfs/attachments/20120823/561f82e2/attachment.htm>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: xfs:avoid_bmap_len_overflow_xfs_bmap_extsize_align.patch
Type: text/x-patch
Size: 2926 bytes
Desc: not available
URL: <http://oss.sgi.com/pipermail/xfs/attachments/20120823/561f82e2/attachment.patch>


More information about the xfs mailing list