/* Already unlinked. Just update nlink and return success */
if (rc == -ENOENT) {
clear_nlink(inode);
+ /* If it is striped directory, and there is bad stripe
+ * Let's revalidate the dentry again, instead of returning
+ * error */
+ if (S_ISDIR(inode->i_mode) &&
+ ll_i2info(inode)->lli_lsm_md != NULL)
+ return 0;
+
/* This path cannot be hit for regular files unless in
* case of obscure races, so no need to to validate
* size. */
/* set the directory layout */
if (lli->lli_lsm_md == NULL) {
+ struct cl_attr *attr;
rc = ll_init_lsm_md(inode, md);
if (rc != 0)
RETURN(rc);
lli->lli_lsm_md = lsm;
- /* set lsm_md to NULL, so the following free lustre_md
+
+ OBD_ALLOC_PTR(attr);
+ if (attr == NULL)
+ RETURN(-ENOMEM);
+
+ /* validate the lsm */
+ rc = md_merge_attr(ll_i2mdexp(inode), lsm, attr,
+ ll_md_blocking_ast);
+ if (rc != 0) {
+ OBD_FREE_PTR(attr);
+ RETURN(rc);
+ }
+
+ if (md->body->mbo_valid & OBD_MD_FLNLINK)
+ md->body->mbo_nlink = attr->cat_nlink;
+ if (md->body->mbo_valid & OBD_MD_FLSIZE)
+ md->body->mbo_size = attr->cat_size;
+ if (md->body->mbo_valid & OBD_MD_FLATIME)
+ md->body->mbo_atime = attr->cat_atime;
+ if (md->body->mbo_valid & OBD_MD_FLCTIME)
+ md->body->mbo_ctime = attr->cat_ctime;
+ if (md->body->mbo_valid & OBD_MD_FLMTIME)
+ md->body->mbo_mtime = attr->cat_mtime;
+
+ OBD_FREE_PTR(attr);
+
+
+ /* set lsm_md to NULL, so the following free lustre_md
* will not free this lsm */
md->lmv = NULL;
CDEBUG(D_INODE, "Set lsm %p magic %x to "DFID"\n", lsm,
&RMF_MDT_BODY);
LASSERT(body != NULL);
if (unlikely(body->mbo_nlink < 2)) {
- CERROR("%s: nlink %d < 2 corrupt stripe %d "DFID
- ":" DFID"\n",
+ /* If this is bad stripe, most likely due
+ * to the race between close(unlink) and
+ * getattr, let's return -EONENT, so llite
+ * will revalidate the dentry see
+ * ll_inode_revalidate_fini() */
+ CDEBUG(D_INODE, "%s: nlink %d < 2 bad stripe %d"
+ DFID ":" DFID"\n",
obd->obd_name, body->mbo_nlink, i,
PFID(&lsm->lsm_md_oinfo[i].lmo_fid),
PFID(&lsm->lsm_md_oinfo[0].lmo_fid));
it.d.lustre.it_lock_mode = 0;
}
- GOTO(cleanup, rc = -EIO);
+ GOTO(cleanup, rc = -ENOENT);
}
-
i_size_write(inode, body->mbo_size);
inode->i_blocks = body->mbo_blocks;
set_nlink(inode, body->mbo_nlink);