From patchwork Tue Feb 6 11:32:07 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Steven Rostedt X-Patchwork-Id: 197341 Return-Path: Delivered-To: ouuuleilei@gmail.com Received: by 2002:a05:7301:168b:b0:106:860b:bbdd with SMTP id ma11csp1481127dyb; Tue, 6 Feb 2024 03:49:39 -0800 (PST) X-Google-Smtp-Source: AGHT+IHcOq9Nb03GAWcwBhdtlAt9AOGiDXL0OmPvUXKIh7BrP+Di7MAqQqokJhbnwkZGMo17q/pL X-Received: by 2002:a05:6358:5e05:b0:176:56b9:d4e1 with SMTP id q5-20020a0563585e0500b0017656b9d4e1mr2366514rwn.23.1707220179059; Tue, 06 Feb 2024 03:49:39 -0800 (PST) ARC-Seal: i=2; a=rsa-sha256; t=1707220179; cv=pass; d=google.com; s=arc-20160816; b=NlGuU8+l9OhI3ctc5IU2v7PfRl6OGUmPdzggriAKvi9XTzC7/2b5ibpn8QO1fV0X42 9MBmjD+kP/PeCwG5lGRTWfSdzPlQJ5TnU6kWluWjEaxygncp+VKDxOgC2VsAj41doUs1 qN4OqxKH6HIvIx9xLPfHo4W5eamJtb4aYYK/JPxP0zv2zKkswTGtSi8jshmPtB6B7/4P aNyOgx3Vpy2oFdeZcJF6DfVCfd8WzHwEbUTepjYaegiFrVzwuLiMGKcKBOazkJuxXgkS leXq+e3UF2AGk+2WixUpFiDyz9LgRffYgQcreief6+005GBmDfQcD8BVUlWZEa7g1cXp yfXg== ARC-Message-Signature: i=2; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=mime-version:list-unsubscribe:list-subscribe:list-id:precedence :references:subject:cc:to:from:date:user-agent:message-id; bh=4kJElqzHxcp8SMj6H2Aq/UhawQMCk4MTJETashvgb4Y=; fh=R3Gp4ReT6kVBtpDTnuSowjwl8rBEZgedXHtpbDdN+qM=; b=w/lXCTbzR3UXJFE+nptRXFWZSiYlVD4mQjo+Bk17rDGUHqnCmDsVdclRAKdLg1ZXkS f8ESIQ82pWbJlMVMRLfUGraLBU3SXYQUkvES+fcEt3wihhnJJU0KaLRe28YP7RmjZevk BChGaRfzuucb+j3HOWQ7M5DxoUnDYbZHpnOj6kX70eJcdRIA8zVDsDwbHkBzM8h+Lbjz z8LQP+mnX25wu626GEszj/2nNBVEkUdLGjcEE4x5DAr+MqbaHq8+2dCb2xaPFsSvKKXQ SQoB3kbzuNBYa3JGXVfes7h1CziO/luWLqFoXDULZrd0u3Vy+e0bDcQMW4UMcsUj6s6B 1blQ==; dara=google.com ARC-Authentication-Results: i=2; mx.google.com; arc=pass (i=1); spf=pass (google.com: domain of linux-kernel+bounces-54795-ouuuleilei=gmail.com@vger.kernel.org designates 139.178.88.99 as permitted sender) smtp.mailfrom="linux-kernel+bounces-54795-ouuuleilei=gmail.com@vger.kernel.org" X-Forwarded-Encrypted: i=1; AJvYcCVQGb9p1OaE+6BHstN/TR4ajLzM1UactKSYbmxqTFWnLIde79zQ0quFbcvkNVhPDRG0PZXoKBSgLEgcnujwePeB33P1iA== Received: from sv.mirrors.kernel.org (sv.mirrors.kernel.org. [139.178.88.99]) by mx.google.com with ESMTPS id q124-20020a632a82000000b005dc15e82c47si1555129pgq.363.2024.02.06.03.49.38 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 06 Feb 2024 03:49:39 -0800 (PST) Received-SPF: pass (google.com: domain of linux-kernel+bounces-54795-ouuuleilei=gmail.com@vger.kernel.org designates 139.178.88.99 as permitted sender) client-ip=139.178.88.99; Authentication-Results: mx.google.com; arc=pass (i=1); spf=pass (google.com: domain of linux-kernel+bounces-54795-ouuuleilei=gmail.com@vger.kernel.org designates 139.178.88.99 as permitted sender) smtp.mailfrom="linux-kernel+bounces-54795-ouuuleilei=gmail.com@vger.kernel.org" Received: from smtp.subspace.kernel.org (wormhole.subspace.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by sv.mirrors.kernel.org (Postfix) with ESMTPS id C4BEF281AAA for ; Tue, 6 Feb 2024 11:49:38 +0000 (UTC) Received: from localhost.localdomain (localhost.localdomain [127.0.0.1]) by smtp.subspace.kernel.org (Postfix) with ESMTP id E8DD0137C20; Tue, 6 Feb 2024 11:33:36 +0000 (UTC) Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 7CF9F13399D; Tue, 6 Feb 2024 11:33:31 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1707219211; cv=none; b=KVDfZGkyJDJsBZQxdY25OgvqKHJDlyRTTy+iqUjf8UB/W1+xoFXE+W9nua+bRGJD4O/nkU3bGWxBtROn1hYQoK3z5a/1itYAE5WA1HExltIUDUJVMItK//1NeQJOX776xVmMPG7trtfqomhIezV0Pie0hUsvz2xy8D7uhutxQsM= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1707219211; c=relaxed/simple; bh=iFY7n9Vhp/1z36GCtxu4sEAjzXxFREHW/cV48tOlaOw=; h=Message-ID:Date:From:To:Cc:Subject:References:MIME-Version: Content-Type; b=N1C0I2XVTIRK7a+hXA0K+5uyWQ6KCvvPbZBNFYN07v7gzqKclkMC+svMY+pSrdEhEFIi43a42bY3w2CsAVDHeyFIzrekp5t3hUs8k5Y7z8muOLlijj2FQDwmL58MIX/N1yeEV8WBJMi2jYDME6lVTKn3r9MfGu48ZG96lmIZpjA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 Received: by smtp.kernel.org (Postfix) with ESMTPSA id 589ABC43390; Tue, 6 Feb 2024 11:33:31 +0000 (UTC) Received: from rostedt by gandalf with local (Exim 4.97) (envelope-from ) id 1rXJiB-00000006aKn-2upQ; Tue, 06 Feb 2024 06:33:59 -0500 Message-ID: <20240206113359.552951427@rostedt.homelinux.com> User-Agent: quilt/0.67 Date: Tue, 06 Feb 2024 06:32:07 -0500 From: Steven Rostedt To: linux-kernel@vger.kernel.org, stable@vger.kernel.org Cc: Linus Torvalds , Greg Kroah-Hartman , Sasha Levin , Masami Hiramatsu , Mark Rutland , Mathieu Desnoyers , Christian Brauner , Al Viro , Ajay Kaher , kernel test robot Subject: [v6.7][PATCH v2 09/23] eventfs: Do not create dentries nor inodes in iterate_shared References: <20240206113158.822006147@rostedt.homelinux.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-getmail-retrieved-from-mailbox: INBOX X-GMAIL-THRID: 1790150106536649920 X-GMAIL-MSGID: 1790150106536649920 From: "Steven Rostedt (Google)" The original eventfs code added a wrapper around the dcache_readdir open callback and created all the dentries and inodes at open, and increment their ref count. A wrapper was added around the dcache_readdir release function to decrement all the ref counts of those created inodes and dentries. But this proved to be buggy[1] for when a kprobe was created during a dir read, it would create a dentry between the open and the release, and because the release would decrement all ref counts of all files and directories, that would include the kprobe directory that was not there to have its ref count incremented in open. This would cause the ref count to go to negative and later crash the kernel. To solve this, the dentries and inodes that were created and had their ref count upped in open needed to be saved. That list needed to be passed from the open to the release, so that the release would only decrement the ref counts of the entries that were incremented in the open. Unfortunately, the dcache_readdir logic was already using the file->private_data, which is the only field that can be used to pass information from the open to the release. What was done was the eventfs created another descriptor that had a void pointer to save the dcache_readdir pointer, and it wrapped all the callbacks, so that it could save the list of entries that had their ref counts incremented in the open, and pass it to the release. The wrapped callbacks would just put back the dcache_readdir pointer and call the functions it used so it could still use its data[2]. But Linus had an issue with the "hijacking" of the file->private_data (unfortunately this discussion was on a security list, so no public link). Which we finally agreed on doing everything within the iterate_shared callback and leave the dcache_readdir out of it[3]. All the information needed for the getents() could be created then. But this ended up being buggy too[4]. The iterate_shared callback was not the right place to create the dentries and inodes. Even Christian Brauner had issues with that[5]. An attempt was to go back to creating the inodes and dentries at the open, create an array to store the information in the file->private_data, and pass that information to the other callbacks.[6] The difference between that and the original method, is that it does not use dcache_readdir. It also does not up the ref counts of the dentries and pass them. Instead, it creates an array of a structure that saves the dentry's name and inode number. That information is used in the iterate_shared callback, and the array is freed in the dir release. The dentries and inodes created in the open are not used for the iterate_share or release callbacks. Just their names and inode numbers. Linus did not like that either[7] and just wanted to remove the dentries being created in iterate_shared and use the hard coded inode numbers. [ All this while Linus enjoyed an unexpected vacation during the merge window due to lack of power. ] [1] https://lore.kernel.org/linux-trace-kernel/20230919211804.230edf1e@gandalf.local.home/ [2] https://lore.kernel.org/linux-trace-kernel/20230922163446.1431d4fa@gandalf.local.home/ [3] https://lore.kernel.org/linux-trace-kernel/20240104015435.682218477@goodmis.org/ [4] https://lore.kernel.org/all/202401152142.bfc28861-oliver.sang@intel.com/ [5] https://lore.kernel.org/all/20240111-unzahl-gefegt-433acb8a841d@brauner/ [6] https://lore.kernel.org/all/20240116114711.7e8637be@gandalf.local.home/ [7] https://lore.kernel.org/all/20240116170154.5bf0a250@gandalf.local.home/ Link: https://lore.kernel.org/linux-trace-kernel/20240116211353.573784051@goodmis.org Cc: Masami Hiramatsu Cc: Mark Rutland Cc: Mathieu Desnoyers Cc: Linus Torvalds Cc: Christian Brauner Cc: Al Viro Cc: Ajay Kaher Fixes: 493ec81a8fb8 ("eventfs: Stop using dcache_readdir() for getdents()") Reported-by: kernel test robot Closes: https://lore.kernel.org/oe-lkp/202401152142.bfc28861-oliver.sang@intel.com Signed-off-by: Steven Rostedt (Google) (cherry picked from commit 852e46e239ee6db3cd220614cf8bce96e79227c2) --- fs/tracefs/event_inode.c | 20 +++++--------------- 1 file changed, 5 insertions(+), 15 deletions(-) diff --git a/fs/tracefs/event_inode.c b/fs/tracefs/event_inode.c index 5edf0b96758b..10580d6b5012 100644 --- a/fs/tracefs/event_inode.c +++ b/fs/tracefs/event_inode.c @@ -727,8 +727,6 @@ static int eventfs_iterate(struct file *file, struct dir_context *ctx) struct eventfs_inode *ei_child; struct tracefs_inode *ti; struct eventfs_inode *ei; - struct dentry *ei_dentry = NULL; - struct dentry *dentry; const char *name; umode_t mode; int idx; @@ -749,11 +747,11 @@ static int eventfs_iterate(struct file *file, struct dir_context *ctx) mutex_lock(&eventfs_mutex); ei = READ_ONCE(ti->private); - if (ei && !ei->is_freed) - ei_dentry = READ_ONCE(ei->dentry); + if (ei && ei->is_freed) + ei = NULL; mutex_unlock(&eventfs_mutex); - if (!ei || !ei_dentry) + if (!ei) goto out; /* @@ -780,11 +778,7 @@ static int eventfs_iterate(struct file *file, struct dir_context *ctx) if (r <= 0) continue; - dentry = create_file_dentry(ei, i, ei_dentry, name, mode, cdata, fops); - if (!dentry) - goto out; - ino = dentry->d_inode->i_ino; - dput(dentry); + ino = EVENTFS_FILE_INODE_INO; if (!dir_emit(ctx, name, strlen(name), ino, DT_REG)) goto out; @@ -808,11 +802,7 @@ static int eventfs_iterate(struct file *file, struct dir_context *ctx) name = ei_child->name; - dentry = create_dir_dentry(ei, ei_child, ei_dentry); - if (!dentry) - goto out_dec; - ino = dentry->d_inode->i_ino; - dput(dentry); + ino = EVENTFS_DIR_INODE_INO; if (!dir_emit(ctx, name, strlen(name), ino, DT_DIR)) goto out_dec;