LCOV - code coverage report
Current view: top level - fs/xfs/libxfs - xfs_rtgroup.h (source / functions) Hit Total Coverage
Test: fstests of 6.5.0-rc4-xfsa @ Mon Jul 31 20:08:27 PDT 2023 Lines: 31 32 96.9 %
Date: 2023-07-31 20:08:27 Functions: 5 5 100.0 %

          Line data    Source code
       1             : /* SPDX-License-Identifier: GPL-2.0-or-later */
       2             : /*
       3             :  * Copyright (C) 2022-2023 Oracle.  All Rights Reserved.
       4             :  * Author: Darrick J. Wong <djwong@kernel.org>
       5             :  */
       6             : #ifndef __LIBXFS_RTGROUP_H
       7             : #define __LIBXFS_RTGROUP_H 1
       8             : 
       9             : struct xfs_mount;
      10             : struct xfs_trans;
      11             : 
      12             : /*
      13             :  * Realtime group incore structure, similar to the per-AG structure.
      14             :  */
      15             : struct xfs_rtgroup {
      16             :         struct xfs_mount        *rtg_mount;
      17             :         xfs_rgnumber_t          rtg_rgno;
      18             :         atomic_t                rtg_ref;        /* passive reference count */
      19             :         atomic_t                rtg_active_ref; /* active reference count */
      20             :         wait_queue_head_t       rtg_active_wq;/* woken active_ref falls to zero */
      21             : 
      22             :         /* for rcu-safe freeing */
      23             :         struct rcu_head         rcu_head;
      24             : 
      25             :         /* reverse mapping btree inode */
      26             :         struct xfs_inode        *rtg_rmapip;
      27             : 
      28             :         /* refcount btree inode */
      29             :         struct xfs_inode        *rtg_refcountip;
      30             : 
      31             :         /* Number of blocks in this group */
      32             :         xfs_rgblock_t           rtg_blockcount;
      33             : 
      34             :         /*
      35             :          * Bitsets of per-rtgroup metadata that have been checked and/or are
      36             :          * sick.  Callers should hold rtg_state_lock before accessing this
      37             :          * field.
      38             :          */
      39             :         uint16_t                rtg_checked;
      40             :         uint16_t                rtg_sick;
      41             : 
      42             : #ifdef __KERNEL__
      43             :         /* -- kernel only structures below this line -- */
      44             :         spinlock_t              rtg_state_lock;
      45             : 
      46             :         /*
      47             :          * We use xfs_drain to track the number of deferred log intent items
      48             :          * that have been queued (but not yet processed) so that waiters (e.g.
      49             :          * scrub) will not lock resources when other threads are in the middle
      50             :          * of processing a chain of intent items only to find momentary
      51             :          * inconsistencies.
      52             :          */
      53             :         struct xfs_defer_drain  rtg_intents_drain;
      54             : 
      55             :         /* Hook to feed rt rmapbt updates to an active online repair. */
      56             :         struct xfs_hooks        rtg_rmap_update_hooks;
      57             : #endif /* __KERNEL__ */
      58             : };
      59             : 
      60             : #ifdef CONFIG_XFS_RT
      61             : /* Passive rtgroup references */
      62             : struct xfs_rtgroup *xfs_rtgroup_get(struct xfs_mount *mp, xfs_rgnumber_t rgno);
      63             : struct xfs_rtgroup *xfs_rtgroup_hold(struct xfs_rtgroup *rtg);
      64             : void xfs_rtgroup_put(struct xfs_rtgroup *rtg);
      65             : 
      66             : /* Active rtgroup references */
      67             : struct xfs_rtgroup *xfs_rtgroup_grab(struct xfs_mount *mp, xfs_rgnumber_t rgno);
      68             : void xfs_rtgroup_rele(struct xfs_rtgroup *rtg);
      69             : 
      70             : int xfs_initialize_rtgroups(struct xfs_mount *mp, xfs_rgnumber_t rgcount);
      71             : void xfs_free_rtgroups(struct xfs_mount *mp);
      72             : #else
      73             : static inline struct xfs_rtgroup *
      74             : xfs_rtgroup_get(
      75             :         struct xfs_mount        *mp,
      76             :         xfs_rgnumber_t          rgno)
      77             : {
      78             :         return NULL;
      79             : }
      80             : static inline struct xfs_rtgroup *
      81             : xfs_rtgroup_hold(struct xfs_rtgroup *rtg)
      82             : {
      83             :         ASSERT(rtg == NULL);
      84             :         return NULL;
      85             : }
      86             : # define xfs_rtgroup_grab                       xfs_rtgroup_get
      87             : # define xfs_rtgroup_put(rtg)                   ((void)0)
      88             : # define xfs_rtgroup_rele(rtg)                  ((void)0)
      89             : # define xfs_initialize_rtgroups(mp, rgcount)   (0)
      90             : # define xfs_free_rtgroups(mp)                  ((void)0)
      91             : #endif /* CONFIG_XFS_RT */
      92             : 
      93             : /*
      94             :  * rt group iteration APIs
      95             :  */
      96             : static inline struct xfs_rtgroup *
      97     1155849 : xfs_rtgroup_next(
      98             :         struct xfs_rtgroup      *rtg,
      99             :         xfs_rgnumber_t          *rgno,
     100             :         xfs_rgnumber_t          end_rgno)
     101             : {
     102     1155849 :         struct xfs_mount        *mp = rtg->rtg_mount;
     103             : 
     104     1155849 :         *rgno = rtg->rtg_rgno + 1;
     105     1155849 :         xfs_rtgroup_rele(rtg);
     106     1155854 :         if (*rgno > end_rgno)
     107             :                 return NULL;
     108      932350 :         return xfs_rtgroup_grab(mp, *rgno);
     109             : }
     110             : 
     111             : #define for_each_rtgroup_range(mp, rgno, end_rgno, rtg) \
     112             :         for ((rtg) = xfs_rtgroup_grab((mp), (rgno)); \
     113             :                 (rtg) != NULL; \
     114             :                 (rtg) = xfs_rtgroup_next((rtg), &(rgno), (end_rgno)))
     115             : 
     116             : #define for_each_rtgroup_from(mp, rgno, rtg) \
     117             :         for_each_rtgroup_range((mp), (rgno), (mp)->m_sb.sb_rgcount - 1, (rtg))
     118             : 
     119             : 
     120             : #define for_each_rtgroup(mp, rgno, rtg) \
     121             :         (rgno) = 0; \
     122             :         for_each_rtgroup_from((mp), (rgno), (rtg))
     123             : 
     124             : static inline bool
     125             : xfs_verify_rgbno(
     126             :         struct xfs_rtgroup      *rtg,
     127             :         xfs_rgblock_t           rgbno)
     128             : {
     129 89149617476 :         if (rgbno >= rtg->rtg_blockcount)
     130             :                 return false;
     131 89149617476 :         if (rgbno < rtg->rtg_mount->m_sb.sb_rextsize)
     132           0 :                 return false;
     133             :         return true;
     134             : }
     135             : 
     136             : static inline bool
     137 44574808738 : xfs_verify_rgbext(
     138             :         struct xfs_rtgroup      *rtg,
     139             :         xfs_rgblock_t           rgbno,
     140             :         xfs_rgblock_t           len)
     141             : {
     142 44574808738 :         if (rgbno + len <= rgbno)
     143             :                 return false;
     144             : 
     145 44574808738 :         if (!xfs_verify_rgbno(rtg, rgbno))
     146             :                 return false;
     147             : 
     148 44574808738 :         return xfs_verify_rgbno(rtg, rgbno + len - 1);
     149             : }
     150             : 
     151             : static inline xfs_rtblock_t
     152   715057826 : xfs_rgbno_to_rtb(
     153             :         struct xfs_mount        *mp,
     154             :         xfs_rgnumber_t          rgno,
     155             :         xfs_rgblock_t           rgbno)
     156             : {
     157   715057826 :         ASSERT(xfs_has_rtgroups(mp));
     158             : 
     159   715057826 :         if (mp->m_rgblklog >= 0)
     160   715057684 :                 return ((xfs_rtblock_t)rgno << mp->m_rgblklog) | rgbno;
     161             : 
     162         142 :         return ((xfs_rtblock_t)rgno * mp->m_sb.sb_rgblocks) + rgbno;
     163             : }
     164             : 
     165             : static inline xfs_rgnumber_t
     166  1128996828 : xfs_rtb_to_rgno(
     167             :         struct xfs_mount        *mp,
     168             :         xfs_rtblock_t           rtbno)
     169             : {
     170  1128996828 :         ASSERT(xfs_has_rtgroups(mp));
     171             : 
     172  1128996828 :         if (mp->m_rgblklog >= 0)
     173  1128995720 :                 return rtbno >> mp->m_rgblklog;
     174             : 
     175        1108 :         return div_u64(rtbno, mp->m_sb.sb_rgblocks);
     176             : }
     177             : 
     178             : static inline xfs_rgblock_t
     179  1164613387 : xfs_rtb_to_rgbno(
     180             :         struct xfs_mount        *mp,
     181             :         xfs_rtblock_t           rtbno,
     182             :         xfs_rgnumber_t          *rgno)
     183             : {
     184  1164613387 :         uint32_t                rem;
     185             : 
     186  1164613387 :         ASSERT(xfs_has_rtgroups(mp));
     187             : 
     188  1164613387 :         if (mp->m_rgblklog >= 0) {
     189  1164612141 :                 *rgno = rtbno >> mp->m_rgblklog;
     190  1164612141 :                 return rtbno & mp->m_rgblkmask;
     191             :         }
     192             : 
     193        1246 :         *rgno = div_u64_rem(rtbno, mp->m_sb.sb_rgblocks, &rem);
     194        1246 :         return rem;
     195             : }
     196             : 
     197             : static inline xfs_daddr_t
     198             : xfs_rtb_to_daddr(
     199             :         struct xfs_mount        *mp,
     200             :         xfs_rtblock_t           rtbno)
     201             : {
     202    28214210 :         return rtbno << mp->m_blkbb_log;
     203             : }
     204             : 
     205             : static inline xfs_rtblock_t
     206             : xfs_daddr_to_rtb(
     207             :         struct xfs_mount        *mp,
     208             :         xfs_daddr_t             daddr)
     209             : {
     210             :         return daddr >> mp->m_blkbb_log;
     211             : }
     212             : 
     213             : static inline xfs_rgnumber_t
     214             : xfs_daddr_to_rgno(
     215             :         struct xfs_mount        *mp,
     216             :         xfs_daddr_t             daddr)
     217             : {
     218             :         xfs_rtblock_t           rtb = daddr >> mp->m_blkbb_log;
     219             : 
     220             :         return xfs_rtb_to_rgno(mp, rtb);
     221             : }
     222             : 
     223             : static inline xfs_rgblock_t
     224             : xfs_daddr_to_rgbno(
     225             :         struct xfs_mount        *mp,
     226             :         xfs_daddr_t             daddr)
     227             : {
     228             :         xfs_rtblock_t           rtb = daddr >> mp->m_blkbb_log;
     229             :         xfs_rgnumber_t          rgno;
     230             : 
     231             :         return xfs_rtb_to_rgbno(mp, rtb, &rgno);
     232             : }
     233             : 
     234             : #ifdef CONFIG_XFS_RT
     235             : xfs_rgblock_t xfs_rtgroup_block_count(struct xfs_mount *mp,
     236             :                 xfs_rgnumber_t rgno);
     237             : 
     238             : void xfs_rtgroup_update_super(struct xfs_buf *rtsb_bp,
     239             :                 const struct xfs_buf *sb_bp);
     240             : void xfs_rtgroup_log_super(struct xfs_trans *tp, const struct xfs_buf *sb_bp);
     241             : int xfs_rtgroup_update_secondary_sbs(struct xfs_mount *mp);
     242             : int xfs_rtgroup_init_secondary_super(struct xfs_mount *mp, xfs_rgnumber_t rgno,
     243             :                 struct xfs_buf **bpp);
     244             : 
     245             : /* Lock the rt bitmap inode in exclusive mode */
     246             : #define XFS_RTGLOCK_BITMAP              (1U << 0)
     247             : /* Lock the rt bitmap inode in shared mode */
     248             : #define XFS_RTGLOCK_BITMAP_SHARED       (1U << 1)
     249             : /* Lock the rt rmap inode in exclusive mode */
     250             : #define XFS_RTGLOCK_RMAP                (1U << 2)
     251             : /* Lock the rt refcount inode in exclusive mode */
     252             : #define XFS_RTGLOCK_REFCOUNT            (1U << 3)
     253             : 
     254             : #define XFS_RTGLOCK_ALL_FLAGS   (XFS_RTGLOCK_BITMAP | \
     255             :                                  XFS_RTGLOCK_BITMAP_SHARED | \
     256             :                                  XFS_RTGLOCK_RMAP | \
     257             :                                  XFS_RTGLOCK_REFCOUNT)
     258             : 
     259             : void xfs_rtgroup_lock(struct xfs_trans *tp, struct xfs_rtgroup *rtg,
     260             :                 unsigned int rtglock_flags);
     261             : void xfs_rtgroup_unlock(struct xfs_rtgroup *rtg, unsigned int rtglock_flags);
     262             : 
     263             : int xfs_rtgroup_get_geometry(struct xfs_rtgroup *rtg,
     264             :                 struct xfs_rtgroup_geometry *rgeo);
     265             : #else
     266             : # define xfs_rtgroup_block_count(mp, rgno)      (0)
     267             : # define xfs_rtgroup_update_super(bp, sb_bp)    ((void)0)
     268             : # define xfs_rtgroup_log_super(tp, sb_bp)       ((void)0)
     269             : # define xfs_rtgroup_update_secondary_sbs(mp)   (0)
     270             : # define xfs_rtgroup_init_secondary_super(mp, rgno, bpp)        (-EOPNOTSUPP)
     271             : # define xfs_rtgroup_lock(tp, rtg, gf)          ((void)0)
     272             : # define xfs_rtgroup_unlock(rtg, gf)            ((void)0)
     273             : # define xfs_rtgroup_get_geometry(rtg, rgeo)    (-EOPNOTSUPP)
     274             : #endif /* CONFIG_XFS_RT */
     275             : 
     276             : #endif /* __LIBXFS_RTGROUP_H */

Generated by: LCOV version 1.14