goto clear_bad_out;
}
+ if ((flags2 & XFS_DIFLAG2_COWEXTSIZE) &&
+ !xfs_sb_version_hasreflink(&mp->m_sb)) {
+ if (!uncertain) {
+ do_warn(
+ _("inode %" PRIu64 " has CoW extent size hint but file system does not support reflink\n"),
+ lino);
+ }
+ flags2 &= ~XFS_DIFLAG2_COWEXTSIZE;
+ }
+
+ if (flags2 & XFS_DIFLAG2_COWEXTSIZE) {
+ /* must be a directory or file */
+ if (di_mode && !S_ISDIR(di_mode) && !S_ISREG(di_mode)) {
+ if (!uncertain) {
+ do_warn(
+ _("CoW extent size flag set on non-file, non-directory inode %" PRIu64 "\n" ),
+ lino);
+ }
+ flags2 &= ~XFS_DIFLAG2_COWEXTSIZE;
+ }
+ }
+
+ if ((flags2 & XFS_DIFLAG2_COWEXTSIZE) &&
+ (flags & (XFS_DIFLAG_REALTIME | XFS_DIFLAG_RTINHERIT))) {
+ if (!uncertain) {
+ do_warn(
+ _("Cannot have CoW extent size hint on a realtime inode %" PRIu64 "\n"),
+ lino);
+ }
+ flags2 &= ~XFS_DIFLAG2_COWEXTSIZE;
+ }
+
if (!verify_mode && flags2 != be64_to_cpu(dino->di_flags2)) {
if (!no_modify) {
do_warn(_("fixing bad flags2.\n"));
}
}
+ /*
+ * Only (regular files and directories) with COWEXTSIZE flags
+ * set can have extsize set.
+ */
+ if (dino->di_version >= 3 &&
+ be32_to_cpu(dino->di_cowextsize) != 0) {
+ if ((type == XR_INO_DIR || type == XR_INO_DATA) &&
+ (be64_to_cpu(dino->di_flags2) &
+ XFS_DIFLAG2_COWEXTSIZE)) {
+ /* s'okay */ ;
+ } else {
+ do_warn(
+_("Cannot have non-zero CoW extent size %u on non-cowextsize inode %" PRIu64 ", "),
+ be32_to_cpu(dino->di_cowextsize), lino);
+ if (!no_modify) {
+ do_warn(_("resetting to zero\n"));
+ dino->di_cowextsize = 0;
+ *dirty = 1;
+ } else
+ do_warn(_("would reset to zero\n"));
+ }
+ }
+
/*
* general size/consistency checks:
*/