Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

at v6.19 453 lines 12 kB view raw
1// SPDX-License-Identifier: GPL-2.0 2/* 3 * Copyright (c) 2000-2003,2005 Silicon Graphics, Inc. 4 * All Rights Reserved. 5 */ 6#ifndef __XFS_RTBITMAP_H__ 7#define __XFS_RTBITMAP_H__ 8 9#include "xfs_rtgroup.h" 10 11struct xfs_rtalloc_args { 12 struct xfs_rtgroup *rtg; 13 struct xfs_mount *mp; 14 struct xfs_trans *tp; 15 16 struct xfs_buf *rbmbp; /* bitmap block buffer */ 17 struct xfs_buf *sumbp; /* summary block buffer */ 18 19 xfs_fileoff_t rbmoff; /* bitmap block number */ 20 xfs_fileoff_t sumoff; /* summary block number */ 21}; 22 23static inline xfs_rtblock_t 24xfs_rtx_to_rtb( 25 struct xfs_rtgroup *rtg, 26 xfs_rtxnum_t rtx) 27{ 28 struct xfs_mount *mp = rtg_mount(rtg); 29 xfs_rtblock_t start = xfs_group_start_fsb(rtg_group(rtg)); 30 31 if (mp->m_rtxblklog >= 0) 32 return start + (rtx << mp->m_rtxblklog); 33 return start + (rtx * mp->m_sb.sb_rextsize); 34} 35 36/* Convert an rgbno into an rt extent number. */ 37static inline xfs_rtxnum_t 38xfs_rgbno_to_rtx( 39 struct xfs_mount *mp, 40 xfs_rgblock_t rgbno) 41{ 42 if (likely(mp->m_rtxblklog >= 0)) 43 return rgbno >> mp->m_rtxblklog; 44 return rgbno / mp->m_sb.sb_rextsize; 45} 46 47static inline uint64_t 48xfs_rtbxlen_to_blen( 49 struct xfs_mount *mp, 50 xfs_rtbxlen_t rtbxlen) 51{ 52 if (mp->m_rtxblklog >= 0) 53 return rtbxlen << mp->m_rtxblklog; 54 55 return rtbxlen * mp->m_sb.sb_rextsize; 56} 57 58static inline xfs_extlen_t 59xfs_rtxlen_to_extlen( 60 struct xfs_mount *mp, 61 xfs_rtxlen_t rtxlen) 62{ 63 if (mp->m_rtxblklog >= 0) 64 return rtxlen << mp->m_rtxblklog; 65 66 return rtxlen * mp->m_sb.sb_rextsize; 67} 68 69/* Compute the misalignment between an extent length and a realtime extent .*/ 70static inline unsigned int 71xfs_extlen_to_rtxmod( 72 struct xfs_mount *mp, 73 xfs_extlen_t len) 74{ 75 if (mp->m_rtxblklog >= 0) 76 return len & mp->m_rtxblkmask; 77 78 return len % mp->m_sb.sb_rextsize; 79} 80 81static inline xfs_rtxlen_t 82xfs_extlen_to_rtxlen( 83 struct xfs_mount *mp, 84 xfs_extlen_t len) 85{ 86 if (mp->m_rtxblklog >= 0) 87 return len >> mp->m_rtxblklog; 88 89 return len / mp->m_sb.sb_rextsize; 90} 91 92/* Convert an rt block count into an rt extent count. */ 93static inline xfs_rtbxlen_t 94xfs_blen_to_rtbxlen( 95 struct xfs_mount *mp, 96 uint64_t blen) 97{ 98 if (likely(mp->m_rtxblklog >= 0)) 99 return blen >> mp->m_rtxblklog; 100 101 return div_u64(blen, mp->m_sb.sb_rextsize); 102} 103 104/* Return the offset of a file block length within an rt extent. */ 105static inline xfs_extlen_t 106xfs_blen_to_rtxoff( 107 struct xfs_mount *mp, 108 xfs_filblks_t blen) 109{ 110 if (likely(mp->m_rtxblklog >= 0)) 111 return blen & mp->m_rtxblkmask; 112 113 return do_div(blen, mp->m_sb.sb_rextsize); 114} 115 116/* Round this block count up to the nearest rt extent size. */ 117static inline xfs_filblks_t 118xfs_blen_roundup_rtx( 119 struct xfs_mount *mp, 120 xfs_filblks_t blen) 121{ 122 return roundup_64(blen, mp->m_sb.sb_rextsize); 123} 124 125/* Convert an rt block number into an rt extent number. */ 126static inline xfs_rtxnum_t 127xfs_rtb_to_rtx( 128 struct xfs_mount *mp, 129 xfs_rtblock_t rtbno) 130{ 131 /* open-coded 64-bit masking operation */ 132 rtbno &= mp->m_groups[XG_TYPE_RTG].blkmask; 133 if (likely(mp->m_rtxblklog >= 0)) 134 return rtbno >> mp->m_rtxblklog; 135 return div_u64(rtbno, mp->m_sb.sb_rextsize); 136} 137 138/* Return the offset of a rtgroup block number within an rt extent. */ 139static inline xfs_extlen_t 140xfs_rgbno_to_rtxoff( 141 struct xfs_mount *mp, 142 xfs_rgblock_t rgbno) 143{ 144 return rgbno % mp->m_sb.sb_rextsize; 145} 146 147/* Return the offset of an rt block number within an rt extent. */ 148static inline xfs_extlen_t 149xfs_rtb_to_rtxoff( 150 struct xfs_mount *mp, 151 xfs_rtblock_t rtbno) 152{ 153 /* open-coded 64-bit masking operation */ 154 rtbno &= mp->m_groups[XG_TYPE_RTG].blkmask; 155 if (likely(mp->m_rtxblklog >= 0)) 156 return rtbno & mp->m_rtxblkmask; 157 return do_div(rtbno, mp->m_sb.sb_rextsize); 158} 159 160/* Round this file block offset up to the nearest rt extent size. */ 161static inline xfs_rtblock_t 162xfs_fileoff_roundup_rtx( 163 struct xfs_mount *mp, 164 xfs_fileoff_t off) 165{ 166 return roundup_64(off, mp->m_sb.sb_rextsize); 167} 168 169/* Round this file block offset down to the nearest rt extent size. */ 170static inline xfs_rtblock_t 171xfs_fileoff_rounddown_rtx( 172 struct xfs_mount *mp, 173 xfs_fileoff_t off) 174{ 175 return rounddown_64(off, mp->m_sb.sb_rextsize); 176} 177 178/* Convert an rt extent number to a file block offset in the rt bitmap file. */ 179static inline xfs_fileoff_t 180xfs_rtx_to_rbmblock( 181 struct xfs_mount *mp, 182 xfs_rtxnum_t rtx) 183{ 184 if (xfs_has_rtgroups(mp)) 185 return div_u64(rtx, mp->m_rtx_per_rbmblock); 186 187 return rtx >> mp->m_blkbit_log; 188} 189 190/* Convert an rt extent number to a word offset within an rt bitmap block. */ 191static inline unsigned int 192xfs_rtx_to_rbmword( 193 struct xfs_mount *mp, 194 xfs_rtxnum_t rtx) 195{ 196 if (xfs_has_rtgroups(mp)) { 197 unsigned int mod; 198 199 div_u64_rem(rtx >> XFS_NBWORDLOG, mp->m_blockwsize, &mod); 200 return mod; 201 } 202 203 return (rtx >> XFS_NBWORDLOG) & (mp->m_blockwsize - 1); 204} 205 206/* Convert a file block offset in the rt bitmap file to an rt extent number. */ 207static inline xfs_rtxnum_t 208xfs_rbmblock_to_rtx( 209 struct xfs_mount *mp, 210 xfs_fileoff_t rbmoff) 211{ 212 if (xfs_has_rtgroups(mp)) 213 return rbmoff * mp->m_rtx_per_rbmblock; 214 215 return rbmoff << mp->m_blkbit_log; 216} 217 218/* Return a pointer to a bitmap word within a rt bitmap block. */ 219static inline union xfs_rtword_raw * 220xfs_rbmblock_wordptr( 221 struct xfs_rtalloc_args *args, 222 unsigned int index) 223{ 224 struct xfs_mount *mp = args->mp; 225 union xfs_rtword_raw *words; 226 struct xfs_rtbuf_blkinfo *hdr = args->rbmbp->b_addr; 227 228 if (xfs_has_rtgroups(mp)) 229 words = (union xfs_rtword_raw *)(hdr + 1); 230 else 231 words = args->rbmbp->b_addr; 232 233 return words + index; 234} 235 236/* Convert an ondisk bitmap word to its incore representation. */ 237static inline xfs_rtword_t 238xfs_rtbitmap_getword( 239 struct xfs_rtalloc_args *args, 240 unsigned int index) 241{ 242 union xfs_rtword_raw *word = xfs_rbmblock_wordptr(args, index); 243 244 if (xfs_has_rtgroups(args->mp)) 245 return be32_to_cpu(word->rtg); 246 return word->old; 247} 248 249/* Set an ondisk bitmap word from an incore representation. */ 250static inline void 251xfs_rtbitmap_setword( 252 struct xfs_rtalloc_args *args, 253 unsigned int index, 254 xfs_rtword_t value) 255{ 256 union xfs_rtword_raw *word = xfs_rbmblock_wordptr(args, index); 257 258 if (xfs_has_rtgroups(args->mp)) 259 word->rtg = cpu_to_be32(value); 260 else 261 word->old = value; 262} 263 264/* 265 * Convert a rt extent length and rt bitmap block number to a xfs_suminfo_t 266 * offset within the rt summary file. 267 */ 268static inline xfs_rtsumoff_t 269xfs_rtsumoffs( 270 struct xfs_mount *mp, 271 int log2_len, 272 xfs_fileoff_t rbmoff) 273{ 274 return log2_len * mp->m_sb.sb_rbmblocks + rbmoff; 275} 276 277/* 278 * Convert an xfs_suminfo_t offset to a file block offset within the rt summary 279 * file. 280 */ 281static inline xfs_fileoff_t 282xfs_rtsumoffs_to_block( 283 struct xfs_mount *mp, 284 xfs_rtsumoff_t rsumoff) 285{ 286 if (xfs_has_rtgroups(mp)) 287 return rsumoff / mp->m_blockwsize; 288 289 return XFS_B_TO_FSBT(mp, rsumoff * sizeof(xfs_suminfo_t)); 290} 291 292/* 293 * Convert an xfs_suminfo_t offset to an info word offset within an rt summary 294 * block. 295 */ 296static inline unsigned int 297xfs_rtsumoffs_to_infoword( 298 struct xfs_mount *mp, 299 xfs_rtsumoff_t rsumoff) 300{ 301 unsigned int mask = mp->m_blockmask >> XFS_SUMINFOLOG; 302 303 if (xfs_has_rtgroups(mp)) 304 return rsumoff % mp->m_blockwsize; 305 306 return rsumoff & mask; 307} 308 309/* Return a pointer to a summary info word within a rt summary block. */ 310static inline union xfs_suminfo_raw * 311xfs_rsumblock_infoptr( 312 struct xfs_rtalloc_args *args, 313 unsigned int index) 314{ 315 union xfs_suminfo_raw *info; 316 struct xfs_rtbuf_blkinfo *hdr = args->sumbp->b_addr; 317 318 if (xfs_has_rtgroups(args->mp)) 319 info = (union xfs_suminfo_raw *)(hdr + 1); 320 else 321 info = args->sumbp->b_addr; 322 323 return info + index; 324} 325 326/* Get the current value of a summary counter. */ 327static inline xfs_suminfo_t 328xfs_suminfo_get( 329 struct xfs_rtalloc_args *args, 330 unsigned int index) 331{ 332 union xfs_suminfo_raw *info = xfs_rsumblock_infoptr(args, index); 333 334 if (xfs_has_rtgroups(args->mp)) 335 return be32_to_cpu(info->rtg); 336 return info->old; 337} 338 339/* Add to the current value of a summary counter and return the new value. */ 340static inline xfs_suminfo_t 341xfs_suminfo_add( 342 struct xfs_rtalloc_args *args, 343 unsigned int index, 344 int delta) 345{ 346 union xfs_suminfo_raw *info = xfs_rsumblock_infoptr(args, index); 347 348 if (xfs_has_rtgroups(args->mp)) { 349 be32_add_cpu(&info->rtg, delta); 350 return be32_to_cpu(info->rtg); 351 } 352 353 info->old += delta; 354 return info->old; 355} 356 357static inline const struct xfs_buf_ops * 358xfs_rtblock_ops( 359 struct xfs_mount *mp, 360 enum xfs_rtg_inodes type) 361{ 362 if (xfs_has_rtgroups(mp)) { 363 if (type == XFS_RTGI_SUMMARY) 364 return &xfs_rtsummary_buf_ops; 365 return &xfs_rtbitmap_buf_ops; 366 } 367 return &xfs_rtbuf_ops; 368} 369 370/* 371 * Functions for walking free space rtextents in the realtime bitmap. 372 */ 373struct xfs_rtalloc_rec { 374 xfs_rtxnum_t ar_startext; 375 xfs_rtbxlen_t ar_extcount; 376}; 377 378typedef int (*xfs_rtalloc_query_range_fn)( 379 struct xfs_rtgroup *rtg, 380 struct xfs_trans *tp, 381 const struct xfs_rtalloc_rec *rec, 382 void *priv); 383 384#ifdef CONFIG_XFS_RT 385void xfs_rtbuf_cache_relse(struct xfs_rtalloc_args *args); 386int xfs_rtbitmap_read_buf(struct xfs_rtalloc_args *args, xfs_fileoff_t block); 387int xfs_rtsummary_read_buf(struct xfs_rtalloc_args *args, xfs_fileoff_t block); 388int xfs_rtcheck_range(struct xfs_rtalloc_args *args, xfs_rtxnum_t start, 389 xfs_rtxlen_t len, int val, xfs_rtxnum_t *new, int *stat); 390int xfs_rtfind_back(struct xfs_rtalloc_args *args, xfs_rtxnum_t start, 391 xfs_rtxnum_t *rtblock); 392int xfs_rtfind_forw(struct xfs_rtalloc_args *args, xfs_rtxnum_t start, 393 xfs_rtxnum_t limit, xfs_rtxnum_t *rtblock); 394int xfs_rtmodify_range(struct xfs_rtalloc_args *args, xfs_rtxnum_t start, 395 xfs_rtxlen_t len, int val); 396int xfs_rtget_summary(struct xfs_rtalloc_args *args, int log, 397 xfs_fileoff_t bbno, xfs_suminfo_t *sum); 398int xfs_rtmodify_summary(struct xfs_rtalloc_args *args, int log, 399 xfs_fileoff_t bbno, int delta); 400int xfs_rtfree_range(struct xfs_rtalloc_args *args, xfs_rtxnum_t start, 401 xfs_rtxlen_t len); 402int xfs_rtalloc_query_range(struct xfs_rtgroup *rtg, struct xfs_trans *tp, 403 xfs_rtxnum_t start, xfs_rtxnum_t end, 404 xfs_rtalloc_query_range_fn fn, void *priv); 405int xfs_rtalloc_query_all(struct xfs_rtgroup *rtg, struct xfs_trans *tp, 406 xfs_rtalloc_query_range_fn fn, void *priv); 407int xfs_rtalloc_extent_is_free(struct xfs_rtgroup *rtg, struct xfs_trans *tp, 408 xfs_rtxnum_t start, xfs_rtxlen_t len, bool *is_free); 409int xfs_rtfree_extent(struct xfs_trans *tp, struct xfs_rtgroup *rtg, 410 xfs_rtxnum_t start, xfs_rtxlen_t len); 411/* Same as above, but in units of rt blocks. */ 412int xfs_rtfree_blocks(struct xfs_trans *tp, struct xfs_rtgroup *rtg, 413 xfs_fsblock_t rtbno, xfs_filblks_t rtlen); 414 415xfs_rtxnum_t xfs_rtbitmap_rtx_per_rbmblock(struct xfs_mount *mp); 416xfs_filblks_t xfs_rtbitmap_blockcount(struct xfs_mount *mp); 417xfs_filblks_t xfs_rtbitmap_blockcount_len(struct xfs_mount *mp, 418 xfs_rtbxlen_t rtextents); 419xfs_filblks_t xfs_rtsummary_blockcount(struct xfs_mount *mp, 420 unsigned int *rsumlevels); 421 422int xfs_rtfile_initialize_blocks(struct xfs_rtgroup *rtg, 423 enum xfs_rtg_inodes type, xfs_fileoff_t offset_fsb, 424 xfs_fileoff_t end_fsb, void *data); 425int xfs_rtbitmap_create(struct xfs_rtgroup *rtg, struct xfs_inode *ip, 426 struct xfs_trans *tp, bool init); 427int xfs_rtsummary_create(struct xfs_rtgroup *rtg, struct xfs_inode *ip, 428 struct xfs_trans *tp, bool init); 429 430#else /* CONFIG_XFS_RT */ 431# define xfs_rtfree_extent(t,b,l) (-ENOSYS) 432 433static inline int xfs_rtfree_blocks(struct xfs_trans *tp, 434 struct xfs_rtgroup *rtg, xfs_fsblock_t rtbno, 435 xfs_filblks_t rtlen) 436{ 437 return -ENOSYS; 438} 439# define xfs_rtalloc_query_range(m,t,l,h,f,p) (-ENOSYS) 440# define xfs_rtalloc_query_all(m,t,f,p) (-ENOSYS) 441# define xfs_rtbitmap_read_buf(a,b) (-ENOSYS) 442# define xfs_rtsummary_read_buf(a,b) (-ENOSYS) 443# define xfs_rtbuf_cache_relse(a) (0) 444# define xfs_rtalloc_extent_is_free(m,t,s,l,i) (-ENOSYS) 445static inline xfs_filblks_t 446xfs_rtbitmap_blockcount_len(struct xfs_mount *mp, xfs_rtbxlen_t rtextents) 447{ 448 /* shut up gcc */ 449 return 0; 450} 451#endif /* CONFIG_XFS_RT */ 452 453#endif /* __XFS_RTBITMAP_H__ */