Message ID | 20230516160753.32317-2-rf@opensource.cirrus.com |
---|---|
State | New |
Headers |
Return-Path: <linux-kernel-owner@vger.kernel.org> Delivered-To: ouuuleilei@gmail.com Received: by 2002:a59:b0ea:0:b0:3b6:4342:cba0 with SMTP id b10csp543567vqo; Tue, 16 May 2023 09:11:45 -0700 (PDT) X-Google-Smtp-Source: ACHHUZ7A2lVxZ2XPNzP+SpRDnu2JF+plPWxEaZ3YFdONUW8FCXzMRdnoGUZ1h4UPf2um8MzagPO9 X-Received: by 2002:a05:6a20:3947:b0:104:b21f:26b0 with SMTP id r7-20020a056a20394700b00104b21f26b0mr18997836pzg.47.1684253505212; Tue, 16 May 2023 09:11:45 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1684253505; cv=none; d=google.com; s=arc-20160816; b=g6dEDpTsAcYsXkv8V+6XgsABwPrnLmMj5SSQ83mbHWd3PdyODYTfX94hjHZSObW0D6 BDylkZMoK5ZYL2rZaJ6+UQWtfSriJ6YKtkSLQjqsZjJUUCVp0X1vuUPbmAkMUHOjqYhu /OWLb/rTm/ToIw96X6qGEfGedNFiB4rTXN7diyykeaDTMnKmqLxYq5XpfJjqAhDCNlSr /JWsYprxVxR/8fiUOYkVcA3krDXRJW7geq/VLh8D8MkA8YjdyPAWDKKCJGIDBWIcn96C E9zedLVxrTYNm04z+hbt75Vsrt6X1aXvHzvdMlIR9ACxxsu+YO/xP1RSMVwJOhad4fHU ZVNA== 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 :dkim-signature; bh=T2DH6/H5m8Qazyq8fWgGGTIxlN/LEAb7+hM6ytoAYMY=; b=d78rzrVA3y6O3k9ZW10OToLBTMaeDJULXRSeUoKTNh3TEP9BB4LEmhgmp9BlpEUB66 7Ya4xIt/9JaqqPCj+y78NWI28BFnBiAo7ACe1I6oDFynIO7whXP9lD4ffHSRHdY2o2g1 S9BhzNi+211Yob8PTA/noj0Hncb0HLxTD9xa7ywnlS31V7SQU/38jcxU+C92xJxPuUGM eVPj4DfWArUIXIPVrZ941/vQlmqQ7pPzzeQpjaucuhPAMFCqpLwNlz5ZiFZIAicTxFxG qCV9hTCvtX2zmzczsMVD7eEG3K7UGXlMKxO/0bDLd8nYGTc3xDzPwvlrFyu/4/ZVhIjU ZW0Q== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@cirrus.com header.s=PODMain02222019 header.b=jaYJo2OZ; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=cirrus.com Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id j65-20020a638b44000000b0051b10b20ceasi20090098pge.893.2023.05.16.09.11.29; Tue, 16 May 2023 09:11:45 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@cirrus.com header.s=PODMain02222019 header.b=jaYJo2OZ; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=cirrus.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S234527AbjEPQJg (ORCPT <rfc822;peekingduck44@gmail.com> + 99 others); Tue, 16 May 2023 12:09:36 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:33342 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231241AbjEPQJJ (ORCPT <rfc822;linux-kernel@vger.kernel.org>); Tue, 16 May 2023 12:09:09 -0400 Received: from mx0b-001ae601.pphosted.com (mx0a-001ae601.pphosted.com [67.231.149.25]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 920BA9EEF for <linux-kernel@vger.kernel.org>; Tue, 16 May 2023 09:08:34 -0700 (PDT) Received: from pps.filterd (m0077473.ppops.net [127.0.0.1]) by mx0a-001ae601.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 34GFMLXM013969; Tue, 16 May 2023 11:07:58 -0500 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=cirrus.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=PODMain02222019; bh=T2DH6/H5m8Qazyq8fWgGGTIxlN/LEAb7+hM6ytoAYMY=; b=jaYJo2OZNJaOaQrzjITNXQW+77MenPnRLDgfl4yJSF1ZEy4lESaGCIij26mkBdeoOcL3 jw8dqXTMd/lPIbf+go/3Tw4kfuwPUpiEi3CUuWdr7qE48C6GbsPVj7I/LpzW/H/mQfiV JRLbofGTer24W/7Kmh6ZfEaJn/3fQQsREwv5Yj+/1qGlLebFTH6Va+4FT/GEwLNWJb6J EuwwV65XH+BYiYBsGU2ANWfdS0WlbmdCp28sszGEpVvdbDfMOdYs5coM+wBmh8uJ3vN/ NT5cldcZCzXw+akmOEt3X8xBudYqH8jlySboURtFo9S2zwdxv8rfVBfqEcuAffOypIAd OQ== Received: from ediex02.ad.cirrus.com ([84.19.233.68]) by mx0a-001ae601.pphosted.com (PPS) with ESMTPS id 3qj7y14epn-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Tue, 16 May 2023 11:07:58 -0500 Received: from ediex01.ad.cirrus.com (198.61.84.80) by ediex02.ad.cirrus.com (198.61.84.81) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1118.26; Tue, 16 May 2023 11:07:56 -0500 Received: from ediswmail.ad.cirrus.com (198.61.86.93) by ediex01.ad.cirrus.com (198.61.84.80) with Microsoft SMTP Server id 15.2.1118.26 via Frontend Transport; Tue, 16 May 2023 11:07:56 -0500 Received: from EDIN4L06LR3.ad.cirrus.com (EDIN4L06LR3.ad.cirrus.com [198.61.64.66]) by ediswmail.ad.cirrus.com (Postfix) with ESMTP id 15B7211A8; Tue, 16 May 2023 16:07:56 +0000 (UTC) From: Richard Fitzgerald <rf@opensource.cirrus.com> To: <gregkh@linuxfoundation.org>, <rafael@kernel.org> CC: <linux-kernel@vger.kernel.org>, <patches@opensource.cirrus.com>, Richard Fitzgerald <rf@opensource.cirrus.com> Subject: [PATCH 1/5] debugfs: Prevent NULL dereference reading from string property Date: Tue, 16 May 2023 17:07:49 +0100 Message-ID: <20230516160753.32317-2-rf@opensource.cirrus.com> X-Mailer: git-send-email 2.30.2 In-Reply-To: <20230516160753.32317-1-rf@opensource.cirrus.com> References: <20230516160753.32317-1-rf@opensource.cirrus.com> MIME-Version: 1.0 Content-Transfer-Encoding: 8bit Content-Type: text/plain X-Proofpoint-GUID: F3BY0PdYc71JIRmuN6TytsC3HzMbVf3f X-Proofpoint-ORIG-GUID: F3BY0PdYc71JIRmuN6TytsC3HzMbVf3f X-Proofpoint-Spam-Reason: safe X-Spam-Status: No, score=-2.7 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_EF,RCVD_IN_DNSWL_LOW,SPF_HELO_NONE,SPF_PASS, T_SCC_BODY_TEXT_LINE,URIBL_BLOCKED autolearn=ham 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: <linux-kernel.vger.kernel.org> X-Mailing-List: linux-kernel@vger.kernel.org X-getmail-retrieved-from-mailbox: =?utf-8?q?INBOX?= X-GMAIL-THRID: =?utf-8?q?1766067803400470287?= X-GMAIL-MSGID: =?utf-8?q?1766067803400470287?= |
Series |
debugfs: Fixes and improvements to debugfs_create_str()
|
|
Commit Message
Richard Fitzgerald
May 16, 2023, 4:07 p.m. UTC
Check in debugfs_read_file_str() if the string pointer is NULL.
It is perfectly reasonable that a driver may wish to export a string
to debugfs that can have the value NULL to indicate empty/unused/ignore.
Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com>
---
fs/debugfs/file.c | 3 +++
1 file changed, 3 insertions(+)
Comments
On Tue, May 16, 2023 at 05:07:49PM +0100, Richard Fitzgerald wrote: > Check in debugfs_read_file_str() if the string pointer is NULL. > > It is perfectly reasonable that a driver may wish to export a string > to debugfs that can have the value NULL to indicate empty/unused/ignore. Does any in-kernel driver do this today? If not, why not fix up the driver instead? > > Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com> > --- > fs/debugfs/file.c | 3 +++ > 1 file changed, 3 insertions(+) > > diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c > index 1f971c880dde..2c085ab4e800 100644 > --- a/fs/debugfs/file.c > +++ b/fs/debugfs/file.c > @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, > return ret; > > str = *(char **)file->private_data; > + if (!str) > + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); Why not print "(NULL)"? thanks, greg k-h
On 16/5/23 17:07, Richard Fitzgerald wrote: > --- a/fs/debugfs/file.c > +++ b/fs/debugfs/file.c > @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, > return ret; > > str = *(char **)file->private_data; > + if (!str) > + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); > + Oh, this isn't right. I've somehow sent an older version that is missing the call to debugfs_file_put(). Sorry. I'll send a v2 chain.
On 16/5/23 17:33, Greg KH wrote: > On Tue, May 16, 2023 at 05:07:49PM +0100, Richard Fitzgerald wrote: >> Check in debugfs_read_file_str() if the string pointer is NULL. >> >> It is perfectly reasonable that a driver may wish to export a string >> to debugfs that can have the value NULL to indicate empty/unused/ignore. > > Does any in-kernel driver do this today? I don't know. The history here is that I was using debugfs_create_str() to add a debugfs to a driver and made these improvements along the way. Ultimately I had a reason to use a custom reader implementation. But as I'd already written these patches I thought I'd send them. > > If not, why not fix up the driver instead? > Well... could do. Though it seems a bit odd to me that a driver design should be forced by the debugfs API, instead of the debugfs API fitting normal code design. It's pretty standard and idiomatic for code to use if (!str) { /* bail */ } type logic, so why shouldn't the debugfs API handle that? >> >> Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com> >> --- >> fs/debugfs/file.c | 3 +++ >> 1 file changed, 3 insertions(+) >> >> diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c >> index 1f971c880dde..2c085ab4e800 100644 >> --- a/fs/debugfs/file.c >> +++ b/fs/debugfs/file.c >> @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, >> return ret; >> >> str = *(char **)file->private_data; >> + if (!str) >> + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); > > Why not print "(NULL)"? > Again, could do. My thought here is that a debugfs can be piped into tools and having to insert a catch for "(NULL)" in the pipeline is a nuisance. This is a bit different from a dmesg print, which is less likely to be used this way or to guarantee machine-parsing. However, I don't mind changing to "(NULL)" if you prefer. > thanks, > > greg k-h
On Tue, May 16, 2023 at 06:29:52PM +0100, Richard Fitzgerald wrote: > On 16/5/23 17:33, Greg KH wrote: > > On Tue, May 16, 2023 at 05:07:49PM +0100, Richard Fitzgerald wrote: > > > Check in debugfs_read_file_str() if the string pointer is NULL. > > > > > > It is perfectly reasonable that a driver may wish to export a string > > > to debugfs that can have the value NULL to indicate empty/unused/ignore. > > > > Does any in-kernel driver do this today? > > I don't know. The history here is that I was using debugfs_create_str() > to add a debugfs to a driver and made these improvements along the way. > Ultimately I had a reason to use a custom reader implementation. > But as I'd already written these patches I thought I'd send them. > > > > > If not, why not fix up the driver instead? > > > > Well... could do. Though it seems a bit odd to me that a driver > design should be forced by the debugfs API, instead of the debugfs API > fitting normal code design. It's pretty standard and idiomatic for code > to use if (!str) { /* bail */ } type logic, so why shouldn't the debugfs > API handle that? > > > > > > > Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com> > > > --- > > > fs/debugfs/file.c | 3 +++ > > > 1 file changed, 3 insertions(+) > > > > > > diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c > > > index 1f971c880dde..2c085ab4e800 100644 > > > --- a/fs/debugfs/file.c > > > +++ b/fs/debugfs/file.c > > > @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, > > > return ret; > > > str = *(char **)file->private_data; > > > + if (!str) > > > + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); > > > > Why not print "(NULL)"? > > > > Again, could do. My thought here is that a debugfs can be piped into > tools and having to insert a catch for "(NULL)" in the pipeline is a > nuisance. This is a bit different from a dmesg print, which is less > likely to be used this way or to guarantee machine-parsing. > However, I don't mind changing to "(NULL)" if you prefer. If a driver wants an "empty" string, they should provide an empty string. We don't do empty values for any other type of pointer, right? Actually we really should just bail out with an error if this is NULL, let's not paper over bad drivers like this. thanks, greg k-h
On 16/5/23 18:43, Greg KH wrote: > On Tue, May 16, 2023 at 06:29:52PM +0100, Richard Fitzgerald wrote: >> On 16/5/23 17:33, Greg KH wrote: >>> On Tue, May 16, 2023 at 05:07:49PM +0100, Richard Fitzgerald wrote: >>>> Check in debugfs_read_file_str() if the string pointer is NULL. >>>> >>>> It is perfectly reasonable that a driver may wish to export a string >>>> to debugfs that can have the value NULL to indicate empty/unused/ignore. >>> >>> Does any in-kernel driver do this today? >> >> I don't know. The history here is that I was using debugfs_create_str() >> to add a debugfs to a driver and made these improvements along the way. >> Ultimately I had a reason to use a custom reader implementation. >> But as I'd already written these patches I thought I'd send them. >> >>> >>> If not, why not fix up the driver instead? >>> >> >> Well... could do. Though it seems a bit odd to me that a driver >> design should be forced by the debugfs API, instead of the debugfs API >> fitting normal code design. It's pretty standard and idiomatic for code >> to use if (!str) { /* bail */ } type logic, so why shouldn't the debugfs >> API handle that? >> >>>> >>>> Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com> >>>> --- >>>> fs/debugfs/file.c | 3 +++ >>>> 1 file changed, 3 insertions(+) >>>> >>>> diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c >>>> index 1f971c880dde..2c085ab4e800 100644 >>>> --- a/fs/debugfs/file.c >>>> +++ b/fs/debugfs/file.c >>>> @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, >>>> return ret; >>>> str = *(char **)file->private_data; >>>> + if (!str) >>>> + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); >>> >>> Why not print "(NULL)"? >>> >> >> Again, could do. My thought here is that a debugfs can be piped into >> tools and having to insert a catch for "(NULL)" in the pipeline is a >> nuisance. This is a bit different from a dmesg print, which is less >> likely to be used this way or to guarantee machine-parsing. >> However, I don't mind changing to "(NULL)" if you prefer. > > If a driver wants an "empty" string, they should provide an empty > string. We don't do empty values for any other type of pointer, right? > > Actually we really should just bail out with an error if this is NULL, > let's not paper over bad drivers like this. > I don't understand this comment. I think you'll find there is a very large amount of kernel code that uses a NULL value in a pointer to mean ignore/unspecified in some way. This has always been accepted C coding style. The whole idea that a driver is "bad" for signalling some state by a pointer being NULL makes no sense. Please ignore this patch chain. I really don't feel like writing non-idiomatic C code just to work around badly designed debugfs APIs. Better to write a custom read(). > thanks, > > greg k-h
On Tue, May 16, 2023 at 07:04:42PM +0100, Richard Fitzgerald wrote: > On 16/5/23 18:43, Greg KH wrote: > > On Tue, May 16, 2023 at 06:29:52PM +0100, Richard Fitzgerald wrote: > > > On 16/5/23 17:33, Greg KH wrote: > > > > On Tue, May 16, 2023 at 05:07:49PM +0100, Richard Fitzgerald wrote: > > > > > Check in debugfs_read_file_str() if the string pointer is NULL. > > > > > > > > > > It is perfectly reasonable that a driver may wish to export a string > > > > > to debugfs that can have the value NULL to indicate empty/unused/ignore. > > > > > > > > Does any in-kernel driver do this today? > > > > > > I don't know. The history here is that I was using debugfs_create_str() > > > to add a debugfs to a driver and made these improvements along the way. > > > Ultimately I had a reason to use a custom reader implementation. > > > But as I'd already written these patches I thought I'd send them. > > > > > > > > > > > If not, why not fix up the driver instead? > > > > > > > > > > Well... could do. Though it seems a bit odd to me that a driver > > > design should be forced by the debugfs API, instead of the debugfs API > > > fitting normal code design. It's pretty standard and idiomatic for code > > > to use if (!str) { /* bail */ } type logic, so why shouldn't the debugfs > > > API handle that? > > > > > > > > > > > > > Signed-off-by: Richard Fitzgerald <rf@opensource.cirrus.com> > > > > > --- > > > > > fs/debugfs/file.c | 3 +++ > > > > > 1 file changed, 3 insertions(+) > > > > > > > > > > diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c > > > > > index 1f971c880dde..2c085ab4e800 100644 > > > > > --- a/fs/debugfs/file.c > > > > > +++ b/fs/debugfs/file.c > > > > > @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, > > > > > return ret; > > > > > str = *(char **)file->private_data; > > > > > + if (!str) > > > > > + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); > > > > > > > > Why not print "(NULL)"? > > > > > > > > > > Again, could do. My thought here is that a debugfs can be piped into > > > tools and having to insert a catch for "(NULL)" in the pipeline is a > > > nuisance. This is a bit different from a dmesg print, which is less > > > likely to be used this way or to guarantee machine-parsing. > > > However, I don't mind changing to "(NULL)" if you prefer. > > > > If a driver wants an "empty" string, they should provide an empty > > string. We don't do empty values for any other type of pointer, right? > > > > Actually we really should just bail out with an error if this is NULL, > > let's not paper over bad drivers like this. > > > > I don't understand this comment. > I think you'll find there is a very large amount of kernel code that > uses a NULL value in a pointer to mean ignore/unspecified in > some way. This has always been accepted C coding style. > > The whole idea that a driver is "bad" for signalling some state > by a pointer being NULL makes no sense. The whole idea of passing a NULL pointer to debugfs makes no sense :) If a driver does this, then they deserve the crash, let's just say "do not do that" and leave it at that please. > Please ignore this patch chain. I really don't feel like writing > non-idiomatic C code just to work around badly designed debugfs APIs. > Better to write a custom read(). Let's fix the badly designed debugfs apis please, it's not good to have code that is impossible to use correctly. thanks, greg k-h
diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c index 1f971c880dde..2c085ab4e800 100644 --- a/fs/debugfs/file.c +++ b/fs/debugfs/file.c @@ -878,6 +878,9 @@ ssize_t debugfs_read_file_str(struct file *file, char __user *user_buf, return ret; str = *(char **)file->private_data; + if (!str) + return simple_read_from_buffer(user_buf, count, ppos, "\n", 1); + len = strlen(str) + 1; copy = kmalloc(len, GFP_KERNEL); if (!copy) {