rtbitmap.c 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229
  1. // SPDX-License-Identifier: GPL-2.0-or-later
  2. /*
  3. * Copyright (C) 2017-2023 Oracle. All Rights Reserved.
  4. * Author: Darrick J. Wong <djwong@kernel.org>
  5. */
  6. #include "xfs.h"
  7. #include "xfs_fs.h"
  8. #include "xfs_shared.h"
  9. #include "xfs_format.h"
  10. #include "xfs_trans_resv.h"
  11. #include "xfs_mount.h"
  12. #include "xfs_log_format.h"
  13. #include "xfs_trans.h"
  14. #include "xfs_rtbitmap.h"
  15. #include "xfs_inode.h"
  16. #include "xfs_bmap.h"
  17. #include "xfs_bit.h"
  18. #include "xfs_sb.h"
  19. #include "scrub/scrub.h"
  20. #include "scrub/common.h"
  21. #include "scrub/repair.h"
  22. #include "scrub/rtbitmap.h"
  23. /* Set us up with the realtime metadata locked. */
  24. int
  25. xchk_setup_rtbitmap(
  26. struct xfs_scrub *sc)
  27. {
  28. struct xfs_mount *mp = sc->mp;
  29. struct xchk_rtbitmap *rtb;
  30. int error;
  31. rtb = kzalloc(sizeof(struct xchk_rtbitmap), XCHK_GFP_FLAGS);
  32. if (!rtb)
  33. return -ENOMEM;
  34. sc->buf = rtb;
  35. if (xchk_could_repair(sc)) {
  36. error = xrep_setup_rtbitmap(sc, rtb);
  37. if (error)
  38. return error;
  39. }
  40. error = xchk_trans_alloc(sc, rtb->resblks);
  41. if (error)
  42. return error;
  43. error = xchk_install_live_inode(sc, sc->mp->m_rbmip);
  44. if (error)
  45. return error;
  46. error = xchk_ino_dqattach(sc);
  47. if (error)
  48. return error;
  49. xchk_ilock(sc, XFS_ILOCK_EXCL | XFS_ILOCK_RTBITMAP);
  50. /*
  51. * Now that we've locked the rtbitmap, we can't race with growfsrt
  52. * trying to expand the bitmap or change the size of the rt volume.
  53. * Hence it is safe to compute and check the geometry values.
  54. */
  55. if (mp->m_sb.sb_rblocks) {
  56. rtb->rextents = xfs_rtb_to_rtx(mp, mp->m_sb.sb_rblocks);
  57. rtb->rextslog = xfs_compute_rextslog(rtb->rextents);
  58. rtb->rbmblocks = xfs_rtbitmap_blockcount(mp, rtb->rextents);
  59. }
  60. return 0;
  61. }
  62. /* Realtime bitmap. */
  63. /* Scrub a free extent record from the realtime bitmap. */
  64. STATIC int
  65. xchk_rtbitmap_rec(
  66. struct xfs_mount *mp,
  67. struct xfs_trans *tp,
  68. const struct xfs_rtalloc_rec *rec,
  69. void *priv)
  70. {
  71. struct xfs_scrub *sc = priv;
  72. xfs_rtblock_t startblock;
  73. xfs_filblks_t blockcount;
  74. startblock = xfs_rtx_to_rtb(mp, rec->ar_startext);
  75. blockcount = xfs_rtx_to_rtb(mp, rec->ar_extcount);
  76. if (!xfs_verify_rtbext(mp, startblock, blockcount))
  77. xchk_fblock_set_corrupt(sc, XFS_DATA_FORK, 0);
  78. return 0;
  79. }
  80. /* Make sure the entire rtbitmap file is mapped with written extents. */
  81. STATIC int
  82. xchk_rtbitmap_check_extents(
  83. struct xfs_scrub *sc)
  84. {
  85. struct xfs_bmbt_irec map;
  86. struct xfs_iext_cursor icur;
  87. struct xfs_mount *mp = sc->mp;
  88. struct xfs_inode *ip = sc->ip;
  89. xfs_fileoff_t off = 0;
  90. xfs_fileoff_t endoff;
  91. int error = 0;
  92. /* Mappings may not cross or lie beyond EOF. */
  93. endoff = XFS_B_TO_FSB(mp, ip->i_disk_size);
  94. if (xfs_iext_lookup_extent(ip, &ip->i_df, endoff, &icur, &map)) {
  95. xchk_fblock_set_corrupt(sc, XFS_DATA_FORK, endoff);
  96. return 0;
  97. }
  98. while (off < endoff) {
  99. int nmap = 1;
  100. if (xchk_should_terminate(sc, &error) ||
  101. (sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT))
  102. break;
  103. /* Make sure we have a written extent. */
  104. error = xfs_bmapi_read(ip, off, endoff - off, &map, &nmap,
  105. XFS_DATA_FORK);
  106. if (!xchk_fblock_process_error(sc, XFS_DATA_FORK, off, &error))
  107. break;
  108. if (nmap != 1 || !xfs_bmap_is_written_extent(&map)) {
  109. xchk_fblock_set_corrupt(sc, XFS_DATA_FORK, off);
  110. break;
  111. }
  112. off += map.br_blockcount;
  113. }
  114. return error;
  115. }
  116. /* Scrub the realtime bitmap. */
  117. int
  118. xchk_rtbitmap(
  119. struct xfs_scrub *sc)
  120. {
  121. struct xfs_mount *mp = sc->mp;
  122. struct xchk_rtbitmap *rtb = sc->buf;
  123. int error;
  124. /* Is sb_rextents correct? */
  125. if (mp->m_sb.sb_rextents != rtb->rextents) {
  126. xchk_ino_set_corrupt(sc, mp->m_rbmip->i_ino);
  127. return 0;
  128. }
  129. /* Is sb_rextslog correct? */
  130. if (mp->m_sb.sb_rextslog != rtb->rextslog) {
  131. xchk_ino_set_corrupt(sc, mp->m_rbmip->i_ino);
  132. return 0;
  133. }
  134. /*
  135. * Is sb_rbmblocks large enough to handle the current rt volume? In no
  136. * case can we exceed 4bn bitmap blocks since the super field is a u32.
  137. */
  138. if (rtb->rbmblocks > U32_MAX) {
  139. xchk_ino_set_corrupt(sc, mp->m_rbmip->i_ino);
  140. return 0;
  141. }
  142. if (mp->m_sb.sb_rbmblocks != rtb->rbmblocks) {
  143. xchk_ino_set_corrupt(sc, mp->m_rbmip->i_ino);
  144. return 0;
  145. }
  146. /* The bitmap file length must be aligned to an fsblock. */
  147. if (mp->m_rbmip->i_disk_size & mp->m_blockmask) {
  148. xchk_ino_set_corrupt(sc, mp->m_rbmip->i_ino);
  149. return 0;
  150. }
  151. /*
  152. * Is the bitmap file itself large enough to handle the rt volume?
  153. * growfsrt expands the bitmap file before updating sb_rextents, so the
  154. * file can be larger than sb_rbmblocks.
  155. */
  156. if (mp->m_rbmip->i_disk_size < XFS_FSB_TO_B(mp, rtb->rbmblocks)) {
  157. xchk_ino_set_corrupt(sc, mp->m_rbmip->i_ino);
  158. return 0;
  159. }
  160. /* Invoke the fork scrubber. */
  161. error = xchk_metadata_inode_forks(sc);
  162. if (error || (sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT))
  163. return error;
  164. error = xchk_rtbitmap_check_extents(sc);
  165. if (error || (sc->sm->sm_flags & XFS_SCRUB_OFLAG_CORRUPT))
  166. return error;
  167. error = xfs_rtalloc_query_all(mp, sc->tp, xchk_rtbitmap_rec, sc);
  168. if (!xchk_fblock_process_error(sc, XFS_DATA_FORK, 0, &error))
  169. return error;
  170. return 0;
  171. }
  172. /* xref check that the extent is not free in the rtbitmap */
  173. void
  174. xchk_xref_is_used_rt_space(
  175. struct xfs_scrub *sc,
  176. xfs_rtblock_t rtbno,
  177. xfs_extlen_t len)
  178. {
  179. xfs_rtxnum_t startext;
  180. xfs_rtxnum_t endext;
  181. bool is_free;
  182. int error;
  183. if (xchk_skip_xref(sc->sm))
  184. return;
  185. startext = xfs_rtb_to_rtx(sc->mp, rtbno);
  186. endext = xfs_rtb_to_rtx(sc->mp, rtbno + len - 1);
  187. xfs_ilock(sc->mp->m_rbmip, XFS_ILOCK_SHARED | XFS_ILOCK_RTBITMAP);
  188. error = xfs_rtalloc_extent_is_free(sc->mp, sc->tp, startext,
  189. endext - startext + 1, &is_free);
  190. if (!xchk_should_check_xref(sc, &error, NULL))
  191. goto out_unlock;
  192. if (is_free)
  193. xchk_ino_xref_set_corrupt(sc, sc->mp->m_rbmip->i_ino);
  194. out_unlock:
  195. xfs_iunlock(sc->mp->m_rbmip, XFS_ILOCK_SHARED | XFS_ILOCK_RTBITMAP);
  196. }