[Esbox-commits] r2262 - in trunk: org.maemo.esbox.maemosdk.core/conf org.maemo.esbox.maemosdk.core/src/org/maemo/esbox/maemosdk/core org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/launcher org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard org.maemo.esbox.scratchbox.sb2/src/org/maemo/esbox/internal/scratchbox/sb2/ui/wizard org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ui/actions org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/ui/wizards

eswartz at garage.maemo.org eswartz at garage.maemo.org
Sun Oct 4 19:44:03 EEST 2009


Author: eswartz
Date: 2009-10-04 19:44:00 +0300 (Sun, 04 Oct 2009)
New Revision: 2262

Added:
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/MachineShareContentProvider.java
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SelectMachineShareDialog.java
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTreeViewer.java
Removed:
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTableViewer.java
Modified:
   trunk/org.maemo.esbox.maemosdk.core/conf/maemo_prefs.xml
   trunk/org.maemo.esbox.maemosdk.core/src/org/maemo/esbox/maemosdk/core/MaemoPreferenceConstants.java
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BaseMachinePreferencePage.java
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BuildMachinePreferencePage.java
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFoldersPreferencePage.java
   trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/ValidateMachineRunner.java
   trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/launcher/Scratchbox1ProcessLauncher.java
   trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1SDKInstallerSelectionWizardPage.java
   trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1TargetInstallerSelectionWizardPage.java
   trunk/org.maemo.esbox.scratchbox.sb2/src/org/maemo/esbox/internal/scratchbox/sb2/ui/wizard/TargetWizardRootstrapSb2Page.java
   trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuMachineController.java
   trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuSettingsPreferencePage.java
   trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxMachineController.java
   trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxSettingsPreferencePage.java
   trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareMachineController.java
   trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareSettingsPreferencePage.java
   trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareUtils.java
   trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/ui/wizards/MaemoSDKVMSelectionWizardPage.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualBuildMachine.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineConfiguration.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineController.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/BaseVirtualMachinePreferencePage.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/CommonVirtualMachineSettingsPreferencePage.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ESboxHostBuildMachineFactory.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/LinuxX86On64BuildMachineWrapper.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ManualVirtualMachineController.java
   trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ui/actions/ValidateVirtualMachineCommand.java
Log:
Merge revs 2239:2261 from work_Ed branch

Modified: trunk/org.maemo.esbox.maemosdk.core/conf/maemo_prefs.xml
===================================================================
--- trunk/org.maemo.esbox.maemosdk.core/conf/maemo_prefs.xml	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.core/conf/maemo_prefs.xml	2009-10-04 16:44:00 UTC (rev 2262)
@@ -23,4 +23,7 @@
 	<entry key="MAEMO_START_ACTION">start</entry>
 	<entry key="MAEMO_RESTART_ACTION">restart</entry>
 	<entry key="MAEMO_STOP_ACTION">stop</entry>
+	
+	<entry key="VALIDATE_SHARED_FOLDERS">true</entry>
+	
 </properties>

Modified: trunk/org.maemo.esbox.maemosdk.core/src/org/maemo/esbox/maemosdk/core/MaemoPreferenceConstants.java
===================================================================
--- trunk/org.maemo.esbox.maemosdk.core/src/org/maemo/esbox/maemosdk/core/MaemoPreferenceConstants.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.core/src/org/maemo/esbox/maemosdk/core/MaemoPreferenceConstants.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -40,5 +40,7 @@
 	public static final String X_DISPLAY = "X_DISPLAY";
 	public static final String X_PATH = "X_PATH";
 	
+	public static final String VALIDATE_SHARED_FOLDERS = "VALIDATE_SHARED_FOLDERS";
+	
 	static final Class<?> privateKeysClass = MaemoPreferenceConstantsPrivate.class;
 }

Modified: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BaseMachinePreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BaseMachinePreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BaseMachinePreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -33,4 +33,11 @@
 	 */
 	public abstract IMachine createMachine();
 
+	/**
+	 * Refresh contents after machine was scanned. 
+	 */
+	public void validationFinished(IMachine machine) {
+		
+	}
+
 }
\ No newline at end of file

Modified: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BuildMachinePreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BuildMachinePreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/BuildMachinePreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -22,7 +22,10 @@
 import java.util.Map;
 
 import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.Status;
 import org.eclipse.core.runtime.SubProgressMonitor;
+import org.eclipse.core.runtime.jobs.Job;
 import org.eclipse.jface.dialogs.ProgressMonitorDialog;
 import org.eclipse.jface.operation.IRunnableWithProgress;
 import org.eclipse.jface.preference.PreferencePage;
@@ -203,7 +206,7 @@
 		
 		Label label = new Label(comboAndLabel, SWT.NONE);
 		label.setLayoutData(new GridData(SWT.LEFT, SWT.CENTER, false, false));
-		label.setText("Build machine:");
+		label.setText("&Build machine:");
 		
 		CCombo machineCombo = new CCombo(comboAndLabel, SWT.READ_ONLY | SWT.BORDER | SWT.SHADOW_OUT);
 		machineCombo.setBackground(selectorComposite.getDisplay().getSystemColor(SWT.COLOR_LIST_BACKGROUND));
@@ -395,12 +398,21 @@
 			// now allow the refresh
 			SDKManagerInternal.getInstance().unlock();
 		}
+		
+		Job job = new Job("Applying new machine") {
+
+			@Override
+			protected IStatus run(IProgressMonitor monitor) {
+				if (selectedMachine != null && !MachineManager.getInstance().isActive(selectedMachine)) {
+					//MachineManager.getInstance().scheduleAcquireMachine(selectedMachine);
+					// need to properly time the SDK refresh to use the new machine, so do this first
+					SDKManagerInternal.getInstance().refresh(true);
+				}
+				return Status.OK_STATUS;
+			}
 			
-		if (selectedMachine != null && !MachineManager.getInstance().isActive(selectedMachine)) {
-			//MachineManager.getInstance().scheduleAcquireMachine(selectedMachine);
-			// need to properly time the SDK refresh to use the new machine, so do this first
-			SDKManagerInternal.getInstance().refresh(true);
-		}
+		};
+		job.schedule();
 	}
 
 	/**
@@ -501,6 +513,8 @@
 						}
 						
 					});
+				} catch (InvocationTargetException e) {
+					UIActivator.getErrorLogger().logError("Unexpected error shutting down machines", e.getCause());
 				} catch (Exception e) {
 					UIActivator.getErrorLogger().logError("Unexpected error shutting down machines", e);
 				}
@@ -597,9 +611,7 @@
 		
 		dialog.open();
 		
-		IMachine machineToValidate = selectedMachinePage instanceof BaseMachinePreferencePage ?
-				((BaseMachinePreferencePage) selectedMachinePage).createMachine() :
-					selectedMachine;
+		IMachine machineToValidate = getCurrentMachine();
 
 		shutDownMachinesBeforeSwitchingTo(machineToValidate);
 
@@ -610,11 +622,26 @@
 			dialog.run(true, true, runner);
 		} catch (InterruptedException e) {
 			// ignore
+		} catch (InvocationTargetException e) {
+			UIActivator.getErrorLogger().logAndShowError("Unexpected exception running tests", e.getCause());
 		} catch (Exception e) {
 			UIActivator.getErrorLogger().logAndShowError("Unexpected exception running tests", e);
 		}
 		
 		lastValidatedMachine = machineToValidate;
+		if (selectedMachinePage instanceof BaseMachinePreferencePage)
+			((BaseMachinePreferencePage) selectedMachinePage).validationFinished(lastValidatedMachine);
 	}
+
+	/**
+	 * Get the machine that is being configured.
+	 * @return IMachine
+	 */
+	public IMachine getCurrentMachine() {
+		IMachine machineToValidate = selectedMachinePage instanceof BaseMachinePreferencePage ?
+				((BaseMachinePreferencePage) selectedMachinePage).createMachine() :
+					selectedMachine;
+		return machineToValidate;
+	}
 	
 }

Copied: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/MachineShareContentProvider.java (from rev 2261, branches/work_Ed/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/MachineShareContentProvider.java)
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/MachineShareContentProvider.java	                        (rev 0)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/MachineShareContentProvider.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -0,0 +1,138 @@
+/*******************************************************************************
+ * Copyright (c) 2009 Nokia Corporation
+ * 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:
+ *    Ed Swartz (Nokia) - initial API and implementation
+ *******************************************************************************/
+
+package org.maemo.esbox.internal.api.maemosdk.ui.preferences;
+
+import java.util.Arrays;
+
+import org.eclipse.core.runtime.IProgressMonitor;
+import org.eclipse.core.runtime.NullProgressMonitor;
+import org.eclipse.core.runtime.SubProgressMonitor;
+import org.eclipse.swt.graphics.Image;
+import org.maemo.mica.common.core.MicaException;
+import org.maemo.mica.common.core.machine.IMachine;
+import org.maemo.mica.common.core.machine.MachineUtils;
+import org.maemo.mica.internal.api.common.core.filesystem.MachineShare;
+import org.maemo.mica.internal.api.common.core.filesystem.SambaUtils;
+import org.maemo.mica.internal.api.common.ui.LazyLoadingThreadTableContentProvider;
+
+/**
+ * Fetch the exposed shares from a machine. 
+ * @author eswartz
+ *
+ */
+public class MachineShareContentProvider extends
+		LazyLoadingThreadTableContentProvider {
+
+	final static public int COLUMN_SHARENAME = 0;
+	final static public int COLUMN_PATH = 1;
+	final static public int COLUMN_COMMENT = 2;
+
+
+	protected class MachineShareFetchThread extends Thread {
+		protected Object newInput;
+
+		public MachineShareFetchThread(Object newInput) {
+			this.newInput = newInput;
+		}
+
+		protected MachineShare[] doScanFromMachine(final IMachine machine) throws MicaException {
+			IProgressMonitor monitor = new NullProgressMonitor();
+			MachineUtils.acquireMachine(machine, new SubProgressMonitor(monitor, 7));
+			if (monitor.isCanceled() || isInterrupted())
+				return null;
+			
+			return SambaUtils.getMachineShares(machine, new SubProgressMonitor(monitor, 3));
+		}
+		
+		public void run() {
+			IMachine machine = (IMachine) newInput;
+			try {
+				MachineShare[] shares = doScanFromMachine(machine);
+				synchronized (contents) {
+					contents.clear();
+					if (shares != null) {
+						contents.addAll(Arrays.asList(shares));
+					} else {
+						contents.add("Failed to find any shared folders on " + machine.getName());
+					}
+				}
+			} catch (MicaException e) {
+				synchronized (contents) {
+					contents.clear();
+					contents.add("Failed to fetch shared folders from " + machine.getName() + ": " + e.getMessage());
+				}
+			}
+			fetchThread = null;
+			doFireContentChanged();
+		}
+
+	}
+
+	/* (non-Javadoc)
+	 * @see org.maemo.mica.internal.api.common.ui.LazyLoadingThreadTableContentProvider#createContentFetchThread(java.lang.Object)
+	 */
+	@Override
+	protected Thread createContentFetchThread(Object newInput) {
+		return new MachineShareFetchThread(newInput);
+	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.viewers.ITreeContentProvider#getChildren(java.lang.Object)
+	 */
+	public Object[] getChildren(Object parentElement) {
+		return null;
+	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.viewers.ITreeContentProvider#getParent(java.lang.Object)
+	 */
+	public Object getParent(Object element) {
+		return null;
+	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.viewers.ITreeContentProvider#hasChildren(java.lang.Object)
+	 */
+	public boolean hasChildren(Object element) {
+		return false;
+	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.viewers.ITableLabelProvider#getColumnImage(java.lang.Object, int)
+	 */
+	public Image getColumnImage(Object element, int columnIndex) {
+		return null;
+	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.viewers.ITableLabelProvider#getColumnText(java.lang.Object, int)
+	 */
+	public String getColumnText(Object element, int columnIndex) {
+		if (element == LOADING_LABEL)
+			return super.getColumnText(element, columnIndex);
+
+		if (!(element instanceof MachineShare))
+			return null;
+		
+		MachineShare share = (MachineShare) element;
+		switch (columnIndex) {
+		case COLUMN_SHARENAME:
+			return share.getShareName();
+		case COLUMN_PATH:
+			return share.getPath().toPortableString();
+		case COLUMN_COMMENT:
+			return share.getComment();
+		}
+		return null;
+	}
+
+}

Copied: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SelectMachineShareDialog.java (from rev 2261, branches/work_Ed/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SelectMachineShareDialog.java)
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SelectMachineShareDialog.java	                        (rev 0)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SelectMachineShareDialog.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -0,0 +1,141 @@
+package org.maemo.esbox.internal.api.maemosdk.ui.preferences;
+
+import org.eclipse.jface.dialogs.Dialog;
+import org.eclipse.jface.dialogs.IDialogConstants;
+import org.eclipse.jface.layout.GridDataFactory;
+import org.eclipse.jface.viewers.DoubleClickEvent;
+import org.eclipse.jface.viewers.IDoubleClickListener;
+import org.eclipse.jface.viewers.ISelectionChangedListener;
+import org.eclipse.jface.viewers.IStructuredSelection;
+import org.eclipse.jface.viewers.SelectionChangedEvent;
+import org.eclipse.jface.viewers.TableViewer;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.graphics.Point;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.Shell;
+import org.eclipse.swt.widgets.Table;
+import org.eclipse.swt.widgets.TableColumn;
+import org.maemo.mica.common.core.machine.IMachine;
+import org.maemo.mica.internal.api.common.core.filesystem.MachineShare;
+
+/**
+ * This dialog lets the user select a share from a machine and configure the mount
+ * location as well.
+ * @author eswartz
+ *
+ */
+public final class SelectMachineShareDialog extends Dialog {
+
+	private MachineShare selectedShare;
+	private TableViewer viewer;
+	private final IMachine machine;
+
+	public SelectMachineShareDialog(Shell shell, IMachine machine) {
+		super(shell);
+		this.machine = machine;
+		setShellStyle(getShellStyle() | SWT.RESIZE);
+	}
+	
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.dialogs.Dialog#getInitialSize()
+	 */
+	@Override
+	protected Point getInitialSize() {
+		return new Point(400, 300);
+	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.window.Window#configureShell(org.eclipse.swt.widgets.Shell)
+	 */
+	@Override
+	protected void configureShell(Shell newShell) {
+		super.configureShell(newShell);
+		newShell.setText("Configure a share");
+	}
+	@Override
+	protected Control createDialogArea(Composite parent) {
+		Composite composite = (Composite) super.createDialogArea(parent);
+		
+		Label label;
+
+		//label = new Label(composite, SWT.WRAP);
+		//GridDataFactory.fillDefaults().applyTo(label);
+		//label.setText(labelText);
+		//////
+		
+		label = new Label(composite, SWT.WRAP);
+		GridDataFactory.fillDefaults().applyTo(label);
+		label.setText("Select one of the shares:");
+		
+		viewer = new TableViewer(composite, SWT.READ_ONLY | SWT.FULL_SELECTION | SWT.BORDER);
+		Table table = viewer.getTable();
+		GridDataFactory.fillDefaults().grab(true, true).applyTo(table);
+		
+		table.setHeaderVisible(true);
+		table.setLinesVisible(true);
+		
+		TableColumn column;
+		
+		column = new TableColumn(table, SWT.LEFT);
+		column.setText("Share name");
+		column = new TableColumn(table, SWT.LEFT);
+		column.setText("Path");
+		column = new TableColumn(table, SWT.LEFT);
+		column.setText("Comment");
+		
+		MachineShareContentProvider provider = new MachineShareContentProvider();
+		viewer.setContentProvider(provider);
+		viewer.setLabelProvider(provider);
+		provider.attachContentChangedListener(viewer);
+		
+		viewer.addDoubleClickListener(new IDoubleClickListener() {
+
+			public void doubleClick(DoubleClickEvent event) {
+				Object sel = ((IStructuredSelection) event.getSelection()).getFirstElement();
+				if (sel instanceof MachineShare) {
+					selectedShare = (MachineShare) sel;
+					close();
+				}
+			}
+		});
+		
+		viewer.addSelectionChangedListener(new ISelectionChangedListener() {
+
+			public void selectionChanged(SelectionChangedEvent event) {
+				Object sel = ((IStructuredSelection) event.getSelection()).getFirstElement();
+				if (sel instanceof MachineShare) {
+					selectedShare = (MachineShare) sel;
+					validate();
+				}
+			}
+			
+		});
+		viewer.setInput(machine);
+		
+		table.pack();
+		for (TableColumn columnx : table.getColumns())
+			columnx.pack();
+		
+		return composite;
+	}
+	
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.dialogs.Dialog#createButtonsForButtonBar(org.eclipse.swt.widgets.Composite)
+	 */
+	@Override
+	protected void createButtonsForButtonBar(Composite parent) {
+		super.createButtonsForButtonBar(parent);
+		validate();
+	}
+	protected void validate() { 
+		Button button = getButton(IDialogConstants.OK_ID);
+		button.setEnabled(selectedShare != null);
+	}
+	
+	public MachineShare getShare() {
+		return selectedShare;
+	}
+}
\ No newline at end of file

Deleted: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTableViewer.java
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTableViewer.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTableViewer.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -1,556 +0,0 @@
-/*******************************************************************************
- * Copyright (c) 2008-2009 Nokia Corporation
- * 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:
- *    Ed Swartz (Nokia) - initial API and implementation
- *******************************************************************************/
-
-package org.maemo.esbox.internal.api.maemosdk.ui.preferences;
-
-import java.util.Collection;
-
-import org.eclipse.core.runtime.Path;
-import org.eclipse.jface.viewers.BaseLabelProvider;
-import org.eclipse.jface.viewers.CellEditor;
-import org.eclipse.jface.viewers.CheckboxCellEditor;
-import org.eclipse.jface.viewers.ComboBoxCellEditor;
-import org.eclipse.jface.viewers.EditingSupport;
-import org.eclipse.jface.viewers.ITableLabelProvider;
-import org.eclipse.jface.viewers.ITreeContentProvider;
-import org.eclipse.jface.viewers.TextCellEditor;
-import org.eclipse.jface.viewers.TreeViewer;
-import org.eclipse.jface.viewers.TreeViewerColumn;
-import org.eclipse.jface.viewers.Viewer;
-import org.eclipse.swt.SWT;
-import org.eclipse.swt.events.ControlAdapter;
-import org.eclipse.swt.events.ControlEvent;
-import org.eclipse.swt.graphics.Image;
-import org.eclipse.swt.widgets.Composite;
-import org.eclipse.swt.widgets.Control;
-import org.eclipse.swt.widgets.DirectoryDialog;
-import org.eclipse.swt.widgets.Tree;
-import org.eclipse.swt.widgets.TreeColumn;
-import org.maemo.mica.common.core.filesystem.EShareType;
-import org.maemo.mica.common.core.filesystem.ISharedFolder;
-import org.maemo.mica.common.ui.TextAndDialogCellEditor;
-import org.maemo.mica.common.ui.dialogs.DirectoryDialogHelper;
-import org.maemo.mica.internal.api.common.ui.ViewerTooltipSupport;
-
-/**
- * A table viewer for shared folder mappings.  The content should be 
- * ISharedFolder entries.
- * @author eswartz
- *
- */
-public class SharedFolderTableViewer extends TreeViewer {
-	/**
-	 * 
-	 */
-	
-	private Collection<ISharedFolder> mappings;
-	private TreeViewerColumn contentViewerColumn;
-	
-	static abstract class FieldItem {
-		String label;
-		ISharedFolder folder;
-		String tooltip;
-		
-		/**
-		 * @param label
-		 * @param parent
-		 */
-		public FieldItem(String label, String tooltip, ISharedFolder parent) {
-			super();
-			this.label = label;
-			this.tooltip = tooltip;
-			this.folder = parent;
-		}
-		
-		protected CellEditor getCellEditor(ISharedFolder folder, Tree tree) {
-			return new TextCellEditor(tree);
-		}
-		
-		abstract protected void setField(Object value);
-		abstract protected Object getField();
-
-		public String getLabel() {
-			return getField().toString();
-		}
-
-		/**
-		 * @return
-		 */
-		public ISharedFolder getFolder() {
-			return folder;
-		}
-	}
-
-	static class DirectoryBrowserCellEditor extends TextAndDialogCellEditor {
-		
-		public DirectoryBrowserCellEditor(Tree tree) {
-			super(tree);
-		}
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.DialogCellEditor#openDialogBox(org.eclipse.swt.widgets.Control)
-		 */
-		@Override
-		protected Object openDialogBox(Control cellEditorWindow) {
-			DirectoryDialog dialog = new DirectoryDialog(cellEditorWindow.getShell());
-			Object current = getValue();
-			DirectoryDialogHelper.setFilterPathToExistingDirectory(dialog, 
-					current instanceof String 
-					? new Path((String)current).toOSString() : Path.ROOT.toOSString());
-			return dialog.open();
-		}
-	}
-	
-	static abstract class PathFieldItem extends FieldItem {
-		public PathFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		protected abstract boolean isHostPath(ISharedFolder folder);
-		/* (non-Javadoc)
-		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.FieldItem#getCellEditor(org.eclipse.swt.widgets.Tree)
-		 */
-		@Override
-		protected CellEditor getCellEditor(final ISharedFolder folder, Tree tree) {
-			final CellEditor cellEditor;
-			if (isHostPath(folder)) {
-				cellEditor = new DirectoryBrowserCellEditor(tree);
-			} else {
-				cellEditor = new TextCellEditor(tree);
-			}
-			
-			/*  none of this stuff works... :p  The validator is called only
-			 * less than half the time, and the tooltip doesn't show any text, ever 
-			cellEditor.setValidator(new ICellEditorValidator() {
-
-				public String isValid(Object value) {
-					IPath path = new Path(value.toString());
-					if (!path.isAbsolute())
-						return "Path must be absolute";
-					if (isHostPath(folder) && !path.toFile().exists())
-						return "Folder does not exist on host";
-					return null;
-				}
-				
-			});
-			cellEditor.addListener(new ICellEditorListener() {
-				ToolTip errorTip = null;
-				
-				public void applyEditorValue() {
-					if (errorTip != null)
-						errorTip.dispose();
-					errorTip = null;
-				}
-
-				public void cancelEditor() {
-					if (errorTip != null)
-						errorTip.dispose();
-					errorTip = null;
-				}
-
-				public void editorValueChanged(boolean oldValidState,
-						final boolean newValidState) {
-					Display.getDefault().asyncExec(new Runnable() {
-
-						public void run() {
-							if (cellEditor.getControl().isDisposed())
-								return;
-							// the "newValidState" seems to be bogus; we need to look at the message
-							if (errorTip == null && cellEditor.getErrorMessage() != null) {
-								errorTip = new ToolTip(cellEditor.getControl().getShell(), SWT.ICON_ERROR);
-								errorTip.setLocation(cellEditor.getControl().toDisplay(cellEditor.getControl().getLocation()));
-								errorTip.setVisible(true);
-							}
-							if (cellEditor.getErrorMessage() != null)
-								errorTip.setText(cellEditor.getErrorMessage());
-							else {
-								if (errorTip != null)
-									errorTip.dispose();
-								errorTip = null;
-							}
-						}
-						
-					});
-				}
-				
-			});
-			*/
-			return cellEditor;
-		}
-	}
-	
-	static class SharePathFieldItem extends PathFieldItem {
-		public SharePathFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		/* (non-Javadoc)
-		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.PathFieldItem#isHostPath()
-		 */
-		@Override
-		protected boolean isHostPath(ISharedFolder folder) {
-			return folder.isHostProvidedShare();
-		}
-		@Override
-		protected Object getField() {
-			return isHostPath(folder) ? folder.getSharePath().toOSString() 
-					: folder.getSharePath().toPortableString();
-		}
-		@Override
-		protected void setField(Object value) {
-			folder.setSharePath(new Path((String)value).makeAbsolute());
-		}
-	}
-	
-	static class MountPathFieldItem extends PathFieldItem {
-		public MountPathFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		/* (non-Javadoc)
-		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.PathFieldItem#isHostPath(org.maemo.mica.common.core.machine.ISharedFolder)
-		 */
-		@Override
-		protected boolean isHostPath(ISharedFolder folder) {
-			return !folder.isHostProvidedShare();
-		}
-		@Override
-		protected Object getField() {
-			return isHostPath(folder) ? folder.getMountPath().toOSString() 
-					: folder.getMountPath().toPortableString();
-		}
-		@Override
-		protected void setField(Object value) {
-			folder.setMountPath(new Path((String) value).makeAbsolute());
-		}
-	}
-	
-	static class ShareNameFieldItem extends FieldItem {
-		public ShareNameFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		@Override
-		protected Object getField() {
-			return folder.getShareName();
-		}
-		@Override
-		protected void setField(Object value) {
-			folder.setShareName((String) value);
-		}
-	}
-
-	/**
-	 * A cell editor for "yes/no" values.  Use this instead of {@link CheckboxCellEditor}
-	 * since that has the unwanted behavior that merely clicking will change the value.
-	 * This widget provides feedback and allows the user to know what's happening.
-	 * @author eswartz
-	 *
-	 */
-	static class YesNoCellEditor extends ComboBoxCellEditor {
-
-		public YesNoCellEditor(Composite parent) {
-			super(parent, new String[] { "no", "yes" });
-		}
-
-		@Override
-		protected Object doGetValue() {
-			Integer value = (Integer) super.doGetValue();
-			return Boolean.valueOf(value.intValue() != 0);
-		}
-
-		@Override
-		protected void doSetValue(Object value) {
-			Boolean bool = (Boolean) value;
-			super.doSetValue(Integer.valueOf(bool ? 1 : 0));
-		}
-		
-	}
-	static abstract class BooleanFieldItem extends FieldItem {
-		public BooleanFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		@Override
-		protected CellEditor getCellEditor(ISharedFolder folder, Tree tree) {
-			return new YesNoCellEditor(tree);
-		}
-		@Override
-		public String getLabel() {
-			return ((Boolean) getField()) ? "yes" : "no";
-		}
-	}
-	
-	static class AutoMountFieldItem extends BooleanFieldItem {
-		public AutoMountFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		@Override
-		protected Object getField() {
-			return !folder.isManual();
-		}
-		@Override
-		protected void setField(Object value) {
-			folder.setManual(!(Boolean)value);
-		}
-	}
-
-	static class HostProvidedFieldItem extends BooleanFieldItem {
-		public HostProvidedFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		@Override
-		protected Object getField() {
-			return folder.isHostProvidedShare();
-		}
-		@Override
-		protected void setField(Object value) {
-			folder.setHostProvidedShare((Boolean)value);
-		}
-	}
-	
-	static class StaticFieldItem extends FieldItem {
-		public StaticFieldItem(String label, String tooltip, ISharedFolder parent) {
-			super(label, tooltip, parent);
-		}
-		/* (non-Javadoc)
-		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.FieldItem#getCellEditor(org.eclipse.swt.widgets.Tree)
-		 */
-		@Override
-		protected CellEditor getCellEditor(ISharedFolder folder, Tree tree) {
-			return null;
-		}
-		@Override
-		protected Object getField() {
-			return folder.getShareType().toString();
-		}
-		@Override
-		protected void setField(Object value) {
-			folder.setShareType(EShareType.valueOf((String) value));
-		}
-	}
-	
-	/**
-	 * This content provider simply provides a "tree" where each root
-	 * node is an ISharedFolder whose label provider is a summary of its
-	 * structure and whose children are Strings providing details about
-	 * the entry.  The node as a whole is edited separately in a dialog.
-	 * @author eswartz
-	 *
-	 */
-	static class SharedFolderContentProvider implements ITreeContentProvider {
-
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.IStructuredContentProvider#getElements(java.lang.Object)
-		 */
-		public Object[] getElements(Object inputElement) {
-			return ((Collection) inputElement).toArray();
-		}
-		
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.ITreeContentProvider#getChildren(java.lang.Object)
-		 */
-		public Object[] getChildren(Object parentElement) {
-			if (parentElement instanceof ISharedFolder) {
-				ISharedFolder folder = (ISharedFolder) parentElement;
-				return new Object[] {
-					new SharePathFieldItem(
-							"Share path",
-							"The full path of the shared folder.",
-							folder),
-					new HostProvidedFieldItem(
-							"Local share?",
-							"Tells whether this machine exports the share (yes), or the virtual machine exports it (no).\n\nThe other machine will mount the share.",
-							folder),
-					new MountPathFieldItem(
-							"Mount path", 
-							"The full path where the share will be mounted.",
-							folder),
-					new ShareNameFieldItem(
-							"Share name",
-							"The name of the share (for SMB).",
-							folder),
-					new StaticFieldItem(
-							"Share type",
-							"The protocol by which the share is provided.",
-							folder),
-					new AutoMountFieldItem(
-							"Auto connect?",
-							"If yes, attempt to mount this share when the virtual machine is started.\n\nOtherwise, make use of this share mapping for path conversion purposes only.",
-							folder),
-				};
-			}
-			return null;
-		}
-		
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.ITreeContentProvider#getParent(java.lang.Object)
-		 */
-		public Object getParent(Object element) {
-			if (element instanceof FieldItem)
-				return ((FieldItem) element).folder;
-			else
-				return null;
-		}
-		
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.ITreeContentProvider#hasChildren(java.lang.Object)
-		 */
-		public boolean hasChildren(Object element) {
-			return element instanceof Collection || element instanceof ISharedFolder;
-		}
-
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.IContentProvider#dispose()
-		 */
-		public void dispose() {
-		}
-
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.IContentProvider#inputChanged(org.eclipse.jface.viewers.Viewer, java.lang.Object, java.lang.Object)
-		 */
-		public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
-		}
-		
-	}
-	
-	static class SharedFolderLabelProvider extends BaseLabelProvider implements 
-		ITableLabelProvider {
-		
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.ITableLabelProvider#getColumnImage(java.lang.Object, int)
-		 */
-		public Image getColumnImage(Object element, int columnIndex) {
-			return null;
-		}
-
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.ITableLabelProvider#getColumnText(java.lang.Object, int)
-		 */
-		public String getColumnText(Object element, int columnIndex) {
-			if (element instanceof ISharedFolder) {
-				if (columnIndex == 0) {
-					ISharedFolder folder = (ISharedFolder) element;
-					return (folder.isHostProvidedShare()
-							? folder.getLocalPath().toOSString() 
-									: folder.getRemotePath().toPortableString());
-				}
-			}
-			if (element instanceof FieldItem) {
-				FieldItem item = (FieldItem) element;
-				if (columnIndex == 0)
-					return item.label;
-				else
-					return item.getLabel();
-			}
-			return null;
-		}
-		
-		/* (non-Javadoc)
-		 * @see org.eclipse.jface.viewers.ITableFontProvider#getFont(java.lang.Object, int)
-		 */
-		/*
-		public Font getFont(Object element, int columnIndex) {
-			if (element instanceof DescriptionItem && columnIndex == 0) {
-				return JFaceResources.getFontRegistry().getBold(
-						JFaceResources.DIALOG_FONT);
-			}
-			return JFaceResources.getFontRegistry().get(
-					JFaceResources.DIALOG_FONT);
-		}*/
-	}
-	
-	public SharedFolderTableViewer(Composite parent, int style) {
-		super(parent, style | SWT.FULL_SELECTION | SWT.SINGLE);
-		
-		final Tree tree = getTree();
-		
-		tree.setLinesVisible(true);
-		tree.setHeaderVisible(true);
-		
-		final TreeColumn fieldColumn = new TreeColumn(tree, SWT.LEFT);
-		fieldColumn.setText("Name");
-		fieldColumn.pack();
-		fieldColumn.setResizable(true);
-		
-		final TreeColumn contentColumn = new TreeColumn(tree, SWT.LEFT);
-		contentColumn.setText("Value");
-		contentColumn.pack();
-		contentColumn.setResizable(true);
-		
-		contentViewerColumn = new TreeViewerColumn(this, contentColumn);
-		
-		tree.addControlListener(new ControlAdapter() {
-			@Override
-			public void controlResized(ControlEvent e) {
-				int fullSize = tree.getSize().x;
-				
-				fieldColumn.pack();
-				contentColumn.setWidth(fullSize - fieldColumn.getWidth() - 3);
-			}
-		});
-		
-		ViewerTooltipSupport.addTooltipSupport(this, new ViewerTooltipSupport.ITooltipProvider() {
-
-			public String getTooltip(Object element) {
-				if (element instanceof FieldItem)
-					return ((FieldItem) element).tooltip;
-				return null;
-			}
-			
-		});
-
-		setContentProvider(new SharedFolderContentProvider());
-		setLabelProvider(new SharedFolderLabelProvider());
-	}
-
-	public Collection<ISharedFolder> getMappings() {
-		return mappings;
-	}
-
-	/**
-	 * Add cell editors to the viewer.
-	 */
-	public void addEditors() {
-		contentViewerColumn.setEditingSupport(new EditingSupport(this) {
-
-			protected ISharedFolder getFolder(Object element) {
-				return ((FieldItem) element).folder;
-			}
-			@Override
-			protected boolean canEdit(Object element) {
-				if (element instanceof FieldItem) {
-					return ((FieldItem) element).getCellEditor(getFolder(element), getTree()) != null;
-				}
-				return false;
-			}
-
-			@Override
-			protected CellEditor getCellEditor(final Object element) {
-				if (element instanceof FieldItem) {
-					return ((FieldItem) element).getCellEditor(getFolder(element), getTree());
-				}
-				return null;
-			}
-
-			@Override
-			protected Object getValue(Object element) {
-				if (element instanceof FieldItem) {
-					return ((FieldItem) element).getField();
-				}
-				return null;
-			}
-
-			@Override
-			protected void setValue(Object element, Object value) {
-				if (element instanceof FieldItem && value != null) {
-					((FieldItem) element).setField(value);
-					refresh(getFolder(element));
-				}
-			}
-			
-		});
-	}
-}

Copied: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTreeViewer.java (from rev 2261, branches/work_Ed/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTreeViewer.java)
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTreeViewer.java	                        (rev 0)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFolderTreeViewer.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -0,0 +1,766 @@
+/*******************************************************************************
+ * Copyright (c) 2008-2009 Nokia Corporation
+ * 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:
+ *    Ed Swartz (Nokia) - initial API and implementation
+ *******************************************************************************/
+
+package org.maemo.esbox.internal.api.maemosdk.ui.preferences;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+import org.eclipse.core.runtime.IPath;
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.NullProgressMonitor;
+import org.eclipse.core.runtime.Path;
+import org.eclipse.jface.resource.JFaceResources;
+import org.eclipse.jface.viewers.BaseLabelProvider;
+import org.eclipse.jface.viewers.CellEditor;
+import org.eclipse.jface.viewers.CheckboxCellEditor;
+import org.eclipse.jface.viewers.ComboBoxCellEditor;
+import org.eclipse.jface.viewers.EditingSupport;
+import org.eclipse.jface.viewers.ITableFontProvider;
+import org.eclipse.jface.viewers.ITableLabelProvider;
+import org.eclipse.jface.viewers.ITreeContentProvider;
+import org.eclipse.jface.viewers.TextCellEditor;
+import org.eclipse.jface.viewers.TreeViewer;
+import org.eclipse.jface.viewers.TreeViewerColumn;
+import org.eclipse.jface.viewers.Viewer;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.events.ControlAdapter;
+import org.eclipse.swt.events.ControlEvent;
+import org.eclipse.swt.graphics.Font;
+import org.eclipse.swt.graphics.Image;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.DirectoryDialog;
+import org.eclipse.swt.widgets.Display;
+import org.eclipse.swt.widgets.Tree;
+import org.eclipse.swt.widgets.TreeColumn;
+import org.maemo.mica.common.core.HostUtils;
+import org.maemo.mica.common.core.filesystem.EShareType;
+import org.maemo.mica.common.core.filesystem.ISharedFolder;
+import org.maemo.mica.common.core.filesystem.SharedFolderManager;
+import org.maemo.mica.common.core.filesystem.SharedFolderState;
+import org.maemo.mica.common.core.machine.IMachine;
+import org.maemo.mica.common.core.machine.MachineRegistry;
+import org.maemo.mica.common.ui.CommonUIImages;
+import org.maemo.mica.common.ui.TextAndDialogCellEditor;
+import org.maemo.mica.common.ui.dialogs.DirectoryDialogHelper;
+import org.maemo.mica.internal.api.common.ui.ViewerTooltipSupport;
+
+import com.nokia.cpp.internal.api.utils.core.ObjectUtils;
+
+/**
+ * A tree viewer for shared folder mappings.  The content should be 
+ * ISharedFolder entries.
+ * @author eswartz
+ *
+ */
+public class SharedFolderTreeViewer extends TreeViewer {
+	public static final int COLUMN_FIELD = 0;
+	public static final int COLUMN_CONTENT = 1;
+	
+	private TreeViewerColumn contentViewerColumn;
+	private SharedFolderState shareState;
+	private ScanSharedFoldersThread scanSharedFoldersThread;
+	
+	private static boolean SHOW_SHARE_TYPE = false;
+	private boolean pendingStatusUpdate;
+	
+	private IMachine remoteMachine;
+	private boolean scanFolders;
+	
+	static abstract class FieldItem {
+		String label;
+		ISharedFolder folder;
+		String tooltip;
+		
+		/**
+		 * @param label
+		 * @param parent
+		 */
+		public FieldItem(String label, String tooltip, ISharedFolder parent) {
+			super();
+			this.label = label;
+			this.tooltip = tooltip;
+			this.folder = parent;
+		}
+		
+		protected CellEditor getCellEditor(ISharedFolder folder, Tree tree) {
+			return new TextCellEditor(tree);
+		}
+		
+		abstract protected void setField(Object value);
+		abstract protected Object getField();
+
+		public String getLabel() {
+			return getField().toString();
+		}
+
+		/**
+		 * @return
+		 */
+		public ISharedFolder getFolder() {
+			return folder;
+		}
+	}
+
+	static class DirectoryBrowserCellEditor extends TextAndDialogCellEditor {
+		
+		public DirectoryBrowserCellEditor(Tree tree) {
+			super(tree);
+		}
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.DialogCellEditor#openDialogBox(org.eclipse.swt.widgets.Control)
+		 */
+		@Override
+		protected Object openDialogBox(Control cellEditorWindow) {
+			DirectoryDialog dialog = new DirectoryDialog(cellEditorWindow.getShell());
+			Object current = getValue();
+			DirectoryDialogHelper.setFilterPathToExistingDirectory(dialog, 
+					current instanceof String 
+					? new Path((String)current).toOSString() : Path.ROOT.toOSString());
+			
+			String path = dialog.open();
+			return canonical(path);
+		}
+
+		/* (non-Javadoc)
+		 * @see org.maemo.mica.common.ui.TextAndDialogCellEditor#doGetValue()
+		 */
+		@Override
+		protected Object doGetValue() {
+			Object value = super.doGetValue();
+			if (value instanceof String) {
+				value = canonical((String) value);
+			}
+			return value;
+		}
+		/**
+		 * Only store canonical paths, so we can match mount points properly.
+		 * @param value
+		 * @return
+		 */
+		private String canonical(String value) {
+			if (value != null) {
+				try {
+					value = new File(value).getCanonicalPath();
+				} catch (IOException e) {
+				}
+			}
+			return value;
+		}
+	}
+	
+	static abstract class PathFieldItem extends FieldItem {
+		public PathFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		protected abstract boolean isHostPath(ISharedFolder folder);
+		/* (non-Javadoc)
+		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.FieldItem#getCellEditor(org.eclipse.swt.widgets.Tree)
+		 */
+		@Override
+		protected CellEditor getCellEditor(final ISharedFolder folder, Tree tree) {
+			final CellEditor cellEditor;
+			if (isHostPath(folder)) {
+				cellEditor = new DirectoryBrowserCellEditor(tree);
+			} else {
+				cellEditor = new TextCellEditor(tree);
+			}
+			return cellEditor;
+		}
+	}
+	
+	static class SharePathFieldItem extends PathFieldItem {
+		public SharePathFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		/* (non-Javadoc)
+		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.PathFieldItem#isHostPath()
+		 */
+		@Override
+		protected boolean isHostPath(ISharedFolder folder) {
+			return folder.isHostProvidedShare();
+		}
+		@Override
+		protected Object getField() {
+			return isHostPath(folder) ? folder.getSharePath().toOSString() 
+					: folder.getSharePath().toPortableString();
+		}
+		@Override
+		protected void setField(Object value) {
+			folder.setSharePath(new Path((String)value).makeAbsolute());
+		}
+	}
+	
+	static class MountPathFieldItem extends PathFieldItem {
+		public MountPathFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		/* (non-Javadoc)
+		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.PathFieldItem#isHostPath(org.maemo.mica.common.core.machine.ISharedFolder)
+		 */
+		@Override
+		protected boolean isHostPath(ISharedFolder folder) {
+			return !folder.isHostProvidedShare();
+		}
+		@Override
+		protected Object getField() {
+			return isHostPath(folder) ? folder.getMountPath().toOSString() 
+					: folder.getMountPath().toPortableString();
+		}
+		@Override
+		protected void setField(Object value) {
+			// for Windows mounts, force to be a bare drive
+			
+			IPath path = new Path((String) value);
+			if (isHostPath(folder) && HostUtils.isWindows())
+				path = path.makeRelative();
+			else
+				path = path.makeAbsolute();
+			folder.setMountPath(path);
+		}
+	}
+	
+	static class ShareNameFieldItem extends FieldItem {
+		public ShareNameFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		@Override
+		protected Object getField() {
+			return folder.getShareName();
+		}
+		@Override
+		protected void setField(Object value) {
+			folder.setShareName((String) value);
+		}
+	}
+
+	/**
+	 * A cell editor for "yes/no" values.  Use this instead of {@link CheckboxCellEditor}
+	 * since that has the unwanted behavior that merely clicking will change the value.
+	 * This widget provides feedback and allows the user to know what's happening.
+	 * @author eswartz
+	 *
+	 */
+	static class YesNoCellEditor extends ComboBoxCellEditor {
+
+		public YesNoCellEditor(Composite parent) {
+			super(parent, new String[] { "no", "yes" });
+		}
+
+		@Override
+		protected Object doGetValue() {
+			Integer value = (Integer) super.doGetValue();
+			return Boolean.valueOf(value.intValue() != 0);
+		}
+
+		@Override
+		protected void doSetValue(Object value) {
+			Boolean bool = (Boolean) value;
+			super.doSetValue(Integer.valueOf(bool ? 1 : 0));
+		}
+		
+	}
+	static abstract class BooleanFieldItem extends FieldItem {
+		public BooleanFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		@Override
+		protected CellEditor getCellEditor(ISharedFolder folder, Tree tree) {
+			return new YesNoCellEditor(tree);
+		}
+		@Override
+		public String getLabel() {
+			return ((Boolean) getField()) ? "yes" : "no";
+		}
+	}
+	
+	static class AutoMountFieldItem extends BooleanFieldItem {
+		public AutoMountFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		@Override
+		protected Object getField() {
+			return !folder.isManual();
+		}
+		@Override
+		protected void setField(Object value) {
+			folder.setManual(!(Boolean)value);
+		}
+	}
+
+	static class HostProvidedFieldItem extends BooleanFieldItem {
+		public HostProvidedFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		@Override
+		protected Object getField() {
+			return folder.isHostProvidedShare();
+		}
+		@Override
+		protected void setField(Object value) {
+			folder.setHostProvidedShare((Boolean)value);
+		}
+	}
+	
+	static class StaticFieldItem extends FieldItem {
+		public StaticFieldItem(String label, String tooltip, ISharedFolder parent) {
+			super(label, tooltip, parent);
+		}
+		/* (non-Javadoc)
+		 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFolderTableViewer.FieldItem#getCellEditor(org.eclipse.swt.widgets.Tree)
+		 */
+		@Override
+		protected CellEditor getCellEditor(ISharedFolder folder, Tree tree) {
+			return null;
+		}
+		@Override
+		protected Object getField() {
+			return folder.getShareType().toString();
+		}
+		@Override
+		protected void setField(Object value) {
+			folder.setShareType(EShareType.valueOf((String) value));
+		}
+	}
+	
+	/**
+	 * This content provider simply provides a "tree" where each root
+	 * node is an ISharedFolder whose label provider is a summary of its
+	 * structure and whose children are Strings providing details about
+	 * the entry.  The node as a whole is edited separately in a dialog.
+	 * @author eswartz
+	 *
+	 */
+	static class SharedFolderContentProvider implements ITreeContentProvider {
+
+		private Object[] getFields(ISharedFolder folder) {
+			List<Object> fieldList = new ArrayList<Object>();
+			
+			fieldList.add(new SharePathFieldItem(
+							"Share path",
+							"The full path of the shared folder.",
+							folder));
+			fieldList.add(new HostProvidedFieldItem(
+							"Local share?",
+							"Tells whether the host exports the share (yes), or the virtual machine exports it (no).\n\nThe other machine will mount the share.",
+							folder));
+			fieldList.add(new MountPathFieldItem(
+							"Mount path", 
+							"The full path where the share will be mounted.",
+							folder));
+			fieldList.add(new ShareNameFieldItem(
+							"Share name",
+							"The name of the share (for SMB).",
+							folder));
+			if (SHOW_SHARE_TYPE) {
+				fieldList.add(new StaticFieldItem(
+								"Share type",
+								"The protocol by which the share is provided.",
+								folder));
+			}
+			fieldList.add(new AutoMountFieldItem(
+							"Auto mount?",
+							"If yes, attempt to mount this share when the virtual machine is started.\n\n(NOTE:  ESbox may not be able to mount all folders automatically.)\n\nIf not set, make use of this share mapping for path conversion purposes only.",
+							folder));
+
+			return (Object[]) fieldList.toArray(new Object[fieldList.size()]);
+			
+		}
+		
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.IStructuredContentProvider#getElements(java.lang.Object)
+		 */
+		public Object[] getElements(Object inputElement) {
+			return ((Collection<?>) inputElement).toArray();
+		}
+		
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.ITreeContentProvider#getChildren(java.lang.Object)
+		 */
+		public Object[] getChildren(Object parentElement) {
+			if (parentElement instanceof ISharedFolder) {
+				ISharedFolder folder = (ISharedFolder) parentElement;
+				return getFields(folder);
+			}
+			return null;
+		}
+		
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.ITreeContentProvider#getParent(java.lang.Object)
+		 */
+		public Object getParent(Object element) {
+			if (element instanceof FieldItem)
+				return ((FieldItem) element).folder;
+			else
+				return null;
+		}
+		
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.ITreeContentProvider#hasChildren(java.lang.Object)
+		 */
+		public boolean hasChildren(Object element) {
+			return element instanceof Collection || element instanceof ISharedFolder;
+		}
+
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.IContentProvider#dispose()
+		 */
+		public void dispose() {
+		}
+
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.IContentProvider#inputChanged(org.eclipse.jface.viewers.Viewer, java.lang.Object, java.lang.Object)
+		 */
+		public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
+			viewer.refresh();
+		}
+		
+	}
+	
+	class SharedFolderLabelProvider extends BaseLabelProvider implements 
+		ITableLabelProvider, ITableFontProvider {
+		
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.ITableLabelProvider#getColumnImage(java.lang.Object, int)
+		 */
+		public Image getColumnImage(Object element, int columnIndex) {
+			ISharedFolder folder = null;
+			if (scanFolders && element instanceof ISharedFolder && columnIndex == COLUMN_FIELD) {
+				folder = (ISharedFolder) element;
+				IStatus status = getShareStatus(folder);
+				if (status != null)
+					return CommonUIImages.getStatusLightIcon(status);
+				else if (scanSharedFoldersThread != null)
+					return CommonUIImages.getImage(CommonUIImages.STATUS_PENDING_ICON);
+			}
+			return null;
+		}
+
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.ITableLabelProvider#getColumnText(java.lang.Object, int)
+		 */
+		public String getColumnText(Object element, int columnIndex) {
+			if (element instanceof ISharedFolder) {
+				ISharedFolder folder = (ISharedFolder) element;
+				if (columnIndex == COLUMN_FIELD) {
+					return (folder.isHostProvidedShare()
+							? folder.getLocalPath().toOSString() 
+									: folder.getRemotePath().toPortableString());
+				} else if (scanFolders && columnIndex == COLUMN_CONTENT) {
+					IStatus status = getShareStatus(folder);
+					if (status != null) {
+						if (!status.isOK() && status.getSeverity() != IStatus.CANCEL) {
+							String prefix = "";
+							if (status.getSeverity() == IStatus.WARNING)
+								prefix = "Warning: ";
+							else if (status.getSeverity() == IStatus.ERROR)
+								prefix = "Error: ";
+							else if (status.getSeverity() == IStatus.INFO)
+								prefix = "Info: ";
+							return prefix + status.getMessage();
+						}
+						return "";
+					} else if (scanSharedFoldersThread != null) {
+						return "Scanning...";
+					}
+				}
+			}
+			if (element instanceof FieldItem) {
+				FieldItem item = (FieldItem) element;
+				if (columnIndex == COLUMN_FIELD)
+					return item.label;
+				else if (columnIndex == COLUMN_CONTENT)
+					return item.getLabel();
+			}
+			return null;
+		}
+		
+		/* (non-Javadoc)
+		 * @see org.eclipse.jface.viewers.ITableFontProvider#getFont(java.lang.Object, int)
+		 */
+		public Font getFont(Object element, int columnIndex) {
+			if (element instanceof ISharedFolder && columnIndex == COLUMN_CONTENT) {
+				return JFaceResources.getFontRegistry().getItalic(
+						JFaceResources.DIALOG_FONT);
+			}
+			return null;
+		}
+	}
+	
+	public SharedFolderTreeViewer(Composite parent, int style) {
+		super(parent, style | SWT.FULL_SELECTION | SWT.SINGLE);
+		
+		final Tree tree = getTree();
+		
+		tree.setLinesVisible(true);
+		tree.setHeaderVisible(true);
+		
+		final TreeColumn fieldColumn = new TreeColumn(tree, SWT.LEFT);
+		fieldColumn.setText("Name");
+		fieldColumn.pack();
+		fieldColumn.setResizable(true);
+
+		final TreeColumn contentColumn = new TreeColumn(tree, SWT.LEFT);
+		contentColumn.setText("Value");
+		contentColumn.pack();
+		contentColumn.setResizable(true);
+		
+		contentViewerColumn = new TreeViewerColumn(this, contentColumn);
+
+		tree.addControlListener(new ControlAdapter() {
+			@Override
+			public void controlResized(ControlEvent e) {
+				int fullSize = tree.getSize().x;
+				
+				fieldColumn.pack();
+				contentColumn.setWidth(fullSize - fieldColumn.getWidth() - 3);
+			}
+		});
+		
+		ViewerTooltipSupport.addTooltipSupport(this, new ViewerTooltipSupport.ITooltipProvider() {
+
+			public String getTooltip(Object element) {
+				if (isCellEditorActive())
+					return null;
+				if (element instanceof FieldItem)
+					return ((FieldItem) element).tooltip;
+				/*if (element instanceof ISharedFolder) {
+					IStatus status = getShareStatus((ISharedFolder) element);
+					if (status != null)
+						return status.getMessage();
+				}*/
+					
+				return null;
+			}
+			
+		});
+
+		setContentProvider(new SharedFolderContentProvider());
+		setLabelProvider(new SharedFolderLabelProvider());
+	}
+
+	/**
+	 * @param element
+	 * @return
+	 */
+	public IStatus getShareStatus(ISharedFolder sharedFolder) {
+		IStatus status = null;
+		synchronized (this) {
+			if (shareState != null) {
+				// the statuses will not map exactly using #equals() or #hashCode()
+				// since we're editing them, so only match on the local/remote path
+				Map<ISharedFolder, IStatus> statuses = shareState.getSharedFolderStatuses();
+				
+				for (Map.Entry<ISharedFolder, IStatus> entry : statuses.entrySet()) {
+					if (entry.getKey().getSharePath().equals(sharedFolder.getSharePath())
+							&& entry.getKey().getMountPath().equals(sharedFolder.getMountPath())) {
+						status = entry.getValue();
+						break;
+					}
+				}
+				
+				if (status == null) {
+					for (Map.Entry<ISharedFolder, IStatus> entry : statuses.entrySet()) {
+						if (entry.getKey().getSharePath().equals(sharedFolder.getSharePath())) {
+							status = entry.getValue();
+							break;
+						}
+					}
+				}
+			}
+		}
+		return status;
+	}
+
+	static class InterruptedThreadMonitor extends NullProgressMonitor {
+		@Override
+		public boolean isCanceled() {
+			setCanceled(super.isCanceled() | Thread.currentThread().isInterrupted());
+			return super.isCanceled();
+		}
+	}
+	
+	class ScanSharedFoldersThread extends Thread {
+
+		private List<ISharedFolder> mappings;
+
+		/**
+		 * @param mappings 
+		 */
+		@SuppressWarnings("unchecked")
+		public ScanSharedFoldersThread() {
+			this.mappings = new ArrayList<ISharedFolder>();
+			if (getInput() instanceof Collection)
+				this.mappings.addAll((Collection) getInput());
+		}		
+		
+		/* (non-Javadoc)
+		 * @see java.lang.Thread#run()
+		 */
+		@Override
+		public void run() {
+			if (remoteMachine == null) {
+				scanSharedFoldersThread = null;
+				return;
+			}
+			
+			InterruptedThreadMonitor monitor = new InterruptedThreadMonitor();
+			
+			SharedFolderState state;
+			boolean retry = false;
+			do {
+				remoteMachine.getFileSystemAccess().refresh();
+				
+				state = SharedFolderManager.getInstance().analyzeSharedFolderState(
+						MachineRegistry.getInstance().getLocalMachine(),
+						remoteMachine,
+						mappings,
+						monitor);
+			 	synchronized (SharedFolderTreeViewer.this) {
+					retry = pendingStatusUpdate;
+					pendingStatusUpdate = false;
+			 	}
+			} while (retry && !monitor.isCanceled());
+			
+			synchronized (SharedFolderTreeViewer.this) {
+				if (!monitor.isCanceled()) {
+					shareState = state;
+					updateLabels();
+				}
+				
+				scanSharedFoldersThread = null;
+			}
+		}
+		
+	}
+	/**
+	 *	Update the dynamic status of the shared folders 
+	 */
+	public void scheduleStatusUpdate() {
+		synchronized (this) {
+			if (scanSharedFoldersThread == null) {
+				scanSharedFoldersThread = new ScanSharedFoldersThread();
+				scanSharedFoldersThread.start();
+				pendingStatusUpdate = false;
+				
+				updateLabels();
+			} else {
+				pendingStatusUpdate = true;
+			}
+		}
+	}
+	
+	/**
+	 * 
+	 */
+	protected void updateLabels() {
+		Display.getDefault().asyncExec(new Runnable() {
+			public void run() {
+				if (!getControl().isDisposed()) {
+					if (getInput() instanceof Collection) {
+						Object[] objs = ((Collection<?>) getInput()).toArray();
+						update(objs, null);
+						for (TreeColumn column : ((Tree) getControl()).getColumns())
+							column.pack();
+					}
+				}
+			}
+		});
+	}
+
+	public void cancelStatusUpdate() {
+		Thread thread = scanSharedFoldersThread;
+		if (thread != null) {
+			thread.interrupt();
+			try {
+				thread.join(5000);
+			} catch (InterruptedException e) {
+			}
+			scanSharedFoldersThread = null;
+			updateLabels();
+		}
+	}
+
+	/**
+	 * Add cell editors to the viewer.
+	 */
+	public void addEditors() {
+		contentViewerColumn.setEditingSupport(new EditingSupport(this) {
+
+			protected ISharedFolder getFolder(Object element) {
+				return ((FieldItem) element).folder;
+			}
+			@Override
+			protected boolean canEdit(Object element) {
+				if (element instanceof FieldItem) {
+					return ((FieldItem) element).getCellEditor(getFolder(element), getTree()) != null;
+				}
+				return false;
+			}
+
+			@Override
+			protected CellEditor getCellEditor(final Object element) {
+				if (element instanceof FieldItem) {
+					return ((FieldItem) element).getCellEditor(getFolder(element), getTree());
+				}
+				return null;
+			}
+
+			@Override
+			protected Object getValue(Object element) {
+				if (element instanceof FieldItem) {
+					return ((FieldItem) element).getField();
+				}
+				return null;
+			}
+
+			@Override
+			protected void setValue(Object element, Object value) {
+				if (element instanceof FieldItem && value != null) {
+					Object oldValue = ((FieldItem) element).getField();
+					
+					((FieldItem) element).setField(value);
+					refresh(getFolder(element));
+					
+					if (scanFolders && !ObjectUtils.equals(oldValue, value))
+						scheduleStatusUpdate();
+				}
+			}
+			
+		});
+	}
+	
+	public void setMachine(IMachine machine) {
+		cancelStatusUpdate();
+		this.remoteMachine = machine;
+		scheduleStatusUpdate();
+	}
+
+	/**
+	 * @param scan
+	 */
+	public void setScanFolders(boolean scan) {
+		this.scanFolders = scan;
+		cancelStatusUpdate();
+		if (scanFolders) {
+			scheduleStatusUpdate();
+		} else {
+			updateLabels();
+			for (TreeColumn column : ((Tree) getControl()).getColumns())
+				column.pack();
+		}
+	}
+}

Modified: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFoldersPreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFoldersPreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/SharedFoldersPreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -11,23 +11,47 @@
 
 package org.maemo.esbox.internal.api.maemosdk.ui.preferences;
 
-import org.eclipse.core.runtime.IPath;
+import java.text.MessageFormat;
+import java.util.List;
+
 import org.eclipse.core.runtime.Path;
+import org.eclipse.jface.dialogs.IDialogConstants;
+import org.eclipse.jface.layout.GridDataFactory;
+import org.eclipse.jface.layout.GridLayoutFactory;
+import org.eclipse.jface.preference.BooleanFieldEditor;
 import org.eclipse.jface.preference.IPreferenceStore;
-import org.eclipse.jface.viewers.*;
+import org.eclipse.jface.util.IPropertyChangeListener;
+import org.eclipse.jface.util.PropertyChangeEvent;
+import org.eclipse.jface.viewers.ISelectionChangedListener;
+import org.eclipse.jface.viewers.IStructuredSelection;
+import org.eclipse.jface.viewers.SelectionChangedEvent;
+import org.eclipse.jface.viewers.StructuredSelection;
+import org.eclipse.jface.viewers.TreeViewer;
 import org.eclipse.swt.SWT;
-import org.eclipse.swt.events.*;
+import org.eclipse.swt.events.DisposeEvent;
+import org.eclipse.swt.events.DisposeListener;
+import org.eclipse.swt.events.KeyAdapter;
+import org.eclipse.swt.events.KeyEvent;
+import org.eclipse.swt.events.SelectionAdapter;
+import org.eclipse.swt.events.SelectionEvent;
 import org.eclipse.swt.layout.GridData;
 import org.eclipse.swt.layout.GridLayout;
-import org.eclipse.swt.widgets.*;
+import org.eclipse.swt.widgets.Button;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Control;
+import org.eclipse.swt.widgets.Label;
+import org.eclipse.swt.widgets.Tree;
+import org.maemo.esbox.maemosdk.core.MaemoPreferenceConstants;
+import org.maemo.mica.common.core.filesystem.EShareType;
 import org.maemo.mica.common.core.filesystem.ISharedFolder;
+import org.maemo.mica.common.core.machine.IMachine;
+import org.maemo.mica.common.core.machine.MachineRegistry;
 import org.maemo.mica.common.ui.preferences.BaseComposablePreferencePage;
 import org.maemo.mica.internal.api.common.core.filesystem.BaseSharedFolder;
+import org.maemo.mica.internal.api.common.core.filesystem.MachineShare;
 import org.maemo.mica.internal.api.common.core.filesystem.SharedFolderPreferenceConverter;
+import org.maemo.mica.internal.api.common.core.ui.GridLayoutWrappedTextUtils;
 
-import java.text.MessageFormat;
-import java.util.List;
-
 /**
  * This page is included inside a BuildMachineSelectionPreferencePage
  * to configure the shared folder mappings between host and target.
@@ -36,19 +60,25 @@
  */
 public class SharedFoldersPreferencePage extends BaseComposablePreferencePage {
 
-	private SharedFolderTableViewer treeViewer;
+	private SharedFolderTreeViewer treeViewer;
 	private Composite composite;
 	private Button addButton;
+	private Button addLocalButton;
+	private Button addRemoteButton;
 	private Button removeButton;
 	private Button duplicateButton;
 	private Tree tree;
 	private SharedFolderPreferenceConverter preferenceConverter;
 	private List<ISharedFolder> model;
 	private final String preferenceName;
-
-	public SharedFoldersPreferencePage(IPreferenceStore store, String preferenceName) {
+	private IMachine remoteMachine;
+	private final BaseMachinePreferencePage machinePreferencePage;
+	private IPropertyChangeListener scanFoldersListener;
+	
+	public SharedFoldersPreferencePage(BaseMachinePreferencePage machinePreferencePage, IPreferenceStore store, String preferenceName) {
 		super();
-		setTitle("Shared folders");
+		this.machinePreferencePage = machinePreferencePage;
+		setTitle("&Shared folders");
 		setPreferenceStore(store);
 		this.preferenceName = preferenceName;
 		this.preferenceConverter = new SharedFolderPreferenceConverter();
@@ -85,6 +115,7 @@
 		String info = getStoredPreference(isDefault);
 		model = preferenceConverter.convertPreferenceToModel(info);
 		if (treeViewer != null) {
+			treeViewer.cancelStatusUpdate();
 			treeViewer.setInput(model);
 		}
 		validate();
@@ -132,19 +163,46 @@
 		composite.setLayoutData(layoutData);
 		
 		// left side is the table
-		Label label = new Label(composite, SWT.NONE);
-		label.setText("Shared folder mappings:");
+		Label label = new Label(composite, SWT.WRAP);
+		label.setText(
+		"ESbox needs to create projects on the host, in a shared folder visible to the VM.  "+
+		"For C/C++ indexing and C++ hover help, ESbox must be able to see SDK contents from a VM shared folder visible to the host.\n\n"+
+		"&Configure the shared folders to use:");
+		
 		GridData labelLayout = new GridData(SWT.LEFT, SWT.TOP, true, false);
 		labelLayout.horizontalSpan = 2;
-		label.setLayoutData(labelLayout);
+		GridLayoutWrappedTextUtils.setupLabel(parent, label, labelLayout);
+
+		Composite tableComposite = new Composite(composite, SWT.NONE);
+		GridLayoutFactory.fillDefaults().applyTo(tableComposite);
+		GridDataFactory.fillDefaults().grab(true, true).applyTo(tableComposite);
 		
-		treeViewer = new SharedFolderTableViewer(composite, SWT.BORDER);
+		treeViewer = new SharedFolderTreeViewer(tableComposite, SWT.BORDER);
 		treeViewer.addEditors();
 		
 		GridData tableLayoutData = new GridData(SWT.FILL, SWT.FILL, true, true);
 		tableLayoutData.heightHint = 64;
 		tree = treeViewer.getTree();
 		tree.setLayoutData(tableLayoutData);
+
+		// option to scan folders
+		boolean scanFolders = MaemoPreferenceConstants.getPreferenceStore().getBoolean(
+				MaemoPreferenceConstants.VALIDATE_SHARED_FOLDERS);
+		treeViewer.setScanFolders(scanFolders);
+
+		final Button scanFoldersButton = new Button(tableComposite, SWT.CHECK);
+		scanFoldersButton.setSelection(scanFolders);
+		scanFoldersButton.setText("Dynamically update shared folder status");
+		scanFoldersButton.addSelectionListener(new SelectionAdapter() {
+			@Override
+			public void widgetSelected(SelectionEvent e) {
+				treeViewer.setScanFolders(scanFoldersButton.getSelection());
+				
+				MaemoPreferenceConstants.getPreferenceStore().setValue(
+						MaemoPreferenceConstants.VALIDATE_SHARED_FOLDERS,
+						scanFoldersButton.getSelection());
+			}
+		});
 		
 		// right side is buttons
 		Composite buttonBox = new Composite(composite, SWT.NONE);
@@ -155,7 +213,7 @@
 		
 		addButton = new Button(buttonBox, SWT.PUSH);
 		addButton.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
-		addButton.setText("Add");
+		addButton.setText("&New");
 		addButton.addSelectionListener(new SelectionAdapter() {
 			@Override
 			public void widgetSelected(SelectionEvent e) {
@@ -163,9 +221,30 @@
 			}
 		});
 		
+		addLocalButton = new Button(buttonBox, SWT.PUSH);
+		addLocalButton.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
+		addLocalButton.setText("Add &Host Share...");
+		addLocalButton.addSelectionListener(new SelectionAdapter() {
+			@Override
+			public void widgetSelected(SelectionEvent e) {
+				doAddLocal();
+			}
+		});
+		
+		addRemoteButton = new Button(buttonBox, SWT.PUSH);
+		addRemoteButton.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
+		addRemoteButton.setText("Add &VM Share...");
+		addRemoteButton.setEnabled(false);
+		addRemoteButton.addSelectionListener(new SelectionAdapter() {
+			@Override
+			public void widgetSelected(SelectionEvent e) {
+				doAddRemote();
+			}
+		});
+		
 		removeButton = new Button(buttonBox, SWT.PUSH);
 		removeButton.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
-		removeButton.setText("Remove");
+		removeButton.setText("&Remove");
 		removeButton.addSelectionListener(new SelectionAdapter() {
 			@Override
 			public void widgetSelected(SelectionEvent e) {
@@ -175,7 +254,7 @@
 		
 		duplicateButton = new Button(buttonBox, SWT.PUSH);
 		duplicateButton.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false));
-		duplicateButton.setText("Duplicate");
+		duplicateButton.setText("&Duplicate");
 		duplicateButton.addSelectionListener(new SelectionAdapter() {
 			@Override
 			public void widgetSelected(SelectionEvent e) {
@@ -209,11 +288,28 @@
 			}
 		});
 		
+		treeViewer.getControl().addDisposeListener(new DisposeListener() {
+
+			public void widgetDisposed(DisposeEvent e) {
+				treeViewer.cancelStatusUpdate();
+			}
+			
+		});
+		
 		loadModel(false);
 		
 		treeViewer.expandAll();
 	}
 
+	/**
+	 * 
+	 */
+	protected void updateScanFoldersValue() {
+		boolean scan = MaemoPreferenceConstants.getPreferenceStore().getBoolean(
+				MaemoPreferenceConstants.VALIDATE_SHARED_FOLDERS);
+		treeViewer.setScanFolders(scan);
+	}
+
 	/* (non-Javadoc)
 	 * @see org.maemo.mica.common.core.machine.IComposablePreferencePage#revalidate()
 	 */
@@ -222,9 +318,30 @@
 	}
 	
 	protected void validate() {
+		if (treeViewer.getControl().isDisposed())
+			return;
+		
 		setErrorMessage(null);
 		setMessage(null, INFORMATION);
+		
+		// only check quick stuff here
 		for (ISharedFolder share : model) {
+			if (share.getSharePath().toString().length() == 0) {
+				setErrorMessage(MessageFormat.format(
+						"The shared folder path for ''{0}'' is empty.",
+						share.toString()));
+				setValid(false);
+				return;
+			}
+			if (share.getMountPath().toString().length() == 0) {
+				setErrorMessage(MessageFormat.format(
+						"The mount path is for ''{0}'' is empty.",
+						share.toString()));
+				setValid(false);
+				return;
+			}		
+			
+			/*
 			if (share.isHostProvidedShare()) {
 				IPath path = share.getSharePath();
 				if (!path.toFile().exists()) {
@@ -247,8 +364,9 @@
 								path.toOSString()), WARNING);
 					}
 				}
-			}
+			}*/
 		}
+		
 		setValid(true);
 	}
 
@@ -258,6 +376,29 @@
 		addNewShare(share);
 	}
 
+
+	
+	protected void doAddFromMachine(IMachine machine, boolean isLocal) {
+		SelectMachineShareDialog dialog = new SelectMachineShareDialog(getShell(), machine);
+		
+		int ret = dialog.open();
+		MachineShare share = dialog.getShare();
+		if (ret == IDialogConstants.OK_ID && share != null) {
+			ISharedFolder sharedFolder = new BaseSharedFolder();
+			sharedFolder.setSharePath(share.getPath());
+			sharedFolder.setShareName(share.getShareName());
+			sharedFolder.setHostProvidedShare(isLocal);
+			sharedFolder.setShareType(EShareType.SMB);
+			addNewShare(sharedFolder);
+		}
+	}
+	protected void doAddLocal() {
+		doAddFromMachine(MachineRegistry.getInstance().getLocalMachine(), true);
+	}
+	protected void doAddRemote() {
+		if (remoteMachine != null)
+			doAddFromMachine(remoteMachine, false);
+	}
 	private void addNewShare(ISharedFolder share) {
 		model.add(share);
 		
@@ -276,8 +417,8 @@
 		if (ss.isEmpty())
 			return;
 		Object element = ss.getFirstElement();
-		if (element instanceof SharedFolderTableViewer.FieldItem)
-			element = ((SharedFolderTableViewer.FieldItem)element).getFolder();
+		if (element instanceof SharedFolderTreeViewer.FieldItem)
+			element = ((SharedFolderTreeViewer.FieldItem)element).getFolder();
 		model.remove(element);
 		treeViewer.refresh();
 	}
@@ -288,8 +429,8 @@
 			return;
 		ISharedFolder folder;
 		Object element = ss.getFirstElement();
-		if (element instanceof SharedFolderTableViewer.FieldItem)
-			folder = ((SharedFolderTableViewer.FieldItem)element).getFolder();
+		if (element instanceof SharedFolderTreeViewer.FieldItem)
+			folder = ((SharedFolderTreeViewer.FieldItem)element).getFolder();
 		else if (element instanceof ISharedFolder)
 			folder = (ISharedFolder) element;
 		else
@@ -324,5 +465,23 @@
 	public List<ISharedFolder> getSharedFolders() {
 		return model;
 	}
+
+	/* (non-Javadoc)
+	 * @see org.eclipse.jface.dialogs.DialogPage#setVisible(boolean)
+	 */
+	@Override
+	public void setVisible(boolean visible) {
+		super.setVisible(visible);
+		if (visible) {
+			setMachine(remoteMachine != null ? remoteMachine : machinePreferencePage.createMachine());
+		}
+	}
 	
+	public void setMachine(IMachine machine) {
+		this.remoteMachine = machine;
+		treeViewer.setMachine(machine);
+		if (addRemoteButton != null && !addRemoteButton.isDisposed())
+			addRemoteButton.setEnabled(machine != null && machine.isAlive());
+	}
+	
 }

Modified: trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/ValidateMachineRunner.java
===================================================================
--- trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/ValidateMachineRunner.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.maemosdk.ui/src/org/maemo/esbox/internal/api/maemosdk/ui/preferences/ValidateMachineRunner.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -30,14 +30,15 @@
 import org.eclipse.core.runtime.Path;
 import org.eclipse.core.runtime.SubProgressMonitor;
 import org.eclipse.jface.operation.IRunnableWithProgress;
-import org.eclipse.swt.widgets.Shell;
 import org.maemo.esbox.internal.maemosdk.ui.UIActivator;
 import org.maemo.mica.common.core.MicaCanceledException;
 import org.maemo.mica.common.core.MicaException;
 import org.maemo.mica.common.core.Policy;
 import org.maemo.mica.common.core.filesystem.ISharedFilesystemProvider;
 import org.maemo.mica.common.core.filesystem.ISharedFolder;
+import org.maemo.mica.common.core.filesystem.SharedFolderManager;
 import org.maemo.mica.common.core.machine.IMachine;
+import org.maemo.mica.common.core.machine.MachineRegistry;
 import org.maemo.mica.common.core.machine.MachineUtils;
 import org.maemo.mica.common.core.process.CommandLineArguments;
 import org.maemo.mica.common.core.process.IProcessLauncher;
@@ -60,6 +61,7 @@
 
 	private IMachine machine;
 	private final IProgressReporter reporter;
+	private ISDKTarget[] sdkTargets;
 
 	public ValidateMachineRunner(IProgressReporter reporter,
 			IMachine machine) {
@@ -69,8 +71,6 @@
 		this.machine = machine;
 	}
 	
-	private Shell shell;
-
 	protected void fail(final String msg, final Object... param) {
 		reporter.log(UIActivator.createErrorStatus(
 				MessageFormat.format(msg, param), null));
@@ -208,6 +208,10 @@
 	 * @return true for success
 	 */
 	private boolean testSharedFolders(IProgressMonitor monitor) {
+		// re-detect mounts each time
+		machine.getFileSystemAccess().refresh();
+		MachineRegistry.getInstance().getLocalMachine().getFileSystemAccess().refresh();
+		
 		ISharedFilesystemProvider sharedFilesystemProvider = machine.getSharedFilesystemProvider();
 		if (sharedFilesystemProvider == null)
 			return true;
@@ -217,17 +221,20 @@
 		step(monitor, "Checking shared folders");
 		
 		// ping them all
-		IStatus status = machine.ensureSharesMounted(new SubProgressMonitor(monitor, 1));
+		IStatus status = SharedFolderManager.getInstance().validateShares(
+				MachineRegistry.getInstance().getLocalMachine(), machine, 
+				new SubProgressMonitor(monitor, 1));
+		
 		if (status.getSeverity() == IStatus.WARNING)
 			reporter.log(status);
 		else if (status.getSeverity() == IStatus.ERROR) {
-//			reporter.log(status);
+			reporter.log(status);
 			return false;
 		}
 		
 		boolean succeeded = true;
 		if (sharedFolders.size() == 0) {
-			warn("No shared folders are defined or available\nfor this machine... typically this won't work very well.");
+			warn("No shared folders are defined or available\nfor the machine... typically this won't work very well.");
 			succeeded = false;
 		}
 		for (ISharedFolder share : sharedFolders) {
@@ -402,15 +409,18 @@
 	 * @return non-<code>null</code> array
 	 */
 	private ISDKTarget[] getMachineProvidedTargets(IProgressMonitor monitor) {
-		RefreshSDKManagerJob job = new RefreshSDKManagerJob(machine, true);
-		job.run(monitor);
-		
-		List<ISDKTarget> sdktargetsList = new ArrayList<ISDKTarget>();
-		for (ISDK sdk : job.getSDKs()) {
-			sdktargetsList.addAll(Arrays.asList(sdk.getSDKTargets()));
+		if (sdkTargets == null) {
+			RefreshSDKManagerJob job = new RefreshSDKManagerJob(machine, true);
+			job.run(monitor);
+			
+			List<ISDKTarget> sdktargetsList = new ArrayList<ISDKTarget>();
+			for (ISDK sdk : job.getSDKs()) {
+				sdktargetsList.addAll(Arrays.asList(sdk.getSDKTargets()));
+			}
+			sdkTargets = (ISDKTarget[]) sdktargetsList.toArray(new ISDKTarget[sdktargetsList
+				.size()]);
 		}
-		return (ISDKTarget[]) sdktargetsList.toArray(new ISDKTarget[sdktargetsList
-				.size()]);
+		return sdkTargets;
 	}
 
 }

Modified: trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/launcher/Scratchbox1ProcessLauncher.java
===================================================================
--- trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/launcher/Scratchbox1ProcessLauncher.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/launcher/Scratchbox1ProcessLauncher.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -21,6 +21,7 @@
 import org.maemo.mica.common.core.HostUtils;
 import org.maemo.mica.common.core.MicaException;
 import org.maemo.mica.common.core.Policy;
+import org.maemo.mica.common.core.TimeoutProgressMonitor;
 import org.maemo.mica.common.core.process.*;
 import org.maemo.mica.common.core.sdk.ISDKTarget;
 
@@ -143,7 +144,7 @@
 			@Override
 			public void processExited(int exitCode) {
 				try {
-					store.delete(0, null);
+					store.delete(0, new TimeoutProgressMonitor(5000));
 				} catch (CoreException e) {
 					Activator.getErrorLogger().logError("Error removing  " + runScriptName, e);
 				}

Modified: trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1SDKInstallerSelectionWizardPage.java
===================================================================
--- trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1SDKInstallerSelectionWizardPage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1SDKInstallerSelectionWizardPage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -133,22 +133,8 @@
 		
 		sdkTable.setContentProvider(platformProvider);
 		sdkTable.setLabelProvider(platformProvider);
+		platformProvider.attachContentChangedListener(sdkTable);
 		
-		platformProvider.addListener(new ILabelProviderListener() {
-
-			public void labelProviderChanged(LabelProviderChangedEvent event) {
-				Display.getDefault().asyncExec(new Runnable() {
-					public void run() {
-						if (!sdkTable.getTable().isDisposed()) {
-							for (TableColumn column : sdkTable.getTable().getColumns()) {
-								column.pack();
-							}
-						}
-					}
-				});
-			}
-		});
-		
 		Table table = sdkTable.getTable();
 		GridDataFactory.fillDefaults().grab(true, true).span(2, 1).applyTo(table);
 		

Modified: trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1TargetInstallerSelectionWizardPage.java
===================================================================
--- trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1TargetInstallerSelectionWizardPage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.scratchbox.sb1/src/org/maemo/esbox/internal/scratchbox/sb1/ui/wizard/Scratchbox1TargetInstallerSelectionWizardPage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -23,12 +23,10 @@
 import org.eclipse.jface.operation.IRunnableWithProgress;
 import org.eclipse.jface.viewers.ArrayContentProvider;
 import org.eclipse.jface.viewers.ComboViewer;
-import org.eclipse.jface.viewers.ILabelProviderListener;
 import org.eclipse.jface.viewers.IOpenListener;
 import org.eclipse.jface.viewers.ISelectionChangedListener;
 import org.eclipse.jface.viewers.IStructuredSelection;
 import org.eclipse.jface.viewers.LabelProvider;
-import org.eclipse.jface.viewers.LabelProviderChangedEvent;
 import org.eclipse.jface.viewers.OpenEvent;
 import org.eclipse.jface.viewers.SelectionChangedEvent;
 import org.eclipse.jface.viewers.StructuredSelection;
@@ -219,23 +217,8 @@
 		
 		platformTable.setContentProvider(platformProvider);
 		platformTable.setLabelProvider(platformProvider);
+		platformProvider.attachContentChangedListener(platformTable);
 		
-		platformProvider.addListener(new ILabelProviderListener() {
-
-			public void labelProviderChanged(LabelProviderChangedEvent event) {
-				Display.getDefault().asyncExec(new Runnable() {
-					public void run() {
-						if (!platformTable.getTable().isDisposed()) {
-							for (TableColumn column : platformTable.getTable().getColumns()) {
-								column.pack();
-							}
-						}
-					}
-				});
-			}
-		});
-
-		
 		Table table = platformTable.getTable();
 		GridDataFactory.fillDefaults().grab(true, true).span(2,1).applyTo(table);
 		

Modified: trunk/org.maemo.esbox.scratchbox.sb2/src/org/maemo/esbox/internal/scratchbox/sb2/ui/wizard/TargetWizardRootstrapSb2Page.java
===================================================================
--- trunk/org.maemo.esbox.scratchbox.sb2/src/org/maemo/esbox/internal/scratchbox/sb2/ui/wizard/TargetWizardRootstrapSb2Page.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.scratchbox.sb2/src/org/maemo/esbox/internal/scratchbox/sb2/ui/wizard/TargetWizardRootstrapSb2Page.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -88,7 +88,8 @@
 		provider = new MaemoRootstrapContentLabelProvider(sdk);
 		rootstrapTargetViewer.setContentProvider(provider);
 		rootstrapTargetViewer.setLabelProvider(provider);
-
+		provider.attachContentChangedListener(rootstrapTargetViewer);
+		
 		rootstrapTargetViewer
 				.addSelectionChangedListener(new ISelectionChangedListener() {
 
@@ -100,14 +101,6 @@
 
 				});
 
-		provider.addListener(new ILabelProviderListener() {
-
-			public void labelProviderChanged(LabelProviderChangedEvent event) {
-				rootstrapTargetViewer.refresh();
-			}
-
-		});
-
 		rootstrapTargetViewer.getTree().setLinesVisible(true);
 		rootstrapTargetViewer.getTree().setHeaderVisible(true);
 

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualBuildMachine.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualBuildMachine.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualBuildMachine.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -12,10 +12,6 @@
 package org.maemo.esbox.internal.api.vm.core;
 
 
-import org.eclipse.core.runtime.IProgressMonitor;
-import org.eclipse.core.runtime.IStatus;
-import org.eclipse.core.runtime.Status;
-import org.eclipse.core.runtime.jobs.Job;
 import org.maemo.mica.common.core.filesystem.IFileSystemAccess;
 import org.maemo.mica.common.core.filesystem.ISharedFilesystemProvider;
 import org.maemo.mica.common.core.machine.IMachineController;
@@ -28,7 +24,7 @@
  *
  */
 public abstract class BaseVirtualBuildMachine extends BaseVirtualMachine implements IBuildMachineImpl {
-	private Job validateSharesJob;
+	//private Job validateSharesJob;
 
 
 	public BaseVirtualBuildMachine(String id, String name, String os, String arch,
@@ -44,6 +40,7 @@
 	 */
 	@Override
 	public IFileSystemAccess getFileSystemAccess() {
+		/*
 		// EJS 090624: do this in a job to avoid using a null progress monitor;
 		// if network settings are not perfect, then smbmount will hang for a
 		// very long time and this will be uncancellable.
@@ -79,24 +76,7 @@
 			}
 			validateSharesJob = null;
 		}
-		
-		/*
-		// for this kind of machine, check more proactively,
-		// otherwise build-related stuff is likely to fail
-
-		boolean shouldValidate;
-		synchronized (this) {
-			shouldValidate = !validatedShares && !isValidatingShares;
-		}
-		if (shouldValidate) {
-			// now, verify shared folders
-			ensureSharesMounted(new NullProgressMonitor());
-			
-			// maybe the user cancelled or there were errors... but don't keep asking
-			validatedShares = true;		
-		}
 		*/
-		
 		return super.getFileSystemAccess();
 	}
 }

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineConfiguration.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineConfiguration.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineConfiguration.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -85,7 +85,9 @@
 				String string = iterator.next();
 				Matcher matcher = itemPattern.matcher(string);
 				if (matcher.find()) {
-					if (!registeredKeys.contains(matcher.group(1)))
+					String key = matcher.group(1);
+					// N.B. ssh is not configurable yet
+					if (!registeredKeys.contains(key) || key.equals(VirtualMachinePreferenceConstants.VM_SSH_TIMEOUT))
 						iterator.remove();
 				}
 			}

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineController.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineController.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/core/BaseVirtualMachineController.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -62,7 +62,9 @@
 public abstract class BaseVirtualMachineController extends SSHMachineControllerBase {
 
 	protected static final IStatus CANCEL_STATUS = Policy.getCancelStatus(Activator.getDefault());
-	
+	private long nextVMAliveCheck;
+	private boolean isVMRunning;
+
 	protected IVirtualMachineConfiguration machineConfiguration;
 	
 	public BaseVirtualMachineController(IVirtualMachineConfiguration configuration) {
@@ -80,16 +82,60 @@
 		return machineConfiguration.getSSHConfiguration(); 
 	}
 	
-
 	/**
 	 * Tell if the virtual machine or engine is running.  This either detects
 	 * existing instances of the machine running on the host, or verifies
 	 * that a previously launched instance via {@link #startMachine(IProgressMonitor)} 
 	 * is still valid.
+	 * <p>
+	 * This check uses cached information that remains "true" for a long time
+	 * after the machine is detected.  Use {@link #scheduleProbe()} to reset.
 	 * @return true if it is likely running, false if we either don't know
 	 * or if it is not running.  If unsure, return false.
 	 */
-	abstract public boolean isMachineRunning();
+	final public boolean isMachineRunning() {
+		if (System.currentTimeMillis() >= nextVMAliveCheck) {
+			isVMRunning = doIsMachineRunning();
+			if (!isVMRunning) {
+				// check fairly often while it is not running
+				nextVMAliveCheck = System.currentTimeMillis() + getNextIsRunningDelay(false);
+			} else {
+				// don't check if it is working
+				nextVMAliveCheck = System.currentTimeMillis() + getNextIsRunningDelay(true);
+			}
+		}
+		return isVMRunning;
+	}
+
+	/**
+	 * Get the delay before checking whether the VM is running.
+	 * The time should be short is the machine is not running and
+	 * longer if it is running.
+	 * @param isRunning 
+	 * @return delay in ms
+	 */
+	protected long getNextIsRunningDelay(boolean isRunning) {
+		return isRunning ? 60 * 1000 : 5 * 1000;
+	}
+
+	/**
+	 * Implement the check for the virtual machine or engine is running.  This either detects
+	 * existing instances of the machine running on the host, or verifies
+	 * that a previously launched instance via {@link #startMachine(IProgressMonitor)} 
+	 * is still valid.
+	 * @return true if it is likely running, false if we either don't know
+	 * or if it is not running.  If unsure, return false.
+	 */
+	abstract protected boolean doIsMachineRunning();
+
+	/* (non-Javadoc)
+	 * @see org.maemo.mica.internal.api.protocol.ssh.SSHMachineControllerBase#scheduleProbe()
+	 */
+	@Override
+	public void scheduleProbe() {
+		super.scheduleProbe();
+		nextVMAliveCheck = System.currentTimeMillis();
+	}
 	
 	/**
 	 * Probe the machine until the connection is established.  Since this
@@ -109,6 +155,9 @@
 		while (true) {
 			IStatus status;
 			
+			// probe often
+			scheduleProbe();
+			
 			// see if the process died
 			if (launchInfo != null) {
 				status = launchInfo.checkAlive();
@@ -140,7 +189,6 @@
 			}
 			
 			// test the connection
-			scheduleProbe();
 			status = doProbeMachine(new SubProgressMonitor(monitor, 1));
 			if (status.isOK()) {
 				// XXX: do this more intelligently

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/BaseVirtualMachinePreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/BaseVirtualMachinePreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/BaseVirtualMachinePreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -19,6 +19,7 @@
 import org.maemo.esbox.internal.api.maemosdk.ui.preferences.SharedFoldersPreferencePage;
 import org.maemo.esbox.vm.core.IVirtualMachineConfiguration;
 import org.maemo.esbox.vm.core.VirtualMachinePreferenceConstants;
+import org.maemo.mica.common.core.machine.IMachine;
 import org.maemo.mica.internal.api.common.core.DialogSettingsPreferenceStore;
 
 /**
@@ -49,6 +50,7 @@
 				addressConfigurator,
 				this);
 		sharedFoldersPrefPage = new SharedFoldersPreferencePage(
+				this,
 				getPreferenceStore(),
 				VirtualMachinePreferenceConstants.VM_SHARED_FOLDERS);
 		
@@ -99,79 +101,13 @@
 		}
 	}
 	
-	/**
-	 * Call from a VM page to launch the VM with the current settings
-	 * if it does not seem to be running already.
-	 * <p>
-	 * Not currently used.
+	/* (non-Javadoc)
+	 * @see org.maemo.esbox.internal.api.maemosdk.ui.preferences.BaseMachinePreferencePage#validationFinished(org.maemo.mica.common.core.machine.IMachine)
 	 */
-	/*
-	public void promptLaunchMachine() {
+	@Override
+	public void validationFinished(IMachine machine) {
+		super.validationFinished(machine);
 		
-		if (vmPrefPage == null)
-			return;
-		
-		if (!vmPrefPage.isValid()) {
-			getShell().getDisplay().syncExec(new Runnable() {
-				public void run() {
-					MessageDialog.openInformation(getShell(), 
-							"Invalid configuration",
-							MessageFormat.format(
-								"The {0} preference tab is not valid:\n\n{1}\n\nPlease correct this first.",
-								vmPrefPage.getTitle(),
-								vmPrefPage.getMessage()));
-				}
-			});
-			return;
-		}
-			
-		IVirtualMachine machine = createMachine();
-		if (machine == null)
-			return;
-			
-		IMachineImpl machineImpl = (IMachineImpl) machine;
-		if (!(machineImpl.getMachineController() instanceof ILaunchableVirtualMachineController))
-			return;
-
-		final ILaunchableVirtualMachineController controller =
-			(ILaunchableVirtualMachineController) machineImpl.getMachineController();
-
-		//if (controller.isMachineRunning())
-		//	return;
-		
-		final boolean[] launch = { false };
-		getShell().getDisplay().syncExec(new Runnable() {
-			public void run() {
-				launch[0] = MessageDialog.openQuestion(getShell(), 
-						"Launch virtual machine?", 
-						"If the virtual machine is running, it may be easier to verify some network settings or correct guessed values.\n\n"+
-						"Launch the virtual machine now?");
-				
-			}
-		});
-		if (launch[0]) {
-			try {
-				
-				final IStatus[] statuses = { null };
-				
-				ProgressMonitorDialog dialog = new ProgressMonitorDialog(getShell());
-				dialog.run(true, true, new IRunnableWithProgress() {
-
-					public void run(IProgressMonitor monitor)
-							throws InvocationTargetException,
-							InterruptedException {
-						statuses[0] = controller.startMachine(monitor);
-					}
-					
-				});
-				
-				if (!statuses[0].isOK()) {
-					Activator.getErrorLogger().show(statuses[0]);
-				}
-			} catch (Exception e) {
-				Activator.getErrorLogger().showError("Unexpected error launching the VM", e);
-			}
-		}
+		sharedFoldersPrefPage.setMachine(machine);
 	}
-	*/
 }

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/CommonVirtualMachineSettingsPreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/CommonVirtualMachineSettingsPreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/api/vm/ui/preferences/CommonVirtualMachineSettingsPreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -92,7 +92,7 @@
 		super();
 		this.addressConfigurator = addressConfigurator;
 		this.basePrefPage = basePrefPage;
-		setTitle("Machine access");
+		setTitle("&Machine access");
 		setPreferenceStore(preferenceStore);
 	}
 	

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ESboxHostBuildMachineFactory.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ESboxHostBuildMachineFactory.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ESboxHostBuildMachineFactory.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -61,15 +61,6 @@
 		public IBuildMachinePreferencePage createPreferencePage() {
 			return new LinuxX86MachinePreferencesPage();
 		}
-		
-		/* (non-Javadoc)
-		 * @see org.maemo.mica.common.core.machine.IBuildMachine#ensureSharesMounted(org.eclipse.core.runtime.IProgressMonitor)
-		 */
-		public IStatus ensureSharesMounted(IProgressMonitor monitor) {
-			// no shares from host to host
-			return Status.OK_STATUS;
-		}
-		
 	}
 
 	public ESboxHostBuildMachineFactory() {

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/LinuxX86On64BuildMachineWrapper.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/LinuxX86On64BuildMachineWrapper.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/LinuxX86On64BuildMachineWrapper.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -39,13 +39,4 @@
 	public IBuildMachinePreferencePage createPreferencePage() {
 		return new LinuxX86MachinePreferencesPage();
 	}
-	
-	/* (non-Javadoc)
-	 * @see org.maemo.mica.common.core.machine.IBuildMachine#ensureSharesMounted(org.eclipse.core.runtime.IProgressMonitor)
-	 */
-	public IStatus ensureSharesMounted(IProgressMonitor monitor) {
-		// no shares from host to host
-		return Status.OK_STATUS;
-	}
-	
 }

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ManualVirtualMachineController.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ManualVirtualMachineController.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ManualVirtualMachineController.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -58,7 +58,7 @@
 	 * @see org.maemo.esbox.internal.api.vm.core.BaseVirtualMachineController#isMachineRunning()
 	 */
 	@Override
-	public boolean isMachineRunning() {
+	public boolean doIsMachineRunning() {
 		return false;
 	}
 }

Modified: trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ui/actions/ValidateVirtualMachineCommand.java
===================================================================
--- trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ui/actions/ValidateVirtualMachineCommand.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm/src/org/maemo/esbox/internal/vm/ui/actions/ValidateVirtualMachineCommand.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -22,6 +22,7 @@
 import org.maemo.mica.common.core.machine.MachineRegistry;
 import org.maemo.mica.common.ui.dialogs.StyledTextProgressDialog;
 
+import java.lang.reflect.InvocationTargetException;
 import java.text.MessageFormat;
 
 /**
@@ -72,6 +73,9 @@
 					machine);
 			try {
 				dialog.run(true, true, runner);
+			} catch (InterruptedException e) {
+			} catch (InvocationTargetException e) {
+				Activator.getErrorLogger().logAndShowError("Unexpected exception running tests", e.getCause());
 			} catch (Exception e) {
 				Activator.getErrorLogger().logAndShowError("Unexpected exception running tests", e);
 			}

Modified: trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuMachineController.java
===================================================================
--- trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuMachineController.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuMachineController.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -85,7 +85,7 @@
 	 * @see org.maemo.esbox.internal.api.vm.core.BaseLaunchableVirtualMachineController#isMachineRunning()
 	 */
 	@Override
-	public boolean isMachineRunning() {
+	protected boolean doIsMachineRunning() {
 		if (launchInfo != null) {
 			return launchInfo.isAlive();
 		}

Modified: trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuSettingsPreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuSettingsPreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.qemu/src/org/maemo/esbox/internal/vm/qemu/QemuSettingsPreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -38,7 +38,7 @@
 	 * 
 	 */
 	public QemuSettingsPreferencePage(IPreferenceStore prefStore) {
-		setTitle("QEMU Options");
+		setTitle("QEMU &Options");
 		setPreferenceStore(prefStore);
 	}
 

Modified: trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxMachineController.java
===================================================================
--- trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxMachineController.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxMachineController.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -186,7 +186,7 @@
 	 * @see org.maemo.esbox.internal.api.vm.core.BaseLaunchableVirtualMachineController#isMachineRunning()
 	 */
 	@Override
-	public boolean isMachineRunning() {
+	protected boolean doIsMachineRunning() {
 		LaunchResults results = launchAndRunVBoxManage(10, "list", "runningvms");
 		if (results == null)
 			return false;

Modified: trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxSettingsPreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxSettingsPreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.virtualbox/src/org/maemo/esbox/internal/vm/virtualbox/VirtualBoxSettingsPreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -64,7 +64,7 @@
 	 * 
 	 */
 	public VirtualBoxSettingsPreferencePage(IPreferenceStore preferenceStore) {
-		setTitle("VirtualBox Options");
+		setTitle("VirtualBox &Options");
 		setPreferenceStore(preferenceStore);
 	}
 	

Modified: trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareMachineController.java
===================================================================
--- trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareMachineController.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareMachineController.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -90,10 +90,7 @@
 		return (IProcess[]) matches.toArray(new IProcess[matches.size()]);
 	}
 
-	/* (non-Javadoc)
-	 * @see org.maemo.esbox.internal.api.vm.core.IVirtualMachineController#isMachineRunning()
-	 */
-	public boolean isMachineRunning() {
+	protected boolean doIsMachineRunning() {
 		// We can't tell if the machine stopped running just based on the process stopping
 		// (VMware may have used another instance to host the machine, or, vmrun has exited
 		// right away)
@@ -133,6 +130,19 @@
 	}
 	
 	/* (non-Javadoc)
+	 * @see org.maemo.esbox.internal.api.vm.core.BaseVirtualMachineController#getNextIsRunningDelay(boolean)
+	 */
+	@Override
+	protected long getNextIsRunningDelay(boolean isRunning) {
+		long delay = super.getNextIsRunningDelay(isRunning);
+		if (HostUtils.isWindows()) {
+			// longer delay because vmrun is sooooo slow here
+			delay *= 5;
+		}
+		return delay;
+	}
+	
+	/* (non-Javadoc)
 	 * @see org.maemo.esbox.internal.api.vm.core.BaseVirtualMachineController#constructLaunchParameters()
 	 */
 	@Override
@@ -298,11 +308,6 @@
 	 */
 	@Override
 	protected IStatus doProbeMachine(IProgressMonitor monitor) {
-		if (launchInfo != null && !launchInfo.isAlive()) {
-			// re-check if things might be fishy
-			scheduleProbe();
-		}
-		
 		if (!isMachineRunning())
 			return Activator.createErrorStatus("VMware is not running " 
 					+ ((IVirtualMachine) machine).getDescriptiveName(), null);

Modified: trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareSettingsPreferencePage.java
===================================================================
--- trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareSettingsPreferencePage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareSettingsPreferencePage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -49,7 +49,7 @@
 	 */
 	public VMwareSettingsPreferencePage(IPreferenceStore preferenceStore, BaseMachinePreferencePage vmPrefPage) {
 		this.vmPrefPage = vmPrefPage;
-		setTitle("VMware Options");
+		setTitle("VMware &Options");
 		setPreferenceStore(preferenceStore);
 	}
 	

Modified: trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareUtils.java
===================================================================
--- trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareUtils.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/VMwareUtils.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -135,23 +135,27 @@
 	 * @return String, {@value #NETWORK_CONFIG_BRIDGED}, {@value #NETWORK_CONFIG_HOSTONLY}, {@value #NETWORK_CONFIG_NAT}
 	 */
 	public static String getNetworkConfig(Map<String, String> vmxSettings) {
+		String netconfig = null;
 		String config = null;
 		for (Map.Entry<String, String> entry : vmxSettings.entrySet()) {
 			if (entry.getKey().matches("ethernet.*\\.vnet")) {
 				String vmnet = entry.getValue();
 				if (vmnet.endsWith("vmnet8")) {
-					return NETWORK_CONFIG_NAT;
+					netconfig = NETWORK_CONFIG_NAT;
 				} else if (vmnet.endsWith("vmnet1")) {
-					return NETWORK_CONFIG_HOSTONLY;
+					netconfig = NETWORK_CONFIG_HOSTONLY;
 				} else if (vmnet.endsWith("vmnet0")) {
-					return NETWORK_CONFIG_BRIDGED;
+					netconfig = NETWORK_CONFIG_BRIDGED;
 				} 
 			}
 			if (entry.getKey().matches("ethernet.*\\.connectionType")) {
 				config = entry.getValue();
+				if (!config.equals("custom")) {
+					return config;
+				}
 			}
 		}
-		return config;
+		return netconfig != null ? netconfig : config;
 	}
 
 	/**

Modified: trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/ui/wizards/MaemoSDKVMSelectionWizardPage.java
===================================================================
--- trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/ui/wizards/MaemoSDKVMSelectionWizardPage.java	2009-10-04 16:17:49 UTC (rev 2261)
+++ trunk/org.maemo.esbox.vm.vmware/src/org/maemo/esbox/internal/vm/vmware/ui/wizards/MaemoSDKVMSelectionWizardPage.java	2009-10-04 16:44:00 UTC (rev 2262)
@@ -32,7 +32,6 @@
 import org.eclipse.swt.widgets.Button;
 import org.eclipse.swt.widgets.Composite;
 import org.eclipse.swt.widgets.DirectoryDialog;
-import org.eclipse.swt.widgets.Display;
 import org.eclipse.swt.widgets.Event;
 import org.eclipse.swt.widgets.FileDialog;
 import org.eclipse.swt.widgets.Label;
@@ -195,25 +194,10 @@
 		platformProvider.addListener(this);
 		virtualImagesTable.setContentProvider(platformProvider);
 		virtualImagesTable.setLabelProvider(platformProvider);
-
 		virtualImagesTable.setComparator(new VirtualImagesComparator());
 		
-		platformProvider.addListener(new ILabelProviderListener() {
-
-			public void labelProviderChanged(LabelProviderChangedEvent event) {
-				Display.getDefault().asyncExec(new Runnable() {
-					public void run() {
-						if (!virtualImagesTable.getTable().isDisposed()) {
-							for (TableColumn column : virtualImagesTable
-									.getTable().getColumns()) {
-								column.pack();
-							}
-						}
-					}
-				});
-			}
-		});
-
+		platformProvider.attachContentChangedListener(virtualImagesTable);
+		
 		Table table = virtualImagesTable.getTable();
 		GridDataFactory.fillDefaults().grab(true, true).span(4, 1).applyTo(
 				table);



More information about the Esbox-commits mailing list