When registering a software node, ensure that the property data is not
located on the stack, as it is expected to persist for the lifetime of
the node.
Signed-off-by: Dmitry Torokhov <dmitry.torokhov@gmail.com>
---
drivers/base/swnode.c | 10 ++++++++++
1 file changed, 10 insertions(+)
diff --git a/drivers/base/swnode.c b/drivers/base/swnode.c
index 51320837f3a9..286eab02e8fb 100644
--- a/drivers/base/swnode.c
+++ b/drivers/base/swnode.c
@@ -16,6 +16,7 @@
#include <linux/kstrtox.h>
#include <linux/list.h>
#include <linux/property.h>
+#include <linux/sched/task_stack.h>
#include <linux/slab.h>
#include <linux/spinlock.h>
#include <linux/string.h>
@@ -917,6 +918,7 @@ EXPORT_SYMBOL_GPL(software_node_unregister_node_group);
int software_node_register(const struct software_node *node)
{
struct swnode *parent = software_node_to_swnode(node->parent);
+ const struct property_entry *prop;
if (software_node_to_swnode(node))
return -EEXIST;
@@ -924,6 +926,14 @@ int software_node_register(const struct software_node *node)
if (node->parent && !parent)
return -EINVAL;
+ for (prop = node->properties; prop && prop->name; prop++) {
+ if (!prop->is_inline && object_is_on_stack(prop->pointer)) {
+ pr_err("%s: property data can't be on stack ('%s')\n",
+ __func__, prop->name);
+ return -EINVAL;
+ }
+ }
+
return PTR_ERR_OR_ZERO(swnode_register(node, parent, 0));
}
EXPORT_SYMBOL_GPL(software_node_register);
--
2.53.0.1018.g2bb0e51243-goog
On Sun, Mar 29, 2026 at 07:27:50PM -0700, Dmitry Torokhov wrote:
> When registering a software node, ensure that the property data is not
> located on the stack, as it is expected to persist for the lifetime of
> the node.
...
> + for (prop = node->properties; prop && prop->name; prop++) {
> + if (!prop->is_inline && object_is_on_stack(prop->pointer)) {
I read more about this... Any code that uses vmalloc() (or potentially may
switch to it from regular allocator with help of kvalloc() and similar) will
fail now. While it might be no issue right now, this may become a such. So
with this check in place you put a requirement that properties can only be
allocated from a kernel low memory heap and not vm.
> + pr_err("%s: property data can't be on stack ('%s')\n",
> + __func__, prop->name);
> + return -EINVAL;
> + }
> + }
--
With Best Regards,
Andy Shevchenko
On Mon, Mar 30, 2026 at 01:33:47PM +0300, Andy Shevchenko wrote:
> On Sun, Mar 29, 2026 at 07:27:50PM -0700, Dmitry Torokhov wrote:
> > When registering a software node, ensure that the property data is not
> > located on the stack, as it is expected to persist for the lifetime of
> > the node.
>
> ...
>
> > + for (prop = node->properties; prop && prop->name; prop++) {
> > + if (!prop->is_inline && object_is_on_stack(prop->pointer)) {
>
> I read more about this... Any code that uses vmalloc() (or potentially may
> switch to it from regular allocator with help of kvalloc() and similar) will
> fail now. While it might be no issue right now, this may become a such. So
> with this check in place you put a requirement that properties can only be
> allocated from a kernel low memory heap and not vm.
Can you tell me more about this? As far as I can see it will actually
have false negatives with CONFIG_VMAP_STACK, but should be OK not
trigger with vmalloced memory... But I am genuinely interested to know
more.
Thanks.
--
Dmitry
On Mon, Mar 30, 2026 at 02:49:52PM -0700, Dmitry Torokhov wrote:
> On Mon, Mar 30, 2026 at 01:33:47PM +0300, Andy Shevchenko wrote:
> > On Sun, Mar 29, 2026 at 07:27:50PM -0700, Dmitry Torokhov wrote:
...
> > > + for (prop = node->properties; prop && prop->name; prop++) {
> > > + if (!prop->is_inline && object_is_on_stack(prop->pointer)) {
> >
> > I read more about this... Any code that uses vmalloc() (or potentially may
> > switch to it from regular allocator with help of kvalloc() and similar) will
> > fail now. While it might be no issue right now, this may become a such. So
> > with this check in place you put a requirement that properties can only be
> > allocated from a kernel low memory heap and not vm.
>
> Can you tell me more about this? As far as I can see it will actually
> have false negatives with CONFIG_VMAP_STACK, but should be OK not
> trigger with vmalloced memory... But I am genuinely interested to know
> more.
I dug into the history of this macro. It was added for the block and ide
subsystems to make sure that there is no buffer supplied that may not be DMAed.
As we know vmalloc():ed buffers may not be DMAed. In some commit messages
it was explicitly mentioned that this macro fails on vmalloc():ed memory.
Note, I haven't checked the actual behaviour by trying that on the HW.
--
With Best Regards,
Andy Shevchenko
On Tue, Mar 31, 2026 at 11:02:13AM +0300, Andy Shevchenko wrote:
> On Mon, Mar 30, 2026 at 02:49:52PM -0700, Dmitry Torokhov wrote:
> > On Mon, Mar 30, 2026 at 01:33:47PM +0300, Andy Shevchenko wrote:
> > > On Sun, Mar 29, 2026 at 07:27:50PM -0700, Dmitry Torokhov wrote:
...
> > > > + for (prop = node->properties; prop && prop->name; prop++) {
> > > > + if (!prop->is_inline && object_is_on_stack(prop->pointer)) {
> > >
> > > I read more about this... Any code that uses vmalloc() (or potentially may
> > > switch to it from regular allocator with help of kvalloc() and similar) will
> > > fail now. While it might be no issue right now, this may become a such. So
> > > with this check in place you put a requirement that properties can only be
> > > allocated from a kernel low memory heap and not vm.
> >
> > Can you tell me more about this? As far as I can see it will actually
> > have false negatives with CONFIG_VMAP_STACK, but should be OK not
> > trigger with vmalloced memory... But I am genuinely interested to know
> > more.
>
> I dug into the history of this macro. It was added for the block and ide
> subsystems to make sure that there is no buffer supplied that may not be DMAed.
> As we know vmalloc():ed buffers may not be DMAed. In some commit messages
> it was explicitly mentioned that this macro fails on vmalloc():ed memory.
>
> Note, I haven't checked the actual behaviour by trying that on the HW.
OTOH, the check itself covers only 16kB of memory range. I don't understand
how it can give true for anything outside that area...
--
With Best Regards,
Andy Shevchenko
© 2016 - 2026 Red Hat, Inc.