Message ID | 20151117013830.GV8456@google.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
On Mon, 16 Nov 2015, Brian Norris wrote: > On Mon, Nov 16, 2015 at 12:33:14PM +0100, Julia Lawall wrote: > > for_each_available_child_of_node performs an of_node_get on each iteration, > > so a return from the middle of the loop requires an of_node_put. > > > > A simplified version of the semantic patch that finds this problem is as > > follows (http://coccinelle.lip6.fr): > > > > // <smpl> > > @@ > > expression root,e; > > local idexpression child; > > @@ > > > > for_each_available_child_of_node(root, child) { > > ... when != of_node_put(child) > > when != e = child > > ( > > return child; > > | > > * return ...; > > ) > > ... > > } > > // </smpl> > > > > Signed-off-by: Julia Lawall <Julia.Lawall@lip6.fr> > > > > --- > > For this patch: > > Acked-by: Brian Norris <computersforpeace@gmail.com> > > > drivers/phy/phy-brcmstb-sata.c | 17 ++++++++++++----- > > 1 file changed, 12 insertions(+), 5 deletions(-) > > [snip patch, which fixes of_node_put() handling for > for_each_available_child_of_node() loop, which creates PHY devices with > devm_phy_create()] > > This reminds me of a potential problem I'm looking at in other > subsystems: from code reading (I haven't seen any issues in practice, > probably because I don't use OF_DYNAMIC) it looks like device-creating > infrastructure like the PHY subsystem should be acquiring a reference to > the device_node when they stash it away. But drivers/phy/phy-core.c does > not do this, AFAICT. > > See phy_create(), which does > > phy->dev.of_node = node ?: dev->of_node; > > and later might reuse this of_node pointer, even though it never called > of_node_get() on this node. > > Potential patch to fix this (not tested). > > Signed-off-by: Brian Norris <computersforpeace@gmail.com> > > diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c > index fc48fac003a6..8df29caeeef9 100644 > --- a/drivers/phy/phy-core.c > +++ b/drivers/phy/phy-core.c > @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > phy->dev.class = phy_class; > phy->dev.parent = dev; > phy->dev.of_node = node ?: dev->of_node; > + of_node_get(phy->dev.of_node); Why not put of_node_get around dev->of_node? julia > phy->id = id; > phy->ops = ops; > > @@ -726,6 +727,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > return phy; > > put_dev: > + of_node_put(phy->dev.of_node); > put_device(&phy->dev); /* calls phy_release() which frees resources */ > return ERR_PTR(ret); > > @@ -775,6 +777,7 @@ EXPORT_SYMBOL_GPL(devm_phy_create); > */ > void phy_destroy(struct phy *phy) > { > + of_node_put(phy->dev.of_node); > pm_runtime_disable(&phy->dev); > device_unregister(&phy->dev); > } > -- > To unsubscribe from this list: send the line "unsubscribe kernel-janitors" in > the body of a message to majordomo@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html >
On Tue, Nov 17, 2015 at 07:12:22AM +0100, Julia Lawall wrote: > On Mon, 16 Nov 2015, Brian Norris wrote: > > > > This reminds me of a potential problem I'm looking at in other > > subsystems: from code reading (I haven't seen any issues in practice, > > probably because I don't use OF_DYNAMIC) it looks like device-creating > > infrastructure like the PHY subsystem should be acquiring a reference to > > the device_node when they stash it away. But drivers/phy/phy-core.c does > > not do this, AFAICT. > > > > See phy_create(), which does > > > > phy->dev.of_node = node ?: dev->of_node; > > > > and later might reuse this of_node pointer, even though it never called > > of_node_get() on this node. > > > > Potential patch to fix this (not tested). > > > > Signed-off-by: Brian Norris <computersforpeace@gmail.com> > > > > diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c > > index fc48fac003a6..8df29caeeef9 100644 > > --- a/drivers/phy/phy-core.c > > +++ b/drivers/phy/phy-core.c > > @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > > phy->dev.class = phy_class; > > phy->dev.parent = dev; > > phy->dev.of_node = node ?: dev->of_node; > > + of_node_get(phy->dev.of_node); > > Why not put of_node_get around dev->of_node? Like this? phy->dev.of_node = node ?: of_node_get(dev->of_node); Or this? phy->dev.of_node = of_node_get(node ?: dev->of_node); The former wouldn't do what I proposed; if this PHY device is created with a sub-node of 'dev' rather than dev->of_node, then the caller will pass it in as the 2nd argument to phy_create (i.e., 'node'), and then I expect it's the PHY core's responsibility to refcount it. I'd be fine with the latter. Looks a little better, I suppose. If my understanding is correct, I'll send a proper patch to do the latter. Regards, Brian > julia > > > phy->id = id; > > phy->ops = ops; > > > > @@ -726,6 +727,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > > return phy; > > > > put_dev: > > + of_node_put(phy->dev.of_node); > > put_device(&phy->dev); /* calls phy_release() which frees resources */ > > return ERR_PTR(ret); > > > > @@ -775,6 +777,7 @@ EXPORT_SYMBOL_GPL(devm_phy_create); > > */ > > void phy_destroy(struct phy *phy) > > { > > + of_node_put(phy->dev.of_node); > > pm_runtime_disable(&phy->dev); > > device_unregister(&phy->dev); > > } > > -- > > To unsubscribe from this list: send the line "unsubscribe kernel-janitors" in > > the body of a message to majordomo@vger.kernel.org > > More majordomo info at http://vger.kernel.org/majordomo-info.html > >
On Tue, 17 Nov 2015, Brian Norris wrote: > On Tue, Nov 17, 2015 at 07:12:22AM +0100, Julia Lawall wrote: > > On Mon, 16 Nov 2015, Brian Norris wrote: > > > > > > This reminds me of a potential problem I'm looking at in other > > > subsystems: from code reading (I haven't seen any issues in practice, > > > probably because I don't use OF_DYNAMIC) it looks like device-creating > > > infrastructure like the PHY subsystem should be acquiring a reference to > > > the device_node when they stash it away. But drivers/phy/phy-core.c does > > > not do this, AFAICT. > > > > > > See phy_create(), which does > > > > > > phy->dev.of_node = node ?: dev->of_node; > > > > > > and later might reuse this of_node pointer, even though it never called > > > of_node_get() on this node. > > > > > > Potential patch to fix this (not tested). > > > > > > Signed-off-by: Brian Norris <computersforpeace@gmail.com> > > > > > > diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c > > > index fc48fac003a6..8df29caeeef9 100644 > > > --- a/drivers/phy/phy-core.c > > > +++ b/drivers/phy/phy-core.c > > > @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > > > phy->dev.class = phy_class; > > > phy->dev.parent = dev; > > > phy->dev.of_node = node ?: dev->of_node; > > > + of_node_get(phy->dev.of_node); > > > > Why not put of_node_get around dev->of_node? > > Like this? > > phy->dev.of_node = node ?: of_node_get(dev->of_node); > > Or this? > > phy->dev.of_node = of_node_get(node ?: dev->of_node); > > The former wouldn't do what I proposed; if this PHY device is created > with a sub-node of 'dev' rather than dev->of_node, then the caller will > pass it in as the 2nd argument to phy_create (i.e., 'node'), and then I > expect it's the PHY core's responsibility to refcount it. > > I'd be fine with the latter. Looks a little better, I suppose. I proposed it because I was worried that the of_node field could end up containing something that had been freed. But probably this is not possible? If it is not possible, then the ?: in the function argument is probably a bit ugly... Is this something that should be checked for elsewhere? julia > If my understanding is correct, I'll send a proper patch to do the > latter. > > Regards, > Brian > > > julia > > > > > phy->id = id; > > > phy->ops = ops; > > > > > > @@ -726,6 +727,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > > > return phy; > > > > > > put_dev: > > > + of_node_put(phy->dev.of_node); > > > put_device(&phy->dev); /* calls phy_release() which frees resources */ > > > return ERR_PTR(ret); > > > > > > @@ -775,6 +777,7 @@ EXPORT_SYMBOL_GPL(devm_phy_create); > > > */ > > > void phy_destroy(struct phy *phy) > > > { > > > + of_node_put(phy->dev.of_node); > > > pm_runtime_disable(&phy->dev); > > > device_unregister(&phy->dev); > > > } > > > -- > > > To unsubscribe from this list: send the line "unsubscribe kernel-janitors" in > > > the body of a message to majordomo@vger.kernel.org > > > More majordomo info at http://vger.kernel.org/majordomo-info.html > > > >
On Tue, Nov 17, 2015 at 06:48:39PM +0100, Julia Lawall wrote: > On Tue, 17 Nov 2015, Brian Norris wrote: > > On Tue, Nov 17, 2015 at 07:12:22AM +0100, Julia Lawall wrote: > > > On Mon, 16 Nov 2015, Brian Norris wrote: > > > > diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c > > > > index fc48fac003a6..8df29caeeef9 100644 > > > > --- a/drivers/phy/phy-core.c > > > > +++ b/drivers/phy/phy-core.c > > > > @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > > > > phy->dev.class = phy_class; > > > > phy->dev.parent = dev; > > > > phy->dev.of_node = node ?: dev->of_node; > > > > + of_node_get(phy->dev.of_node); > > > > > > Why not put of_node_get around dev->of_node? > > > > Like this? > > > > phy->dev.of_node = node ?: of_node_get(dev->of_node); > > > > Or this? > > > > phy->dev.of_node = of_node_get(node ?: dev->of_node); > > > > The former wouldn't do what I proposed; if this PHY device is created > > with a sub-node of 'dev' rather than dev->of_node, then the caller will > > pass it in as the 2nd argument to phy_create (i.e., 'node'), and then I > > expect it's the PHY core's responsibility to refcount it. > > > > I'd be fine with the latter. Looks a little better, I suppose. > > I proposed it because I was worried that the of_node field could end up > containing something that had been freed. But probably this is not > possible? AIUI, the caller of phy_create() should already have a refcount on both 'dev->of_node' and 'node' (if applicable), so nobody should be freeing it from underneath us right here. But *after* phy_create() returns, there's no guarantee the caller will hold a reference for us. So even if it's ever possible, I'd consider it a bug in the caller, not in phy_create(). > If it is not possible, then the ?: in the function argument is > probably a bit ugly... OK, then I'll go with my first proposal. > Is this something that should be checked for elsewhere? I expect the same sort of problem shows up plenty of other places. I don't think many people use CONFIG_OF_DYNAMIC, so the effects of these failures probably aren't felt by many. Brian
On Tue, Nov 17, 2015 at 10:30:36AM -0800, Brian Norris wrote: > I expect the same sort of problem shows up plenty of other places. I > don't think many people use CONFIG_OF_DYNAMIC, so the effects of these > failures probably aren't felt by many. Also, there's a quite-relevant todo item in Documentation/devicetree/todo.txt: === CONFIG_OF_DYNAMIC === ... - Document node lifecycle for CONFIG_OF_DYNAMIC :) Brian
On Tue, 17 Nov 2015, Brian Norris wrote: > On Tue, Nov 17, 2015 at 06:48:39PM +0100, Julia Lawall wrote: > > On Tue, 17 Nov 2015, Brian Norris wrote: > > > On Tue, Nov 17, 2015 at 07:12:22AM +0100, Julia Lawall wrote: > > > > On Mon, 16 Nov 2015, Brian Norris wrote: > > > > > diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c > > > > > index fc48fac003a6..8df29caeeef9 100644 > > > > > --- a/drivers/phy/phy-core.c > > > > > +++ b/drivers/phy/phy-core.c > > > > > @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > > > > > phy->dev.class = phy_class; > > > > > phy->dev.parent = dev; > > > > > phy->dev.of_node = node ?: dev->of_node; > > > > > + of_node_get(phy->dev.of_node); > > > > > > > > Why not put of_node_get around dev->of_node? > > > > > > Like this? > > > > > > phy->dev.of_node = node ?: of_node_get(dev->of_node); > > > > > > Or this? > > > > > > phy->dev.of_node = of_node_get(node ?: dev->of_node); > > > > > > The former wouldn't do what I proposed; if this PHY device is created > > > with a sub-node of 'dev' rather than dev->of_node, then the caller will > > > pass it in as the 2nd argument to phy_create (i.e., 'node'), and then I > > > expect it's the PHY core's responsibility to refcount it. > > > > > > I'd be fine with the latter. Looks a little better, I suppose. > > > > I proposed it because I was worried that the of_node field could end up > > containing something that had been freed. But probably this is not > > possible? > > AIUI, the caller of phy_create() should already have a refcount on both > 'dev->of_node' and 'node' (if applicable), so nobody should be freeing > it from underneath us right here. But *after* phy_create() returns, > there's no guarantee the caller will hold a reference for us. > > So even if it's ever possible, I'd consider it a bug in the caller, not > in phy_create(). > > > If it is not possible, then the ?: in the function argument is > > probably a bit ugly... > > OK, then I'll go with my first proposal. > > > Is this something that should be checked for elsewhere? > > I expect the same sort of problem shows up plenty of other places. I > don't think many people use CONFIG_OF_DYNAMIC, so the effects of these > failures probably aren't felt by many. I tried the following semantic patch: @@ struct device_node *e; expression e1; identifier fld; @@ ... when != of_node_get(...) *(<+...e1->fld...+>) = e ... when != of_node_get(...) return e1; basically, this says that a structure field is initilized to a device node value, the structure is returned by the containing function, and the containing function contains no of_node_get at all. Certainly this is quite constrained, but it does produce a number of examples. I looked at a few of them: drivers/clk/ingenic/cgu.c, ingenic_cgu_new clk/pistachio/clk.c, pistachio_clk_alloc_provider drivers/mfd/syscon.c, of_syscon_register drivers/of/pdt.c, function of_pdt_create_node Any idea whether these need of_node_get? In all cases the device node value comes in as a parameter. thanks, julia
(changing subject, add devicetree@vger.kernel.org) On Tue, Nov 17, 2015 at 11:33:25PM +0100, Julia Lawall wrote: > On Tue, 17 Nov 2015, Brian Norris wrote: > > On Tue, Nov 17, 2015 at 06:48:39PM +0100, Julia Lawall wrote: > > > Is this something that should be checked for elsewhere? > > > > I expect the same sort of problem shows up plenty of other places. I > > don't think many people use CONFIG_OF_DYNAMIC, so the effects of these > > failures probably aren't felt by many. > > I tried the following semantic patch: > > @@ > struct device_node *e; > expression e1; > identifier fld; > @@ > > ... when != of_node_get(...) > *(<+...e1->fld...+>) = e > ... when != of_node_get(...) > return e1; > > basically, this says that a structure field is initilized to a device node > value, the structure is returned by the containing function, and the > containing function contains no of_node_get at all. Certainly this is > quite constrained, but it does produce a number of examples. > > I looked at a few of them: > > drivers/clk/ingenic/cgu.c, ingenic_cgu_new > clk/pistachio/clk.c, pistachio_clk_alloc_provider It looks like the clock core (drivers/clk/clk.c) initially grabs the clk provider node in of_clk_init(), then drops it after it's initialized, but most of these providers use of_clk_add_provider(), which seems to manage the device_node lifetime for the user. So I think these are OK. > drivers/mfd/syscon.c, of_syscon_register This one looks potentially suspect. Syscon nodes aren't usually directly managed by a single driver, and the device_node pointer is used for lookups later...so I think it should keep a kref, and it doesn't. > drivers/of/pdt.c, function of_pdt_create_node Not real sure about this one. > Any idea whether these need of_node_get? In all cases the device node > value comes in as a parameter. I'm really not an expert on this stuff. I just saw a potential problem that I happen to be looking at in other subsystems, and I wanted to know what others thought. I think this discussion should include the DT folks and the subsystems in question. For one, I'm as interested as anyone in getting this todo clarified: Documentation/devicetree/todo.txt - Document node lifecycle for CONFIG_OF_DYNAMIC Regards, Brian
On Wed, 18 Nov 2015, Brian Norris wrote: > (changing subject, add devicetree@vger.kernel.org) > > On Tue, Nov 17, 2015 at 11:33:25PM +0100, Julia Lawall wrote: > > On Tue, 17 Nov 2015, Brian Norris wrote: > > > On Tue, Nov 17, 2015 at 06:48:39PM +0100, Julia Lawall wrote: > > > > Is this something that should be checked for elsewhere? > > > > > > I expect the same sort of problem shows up plenty of other places. I > > > don't think many people use CONFIG_OF_DYNAMIC, so the effects of these > > > failures probably aren't felt by many. > > > > I tried the following semantic patch: > > > > @@ > > struct device_node *e; > > expression e1; > > identifier fld; > > @@ > > > > ... when != of_node_get(...) > > *(<+...e1->fld...+>) = e > > ... when != of_node_get(...) > > return e1; > > > > basically, this says that a structure field is initilized to a device node > > value, the structure is returned by the containing function, and the > > containing function contains no of_node_get at all. Certainly this is > > quite constrained, but it does produce a number of examples. > > > > I looked at a few of them: > > > > drivers/clk/ingenic/cgu.c, ingenic_cgu_new > > clk/pistachio/clk.c, pistachio_clk_alloc_provider > > It looks like the clock core (drivers/clk/clk.c) initially grabs the clk > provider node in of_clk_init(), then drops it after it's initialized, > but most of these providers use of_clk_add_provider(), which seems to > manage the device_node lifetime for the user. So I think these are OK. > > > drivers/mfd/syscon.c, of_syscon_register > > This one looks potentially suspect. Syscon nodes aren't usually directly > managed by a single driver, and the device_node pointer is used for > lookups later...so I think it should keep a kref, and it doesn't. > > > drivers/of/pdt.c, function of_pdt_create_node > > Not real sure about this one. > > > Any idea whether these need of_node_get? In all cases the device node > > value comes in as a parameter. > > I'm really not an expert on this stuff. I just saw a potential problem > that I happen to be looking at in other subsystems, and I wanted to know > what others thought. Thanks for the analysis. I will look into them a bit more. Hopefully at least the maintainer of each file will know what should be done. julia > I think this discussion should include the DT folks > and the subsystems in question. For one, I'm as interested as anyone in > getting this todo clarified: > > Documentation/devicetree/todo.txt > - Document node lifecycle for CONFIG_OF_DYNAMIC > > Regards, > Brian >
On Wed, Nov 18, 2015 at 1:05 PM, Brian Norris <computersforpeace@gmail.com> wrote: > (changing subject, add devicetree@vger.kernel.org) > > On Tue, Nov 17, 2015 at 11:33:25PM +0100, Julia Lawall wrote: >> On Tue, 17 Nov 2015, Brian Norris wrote: >> > On Tue, Nov 17, 2015 at 06:48:39PM +0100, Julia Lawall wrote: >> > > Is this something that should be checked for elsewhere? >> > >> > I expect the same sort of problem shows up plenty of other places. I >> > don't think many people use CONFIG_OF_DYNAMIC, so the effects of these >> > failures probably aren't felt by many. The "problem" is non-existent because either CONFIG_OF_DYNAMIC is off or where it is used is limited (memory and cpus on PSeries) and now overlays. Overlays have the potential to be problematic, but we should manage ref counting for overlays in a completely different way. What that looks like, I don't know. I'll leave that to the person that cares about removing overlays. >> basically, this says that a structure field is initilized to a device node >> value, the structure is returned by the containing function, and the >> containing function contains no of_node_get at all. Certainly this is >> quite constrained, but it does produce a number of examples. I've got no idea if this is right or not. >> drivers/of/pdt.c, function of_pdt_create_node > > Not real sure about this one. SPARC. Stay away. > >> Any idea whether these need of_node_get? In all cases the device node >> value comes in as a parameter. > > I'm really not an expert on this stuff. I just saw a potential problem > that I happen to be looking at in other subsystems, and I wanted to know > what others thought. I think this discussion should include the DT folks > and the subsystems in question. For one, I'm as interested as anyone in > getting this todo clarified: > > Documentation/devicetree/todo.txt > - Document node lifecycle for CONFIG_OF_DYNAMIC Step 2 after figuring out it can't be documented is "define a new way to handle dynamic DT refcounting aka how to get rid of of_node_get/put." Rob
On Thu, Nov 19, 2015 at 12:44:11PM -0600, Rob Herring wrote: > On Wed, Nov 18, 2015 at 1:05 PM, Brian Norris > <computersforpeace@gmail.com> wrote: > > (changing subject, add devicetree@vger.kernel.org) > > > > On Tue, Nov 17, 2015 at 11:33:25PM +0100, Julia Lawall wrote: > >> On Tue, 17 Nov 2015, Brian Norris wrote: > >> > On Tue, Nov 17, 2015 at 06:48:39PM +0100, Julia Lawall wrote: > >> > > Is this something that should be checked for elsewhere? > >> > > >> > I expect the same sort of problem shows up plenty of other places. I > >> > don't think many people use CONFIG_OF_DYNAMIC, so the effects of these > >> > failures probably aren't felt by many. > > The "problem" is non-existent because either CONFIG_OF_DYNAMIC is off > or where it is used is limited (memory and cpus on PSeries) and now > overlays. Overlays have the potential to be problematic, but we should > manage ref counting for overlays in a completely different way. What > that looks like, I don't know. I'll leave that to the person that > cares about removing overlays. So are you saying we should just forget about of_node_put and delete all of_node_put/of_node_get references in code outside drivers/of ? That seems pretty obtuse given that we do have the overlay code merged, and sounds to me like a very bad idea. Expecting those who want to use overlays to run around checking that the refcounting is correct in drivers is a really silly idea IMHO - the existing API is refcounted, so either people really ought to be using it correctly as it's already been designed (in other words, with correct refcounting, and we shouldn't be shovelling this problem onto other people) or the refcounting should be completely killed. The existing half-way house of "we have refcounting, but we don't care about it" is really insane. Either we have refcounting, and it's used properly, or we don't have refcounting. No middle ground IMHO.
+Grant Hi, On Tuesday 17 November 2015 07:08 AM, Brian Norris wrote: > On Mon, Nov 16, 2015 at 12:33:14PM +0100, Julia Lawall wrote: >> for_each_available_child_of_node performs an of_node_get on each iteration, >> so a return from the middle of the loop requires an of_node_put. >> >> A simplified version of the semantic patch that finds this problem is as >> follows (http://coccinelle.lip6.fr): >> >> // <smpl> >> @@ >> expression root,e; >> local idexpression child; >> @@ >> >> for_each_available_child_of_node(root, child) { >> ... when != of_node_put(child) >> when != e = child >> ( >> return child; >> | >> * return ...; >> ) >> ... >> } >> // </smpl> >> >> Signed-off-by: Julia Lawall <Julia.Lawall@lip6.fr> >> >> --- > > For this patch: > > Acked-by: Brian Norris <computersforpeace@gmail.com> > >> drivers/phy/phy-brcmstb-sata.c | 17 ++++++++++++----- >> 1 file changed, 12 insertions(+), 5 deletions(-) > > [snip patch, which fixes of_node_put() handling for > for_each_available_child_of_node() loop, which creates PHY devices with > devm_phy_create()] > > This reminds me of a potential problem I'm looking at in other > subsystems: from code reading (I haven't seen any issues in practice, > probably because I don't use OF_DYNAMIC) it looks like device-creating > infrastructure like the PHY subsystem should be acquiring a reference to > the device_node when they stash it away. But drivers/phy/phy-core.c does > not do this, AFAICT. > > See phy_create(), which does > > phy->dev.of_node = node ?: dev->of_node; > > and later might reuse this of_node pointer, even though it never called > of_node_get() on this node. > > Potential patch to fix this (not tested). > > Signed-off-by: Brian Norris <computersforpeace@gmail.com> > > diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c > index fc48fac003a6..8df29caeeef9 100644 > --- a/drivers/phy/phy-core.c > +++ b/drivers/phy/phy-core.c > @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > phy->dev.class = phy_class; > phy->dev.parent = dev; > phy->dev.of_node = node ?: dev->of_node; > + of_node_get(phy->dev.of_node); > phy->id = id; > phy->ops = ops; > > @@ -726,6 +727,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, > return phy; > > put_dev: > + of_node_put(phy->dev.of_node); > put_device(&phy->dev); /* calls phy_release() which frees resources */ > return ERR_PTR(ret); > > @@ -775,6 +777,7 @@ EXPORT_SYMBOL_GPL(devm_phy_create); > */ > void phy_destroy(struct phy *phy) > { > + of_node_put(phy->dev.of_node); I think it's better to have this patch in phy-core though OF_DYNAMIC is not enabled? Grant, Is it safe to assume of_node_get() will prevent "anyone else" from deleting the node? Here phy core uses the node pointer (passed to it by phy providers) and we would like to avoid "anyone" from removing this node pointer resulting in phy core having an invalid node pointer. Using of_node_get() in phy core should be sufficient for this? We are also interested in this todo tasklist for Devicetree.. "Document node lifecycle for CONFIG_OF_DYNAMIC" Please find the complete thread of this mail chain here [1] [1] -> http://www.gossamer-threads.com/lists/linux/kernel/2304857 Thanks Kishon > pm_runtime_disable(&phy->dev); > device_unregister(&phy->dev); > } >
diff --git a/drivers/phy/phy-core.c b/drivers/phy/phy-core.c index fc48fac003a6..8df29caeeef9 100644 --- a/drivers/phy/phy-core.c +++ b/drivers/phy/phy-core.c @@ -697,6 +697,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, phy->dev.class = phy_class; phy->dev.parent = dev; phy->dev.of_node = node ?: dev->of_node; + of_node_get(phy->dev.of_node); phy->id = id; phy->ops = ops; @@ -726,6 +727,7 @@ struct phy *phy_create(struct device *dev, struct device_node *node, return phy; put_dev: + of_node_put(phy->dev.of_node); put_device(&phy->dev); /* calls phy_release() which frees resources */ return ERR_PTR(ret); @@ -775,6 +777,7 @@ EXPORT_SYMBOL_GPL(devm_phy_create); */ void phy_destroy(struct phy *phy) { + of_node_put(phy->dev.of_node); pm_runtime_disable(&phy->dev); device_unregister(&phy->dev); }