Whamcloud - gitweb
LU-15542 osd-ldiskfs: exclude EA inode from processing 86/46486/4
authorAlexey Lyashkov <alexey.lyashkov@hpe.com>
Thu, 10 Feb 2022 12:46:00 +0000 (15:46 +0300)
committerOleg Drokin <green@whamcloud.com>
Mon, 30 May 2022 18:44:46 +0000 (18:44 +0000)
EA inode is ldiskfs internal object and this should be
excluded at any osd access.
Panic fixed by this change because iterator will return
an error when tries to access to the ea inode.

osd_ea_fid_get()) Process leaving (rc=18446744073709551614 : -2
osd_it_ea_rec()) Process leaving (rc=18446744073709551614 : -2)
osd_it_ea_next()) Process entered

HPe-bug-id: LUS-10683
Signed-off-by: Alexey Lyashkov <alexey.lyashkov@hpe.com>
Change-Id: I73e5325721ae28ea380e9d216c6c6cf7fa0ac4ea
Reviewed-on: https://review.whamcloud.com/46486
Tested-by: jenkins <devops@whamcloud.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Andrew Perepechko <andrew.perepechko@hpe.com>
Reviewed-by: Alexander Zarochentsev <alexander.zarochentsev@hpe.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
lustre/osd-ldiskfs/osd_compat.c
lustre/osd-ldiskfs/osd_handler.c
lustre/osd-ldiskfs/osd_oi.c
lustre/osd-ldiskfs/osd_scrub.c
lustre/tests/conf-sanity.sh

index 23e623a..80a87a0 100644 (file)
@@ -726,15 +726,6 @@ static int osd_obj_update_entry(struct osd_thread_info *info,
                GOTO(out, rc);
        }
 
-       /*
-        * The EA inode should NOT be in OI, old OI scrub may added
-        * such OI mapping by wrong, replace it.
-        */
-       if (unlikely(osd_is_ea_inode(inode))) {
-               iput(inode);
-               goto update;
-       }
-
        rc = osd_get_lma(info, inode, dentry, &info->oti_ost_attrs);
        if (rc == -ENODATA) {
                rc = osd_get_idif(info, inode, dentry, oi_fid);
index cac70ab..c0f3da9 100644 (file)
@@ -517,11 +517,18 @@ struct inode *osd_iget(struct osd_thread_info *info, struct osd_device *dev,
                iput(inode);
                inode = ERR_PTR(-ESTALE);
        } else if (is_bad_inode(inode)) {
-               rc = -ENOENT;
                CWARN("%s: bad inode: ino = %u: rc = %d\n",
-                     osd_dev2name(dev), id->oii_ino, rc);
+                     osd_dev2name(dev), id->oii_ino, -ENOENT);
                iput(inode);
-               inode = ERR_PTR(rc);
+               inode = ERR_PTR(-ENOENT);
+       } else  if (osd_is_ea_inode(inode)) {
+               /*
+                * EA inode is internal ldiskfs object, should don't visible
+                * on osd
+                */
+               CDEBUG(D_INODE, "EA inode: ino = %u\n", id->oii_ino);
+               iput(inode);
+               inode = ERR_PTR(-ENOENT);
        } else if ((rc = osd_attach_jinode(inode))) {
                iput(inode);
                inode = ERR_PTR(rc);
@@ -634,7 +641,7 @@ static struct inode *osd_iget_check(struct osd_thread_info *info,
         */
 
 again:
-       inode = osd_ldiskfs_iget(osd_sb(dev), id->oii_ino);
+       inode = osd_iget(info, dev, id);
        if (IS_ERR(inode)) {
                rc = PTR_ERR(inode);
                if (!trusted && (rc == -ENOENT || rc == -ESTALE))
@@ -645,40 +652,6 @@ again:
                GOTO(put, rc);
        }
 
-       if (is_bad_inode(inode)) {
-               rc = -ENOENT;
-               if (!trusted)
-                       goto check_oi;
-
-               CDEBUG(D_INODE, "bad inode for FID: "DFID", ino = %u\n",
-                      PFID(fid), id->oii_ino);
-               GOTO(put, rc);
-       }
-
-       if (id->oii_gen != OSD_OII_NOGEN &&
-           inode->i_generation != id->oii_gen) {
-               rc = -ESTALE;
-               if (!trusted)
-                       goto check_oi;
-
-               CDEBUG(D_INODE, "unmatched inode for FID: "DFID", ino = %u, "
-                      "oii_gen = %u, i_generation = %u\n", PFID(fid),
-                      id->oii_ino, id->oii_gen, inode->i_generation);
-               GOTO(put, rc);
-       }
-
-       if (inode->i_nlink == 0) {
-               rc = -ENOENT;
-               if (!trusted)
-                       goto check_oi;
-
-               CDEBUG(D_INODE, "stale inode for FID: "DFID", ino = %u\n",
-                      PFID(fid), id->oii_ino);
-               GOTO(put, rc);
-       }
-
-       ldiskfs_clear_inode_state(inode, LDISKFS_STATE_LUSTRE_DESTROY);
-
 check_oi:
        if (rc != 0) {
                __u32 saved_ino = id->oii_ino;
@@ -752,19 +725,6 @@ check_oi:
                        rc = -ENOENT;
                else
                        rc = -EREMCHG;
-       } else {
-               if (id->oii_gen == OSD_OII_NOGEN)
-                       osd_id_gen(id, inode->i_ino, inode->i_generation);
-
-               /*
-                * Do not update file c/mtime in ldiskfs.
-                * NB: we don't have any lock to protect this because we don't
-                * have reference on osd_object now, but contention with
-                * another lookup + attr_set can't happen in the tiny window
-                * between if (...) and set S_NOCMTIME.
-                */
-               if (!(inode->i_flags & S_NOCMTIME))
-                       inode->i_flags |= S_NOCMTIME;
        }
 
        GOTO(put, rc);
@@ -1179,7 +1139,7 @@ static int osd_fid_lookup(const struct lu_env *env, struct osd_object *obj,
        /* Search order: 3. OI files. */
        result = osd_oi_lookup(info, dev, fid, id, OI_CHECK_FLD);
        if (result == -ENOENT) {
-               if (!(fid_is_norm(fid) || fid_is_igif(fid)) ||
+               if (!fid_is_norm(fid) ||
                    fid_is_on_ost(info, dev, fid, OI_CHECK_FLD) ||
                    !ldiskfs_test_bit(osd_oi_fid2idx(dev, fid),
                                      sf->sf_oi_bitmap))
index 7fb40f3..47df02b 100644 (file)
@@ -742,14 +742,6 @@ int osd_oi_insert(struct osd_thread_info *info, struct osd_device *osd,
                        return rc;
                }
 
-               /* The EA inode should NOT be in OI, old OI scrub may added
-                * such OI mapping by wrong, replace it.
-                */
-               if (unlikely(osd_is_ea_inode(inode))) {
-                       iput(inode);
-                       goto update;
-               }
-
                rc = osd_get_lma(info, inode, &info->oti_obj_dentry,
                                 &info->oti_ost_attrs);
                iput(inode);
index ffe4a0b..0605c31 100644 (file)
@@ -290,10 +290,6 @@ osd_scrub_check_update(struct osd_thread_info *info, struct osd_device *dev,
                        GOTO(out, rc);
                }
 
-               /* The inode has been reused as EA inode, ignore it. */
-               if (unlikely(osd_is_ea_inode(inode)))
-                       GOTO(out, rc = 0);
-
                sf->sf_flags |= SF_UPGRADE;
                sf->sf_internal_flags &= ~SIF_NO_HANDLE_OLD_FID;
                dev->od_check_ff = 1;
@@ -333,10 +329,6 @@ iget:
                                        rc = 0;
                                GOTO(out, rc);
                        }
-
-                       /* The inode has been reused as EA inode, ignore it. */
-                       if (unlikely(osd_is_ea_inode(inode)))
-                               GOTO(out, rc = 0);
                }
 
                switch (val) {
@@ -628,10 +620,6 @@ static int osd_iit_iget(struct osd_thread_info *info, struct osd_device *dev,
        if (dev->od_is_ost && S_ISREG(inode->i_mode) && inode->i_nlink > 1)
                dev->od_scrub.os_scrub.os_has_ml_file = 1;
 
-       /* It is an EA inode, no OI mapping for it, skip it. */
-       if (osd_is_ea_inode(inode))
-               GOTO(put, rc = SCRUB_NEXT_CONTINUE);
-
        if (scrub &&
            ldiskfs_test_inode_state(inode, LDISKFS_STATE_LUSTRE_NOSCRUB)) {
                /* Only skip it for the first OI scrub accessing. */
index 81c9a1e..e7de934 100644 (file)
@@ -5041,7 +5041,7 @@ test_60() { # LU-471
 }
 run_test 60 "check mkfs.lustre --mkfsoptions -E -O options setting"
 
-test_61() { # LU-80
+test_61a() { # LU-80
        local lxattr=$(large_xattr_enabled)
 
        [ "$MDS1_VERSION" -ge $(version_code 2.1.53) ] ||
@@ -5115,7 +5115,79 @@ test_61() { # LU-80
        rm -f $file
        cleanup || error "stopping systems failed"
 }
-run_test 61 "large xattr"
+run_test 61a "large xattr"
+
+test_61b() { # LU-80
+       local lxattr=$(large_xattr_enabled)
+
+       [ "$MDS1_VERSION" -ge $(version_code 2.1.53) ] ||
+               skip "Need MDS version at least 2.1.53"
+
+       if [ "$mds1_FSTYPE" != ldiskfs ]; then
+               skip "ldiskfs specific bug"
+       fi
+
+       if ! large_xattr_enabled; then
+               lxattr=true
+
+               for num in $(seq $MDSCOUNT); do
+                       do_facet mds${num} $TUNE2FS -O ea_inode \
+                               $(mdsdevname $num) ||
+                               error "tune2fs on mds $num failed"
+               done
+       fi
+
+       setup || error "setting up the filesystem failed"
+       client_up || error "starting client failed"
+
+       local _file=$MOUNT/panda
+       local large_value="$(generate_string $(max_xattr_size))"
+       local name="trusted.big"
+
+       touch ${_file} || error "touch ${_file} failed"
+       setfattr -n $name -v $large_value ${_file} ||
+               error "saving $name on $file failed"
+
+       MDT_DEV="${FSNAME}-MDT0000"
+       MDT_DEVNAME=$(mdsdevname ${SINGLEMDS//mds/})
+
+       stopall || error "stopping for e2fsck run"
+
+
+       ino=$(do_facet $SINGLEMDS "$DEBUGFS -R 'stat /ROOT/panda' \
+               ${MDT_DEVNAME} | grep trusted.big")
+       ino=$(echo "${ino}" | awk '{print $2;}')
+       echo "large ea "${ino}
+
+       do_facet $SINGLEMDS "$DEBUGFS -w -R \\\"ln $ino /lost+found\\\" \
+                ${MDT_DEVNAME}"
+
+       setup_noconfig || error "remounting the filesystem failed"
+
+       do_facet $SINGLEMDS $LCTL lfsck_start -M ${MDT_DEV} -t namespace || {
+               error "can't start lfsck namespace"
+       }
+
+       sleep 5
+       wait_update_facet $SINGLEMDS "$LCTL get_param -n \
+               mdd.${MDT_DEV}.lfsck_namespace |
+               awk '/^status/ { print \\\$2 }'" "completed" 32 || {
+               error "(2) unexpected status"
+       }
+
+       stopall || error "stopping for e2fsck run"
+       for num in $(seq $MDSCOUNT); do
+               run_e2fsck $(facet_active_host mds$num) \
+                       $(mdsdevname $num) "-y" ||
+                       error "e2fsck MDT$num failed"
+       done
+       setup_noconfig || error "remounting the filesystem failed"
+
+       # need to delete this file to avoid problems in other tests
+       rm -f $file
+       cleanup || error "stopping systems failed"
+}
+run_test 61b "large xattr"
 
 test_62() {
        if [ "$mds1_FSTYPE" != ldiskfs ]; then