Blame SOURCES/xfsprogs-4.12.0-xfs_db-update-buffer-size-when-new-type-is-set.patch

cbb4b9
From 55f224baf83d71b3d2cc24e6387d9f1f6a5a1eda Mon Sep 17 00:00:00 2001
cbb4b9
From: Bill O'Donnell <billodo@redhat.com>
cbb4b9
Date: Thu, 29 Jun 2017 13:05:00 -0500
cbb4b9
Subject: [PATCH] xfs_db: update buffer size when new type is set
cbb4b9
cbb4b9
xfs_db doesn't take sector size into account when setting type.
cbb4b9
This can result in an errant crc. For example, with a sector size
cbb4b9
of 4096:
cbb4b9
cbb4b9
xfs_db> agi 0
cbb4b9
xfs_db> p crc
cbb4b9
crc = 0xab85043e (correct)
cbb4b9
xfs_db> daddr
cbb4b9
current daddr is 16
cbb4b9
xfs_db> daddr 42
cbb4b9
xfs_db> daddr 16
cbb4b9
xfs_db> type agi
cbb4b9
Metadata CRC error detected at xfs_agi block 0x10/0x200
cbb4b9
xfs_db> p crc
cbb4b9
crc = 0xab85043e (bad)
cbb4b9
cbb4b9
When xfs_db sets the new daddr in daddr_f, it does so with one
cbb4b9
BBSIZE sector (512). Changing the type doesn't change the size
cbb4b9
of the current buffer in iocur_top, so the checksum is calculated
cbb4b9
on the wrong length for the type (when the actual sector size > BBSIZE (512).
cbb4b9
cbb4b9
For types with fields, reread the buffer to pick up the correct size for
cbb4b9
the new type when it gets set. Facilitate the reread by setting the cursor
cbb4b9
with set_cur().
cbb4b9
cbb4b9
Signed-off-by: Bill O'Donnell <billodo@redhat.com>
cbb4b9
Reviewed-by: Carlos Maiolino <cmaiolino@redhat.com>
cbb4b9
Reviewed-by: Darrick J. Wong <darrick.wong@oracle.com>
cbb4b9
[sandeen: fix up long line, clarify subject & comments]
cbb4b9
Signed-off-by: Eric Sandeen <sandeen@sandeen.net>
cbb4b9
---
cbb4b9
 db/io.c | 8 ++++++++
cbb4b9
 1 file changed, 8 insertions(+)
cbb4b9
cbb4b9
Index: xfsprogs-rhel7.5/db/io.c
cbb4b9
===================================================================
cbb4b9
--- xfsprogs-rhel7.5.orig/db/io.c
cbb4b9
+++ xfsprogs-rhel7.5/db/io.c
cbb4b9
@@ -27,6 +27,7 @@
cbb4b9
 #include "output.h"
cbb4b9
 #include "init.h"
cbb4b9
 #include "malloc.h"
cbb4b9
+#include "bit.h"
cbb4b9
 
cbb4b9
 static int	pop_f(int argc, char **argv);
cbb4b9
 static void     pop_help(void);
cbb4b9
@@ -567,6 +568,13 @@ set_iocur_type(
cbb4b9
 {
cbb4b9
 	struct xfs_buf	*bp = iocur_top->bp;
cbb4b9
 
cbb4b9
+	/* adjust buffer size for types with fields & hence fsize() */
cbb4b9
+	if (t->fields) {
cbb4b9
+		int bb_count;	/* type's size in basic blocks */
cbb4b9
+
cbb4b9
+		bb_count = BTOBB(byteize(fsize(t->fields, iocur_top->data, 0, 0)));
cbb4b9
+		set_cur(t, iocur_top->bb, bb_count, DB_RING_IGN, NULL);
cbb4b9
+	}
cbb4b9
 	iocur_top->typ = t;
cbb4b9
 
cbb4b9
 	/* verify the buffer if the type has one. */