[v2] clk: Fix memory leak in devm_clk_notifier_register()

Message ID 20230619112253.v2.1.I13f060c10549ef181603e921291bdea95f83033c@changeid
State New
Headers
Series [v2] clk: Fix memory leak in devm_clk_notifier_register() |

Commit Message

Fei Shao June 19, 2023, 3:22 a.m. UTC
  devm_clk_notifier_register() allocates a devres resource for clk
notifier but didn't register that to the device, so the notifier didn't
get unregistered on device detach and the allocated resource was leaked.

Fix the issue by registering the resource through devres_add().

Fixes: 6d30d50d037d ("clk: add devm variant of clk_notifier_register")
Signed-off-by: Fei Shao <fshao@chromium.org>
---

Changes in v2:
- Revise commit message

 drivers/clk/clk.c | 1 +
 1 file changed, 1 insertion(+)
  

Comments

Dan Carpenter June 19, 2023, 8:48 a.m. UTC | #1
On Mon, Jun 19, 2023 at 11:22:53AM +0800, Fei Shao wrote:
> devm_clk_notifier_register() allocates a devres resource for clk
> notifier but didn't register that to the device, so the notifier didn't
> get unregistered on device detach and the allocated resource was leaked.
> 
> Fix the issue by registering the resource through devres_add().
> 
> Fixes: 6d30d50d037d ("clk: add devm variant of clk_notifier_register")
> Signed-off-by: Fei Shao <fshao@chromium.org>
> ---
> 

Reviewed-by: Dan Carpenter <dan.carpenter@linaro.org>

How did you find this bug?

I can think of some ways to find this bug with static analysis.

KTODO: static analysis:  look at unused parameters

Both GCC and Clang have a warning for unused parameters.  I think the
last time I looked at GCC it had a lot of false positives for functions
which were called as pointers but hopefully that has been fixed now?
Smatch does not have a check for this.  If someone were to write it,
I would probably the check under the --pedantic flag so it would be
turned off by default.

regards,
dan carpenter
  
Fei Shao June 19, 2023, 9:05 a.m. UTC | #2
On Mon, Jun 19, 2023 at 4:48 PM Dan Carpenter <dan.carpenter@linaro.org> wrote:
>
> On Mon, Jun 19, 2023 at 11:22:53AM +0800, Fei Shao wrote:
> > devm_clk_notifier_register() allocates a devres resource for clk
> > notifier but didn't register that to the device, so the notifier didn't
> > get unregistered on device detach and the allocated resource was leaked.
> >
> > Fix the issue by registering the resource through devres_add().
> >
> > Fixes: 6d30d50d037d ("clk: add devm variant of clk_notifier_register")
> > Signed-off-by: Fei Shao <fshao@chromium.org>
> > ---
> >
>
> Reviewed-by: Dan Carpenter <dan.carpenter@linaro.org>
>
> How did you find this bug?
>
> I can think of some ways to find this bug with static analysis.
>

It was actually detected by kmemleak on an unreleased Chromebook device.
I added the trace snippet in the message at first but removed that
before sending this. Maybe I shouldn't have.

I can resend a v3 to add that back if that's preferable. What do you think?

Regards,
Fei


> KTODO: static analysis:  look at unused parameters
>
> Both GCC and Clang have a warning for unused parameters.  I think the
> last time I looked at GCC it had a lot of false positives for functions
> which were called as pointers but hopefully that has been fixed now?
> Smatch does not have a check for this.  If someone were to write it,
> I would probably the check under the --pedantic flag so it would be
> turned off by default.
>
> regards,
> dan carpenter
>
  
Dan Carpenter June 19, 2023, 9:24 a.m. UTC | #3
On Mon, Jun 19, 2023 at 05:05:47PM +0800, Fei Shao wrote:
> On Mon, Jun 19, 2023 at 4:48 PM Dan Carpenter <dan.carpenter@linaro.org> wrote:
> >
> > On Mon, Jun 19, 2023 at 11:22:53AM +0800, Fei Shao wrote:
> > > devm_clk_notifier_register() allocates a devres resource for clk
> > > notifier but didn't register that to the device, so the notifier didn't
> > > get unregistered on device detach and the allocated resource was leaked.
> > >
> > > Fix the issue by registering the resource through devres_add().
> > >
> > > Fixes: 6d30d50d037d ("clk: add devm variant of clk_notifier_register")
> > > Signed-off-by: Fei Shao <fshao@chromium.org>
> > > ---
> > >
> >
> > Reviewed-by: Dan Carpenter <dan.carpenter@linaro.org>
> >
> > How did you find this bug?
> >
> > I can think of some ways to find this bug with static analysis.
> >
> 
> It was actually detected by kmemleak on an unreleased Chromebook device.
> I added the trace snippet in the message at first but removed that
> before sending this. Maybe I shouldn't have.
> 
> I can resend a v3 to add that back if that's preferable. What do you think?

I'm not a clk maintainer, but let's not go overboard resending patches,
especially when they're as straight forward as this one.

This is good information though so I would include that kind of stuff in
future patches.  I don't really need to see the kmemleak warning itself
because I know what those look like already.  But to me it says a lot
that actually this was detected at runtime.  It says good things about
your test infrastructure and makes me feel more confident that your
patch is correct.  So maybe just a comment that "This leak was detected
by kmemleak".

regards,
dan carpenter
  
Fei Shao June 19, 2023, 9:38 a.m. UTC | #4
On Mon, Jun 19, 2023 at 5:24 PM Dan Carpenter <dan.carpenter@linaro.org> wrote:
>
> On Mon, Jun 19, 2023 at 05:05:47PM +0800, Fei Shao wrote:
> > On Mon, Jun 19, 2023 at 4:48 PM Dan Carpenter <dan.carpenter@linaro.org> wrote:
> > >
> > > On Mon, Jun 19, 2023 at 11:22:53AM +0800, Fei Shao wrote:
> > > > devm_clk_notifier_register() allocates a devres resource for clk
> > > > notifier but didn't register that to the device, so the notifier didn't
> > > > get unregistered on device detach and the allocated resource was leaked.
> > > >
> > > > Fix the issue by registering the resource through devres_add().
> > > >
> > > > Fixes: 6d30d50d037d ("clk: add devm variant of clk_notifier_register")
> > > > Signed-off-by: Fei Shao <fshao@chromium.org>
> > > > ---
> > > >
> > >
> > > Reviewed-by: Dan Carpenter <dan.carpenter@linaro.org>
> > >
> > > How did you find this bug?
> > >
> > > I can think of some ways to find this bug with static analysis.
> > >
> >
> > It was actually detected by kmemleak on an unreleased Chromebook device.
> > I added the trace snippet in the message at first but removed that
> > before sending this. Maybe I shouldn't have.
> >
> > I can resend a v3 to add that back if that's preferable. What do you think?
>
> I'm not a clk maintainer, but let's not go overboard resending patches,
> especially when they're as straight forward as this one.
>
> This is good information though so I would include that kind of stuff in
> future patches.  I don't really need to see the kmemleak warning itself
> because I know what those look like already.  But to me it says a lot
> that actually this was detected at runtime.  It says good things about
> your test infrastructure and makes me feel more confident that your
> patch is correct.  So maybe just a comment that "This leak was detected
> by kmemleak".

That makes sense. Acknowledged and noted.

Thanks,
Fei

>
> regards,
> dan carpenter
>
  
Dan Carpenter June 19, 2023, 9:57 a.m. UTC | #5
On Mon, Jun 19, 2023 at 12:24:41PM +0300, Dan Carpenter wrote:
> > It was actually detected by kmemleak on an unreleased Chromebook device.
> > I added the trace snippet in the message at first but removed that
> > before sending this. Maybe I shouldn't have.
> > 
> > I can resend a v3 to add that back if that's preferable. What do you think?

The other reason to include stack traces is so that if someone else
runs into the same bug they can find your patch by googling their stack
trace.

Normal users aren't going to be running kmemleak.  And people doing
testing work for companies are hopefully going to pull this fix in via
the stable tree so they'll get this patch automatically that way so
they won't see it either.

But if the stack trace is like a NULL dereference bug, then users
absolutely do notice that kind of thing.  You should always include
those kind of stack traces.

regards,
dan carpenter
  
Fei Shao June 19, 2023, 10:34 a.m. UTC | #6
On Mon, Jun 19, 2023 at 5:57 PM Dan Carpenter <dan.carpenter@linaro.org> wrote:
> The other reason to include stack traces is so that if someone else
> runs into the same bug they can find your patch by googling their stack
> trace.
>
> Normal users aren't going to be running kmemleak.  And people doing
> testing work for companies are hopefully going to pull this fix in via
> the stable tree so they'll get this patch automatically that way so
> they won't see it either.
>
> But if the stack trace is like a NULL dereference bug, then users
> absolutely do notice that kind of thing.  You should always include
> those kind of stack traces.

If that's the case, I can leave a retrospective trace record here:

unreferenced object 0xffffff80c4e34a00 (size 256):
  comm "swapper/0", pid 1, jiffies 4294667967 (age 288.740s)
  hex dump (first 32 bytes):
    00 4a e3 c4 80 ff ff ff 00 4a e3 c4 80 ff ff ff  .J.......J......
    1c 2a 7a ae d8 ff ff ff a0 b0 af af d8 ff ff ff  .*z.............
  backtrace:
    [<000000007d72e65c>] __kmem_cache_alloc_node+0x198/0x240
    [<00000000dfce47ef>] __kmalloc_node_track_caller+0x6c/0x1b8
    [<00000000b6c409fe>] __devres_alloc_node+0x60/0x104
    [<0000000081112baf>] devm_clk_notifier_register+0x44/0xc8
    [<0000000070bfe318>] devm_mtk_clk_mux_notifier_register+0x60/0x74
    [<000000000242235f>] clk_mt8188_reg_mfg_mux_notifier+0x84/0xb4
    [<00000000f67ce424>] clk_mt8188_topck_probe+0x1b8/0x2e4
    [<0000000006eef8cd>] platform_probe+0x12c/0x17c
    [<00000000eacf783c>] really_probe+0x1f0/0x4d8
    [<00000000f321a3f0>] __driver_probe_device+0x160/0x230
    [<00000000bbeed898>] driver_probe_device+0x6c/0x148
    [<000000007d5af62b>] __driver_attach+0x164/0x20c
    [<00000000c5c25e77>] bus_for_each_dev+0xf4/0x144
    [<00000000e2c0100f>] driver_attach+0x50/0x60
    [<00000000cc421ec0>] bus_add_driver+0x2a8/0x458
    [<000000007814168a>] driver_register+0x16c/0x29c

It's up to the maintainers for the next step and I'll follow the call.

Regards,
Fei
  
Stephen Boyd June 20, 2023, 7:03 p.m. UTC | #7
Quoting Fei Shao (2023-06-18 20:22:53)
> devm_clk_notifier_register() allocates a devres resource for clk
> notifier but didn't register that to the device, so the notifier didn't
> get unregistered on device detach and the allocated resource was leaked.
> 
> Fix the issue by registering the resource through devres_add().
> 
> Fixes: 6d30d50d037d ("clk: add devm variant of clk_notifier_register")
> Signed-off-by: Fei Shao <fshao@chromium.org>
> ---

Applied to clk-next

It would be nice to also add a test or two for this.
  

Patch

diff --git a/drivers/clk/clk.c b/drivers/clk/clk.c
index 7ac9f7a8cb84..c249f9791ae8 100644
--- a/drivers/clk/clk.c
+++ b/drivers/clk/clk.c
@@ -4741,6 +4741,7 @@  int devm_clk_notifier_register(struct device *dev, struct clk *clk,
 	if (!ret) {
 		devres->clk = clk;
 		devres->nb = nb;
+		devres_add(dev, devres);
 	} else {
 		devres_free(devres);
 	}