diff options
author | Darrick J. Wong <darrick.wong@oracle.com> | 2019-04-12 10:41:17 -0400 |
---|---|---|
committer | Darrick J. Wong <darrick.wong@oracle.com> | 2019-04-14 21:15:57 -0400 |
commit | 7cd5006bdb6f6d9d9d7e68aa1d96b6e4a8b68bc5 (patch) | |
tree | df47e1074e3c043f5206a0e6c0201ae421fc0462 /fs/xfs | |
parent | 1b6d968de22bffd85a60538d2628185b17228291 (diff) |
xfs: add a new ioctl to describe allocation group geometry
Add a new ioctl to describe an allocation group's geometry.
Signed-off-by: Darrick J. Wong <darrick.wong@oracle.com>
Reviewed-by: Brian Foster <bfoster@redhat.com>
Diffstat (limited to 'fs/xfs')
-rw-r--r-- | fs/xfs/libxfs/xfs_ag.c | 52 | ||||
-rw-r--r-- | fs/xfs/libxfs/xfs_ag.h | 2 | ||||
-rw-r--r-- | fs/xfs/libxfs/xfs_fs.h | 14 | ||||
-rw-r--r-- | fs/xfs/xfs_ioctl.c | 24 | ||||
-rw-r--r-- | fs/xfs/xfs_ioctl32.c | 1 |
5 files changed, 93 insertions, 0 deletions
diff --git a/fs/xfs/libxfs/xfs_ag.c b/fs/xfs/libxfs/xfs_ag.c index 1ef8acf35e7d..1c0f2a6c10b4 100644 --- a/fs/xfs/libxfs/xfs_ag.c +++ b/fs/xfs/libxfs/xfs_ag.c | |||
@@ -19,6 +19,7 @@ | |||
19 | #include "xfs_ialloc.h" | 19 | #include "xfs_ialloc.h" |
20 | #include "xfs_rmap.h" | 20 | #include "xfs_rmap.h" |
21 | #include "xfs_ag.h" | 21 | #include "xfs_ag.h" |
22 | #include "xfs_ag_resv.h" | ||
22 | 23 | ||
23 | static struct xfs_buf * | 24 | static struct xfs_buf * |
24 | xfs_get_aghdr_buf( | 25 | xfs_get_aghdr_buf( |
@@ -461,3 +462,54 @@ xfs_ag_extend_space( | |||
461 | len, &XFS_RMAP_OINFO_SKIP_UPDATE, | 462 | len, &XFS_RMAP_OINFO_SKIP_UPDATE, |
462 | XFS_AG_RESV_NONE); | 463 | XFS_AG_RESV_NONE); |
463 | } | 464 | } |
465 | |||
466 | /* Retrieve AG geometry. */ | ||
467 | int | ||
468 | xfs_ag_get_geometry( | ||
469 | struct xfs_mount *mp, | ||
470 | xfs_agnumber_t agno, | ||
471 | struct xfs_ag_geometry *ageo) | ||
472 | { | ||
473 | struct xfs_buf *agi_bp; | ||
474 | struct xfs_buf *agf_bp; | ||
475 | struct xfs_agi *agi; | ||
476 | struct xfs_agf *agf; | ||
477 | struct xfs_perag *pag; | ||
478 | unsigned int freeblks; | ||
479 | int error; | ||
480 | |||
481 | if (agno >= mp->m_sb.sb_agcount) | ||
482 | return -EINVAL; | ||
483 | |||
484 | /* Lock the AG headers. */ | ||
485 | error = xfs_ialloc_read_agi(mp, NULL, agno, &agi_bp); | ||
486 | if (error) | ||
487 | return error; | ||
488 | error = xfs_alloc_read_agf(mp, NULL, agno, 0, &agf_bp); | ||
489 | if (error) | ||
490 | goto out_agi; | ||
491 | pag = xfs_perag_get(mp, agno); | ||
492 | |||
493 | /* Fill out form. */ | ||
494 | memset(ageo, 0, sizeof(*ageo)); | ||
495 | ageo->ag_number = agno; | ||
496 | |||
497 | agi = XFS_BUF_TO_AGI(agi_bp); | ||
498 | ageo->ag_icount = be32_to_cpu(agi->agi_count); | ||
499 | ageo->ag_ifree = be32_to_cpu(agi->agi_freecount); | ||
500 | |||
501 | agf = XFS_BUF_TO_AGF(agf_bp); | ||
502 | ageo->ag_length = be32_to_cpu(agf->agf_length); | ||
503 | freeblks = pag->pagf_freeblks + | ||
504 | pag->pagf_flcount + | ||
505 | pag->pagf_btreeblks - | ||
506 | xfs_ag_resv_needed(pag, XFS_AG_RESV_NONE); | ||
507 | ageo->ag_freeblks = freeblks; | ||
508 | |||
509 | /* Release resources. */ | ||
510 | xfs_perag_put(pag); | ||
511 | xfs_buf_relse(agf_bp); | ||
512 | out_agi: | ||
513 | xfs_buf_relse(agi_bp); | ||
514 | return error; | ||
515 | } | ||
diff --git a/fs/xfs/libxfs/xfs_ag.h b/fs/xfs/libxfs/xfs_ag.h index 412702e23f61..5166322807e7 100644 --- a/fs/xfs/libxfs/xfs_ag.h +++ b/fs/xfs/libxfs/xfs_ag.h | |||
@@ -26,5 +26,7 @@ struct aghdr_init_data { | |||
26 | int xfs_ag_init_headers(struct xfs_mount *mp, struct aghdr_init_data *id); | 26 | int xfs_ag_init_headers(struct xfs_mount *mp, struct aghdr_init_data *id); |
27 | int xfs_ag_extend_space(struct xfs_mount *mp, struct xfs_trans *tp, | 27 | int xfs_ag_extend_space(struct xfs_mount *mp, struct xfs_trans *tp, |
28 | struct aghdr_init_data *id, xfs_extlen_t len); | 28 | struct aghdr_init_data *id, xfs_extlen_t len); |
29 | int xfs_ag_get_geometry(struct xfs_mount *mp, xfs_agnumber_t agno, | ||
30 | struct xfs_ag_geometry *ageo); | ||
29 | 31 | ||
30 | #endif /* __LIBXFS_AG_H */ | 32 | #endif /* __LIBXFS_AG_H */ |
diff --git a/fs/xfs/libxfs/xfs_fs.h b/fs/xfs/libxfs/xfs_fs.h index cb7d0b1453cd..ee33d628a240 100644 --- a/fs/xfs/libxfs/xfs_fs.h +++ b/fs/xfs/libxfs/xfs_fs.h | |||
@@ -268,6 +268,19 @@ typedef struct xfs_fsop_resblks { | |||
268 | (s)->sb_agblocks + XFS_MIN_AG_BLOCKS) | 268 | (s)->sb_agblocks + XFS_MIN_AG_BLOCKS) |
269 | 269 | ||
270 | /* | 270 | /* |
271 | * Output for XFS_IOC_AG_GEOMETRY | ||
272 | */ | ||
273 | struct xfs_ag_geometry { | ||
274 | uint32_t ag_number; /* i/o: AG number */ | ||
275 | uint32_t ag_length; /* o: length in blocks */ | ||
276 | uint32_t ag_freeblks; /* o: free space */ | ||
277 | uint32_t ag_icount; /* o: inodes allocated */ | ||
278 | uint32_t ag_ifree; /* o: inodes free */ | ||
279 | uint32_t ag_reserved32; /* o: zero */ | ||
280 | uint64_t ag_reserved[13];/* o: zero */ | ||
281 | }; | ||
282 | |||
283 | /* | ||
271 | * Structures for XFS_IOC_FSGROWFSDATA, XFS_IOC_FSGROWFSLOG & XFS_IOC_FSGROWFSRT | 284 | * Structures for XFS_IOC_FSGROWFSDATA, XFS_IOC_FSGROWFSLOG & XFS_IOC_FSGROWFSRT |
272 | */ | 285 | */ |
273 | typedef struct xfs_growfs_data { | 286 | typedef struct xfs_growfs_data { |
@@ -620,6 +633,7 @@ struct xfs_scrub_metadata { | |||
620 | #define XFS_IOC_FREE_EOFBLOCKS _IOR ('X', 58, struct xfs_fs_eofblocks) | 633 | #define XFS_IOC_FREE_EOFBLOCKS _IOR ('X', 58, struct xfs_fs_eofblocks) |
621 | /* XFS_IOC_GETFSMAP ------ hoisted 59 */ | 634 | /* XFS_IOC_GETFSMAP ------ hoisted 59 */ |
622 | #define XFS_IOC_SCRUB_METADATA _IOWR('X', 60, struct xfs_scrub_metadata) | 635 | #define XFS_IOC_SCRUB_METADATA _IOWR('X', 60, struct xfs_scrub_metadata) |
636 | #define XFS_IOC_AG_GEOMETRY _IOWR('X', 61, struct xfs_ag_geometry) | ||
623 | 637 | ||
624 | /* | 638 | /* |
625 | * ioctl commands that replace IRIX syssgi()'s | 639 | * ioctl commands that replace IRIX syssgi()'s |
diff --git a/fs/xfs/xfs_ioctl.c b/fs/xfs/xfs_ioctl.c index ec3c6c401ee7..b36abd453709 100644 --- a/fs/xfs/xfs_ioctl.c +++ b/fs/xfs/xfs_ioctl.c | |||
@@ -33,6 +33,7 @@ | |||
33 | #include "xfs_fsmap.h" | 33 | #include "xfs_fsmap.h" |
34 | #include "scrub/xfs_scrub.h" | 34 | #include "scrub/xfs_scrub.h" |
35 | #include "xfs_sb.h" | 35 | #include "xfs_sb.h" |
36 | #include "xfs_ag.h" | ||
36 | 37 | ||
37 | #include <linux/capability.h> | 38 | #include <linux/capability.h> |
38 | #include <linux/cred.h> | 39 | #include <linux/cred.h> |
@@ -804,6 +805,26 @@ xfs_ioc_fsgeometry( | |||
804 | return 0; | 805 | return 0; |
805 | } | 806 | } |
806 | 807 | ||
808 | STATIC int | ||
809 | xfs_ioc_ag_geometry( | ||
810 | struct xfs_mount *mp, | ||
811 | void __user *arg) | ||
812 | { | ||
813 | struct xfs_ag_geometry ageo; | ||
814 | int error; | ||
815 | |||
816 | if (copy_from_user(&ageo, arg, sizeof(ageo))) | ||
817 | return -EFAULT; | ||
818 | |||
819 | error = xfs_ag_get_geometry(mp, ageo.ag_number, &ageo); | ||
820 | if (error) | ||
821 | return error; | ||
822 | |||
823 | if (copy_to_user(arg, &ageo, sizeof(ageo))) | ||
824 | return -EFAULT; | ||
825 | return 0; | ||
826 | } | ||
827 | |||
807 | /* | 828 | /* |
808 | * Linux extended inode flags interface. | 829 | * Linux extended inode flags interface. |
809 | */ | 830 | */ |
@@ -1930,6 +1951,9 @@ xfs_file_ioctl( | |||
1930 | case XFS_IOC_FSGEOMETRY: | 1951 | case XFS_IOC_FSGEOMETRY: |
1931 | return xfs_ioc_fsgeometry(mp, arg, 5); | 1952 | return xfs_ioc_fsgeometry(mp, arg, 5); |
1932 | 1953 | ||
1954 | case XFS_IOC_AG_GEOMETRY: | ||
1955 | return xfs_ioc_ag_geometry(mp, arg); | ||
1956 | |||
1933 | case XFS_IOC_GETVERSION: | 1957 | case XFS_IOC_GETVERSION: |
1934 | return put_user(inode->i_generation, (int __user *)arg); | 1958 | return put_user(inode->i_generation, (int __user *)arg); |
1935 | 1959 | ||
diff --git a/fs/xfs/xfs_ioctl32.c b/fs/xfs/xfs_ioctl32.c index 55ace6308637..65997a6315e9 100644 --- a/fs/xfs/xfs_ioctl32.c +++ b/fs/xfs/xfs_ioctl32.c | |||
@@ -563,6 +563,7 @@ xfs_file_compat_ioctl( | |||
563 | case XFS_IOC_DIOINFO: | 563 | case XFS_IOC_DIOINFO: |
564 | case XFS_IOC_FSGEOMETRY_V4: | 564 | case XFS_IOC_FSGEOMETRY_V4: |
565 | case XFS_IOC_FSGEOMETRY: | 565 | case XFS_IOC_FSGEOMETRY: |
566 | case XFS_IOC_AG_GEOMETRY: | ||
566 | case XFS_IOC_FSGETXATTR: | 567 | case XFS_IOC_FSGETXATTR: |
567 | case XFS_IOC_FSSETXATTR: | 568 | case XFS_IOC_FSSETXATTR: |
568 | case XFS_IOC_FSGETXATTRA: | 569 | case XFS_IOC_FSGETXATTRA: |