Some Eclipse Foundation services are deprecated, or will be soon. Please ensure you've read this important communication.

Bug 366517

Summary: JobManager Deadlock, Device.dispose() vs Device.isDisposed()
Product: [RT] RAP Reporter: Wolfgang Pedot <wolfgang.pedot>
Component: WorkbenchAssignee: Project Inbox <rap-inbox>
Status: RESOLVED DUPLICATE QA Contact:
Severity: normal    
Priority: P3    
Version: 1.4   
Target Milestone: ---   
Hardware: PC   
OS: Linux   
Whiteboard:

Description Wolfgang Pedot CLA 2011-12-13 07:00:18 EST
Build Identifier: 1.4.0.20110614-2335

Every now and again our application suffers a "catastrophic" deadlock blocking the global JobManager-Instance. This means we have to restart our server because parts of the UI do not work without jobs.

The problem appears when a workbench gets shut down due to a session timeout (display is disposed) AND a job finishes/is canceled while "dispose" is running.
In the end it comes down to "Device.dispose()" vs "Device.isDisposed()".

Stacktraces of the UIThread vary but the Worker-Thread is always locked in JobManagerAdapter.done, I have attached two sample-stacktraces below.

I have not found a duplicate of this bug although I imagine that "dispose" vs "isDisposed" caused a few other problems as well...

Maybe this could be fixed by only protecting the change of the "disposed" member in "dispose" and have "isDisposed" return true once "dispose" has started rather than blocking it until "dispose" is done but I lack the insight to know what other repercussions this might have.

Reproducible: Sometimes

Steps to Reproduce:
First Example: lock triggered by our widget canceling a job

Name: Worker-17
State: BLOCKED on java.lang.Object@2eff54aa owned by: UIThread [rq710pfmfnqpsd6a2dyptd9a]
Total blocked: 144  Total waited: 241

Stack trace: 
org.eclipse.swt.graphics.Device.isDisposed(Device.java:304)
org.eclipse.rap.ui.internal.progress.JobManagerAdapter.done(JobManagerAdapter.java:120)
   - locked java.lang.Object@db80f77
org.eclipse.core.internal.jobs.JobListeners$3.notify(JobListeners.java:39)
org.eclipse.core.internal.jobs.JobListeners.doNotify(JobListeners.java:96)
org.eclipse.core.internal.jobs.JobListeners.done(JobListeners.java:152)
org.eclipse.core.internal.jobs.JobManager.endJob(JobManager.java:647)
org.eclipse.core.internal.jobs.JobManager.startJob(JobManager.java:1507)
org.eclipse.core.internal.jobs.WorkerPool.startJob(WorkerPool.java:221)
org.eclipse.core.internal.jobs.Worker.run(Worker.java:50)

Name: UIThread [rq710pfmfnqpsd6a2dyptd9a]
State: BLOCKED on java.lang.Object@db80f77 owned by: Worker-17
Total blocked: 137  Total waited: 137

Stack trace: 
org.eclipse.core.internal.jobs.JobManager.cancel(JobManager.java:296)
org.eclipse.core.internal.jobs.InternalJob.cancel(InternalJob.java:187)
org.eclipse.core.runtime.jobs.Job.cancel(Job.java:195)
at.finkzeit.zsw.client.main.masterdata.table.FilteredTable$1.widgetDisposed(FilteredTable.java:408)
org.eclipse.swt.events.DisposeEvent.dispatchToObserver(DisposeEvent.java:64)
org.eclipse.rwt.internal.events.Event.processEvent(Event.java:44)
org.eclipse.swt.events.TypedEvent.processEvent(TypedEvent.java:163)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:771)
org.eclipse.swt.widgets.Composite.releaseChildren(Composite.java:820)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:774)
org.eclipse.swt.widgets.Composite.releaseChildren(Composite.java:820)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:774)
org.eclipse.swt.widgets.Composite.releaseChildren(Composite.java:820)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:774)
org.eclipse.swt.widgets.Composite.releaseChildren(Composite.java:820)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:774)
org.eclipse.swt.widgets.Composite.releaseChildren(Composite.java:820)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:774)
org.eclipse.swt.widgets.Composite.releaseChildren(Composite.java:820)
org.eclipse.swt.widgets.Widget.dispose(Widget.java:774)
org.eclipse.ui.internal.PartPane.dispose(PartPane.java:185)
org.eclipse.ui.internal.ViewPane.dispose(ViewPane.java:192)
org.eclipse.ui.internal.WorkbenchPartReference.dispose(WorkbenchPartReference.java:685)
org.eclipse.ui.internal.WorkbenchPage.disposePart(WorkbenchPage.java:1719)
org.eclipse.ui.internal.WorkbenchPage.partRemoved(WorkbenchPage.java:1711)
org.eclipse.ui.internal.ViewFactory.releaseView(ViewFactory.java:254)
org.eclipse.ui.internal.Perspective.dispose(Perspective.java:293)
org.eclipse.ui.internal.WorkbenchPage.dispose(WorkbenchPage.java:1791)
org.eclipse.ui.internal.WorkbenchWindow.closeAllPages(WorkbenchWindow.java:853)
org.eclipse.ui.internal.WorkbenchWindow.hardClose(WorkbenchWindow.java:1779)
org.eclipse.ui.internal.WorkbenchWindow.busyClose(WorkbenchWindow.java:726)
org.eclipse.ui.internal.WorkbenchWindow.access$0(WorkbenchWindow.java:702)
org.eclipse.ui.internal.WorkbenchWindow$5.run(WorkbenchWindow.java:818)
org.eclipse.swt.custom.BusyIndicator.showWhile(BusyIndicator.java:66)
org.eclipse.ui.internal.WorkbenchWindow.close(WorkbenchWindow.java:816)
org.eclipse.jface.window.WindowManager.close(WindowManager.java:109)
org.eclipse.ui.internal.Workbench$14.run(Workbench.java:1152)
org.eclipse.core.runtime.SafeRunner.run(SafeRunner.java:42)
org.eclipse.ui.internal.Workbench.busyClose(Workbench.java:1149)
org.eclipse.ui.internal.Workbench.access$12(Workbench.java:1072)
org.eclipse.ui.internal.Workbench$22.run(Workbench.java:1338)
org.eclipse.swt.custom.BusyIndicator.showWhile(BusyIndicator.java:66)
org.eclipse.ui.internal.Workbench.close(Workbench.java:1336)
org.eclipse.ui.internal.Workbench.close(Workbench.java:1298)
org.eclipse.ui.internal.Workbench$ShutdownHandler.handleEvent(Workbench.java:388)
org.eclipse.swt.widgets.Display.sendDisposeEvent(Display.java:709)
org.eclipse.swt.widgets.Display.release(Display.java:688)
org.eclipse.swt.graphics.Device.dispose(Device.java:286)
   - locked java.lang.Object@2eff54aa
org.eclipse.rwt.internal.lifecycle.UIThread.processShutdown(UIThread.java:159)
org.eclipse.rwt.internal.lifecycle.RWTLifeCycle$UIThreadController.run(RWTLifeCycle.java:102)
   - locked org.eclipse.rwt.internal.lifecycle.UIThread@3400bbce
java.lang.Thread.run(Thread.java:636)
org.eclipse.rwt.internal.lifecycle.UIThread.run(UIThread.java:102)


Second Example: lock triggered by "cancelEarlyStartup" or Workbench

Name: Worker-0
State: BLOCKED on java.lang.Object@2e705b48 owned by: UIThread [lffk9p7yrm3w1c9utk6celbgu]
Total blocked: 672  Total waited: 1.425

Stack trace: 
org.eclipse.swt.graphics.Device.isDisposed(Device.java:304)
org.eclipse.rap.ui.internal.progress.JobManagerAdapter.done(JobManagerAdapter.java:120)
   - locked java.lang.Object@6ca88fab
org.eclipse.core.internal.jobs.JobListeners$3.notify(JobListeners.java:39)
org.eclipse.core.internal.jobs.JobListeners.doNotify(JobListeners.java:96)
org.eclipse.core.internal.jobs.JobListeners.done(JobListeners.java:152)
org.eclipse.core.internal.jobs.JobManager.endJob(JobManager.java:647)
org.eclipse.core.internal.jobs.JobManager.startJob(JobManager.java:1507)
org.eclipse.core.internal.jobs.WorkerPool.startJob(WorkerPool.java:221)
org.eclipse.core.internal.jobs.Worker.run(Worker.java:50)

Name: UIThread [lffk9p7yrm3w1c9utk6celbgu]
State: BLOCKED on java.lang.Object@6ca88fab owned by: Worker-0
Total blocked: 260  Total waited: 264

Stack trace: 
org.eclipse.core.internal.jobs.JobManager.select(JobManager.java:1159)
org.eclipse.core.internal.jobs.JobManager.select(JobManager.java:1149)
org.eclipse.core.internal.jobs.JobManager.cancel(JobManager.java:334)
org.eclipse.ui.internal.Workbench.cancelEarlyStartup(Workbench.java:3120)
org.eclipse.ui.internal.Workbench.shutdown(Workbench.java:3083)
org.eclipse.ui.internal.Workbench.busyClose(Workbench.java:1161)
org.eclipse.ui.internal.Workbench.access$12(Workbench.java:1072)
org.eclipse.ui.internal.Workbench$22.run(Workbench.java:1338)
org.eclipse.swt.custom.BusyIndicator.showWhile(BusyIndicator.java:66)
org.eclipse.ui.internal.Workbench.close(Workbench.java:1336)
org.eclipse.ui.internal.Workbench.close(Workbench.java:1298)
org.eclipse.ui.internal.Workbench$ShutdownHandler.handleEvent(Workbench.java:388)
org.eclipse.swt.widgets.Display.sendDisposeEvent(Display.java:709)
org.eclipse.swt.widgets.Display.release(Display.java:688)
org.eclipse.swt.graphics.Device.dispose(Device.java:286)
   - locked java.lang.Object@2e705b48
org.eclipse.rwt.internal.lifecycle.UIThread.processShutdown(UIThread.java:159)
org.eclipse.rwt.internal.lifecycle.RWTLifeCycle$UIThreadController.run(RWTLifeCycle.java:102)
   - locked org.eclipse.rwt.internal.lifecycle.UIThread@7cbcdba9
java.lang.Thread.run(Thread.java:636)
org.eclipse.rwt.internal.lifecycle.UIThread.run(UIThread.java:102)
Comment 1 RĂ¼diger Herrmann CLA 2011-12-13 08:41:18 EST
To me this looks like a buplicate of bug 320182. The issue is fixed in 1.5M4 and the fix is proposed for the 1.4.2 service release ( 2/24/2012).
Please reopen if you disagree.

*** This bug has been marked as a duplicate of bug 320182 ***
Comment 2 Wolfgang Pedot CLA 2011-12-13 08:47:33 EST
For some reason I did not see that bug when I searched for "deadlock", I fully agree that this is a duplicate and will check out the solution.

Sorry for the inconvenience.