!27 [sync] PR-26: 回合高版本补丁
From: @openeuler-sync-bot Reviewed-by: @liuzhiqiang26 Signed-off-by: @liuzhiqiang26
This commit is contained in:
commit
48dd2baef2
110
0002-xfs-add-agf-freeblocks-verify-in-xfs_agf_verify.patch
Normal file
110
0002-xfs-add-agf-freeblocks-verify-in-xfs_agf_verify.patch
Normal file
@ -0,0 +1,110 @@
|
||||
From 0f24228d7661305ce050a6294e9b0fe4b484b791 Mon Sep 17 00:00:00 2001
|
||||
From: Zheng Bin <zhengbin13@huawei.com>
|
||||
Date: Wed, 29 Apr 2020 14:10:49 -0400
|
||||
Subject: [PATCH] xfs: add agf freeblocks verify in xfs_agf_verify
|
||||
|
||||
Source kernel commit: d0c7feaf87678371c2c09b3709400be416b2dc62
|
||||
|
||||
We recently used fuzz(hydra) to test XFS and automatically generate
|
||||
tmp.img(XFS v5 format, but some metadata is wrong)
|
||||
|
||||
xfs_repair information(just one AG):
|
||||
agf_freeblks 0, counted 3224 in ag 0
|
||||
agf_longest 536874136, counted 3224 in ag 0
|
||||
sb_fdblocks 613, counted 3228
|
||||
|
||||
Test as follows:
|
||||
mount tmp.img tmpdir
|
||||
cp file1M tmpdir
|
||||
sync
|
||||
|
||||
In 4.19-stable, sync will stuck, the reason is:
|
||||
xfs_mountfs
|
||||
xfs_check_summary_counts
|
||||
if ((!xfs_sb_version_haslazysbcount(&mp->m_sb) ||
|
||||
XFS_LAST_UNMOUNT_WAS_CLEAN(mp)) &&
|
||||
!xfs_fs_has_sickness(mp, XFS_SICK_FS_COUNTERS))
|
||||
return 0; -->just return, incore sb_fdblocks still be 613
|
||||
xfs_initialize_perag_data
|
||||
|
||||
cp file1M tmpdir -->ok(write file to pagecache)
|
||||
sync -->stuck(write pagecache to disk)
|
||||
xfs_map_blocks
|
||||
xfs_iomap_write_allocate
|
||||
while (count_fsb != 0) {
|
||||
nimaps = 0;
|
||||
while (nimaps == 0) { --> endless loop
|
||||
nimaps = 1;
|
||||
xfs_bmapi_write(..., &nimaps) --> nimaps becomes 0 again
|
||||
xfs_bmapi_write
|
||||
xfs_bmap_alloc
|
||||
xfs_bmap_btalloc
|
||||
xfs_alloc_vextent
|
||||
xfs_alloc_fix_freelist
|
||||
xfs_alloc_space_available -->fail(agf_freeblks is 0)
|
||||
|
||||
In linux-next, sync not stuck, cause commit c2b3164320b5 ("xfs:
|
||||
use the latest extent at writeback delalloc conversion time") remove
|
||||
the above while, dmesg is as follows:
|
||||
[ 55.250114] XFS (loop0): page discard on page ffffea0008bc7380, inode 0x1b0c, offset 0.
|
||||
|
||||
Users do not know why this page is discard, the better soultion is:
|
||||
1. Like xfs_repair, make sure sb_fdblocks is equal to counted
|
||||
(xfs_initialize_perag_data did this, who is not called at this mount)
|
||||
2. Add agf verify, if fail, will tell users to repair
|
||||
|
||||
This patch use the second soultion.
|
||||
|
||||
Signed-off-by: Zheng Bin <zhengbin13@huawei.com>
|
||||
Signed-off-by: Ren Xudong <renxudong1@huawei.com>
|
||||
Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_alloc.c | 16 ++++++++++++++++
|
||||
1 file changed, 16 insertions(+)
|
||||
|
||||
diff --git a/libxfs/xfs_alloc.c b/libxfs/xfs_alloc.c
|
||||
index a92ca524..09db6693 100644
|
||||
--- a/libxfs/xfs_alloc.c
|
||||
+++ b/libxfs/xfs_alloc.c
|
||||
@@ -2854,6 +2854,13 @@ xfs_agf_verify(
|
||||
be32_to_cpu(agf->agf_flcount) <= xfs_agfl_size(mp)))
|
||||
return __this_address;
|
||||
|
||||
+ if (be32_to_cpu(agf->agf_length) > mp->m_sb.sb_dblocks)
|
||||
+ return __this_address;
|
||||
+
|
||||
+ if (be32_to_cpu(agf->agf_freeblks) < be32_to_cpu(agf->agf_longest) ||
|
||||
+ be32_to_cpu(agf->agf_freeblks) > be32_to_cpu(agf->agf_length))
|
||||
+ return __this_address;
|
||||
+
|
||||
if (be32_to_cpu(agf->agf_levels[XFS_BTNUM_BNO]) < 1 ||
|
||||
be32_to_cpu(agf->agf_levels[XFS_BTNUM_CNT]) < 1 ||
|
||||
be32_to_cpu(agf->agf_levels[XFS_BTNUM_BNO]) > XFS_BTREE_MAXLEVELS ||
|
||||
@@ -2865,6 +2872,10 @@ xfs_agf_verify(
|
||||
be32_to_cpu(agf->agf_levels[XFS_BTNUM_RMAP]) > XFS_BTREE_MAXLEVELS))
|
||||
return __this_address;
|
||||
|
||||
+ if (xfs_sb_version_hasrmapbt(&mp->m_sb) &&
|
||||
+ be32_to_cpu(agf->agf_rmap_blocks) > be32_to_cpu(agf->agf_length))
|
||||
+ return __this_address;
|
||||
+
|
||||
/*
|
||||
* during growfs operations, the perag is not fully initialised,
|
||||
* so we can't use it for any useful checking. growfs ensures we can't
|
||||
@@ -2878,6 +2889,11 @@ xfs_agf_verify(
|
||||
be32_to_cpu(agf->agf_btreeblks) > be32_to_cpu(agf->agf_length))
|
||||
return __this_address;
|
||||
|
||||
+ if (xfs_sb_version_hasreflink(&mp->m_sb) &&
|
||||
+ be32_to_cpu(agf->agf_refcount_blocks) >
|
||||
+ be32_to_cpu(agf->agf_length))
|
||||
+ return __this_address;
|
||||
+
|
||||
if (xfs_sb_version_hasreflink(&mp->m_sb) &&
|
||||
(be32_to_cpu(agf->agf_refcount_level) < 1 ||
|
||||
be32_to_cpu(agf->agf_refcount_level) > XFS_BTREE_MAXLEVELS))
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,40 @@
|
||||
From e28956c1490593cadd6f5c6bc4b35cd2b3b632d1 Mon Sep 17 00:00:00 2001
|
||||
From: "Darrick J. Wong" <darrick.wong@oracle.com>
|
||||
Date: Fri, 1 May 2020 17:37:09 -0400
|
||||
Subject: [PATCH] xfs: don't ever return a stale pointer from
|
||||
__xfs_dir3_free_read
|
||||
|
||||
Source kernel commit: 1cb5deb5bc095c070c09a4540c45f9c9ba24be43
|
||||
|
||||
If we decide that a directory free block is corrupt, we must take care
|
||||
not to leak a buffer pointer to the caller. After xfs_trans_brelse
|
||||
returns, the buffer can be freed or reused, which means that we have to
|
||||
set *bpp back to NULL.
|
||||
|
||||
Callers are supposed to notice the nonzero return value and not use the
|
||||
buffer pointer, but we should code more defensively, even if all current
|
||||
callers handle this situation correctly.
|
||||
|
||||
Fixes: de14c5f541e7 ("xfs: verify free block header fields")
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Dave Chinner <dchinner@redhat.com>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_dir2_node.c | 1 +
|
||||
1 file changed, 1 insertion(+)
|
||||
|
||||
diff --git a/libxfs/xfs_dir2_node.c b/libxfs/xfs_dir2_node.c
|
||||
index ffa136b..c2deafa 100644
|
||||
--- a/libxfs/xfs_dir2_node.c
|
||||
+++ b/libxfs/xfs_dir2_node.c
|
||||
@@ -225,6 +225,7 @@ __xfs_dir3_free_read(
|
||||
if (fa) {
|
||||
xfs_verifier_error(*bpp, -EFSCORRUPTED, fa);
|
||||
xfs_trans_brelse(tp, *bpp);
|
||||
+ *bpp = NULL;
|
||||
return -EFSCORRUPTED;
|
||||
}
|
||||
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,41 @@
|
||||
From a2a0a99a70b02649250fe2c50ef9546f9e306d44 Mon Sep 17 00:00:00 2001
|
||||
From: "Darrick J. Wong" <darrick.wong@oracle.com>
|
||||
Date: Fri, 1 May 2020 17:37:09 -0400
|
||||
Subject: [PATCH] xfs: xfs_dabuf_map should return ENOMEM when map allocation
|
||||
fails
|
||||
|
||||
Source kernel commit: faf8ee8476c19b30fd16079ad616b2b0f56eaff4
|
||||
|
||||
If the xfs_buf_map array allocation in xfs_dabuf_map fails for whatever
|
||||
reason, we bail out with error code zero. This will confuse callers, so
|
||||
make sure that we return ENOMEM. Allocation failure should never happen
|
||||
with the small size of the array, but code defensively anyway.
|
||||
|
||||
Fixes: 45feef8f50b94d ("xfs: refactor xfs_dabuf_map")
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Christoph Hellwig <hch@lst.de>
|
||||
Reviewed-by: Chaitanya Kulkarni <chaitanya.kulkarni@wdc.com>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_da_btree.c | 4 +++-
|
||||
1 file changed, 3 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/libxfs/xfs_da_btree.c b/libxfs/xfs_da_btree.c
|
||||
index d785312f..4e909caa 100644
|
||||
--- a/libxfs/xfs_da_btree.c
|
||||
+++ b/libxfs/xfs_da_btree.c
|
||||
@@ -2518,8 +2518,10 @@ xfs_dabuf_map(
|
||||
*/
|
||||
if (nirecs > 1) {
|
||||
map = kmem_zalloc(nirecs * sizeof(struct xfs_buf_map), KM_NOFS);
|
||||
- if (!map)
|
||||
+ if (!map) {
|
||||
+ error = -ENOMEM;
|
||||
goto out_free_irecs;
|
||||
+ }
|
||||
*mapp = map;
|
||||
}
|
||||
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,36 @@
|
||||
From 2c711623374764cd7f9e95da7fdf4d9e90feb4c0 Mon Sep 17 00:00:00 2001
|
||||
From: "Darrick J. Wong" <darrick.wong@oracle.com>
|
||||
Date: Fri, 1 May 2020 17:37:09 -0400
|
||||
Subject: [PATCH] xfs: fix incorrect test in xfs_alloc_ag_vextent_lastblock
|
||||
|
||||
Source kernel commit: 77ca1eed5a7d2bf0905562eb1a15aac76bc19fe4
|
||||
|
||||
When I lifted the code in xfs_alloc_ag_vextent_lastblock out of a loop,
|
||||
I forgot to convert all the accesses to len to be pointer dereferences.
|
||||
|
||||
Coverity-id: 1457918
|
||||
Fixes: 5113f8ec3753ed ("xfs: clean up weird while loop in xfs_alloc_ag_vextent_near")
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Brian Foster <bfoster@redhat.com>
|
||||
Reviewed-by: Christoph Hellwig <hch@lst.de>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_alloc.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/libxfs/xfs_alloc.c b/libxfs/xfs_alloc.c
|
||||
index 841b0305..fee4039c 100644
|
||||
--- a/libxfs/xfs_alloc.c
|
||||
+++ b/libxfs/xfs_alloc.c
|
||||
@@ -1510,7 +1510,7 @@ xfs_alloc_ag_vextent_lastblock(
|
||||
* maxlen, go to the start of this block, and skip all those smaller
|
||||
* than minlen.
|
||||
*/
|
||||
- if (len || args->alignment > 1) {
|
||||
+ if (*len || args->alignment > 1) {
|
||||
acur->cnt->bc_ptrs[0] = 1;
|
||||
do {
|
||||
error = xfs_alloc_get_rec(acur->cnt, bno, len, &i);
|
||||
--
|
||||
2.27.0
|
||||
|
||||
41
0006-xfs_db-fix-crc-invalidation-segfault.patch
Normal file
41
0006-xfs_db-fix-crc-invalidation-segfault.patch
Normal file
@ -0,0 +1,41 @@
|
||||
From a19679ec0fa23fd360c510f21c498dd37d35713c Mon Sep 17 00:00:00 2001
|
||||
From: Anthony Iliopoulos <ailiop@suse.com>
|
||||
Date: Tue, 26 May 2020 14:35:51 -0400
|
||||
Subject: [PATCH] xfs_db: fix crc invalidation segfault
|
||||
|
||||
The nowrite_ops var is declared within nested block scope but used
|
||||
outside that scope, causing xfs_db to crash while trying to defererence
|
||||
the verify_write pointer. Fix it by lifting the declaration to the outer
|
||||
scope, where it is accessed.
|
||||
|
||||
Fixes: b64af2c48220c8 ("xfs_db: add crc manipulation commands")
|
||||
Reviewed-by: Eric Sandeen <sandeen@redhat.com>
|
||||
Signed-off-by: Anthony Iliopoulos <ailiop@suse.com>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
db/crc.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/db/crc.c b/db/crc.c
|
||||
index 95161c6d..b23417a1 100644
|
||||
--- a/db/crc.c
|
||||
+++ b/db/crc.c
|
||||
@@ -53,6 +53,7 @@ crc_f(
|
||||
char **argv)
|
||||
{
|
||||
const struct xfs_buf_ops *stashed_ops = NULL;
|
||||
+ struct xfs_buf_ops nowrite_ops;
|
||||
extern char *progname;
|
||||
const field_t *fields;
|
||||
const ftattr_t *fa;
|
||||
@@ -127,7 +128,6 @@ crc_f(
|
||||
}
|
||||
|
||||
if (invalidate) {
|
||||
- struct xfs_buf_ops nowrite_ops;
|
||||
flist_t *sfl;
|
||||
int bit_length;
|
||||
int parentoffset;
|
||||
--
|
||||
2.27.0
|
||||
|
||||
124
0007-xfs_repair-fix-missing-dir-buffer-corruption-checks.patch
Normal file
124
0007-xfs_repair-fix-missing-dir-buffer-corruption-checks.patch
Normal file
@ -0,0 +1,124 @@
|
||||
From be752639294c8a1eb0f06275e77744f32e5bd277 Mon Sep 17 00:00:00 2001
|
||||
From: "Darrick J. Wong" <darrick.wong@oracle.com>
|
||||
Date: Fri, 10 Jul 2020 15:34:36 -0400
|
||||
Subject: [PATCH] xfs_repair: fix missing dir buffer corruption checks
|
||||
|
||||
The da_read_buf() function operates in "salvage" mode, which means that
|
||||
if the verifiers fail, it will return a buffer with b_error set. The
|
||||
callers of da_read_buf, however, do not adequately check for verifier
|
||||
errors, which means that repair can fail to flag a corrupt filesystem.
|
||||
|
||||
Fix the callers to do this properly. The dabtree block walker and the
|
||||
dabtree path checker functions to complain any time the da node / leafn
|
||||
verifiers fail. Fix the directory block walking functions to complain
|
||||
about EFSCORRUPTED, since they already dealt with EFSBADCRC.
|
||||
|
||||
Found by running xfs/496 against lhdr.stale = middlebit.
|
||||
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Christoph Hellwig <hch@lst.de>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
repair/da_util.c | 25 ++++++++++++++++---------
|
||||
repair/dir2.c | 21 +++++++++++++++++++++
|
||||
2 files changed, 37 insertions(+), 9 deletions(-)
|
||||
|
||||
diff --git a/repair/da_util.c b/repair/da_util.c
|
||||
index 5061880f..7239c2e2 100644
|
||||
--- a/repair/da_util.c
|
||||
+++ b/repair/da_util.c
|
||||
@@ -134,6 +134,15 @@ _("can't read %s block %u for inode %" PRIu64 "\n"),
|
||||
goto error_out;
|
||||
}
|
||||
|
||||
+ /* corrupt leafn/node; rebuild the dir. */
|
||||
+ if (bp->b_error == -EFSBADCRC || bp->b_error == -EFSCORRUPTED) {
|
||||
+ do_warn(
|
||||
+_("corrupt %s tree block %u for inode %" PRIu64 "\n"),
|
||||
+ FORKNAME(whichfork), bno, da_cursor->ino);
|
||||
+ libxfs_buf_relse(bp);
|
||||
+ goto error_out;
|
||||
+ }
|
||||
+
|
||||
node = bp->b_addr;
|
||||
libxfs_da3_node_hdr_from_disk(mp, &nodehdr, node);
|
||||
|
||||
@@ -160,15 +169,6 @@ _("bad %s magic number 0x%x in inode %" PRIu64 " bno = %u\n"),
|
||||
goto error_out;
|
||||
}
|
||||
|
||||
- /* corrupt node; rebuild the dir. */
|
||||
- if (bp->b_error == -EFSBADCRC || bp->b_error == -EFSCORRUPTED) {
|
||||
- libxfs_buf_relse(bp);
|
||||
- do_warn(
|
||||
-_("corrupt %s tree block %u for inode %" PRIu64 "\n"),
|
||||
- FORKNAME(whichfork), bno, da_cursor->ino);
|
||||
- goto error_out;
|
||||
- }
|
||||
-
|
||||
if (nodehdr.count > geo->node_ents) {
|
||||
do_warn(
|
||||
_("bad %s record count in inode %" PRIu64 ", count = %d, max = %d\n"),
|
||||
@@ -562,6 +562,13 @@ _("can't read %s block %u for inode %" PRIu64 "\n"),
|
||||
FORKNAME(whichfork), dabno, cursor->ino);
|
||||
return 1;
|
||||
}
|
||||
+ if (bp->b_error == -EFSCORRUPTED || bp->b_error == -EFSBADCRC) {
|
||||
+ do_warn(
|
||||
+_("corrupt %s tree block %u for inode %" PRIu64 "\n"),
|
||||
+ FORKNAME(whichfork), dabno, cursor->ino);
|
||||
+ libxfs_buf_relse(bp);
|
||||
+ return 1;
|
||||
+ }
|
||||
|
||||
newnode = bp->b_addr;
|
||||
libxfs_da3_node_hdr_from_disk(mp, &nodehdr, newnode);
|
||||
diff --git a/repair/dir2.c b/repair/dir2.c
|
||||
index cbbce601..b374bc7b 100644
|
||||
--- a/repair/dir2.c
|
||||
+++ b/repair/dir2.c
|
||||
@@ -983,6 +983,13 @@ _("can't read block %u for directory inode %" PRIu64 "\n"),
|
||||
mp->m_dir_geo->datablk, ino);
|
||||
return 1;
|
||||
}
|
||||
+ if (bp->b_error == -EFSCORRUPTED) {
|
||||
+ do_warn(
|
||||
+_("corrupt directory block %u for inode %" PRIu64 "\n"),
|
||||
+ mp->m_dir_geo->datablk, ino);
|
||||
+ libxfs_buf_relse(bp);
|
||||
+ return 1;
|
||||
+ }
|
||||
/*
|
||||
* Verify the block
|
||||
*/
|
||||
@@ -1122,6 +1129,13 @@ _("can't read file block %u for directory inode %" PRIu64 "\n"),
|
||||
da_bno, ino);
|
||||
goto error_out;
|
||||
}
|
||||
+ if (bp->b_error == -EFSCORRUPTED) {
|
||||
+ do_warn(
|
||||
+_("corrupt directory leafn block %u for inode %" PRIu64 "\n"),
|
||||
+ da_bno, ino);
|
||||
+ libxfs_buf_relse(bp);
|
||||
+ goto error_out;
|
||||
+ }
|
||||
leaf = bp->b_addr;
|
||||
libxfs_dir2_leaf_hdr_from_disk(mp, &leafhdr, leaf);
|
||||
/*
|
||||
@@ -1324,6 +1338,13 @@ _("can't read block %" PRIu64 " for directory inode %" PRIu64 "\n"),
|
||||
dbno, ino);
|
||||
continue;
|
||||
}
|
||||
+ if (bp->b_error == -EFSCORRUPTED) {
|
||||
+ do_warn(
|
||||
+_("corrupt directory data block %lu for inode %" PRIu64 "\n"),
|
||||
+ dbno, ino);
|
||||
+ libxfs_buf_relse(bp);
|
||||
+ continue;
|
||||
+ }
|
||||
data = bp->b_addr;
|
||||
if (!(be32_to_cpu(data->magic) == XFS_DIR2_DATA_MAGIC ||
|
||||
be32_to_cpu(data->magic) == XFS_DIR3_DATA_MAGIC))
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,44 @@
|
||||
From 625c12fba2d613c209108c5e4f07af8309bcbafb Mon Sep 17 00:00:00 2001
|
||||
From: Brian Foster <bfoster@redhat.com>
|
||||
Date: Fri, 4 Sep 2020 16:01:20 -0400
|
||||
Subject: [PATCH] xfs: fix inode allocation block res calculation precedence
|
||||
|
||||
Source kernel commit: b2a8864728683443f34a9fd33a2b78b860934cc1
|
||||
|
||||
The block reservation calculation for inode allocation is supposed
|
||||
to consist of the blocks required for the inode chunk plus
|
||||
(maxlevels-1) of the inode btree multiplied by the number of inode
|
||||
btrees in the fs (2 when finobt is enabled, 1 otherwise).
|
||||
|
||||
Instead, the macro returns (ialloc_blocks + 2) due to a precedence
|
||||
error in the calculation logic. This leads to block reservation
|
||||
overruns via generic/531 on small block filesystems with finobt
|
||||
enabled. Add braces to fix the calculation and reserve the
|
||||
appropriate number of blocks.
|
||||
|
||||
Fixes: 9d43b180af67 ("xfs: update inode allocation/free transaction reservations for finobt")
|
||||
Signed-off-by: Brian Foster <bfoster@redhat.com>
|
||||
Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Christoph Hellwig <hch@lst.de>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_trans_space.h | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/libxfs/xfs_trans_space.h b/libxfs/xfs_trans_space.h
|
||||
index 88221c7a..c6df01a2 100644
|
||||
--- a/libxfs/xfs_trans_space.h
|
||||
+++ b/libxfs/xfs_trans_space.h
|
||||
@@ -57,7 +57,7 @@
|
||||
XFS_DAREMOVE_SPACE_RES(mp, XFS_DATA_FORK)
|
||||
#define XFS_IALLOC_SPACE_RES(mp) \
|
||||
(M_IGEO(mp)->ialloc_blks + \
|
||||
- (xfs_sb_version_hasfinobt(&mp->m_sb) ? 2 : 1 * \
|
||||
+ ((xfs_sb_version_hasfinobt(&mp->m_sb) ? 2 : 1) * \
|
||||
(M_IGEO(mp)->inobt_maxlevels - 1)))
|
||||
|
||||
/*
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,79 @@
|
||||
From d6e8deb14cbea11d8f265537f7163428717b93fb Mon Sep 17 00:00:00 2001
|
||||
From: Brian Foster <bfoster@redhat.com>
|
||||
Date: Tue, 15 Sep 2020 15:59:38 -0400
|
||||
Subject: [PATCH] xfs: fix off-by-one in inode alloc block reservation
|
||||
calculation
|
||||
|
||||
Source kernel commit: 657f101930bc6c5b41bd7d6c22565c4302a80d33
|
||||
|
||||
The inode chunk allocation transaction reserves inobt_maxlevels-1
|
||||
blocks to accommodate a full split of the inode btree. A full split
|
||||
requires an allocation for every existing level and a new root
|
||||
block, which means inobt_maxlevels is the worst case block
|
||||
requirement for a transaction that inserts to the inobt. This can
|
||||
lead to a transaction block reservation overrun when tmpfile
|
||||
creation allocates an inode chunk and expands the inobt to its
|
||||
maximum depth. This problem has been observed in conjunction with
|
||||
overlayfs, which makes frequent use of tmpfiles internally.
|
||||
|
||||
The existing reservation code goes back as far as the Linux git repo
|
||||
history (v2.6.12). It was likely never observed as a problem because
|
||||
the traditional file/directory creation transactions also include
|
||||
worst case block reservation for directory modifications, which most
|
||||
likely is able to make up for a single block deficiency in the inode
|
||||
allocation portion of the calculation. tmpfile support is relatively
|
||||
more recent (v3.15), less heavily used, and only includes the inode
|
||||
allocation block reservation as tmpfiles aren't linked into the
|
||||
directory tree on creation.
|
||||
|
||||
Fix up the inode alloc block reservation macro and a couple of the
|
||||
block allocator minleft parameters that enforce an allocation to
|
||||
leave enough free blocks in the AG for a full inobt split.
|
||||
|
||||
Signed-off-by: Brian Foster <bfoster@redhat.com>
|
||||
Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_ialloc.c | 4 ++--
|
||||
libxfs/xfs_trans_space.h | 2 +-
|
||||
2 files changed, 3 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/libxfs/xfs_ialloc.c b/libxfs/xfs_ialloc.c
|
||||
index 5f09ff5a..ce73feed 100644
|
||||
--- a/libxfs/xfs_ialloc.c
|
||||
+++ b/libxfs/xfs_ialloc.c
|
||||
@@ -683,7 +683,7 @@ xfs_ialloc_ag_alloc(
|
||||
args.minalignslop = igeo->cluster_align - 1;
|
||||
|
||||
/* Allow space for the inode btree to split. */
|
||||
- args.minleft = igeo->inobt_maxlevels - 1;
|
||||
+ args.minleft = igeo->inobt_maxlevels;
|
||||
if ((error = xfs_alloc_vextent(&args)))
|
||||
return error;
|
||||
|
||||
@@ -731,7 +731,7 @@ xfs_ialloc_ag_alloc(
|
||||
/*
|
||||
* Allow space for the inode btree to split.
|
||||
*/
|
||||
- args.minleft = igeo->inobt_maxlevels - 1;
|
||||
+ args.minleft = igeo->inobt_maxlevels;
|
||||
if ((error = xfs_alloc_vextent(&args)))
|
||||
return error;
|
||||
}
|
||||
diff --git a/libxfs/xfs_trans_space.h b/libxfs/xfs_trans_space.h
|
||||
index c6df01a2..7ad3659c 100644
|
||||
--- a/libxfs/xfs_trans_space.h
|
||||
+++ b/libxfs/xfs_trans_space.h
|
||||
@@ -58,7 +58,7 @@
|
||||
#define XFS_IALLOC_SPACE_RES(mp) \
|
||||
(M_IGEO(mp)->ialloc_blks + \
|
||||
((xfs_sb_version_hasfinobt(&mp->m_sb) ? 2 : 1) * \
|
||||
- (M_IGEO(mp)->inobt_maxlevels - 1)))
|
||||
+ M_IGEO(mp)->inobt_maxlevels))
|
||||
|
||||
/*
|
||||
* Space reservation values for various transactions.
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,52 @@
|
||||
From be2f3d3984902d7ce1e30fc7ec745f7671b7ffdd Mon Sep 17 00:00:00 2001
|
||||
From: Eric Sandeen <sandeen@redhat.com>
|
||||
Date: Tue, 15 Sep 2020 15:59:38 -0400
|
||||
Subject: [PATCH] xfs: fix boundary test in xfs_attr_shortform_verify
|
||||
|
||||
Source kernel commit: f4020438fab05364018c91f7e02ebdd192085933
|
||||
|
||||
The boundary test for the fixed-offset parts of xfs_attr_sf_entry in
|
||||
xfs_attr_shortform_verify is off by one, because the variable array
|
||||
at the end is defined as nameval[1] not nameval[].
|
||||
Hence we need to subtract 1 from the calculation.
|
||||
|
||||
This can be shown by:
|
||||
|
||||
# touch file
|
||||
# setfattr -n root.a file
|
||||
|
||||
and verifications will fail when it's written to disk.
|
||||
|
||||
This only matters for a last attribute which has a single-byte name
|
||||
and no value, otherwise the combination of namelen & valuelen will
|
||||
push endp further out and this test won't fail.
|
||||
|
||||
Fixes: 1e1bbd8e7ee06 ("xfs: create structure verifier function for shortform xattrs")
|
||||
Signed-off-by: Eric Sandeen <sandeen@redhat.com>
|
||||
Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Christoph Hellwig <hch@lst.de>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_attr_leaf.c | 4 +++-
|
||||
1 file changed, 3 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/libxfs/xfs_attr_leaf.c b/libxfs/xfs_attr_leaf.c
|
||||
index a27107cc..4c871fc1 100644
|
||||
--- a/libxfs/xfs_attr_leaf.c
|
||||
+++ b/libxfs/xfs_attr_leaf.c
|
||||
@@ -1033,8 +1033,10 @@ xfs_attr_shortform_verify(
|
||||
* struct xfs_attr_sf_entry has a variable length.
|
||||
* Check the fixed-offset parts of the structure are
|
||||
* within the data buffer.
|
||||
+ * xfs_attr_sf_entry is defined with a 1-byte variable
|
||||
+ * array at the end, so we must subtract that off.
|
||||
*/
|
||||
- if (((char *)sfep + sizeof(*sfep)) >= endp)
|
||||
+ if (((char *)sfep + sizeof(*sfep) - 1) >= endp)
|
||||
return __this_address;
|
||||
|
||||
/* Don't allow names with known bad length. */
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -0,0 +1,53 @@
|
||||
From fc46ff14390ec9ee346f58b33486ea23157d981f Mon Sep 17 00:00:00 2001
|
||||
From: "Darrick J. Wong" <darrick.wong@oracle.com>
|
||||
Date: Thu, 12 Nov 2020 17:39:58 -0500
|
||||
Subject: [PATCH] xfs: set xefi_discard when creating a deferred agfl free log
|
||||
intent item
|
||||
|
||||
Source kernel commit: 2c334e12f957cd8c6bb66b4aa3f79848b7c33cab
|
||||
|
||||
Make sure that we actually initialize xefi_discard when we're scheduling
|
||||
a deferred free of an AGFL block. This was (eventually) found by the
|
||||
UBSAN while I was banging on realtime rmap problems, but it exists in
|
||||
the upstream codebase. While we're at it, rearrange the structure to
|
||||
reduce the struct size from 64 to 56 bytes.
|
||||
|
||||
Fixes: fcb762f5de2e ("xfs: add bmapi nodiscard flag")
|
||||
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
|
||||
Reviewed-by: Brian Foster <bfoster@redhat.com>
|
||||
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
|
||||
---
|
||||
libxfs/xfs_alloc.c | 1 +
|
||||
libxfs/xfs_bmap.h | 2 +-
|
||||
2 files changed, 2 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/libxfs/xfs_alloc.c b/libxfs/xfs_alloc.c
|
||||
index 93043d59..92f61fae 100644
|
||||
--- a/libxfs/xfs_alloc.c
|
||||
+++ b/libxfs/xfs_alloc.c
|
||||
@@ -2463,6 +2463,7 @@ xfs_defer_agfl_block(
|
||||
new->xefi_startblock = XFS_AGB_TO_FSB(mp, agno, agbno);
|
||||
new->xefi_blockcount = 1;
|
||||
new->xefi_oinfo = *oinfo;
|
||||
+ new->xefi_skip_discard = false;
|
||||
|
||||
trace_xfs_agfl_free_defer(mp, agno, 0, agbno, 1);
|
||||
|
||||
diff --git a/libxfs/xfs_bmap.h b/libxfs/xfs_bmap.h
|
||||
index e1bd484e..6747e97a 100644
|
||||
--- a/libxfs/xfs_bmap.h
|
||||
+++ b/libxfs/xfs_bmap.h
|
||||
@@ -52,9 +52,9 @@ struct xfs_extent_free_item
|
||||
{
|
||||
xfs_fsblock_t xefi_startblock;/* starting fs block number */
|
||||
xfs_extlen_t xefi_blockcount;/* number of blocks in extent */
|
||||
+ bool xefi_skip_discard;
|
||||
struct list_head xefi_list;
|
||||
struct xfs_owner_info xefi_oinfo; /* extent owner */
|
||||
- bool xefi_skip_discard;
|
||||
};
|
||||
|
||||
#define XFS_BMAP_MAX_NMAP 4
|
||||
--
|
||||
2.27.0
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
Name: xfsprogs
|
||||
Version: 5.6.0
|
||||
Release: 3
|
||||
Release: 4
|
||||
Summary: Administration and debugging tools for the XFS file system
|
||||
License: GPL+ and LGPLv2+
|
||||
URL: https://xfs.wiki.kernel.org
|
||||
@ -8,6 +8,16 @@ URL: https://xfs.wiki.kernel.org
|
||||
Source0: http://kernel.org/pub/linux/utils/fs/xfs/xfsprogs/%{name}-%{version}.tar.xz
|
||||
|
||||
Patch1: 0001-mkfs.xfs-fix-ASSERT-on-too-small-device-with-stripe-.patch
|
||||
Patch2: 0002-xfs-add-agf-freeblocks-verify-in-xfs_agf_verify.patch
|
||||
Patch3: 0003-xfs-don-t-ever-return-a-stale-pointer-from-__xfs_dir.patch
|
||||
Patch4: 0004-xfs-xfs_dabuf_map-should-return-ENOMEM-when-map-allo.patch
|
||||
Patch5: 0005-xfs-fix-incorrect-test-in-xfs_alloc_ag_vextent_lastb.patch
|
||||
Patch6: 0006-xfs_db-fix-crc-invalidation-segfault.patch
|
||||
Patch7: 0007-xfs_repair-fix-missing-dir-buffer-corruption-checks.patch
|
||||
Patch8: 0008-xfs-fix-inode-allocation-block-res-calculation-prece.patch
|
||||
Patch9: 0009-xfs-fix-off-by-one-in-inode-alloc-block-reservation-.patch
|
||||
Patch10: 0010-xfs-fix-boundary-test-in-xfs_attr_shortform_verify.patch
|
||||
Patch11: 0011-xfs-set-xefi_discard-when-creating-a-deferred-agfl-f.patch
|
||||
|
||||
BuildRequires: libtool libattr-devel libuuid-devel gcc git
|
||||
BuildRequires: readline-devel libblkid-devel >= 2.30 lvm2-devel libicu-devel >= 62.0
|
||||
@ -100,6 +110,9 @@ rm -rf %{buildroot}%{_datadir}/doc/xfsprogs/
|
||||
|
||||
|
||||
%changelog
|
||||
* Mon Mar 14 2022 wuguanghao <wuguanghao3@huawei.com> - 5.6.0-4
|
||||
- backport bugfix patches from community
|
||||
|
||||
* Wed Mar 02 2022 Zhiqiang Liu <liuzhiqiang26@huawei.com> - 5.6.0-3
|
||||
- mkfs.xfs: fix ASSERT on to-small device with stripe geometry.
|
||||
Fix issue: https://gitee.com/src-openeuler/xfsprogs/issues/I4RZKQ
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user