diff options
author | Anton Leherbauer | 2015-11-27 15:15:57 +0000 |
---|---|---|
committer | Anton Leherbauer | 2015-11-27 15:16:09 +0000 |
commit | dabedd5fad7a418027b532c64a984b96f9efd4b5 (patch) | |
tree | 751e863d18f6f7257411cac97dcf6af95cc206d3 | |
parent | a0ac2a8323dfcc06cea1733d0a2bf23b55b9cdb7 (diff) | |
download | org.eclipse.tcf-dabedd5fad7a418027b532c64a984b96f9efd4b5.tar.gz org.eclipse.tcf-dabedd5fad7a418027b532c64a984b96f9efd4b5.tar.xz org.eclipse.tcf-dabedd5fad7a418027b532c64a984b96f9efd4b5.zip |
Target Explorer: Fix race conditions starting multiple processes in a row
4 files changed, 46 insertions, 33 deletions
diff --git a/target_explorer/plugins/org.eclipse.tcf.te.tcf.core/src/org/eclipse/tcf/te/tcf/core/internal/channelmanager/ChannelManager.java b/target_explorer/plugins/org.eclipse.tcf.te.tcf.core/src/org/eclipse/tcf/te/tcf/core/internal/channelmanager/ChannelManager.java index 93254084d..75ca2e63c 100644 --- a/target_explorer/plugins/org.eclipse.tcf.te.tcf.core/src/org/eclipse/tcf/te/tcf/core/internal/channelmanager/ChannelManager.java +++ b/target_explorer/plugins/org.eclipse.tcf.te.tcf.core/src/org/eclipse/tcf/te/tcf/core/internal/channelmanager/ChannelManager.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2014 Wind River Systems, Inc. and others. All rights reserved. + * Copyright (c) 2014, 2015 Wind River Systems, Inc. and others. All rights reserved. * This program and the accompanying materials are made available under the terms * of the Eclipse Public License v1.0 which accompanies this distribution, and is * available at http://www.eclipse.org/legal/epl-v10.html @@ -780,8 +780,6 @@ public class ChannelManager extends PlatformObject implements IChannelManager { finProxy.removeListener(listener); if (finProxy.isEmpty()) finProxies.remove(finProxy); if (finProxies.isEmpty()) streamProxies.remove(channel); - } else { - finProxy.addListener(listener); } done.doneSubscribeStream(error); } @@ -829,25 +827,27 @@ public class ChannelManager extends PlatformObject implements IChannelManager { proxy.removeListener(listener); // Are there remaining proxied listeners for this stream type? if (proxy.isEmpty()) { + // Remove from proxy list + proxies.remove(proxy); + if (proxies.isEmpty()) streamProxies.remove(channel); // Unregister the stream type IStreams service = channel.getRemoteService(IStreams.class); if (service != null) { - final StreamListenerProxy finProxy = proxy; - final List<StreamListenerProxy> finProxies = proxies; - // Unsubscribe service.unsubscribe(streamType, proxy, new IStreams.DoneUnsubscribe() { @Override public void doneUnsubscribe(IToken token, Exception error) { - finProxies.remove(finProxy); - if (finProxies.isEmpty()) streamProxies.remove(channel); done.doneUnsubscribeStream(error); } }); } else { done.doneUnsubscribeStream(new Exception(Messages.ChannelManager_stream_missing_service_message)); } + } else { + done.doneUnsubscribeStream(null); } + } else { + done.doneUnsubscribeStream(null); } } diff --git a/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessLauncher.java b/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessLauncher.java index 71f0d2b5a..6ce812511 100644 --- a/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessLauncher.java +++ b/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessLauncher.java @@ -95,7 +95,7 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher /* default */ boolean sigTermSent; // The callback instance - private ICallback callback; + ICallback callback; // The streams listener instance private IChannelManager.IStreamsListener streamsListener = null; @@ -112,6 +112,7 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher // The active token. IToken activeToken = null; + private boolean processExited; /** * Message ID for error message in case the process launch failed. @@ -138,6 +139,8 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher */ @Override public void dispose() { + Assert.isTrue(callback == null || callback.isDone(), "Must not dispose during launch"); //$NON-NLS-1$ + // Unlink the process context processContext = null; @@ -300,19 +303,14 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher Assert.isNotNull(properties); // Normalize the callback - if (callback == null) { - this.callback = new Callback() { - /* (non-Javadoc) - * @see org.eclipse.tcf.te.runtime.callback.Callback#internalDone(java.lang.Object, org.eclipse.core.runtime.IStatus) - */ - @Override - public void internalDone(Object caller, IStatus status) { - } - }; - } - else { - this.callback = callback; - } + this.callback = new Callback() { + @Override + public void internalDone(Object caller, IStatus status) { + if (callback != null) + callback.setResult(getResult()); + doneLaunch(callback, status); + } + }; // Remember the process properties this.properties = properties; @@ -372,6 +370,14 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher } } + protected void doneLaunch(ICallback callback, IStatus status) { + if (callback != null) + callback.done(this, status); + // process exited during launch - dispose now + if (processExited) + dispose(); + } + protected void onChannelOpenDone(final IPeer peer) { Assert.isTrue(Protocol.isDispatchThread(), "Illegal Thread Access"); //$NON-NLS-1$ @@ -1017,17 +1023,16 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher * @param result The result object or <code>null</code>. */ protected void invokeCallback(IStatus status, Object result) { - // Dispose the process launcher if we report an error - if (status.getSeverity() == IStatus.ERROR) { - dispose(); - } - // Invoke the callback ICallback callback = getCallback(); if (callback != null) { callback.setResult(result); callback.done(this, status); } + // Dispose the process launcher if we report an error + if (status.getSeverity() == IStatus.ERROR) { + dispose(); + } } /** @@ -1173,4 +1178,11 @@ public class ProcessLauncher extends PlatformObject implements IProcessLauncher } return result.toString(); } + + void processExited() { + processExited = true; + // dispose unless process launch is still in progress + if (callback.isDone()) + dispose(); + } } diff --git a/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessProcessesListener.java b/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessProcessesListener.java index 6251db486..b3160be27 100644 --- a/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessProcessesListener.java +++ b/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessProcessesListener.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2011 Wind River Systems, Inc. and others. All rights reserved. + * Copyright (c) 2011, 2015 Wind River Systems, Inc. and others. All rights reserved. * This program and the accompanying materials are made available under the terms * of the Eclipse Public License v1.0 which accompanies this distribution, and is * available at http://www.eclipse.org/legal/epl-v10.html @@ -14,11 +14,11 @@ import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Status; import org.eclipse.tcf.services.IProcesses; import org.eclipse.tcf.services.IProcesses.ProcessesListener; +import org.eclipse.tcf.te.runtime.events.EventManager; +import org.eclipse.tcf.te.runtime.interfaces.callback.ICallback; import org.eclipse.tcf.te.tcf.processes.core.activator.CoreBundleActivator; import org.eclipse.tcf.te.tcf.processes.core.interfaces.launcher.IProcessContextAwareListener; import org.eclipse.tcf.te.tcf.processes.core.interfaces.tracing.ITraceIds; -import org.eclipse.tcf.te.runtime.events.EventManager; -import org.eclipse.tcf.te.runtime.interfaces.callback.ICallback; /** * Remote process processes listener implementation. @@ -111,8 +111,8 @@ public class ProcessProcessesListener implements ProcessesListener, IProcessCont // Send a notification ProcessStateChangeEvent event = createRemoteProcessStateChangeEvent(context, exitCode); EventManager.getInstance().fireEvent(event); - // Dispose the parent remote process launcher - getParent().dispose(); + // Notify the parent remote process launcher + getParent().processExited(); } } diff --git a/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessStreamsListener.java b/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessStreamsListener.java index bf2d8631e..717e56693 100644 --- a/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessStreamsListener.java +++ b/target_explorer/plugins/org.eclipse.tcf.te.tcf.processes.core/src/org/eclipse/tcf/te/tcf/processes/core/launcher/ProcessStreamsListener.java @@ -435,7 +435,8 @@ public class ProcessStreamsListener implements IChannelManager.IStreamsListener, } // Store the callback instance - this.callback = callback; + if (callback != null) + this.callback = callback; } /** |