| /******************************************************************************* |
| * Copyright (c) 2011 IBM Corporation 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 |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| *******************************************************************************/ |
| package org.eclipse.stem.ui.headless; |
| |
| import java.io.OutputStream; |
| import java.io.PrintStream; |
| |
| import org.eclipse.core.runtime.Platform; |
| import org.eclipse.equinox.app.IApplication; |
| import org.eclipse.stem.jobs.DisplaySafeExecutor; |
| import org.eclipse.stem.ui.launcher.Launcher; |
| import org.osgi.framework.Bundle; |
| |
| /** |
| * Launcher that starts STEM in a non-GUI "headless" mode. The purpose |
| * of this class is to enable command line execution of specific |
| * STEM operations, such as running individual simulations and experiments. |
| * |
| */ |
| public class HeadlessLauncher extends Launcher |
| { |
| private static final String DISTRIBUTED_CONTROLLER_PLUGIN_NAME = "org.eclipse.stem.graphsynchronizer"; |
| |
| /** |
| * STEM Launcher for headless mode. |
| * @param ctx Eclipse Application Context |
| * @param args Command line arguments |
| */ |
| public HeadlessLauncher() |
| { |
| super(); |
| } |
| |
| /** |
| * Checks for the presence of the -distributed command line option |
| * and enables distributed STEM by issue a transient start to the |
| * implementing OSGi bundle. |
| */ |
| protected void checkDistributed() |
| { |
| if (args.containsKey("distributed")) { |
| try { |
| System.out.println("Enabling STEM distributed mode."); |
| Bundle distBundle = Platform.getBundle(DISTRIBUTED_CONTROLLER_PLUGIN_NAME); |
| if (distBundle != null) { |
| distBundle.start(Bundle.START_TRANSIENT); |
| } else { |
| System.err.println("Distributed STEM plugin not found. Distributed mode not enabled."); |
| } |
| } catch (Exception e) { |
| System.err.println("Error launching distributed STEM plugin. Will continue in standalone."); |
| e.printStackTrace(System.err); |
| } |
| } |
| } |
| |
| /** |
| * Sets the correct System streams based on command line options |
| */ |
| protected void setStreams() |
| { |
| if (args.containsKey("quiet")) { |
| System.setOut(new PrintStream(new NullOutputStream())); |
| } |
| } |
| |
| /* (non-Javadoc) |
| * @see org.eclipse.stem.core.launcher.Launcher#launch() |
| */ |
| public Object launch() |
| { |
| // Drop the splash screen |
| context.applicationRunning(); |
| |
| // Tell the display executor to use non-UI execution controls |
| DisplaySafeExecutor.forceHeadless(); |
| |
| setStreams(); |
| |
| try { |
| // Check for and enable distributed mode if requested |
| checkDistributed(); |
| |
| // Check if we should enable the simulation logger |
| boolean log = args.containsKey("log"); |
| String logDir = null; |
| if (log && args.get("log").size() > 0) { |
| logDir = args.get("log").get(0); |
| } |
| |
| // Collect scenarios to simulate and run |
| HeadlessSimulationRunner runner = new HeadlessSimulationRunner(log, logDir); |
| runner.run(args); |
| |
| return IApplication.EXIT_OK; |
| } finally { |
| //display.dispose(); |
| } |
| |
| |
| } |
| |
| /** |
| * SWT Display synchronizer to fix issues with using Display.syncExec |
| * and Display.asyncExec when no UI is present. Highly non-kosher. |
| * |
| */ |
| // private class HeadlessDisplaySynchronizer extends Synchronizer |
| // { |
| // public HeadlessDisplaySynchronizer(Display d) |
| // { |
| // super(d); |
| // } |
| // |
| // /* (non-Javadoc) |
| // * @see org.eclipse.swt.widgets.Synchronizer#asyncExec(java.lang.Runnable) |
| // */ |
| // protected void asyncExec(final Runnable runnable) |
| // { |
| // // For asynchronous execution, schedule and run |
| // // an asynchronous job to execute the runnable instance. |
| // if (runnable != null) { |
| // new Job(runnable.toString()) { |
| // protected IStatus run(IProgressMonitor monitor) { |
| // runnable.run(); |
| // return Status.OK_STATUS; |
| // } |
| // }.schedule(); |
| // } |
| // } |
| // |
| // /* (non-Javadoc) |
| // * @see org.eclipse.swt.widgets.Synchronizer#syncExec(java.lang.Runnable) |
| // */ |
| // protected void syncExec(final Runnable runnable) |
| // { |
| // // For synchronous execution, just call the |
| // // runnable instance directly. Should block |
| // // on execution to complete. |
| // if (runnable != null) { |
| // runnable.run(); |
| // } |
| // } |
| // |
| // } |
| |
| /** |
| * Null output stream for ignoring all output |
| */ |
| private class NullOutputStream extends OutputStream |
| { |
| NullOutputStream() {} |
| public void close() {} |
| public void flush() {} |
| public void write( byte[] b, int off, int len) {} |
| public void write(byte[] b) {} |
| public void write(int b) {} |
| } |
| } |