I should have cc Carlos Maiolino who authored this patch.
This is now done.


Le mer. 25 août 2021 à 15:32, Erwan Velu <erwanalia...@gmail.com> a écrit :

> Commit 8b1e5d1936fffc490510e85c95f93248453586c1 introduced the support
> of bigtime by adding the some features in inodes V3.
>
> This change extended grub_xfs_inode struct by 76 bytes but also changed the
> computation of XFS_V3_INODE_SIZE & XFS_V2_INODE_SIZE.
>
> Prior this commit, XFS_V2_INODE_SIZE was 100 bytes, after the commit it's
> 84 bytes.
> XFS_V2_INODE_SIZE becomes 16 bytes too small.
>
> As a result, the data structure aren't properly aligned and generates
> "attempt to read or write outside of partition" errors when trying to
> read the filesystem.
>
>                              GNU GRUB  version 2.11
>         ....
>         grub> set debug=efi,gpt,xfs
>         grub> insmod part_gpt
>         grub> ls (hd0,gpt1)/
>         partmap/gpt.c:93: Read a valid GPT header
>         partmap/gpt.c:115: GPT entry 0: start=4096, length=1953125
>         fs/xfs.c:931: Reading sb
>         fs/xfs.c:270: Validating superblock
>         fs/xfs.c:295: XFS v4 superblock detected
>         fs/xfs.c:962: Reading root ino 128
>         fs/xfs.c:515: Reading inode (128) - 64, 0
>         fs/xfs.c:515: Reading inode (739521961424144223) -
> 344365866970255880, 3840
>         error: attempt to read or write outside of partition.
>
> This commit change the XFS_V2_INODE_SIZE computation by substracting 76
> instead of 92 from the actual size of grub_xfs_inode.
> This 76 value is coming from the added :
>         20 uint8   unused5
>          1 uint64  flags2
>         48 uint8   unused6
>
> This patch explicit the split between the v2 and v3 parts of structure.
> The unused4 is still ending to the v2 structures and the v3 starts at
> unused5.
> This will avoid future corruption of v2 or v3.
>
> The XFS_V2_INODE_SIZE is returning to its expected size and the
> filesystem is back to a readable state.
>
>                       GNU GRUB  version 2.11
>         ....
>         grub> set debug=efi,gpt,xfs
>         grub> insmod part_gpt
>         grub> ls (hd0,gpt1)/
>         partmap/gpt.c:93: Read a valid GPT header
>         partmap/gpt.c:115: GPT entry 0: start=4096, length=1953125
>         fs/xfs.c:931: Reading sb
>         fs/xfs.c:270: Validating superblock
>         fs/xfs.c:295: XFS v4 superblock detected
>         fs/xfs.c:962: Reading root ino 128
>         fs/xfs.c:515: Reading inode (128) - 64, 0
>         fs/xfs.c:515: Reading inode (128) - 64, 0
>         fs/xfs.c:931: Reading sb
>         fs/xfs.c:270: Validating superblock
>         fs/xfs.c:295: XFS v4 superblock detected
>         fs/xfs.c:962: Reading root ino 128
>         fs/xfs.c:515: Reading inode (128) - 64, 0
>         fs/xfs.c:515: Reading inode (128) - 64, 0
>         fs/xfs.c:515: Reading inode (128) - 64, 0
>         fs/xfs.c:515: Reading inode (131) - 64, 768
>         efi/ fs/xfs.c:515: Reading inode (3145856) - 1464904, 0
>         grub2/ fs/xfs.c:515: Reading inode (132) - 64, 1024
>         grub/ fs/xfs.c:515: Reading inode (139) - 64, 2816
>         grub>
>
> Signed-off-by: Erwan Velu <e.v...@criteo.com>
> ---
>  grub-core/fs/xfs.c | 10 ++++++----
>  1 file changed, 6 insertions(+), 4 deletions(-)
>
> diff --git a/grub-core/fs/xfs.c b/grub-core/fs/xfs.c
> index 0f524c3a8a61..becea5bcdf61 100644
> --- a/grub-core/fs/xfs.c
> +++ b/grub-core/fs/xfs.c
> @@ -192,6 +192,7 @@ struct grub_xfs_time_legacy
>    grub_uint32_t nanosec;
>  } GRUB_PACKED;
>
> +// From
> https://mirrors.edge.kernel.org/pub/linux/utils/fs/xfs/docs/xfs_filesystem_structure.pdf
> about 'struct xfs_dinode_core'
>  struct grub_xfs_inode
>  {
>    grub_uint8_t magic[2];
> @@ -208,14 +209,15 @@ struct grub_xfs_inode
>    grub_uint32_t nextents;
>    grub_uint16_t unused3;
>    grub_uint8_t fork_offset;
> -  grub_uint8_t unused4[37];
> +  grub_uint8_t unused4[17]; // Last member of inode v2
> +  grub_uint8_t unused5[20]; // First member of inode v3
>    grub_uint64_t flags2;
> -  grub_uint8_t unused5[48];
> +  grub_uint8_t unused6[48]; // Last member of inode v3
>  } GRUB_PACKED;
>
>  #define XFS_V3_INODE_SIZE      sizeof(struct grub_xfs_inode)
> -/* Size of struct grub_xfs_inode until fork_offset (included). */
> -#define XFS_V2_INODE_SIZE      (XFS_V3_INODE_SIZE - 92)
> +/* Size of struct grub_xfs_inode v2, up to unused4 included */
> +#define XFS_V2_INODE_SIZE      (XFS_V3_INODE_SIZE - 76)
>
>  struct grub_xfs_dirblock_tail
>  {
> --
> 2.25.1
>
>
_______________________________________________
Grub-devel mailing list
Grub-devel@gnu.org
https://lists.gnu.org/mailman/listinfo/grub-devel

Reply via email to