xfs: rmap btree add more reserved blocks
Originally-From: Dave Chinner <dchinner@redhat.com> XFS reserves a small amount of space in each AG for the minimum number of free blocks needed for operation. Adding the rmap btree increases the number of reserved blocks, but it also increases the complexity of the calculation as the free inode btree is optional (like the rmbt). Rather than calculate the prealloc blocks every time we need to check it, add a function to calculate it at mount time and store it in the struct xfs_mount, and convert the XFS_PREALLOC_BLOCKS macro just to use the xfs-mount variable directly. Signed-off-by: Dave Chinner <dchinner@redhat.com> Reviewed-by: Brian Foster <bfoster@redhat.com> Signed-off-by: Dave Chinner <david@fromorbit.com>
This commit is contained in:
parent
00f4e4f907
commit
8018026ef2
|
@ -50,6 +50,17 @@ STATIC int xfs_alloc_ag_vextent_size(xfs_alloc_arg_t *);
|
||||||
STATIC int xfs_alloc_ag_vextent_small(xfs_alloc_arg_t *,
|
STATIC int xfs_alloc_ag_vextent_small(xfs_alloc_arg_t *,
|
||||||
xfs_btree_cur_t *, xfs_agblock_t *, xfs_extlen_t *, int *);
|
xfs_btree_cur_t *, xfs_agblock_t *, xfs_extlen_t *, int *);
|
||||||
|
|
||||||
|
xfs_extlen_t
|
||||||
|
xfs_prealloc_blocks(
|
||||||
|
struct xfs_mount *mp)
|
||||||
|
{
|
||||||
|
if (xfs_sb_version_hasrmapbt(&mp->m_sb))
|
||||||
|
return XFS_RMAP_BLOCK(mp) + 1;
|
||||||
|
if (xfs_sb_version_hasfinobt(&mp->m_sb))
|
||||||
|
return XFS_FIBT_BLOCK(mp) + 1;
|
||||||
|
return XFS_IBT_BLOCK(mp) + 1;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Lookup the record equal to [bno, len] in the btree given by cur.
|
* Lookup the record equal to [bno, len] in the btree given by cur.
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -232,4 +232,6 @@ int xfs_alloc_fix_freelist(struct xfs_alloc_arg *args, int flags);
|
||||||
int xfs_free_extent_fix_freelist(struct xfs_trans *tp, xfs_agnumber_t agno,
|
int xfs_free_extent_fix_freelist(struct xfs_trans *tp, xfs_agnumber_t agno,
|
||||||
struct xfs_buf **agbp);
|
struct xfs_buf **agbp);
|
||||||
|
|
||||||
|
xfs_extlen_t xfs_prealloc_blocks(struct xfs_mount *mp);
|
||||||
|
|
||||||
#endif /* __XFS_ALLOC_H__ */
|
#endif /* __XFS_ALLOC_H__ */
|
||||||
|
|
|
@ -1319,18 +1319,11 @@ typedef __be32 xfs_inobt_ptr_t;
|
||||||
*/
|
*/
|
||||||
#define XFS_RMAP_CRC_MAGIC 0x524d4233 /* 'RMB3' */
|
#define XFS_RMAP_CRC_MAGIC 0x524d4233 /* 'RMB3' */
|
||||||
|
|
||||||
/*
|
#define XFS_RMAP_BLOCK(mp) \
|
||||||
* The first data block of an AG depends on whether the filesystem was formatted
|
|
||||||
* with the finobt feature. If so, account for the finobt reserved root btree
|
|
||||||
* block.
|
|
||||||
*/
|
|
||||||
#define XFS_PREALLOC_BLOCKS(mp) \
|
|
||||||
(xfs_sb_version_hasfinobt(&((mp)->m_sb)) ? \
|
(xfs_sb_version_hasfinobt(&((mp)->m_sb)) ? \
|
||||||
XFS_FIBT_BLOCK(mp) + 1 : \
|
XFS_FIBT_BLOCK(mp) + 1 : \
|
||||||
XFS_IBT_BLOCK(mp) + 1)
|
XFS_IBT_BLOCK(mp) + 1)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* BMAP Btree format definitions
|
* BMAP Btree format definitions
|
||||||
*
|
*
|
||||||
|
|
|
@ -243,7 +243,7 @@ xfs_growfs_data_private(
|
||||||
agf->agf_flfirst = cpu_to_be32(1);
|
agf->agf_flfirst = cpu_to_be32(1);
|
||||||
agf->agf_fllast = 0;
|
agf->agf_fllast = 0;
|
||||||
agf->agf_flcount = 0;
|
agf->agf_flcount = 0;
|
||||||
tmpsize = agsize - XFS_PREALLOC_BLOCKS(mp);
|
tmpsize = agsize - mp->m_ag_prealloc_blocks;
|
||||||
agf->agf_freeblks = cpu_to_be32(tmpsize);
|
agf->agf_freeblks = cpu_to_be32(tmpsize);
|
||||||
agf->agf_longest = cpu_to_be32(tmpsize);
|
agf->agf_longest = cpu_to_be32(tmpsize);
|
||||||
if (xfs_sb_version_hascrc(&mp->m_sb))
|
if (xfs_sb_version_hascrc(&mp->m_sb))
|
||||||
|
@ -340,7 +340,7 @@ xfs_growfs_data_private(
|
||||||
agno, 0);
|
agno, 0);
|
||||||
|
|
||||||
arec = XFS_ALLOC_REC_ADDR(mp, XFS_BUF_TO_BLOCK(bp), 1);
|
arec = XFS_ALLOC_REC_ADDR(mp, XFS_BUF_TO_BLOCK(bp), 1);
|
||||||
arec->ar_startblock = cpu_to_be32(XFS_PREALLOC_BLOCKS(mp));
|
arec->ar_startblock = cpu_to_be32(mp->m_ag_prealloc_blocks);
|
||||||
arec->ar_blockcount = cpu_to_be32(
|
arec->ar_blockcount = cpu_to_be32(
|
||||||
agsize - be32_to_cpu(arec->ar_startblock));
|
agsize - be32_to_cpu(arec->ar_startblock));
|
||||||
|
|
||||||
|
@ -369,7 +369,7 @@ xfs_growfs_data_private(
|
||||||
agno, 0);
|
agno, 0);
|
||||||
|
|
||||||
arec = XFS_ALLOC_REC_ADDR(mp, XFS_BUF_TO_BLOCK(bp), 1);
|
arec = XFS_ALLOC_REC_ADDR(mp, XFS_BUF_TO_BLOCK(bp), 1);
|
||||||
arec->ar_startblock = cpu_to_be32(XFS_PREALLOC_BLOCKS(mp));
|
arec->ar_startblock = cpu_to_be32(mp->m_ag_prealloc_blocks);
|
||||||
arec->ar_blockcount = cpu_to_be32(
|
arec->ar_blockcount = cpu_to_be32(
|
||||||
agsize - be32_to_cpu(arec->ar_startblock));
|
agsize - be32_to_cpu(arec->ar_startblock));
|
||||||
nfree += be32_to_cpu(arec->ar_blockcount);
|
nfree += be32_to_cpu(arec->ar_blockcount);
|
||||||
|
|
|
@ -231,6 +231,8 @@ xfs_initialize_perag(
|
||||||
|
|
||||||
if (maxagi)
|
if (maxagi)
|
||||||
*maxagi = index;
|
*maxagi = index;
|
||||||
|
|
||||||
|
mp->m_ag_prealloc_blocks = xfs_prealloc_blocks(mp);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
out_unwind:
|
out_unwind:
|
||||||
|
|
|
@ -119,6 +119,7 @@ typedef struct xfs_mount {
|
||||||
uint m_ag_maxlevels; /* XFS_AG_MAXLEVELS */
|
uint m_ag_maxlevels; /* XFS_AG_MAXLEVELS */
|
||||||
uint m_bm_maxlevels[2]; /* XFS_BM_MAXLEVELS */
|
uint m_bm_maxlevels[2]; /* XFS_BM_MAXLEVELS */
|
||||||
uint m_in_maxlevels; /* max inobt btree levels. */
|
uint m_in_maxlevels; /* max inobt btree levels. */
|
||||||
|
xfs_extlen_t m_ag_prealloc_blocks; /* reserved ag blocks */
|
||||||
struct radix_tree_root m_perag_tree; /* per-ag accounting info */
|
struct radix_tree_root m_perag_tree; /* per-ag accounting info */
|
||||||
spinlock_t m_perag_lock; /* lock for m_perag_tree */
|
spinlock_t m_perag_lock; /* lock for m_perag_tree */
|
||||||
struct mutex m_growlock; /* growfs mutex */
|
struct mutex m_growlock; /* growfs mutex */
|
||||||
|
|
Loading…
Reference in New Issue