-
Rafael J. Wysocki authored
DRM / radeon / KMS: Fix hibernation regression related to radeon PM (was: Re: [Regression, post-2.6.34] Hibernation broken on machines with radeon/KMS and r300) There is a regression from 2.6.34 related to the recent radeon power management changes, caused by attempting to cancel a delayed work item that's never been scheduled. However, the code as is has some other issues potentially leading to visible problems. First, the mutex around cancel_delayed_work() in radeon_pm_suspend() doesn't really serve any purpose, because cancel_delayed_work() only tries to delete the work's timer. Moreover, it doesn't prevent the work handler from running, so the handler can do some wrong things if it wins the race and in that case it will rearm itself to do some more wrong things going forward. So, I think it's better to wait for the handler to return in case it's already been queued up for execution. Also, it should be prevented from rearming itself in that case. Second, in radeon_set_pm_method() the cancel_delayed_work() is not sufficient to prevent the work handler from running and queing up itself for the next run (the failure scenario is that cancel_delayed_work() returns 0, so the handler is run, it waits on the mutex and then rearms itself after the mutex has been released), so again the work handler should be prevented from rearming itself in that case.. Finally, there's a potential deadlock in radeon_pm_fini(), because cancel_delayed_work_sync() is called under rdev->pm.mutex, but the work handler tries to acquire the same mutex (if it wins the race). Fix the issues described above. Signed-off-by: Rafael J. Wysocki <rjw@sisk.pl> Reviewed-by: Alex Deucher <alexdeucher@gmail.com> Signed-off-by: Dave Airlie <airlied@redhat.com>
3f53eb6f