Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0+
0002 /*
0003  * Copyright (C) 2016 Oracle.  All Rights Reserved.
0004  * Author: Darrick J. Wong <darrick.wong@oracle.com>
0005  */
0006 #ifndef __XFS_REFCOUNT_H__
0007 #define __XFS_REFCOUNT_H__
0008 
0009 struct xfs_trans;
0010 struct xfs_mount;
0011 struct xfs_perag;
0012 struct xfs_btree_cur;
0013 struct xfs_bmbt_irec;
0014 struct xfs_refcount_irec;
0015 
0016 extern int xfs_refcount_lookup_le(struct xfs_btree_cur *cur,
0017         xfs_agblock_t bno, int *stat);
0018 extern int xfs_refcount_lookup_ge(struct xfs_btree_cur *cur,
0019         xfs_agblock_t bno, int *stat);
0020 extern int xfs_refcount_lookup_eq(struct xfs_btree_cur *cur,
0021         xfs_agblock_t bno, int *stat);
0022 extern int xfs_refcount_get_rec(struct xfs_btree_cur *cur,
0023         struct xfs_refcount_irec *irec, int *stat);
0024 
0025 enum xfs_refcount_intent_type {
0026     XFS_REFCOUNT_INCREASE = 1,
0027     XFS_REFCOUNT_DECREASE,
0028     XFS_REFCOUNT_ALLOC_COW,
0029     XFS_REFCOUNT_FREE_COW,
0030 };
0031 
0032 struct xfs_refcount_intent {
0033     struct list_head            ri_list;
0034     enum xfs_refcount_intent_type       ri_type;
0035     xfs_extlen_t                ri_blockcount;
0036     xfs_fsblock_t               ri_startblock;
0037 };
0038 
0039 void xfs_refcount_increase_extent(struct xfs_trans *tp,
0040         struct xfs_bmbt_irec *irec);
0041 void xfs_refcount_decrease_extent(struct xfs_trans *tp,
0042         struct xfs_bmbt_irec *irec);
0043 
0044 extern void xfs_refcount_finish_one_cleanup(struct xfs_trans *tp,
0045         struct xfs_btree_cur *rcur, int error);
0046 extern int xfs_refcount_finish_one(struct xfs_trans *tp,
0047         enum xfs_refcount_intent_type type, xfs_fsblock_t startblock,
0048         xfs_extlen_t blockcount, xfs_fsblock_t *new_fsb,
0049         xfs_extlen_t *new_len, struct xfs_btree_cur **pcur);
0050 
0051 extern int xfs_refcount_find_shared(struct xfs_btree_cur *cur,
0052         xfs_agblock_t agbno, xfs_extlen_t aglen, xfs_agblock_t *fbno,
0053         xfs_extlen_t *flen, bool find_end_of_shared);
0054 
0055 void xfs_refcount_alloc_cow_extent(struct xfs_trans *tp, xfs_fsblock_t fsb,
0056         xfs_extlen_t len);
0057 void xfs_refcount_free_cow_extent(struct xfs_trans *tp, xfs_fsblock_t fsb,
0058         xfs_extlen_t len);
0059 extern int xfs_refcount_recover_cow_leftovers(struct xfs_mount *mp,
0060         struct xfs_perag *pag);
0061 
0062 /*
0063  * While we're adjusting the refcounts records of an extent, we have
0064  * to keep an eye on the number of extents we're dirtying -- run too
0065  * many in a single transaction and we'll exceed the transaction's
0066  * reservation and crash the fs.  Each record adds 12 bytes to the
0067  * log (plus any key updates) so we'll conservatively assume 32 bytes
0068  * per record.  We must also leave space for btree splits on both ends
0069  * of the range and space for the CUD and a new CUI.
0070  *
0071  * Each EFI that we attach to the transaction is assumed to consume ~32 bytes.
0072  * This is a low estimate for an EFI tracking a single extent (16 bytes for the
0073  * EFI header, 16 for the extent, and 12 for the xlog op header), but the
0074  * estimate is acceptable if there's more than one extent being freed.
0075  * In the worst case of freeing every other block during a refcount decrease
0076  * operation, we amortize the space used for one EFI log item across 16
0077  * extents.
0078  */
0079 #define XFS_REFCOUNT_ITEM_OVERHEAD  32
0080 
0081 extern int xfs_refcount_has_record(struct xfs_btree_cur *cur,
0082         xfs_agblock_t bno, xfs_extlen_t len, bool *exists);
0083 union xfs_btree_rec;
0084 extern void xfs_refcount_btrec_to_irec(const union xfs_btree_rec *rec,
0085         struct xfs_refcount_irec *irec);
0086 extern int xfs_refcount_insert(struct xfs_btree_cur *cur,
0087         struct xfs_refcount_irec *irec, int *stat);
0088 
0089 extern struct kmem_cache    *xfs_refcount_intent_cache;
0090 
0091 int __init xfs_refcount_intent_init_cache(void);
0092 void xfs_refcount_intent_destroy_cache(void);
0093 
0094 #endif  /* __XFS_REFCOUNT_H__ */