I submitted a patch to scijava-common with the changes. https://github.com/scijava/scijava-common/pull/13
On Mon, Sep 30, 2013 at 3:32 PM, Barry DeZonia <[email protected]> wrote: > A proposed fix would be good Lee. I'd like to test the async status update > code for responsiveness (i.e. when opening a large image let's say). Let me > know when your fix is in place. Thanks. > > > On Fri, Sep 27, 2013 at 6:54 AM, Lee Kamentsky <[email protected]>wrote: > >> Thanks Barry, the email was a little rushed - finished it while going out >> the door. What do you think about sending the status messages >> asynchronously? It looks to me like the AWT event processing will display >> them in the order received, so that makes sure that a "Finished" message >> will be seen after a "% complete" message. Status reporting is such a >> common thing - it'd be a shame for all the worker threads to stall because >> a user was using ImageJ to watch a movie of a cat falling off a TV while >> their batch job was running. >> >> I think I'll submit a patch to DefaultStatusService for asynch reporting >> and maybe Curtis or you could look it over and accept it. If you reject, NP. >> >> --Lee >> >> >> On Thu, Sep 26, 2013 at 7:53 PM, Barry DeZonia <[email protected]>wrote: >> >>> Hi Lee, >>> >>> I added the synchronized keyword yesterday to fix a bug. We can undo >>> that change. I can work around the problem in another fashion if necessary. >>> >>> >>> On Thu, Sep 26, 2013 at 3:57 PM, Lee Kamentsky >>> <[email protected]>wrote: >>> >>>> Hi all, I'm getting a deadly embrace that happens when the AWT event >>>> queue thread tries to get a lock within DefaultDatasetView.getColor and >>>> when DefaultStatusService.showStatus on a worker thread tries to publish a >>>> synchronous request for status display after taking the >>>> DefaultDatasetView's lock in DefaultDatasetView.rebuild. It happens >>>> periodically, but it's timing-dependent, so not so reproducible. >>>> >>>> The bug is somewhat debatable. Possible candidates: It's a little >>>> drastic for DefaultDatasetView.getColor to synchronize on the view itself. >>>> Maybe some proxy for the color system could have a synchronizing object. >>>> The other candidate is DefaultEventService.showStatus which could use >>>> EventService.publishLater - I don't think there's much need for status >>>> publishers to wait around for the status to show on the screen. >>>> >>>> The two stack traces: >>>> Thread [AWT-EventQueue-0] (Suspended) >>>> DefaultDatasetView.getColor(ChannelCollection) line: 261 Synchronized >>>> method on DefaultDatasetView >>>> FgColorTool(AbstractColorTool).drawIcon() line: 175 >>>> FgColorTool(AbstractColorTool).onEvent(DisplayActivatedEvent) line: 184 >>>> NativeMethodAccessorImpl.invoke0(Method, Object, Object[]) line: not >>>> available [native method] >>>> NativeMethodAccessorImpl.invoke(Object, Object[]) line: 39 >>>> DelegatingMethodAccessorImpl.invoke(Object, Object[]) line: 25 >>>> Method.invoke(Object, Object...) line: 597 >>>> DefaultEventService$ProxySubscriber<E>.onEvent(E) line: 282 >>>> DefaultEventService$ProxySubscriber<E>.onEvent(Object) line: 1 >>>> DefaultEventBus(ThreadSafeEventService).publish(Object, String, >>>> Object, List, List, StackTraceElement[]) line: 971 >>>> DefaultEventBus.access$1(DefaultEventBus, Object, String, Object, >>>> List, List, StackTraceElement[]) line: 1 >>>> DefaultEventBus$1.run() line: 201 >>>> DefaultThreadService.invoke(Runnable) line: 91 >>>> DefaultEventBus.publishNow(Object, String, Object, List, List, >>>> StackTraceElement[]) line: 195 >>>> DefaultEventBus.publishNow(Object) line: 86 >>>> DefaultEventService.publish(E) line: 95 >>>> DefaultDisplayService.setActiveDisplay(Display<?>) line: 129 >>>> DefaultDisplayService.onEvent(WinActivatedEvent) line: 247 >>>> NativeMethodAccessorImpl.invoke0(Method, Object, Object[]) line: not >>>> available [native method] >>>> NativeMethodAccessorImpl.invoke(Object, Object[]) line: 39 >>>> DelegatingMethodAccessorImpl.invoke(Object, Object[]) line: 25 >>>> Method.invoke(Object, Object...) line: 597 >>>> DefaultEventService$ProxySubscriber<E>.onEvent(E) line: 282 >>>> DefaultEventService$ProxySubscriber<E>.onEvent(Object) line: 1 >>>> DefaultEventBus(ThreadSafeEventService).publish(Object, String, >>>> Object, List, List, StackTraceElement[]) line: 971 >>>> DefaultEventBus.access$1(DefaultEventBus, Object, String, Object, >>>> List, List, StackTraceElement[]) line: 1 >>>> DefaultEventBus$1.run() line: 201 >>>> DefaultThreadService.invoke(Runnable) line: 91 >>>> DefaultEventBus.publishNow(Object, String, Object, List, List, >>>> StackTraceElement[]) line: 195 >>>> DefaultEventBus.publishNow(Object) line: 86 >>>> DefaultEventService.publish(E) line: 95 >>>> AWTWindowEventDispatcher.windowActivated(WindowEvent) line: 94 >>>> SwingDisplayWindow(Window).processWindowEvent(WindowEvent) line: 1877 >>>> SwingDisplayWindow(JFrame).processWindowEvent(WindowEvent) line: 274 >>>> SwingDisplayWindow(Window).processEvent(AWTEvent) line: 1823 >>>> SwingDisplayWindow(Component).dispatchEventImpl(AWTEvent) line: 4630 >>>> SwingDisplayWindow(Container).dispatchEventImpl(AWTEvent) line: 2099 >>>> SwingDisplayWindow(Window).dispatchEventImpl(AWTEvent) line: 2478 >>>> SwingDisplayWindow(Component).dispatchEvent(AWTEvent) line: 4460 >>>> >>>> DefaultKeyboardFocusManager(KeyboardFocusManager).redispatchEvent(Component, >>>> AWTEvent) line: 1850 >>>> DefaultKeyboardFocusManager.typeAheadAssertions(Component, AWTEvent) >>>> line: 910 >>>> DefaultKeyboardFocusManager.dispatchEvent(AWTEvent) line: 409 >>>> SwingDisplayWindow(Component).dispatchEventImpl(AWTEvent) line: 4502 >>>> SwingDisplayWindow(Container).dispatchEventImpl(AWTEvent) line: 2099 >>>> SwingDisplayWindow(Window).dispatchEventImpl(AWTEvent) line: 2478 >>>> SwingDisplayWindow(Component).dispatchEvent(AWTEvent) line: 4460 >>>> EventQueue.dispatchEvent(AWTEvent) line: 599 >>>> >>>> DefaultKeyboardFocusManager$DefaultKeyboardFocusManagerSentEvent(SentEvent).dispatch() >>>> line: 55 >>>> DefaultKeyboardFocusManager$DefaultKeyboardFocusManagerSentEvent.dispatch() >>>> line: 183 >>>> DefaultKeyboardFocusManager.sendMessage(Component, AWTEvent) line: 210 >>>> DefaultKeyboardFocusManager.dispatchEvent(AWTEvent) line: 286 >>>> SwingDisplayWindow(Component).dispatchEventImpl(AWTEvent) line: 4502 >>>> SwingDisplayWindow(Container).dispatchEventImpl(AWTEvent) line: 2099 >>>> SwingDisplayWindow(Window).dispatchEventImpl(AWTEvent) line: 2478 >>>> SwingDisplayWindow(Component).dispatchEvent(AWTEvent) line: 4460 >>>> EventQueue.dispatchEvent(AWTEvent) line: 599 >>>> SequencedEvent.dispatch() line: 101 >>>> EventQueue.dispatchEvent(AWTEvent) line: 597 >>>> EventDispatchThread.pumpOneEventForFilters(int) line: 269 >>>> EventDispatchThread.pumpEventsForFilter(int, Conditional, >>>> EventFilter) line: 184 >>>> EventDispatchThread.pumpEventsForHierarchy(int, Conditional, Component) >>>> line: 174 >>>> EventDispatchThread.pumpEvents(int, Conditional) line: 169 >>>> EventDispatchThread.pumpEvents(Conditional) line: 161 >>>> EventDispatchThread.run() line: 122 >>>> >>>> Thread [SciJava-4b2922f6-Thread-27] (Suspended) >>>> Object.wait(long) line: not available [native method] >>>> EventQueue$1AWTInvocationLock(Object).wait() line: 485 Waiting for AWT >>>> event thread to read invocation request. >>>> EventQueue.invokeAndWait(Runnable) line: 993 >>>> DefaultThreadService.invoke(Runnable) line: 95 >>>> DefaultEventBus.publishNow(Object, String, Object, List, List, >>>> StackTraceElement[]) line: 195 >>>> DefaultEventBus.publishNow(Object) line: 86 >>>> DefaultEventService.publish(E) line: 95 >>>> DefaultStatusService.showStatus(int, int, String) line: 77 >>>> DefaultMinMaxMethod<T>.report() line: 296 >>>> DefaultMinMaxMethod<T>.process() line: 155 >>>> DefaultAutoscaleMethod<T>.getRange(IterableInterval<T>) line: 70 >>>> DefaultAutoscaleService.getDefaultIntervalRange(IterableInterval<RealType<?>>) >>>> line: 97 >>>> >>>> DefaultAutoscaleService.getDefaultRandomAccessRange(RandomAccessibleInterval<RealType<?>>) >>>> line: 105 >>>> DefaultDatasetView.autoscale(int) line: 176 >>>> DefaultDatasetView.initializeView(boolean) line: 499 >>>> DefaultDatasetView.rebuild() line: 383 Takes the DefaultDatasetView >>>> lock. >>>> DefaultImageDisplay.rebuild() line: 140 >>>> DefaultImageDisplay.display(Object) line: 273 >>>> DefaultOverlayService.addOverlays(ImageDisplay, List<Overlay>) line: 148 >>>> TurboRegRegister.run() line: 144 >>>> CommandModule.run() line: 196 >>>> ModuleRunner.run() line: 168 >>>> ModuleRunner.call() line: 129 >>>> ModuleRunner.call() line: 1 >>>> FutureTask$Sync.innerRun() line: 303 >>>> FutureTask<V>.run() line: 138 >>>> ThreadPoolExecutor$Worker.runTask(Runnable) line: 886 >>>> ThreadPoolExecutor$Worker.run() line: 908 >>>> Thread.run() line: 662 >>>> >>>> >>>> _______________________________________________ >>>> ImageJ-devel mailing list >>>> [email protected] >>>> http://imagej.net/mailman/listinfo/imagej-devel >>>> >>>> >>> >> >
_______________________________________________ ImageJ-devel mailing list [email protected] http://imagej.net/mailman/listinfo/imagej-devel
