lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <202407090910.87821CD@keescook>
Date: Tue, 9 Jul 2024 09:32:22 -0700
From: Kees Cook <kees@...nel.org>
To: Przemek Kitszel <przemyslaw.kitszel@...el.com>
Cc: Vlastimil Babka <vbabka@...e.cz>, Tony Luck <tony.luck@...el.com>,
	"Guilherme G. Piccoli" <gpiccoli@...lia.com>,
	linux-hardening@...r.kernel.org, Jann Horn <jannh@...gle.com>,
	Nick Desaulniers <ndesaulniers@...gle.com>,
	Miguel Ojeda <ojeda@...nel.org>, Marco Elver <elver@...gle.com>,
	Nathan Chancellor <nathan@...nel.org>, Hao Luo <haoluo@...gle.com>,
	Christoph Lameter <cl@...ux.com>, Pekka Enberg <penberg@...nel.org>,
	David Rientjes <rientjes@...gle.com>,
	Joonsoo Kim <iamjoonsoo.kim@....com>,
	Andrew Morton <akpm@...ux-foundation.org>,
	Roman Gushchin <roman.gushchin@...ux.dev>,
	Hyeonggon Yoo <42.hyeyoo@...il.com>,
	Mark Rutland <mark.rutland@....com>,
	Jakub Kicinski <kuba@...nel.org>, Petr Pavlu <petr.pavlu@...e.com>,
	Alexander Lobakin <aleksander.lobakin@...el.com>,
	Tony Ambardar <tony.ambardar@...il.com>,
	linux-kernel@...r.kernel.org, linux-mm@...ck.org
Subject: Re: [RFC][PATCH 4/4] pstore: Replace classic kmalloc code pattern
 with typed argument

On Tue, Jul 09, 2024 at 09:06:58AM +0200, Przemek Kitszel wrote:
> On 7/8/24 21:18, Kees Cook wrote:
> > diff --git a/fs/pstore/blk.c b/fs/pstore/blk.c
> > index de8cf5d75f34..7bb9cacb380f 100644
> > --- a/fs/pstore/blk.c
> > +++ b/fs/pstore/blk.c
> > @@ -297,7 +297,7 @@ static int __init __best_effort_init(void)
> >   		return -EINVAL;
> >   	}
> > -	best_effort_dev = kzalloc(sizeof(*best_effort_dev), GFP_KERNEL);
> > +	best_effort_dev = kzalloc(best_effort_dev, GFP_KERNEL);
> >   	if (!best_effort_dev)
> >   		return -ENOMEM;
> I expect raised eyebrows and typical vocalizations of amusement :D -
> IOW: we should consider changing the name of the macro, although I like
> it as is :)

Yeah, I prefer keeping the name too. I feel like adding yet more macros
around the allocators does not make anyone too happy. :)

> other:
> you repeat the pointer name twice, and code is magic anyway, so perhaps:
> 	kzalloc_me(best_effort_dev, GFP_KERNEL);
> and another variant to cover declaration-with-init.

Switch the calling style is, however, where I think it'd be good
to change the name. I've had push-back in the past on changing away
from the "assignment style" to the "pass by reference" style, but I
would honestly prefer dropping the assignment: it is almost always
redundant. (I understood the push-back to be around the case of not
being able to easily use the "return kmalloc(...)" code pattern.)

It also makes it easier to deal with fixed array and flexible array
variants, as the argument count can be examined to determine if this is
a fixed-size struct or a flexible object:

	kzalloc_struct(ptr, GFP_KERNEL);

	kzalloc_struct(ptr, flex_member, count, GFP_KERNEL);
		-> uses struct_size() to get allocation size

I wonder if we can find a way to also handle the array case at compile
time:

	kzalloc_struct(array, count, GFP_KERNEL);

And if so, maybe the naming should be "kzalloc_me" like you suggest, or
maybe "kzalloc_obj"?

The resulting Coccinelle script gets a little more complex since we have
to rewrite the matched function, but it's not bad:

@find@
type TYPE;
TYPE *P;
expression GFP;
identifier ALLOC =~ "k[mz]alloc";
@@

	P = ALLOC(\(sizeof(*P)\|sizeof(TYPE)\), GFP)

@script:python rename@
alloc_name << find.ALLOC;
ALLOC_OBJ;
@@

coccinelle.ALLOC_OBJ = cocci.make_ident(alloc_name + "_obj")

@convert@
type find.TYPE;
TYPE *find.P;
expression find.GFP;
identifier find.ALLOC;
identifier rename.ALLOC_OBJ;
@@

-	P = ALLOC(\(sizeof(*P)\|sizeof(TYPE)\), GFP)
+	ALLOC_OBJ(P, GFP)

And the results in fs/pstore/ look like this:


diff --git a/fs/pstore/blk.c b/fs/pstore/blk.c
index de8cf5d75f34..bc0e0a170604 100644
--- a/fs/pstore/blk.c
+++ b/fs/pstore/blk.c
@@ -297,7 +297,7 @@ static int __init __best_effort_init(void)
 		return -EINVAL;
 	}
 
-	best_effort_dev = kzalloc(sizeof(*best_effort_dev), GFP_KERNEL);
+	kzalloc_obj(best_effort_dev, GFP_KERNEL);
 	if (!best_effort_dev)
 		return -ENOMEM;
 
diff --git a/fs/pstore/platform.c b/fs/pstore/platform.c
index 03425928d2fb..e0ba70543121 100644
--- a/fs/pstore/platform.c
+++ b/fs/pstore/platform.c
@@ -682,7 +682,7 @@ void pstore_get_backend_records(struct pstore_info *psi,
 		struct pstore_record *record;
 		int rc;
 
-		record = kzalloc(sizeof(*record), GFP_KERNEL);
+		kzalloc_obj(record, GFP_KERNEL);
 		if (!record) {
 			pr_err("out of memory creating record\n");
 			break;
diff --git a/fs/pstore/ram.c b/fs/pstore/ram.c
index b1a455f42e93..93064ba2c480 100644
--- a/fs/pstore/ram.c
+++ b/fs/pstore/ram.c
@@ -228,8 +228,7 @@ static ssize_t ramoops_pstore_read(struct pstore_record *record)
 			 */
 			struct persistent_ram_zone *tmp_prz, *prz_next;
 
-			tmp_prz = kzalloc(sizeof(struct persistent_ram_zone),
-					  GFP_KERNEL);
+			kzalloc_obj(tmp_prz, GFP_KERNEL);
 			if (!tmp_prz)
 				return -ENOMEM;
 			prz = tmp_prz;
diff --git a/fs/pstore/ram_core.c b/fs/pstore/ram_core.c
index f1848cdd6d34..9561f4dfa853 100644
--- a/fs/pstore/ram_core.c
+++ b/fs/pstore/ram_core.c
@@ -588,7 +588,7 @@ struct persistent_ram_zone *persistent_ram_new(phys_addr_t start, size_t size,
 	struct persistent_ram_zone *prz;
 	int ret = -ENOMEM;
 
-	prz = kzalloc(sizeof(struct persistent_ram_zone), GFP_KERNEL);
+	kzalloc_obj(prz, GFP_KERNEL);
 	if (!prz) {
 		pr_err("failed to allocate persistent ram zone\n");
 		goto err;
diff --git a/fs/pstore/zone.c b/fs/pstore/zone.c
index 694db616663f..312796dc93f0 100644
--- a/fs/pstore/zone.c
+++ b/fs/pstore/zone.c
@@ -1165,7 +1165,7 @@ static struct pstore_zone *psz_init_zone(enum pstore_type_id type,
 		return ERR_PTR(-ENOMEM);
 	}
 
-	zone = kzalloc(sizeof(struct pstore_zone), GFP_KERNEL);
+	kzalloc_obj(zone, GFP_KERNEL);
 	if (!zone)
 		return ERR_PTR(-ENOMEM);
 

-- 
Kees Cook

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ