Re: [PATCH] HID: i2c-hid: goodix: Fix a lockdep splat

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi,

On Fri, Jan 28, 2022 at 9:48 AM Daniel Thompson
<daniel.thompson@xxxxxxxxxx> wrote:
>
> I'm was on the receiving end of a lockdep splat from this driver and after
> scratching my head I couldn't be entirely sure it was a false positive
> given we would also have to think about whether the regulator locking is
> safe (since the notifier is called whilst holding regulator locks which
> are also needed for regulator_is_enabled() ).
>
> Regardless of whether it is a real bug or not, the mutex isn't needed.
> We can use reference counting tricks instead to avoid races with the
> notifier calls.
>
> The observed splat follows:
>
> ------------------------------------------------------
> kworker/u16:3/127 is trying to acquire lock:
> ffff00008021fb20 (&ihid_goodix->regulator_mutex){+.+.}-{4:4}, at: ihid_goodix_vdd_notify+0x30/0x94
>
> but task is already holding lock:
> ffff0000835c60c0 (&(&rdev->notifier)->rwsem){++++}-{4:4}, at: blocking_notifier_call_chain+0x30/0x70
>
> which lock already depends on the new lock.
>
>
> the existing dependency chain (in reverse order) is:
>
> -> #1 (&(&rdev->notifier)->rwsem){++++}-{4:4}:
>        down_write+0x68/0x8c
>        blocking_notifier_chain_register+0x54/0x70
>        regulator_register_notifier+0x1c/0x24
>        devm_regulator_register_notifier+0x58/0x98
>        i2c_hid_of_goodix_probe+0xdc/0x158
>        i2c_device_probe+0x25d/0x270
>        really_probe+0x174/0x2cc
>        __driver_probe_device+0xc0/0xd8
>        driver_probe_device+0x50/0xe4
>        __device_attach_driver+0xa8/0xc0
>        bus_for_each_drv+0x9c/0xc0
>        __device_attach_async_helper+0x6c/0xbc
>        async_run_entry_fn+0x38/0x100
>        process_one_work+0x294/0x438
>        worker_thread+0x180/0x258
>        kthread+0x120/0x130
>        ret_from_fork+0x10/0x20
>
> -> #0 (&ihid_goodix->regulator_mutex){+.+.}-{4:4}:
>        __lock_acquire+0xd24/0xfe8
>        lock_acquire+0x288/0x2f4
>        __mutex_lock+0xa0/0x338
>        mutex_lock_nested+0x3c/0x5c
>        ihid_goodix_vdd_notify+0x30/0x94
>        notifier_call_chain+0x6c/0x8c
>        blocking_notifier_call_chain+0x48/0x70
>        _notifier_call_chain.isra.0+0x18/0x20
>        _regulator_enable+0xc0/0x178
>        regulator_enable+0x40/0x7c
>        goodix_i2c_hid_power_up+0x18/0x20
>        i2c_hid_core_power_up.isra.0+0x1c/0x2c
>        i2c_hid_core_probe+0xd8/0x3d4
>        i2c_hid_of_goodix_probe+0x14c/0x158
>        i2c_device_probe+0x25c/0x270
>        really_probe+0x174/0x2cc
>        __driver_probe_device+0xc0/0xd8
>        driver_probe_device+0x50/0xe4
>        __device_attach_driver+0xa8/0xc0
>        bus_for_each_drv+0x9c/0xc0
>        __device_attach_async_helper+0x6c/0xbc
>        async_run_entry_fn+0x38/0x100
>        process_one_work+0x294/0x438
>        worker_thread+0x180/0x258
>        kthread+0x120/0x130
>        ret_from_fork+0x10/0x20
>
> other info that might help us debug this:
>
>  Possible unsafe locking scenario:
>
>        CPU0                    CPU1
>        ----                    ----
>   lock(&(&rdev->notifier)->rwsem);
>                                lock(&ihid_goodix->regulator_mutex);
>                                lock(&(&rdev->notifier)->rwsem);
>   lock(&ihid_goodix->regulator_mutex);
>
>  *** DEADLOCK ***
>
> Signed-off-by: Daniel Thompson <daniel.thompson@xxxxxxxxxx>
> ---
>  drivers/hid/i2c-hid/i2c-hid-of-goodix.c | 28 +++++++++++--------------
>  1 file changed, 12 insertions(+), 16 deletions(-)

Yes, this seems like a reasonable solution, thanks! Probably want:

Fixes: 18eeef46d359 ("HID: i2c-hid: goodix: Tie the reset line to true
state of the regulator")

Reviewed-by: Douglas Anderson <dianders@xxxxxxxxxxxx>



[Index of Archives]     [Linux Media Devel]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Linux Wireless Networking]     [Linux Omap]

  Powered by Linux