1 // SPDX-License-Identifier: GPL-2.0
3 * Copyright (c) 2000-2001,2005 Silicon Graphics, Inc.
11 #include "err_protos.h"
14 * XXX (dgc): What is the point of all the check and repair here when phase 5
15 * recreates the AGF/AGI/AGFL completely from scratch?
19 verify_set_agf(xfs_mount_t
*mp
, xfs_agf_t
*agf
, xfs_agnumber_t i
)
21 xfs_rfsblock_t agblocks
;
24 /* check common fields */
26 if (be32_to_cpu(agf
->agf_magicnum
) != XFS_AGF_MAGIC
) {
28 do_warn(_("bad magic # 0x%x for agf %d\n"),
29 be32_to_cpu(agf
->agf_magicnum
), i
);
32 agf
->agf_magicnum
= cpu_to_be32(XFS_AGF_MAGIC
);
35 if (!XFS_AGF_GOOD_VERSION(be32_to_cpu(agf
->agf_versionnum
))) {
37 do_warn(_("bad version # %d for agf %d\n"),
38 be32_to_cpu(agf
->agf_versionnum
), i
);
41 agf
->agf_versionnum
= cpu_to_be32(XFS_AGF_VERSION
);
44 if (be32_to_cpu(agf
->agf_seqno
) != i
) {
46 do_warn(_("bad sequence # %d for agf %d\n"),
47 be32_to_cpu(agf
->agf_seqno
), i
);
50 agf
->agf_seqno
= cpu_to_be32(i
);
53 if (be32_to_cpu(agf
->agf_length
) != mp
->m_sb
.sb_agblocks
) {
54 if (i
!= mp
->m_sb
.sb_agcount
- 1) {
56 do_warn(_("bad length %d for agf %d, should be %d\n"),
57 be32_to_cpu(agf
->agf_length
), i
,
58 mp
->m_sb
.sb_agblocks
);
61 cpu_to_be32(mp
->m_sb
.sb_agblocks
);
63 agblocks
= mp
->m_sb
.sb_dblocks
-
64 (xfs_rfsblock_t
) mp
->m_sb
.sb_agblocks
* i
;
66 if (be32_to_cpu(agf
->agf_length
) != agblocks
) {
69 _("bad length %d for agf %d, should be %" PRIu64
"\n"),
70 be32_to_cpu(agf
->agf_length
),
73 agf
->agf_length
= cpu_to_be32(agblocks
);
79 * check first/last AGF fields. if need be, lose the free
80 * space in the AGFL, we'll reclaim it later.
82 if (be32_to_cpu(agf
->agf_flfirst
) >= libxfs_agfl_size(mp
)) {
83 do_warn(_("flfirst %d in agf %d too large (max = %u)\n"),
84 be32_to_cpu(agf
->agf_flfirst
),
85 i
, libxfs_agfl_size(mp
) - 1);
87 agf
->agf_flfirst
= cpu_to_be32(0);
90 if (be32_to_cpu(agf
->agf_fllast
) >= libxfs_agfl_size(mp
)) {
91 do_warn(_("fllast %d in agf %d too large (max = %u)\n"),
92 be32_to_cpu(agf
->agf_fllast
),
93 i
, libxfs_agfl_size(mp
) - 1);
95 agf
->agf_fllast
= cpu_to_be32(0);
98 /* don't check freespace btrees -- will be checked by caller */
100 if (!xfs_has_crc(mp
))
103 if (platform_uuid_compare(&agf
->agf_uuid
, &mp
->m_sb
.sb_meta_uuid
)) {
107 platform_uuid_unparse(&agf
->agf_uuid
, uu
);
108 do_warn(_("bad uuid %s for agf %d\n"), uu
, i
);
111 platform_uuid_copy(&agf
->agf_uuid
,
112 &mp
->m_sb
.sb_meta_uuid
);
118 verify_set_agi(xfs_mount_t
*mp
, xfs_agi_t
*agi
, xfs_agnumber_t agno
)
120 xfs_rfsblock_t agblocks
;
123 /* check common fields */
125 if (be32_to_cpu(agi
->agi_magicnum
) != XFS_AGI_MAGIC
) {
127 do_warn(_("bad magic # 0x%x for agi %d\n"),
128 be32_to_cpu(agi
->agi_magicnum
), agno
);
131 agi
->agi_magicnum
= cpu_to_be32(XFS_AGI_MAGIC
);
134 if (!XFS_AGI_GOOD_VERSION(be32_to_cpu(agi
->agi_versionnum
))) {
136 do_warn(_("bad version # %d for agi %d\n"),
137 be32_to_cpu(agi
->agi_versionnum
), agno
);
140 agi
->agi_versionnum
= cpu_to_be32(XFS_AGI_VERSION
);
143 if (be32_to_cpu(agi
->agi_seqno
) != agno
) {
145 do_warn(_("bad sequence # %d for agi %d\n"),
146 be32_to_cpu(agi
->agi_seqno
), agno
);
149 agi
->agi_seqno
= cpu_to_be32(agno
);
152 if (be32_to_cpu(agi
->agi_length
) != mp
->m_sb
.sb_agblocks
) {
153 if (agno
!= mp
->m_sb
.sb_agcount
- 1) {
155 do_warn(_("bad length # %d for agi %d, should be %d\n"),
156 be32_to_cpu(agi
->agi_length
), agno
,
157 mp
->m_sb
.sb_agblocks
);
160 cpu_to_be32(mp
->m_sb
.sb_agblocks
);
162 agblocks
= mp
->m_sb
.sb_dblocks
-
163 (xfs_rfsblock_t
) mp
->m_sb
.sb_agblocks
* agno
;
165 if (be32_to_cpu(agi
->agi_length
) != agblocks
) {
168 _("bad length # %d for agi %d, should be %" PRIu64
"\n"),
169 be32_to_cpu(agi
->agi_length
),
172 agi
->agi_length
= cpu_to_be32(agblocks
);
177 /* don't check inode btree -- will be checked by caller */
179 if (!xfs_has_crc(mp
))
182 if (platform_uuid_compare(&agi
->agi_uuid
, &mp
->m_sb
.sb_meta_uuid
)) {
186 platform_uuid_unparse(&agi
->agi_uuid
, uu
);
187 do_warn(_("bad uuid %s for agi %d\n"), uu
, agno
);
190 platform_uuid_copy(&agi
->agi_uuid
,
191 &mp
->m_sb
.sb_meta_uuid
);
198 * superblock comparison - compare arbitrary superblock with
199 * filesystem mount-point superblock
201 * the verified fields include id and geometry.
203 * the inprogress fields, version numbers, and counters
204 * are allowed to differ as well as all fields after the
205 * counters to cope with the pre-6.5 mkfs non-zeroed
206 * secondary superblock sectors.
209 compare_sb(xfs_mount_t
*mp
, xfs_sb_t
*sb
)
211 fs_geometry_t fs_geo
, sb_geo
;
213 get_sb_geometry(&fs_geo
, &mp
->m_sb
);
214 get_sb_geometry(&sb_geo
, sb
);
216 if (memcmp(&fs_geo
, &sb_geo
,
217 (char *) &fs_geo
.sb_shared_vn
- (char *) &fs_geo
))
218 return(XR_SB_GEO_MISMATCH
);
224 * If the fs feature bits on a secondary superblock don't match the
225 * primary, we need to update them.
228 check_v5_feature_mismatch(
229 struct xfs_mount
*mp
,
235 if (!xfs_has_crc(mp
) || agno
== 0)
238 if (mp
->m_sb
.sb_features_compat
!= sb
->sb_features_compat
) {
241 _("would fix compat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
242 agno
, mp
->m_sb
.sb_features_compat
,
243 sb
->sb_features_compat
);
246 _("will fix compat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
247 agno
, mp
->m_sb
.sb_features_compat
,
248 sb
->sb_features_compat
);
254 * Ignore XFS_SB_FEAT_INCOMPAT_NEEDSREPAIR becauses the repair upgrade
255 * path sets it only on the primary while upgrading.
257 if ((mp
->m_sb
.sb_features_incompat
^ sb
->sb_features_incompat
) &
258 ~XFS_SB_FEAT_INCOMPAT_NEEDSREPAIR
) {
261 _("would fix incompat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
262 agno
, mp
->m_sb
.sb_features_incompat
,
263 sb
->sb_features_incompat
);
266 _("will fix incompat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
267 agno
, mp
->m_sb
.sb_features_incompat
,
268 sb
->sb_features_incompat
);
273 if (mp
->m_sb
.sb_features_ro_compat
!= sb
->sb_features_ro_compat
) {
276 _("would fix ro compat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
277 agno
, mp
->m_sb
.sb_features_ro_compat
,
278 sb
->sb_features_ro_compat
);
281 _("will fix ro compat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
282 agno
, mp
->m_sb
.sb_features_ro_compat
,
283 sb
->sb_features_ro_compat
);
288 if (mp
->m_sb
.sb_features_log_incompat
!= sb
->sb_features_log_incompat
) {
291 _("would fix log incompat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
292 agno
, mp
->m_sb
.sb_features_log_incompat
,
293 sb
->sb_features_log_incompat
);
296 _("will fix log incompat feature mismatch in AG %u super, 0x%x != 0x%x\n"),
297 agno
, mp
->m_sb
.sb_features_log_incompat
,
298 sb
->sb_features_log_incompat
);
306 sb
->sb_features_compat
= mp
->m_sb
.sb_features_compat
;
307 sb
->sb_features_ro_compat
= mp
->m_sb
.sb_features_ro_compat
;
308 sb
->sb_features_incompat
= mp
->m_sb
.sb_features_incompat
;
309 sb
->sb_features_log_incompat
= mp
->m_sb
.sb_features_log_incompat
;
314 * Possible fields that may have been set at mkfs time,
315 * sb_inoalignmt, sb_unit, sb_width and sb_dirblklog.
316 * The quota inode fields in the secondaries should be zero.
317 * Likewise, the sb_flags and sb_shared_vn should also be
318 * zero and the shared version bit should be cleared for
321 * And everything else in the buffer beyond either sb_width,
322 * sb_dirblklog (v2 dirs), or sb_logsectsize can be zeroed.
324 * Note: contrary to the name, this routine is called for all
325 * superblocks, not just the secondary superblocks.
329 struct xfs_mount
*mp
,
330 struct xfs_buf
*sbuf
,
334 struct xfs_dsb
*dsb
= sbuf
->b_addr
;
344 * Check for garbage beyond the last valid field.
345 * Use field addresses instead so this code will still
346 * work against older filesystems when the superblock
347 * gets rev'ed again with new fields appended.
349 * size is the size of data which is valid for this sb.
351 if (xfs_sb_version_hasmetauuid(sb
))
352 size
= offsetof(xfs_sb_t
, sb_meta_uuid
)
353 + sizeof(sb
->sb_meta_uuid
);
354 else if (xfs_sb_version_hascrc(sb
))
355 size
= offsetof(xfs_sb_t
, sb_lsn
)
356 + sizeof(sb
->sb_lsn
);
357 else if (xfs_sb_version_hasmorebits(sb
))
358 size
= offsetof(xfs_sb_t
, sb_bad_features2
)
359 + sizeof(sb
->sb_bad_features2
);
360 else if (xfs_sb_version_haslogv2(sb
))
361 size
= offsetof(xfs_sb_t
, sb_logsunit
)
362 + sizeof(sb
->sb_logsunit
);
363 else if (xfs_sb_version_hassector(sb
))
364 size
= offsetof(xfs_sb_t
, sb_logsectsize
)
365 + sizeof(sb
->sb_logsectsize
);
366 else /* only support dirv2 or more recent */
367 size
= offsetof(xfs_sb_t
, sb_dirblklog
)
368 + sizeof(sb
->sb_dirblklog
);
370 /* Check the buffer we read from disk for garbage outside size */
371 for (ip
= (char *)sbuf
->b_addr
+ size
;
372 ip
< (char *)sbuf
->b_addr
+ mp
->m_sb
.sb_sectsize
;
380 rval
|= XR_AG_SB_SEC
;
383 _("zeroing unused portion of %s superblock (AG #%u)\n"),
384 !i
? _("primary") : _("secondary"), i
);
386 * zero both the in-memory sb and the disk buffer,
387 * because the former was read from disk and
388 * may contain newer version fields that shouldn't
389 * be set, and the latter is never updated past
390 * the last field - just zap them both.
392 memcpy(&tmpuuid
, &sb
->sb_meta_uuid
, sizeof(uuid_t
));
393 memset((void *)((intptr_t)sb
+ size
), 0,
394 mp
->m_sb
.sb_sectsize
- size
);
395 memset((char *)sbuf
->b_addr
+ size
, 0,
396 mp
->m_sb
.sb_sectsize
- size
);
397 /* Preserve meta_uuid so we don't fail uuid checks */
398 memcpy(&sb
->sb_meta_uuid
, &tmpuuid
, sizeof(uuid_t
));
401 _("would zero unused portion of %s superblock (AG #%u)\n"),
402 !i
? _("primary") : _("secondary"), i
);
406 * now look for the fields we can manipulate directly.
407 * if we did a zero and that zero could have included
408 * the field in question, just silently reset it. otherwise,
411 * for now, just zero the flags field since only
412 * the readonly flag is used
419 do_warn(_("bad flags field in superblock %d\n"), i
);
421 rval
|= XR_AG_SB_SEC
;
425 * quota inodes and flags in secondary superblocks are never set by
426 * mkfs. However, they could be set in a secondary if a fs with quotas
427 * was growfs'ed since growfs copies the new primary into the
430 * Also, the in-core inode flags now have different meaning to the
431 * on-disk flags, and so libxfs_sb_to_disk cannot directly write the
432 * sb_gquotino/sb_pquotino fields without specific sb_qflags being set.
433 * Hence we need to zero those fields directly in the sb buffer here.
436 if (sb
->sb_inprogress
== 1 && sb
->sb_uquotino
!= NULLFSINO
) {
442 _("non-null user quota inode field in superblock %d\n"),
446 rval
|= XR_AG_SB_SEC
;
449 if (sb
->sb_inprogress
== 1 && sb
->sb_gquotino
!= NULLFSINO
) {
452 dsb
->sb_gquotino
= 0;
457 _("non-null group quota inode field in superblock %d\n"),
461 rval
|= XR_AG_SB_SEC
;
465 * Note that sb_pquotino is not considered a valid sb field for pre-v5
466 * superblocks. If it is anything other than 0 it is considered garbage
467 * data beyond the valid sb and explicitly zeroed above.
469 if (xfs_has_pquotino(mp
) &&
470 sb
->sb_inprogress
== 1 && sb
->sb_pquotino
!= NULLFSINO
) {
473 dsb
->sb_pquotino
= 0;
478 _("non-null project quota inode field in superblock %d\n"),
482 rval
|= XR_AG_SB_SEC
;
485 if (sb
->sb_inprogress
== 1 && sb
->sb_qflags
) {
490 do_warn(_("non-null quota flags in superblock %d\n"),
493 rval
|= XR_AG_SB_SEC
;
497 * if the secondaries agree on a stripe unit/width or inode
498 * alignment, those fields ought to be valid since they are
499 * written at mkfs time (and the corresponding sb version bits
502 if (!xfs_sb_version_hasalign(sb
) && sb
->sb_inoalignmt
!= 0) {
504 sb
->sb_inoalignmt
= 0;
508 _("bad inode alignment field in superblock %d\n"),
511 rval
|= XR_AG_SB_SEC
;
514 if (!xfs_sb_version_hasdalign(sb
) &&
515 (sb
->sb_unit
!= 0 || sb
->sb_width
!= 0)) {
517 sb
->sb_unit
= sb
->sb_width
= 0;
521 _("bad stripe unit/width fields in superblock %d\n"),
524 rval
|= XR_AG_SB_SEC
;
527 if (!xfs_sb_version_hassector(sb
) &&
528 (sb
->sb_sectsize
!= BBSIZE
|| sb
->sb_sectlog
!= BBSHIFT
||
529 sb
->sb_logsectsize
!= 0 || sb
->sb_logsectlog
!= 0)) {
531 sb
->sb_sectsize
= BBSIZE
;
532 sb
->sb_sectlog
= BBSHIFT
;
533 sb
->sb_logsectsize
= 0;
534 sb
->sb_logsectlog
= 0;
539 _("bad log/data device sector size fields in superblock %d\n"),
542 rval
|= XR_AG_SB_SEC
;
545 rval
|= check_v5_feature_mismatch(mp
, i
, sb
);
547 if (xfs_sb_version_needsrepair(sb
)) {
551 _("clearing needsrepair flag and regenerating metadata\n"));
554 _("would clear needsrepair flag and regenerate metadata\n"));
557 * Quietly clear needsrepair on the secondary supers as
558 * part of ensuring them. If needsrepair is set on the
559 * primary, it will be cleared at the end of repair
560 * once we've flushed all other dirty blocks to disk.
562 sb
->sb_features_incompat
&=
563 ~XFS_SB_FEAT_INCOMPAT_NEEDSREPAIR
;
564 rval
|= XR_AG_SB_SEC
;
572 * verify and reset the ag header if required.
574 * lower 4 bits of rval are set depending on what got modified.
575 * (see agheader.h for more details)
577 * NOTE -- this routine does not tell the user that it has
578 * altered things. Rather, it is up to the caller to do so
579 * using the bits encoded into the return value.
583 verify_set_agheader(xfs_mount_t
*mp
, struct xfs_buf
*sbuf
, xfs_sb_t
*sb
,
584 xfs_agf_t
*agf
, xfs_agi_t
*agi
, xfs_agnumber_t i
)
588 int status_sb
= XR_OK
;
590 status
= verify_sb(sbuf
->b_addr
, sb
, (i
== 0));
592 if (status
!= XR_OK
) {
593 do_warn(_("bad on-disk superblock %d - %s\n"),
594 i
, err_string(status
));
597 status_sb
= compare_sb(mp
, sb
);
599 if (status_sb
!= XR_OK
) {
600 do_warn(_("primary/secondary superblock %d conflict - %s\n"),
601 i
, err_string(status_sb
));
604 if (status
!= XR_OK
|| status_sb
!= XR_OK
) {
609 * clear the more transient fields
611 sb
->sb_inprogress
= 1;
616 sb
->sb_frextents
= 0;
624 rval
|= secondary_sb_whack(mp
, sbuf
, sb
, i
);
626 rval
|= verify_set_agf(mp
, agf
, i
);
627 rval
|= verify_set_agi(mp
, agi
, i
);