Received: by 2002:a6b:500f:0:0:0:0:0 with SMTP id e15csp4865399iob; Mon, 9 May 2022 03:32:59 -0700 (PDT) X-Google-Smtp-Source: ABdhPJzz8yh893bM+06DCajRhGIIT49XwiRMkWmkDy/fN1DHk8Xtd4JlKdsmfxkvC99bW4izScEj X-Received: by 2002:a63:64c2:0:b0:3c6:2d70:9188 with SMTP id y185-20020a6364c2000000b003c62d709188mr12715402pgb.186.1652092379383; Mon, 09 May 2022 03:32:59 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1652092379; cv=none; d=google.com; s=arc-20160816; b=vs5HkQCiubyHcud5PlZ4MoDaZJ4I3XYflJQYH/JOpQMa2kNTpJoK5M0qw3vl0vGjau mwYG9uGeVgHLJ1g00g10DHqABgw6+5Agliad1LykALX4zWbTXQa7G+qfXwJkB5vEHiJR LC/vvoXX3R7JLJEb+//nDD/JXMBrL46X9Q7OQvbS2JXLHVVdE1A883b8sSGLrNCHwFOi QtEGF4OdkVOId5r6bp4s2tV5BJ+rjpqWNmoO0eS9fzHi9uRjdpXOV1uCn6/AGaQZvphg 7DK76XAKT2kYwU/N4NYFM7fJhGB+KQvP10P6necxla/GGkjPMC2eRJbJ8q/0vqzyK90X ui7A== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :references:in-reply-to:message-id:date:subject:cc:to:from; bh=vmnBFfBv4dGfiHGk+6+GLLGF9wN8GRIHp/BaJfNw38Q=; b=BCQTIfhbyoOsX7DzohQhjG6oiIICWgeoT+pS6euBbI91W3phPq0xpzG3ESrQAWaTYC PQdE+NlKqIO39rbB0+zKi9NT0TCnLItEu3J57JNQTy+9c04L0dzKUUbD7+SM6sHwSQah m5mokYPeVQZJFqi99LeXZzz/gnIjZCsdDhYKCSptt2A9Nytv/f3uelNnBrf+gH8Iktcm S7QwnyPMAAdUxv4var1lyBk8P6RHLTgfFG2wlW8hzuhcQXYyFSLhOm4Mnq26Y4mke4Gx mPmKxhA7yK1tuc+mUl9T/jMgGeLPkgmyG9GTiUKj3w9Z/88c4Q+sRkUpURgwCqE0bG5W TKzA== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=alibaba.com Return-Path: Received: from lindbergh.monkeyblade.net (lindbergh.monkeyblade.net. [2620:137:e000::1:18]) by mx.google.com with ESMTPS id d3-20020a637343000000b003c18351c4c1si15173412pgn.673.2022.05.09.03.32.59 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 09 May 2022 03:32:59 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:18 as permitted sender) client-ip=2620:137:e000::1:18; Authentication-Results: mx.google.com; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=alibaba.com Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by lindbergh.monkeyblade.net (Postfix) with ESMTP id AC3D2201C1B; Mon, 9 May 2022 03:02:54 -0700 (PDT) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S236798AbiEIHyE (ORCPT + 99 others); Mon, 9 May 2022 03:54:04 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59026 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S234790AbiEIHow (ORCPT ); Mon, 9 May 2022 03:44:52 -0400 Received: from out30-56.freemail.mail.aliyun.com (out30-56.freemail.mail.aliyun.com [115.124.30.56]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id F31BC14022; Mon, 9 May 2022 00:40:57 -0700 (PDT) X-Alimail-AntiSpam: AC=PASS;BC=-1|-1;BR=01201311R481e4;CH=green;DM=||false|;DS=||;FP=0|-1|-1|-1|0|-1|-1|-1;HT=e01e04395;MF=jefflexu@linux.alibaba.com;NM=1;PH=DS;RN=20;SR=0;TI=SMTPD_---0VCfaIjH_1652082033; Received: from localhost(mailfrom:jefflexu@linux.alibaba.com fp:SMTPD_---0VCfaIjH_1652082033) by smtp.aliyun-inc.com(127.0.0.1); Mon, 09 May 2022 15:40:34 +0800 From: Jeffle Xu To: dhowells@redhat.com, linux-cachefs@redhat.com, xiang@kernel.org, chao@kernel.org, linux-erofs@lists.ozlabs.org Cc: torvalds@linux-foundation.org, gregkh@linuxfoundation.org, willy@infradead.org, linux-fsdevel@vger.kernel.org, joseph.qi@linux.alibaba.com, bo.liu@linux.alibaba.com, tao.peng@linux.alibaba.com, gerry@linux.alibaba.com, eguan@linux.alibaba.com, linux-kernel@vger.kernel.org, luodaowen.backend@bytedance.com, tianzichen@kuaishou.com, yinxin.x@bytedance.com, zhangjiachen.jaycee@bytedance.com, zhujia.zj@bytedance.com Subject: [PATCH v11 03/22] cachefiles: unbind cachefiles gracefully in on-demand mode Date: Mon, 9 May 2022 15:40:09 +0800 Message-Id: <20220509074028.74954-4-jefflexu@linux.alibaba.com> X-Mailer: git-send-email 2.27.0 In-Reply-To: <20220509074028.74954-1-jefflexu@linux.alibaba.com> References: <20220509074028.74954-1-jefflexu@linux.alibaba.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00, HEADER_FROM_DIFFERENT_DOMAINS,MAILING_LIST_MULTI,RDNS_NONE, SPF_HELO_NONE,T_SCC_BODY_TEXT_LINE,UNPARSEABLE_RELAY autolearn=no autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Add a refcount to avoid the deadlock in on-demand read mode. The on-demand read mode will pin the corresponding cachefiles object for each anonymous fd. The cachefiles object is unpinned when the anonymous fd gets closed. When the user daemon exits and the fd of "/dev/cachefiles" device node gets closed, it will wait for all cahcefiles objects getting withdrawn. Then if there's any anonymous fd getting closed after the fd of the device node, the user daemon will hang forever, waiting for all objects getting withdrawn. To fix this, add a refcount indicating if there's any object pinned by anonymous fds. The cachefiles cache gets unbound and withdrawn when the refcount is decreased to 0. It won't change the behaviour of the original mode, in which case the cachefiles cache gets unbound and withdrawn as long as the fd of the device node gets closed. Signed-off-by: Jeffle Xu --- fs/cachefiles/daemon.c | 19 ++++++++++++++++--- fs/cachefiles/internal.h | 3 +++ fs/cachefiles/ondemand.c | 3 +++ 3 files changed, 22 insertions(+), 3 deletions(-) diff --git a/fs/cachefiles/daemon.c b/fs/cachefiles/daemon.c index d5417da7f792..5b1d0642c749 100644 --- a/fs/cachefiles/daemon.c +++ b/fs/cachefiles/daemon.c @@ -111,6 +111,7 @@ static int cachefiles_daemon_open(struct inode *inode, struct file *file) INIT_LIST_HEAD(&cache->volumes); INIT_LIST_HEAD(&cache->object_list); spin_lock_init(&cache->object_list_lock); + refcount_set(&cache->unbind_pincount, 1); xa_init_flags(&cache->reqs, XA_FLAGS_ALLOC); xa_init_flags(&cache->ondemand_ids, XA_FLAGS_ALLOC1); @@ -164,6 +165,20 @@ static void cachefiles_flush_reqs(struct cachefiles_cache *cache) xa_destroy(&cache->ondemand_ids); } +void cachefiles_put_unbind_pincount(struct cachefiles_cache *cache) +{ + if (refcount_dec_and_test(&cache->unbind_pincount)) { + cachefiles_daemon_unbind(cache); + cachefiles_open = 0; + kfree(cache); + } +} + +void cachefiles_get_unbind_pincount(struct cachefiles_cache *cache) +{ + refcount_inc(&cache->unbind_pincount); +} + /* * Release a cache. */ @@ -179,14 +194,12 @@ static int cachefiles_daemon_release(struct inode *inode, struct file *file) if (cachefiles_in_ondemand_mode(cache)) cachefiles_flush_reqs(cache); - cachefiles_daemon_unbind(cache); /* clean up the control file interface */ cache->cachefilesd = NULL; file->private_data = NULL; - cachefiles_open = 0; - kfree(cache); + cachefiles_put_unbind_pincount(cache); _leave(""); return 0; diff --git a/fs/cachefiles/internal.h b/fs/cachefiles/internal.h index 4f5150a96849..e5c612888f84 100644 --- a/fs/cachefiles/internal.h +++ b/fs/cachefiles/internal.h @@ -109,6 +109,7 @@ struct cachefiles_cache { char *rootdirname; /* name of cache root directory */ char *secctx; /* LSM security context */ char *tag; /* cache binding tag */ + refcount_t unbind_pincount;/* refcount to do daemon unbind */ struct xarray reqs; /* xarray of pending on-demand requests */ struct xarray ondemand_ids; /* xarray for ondemand_id allocation */ u32 ondemand_id_next; @@ -171,6 +172,8 @@ extern int cachefiles_has_space(struct cachefiles_cache *cache, * daemon.c */ extern const struct file_operations cachefiles_daemon_fops; +extern void cachefiles_get_unbind_pincount(struct cachefiles_cache *cache); +extern void cachefiles_put_unbind_pincount(struct cachefiles_cache *cache); /* * error_inject.c diff --git a/fs/cachefiles/ondemand.c b/fs/cachefiles/ondemand.c index 64fc312b16d3..7946ee6c40be 100644 --- a/fs/cachefiles/ondemand.c +++ b/fs/cachefiles/ondemand.c @@ -14,6 +14,7 @@ static int cachefiles_ondemand_fd_release(struct inode *inode, object->ondemand_id = CACHEFILES_ONDEMAND_ID_CLOSED; xa_erase(&cache->ondemand_ids, object_id); cachefiles_put_object(object, cachefiles_obj_put_ondemand_fd); + cachefiles_put_unbind_pincount(cache); return 0; } @@ -169,6 +170,8 @@ static int cachefiles_ondemand_get_fd(struct cachefiles_req *req) load->fd = fd; req->msg.object_id = object_id; object->ondemand_id = object_id; + + cachefiles_get_unbind_pincount(cache); return 0; err_put_fd: -- 2.27.0