diff options
author | Darrick J. Wong <darrick.wong@oracle.com> | 2019-07-03 23:36:27 -0400 |
---|---|---|
committer | Darrick J. Wong <darrick.wong@oracle.com> | 2019-07-03 23:36:27 -0400 |
commit | 5f19c7fc6873351a3d81bbbb98c928343902d8d6 (patch) | |
tree | b55f57cbbc13452bd06d5b42309459e34867fbb8 | |
parent | 7035f9724f8497c709077c08df2073bfcde9c2f5 (diff) |
xfs: introduce v5 inode group structure
Introduce a new "v5" inode group structure that fixes the alignment
and padding problems of the existing structure.
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Reviewed-by: Brian Foster <bfoster@redhat.com>
-rw-r--r-- | fs/xfs/libxfs/xfs_fs.h | 11 | ||||
-rw-r--r-- | fs/xfs/xfs_ioctl.c | 9 | ||||
-rw-r--r-- | fs/xfs/xfs_ioctl.h | 2 | ||||
-rw-r--r-- | fs/xfs/xfs_ioctl32.c | 10 | ||||
-rw-r--r-- | fs/xfs/xfs_itable.c | 14 | ||||
-rw-r--r-- | fs/xfs/xfs_itable.h | 4 | ||||
-rw-r--r-- | fs/xfs/xfs_ondisk.h | 1 |
7 files changed, 42 insertions, 9 deletions
diff --git a/fs/xfs/libxfs/xfs_fs.h b/fs/xfs/libxfs/xfs_fs.h index 132e364eb141..8b8fe78511fb 100644 --- a/fs/xfs/libxfs/xfs_fs.h +++ b/fs/xfs/libxfs/xfs_fs.h | |||
@@ -445,6 +445,17 @@ struct xfs_inogrp { | |||
445 | __u64 xi_allocmask; /* mask of allocated inodes */ | 445 | __u64 xi_allocmask; /* mask of allocated inodes */ |
446 | }; | 446 | }; |
447 | 447 | ||
448 | /* New inumbers structure that reports v5 features and fixes padding issues */ | ||
449 | struct xfs_inumbers { | ||
450 | uint64_t xi_startino; /* starting inode number */ | ||
451 | uint64_t xi_allocmask; /* mask of allocated inodes */ | ||
452 | uint8_t xi_alloccount; /* # bits set in allocmask */ | ||
453 | uint8_t xi_version; /* version */ | ||
454 | uint8_t xi_padding[6]; /* zero */ | ||
455 | }; | ||
456 | |||
457 | #define XFS_INUMBERS_VERSION_V1 (1) | ||
458 | #define XFS_INUMBERS_VERSION_V5 (5) | ||
448 | 459 | ||
449 | /* | 460 | /* |
450 | * Error injection. | 461 | * Error injection. |
diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index 9f1984c31ba2..cdec674371a8 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c | |||
@@ -729,10 +729,13 @@ xfs_fsbulkstat_one_fmt( | |||
729 | 729 | ||
730 | int | 730 | int |
731 | xfs_fsinumbers_fmt( | 731 | xfs_fsinumbers_fmt( |
732 | struct xfs_ibulk *breq, | 732 | struct xfs_ibulk *breq, |
733 | const struct xfs_inogrp *igrp) | 733 | const struct xfs_inumbers *igrp) |
734 | { | 734 | { |
735 | if (copy_to_user(breq->ubuffer, igrp, sizeof(*igrp))) | 735 | struct xfs_inogrp ig1; |
736 | |||
737 | xfs_inumbers_to_inogrp(&ig1, igrp); | ||
738 | if (copy_to_user(breq->ubuffer, &ig1, sizeof(struct xfs_inogrp))) | ||
736 | return -EFAULT; | 739 | return -EFAULT; |
737 | return xfs_ibulk_advance(breq, sizeof(struct xfs_inogrp)); | 740 | return xfs_ibulk_advance(breq, sizeof(struct xfs_inogrp)); |
738 | } | 741 | } |
diff --git a/fs/xfs/xfs_ioctl.h b/fs/xfs/xfs_ioctl.h index 514d3028a134..654c0bb1bcf8 100644 --- a/fs/xfs/xfs_ioctl.h +++ b/fs/xfs/xfs_ioctl.h | |||
@@ -83,6 +83,6 @@ struct xfs_inogrp; | |||
83 | 83 | ||
84 | int xfs_fsbulkstat_one_fmt(struct xfs_ibulk *breq, | 84 | int xfs_fsbulkstat_one_fmt(struct xfs_ibulk *breq, |
85 | const struct xfs_bulkstat *bstat); | 85 | const struct xfs_bulkstat *bstat); |
86 | int xfs_fsinumbers_fmt(struct xfs_ibulk *breq, const struct xfs_inogrp *igrp); | 86 | int xfs_fsinumbers_fmt(struct xfs_ibulk *breq, const struct xfs_inumbers *igrp); |
87 | 87 | ||
88 | #endif | 88 | #endif |
diff --git a/fs/xfs/xfs_ioctl32.c b/fs/xfs/xfs_ioctl32.c index ed8e012dabbb..ca734381a557 100644 --- a/fs/xfs/xfs_ioctl32.c +++ b/fs/xfs/xfs_ioctl32.c | |||
@@ -81,10 +81,14 @@ xfs_compat_growfs_rt_copyin( | |||
81 | 81 | ||
82 | STATIC int | 82 | STATIC int |
83 | xfs_fsinumbers_fmt_compat( | 83 | xfs_fsinumbers_fmt_compat( |
84 | struct xfs_ibulk *breq, | 84 | struct xfs_ibulk *breq, |
85 | const struct xfs_inogrp *igrp) | 85 | const struct xfs_inumbers *ig) |
86 | { | 86 | { |
87 | struct compat_xfs_inogrp __user *p32 = breq->ubuffer; | 87 | struct compat_xfs_inogrp __user *p32 = breq->ubuffer; |
88 | struct xfs_inogrp ig1; | ||
89 | struct xfs_inogrp *igrp = &ig1; | ||
90 | |||
91 | xfs_inumbers_to_inogrp(&ig1, ig); | ||
88 | 92 | ||
89 | if (put_user(igrp->xi_startino, &p32->xi_startino) || | 93 | if (put_user(igrp->xi_startino, &p32->xi_startino) || |
90 | put_user(igrp->xi_alloccount, &p32->xi_alloccount) || | 94 | put_user(igrp->xi_alloccount, &p32->xi_alloccount) || |
diff --git a/fs/xfs/xfs_itable.c b/fs/xfs/xfs_itable.c index 5d406915144d..687c873fa635 100644 --- a/fs/xfs/xfs_itable.c +++ b/fs/xfs/xfs_itable.c | |||
@@ -331,10 +331,11 @@ xfs_inumbers_walk( | |||
331 | const struct xfs_inobt_rec_incore *irec, | 331 | const struct xfs_inobt_rec_incore *irec, |
332 | void *data) | 332 | void *data) |
333 | { | 333 | { |
334 | struct xfs_inogrp inogrp = { | 334 | struct xfs_inumbers inogrp = { |
335 | .xi_startino = XFS_AGINO_TO_INO(mp, agno, irec->ir_startino), | 335 | .xi_startino = XFS_AGINO_TO_INO(mp, agno, irec->ir_startino), |
336 | .xi_alloccount = irec->ir_count - irec->ir_freecount, | 336 | .xi_alloccount = irec->ir_count - irec->ir_freecount, |
337 | .xi_allocmask = ~irec->ir_free, | 337 | .xi_allocmask = ~irec->ir_free, |
338 | .xi_version = XFS_INUMBERS_VERSION_V5, | ||
338 | }; | 339 | }; |
339 | struct xfs_inumbers_chunk *ic = data; | 340 | struct xfs_inumbers_chunk *ic = data; |
340 | xfs_agino_t agino; | 341 | xfs_agino_t agino; |
@@ -381,3 +382,14 @@ xfs_inumbers( | |||
381 | 382 | ||
382 | return error; | 383 | return error; |
383 | } | 384 | } |
385 | |||
386 | /* Convert an inumbers (v5) struct to a inogrp (v1) struct. */ | ||
387 | void | ||
388 | xfs_inumbers_to_inogrp( | ||
389 | struct xfs_inogrp *ig1, | ||
390 | const struct xfs_inumbers *ig) | ||
391 | { | ||
392 | ig1->xi_startino = ig->xi_startino; | ||
393 | ig1->xi_alloccount = ig->xi_alloccount; | ||
394 | ig1->xi_allocmask = ig->xi_allocmask; | ||
395 | } | ||
diff --git a/fs/xfs/xfs_itable.h b/fs/xfs/xfs_itable.h index 60e259192056..fa9fb9104c7f 100644 --- a/fs/xfs/xfs_itable.h +++ b/fs/xfs/xfs_itable.h | |||
@@ -46,8 +46,10 @@ void xfs_bulkstat_to_bstat(struct xfs_mount *mp, struct xfs_bstat *bs1, | |||
46 | const struct xfs_bulkstat *bstat); | 46 | const struct xfs_bulkstat *bstat); |
47 | 47 | ||
48 | typedef int (*inumbers_fmt_pf)(struct xfs_ibulk *breq, | 48 | typedef int (*inumbers_fmt_pf)(struct xfs_ibulk *breq, |
49 | const struct xfs_inogrp *igrp); | 49 | const struct xfs_inumbers *igrp); |
50 | 50 | ||
51 | int xfs_inumbers(struct xfs_ibulk *breq, inumbers_fmt_pf formatter); | 51 | int xfs_inumbers(struct xfs_ibulk *breq, inumbers_fmt_pf formatter); |
52 | void xfs_inumbers_to_inogrp(struct xfs_inogrp *ig1, | ||
53 | const struct xfs_inumbers *ig); | ||
52 | 54 | ||
53 | #endif /* __XFS_ITABLE_H__ */ | 55 | #endif /* __XFS_ITABLE_H__ */ |
diff --git a/fs/xfs/xfs_ondisk.h b/fs/xfs/xfs_ondisk.h index 0b4cdda68524..d8f941b4d51c 100644 --- a/fs/xfs/xfs_ondisk.h +++ b/fs/xfs/xfs_ondisk.h | |||
@@ -148,6 +148,7 @@ xfs_check_ondisk_structs(void) | |||
148 | XFS_CHECK_OFFSET(struct xfs_attr3_leafblock, hdr.info.hdr, 0); | 148 | XFS_CHECK_OFFSET(struct xfs_attr3_leafblock, hdr.info.hdr, 0); |
149 | 149 | ||
150 | XFS_CHECK_STRUCT_SIZE(struct xfs_bulkstat, 192); | 150 | XFS_CHECK_STRUCT_SIZE(struct xfs_bulkstat, 192); |
151 | XFS_CHECK_STRUCT_SIZE(struct xfs_inumbers, 24); | ||
151 | } | 152 | } |
152 | 153 | ||
153 | #endif /* __XFS_ONDISK_H */ | 154 | #endif /* __XFS_ONDISK_H */ |