# HG changeset patch # User chpeckha # Date 1267118674 21600 # Node ID 6594b07c89c8e31eb7ae16c71126d0b18692dffb # Parent 5807922922c66974d69f69da74cf44ebcef5b5d3 Changes to fix bugs 10618 10714 10731 10759 10580 merged from 2.5 branch diff -r 5807922922c6 -r 6594b07c89c8 connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/META-INF/MANIFEST.MF --- a/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/META-INF/MANIFEST.MF Wed Feb 24 21:01:05 2010 -0600 +++ b/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/META-INF/MANIFEST.MF Thu Feb 25 11:24:34 2010 -0600 @@ -9,8 +9,7 @@ org.eclipse.core.runtime, org.eclipse.jface, org.eclipse.ui, - com.nokia.carbide.remoteConnections, - com.nokia.cpp.utils.core;bundle-version="1.0.0" + com.nokia.carbide.remoteConnections Bundle-RequiredExecutionEnvironment: J2SE-1.5 Bundle-ActivationPolicy: lazy Bundle-ClassPath: ., diff -r 5807922922c6 -r 6594b07c89c8 connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/agent/PCCSDiscoveryAgent.java --- a/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/agent/PCCSDiscoveryAgent.java Wed Feb 24 21:01:05 2010 -0600 +++ b/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/agent/PCCSDiscoveryAgent.java Thu Feb 25 11:24:34 2010 -0600 @@ -19,11 +19,10 @@ import java.net.MalformedURLException; import java.net.URL; import java.util.Collection; -import java.util.HashMap; import java.util.Map; -import java.util.Set; import org.eclipse.core.runtime.CoreException; +import org.eclipse.core.runtime.IStatus; import com.nokia.carbide.remoteconnections.RemoteConnectionsActivator; import com.nokia.carbide.remoteconnections.discovery.pccs.Activator; @@ -47,6 +46,7 @@ private static final String USB_CONNECTION_TYPE = "com.nokia.carbide.trk.support.connection.USBConnectionType"; //$NON-NLS-1$ private static final String PORT_SETTING = "port"; //$NON-NLS-1$ + private boolean DEBUG = true; public class PCCSPrequisiteStatus implements IPrerequisiteStatus { private boolean isOK = true; @@ -87,16 +87,17 @@ } - protected Map connections; protected IConnectionsManager manager; protected PCCSConnection pccsConnection; private IPrerequisiteStatus loadStatus = new PCCSPrequisiteStatus(); + private UpdateConnectionThread updateThread; + private volatile int numPendingUpdates; /** * Constructs a PCCSDiscoveryAgent object */ public PCCSDiscoveryAgent() { - connections = new HashMap(); +// connections = new HashMap(); manager = RemoteConnectionsActivator.getConnectionsManager(); pccsConnection = new PCCSConnection(); } @@ -125,17 +126,49 @@ case DEVICE_REMOVED: case DEVICE_UPDATED_ADDEDCONNECTION: case DEVICE_UPDATED_REMOVEDCONNECTION: - updateConnections(pccsConnection.getGoodConnectionList()); + if (updateThread != null && updateThread.isAlive()) { + if (DEBUG) System.out.println("onDeviceEvent: update in progress still"); + numPendingUpdates++; + } else { + if (DEBUG) System.out.println("onDeviceEvent: update not started or has finished"); + numPendingUpdates = 1; + updateThread = new UpdateConnectionThread(pccsConnection); + updateThread.start(); + } + +// updateConnections(pccsConnection.getGoodConnectionList()); break; case DEVICE_UPDATED_RENAMED: // TODO what to do when device is renamed? break; } - } catch (CoreException e) { + } catch (Exception e) { RemoteConnectionsActivator.logError(e); } } + private class UpdateConnectionThread extends Thread { + final PCCSConnection pccs; + public UpdateConnectionThread(final PCCSConnection pccs) { + super(Activator.getDisplayName() + ":updateThread"); + this.pccs = pccs; + } + + @Override + public void run() { + try { + do { + if (DEBUG) System.out.println("updateThread updating"); + updateConnections2(pccs.getGoodConnectionList()); + numPendingUpdates--; + } while (numPendingUpdates > 0); + + if (DEBUG) System.out.println("updateThread exiting"); + } catch (CoreException e) { + Activator.logError(e); + } + } + } /* * (non-Javadoc) * @see com.nokia.carbide.remoteconnections.internal.IDeviceDiscoveryAgent#start() @@ -147,7 +180,7 @@ saveLoadStatus(ce); throw ce; // rethrow } - updateConnections(pccsConnection.getGoodConnectionList()); + updateConnections2(pccsConnection.getGoodConnectionList()); pccsConnection.addEventListenter(this); } @@ -192,34 +225,30 @@ * @param deviceConn - device/connection information from PCCS */ protected void createConnection(DeviceConnection deviceConn) { - if (connections.get(getKey(deviceConn)) == null) { - // TODO: currently only handles USB & Serial - if (deviceConn.media.equals("usb")) { //$NON-NLS-1$ - if (deviceConn.mode.equals("serial")) { //$NON-NLS-1$ - IConnectionType connectionType = - RemoteConnectionsActivator.getConnectionTypeProvider().getConnectionType(USB_CONNECTION_TYPE); - if (connectionType != null) { - IConnectionFactory factory = connectionType.getConnectionFactory(); - Map settings = factory.getSettingsFromUI(); - settings.put(PORT_SETTING, deviceConn.port); - IConnection connection = factory.createConnection(settings); - if (connection instanceof IConnection2) { - IConnection2 connection2 = (IConnection2) connection; - connection2.setIdentifier(createUniqueId(deviceConn)); - connection2.setDisplayName(deviceConn.friendlyName); - connection2.setDynamic(true); - String key = getKey(deviceConn); - connections.put(key, connection2); - manager.addConnection(connection2); - } - else { - RemoteConnectionsActivator.log("Could not create dynamic serial connection", null); - } - } - else { - RemoteConnectionsActivator.log("USB connection type extension not found", null); - } + // TODO: currently only handles USB & Serial + if (deviceConn.media.equals("usb") && deviceConn.mode.equals("serial")) { //$NON-NLS-1$ + IConnectionType connectionType = + RemoteConnectionsActivator.getConnectionTypeProvider().getConnectionType(USB_CONNECTION_TYPE); + if (connectionType != null) { + IConnectionFactory factory = connectionType.getConnectionFactory(); + Map settings = factory.getSettingsFromUI(); + settings.put(PORT_SETTING, deviceConn.port); + IConnection connection = factory.createConnection(settings); + if (connection instanceof IConnection2) { + IConnection2 connection2 = (IConnection2) connection; + connection2.setIdentifier(createUniqueId(deviceConn)); + connection2.setDisplayName(deviceConn.friendlyName); + connection2.setDynamic(true); + String key = getKey(deviceConn); + if (DEBUG) System.out.println("createConnection addConnection: " + key); + manager.addConnection(connection2); } + else { + Activator.logMessage("Could not create dynamic serial connection", IStatus.ERROR); + } + } + else { + Activator.logMessage("USB connection type extension not found", IStatus.ERROR); } } } @@ -243,72 +272,77 @@ return key; } /** - * Update existing PCCS connections - * @param connList - the Device/Connection list from PCCS + * update the remote connections */ - protected void updateConnections(Collection connList) { - disconnectAll(); - if (connList != null && !connList.isEmpty()) { - if (connections.isEmpty()) { - // no existing connections, so create new ones - for (DeviceConnection deviceConn : connList) { - createConnection(deviceConn); - } - } - else { - for (DeviceConnection deviceConn : connList) { - String key = getKey(deviceConn); - IConnection2 connection = connections.get(key); - if (connection == null) { - // no existing connection for the device found, must be new connection - createConnection(deviceConn); - } else { - if (!manager.reconnect(connection)) { - manager.addConnection(connection); + private void updateConnections2(Collection connList) { + + if (connList == null || connList.isEmpty()) { + // disconnect all our connections + Collection rConnList = manager.getConnections(); + for (IConnection rConn : rConnList) { + if (rConn instanceof IConnection2) { + if (((IConnection2) rConn).isDynamic()) { + if (rConn.getIdentifier().contains(getClass().getSimpleName())) { + if (DEBUG) System.out.println("new list empty, disconnect: "+ rConn.getIdentifier()); + manager.disconnect((IConnection2) rConn); } } } } + } else { + // new list not empty + // disconnect all remote ones not in our list + Collection rConnList = manager.getConnections(); + for (IConnection rConn : rConnList) { + if (rConn instanceof IConnection2) { + if (((IConnection2) rConn).isDynamic()) { + String uid = rConn.getIdentifier(); + if (uid.contains(getClass().getSimpleName())) { + boolean uidFound = false; + for (DeviceConnection ourConn : connList) { + if (createUniqueId(ourConn).equals(uid)) { + uidFound = true; + break; + } + } + if (!uidFound) { + if (DEBUG) System.out.println("new list not empty, in manager but not in new list -- disconnect: "+ uid); + manager.disconnect((IConnection2) rConn); + } + } + } + } + } + // create if manager doesn't have this connection + // reconnect if manager still does + for (DeviceConnection ourConn : connList) { + String uid = createUniqueId(ourConn); + IConnection2 rConn = (IConnection2) manager.findConnection(uid); + if (rConn == null) { + if (DEBUG) System.out.println("new list not empty, manager doesn't have this -- create: "+ uid); + createConnection(ourConn); + } else { + if (DEBUG) System.out.println("new list not empty, manager has this -- reconnect: "+ uid); + manager.reconnect(rConn); + } + } } } - - private void disconnectAll() { - if (connections.isEmpty()) - return; - Set keySet = connections.keySet(); - for (String key : keySet) { - IConnection2 connection = connections.get(key); - // if manager knows about this connection, disconnect - // otherwise it has already been removed from our system - if (manager.findConnection(connection.getIdentifier()) != null) { - // not removed yet, disconnect only - manager.disconnect(connection); - } else { - // it's been removed from system - // remove it from our list also - connections.remove(key); - } - - } - } - public String getDisplayName() { return Activator.getDisplayName(); } public IPrerequisiteStatus getPrerequisiteStatus() { - // Only try on platforms that run PC Suite - if (HostOS.IS_WIN32) { + // Only try on platforms that run PC Suite + if (HostOS.IS_WIN32) { // Manager calls this first so we can check if we can load. // so let's open the discovery and close it catching any exceptions. try { - pccsConnection.open(); - // successful load - close it as start() will open again - pccsConnection.close(); + pccsConnection.testPrerequisites(); } catch (CoreException ce) { saveLoadStatus(ce); } - } + } return loadStatus; } } diff -r 5807922922c6 -r 6594b07c89c8 connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/ConnAPILibrary.java --- a/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/ConnAPILibrary.java Wed Feb 24 21:01:05 2010 -0600 +++ b/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/ConnAPILibrary.java Thu Feb 25 11:24:34 2010 -0600 @@ -25,10 +25,11 @@ import com.nokia.carbide.remoteconnections.discovery.pccs.Activator; import com.nokia.carbide.remoteconnections.discovery.pccs.Messages; -//import com.nokia.carbide.remoteconnections.discovery.pccs.pccsnative.CONAPI_MEDIA.ByReference; import com.sun.jna.Native; +import com.sun.jna.Pointer; import com.sun.jna.WString; import com.sun.jna.ptr.IntByReference; +import com.sun.jna.ptr.PointerByReference; public class ConnAPILibrary implements IConnAPILibrary { @@ -134,13 +135,27 @@ // TODO Auto-generated method stub return 0; } + public int CONAMMFreeMediaStructures(int dwCountOfMedia, Pointer pMedia) { + // TODO Auto-generated method stub + return 0; + } + public int CONAMMGetMedia(APIHANDLE hMCHandle, IntBuffer pdwCountOfMedia, CONAPI_MEDIA.ByReference[] ppMedia) { // TODO Auto-generated method stub return 0; } - + public int CONAMMGetMedia(APIHANDLE hMCHandle, IntBuffer pdwCountOfMedia, + CONAPI_MEDIA.ByReference ppMedia) { + // TODO Auto-generated method stub + return 0; + } + public int CONAMMGetMedia(APIHANDLE hMCHandle, IntBuffer pdwCountOfMedia, + PointerByReference ppMedia) { + // TODO Auto-generated method stub + return 0; + } public int CONAMMSetMedia(APIHANDLE hMCHandle, CONAPI_MEDIA[] pMedia) { // TODO Auto-generated method stub return 0; @@ -272,4 +287,10 @@ return 0; } + public int CONAMMSetMedia(APIHANDLE hMCHandle, Pointer pMedia) { + // TODO Auto-generated method stub + return 0; + } + + } diff -r 5807922922c6 -r 6594b07c89c8 connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/IConnAPILibrary.java --- a/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/IConnAPILibrary.java Wed Feb 24 21:01:05 2010 -0600 +++ b/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/IConnAPILibrary.java Thu Feb 25 11:24:34 2010 -0600 @@ -19,13 +19,17 @@ import java.nio.IntBuffer; import java.nio.ShortBuffer; +import com.sun.jna.Native; +import com.sun.jna.Pointer; import com.sun.jna.WString; import com.sun.jna.ptr.IntByReference; +import com.sun.jna.ptr.PointerByReference; import com.sun.jna.ptr.ShortByReference; import com.sun.jna.win32.StdCallLibrary; public interface IConnAPILibrary extends StdCallLibrary { + public static IConnAPILibrary INSTANCE = (IConnAPILibrary) Native.loadLibrary("ConnAPI", IConnAPILibrary.class); //$NON-NLS-1$ // DMAPI Device Management // DMAPI Callbacks public interface IConnAPIDeviceCallback extends StdCallCallback { @@ -59,8 +63,12 @@ int CONAOpenMM(LPAPIHANDLE phMCHandle, int dwValue); int CONACloseMM(APIHANDLE hMCHandle); int CONAMMGetMedia(APIHANDLE hMCHandle, IntBuffer pdwCountOfMedia, CONAPI_MEDIA.ByReference[] ppMedia); //TODO: c++ - CONAPI_MEDIA** ppMedia + int CONAMMGetMedia(APIHANDLE hMCHandle, IntBuffer pdwCountOfMedia, CONAPI_MEDIA.ByReference ppMedia); //TODO: c++ - CONAPI_MEDIA** ppMedia + int CONAMMGetMedia(APIHANDLE hMCHandle, IntBuffer pdwCountOfMedia, PointerByReference ppMedia); //TODO: c++ - CONAPI_MEDIA** ppMedia int CONAMMSetMedia(APIHANDLE hMCHandle, CONAPI_MEDIA[] pMedia); + int CONAMMSetMedia(APIHANDLE hMCHandle, Pointer pMedia); int CONAMMFreeMediaStructures(int dwCountOfMedia, CONAPI_MEDIA[] pMedia); + int CONAMMFreeMediaStructures(int dwCountOfMedia, Pointer pMedia); int MCAPI_GetMediaInfo(APIHANDLE hMCHandle, ShortBuffer pstrMediaID, CONAPI_MEDIA_INFO[] pMediaInfo); int MCAPI_FreeMediaInfo(CONAPI_MEDIA_INFO[] pMediaInfo); int CONARegisterMMNotifyCallback(APIHANDLE hMCHandle, int dwState, IConnAPIMediaCallback pfnNotify); diff -r 5807922922c6 -r 6594b07c89c8 connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/PCCSConnection.java --- a/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/PCCSConnection.java Wed Feb 24 21:01:05 2010 -0600 +++ b/connectivity/com.nokia.carbide.remoteConnections.discovery.pccs/src/com/nokia/carbide/remoteconnections/discovery/pccs/pccsnative/PCCSConnection.java Thu Feb 25 11:24:34 2010 -0600 @@ -39,6 +39,7 @@ import com.nokia.carbide.remoteconnections.discovery.pccs.Messages; import com.nokia.carbide.remoteconnections.discovery.pccs.pccsnative.IConnAPILibrary.IConnAPIDeviceCallback; import com.nokia.cpp.internal.api.utils.ui.WorkbenchUtils; + import com.sun.jna.Pointer; import com.sun.jna.WString; import com.sun.jna.ptr.IntByReference; @@ -47,8 +48,7 @@ public class PCCSConnection { private static final String NOT_KNOWN = "not known"; //$NON-NLS-1$ // used for all string structure elements that come back from PCCS as null - private boolean DEBUG = false; - private boolean SWITCH_TO_RNDIS = false; // false for 2.x, true for 3.x + private boolean DEBUG = true; private String DONT_ASK_AGAIN_KEY = "DontAskAgain"; //$NON-NLS-1$ /** @@ -60,52 +60,46 @@ * @see com.nokia.carbide.remoteconnections.discovery.pccs.pccsnative.IConnAPILibrary.IConnAPIDeviceCallback#invoke(int, com.sun.jna.ptr.ShortByReference) */ public int invoke(final int dwStatus, final ShortByReference pstrSerialNumber) { - Display.getDefault().asyncExec( - new Runnable () { - public void run() { - // check for NULL, since I am seeing bogus events coming from PCCS before the real one - // and the serial number is not filled in. If the serial number is null, - // everything else will be null (according to the PCCS docs) - // TODO: bug in PCCS API: - if (DEBUG) System.out.printf("DeviceNotificationCallback %x %s\n", dwStatus, (pstrSerialNumber == null ? "serNum: null" : pstrSerialNumber.getPointer().getString(0, true))); //$NON-NLS-1$ //$NON-NLS-2$ - String serialNumber = NOT_KNOWN; - if (pstrSerialNumber != null) { - serialNumber = pstrSerialNumber.getPointer().getString(0, true); - } + // check for NULL, since I am seeing bogus events coming from PCCS before the real one + // and the serial number is not filled in. If the serial number is null, + // everything else will be null (according to the PCCS docs) + // TODO: bug in PCCS API: + if (DEBUG) System.out.printf("DeviceNotificationCallback %x %s\n", dwStatus, (pstrSerialNumber == null ? "serNum: null" : pstrSerialNumber.getPointer().getString(0, true))); //$NON-NLS-1$ //$NON-NLS-2$ + String serialNumber = NOT_KNOWN; + if (pstrSerialNumber != null) { + serialNumber = pstrSerialNumber.getPointer().getString(0, true); + } - DeviceEventListener.DeviceEvent eventType = DeviceEventListener.DeviceEvent.DEVICE_LIST_UPDATED; - // decode dwStatus per PCCS docs - switch(DMAPIDefinitions.GET_CONAPI_CB_STATUS(dwStatus)) { - case DMAPIDefinitions.CONAPI_DEVICE_LIST_UPDATED: - eventType = DeviceEventListener.DeviceEvent.DEVICE_LIST_UPDATED; - break; - case DMAPIDefinitions.CONAPI_DEVICE_ADDED: - eventType = DeviceEventListener.DeviceEvent.DEVICE_ADDED; - break; - case DMAPIDefinitions.CONAPI_DEVICE_REMOVED: - eventType = DeviceEventListener.DeviceEvent.DEVICE_REMOVED; - break; - case DMAPIDefinitions.CONAPI_DEVICE_UPDATED: - switch(DMAPIDefinitions.GET_CONAPI_CB_INFO(dwStatus)) { - case DMAPIDefinitions.CONAPI_CONNECTION_ADDED: - eventType = DeviceEventListener.DeviceEvent.DEVICE_UPDATED_ADDEDCONNECTION; - break; - case DMAPIDefinitions.CONAPI_CONNECTION_REMOVED: - eventType = DeviceEventListener.DeviceEvent.DEVICE_UPDATED_REMOVEDCONNECTION; - break; - case DMAPIDefinitions.CONAPI_DEVICE_RENAMED: - eventType = DeviceEventListener.DeviceEvent.DEVICE_UPDATED_RENAMED; - break; - } - } - // fire events - Iterator iter = listeners.iterator(); - while (iter.hasNext()) { - iter.next().onDeviceEvent(eventType, serialNumber); - } - } + DeviceEventListener.DeviceEvent eventType = DeviceEventListener.DeviceEvent.DEVICE_LIST_UPDATED; + // decode dwStatus per PCCS docs + switch(DMAPIDefinitions.GET_CONAPI_CB_STATUS(dwStatus)) { + case DMAPIDefinitions.CONAPI_DEVICE_LIST_UPDATED: + eventType = DeviceEventListener.DeviceEvent.DEVICE_LIST_UPDATED; + break; + case DMAPIDefinitions.CONAPI_DEVICE_ADDED: + eventType = DeviceEventListener.DeviceEvent.DEVICE_ADDED; + break; + case DMAPIDefinitions.CONAPI_DEVICE_REMOVED: + eventType = DeviceEventListener.DeviceEvent.DEVICE_REMOVED; + break; + case DMAPIDefinitions.CONAPI_DEVICE_UPDATED: + switch(DMAPIDefinitions.GET_CONAPI_CB_INFO(dwStatus)) { + case DMAPIDefinitions.CONAPI_CONNECTION_ADDED: + eventType = DeviceEventListener.DeviceEvent.DEVICE_UPDATED_ADDEDCONNECTION; + break; + case DMAPIDefinitions.CONAPI_CONNECTION_REMOVED: + eventType = DeviceEventListener.DeviceEvent.DEVICE_UPDATED_REMOVEDCONNECTION; + break; + case DMAPIDefinitions.CONAPI_DEVICE_RENAMED: + eventType = DeviceEventListener.DeviceEvent.DEVICE_UPDATED_RENAMED; + break; } - ); + } + // fire events + Iterator iter = listeners.iterator(); + while (iter.hasNext()) { + iter.next().onDeviceEvent(eventType, serialNumber); + } return PCCSErrors.CONA_OK; } } @@ -115,10 +109,15 @@ private DeviceNotificationCallback pfnCallback = new DeviceNotificationCallback(); public static final int PCCS_NOT_FOUND = 1; public static final int PCCS_WRONG_VERSION = 2; + private static final int DMAPI_VERSION = DMAPIDefinitions.DMAPI_VERSION_34; private APIHANDLE dmHandle = APIHANDLE.INVALID_HANDLE_VALUE; private APIHANDLE mcHandle = APIHANDLE.INVALID_HANDLE_VALUE; private APIHANDLE upHandle = APIHANDLE.INVALID_HANDLE_VALUE; + private boolean dontAskAgain; + private boolean doSwitch; + + private Collection noSwitchConnections = new ArrayList(); private void storeDontAskAgain() { Activator.getDefault().getPreferenceStore().setValue(DONT_ASK_AGAIN_KEY, true); @@ -131,43 +130,47 @@ private boolean dontAskAgain() { return Activator.getDefault().getPreferenceStore().getBoolean(DONT_ASK_AGAIN_KEY); } - /** - * - */ + public PCCSConnection() { } public void open() throws CoreException { if (library == null) { - library = ConnAPILibrary.getInstance(); + try { + library = IConnAPILibrary.INSTANCE; + } catch (UnsatisfiedLinkError e) { + String msg; + if (Activator.isSymSEELayout()) { + msg = Messages.ConnAPILibrary_PCCS_Not_Found_Error + Activator.getLoadErrorURL(); + } else { + msg = Messages.ConnAPILibrary_PCSuite_Not_Found_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCSConnection.PCCS_NOT_FOUND, msg, e)); + } catch (NoClassDefFoundError e) { + String msg; + if (Activator.isSymSEELayout()) { + msg = Messages.ConnAPILibrary_PCCS_Not_Found_Error + Activator.getLoadErrorURL(); + } else { + msg = Messages.ConnAPILibrary_PCSuite_Not_Found_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCSConnection.PCCS_NOT_FOUND, msg, e)); + } } // this uses the MCAPI only to enable required media ensureMediaEnabled(); // load DMAPI - loadDMAPI(); + initDMAPI(); + dmHandle = loadDMAPI(); + if (!APIHANDLE.INVALID_HANDLE_VALUE.equals(dmHandle)) { + startDMNotifications(dmHandle); + } } - private void ensureMediaEnabled() throws CoreException { - // open the MCAPI - loadMCAPI(); - // TODO: - // get media - // enable media - // close MCAPI - closeMCAPI(); - } - - /** - * Initializes the Device Management API (DMAPI) for use. - * - * @throws CoreException - */ - private void loadDMAPI() throws CoreException { - - int dwResult = library.DMAPI_Initialize(DMAPIDefinitions.DMAPI_VERSION_34, null); + private void initDMAPI() throws CoreException { + int dwResult = library.DMAPI_Initialize(DMAPI_VERSION, null); if (dwResult != PCCSErrors.CONA_OK) { - library.DMAPI_Terminate(null); + terminateDMAPI(); String msg; if (Activator.isSymSEELayout()) { msg = String.format("PCCS DMAPI_Initialize API returned error on initialization %x", dwResult); //$NON-NLS-1$ @@ -179,38 +182,14 @@ } throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCS_WRONG_VERSION, msg, null)); } - - // initialize common API -// dwResult = library.CFAPI_Initialize(DMAPIDefinitions.CFAPI_VERSION_10, null); unnecessary -// if (dwResult != PCCSErrors.CONA_OK) { -// library.DMAPI_Terminate(null); -// String msg = String.format("PCCS CFAPI_Initialize API returned error on initialization %x", dwResult); -// throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, dwResult, msg, null)); -// } - - // open a DM handle - dmHandle = APIHANDLE.INVALID_HANDLE_VALUE; - LPAPIHANDLE pHandle = new LPAPIHANDLE(); - dwResult = library.CONAOpenDM(pHandle); - + if (DEBUG) System.out.println("initDMAPI"); //$NON-NLS-1$ + } + private void startDMNotifications(APIHANDLE handle) throws CoreException { + // register a call back + int dwResult = library.CONARegisterNotifyCallback(handle, PCCSTypeDefinitions.API_REGISTER, pfnCallback); if (dwResult != PCCSErrors.CONA_OK) { - library.DMAPI_Terminate(null); - String msg = String.format(Messages.PCCSConnection_PCCS_CONAOpenDM_Error, dwResult); - if (dwResult == PCCSErrors.ECONA_NOT_ENOUGH_MEMORY) { - msg = Messages.PCCSConnection_PCCS_Not_Enough_Memory_Error; - } - throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, dwResult, msg, null)); - } else { - dmHandle = pHandle.getValue(); - } - - // register a call back - dwResult = library.CONARegisterNotifyCallback(dmHandle, PCCSTypeDefinitions.API_REGISTER, pfnCallback); - if (dwResult != PCCSErrors.CONA_OK) { -// System.out.printf("CONAOpenDM returned: %x\n", dwResult); - library.DMAPI_Terminate(null); - library.CONACloseDM(dmHandle); - dmHandle = APIHANDLE.INVALID_HANDLE_VALUE; + library.CONACloseDM(handle); + handle = APIHANDLE.INVALID_HANDLE_VALUE; String msg = String.format(Messages.PCCSConnection_PCCS_CONARegisterNotifyCallback_Error, dwResult); if (dwResult == PCCSErrors.ECONA_INVALID_POINTER) { @@ -218,6 +197,80 @@ } throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, dwResult, msg, null)); } + if (DEBUG) System.out.println("startDMNotifications"); //$NON-NLS-1$ + + } + private void ensureMediaEnabled() throws CoreException { + // open the MCAPI + loadMCAPI(); + // get media list + IntBuffer pdwCount = IntBuffer.allocate(1); + CONAPI_MEDIA.ByReference ppMedia = new CONAPI_MEDIA.ByReference(); + + int dwResult = library.CONAMMGetMedia(mcHandle, pdwCount, ppMedia); + if (DEBUG) + System.out.printf("CONAMMGetMedia dwResult = %x\tpdwCount = %d\n", dwResult, pdwCount.get(0)); //$NON-NLS-1$ + + int count = pdwCount.get(0); + + Pointer pMedia = ppMedia.getPointer(); + Pointer nativePointer = pMedia.getPointer(0); // save this for freeing media + int size = ppMedia.size(); + + if (count > 0) { + CONAPI_MEDIA media[] = new CONAPI_MEDIA[count]; + for (int i = 0; i < count; i++) { + // get pointer from offset of native pointer + Pointer sharedP = nativePointer.share(0 + i*size); + media[i] = new CONAPI_MEDIA(sharedP); + // and read the data from native memory + media[i].read(); + } + for (int i = 0; i < count; i++) { + if (MCAPIDefinitions.CONAPI_GET_MEDIA_TYPE(media[i].dwMedia) == MCAPIDefinitions.CONAPI_MEDIA_USB) { + if (MCAPIDefinitions.CONAPI_IS_MEDIA_UNACTIVE(media[i].dwState)) { + media[i].dwState = MCAPIDefinitions.CONAPI_MEDIA_ACTIVE; + dwResult = library.CONAMMSetMedia(mcHandle, media); + if (DEBUG) + System.out.printf("CONAMMSetMedia dwResult = %x\n", dwResult); //$NON-NLS-1$ + } + } + } + dwResult = library.CONAMMFreeMediaStructures(count, nativePointer); + if (DEBUG) + System.out.printf("CONAMMFreeMediaStructures dwResult = %x\n", dwResult); //$NON-NLS-1$ + } + + // close MCAPI + closeMCAPI(); + } + + /** + * Opens Device Management API (DMAPI) for use. Note: initDMAPI must be called prior to this.
+ * initDMAPI need be called only once, but this can be called whenever we need a handle to + * the DMAPI. + * + * @throws CoreException + */ + private APIHANDLE loadDMAPI() throws CoreException { + + // open a DM handle + APIHANDLE handle = APIHANDLE.INVALID_HANDLE_VALUE; + LPAPIHANDLE pHandle = new LPAPIHANDLE(); + int dwResult = library.CONAOpenDM(pHandle); + + if (dwResult != PCCSErrors.CONA_OK) { + String msg = String.format(Messages.PCCSConnection_PCCS_CONAOpenDM_Error, dwResult); + if (dwResult == PCCSErrors.ECONA_NOT_ENOUGH_MEMORY) { + msg = Messages.PCCSConnection_PCCS_Not_Enough_Memory_Error; + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, dwResult, msg, null)); + } else { + handle = pHandle.getValue(); + } + + if (DEBUG) System.out.printf("loadDMAPI handle=%s\n", handle.toString()); //$NON-NLS-1$ + return handle; } private void loadMCAPI() throws CoreException { @@ -249,6 +302,7 @@ } else { mcHandle = pHandle.getValue(); } + if (DEBUG) System.out.println("\n-----loadMCAPI"); //$NON-NLS-1$ } private void loadUPAPI() throws CoreException { @@ -288,27 +342,40 @@ if (library == null) return; + stopDMNotifications(dmHandle); + // DMAPI should only one be open - closeDMAPI(); + dmHandle = closeDMAPI(dmHandle); + + terminateDMAPI(); } + private void terminateDMAPI() { + // Terminate Device management API + int dwResult = library.DMAPI_Terminate(null); + if (DEBUG) System.out.println("terminateDMAPI"); //$NON-NLS-1$ + } + private void stopDMNotifications(APIHANDLE handle) { + int dwResult = PCCSErrors.CONA_OK; + if (!APIHANDLE.INVALID_HANDLE_VALUE.equals(handle)) { + // unregister callback + dwResult = library.CONARegisterNotifyCallback(handle, PCCSTypeDefinitions.API_UNREGISTER, pfnCallback); + } + if (DEBUG) System.out.println("stopDMNotifications"); //$NON-NLS-1$ + } /** * Closes the DMAPI. * @throws CoreException */ - private void closeDMAPI() throws CoreException { + private APIHANDLE closeDMAPI(APIHANDLE handle) throws CoreException { int dwResult = PCCSErrors.CONA_OK; - if (!APIHANDLE.INVALID_HANDLE_VALUE.equals(dmHandle)) { - // unregister callback - dwResult = library.CONARegisterNotifyCallback(dmHandle, PCCSTypeDefinitions.API_UNREGISTER, pfnCallback); + if (!APIHANDLE.INVALID_HANDLE_VALUE.equals(handle)) { // close DM connection - dwResult = library.CONACloseDM(dmHandle); - dmHandle = APIHANDLE.INVALID_HANDLE_VALUE; - // Terminate Common Functions API -// dwResult = library.CFAPI_Terminate(null); unnecessary - // Terminate Device management API - dwResult = library.DMAPI_Terminate(null); + dwResult = library.CONACloseDM(handle); + if (DEBUG) System.out.printf("closeDMAPI ret=%x handle=%s\n", dwResult, handle.toString()); //$NON-NLS-1$ + handle = APIHANDLE.INVALID_HANDLE_VALUE; } + return handle; } private void closeMCAPI() { @@ -320,12 +387,12 @@ // Terminate Device management API dwResult = library.MCAPI_Terminate(null); } + if (DEBUG) System.out.println("closeMCAPI----\n"); //$NON-NLS-1$ } private void closeUPAPI() { int dwResult = PCCSErrors.CONA_OK; if (!APIHANDLE.INVALID_HANDLE_VALUE.equals(upHandle)) { -// if (upHandle.getValue() != APIHANDLE.INVALID_HANDLE_VALUE) { // close DM connection dwResult = library.UPAPI_CloseUSBPersonality(upHandle); if (dwResult != PCCSErrors.CONA_OK) { @@ -341,42 +408,6 @@ if (DEBUG) System.out.println("closeUPAPI----\n"); //$NON-NLS-1$ } - public void getMediaList() { - if (!APIHANDLE.INVALID_HANDLE_VALUE.equals(mcHandle)) { - IntBuffer pdwCount = IntBuffer.allocate(1); - - CONAPI_MEDIA.ByReference[] ppMedia = (CONAPI_MEDIA.ByReference[])new CONAPI_MEDIA.ByReference().toArray(10); - - int dwResult = library.CONAMMGetMedia(mcHandle, pdwCount, ppMedia); - if (DEBUG) System.out.printf("dwResult = %x\tpdwCount = %d\n", dwResult, pdwCount.get(0)); //$NON-NLS-1$ - int size = pdwCount.get(0); - CONAPI_MEDIA[] pMedia = CONAPI_MEDIA.newArray(10); - Pointer p0 = ppMedia[0].getPointer().getPointer(0); - Pointer p1 = ppMedia[1].getPointer().getPointer(0); - CONAPI_MEDIA media0 = ppMedia[0].newInstance(); - CONAPI_MEDIA media1 = ppMedia[1].newInstance(); - if (dwResult == PCCSErrors.CONA_OK) { - for (int i = 0; i < size; i++) { - // if (DEBUG) { - // System.out.printf("dwSize=%d\tdwMedia=%x\tpstrDescription=%s\n", - // media.dwMedia, - // media.dwMedia, - // (media.pstrDescription == null) ? "null" : media.pstrDescription.getPointer().getString(0, true)); - // System.out.printf("dwState=%d\tdwOptions=%x\tdwMediaData=%d\tpstrID=%s\n", - // media.dwState, - // media.dwOptions, - // media.dwMediaData, - // (media.pstrID == null) ? "null" : media.pstrID.getPointer().getString(0, true)); - // } - // - } - dwResult = library.CONAMMFreeMediaStructures(size, pMedia); - if (dwResult != PCCSErrors.CONA_OK) { - if (DEBUG) System.out.printf("CONAMMFreeMediaStructures = %x\n", dwResult); //$NON-NLS-1$ - } - } - } - } /** * All devices detected are gotten here - BT, USB, etc. * No checking of a valid connection is done here @@ -385,20 +416,34 @@ */ private DeviceInfo[] getCompleteDeviceList() { DeviceInfo[] deviceInfo = null; - + APIHANDLE handle = APIHANDLE.INVALID_HANDLE_VALUE; + try { + handle = loadDMAPI(); + } catch (CoreException e) { + return deviceInfo; + } IntByReference pdwCount = new IntByReference(0); - int dwResult = library.CONAGetDeviceCount(dmHandle, pdwCount); + int dwResult = library.CONAGetDeviceCount(handle, pdwCount); if (DEBUG) System.out.printf("CONAGetDeviceCount: %x number of devices: %d\n", dwResult, pdwCount.getValue()); //$NON-NLS-1$ - if (dwResult != PCCSErrors.CONA_OK) + if (dwResult != PCCSErrors.CONA_OK) { + try { + closeDMAPI(handle); + } catch (CoreException e) { + } return deviceInfo; + } int deviceCount = pdwCount.getValue(); if (deviceCount > 0) { CONAPI_DEVICE[] pDevices = (CONAPI_DEVICE[])new CONAPI_DEVICE().toArray(deviceCount); - dwResult = library.CONAGetDevices(dmHandle, pdwCount, pDevices); + dwResult = library.CONAGetDevices(handle, pdwCount, pDevices); if (DEBUG) System.out.printf("CONAGetDevices: %x number of devices: %d\n", dwResult, deviceCount); //$NON-NLS-1$ if (dwResult != PCCSErrors.CONA_OK) { + try { + closeDMAPI(handle); + } catch (CoreException e) { + } return deviceInfo; } @@ -475,10 +520,20 @@ } dwResult = library.CONAFreeDeviceStructure(deviceCount, pDevices); } - + try { + closeDMAPI(handle); + } catch (CoreException e) { + } + return deviceInfo; } + /** + * Gets the complete list of connections and weeds out "good" connections (i.e., non-debuggable) + * + * @return + * @throws CoreException + */ public synchronized Collection getGoodConnectionList() throws CoreException { DeviceInfo[] deviceList = getCompleteDeviceList(); Collection goodConnections = new ArrayList(); @@ -493,33 +548,48 @@ return goodConnections; } boolean upapiOpen = true; - Collection personalityList = getAllDeviceUSBPersonalities(); - // sometimes on a phone connected to USB, this is failing at least a couple of times - // so retry a number of times - // if there are no USB connections, this failure is expected - if (personalityList == null || personalityList.size() == 0) { - if (DEBUG) System.out.printf("Error 1 getting USB personalities\n"); //$NON-NLS-1$ - closeUPAPI(); - upapiOpen = false; - for (int i = 2; i < 6; i++) { - try { - Thread.sleep(1000); - } catch (InterruptedException e) { + int numUSBPersonalities = 0; + for (DeviceInfo device : deviceList) { + Collection connectionList = device.connections; + for (DeviceConnectionInfo connInfo : connectionList) { + if (connInfo.media.equals("usb")) { + numUSBPersonalities++; } - try { - loadUPAPI(); - upapiOpen = true; - } catch (CoreException e) { - Activator.logError(e); - } - if (upapiOpen) - personalityList = getAllDeviceUSBPersonalities(); - if (personalityList == null || personalityList.size() == 0) { - if (DEBUG) System.out.printf("Error %d getting USB personalities\n", i); //$NON-NLS-1$ - closeUPAPI(); - upapiOpen = false; - } else { - break; + } + } + if (DEBUG) + System.out.println("numUSBPersonalities: " + numUSBPersonalities); + + Collection personalityList = null; + if (numUSBPersonalities > 0) { + personalityList = getAllDeviceUSBPersonalities(); + // sometimes on a phone connected to USB, this is failing at least a couple of times + // so retry a number of times + // if there are no USB connections, this failure is expected + if (personalityList == null || personalityList.size() < numUSBPersonalities) { + if (DEBUG) System.out.printf("Error 1 getting USB personalities: %d of %d total\n", (personalityList != null) ? personalityList.size() : 0, numUSBPersonalities); //$NON-NLS-1$ + closeUPAPI(); + upapiOpen = false; + for (int i = 2; i < 6; i++) { + try { + Thread.sleep(1000); + } catch (InterruptedException e) { + } + try { + loadUPAPI(); + upapiOpen = true; + } catch (CoreException e) { + Activator.logError(e); + } + if (upapiOpen) + personalityList = getAllDeviceUSBPersonalities(); + if (personalityList == null || personalityList.size() < numUSBPersonalities) { + if (DEBUG) System.out.printf("Error %d getting USB personalities: %d of %d total\n", (personalityList != null) ? personalityList.size() : 0, numUSBPersonalities); //$NON-NLS-1$ + closeUPAPI(); + upapiOpen = false; + } else { + break; + } } } } @@ -531,6 +601,8 @@ upapiOpen = true; } + forgetAllNoSwitchConnectionsNotInCurrentList(personalityList); + // go through each connected device and check for good connection modes (e.g. USB in debuggable mode) if (DEBUG) System.out.printf("getGoodConnectionList: sizeof deviceList: %d\n", deviceList.length); //$NON-NLS-1$ for (DeviceInfo device : deviceList) { @@ -582,6 +654,34 @@ return goodConnections; } /** + * Forget all previous "no-switch-personality" devices that are not in current list (e.g., device is now disconnected) + * + * @param personalityList + */ + private void forgetAllNoSwitchConnectionsNotInCurrentList( + Collection personalityList) { + if (personalityList == null || personalityList.isEmpty()) { + if (DEBUG) System.out.println("forgetAllNoSwitchConnectionsNotInCurrentList: all"); + noSwitchConnections.clear(); + } else if (noSwitchConnections == null || noSwitchConnections.isEmpty()) { + if (DEBUG) System.out.println("forgetAllNoSwitchConnectionsNotInCurrentList: noSwitchConnections already empty"); + return; + } else { + for (String id : new ArrayList(noSwitchConnections)) { + boolean found = false; + for (DeviceUSBPersonalityInfo personality : personalityList) { + if (id.equals(personality.deviceID)) { + found = true; + } + } + if (!found) { + if (DEBUG) System.out.println("forgetAllNoSwitchConnectionsNotInCurrentList: " + id); + noSwitchConnections.remove(id); + } + } + } + } + /** * Find a matching device in the personality list (all USB devices).

* Might have to use a combination of the serial number and device ID to match with ID's from personality. * @@ -620,6 +720,13 @@ return personality; } } + // sometimes the serial number is part of the address! + if (!address.equals(NOT_KNOWN) && !personality.serialNumber.equals(NOT_KNOWN)) { + if (address.endsWith(personality.serialNumber)) { + if (DEBUG) System.out.println("findPersonality: address contains serialNumber"); + return personality; + } + } } if (DEBUG) System.out.println("findPersonality end return null"); //$NON-NLS-1$ return null; @@ -650,6 +757,7 @@ connInfo.mode = "serial"; //$NON-NLS-1$ connInfo.port = getUSBComPort(connInfo.address); // good personality + forgetNoSwitchConnections(personality.deviceID); return true; } @@ -669,37 +777,80 @@ return false; } - // ask to switch - askToSwitchPersonality(device, personality, goodCode, goodDesc); + if (!noSwitchConnectionsContains(personality.deviceID)) + // ask to switch + askToSwitchPersonality(device, personality, goodCode, goodDesc); // was bad personality - if we switched, it will be good next notification if (DEBUG) System.out.println("isGoodUSBPersonality: return false"); //$NON-NLS-1$ return false; } - private void askToSwitchPersonality(DeviceInfo device, - DeviceUSBPersonalityInfo personality, int goodCode, String goodDesc) { + + /** + * Search previous "no-switch-personality" list for a new device (e.g., user already said no before - don't ask again unless he reconnects) + * + * @param deviceID + * @return + */ + private boolean noSwitchConnectionsContains(String deviceID) { + if (!noSwitchConnections.isEmpty()) { + for (String id : noSwitchConnections) { + if (id.equals(deviceID)) { + return true; + } + } + } + return false; + } + /** + * Forget one device in previous "no-switch-personality" list (e.g., device is now in a good personality and doesn't need switching) + * + * @param deviceID + */ + private void forgetNoSwitchConnections(String deviceID) { + if (noSwitchConnections.isEmpty()) { + if (DEBUG) System.out.println("forgetNoSwitchConnections empty"); + return; + } + for (String id : new ArrayList(noSwitchConnections)) { + if (id.equals(deviceID)) { + if (DEBUG) System.out.println("forgetNoSwitchConnections: " + deviceID); + noSwitchConnections.remove(id); + } + } + } + private void askToSwitchPersonality(final DeviceInfo device, + final DeviceUSBPersonalityInfo personality, final int goodCode, final String goodDesc) { + + doSwitch = false; + Display.getDefault().syncExec( + new Runnable() { - // ask the user and switch - String fmt = Messages.PCCSConnection_Switch_Message1 + - Messages.PCCSConnection_Swtich_Message2 + - Messages.PCCSConnection_Switch_Message3 + - Messages.PCCSConnection_Switch_Message4; - String message = MessageFormat.format(fmt, - device.friendlyName, - personality.currentPersonalityDescription, - goodDesc); + public void run() { + // ask the user and switch + String fmt = Messages.PCCSConnection_Switch_Message1 + + Messages.PCCSConnection_Swtich_Message2 + + Messages.PCCSConnection_Switch_Message3 + + Messages.PCCSConnection_Switch_Message4; + String message = MessageFormat.format(fmt, + device.friendlyName, + personality.currentPersonalityDescription, + goodDesc); - MessageDialogWithToggle dlg = MessageDialogWithToggle.openYesNoQuestion( - WorkbenchUtils.getSafeShell(), - Messages.PCCSConnection_Switch_Message_Title, - message, - Messages.PCCSConnection_DontAsk_CheckText, - false, - null, - null); - boolean dontAskAgain = dlg.getToggleState(); - boolean doSwitch = (dlg.getReturnCode() == IDialogConstants.YES_ID); - + MessageDialogWithToggle dlg = MessageDialogWithToggle.openYesNoQuestion( + WorkbenchUtils.getSafeShell(), + Messages.PCCSConnection_Switch_Message_Title, + message, + Messages.PCCSConnection_DontAsk_CheckText, + false, + null, + null); + dontAskAgain = dlg.getToggleState(); + doSwitch = (dlg.getReturnCode() == IDialogConstants.YES_ID); + + } + } + ); if (doSwitch) { WString pstrDeviceId = new WString(personality.deviceID); int dwResult = library.UPAPI_SetPersonality(upHandle, pstrDeviceId, goodCode); @@ -707,6 +858,15 @@ if (DEBUG) System.out.printf("UPAPI_SetPersonality failed: %x\n", dwResult); //$NON-NLS-1$ } + } else { + // remember this device so we don't ask again unless it changes personality or is reconnected + rememberNoSwitchConnections(personality.deviceID); + // also log an info message to error log regarding this + String fmt = Messages.PCCSConnection_Switch_Message1 + Messages.PCCSConnection_Swtich_Message2; + String message = MessageFormat.format(fmt, device.friendlyName, + personality.currentPersonalityDescription, + goodDesc); + Activator.logMessage(message, IStatus.INFO); } // store don't ask again only if selected if (dontAskAgain) @@ -714,12 +874,22 @@ } /** + * Device is bad personality and user said 'no' to switch (we won't ask again for this device unless it is reconnected or now in a good mode) + * + * @param deviceID + */ + private void rememberNoSwitchConnections(String deviceID) { + if (DEBUG) System.out.println("rememberNoSwitchConnections: " + deviceID); + noSwitchConnections.add(deviceID); + } + /** * This function assumes the UPAPI has already been loaded by the caller * @return - list of personalities */ private Collection getAllDeviceUSBPersonalities() { Collection p = new ArrayList(); boolean apiError = false; + // how many USB devices are connected IntBuffer pdwDeviceCount = IntBuffer.allocate(1); int dwResult = library.UPAPI_QueryDeviceCount(upHandle, pdwDeviceCount); @@ -771,7 +941,7 @@ if (DEBUG) System.out.printf("UPAPI_QueryDeviceCount dwResult = %x\n", dwResult); //$NON-NLS-1$ } - if (DEBUG) System.out.printf("getAllDeviceUSBPersonalities return p size : %s\n", p.size()); //$NON-NLS-1$ + if (DEBUG) System.out.printf("getAllDeviceUSBPersonalities return size : %s\n", p.size()); //$NON-NLS-1$ return p; } private boolean getPersonalityDescriptors( @@ -846,134 +1016,6 @@ return apiError; } - /** - * @return null if no device found. - * @throws CoreException - * @deprecated Use {@link #getGoodConnectionList()} instead. - */ - public DeviceInfo[] getDeviceList() throws CoreException { - - DeviceInfo[] deviceInfo = null; - - int dwResult = PCCSErrors.CONA_OK; - IntByReference pdwCount = new IntByReference(0); - dwResult = library.CONAGetDeviceCount(dmHandle, pdwCount); - if (DEBUG) System.out.printf("CONAGetDeviceCount: %x number of devices: %d\n", dwResult, pdwCount.getValue()); //$NON-NLS-1$ - - int deviceCnt = pdwCount.getValue(); - if (dwResult != PCCSErrors.CONA_OK || deviceCnt == 0) - return deviceInfo; - - // array of structs in contiguous memory required ! - CONAPI_DEVICE[] pDevices = (CONAPI_DEVICE[])new CONAPI_DEVICE().toArray(deviceCnt); - dwResult = library.CONAGetDevices(dmHandle, pdwCount, pDevices); - if (DEBUG) System.out.printf("CONAGetDevices: %x number of devices: %d\n", dwResult, deviceCnt); //$NON-NLS-1$ - - if (dwResult == PCCSErrors.CONA_OK) { - // extract to regular java types - if (deviceCnt > 0) { - deviceInfo = new DeviceInfo[deviceCnt]; - CONAPI_DEVICE[] devices = pDevices; - for (int i = 0; i < deviceCnt; i++) { - deviceInfo[i] = new DeviceInfo(); - if (devices[i].pstrSerialNumber != null) { - deviceInfo[i].serialNumber = devices[i].pstrSerialNumber.getPointer().getString(0, true); - } else { - // TODO: docs say if ser num == null --> device unsupported, but this is a bug in PCCS - deviceInfo[i].serialNumber = NOT_KNOWN; //$NON-NLS-1$ - } - if (devices[i].pstrFriendlyName != null) { - deviceInfo[i].friendlyName = devices[i].pstrFriendlyName.getPointer().getString(0, true); - } else { - deviceInfo[i].friendlyName = NOT_KNOWN; //$NON-NLS-1$ - } - if (devices[i].pstrModel != null) { - deviceInfo[i].model = devices[i].pstrModel.getPointer().getString(0, true); - } else { - deviceInfo[i].model = NOT_KNOWN; //$NON-NLS-1$ - } - if (devices[i].pstrManufacturer != null) { - deviceInfo[i].mfr = devices[i].pstrManufacturer.getPointer().getString(0, true); - } else { - deviceInfo[i].mfr = NOT_KNOWN; //$NON-NLS-1$ - } - int numItems = deviceInfo[i].numberOfConnections = devices[i].dwNumberOfItems; - - CONAPI_CONNECTION_INFO[] conn = null; - if (numItems > 0) - conn = (CONAPI_CONNECTION_INFO[])devices[i].pItems.toArray(numItems); - for (int j = 0; j < numItems; j++) { - DeviceConnectionInfo connInfo = new DeviceConnectionInfo(); - connInfo.deviceID = conn[j].dwDeviceID; - switch(conn[j].dwMedia){ - case PCCSTypeDefinitions.API_MEDIA_BLUETOOTH: - connInfo.media = "bluetooth"; //$NON-NLS-1$ - break; - case PCCSTypeDefinitions.API_MEDIA_IRDA: - connInfo.media = "irda"; //$NON-NLS-1$ - break; - case PCCSTypeDefinitions.API_MEDIA_SERIAL: - connInfo.media = "serial-ca42"; //$NON-NLS-1$ - break; - default: - case PCCSTypeDefinitions.API_MEDIA_USB: - connInfo.media = "usb"; //$NON-NLS-1$ - break; - } - if (conn[j].pstrDeviceName != null) { - connInfo.deviceName = conn[j].pstrDeviceName.getPointer().getString(0,true); - if (deviceInfo[i].friendlyName.equals(NOT_KNOWN)) { //$NON-NLS-1$ - // use device name as friendly name (latter was null) - deviceInfo[i].friendlyName = connInfo.deviceName; - } - } else { - connInfo.deviceName = NOT_KNOWN; //$NON-NLS-1$ - } - // Bomb if friendly name is not known or address is not known - // since these are essential to a connection - if (conn[j].pstrAddress == null || deviceInfo[i].friendlyName.equals(NOT_KNOWN)) //$NON-NLS-1$ - continue; - - connInfo.address = conn[j].pstrAddress.getPointer().getString(0, true); - connInfo.state = conn[j].dwState; - - if (connInfo.media.equals("usb")) { //$NON-NLS-1$ - if (checkUSBMode(deviceInfo[i], connInfo)){ - connInfo.port = getUSBComPort(connInfo.address); - } else { - // don't store - not in good USB personality mode - continue; - } - } else if (connInfo.media.equals("bluetooth")) { //$NON-NLS-1$ - // TODO: implement BT - connInfo.port = getBTComPort(connInfo.address); - } else { - // IRDA and Serial(CA42) probably will not come here anyway - connInfo.port = null; - } - if (connInfo.port != null) - deviceInfo[i].connections.add(connInfo); - } - } - } - dwResult = library.CONAFreeDeviceStructure(deviceCnt, pDevices); - if (DEBUG) System.out.printf("CONAFreeDeviceStructure: %x\n", dwResult); //$NON-NLS-1$ - } - return deviceInfo; - } - - /** - * - * @param deviceInfo - * @param connInfo - * @return - * - * @deprecated not used anymore - */ - private boolean checkUSBMode(DeviceInfo deviceInfo, - DeviceConnectionInfo connInfo) { - return true; - } private String getBTComPort(String address) { // TODO Auto-generated method stub @@ -1053,4 +1095,89 @@ // string = personality description for code from device Map supportedPersonalities; } + public void testPrerequisites() throws CoreException { + try { + if (library == null) + library = IConnAPILibrary.INSTANCE; + } catch (UnsatisfiedLinkError e) { + String msg; + if (Activator.isSymSEELayout()) { + msg = Messages.ConnAPILibrary_PCCS_Not_Found_Error + Activator.getLoadErrorURL(); + } else { + msg = Messages.ConnAPILibrary_PCSuite_Not_Found_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCSConnection.PCCS_NOT_FOUND, msg, e)); + } catch (NoClassDefFoundError e) { + String msg; + if (Activator.isSymSEELayout()) { + msg = Messages.ConnAPILibrary_PCCS_Not_Found_Error + Activator.getLoadErrorURL(); + } else { + msg = Messages.ConnAPILibrary_PCSuite_Not_Found_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCSConnection.PCCS_NOT_FOUND, msg, e)); + } + testDMAPI(); + testUPAPI(); + testMCAPI(); + } + /* + * Tests version of DMAPI and leaves it closed + */ + private void testDMAPI() throws CoreException { + int dwResult = library.DMAPI_Initialize(DMAPI_VERSION, null); + library.DMAPI_Terminate(null); + if (dwResult != PCCSErrors.CONA_OK) { + String msg; + if (Activator.isSymSEELayout()) { + msg = String.format("PCCS DMAPI_Initialize API returned error on initialization %x", dwResult); //$NON-NLS-1$ + if (dwResult == PCCSErrors.ECONA_UNSUPPORTED_API_VERSION) { + msg = Messages.PCCSConnection_PCCS_Version_Error + Activator.getLoadErrorURL(); + } + } else { + msg = Messages.PCCSConnection_PCSuite_Version_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCS_WRONG_VERSION, msg, null)); + } + } + /* + * Test version of UPAPI and leaves it closed + */ + private void testUPAPI() throws CoreException { + int dwResult = PCCSErrors.CONA_OK; + dwResult = library.UPAPI_Initialize(UPAPIDefinitions.UPAPI_VERSION_10, null); + library.UPAPI_Terminate(null); + if (dwResult != PCCSErrors.CONA_OK) { + String msg; + msg = String.format("PCCS UPAPI_Initialize API returned error on initialization %x", dwResult); //$NON-NLS-1$ + if (DEBUG) System.out.println(msg); + if (Activator.isSymSEELayout()) { + if (dwResult == PCCSErrors.ECONA_UNSUPPORTED_API_VERSION) { + msg = Messages.PCCSConnection_PCCS_Version_Error + Activator.getLoadErrorURL(); + } + } else { + msg = Messages.PCCSConnection_PCSuite_Version_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCS_WRONG_VERSION, msg, null)); + } + } + /* + * Test version of MCAPI and leaves it closed + */ + private void testMCAPI() throws CoreException { + int dwResult = PCCSErrors.CONA_OK; + dwResult = library.MCAPI_Initialize(MCAPIDefinitions.MCAPI_VERSION_32, null); + library.MCAPI_Terminate(null); + if (dwResult != PCCSErrors.CONA_OK) { + String msg; + if (Activator.isSymSEELayout()) { + msg = String.format("PCCS MCAPI_Initialize API returned error on initialization %x", dwResult); //$NON-NLS-1$ + if (dwResult == PCCSErrors.ECONA_UNSUPPORTED_API_VERSION) { + msg = Messages.PCCSConnection_PCCS_Version_Error + Activator.getLoadErrorURL(); + } + } else { + msg = Messages.PCCSConnection_PCSuite_Version_Error + Activator.getLoadErrorURL(); + } + throw new CoreException(new Status(IStatus.ERROR, Activator.PLUGIN_ID, PCCS_WRONG_VERSION, msg, null)); + } + } }