From 31e047125e47f2cfe056a139bfd490042fa59a29 Mon Sep 17 00:00:00 2001 From: Patrick Farrell Date: Wed, 17 Nov 2021 15:11:45 -0500 Subject: [PATCH] LU-15245 mdc: GET(X)ATTR to READPAGE portal Send the MDS_GETATTR and MDS_GETXATTR RPCs to the MDS_READPAGE_PORTAL instead of the default portal to avoid deadlocks with other MDS_REINT RPCs that may block all of the MDS service threads on that portal. This deadlock occurs with MDS_GETXATTR when selinux is enabled, because getxattr becomes part of lookup, so it takes a reference on a lock used for lookup. However, all of the MDS service threads on the default portal can be consumed by threads waiting for that lock, resulting in a deadlock when the getxattr can't be processed. Lustre-change: https://review.whamcloud.com/45593 Lustre-commit: ebb035756eb059b255d4c8245d42bc5d5b96bab9 (tbd) Signed-off-by: Andreas Dilger Signed-off-by: Patrick Farrell Change-Id: I4fbae266022ee9fa38f3196acb1443df5056fe5e Reviewed-on: https://review.whamcloud.com/45594 Tested-by: jenkins Tested-by: Maloo --- lustre/mdc/mdc_request.c | 31 +++++++++++++++++++------------ 1 file changed, 19 insertions(+), 12 deletions(-) diff --git a/lustre/mdc/mdc_request.c b/lustre/mdc/mdc_request.c index d47e747..43bedb7 100644 --- a/lustre/mdc/mdc_request.c +++ b/lustre/mdc/mdc_request.c @@ -221,14 +221,17 @@ static int mdc_getattr(struct obd_export *exp, struct md_op_data *op_data, *request = NULL; req = ptlrpc_request_alloc(imp, &RQF_MDS_GETATTR); - if (req == NULL) - RETURN(-ENOMEM); + if (req == NULL) + RETURN(-ENOMEM); - rc = ptlrpc_request_pack(req, LUSTRE_MDS_VERSION, MDS_GETATTR); - if (rc) { - ptlrpc_request_free(req); - RETURN(rc); - } + rc = ptlrpc_request_pack(req, LUSTRE_MDS_VERSION, MDS_GETATTR); + if (rc) { + ptlrpc_request_free(req); + RETURN(rc); + } + + /* LU-15245: avoid deadlock with modifying RPCs on MDS_REQUEST_PORTAL */ + req->rq_request_portal = MDS_READPAGE_PORTAL; again: mdc_pack_body(req, &op_data->op_fid1, op_data->op_valid, @@ -388,14 +391,18 @@ static int mdc_xattr_common(struct obd_export *exp,const struct req_format *fmt, rec->sx_fsgid = from_kgid(&init_user_ns, current_fsgid()); rec->sx_cap = cfs_curproc_cap_pack(); rec->sx_suppgid1 = suppgid; - rec->sx_suppgid2 = -1; - rec->sx_fid = *fid; - rec->sx_valid = valid | OBD_MD_FLCTIME; + rec->sx_suppgid2 = -1; + rec->sx_fid = *fid; + rec->sx_valid = valid | OBD_MD_FLCTIME; rec->sx_time = ktime_get_real_seconds(); - rec->sx_size = output_size; - rec->sx_flags = flags; + rec->sx_size = output_size; + rec->sx_flags = flags; } else { mdc_pack_body(req, fid, valid, output_size, suppgid, flags); + /* Avoid deadlock with modifying RPCs on MDS_REQUEST_PORTAL. + * See LU-15245. + */ + req->rq_request_portal = MDS_READPAGE_PORTAL; } if (xattr_name) { -- 1.8.3.1