⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mds_reint.c

📁 lustre 1.6.5 source code
💻 C
📖 第 1 页 / 共 5 页
字号:
        } else if (ia_valid & ATTR_MODE) {                int mode = attr->ia_mode;                /* chmod */                if (attr->ia_mode == (umode_t)-1)                        mode = inode->i_mode;                attr->ia_mode =                        (mode & S_IALLUGO) | (inode->i_mode & ~S_IALLUGO);        }        RETURN(0);}void mds_steal_ack_locks(struct ptlrpc_request *req){        struct obd_export         *exp = req->rq_export;        struct list_head          *tmp;        struct ptlrpc_reply_state *oldrep;        struct ptlrpc_service     *svc;        int                        i;        /* CAVEAT EMPTOR: spinlock order */        spin_lock(&exp->exp_lock);        list_for_each (tmp, &exp->exp_outstanding_replies) {                oldrep = list_entry(tmp, struct ptlrpc_reply_state,rs_exp_list);                if (oldrep->rs_xid != req->rq_xid)                        continue;                if (lustre_msg_get_opc(oldrep->rs_msg) !=                    lustre_msg_get_opc(req->rq_reqmsg))                        CERROR ("Resent req xid "LPX64" has mismatched opc: "                                "new %d old %d\n", req->rq_xid,                                lustre_msg_get_opc(req->rq_reqmsg),                                lustre_msg_get_opc(oldrep->rs_msg));                svc = oldrep->rs_service;                spin_lock (&svc->srv_lock);                list_del_init (&oldrep->rs_exp_list);                CWARN("Stealing %d locks from rs %p x"LPD64".t"LPD64                      " o%d NID %s\n",                      oldrep->rs_nlocks, oldrep,                      oldrep->rs_xid, oldrep->rs_transno,                      lustre_msg_get_opc(oldrep->rs_msg),                      libcfs_nid2str(exp->exp_connection->c_peer.nid));                for (i = 0; i < oldrep->rs_nlocks; i++)                        ptlrpc_save_lock(req,                                         &oldrep->rs_locks[i],                                         oldrep->rs_modes[i]);                oldrep->rs_nlocks = 0;                DEBUG_REQ(D_DLMTRACE, req, "stole locks for");                ptlrpc_schedule_difficult_reply (oldrep);                spin_unlock (&svc->srv_lock);                break;        }        spin_unlock(&exp->exp_lock);}void mds_req_from_mcd(struct ptlrpc_request *req, struct mds_client_data *mcd){        if (lustre_msg_get_opc(req->rq_reqmsg) == MDS_CLOSE) {                req->rq_transno = le64_to_cpu(mcd->mcd_last_close_transno);                lustre_msg_set_transno(req->rq_repmsg, req->rq_transno);                req->rq_status = le32_to_cpu(mcd->mcd_last_close_result);                lustre_msg_set_status(req->rq_repmsg, req->rq_status);        } else {                req->rq_transno = le64_to_cpu(mcd->mcd_last_transno);                lustre_msg_set_transno(req->rq_repmsg, req->rq_transno);                req->rq_status = le32_to_cpu(mcd->mcd_last_result);                lustre_msg_set_status(req->rq_repmsg, req->rq_status);        }        DEBUG_REQ(D_RPCTRACE, req, "restoring transno "LPD64"/status %d",                  req->rq_transno, req->rq_status);        mds_steal_ack_locks(req);}static void reconstruct_reint_setattr(struct mds_update_record *rec,                                      int offset, struct ptlrpc_request *req){        struct mds_export_data *med = &req->rq_export->exp_mds_data;        struct mds_obd *obd = &req->rq_export->exp_obd->u.mds;        struct dentry *de;        struct mds_body *body;        mds_req_from_mcd(req, med->med_mcd);        de = mds_fid2dentry(obd, rec->ur_fid1, NULL);        if (IS_ERR(de)) {                LASSERT(PTR_ERR(de) == req->rq_status);                return;        }        body = lustre_msg_buf(req->rq_repmsg, offset, sizeof(*body));        mds_pack_inode2fid(&body->fid1, de->d_inode);        mds_pack_inode2body(body, de->d_inode);        /* Don't return OST-specific attributes if we didn't just set them */        if (rec->ur_iattr.ia_valid & ATTR_SIZE)                body->valid |= OBD_MD_FLSIZE | OBD_MD_FLBLOCKS;        if (rec->ur_iattr.ia_valid & (ATTR_MTIME | ATTR_MTIME_SET))                body->valid |= OBD_MD_FLMTIME;        if (rec->ur_iattr.ia_valid & (ATTR_ATIME | ATTR_ATIME_SET))                body->valid |= OBD_MD_FLATIME;        l_dput(de);}int mds_osc_setattr_async(struct obd_device *obd, struct inode *inode,                          struct lov_mds_md *lmm, int lmm_size,                          struct llog_cookie *logcookies, struct ll_fid *fid){        struct mds_obd *mds = &obd->u.mds;        struct obd_trans_info oti = { 0 };        struct obd_info oinfo = { { { 0 } } };        int rc;        ENTRY;        if (OBD_FAIL_CHECK(OBD_FAIL_MDS_OST_SETATTR))                RETURN(0);        /* first get memory EA */        OBDO_ALLOC(oinfo.oi_oa);        if (!oinfo.oi_oa)                RETURN(-ENOMEM);        LASSERT(lmm);        rc = obd_unpackmd(mds->mds_osc_exp, &oinfo.oi_md, lmm, lmm_size);        if (rc < 0) {                CERROR("Error unpack md %p for inode %lu\n", lmm, inode->i_ino);                GOTO(out, rc);        }        rc = obd_checkmd(mds->mds_osc_exp, obd->obd_self_export, oinfo.oi_md);        if (rc) {                CERROR("Error revalidate lsm %p \n", oinfo.oi_md);                GOTO(out, rc);        }        /* then fill oa */        obdo_from_inode(oinfo.oi_oa, inode, OBD_MD_FLUID | OBD_MD_FLGID);        oinfo.oi_oa->o_valid |= OBD_MD_FLID;        oinfo.oi_oa->o_id = oinfo.oi_md->lsm_object_id;        if (logcookies) {                oinfo.oi_oa->o_valid |= OBD_MD_FLCOOKIE;                oti.oti_logcookies = logcookies;        }        LASSERT(fid != NULL);        oinfo.oi_oa->o_fid = fid->id;        oinfo.oi_oa->o_generation = fid->generation;        oinfo.oi_oa->o_valid |= OBD_MD_FLFID | OBD_MD_FLGENER;        /* do async setattr from mds to ost not waiting for responses. */        rc = obd_setattr_async(mds->mds_osc_exp, &oinfo, &oti, NULL);        if (rc)                CDEBUG(D_INODE, "mds to ost setattr objid 0x"LPX64                       " on ost error %d\n", oinfo.oi_md->lsm_object_id, rc);out:        if (oinfo.oi_md)                obd_free_memmd(mds->mds_osc_exp, &oinfo.oi_md);        OBDO_FREE(oinfo.oi_oa);        RETURN(rc);}/* In the raw-setattr case, we lock the child inode. * In the write-back case or if being called from open, the client holds a lock * already. * * We use the ATTR_FROM_OPEN flag to tell these cases apart. */static int mds_reint_setattr(struct mds_update_record *rec, int offset,                             struct ptlrpc_request *req,                             struct lustre_handle *lh){        unsigned int ia_valid = rec->ur_iattr.ia_valid;        struct mds_obd *mds = mds_req2mds(req);        struct obd_device *obd = req->rq_export->exp_obd;        struct mds_body *body;        struct dentry *de;        struct inode *inode = NULL;        struct lustre_handle lockh;        void *handle = NULL;        struct mds_logcancel_data *mlcd = NULL;        struct lov_mds_md *lmm = NULL;        struct llog_cookie *logcookies = NULL;        int lmm_size = 0, need_lock = 1, cookie_size = 0;        int rc = 0, cleanup_phase = 0, err, locked = 0, sync = 0;        unsigned int qcids[MAXQUOTAS] = { 0, 0 };        unsigned int qpids[MAXQUOTAS] = { rec->ur_iattr.ia_uid,                                           rec->ur_iattr.ia_gid };        ENTRY;        LASSERT(offset == REQ_REC_OFF);        offset = REPLY_REC_OFF;        DEBUG_REQ(D_INODE, req, "setattr "LPU64"/%u %x", rec->ur_fid1->id,                  rec->ur_fid1->generation, rec->ur_iattr.ia_valid);        OBD_COUNTER_INCREMENT(obd, setattr);        MDS_CHECK_RESENT(req, reconstruct_reint_setattr(rec, offset, req));        if (rec->ur_dlm)                ldlm_request_cancel(req, rec->ur_dlm, 0);        if (rec->ur_iattr.ia_valid & ATTR_FROM_OPEN ||            (req->rq_export->exp_connect_flags & OBD_CONNECT_RDONLY)) {                de = mds_fid2dentry(mds, rec->ur_fid1, NULL);                if (IS_ERR(de))                        GOTO(cleanup, rc = PTR_ERR(de));                if (req->rq_export->exp_connect_flags & OBD_CONNECT_RDONLY)                        GOTO(cleanup, rc = -EROFS);        } else {                __u64 lockpart = MDS_INODELOCK_UPDATE;                if (rec->ur_iattr.ia_valid & (ATTR_MODE|ATTR_UID|ATTR_GID))                        lockpart |= MDS_INODELOCK_LOOKUP;                de = mds_fid2locked_dentry(obd, rec->ur_fid1, NULL, LCK_EX,                                           &lockh, NULL, 0, lockpart);                if (IS_ERR(de))                        GOTO(cleanup, rc = PTR_ERR(de));                locked = 1;        }        cleanup_phase = 1;        inode = de->d_inode;        LASSERT(inode);        if ((rec->ur_iattr.ia_valid & ATTR_FROM_OPEN) ||            (rec->ur_iattr.ia_valid & ATTR_SIZE)) {                /* Check write access for the O_TRUNC case */                if (mds_query_write_access(inode) < 0)                        GOTO(cleanup, rc = -ETXTBSY);        }        /* save uid/gid for quota acq/rel */        qcids[USRQUOTA] = inode->i_uid;        qcids[GRPQUOTA] = inode->i_gid;        if ((S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)) &&            rec->ur_eadata != NULL) {                LOCK_INODE_MUTEX(inode);                need_lock = 0;        }        OBD_FAIL_WRITE(obd, OBD_FAIL_MDS_REINT_SETATTR_WRITE, inode->i_sb);        /* start a log jounal handle if needed */        if (S_ISREG(inode->i_mode) &&            rec->ur_iattr.ia_valid & (ATTR_UID | ATTR_GID)) {                lmm_size = mds->mds_max_mdsize;                OBD_ALLOC(lmm, lmm_size);                if (lmm == NULL)                        GOTO(cleanup, rc = -ENOMEM);                cleanup_phase = 2;                rc = mds_get_md(obd, inode, lmm, &lmm_size, need_lock, 0);                if (rc < 0)                        GOTO(cleanup, rc);                rc = 0;                handle = fsfilt_start_log(obd, inode, FSFILT_OP_SETATTR, NULL,                                          le32_to_cpu(lmm->lmm_stripe_count));        } else {                handle = fsfilt_start(obd, inode, FSFILT_OP_SETATTR, NULL);        }        if (IS_ERR(handle))                GOTO(cleanup, rc = PTR_ERR(handle));        if (rec->ur_iattr.ia_valid & (ATTR_MTIME | ATTR_CTIME))                CDEBUG(D_INODE, "setting mtime %lu, ctime %lu\n",                       LTIME_S(rec->ur_iattr.ia_mtime),                       LTIME_S(rec->ur_iattr.ia_ctime));        rc = mds_fix_attr(inode, rec);        if (rc)                GOTO(cleanup, rc);        if (rec->ur_iattr.ia_valid & ATTR_ATTR_FLAG) {  /* ioctl */                rc = fsfilt_iocontrol(obd, inode, NULL, EXT3_IOC_SETFLAGS,                                      (long)&rec->ur_flags);        } else if (rec->ur_iattr.ia_valid) {            /* setattr */                rc = fsfilt_setattr(obd, de, handle, &rec->ur_iattr, 0);                /* journal chown/chgrp in llog, just like unlink */                if (rc == 0 && lmm_size){                        cookie_size = mds_get_cookie_size(obd, lmm);                        OBD_ALLOC(logcookies, cookie_size);                        if (logcookies == NULL)                                GOTO(cleanup, rc = -ENOMEM);                        if (mds_log_op_setattr(obd, inode, lmm, lmm_size,                                               logcookies, cookie_size) <= 0) {                                OBD_FREE(logcookies, cookie_size);                                logcookies = NULL;                        }                }        }        if (rc == 0 && (S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)) &&            rec->ur_eadata != NULL) {                struct lov_stripe_md *lsm = NULL;                struct lov_user_md *lum = NULL;                rc = ll_permission(inode, MAY_WRITE, NULL);                if (rc < 0)                        GOTO(cleanup, rc);                lum = rec->ur_eadata;                /* if { size, offset, count } = { 0, -1, 0 } (i.e. all default                 * values specified) then delete default striping from dir. */                if (S_ISDIR(inode->i_mode) &&                    ((lum->lmm_stripe_size == 0 &&                      lum->lmm_stripe_offset ==                      (typeof(lum->lmm_stripe_offset))(-1) &&                      lum->lmm_stripe_count == 0) ||                    /* lmm_stripe_size == -1 is deprecated in 1.4.6 */                    lum->lmm_stripe_size ==                    (typeof(lum->lmm_stripe_size))(-1))){                        rc = fsfilt_set_md(obd, inode, handle, NULL, 0, "lov");

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -