From 6cc69f2a404dea8641d6cf97c0fbe8d24579e259 Mon Sep 17 00:00:00 2001 From: hayeswang Date: Fri, 17 Oct 2014 16:55:08 +0800 Subject: [PATCH] r8152: return -EBUSY for runtime suspend Remove calling cancel_delayed_work_sync() for runtime suspend, because it would cause dead lock. Instead, return -EBUSY to avoid the device enters suspending if the net is running and the delayed work is pending or running. The delayed work would try to wake up the device later, so the suspending is not necessary. Signed-off-by: Hayes Wang Signed-off-by: David S. Miller --- drivers/net/usb/r8152.c | 22 +++++++++++++++------- 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/drivers/net/usb/r8152.c b/drivers/net/usb/r8152.c index 864159eb744e..e3d84c322e4e 100644 --- a/drivers/net/usb/r8152.c +++ b/drivers/net/usb/r8152.c @@ -3189,31 +3189,39 @@ static void r8153_init(struct r8152 *tp) static int rtl8152_suspend(struct usb_interface *intf, pm_message_t message) { struct r8152 *tp = usb_get_intfdata(intf); + struct net_device *netdev = tp->netdev; + int ret = 0; mutex_lock(&tp->control); - if (PMSG_IS_AUTO(message)) + if (PMSG_IS_AUTO(message)) { + if (netif_running(netdev) && work_busy(&tp->schedule.work)) { + ret = -EBUSY; + goto out1; + } + set_bit(SELECTIVE_SUSPEND, &tp->flags); - else - netif_device_detach(tp->netdev); + } else { + netif_device_detach(netdev); + } - if (netif_running(tp->netdev)) { + if (netif_running(netdev)) { clear_bit(WORK_ENABLE, &tp->flags); usb_kill_urb(tp->intr_urb); - cancel_delayed_work_sync(&tp->schedule); tasklet_disable(&tp->tl); if (test_bit(SELECTIVE_SUSPEND, &tp->flags)) { rtl_stop_rx(tp); rtl_runtime_suspend_enable(tp, true); } else { + cancel_delayed_work_sync(&tp->schedule); tp->rtl_ops.down(tp); } tasklet_enable(&tp->tl); } - +out1: mutex_unlock(&tp->control); - return 0; + return ret; } static int rtl8152_resume(struct usb_interface *intf) -- 2.30.2