diff --git a/usbSerialForAndroid/src/androidTest/java/com/hoho/android/usbserial/DeviceTest.java b/usbSerialForAndroid/src/androidTest/java/com/hoho/android/usbserial/DeviceTest.java index 992d46a..f485fe4 100644 --- a/usbSerialForAndroid/src/androidTest/java/com/hoho/android/usbserial/DeviceTest.java +++ b/usbSerialForAndroid/src/androidTest/java/com/hoho/android/usbserial/DeviceTest.java @@ -73,8 +73,9 @@ public class DeviceTest implements SerialInputOutputManager.Listener { private static int test_device_port; private final static int TELNET_READ_WAIT = 500; - private final static int USB_READ_WAIT = 500; - private final static int USB_WRITE_WAIT = 500; + private final static int TELNET_COMMAND_WAIT = 2000; + private final static int USB_READ_WAIT = 500; + private final static int USB_WRITE_WAIT = 500; private final static Integer SERIAL_INPUT_OUTPUT_MANAGER_THREAD_PRIORITY = Process.THREAD_PRIORITY_URGENT_AUDIO; private final static String TAG = "DeviceTest"; @@ -83,13 +84,16 @@ public class DeviceTest implements SerialInputOutputManager.Listener { private final static byte RFC2217_SET_DATASIZE = 2; private final static byte RFC2217_SET_PARITY = 3; private final static byte RFC2217_SET_STOPSIZE = 4; + private final static byte RFC2217_PURGE_DATA = 12; private Context context; + private UsbManager usbManager; private UsbSerialDriver usbSerialDriver; private UsbDeviceConnection usbDeviceConnection; private UsbSerialPort usbSerialPort; private SerialInputOutputManager usbIoManager; private final Deque usbReadBuffer = new LinkedList<>(); + private Exception usbReadError; private boolean usbReadBlock = false; private long usbReadTime = 0; @@ -137,10 +141,18 @@ public class DeviceTest implements SerialInputOutputManager.Listener { setUpFixtureInt(); telnetClient.sendAYT(1000); // not correctly handled by rfc2217_server.py, but WARNING output "ignoring Telnet command: '\xf6'" is a nice separator between tests telnetComPortOptionCounter[0] = 0; + telnetClient.sendCommand((byte)TelnetCommand.SB); + telnetWriteStream.write(new byte[] {RFC2217_COM_PORT_OPTION, RFC2217_PURGE_DATA, 3}); + telnetClient.sendCommand((byte)TelnetCommand.SE); + for(int i=0; i availableDrivers = UsbSerialProber.getDefaultProber().findAllDrivers(usbManager); assertEquals("no USB device found", 1, availableDrivers.size()); usbSerialDriver = availableDrivers.get(0); @@ -173,24 +185,7 @@ public class DeviceTest implements SerialInputOutputManager.Listener { } assertTrue("USB permission dialog not confirmed", granted[0]); } - usbDeviceConnection = usbManager.openDevice(usbSerialDriver.getDevice()); - usbSerialPort.open(usbDeviceConnection); - usbSerialPort.setDTR(true); - usbSerialPort.setRTS(true); - usbIoManager = new SerialInputOutputManager(usbSerialPort, this) { - @Override - public void run() { - if(SERIAL_INPUT_OUTPUT_MANAGER_THREAD_PRIORITY != null) - Process.setThreadPriority(SERIAL_INPUT_OUTPUT_MANAGER_THREAD_PRIORITY); - super.run(); - } - }; - - Executors.newSingleThreadExecutor().submit(usbIoManager); - - synchronized (usbReadBuffer) { - usbReadBuffer.clear(); - } + usbOpen(true); } @After @@ -266,6 +261,46 @@ public class DeviceTest implements SerialInputOutputManager.Listener { } } + private void usbClose() { + if (usbIoManager != null) { + usbIoManager.stop(); + usbIoManager = null; + } + if (usbSerialPort != null) { + try { + usbSerialPort.close(); + } catch (IOException ignored) { + } + usbSerialPort = null; + } + if(usbDeviceConnection != null) + usbDeviceConnection.close(); + usbDeviceConnection = null; + } + + private void usbOpen(boolean withIoManager) throws Exception { + usbDeviceConnection = usbManager.openDevice(usbSerialDriver.getDevice()); + usbSerialPort = usbSerialDriver.getPorts().get(test_device_port); + usbSerialPort.open(usbDeviceConnection); + usbSerialPort.setDTR(true); + usbSerialPort.setRTS(true); + if(withIoManager) { + usbIoManager = new SerialInputOutputManager(usbSerialPort, this) { + @Override + public void run() { + if (SERIAL_INPUT_OUTPUT_MANAGER_THREAD_PRIORITY != null) + Process.setThreadPriority(SERIAL_INPUT_OUTPUT_MANAGER_THREAD_PRIORITY); + super.run(); + } + }; + Executors.newSingleThreadExecutor().submit(usbIoManager); + } + synchronized (usbReadBuffer) { + usbReadBuffer.clear(); + } + usbReadError = null; + } + // wait full time private byte[] usbRead() throws Exception { return usbRead(-1); @@ -276,6 +311,8 @@ public class DeviceTest implements SerialInputOutputManager.Listener { ByteBuffer buf = ByteBuffer.allocate(8192); if(usbIoManager != null) { while (System.currentTimeMillis() < end) { + if(usbReadError != null) + throw usbReadError; synchronized (usbReadBuffer) { while(usbReadBuffer.peek() != null) buf.put(usbReadBuffer.remove()); @@ -336,7 +373,7 @@ public class DeviceTest implements SerialInputOutputManager.Listener { telnetClient.sendCommand((byte)TelnetCommand.SE); // windows does not like nonstandard baudrates. rfc2217_server.py terminates w/o response - for(int i=0; i<2000; i++) { + for(int i=0; i " + data.length()); + + assertTrue(data.length() > 5); + if(purged) + assertTrue(data.length() < buf.length+1); + else + assertEquals(data.length(), buf.length + 3); + + // todo: purge receive buffer + } } diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CdcAcmSerialDriver.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CdcAcmSerialDriver.java index a3d9a76..264bbd4 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CdcAcmSerialDriver.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CdcAcmSerialDriver.java @@ -401,7 +401,7 @@ public class CdcAcmSerialDriver implements UsbSerialDriver { public static Map getSupportedDevices() { final Map supportedDevices = new LinkedHashMap(); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_ARDUINO), + supportedDevices.put(UsbId.VENDOR_ARDUINO, new int[] { UsbId.ARDUINO_UNO, UsbId.ARDUINO_UNO_R3, @@ -414,19 +414,19 @@ public class CdcAcmSerialDriver implements UsbSerialDriver { UsbId.ARDUINO_LEONARDO, UsbId.ARDUINO_MICRO, }); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_VAN_OOIJEN_TECH), + supportedDevices.put(UsbId.VENDOR_VAN_OOIJEN_TECH, new int[] { UsbId.VAN_OOIJEN_TECH_TEENSYDUINO_SERIAL, }); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_ATMEL), + supportedDevices.put(UsbId.VENDOR_ATMEL, new int[] { UsbId.ATMEL_LUFA_CDC_DEMO_APP, }); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_LEAFLABS), + supportedDevices.put(UsbId.VENDOR_LEAFLABS, new int[] { UsbId.LEAFLABS_MAPLE, }); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_ARM), + supportedDevices.put(UsbId.VENDOR_ARM, new int[] { UsbId.ARM_MBED, }); diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Ch34xSerialDriver.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Ch34xSerialDriver.java index 0b0ae97..b35cbef 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Ch34xSerialDriver.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Ch34xSerialDriver.java @@ -426,11 +426,6 @@ public class Ch34xSerialDriver implements UsbSerialDriver { writeHandshakeByte(); } - @Override - public boolean purgeHwBuffers(boolean purgeReadBuffers, boolean purgeWriteBuffers) throws IOException { - return true; - } - } public static Map getSupportedDevices() { diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CommonUsbSerialPort.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CommonUsbSerialPort.java index d47c5a9..fb7ddc9 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CommonUsbSerialPort.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/CommonUsbSerialPort.java @@ -160,8 +160,8 @@ abstract class CommonUsbSerialPort implements UsbSerialPort { public abstract void setRTS(boolean value) throws IOException; @Override - public boolean purgeHwBuffers(boolean flushReadBuffers, boolean flushWriteBuffers) throws IOException { - return !flushReadBuffers && !flushWriteBuffers; + public boolean purgeHwBuffers(boolean purgeWriteBuffers, boolean purgeReadBuffers) throws IOException { + return false; } } diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Cp21xxSerialDriver.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Cp21xxSerialDriver.java index 4bc07ee..8bd90f0 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Cp21xxSerialDriver.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/Cp21xxSerialDriver.java @@ -379,8 +379,7 @@ public class Cp21xxSerialDriver implements UsbSerialDriver { } @Override - public boolean purgeHwBuffers(boolean purgeReadBuffers, - boolean purgeWriteBuffers) throws IOException { + public boolean purgeHwBuffers(boolean purgeWriteBuffers, boolean purgeReadBuffers) throws IOException { int value = (purgeReadBuffers ? FLUSH_READ_CODE : 0) | (purgeWriteBuffers ? FLUSH_WRITE_CODE : 0); @@ -395,7 +394,7 @@ public class Cp21xxSerialDriver implements UsbSerialDriver { public static Map getSupportedDevices() { final Map supportedDevices = new LinkedHashMap(); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_SILABS), + supportedDevices.put(UsbId.VENDOR_SILABS, new int[] { UsbId.SILABS_CP2102, UsbId.SILABS_CP2105, diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/FtdiSerialDriver.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/FtdiSerialDriver.java index ccdc25e..60d0632 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/FtdiSerialDriver.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/FtdiSerialDriver.java @@ -165,7 +165,7 @@ public class FtdiSerialDriver implements UsbSerialDriver { private static final int SIO_SET_DATA_REQUEST = 4; private static final int SIO_RESET_SIO = 0; - private static final int SIO_RESET_PURGE_RX = 1; + private static final int SIO_RESET_PURGE_RX = 1; // RX @ FTDI device = write @ usb-serial-for-android library private static final int SIO_RESET_PURGE_TX = 2; public static final int FTDI_DEVICE_OUT_REQTYPE = @@ -534,20 +534,20 @@ public class FtdiSerialDriver implements UsbSerialDriver { } @Override - public boolean purgeHwBuffers(boolean purgeReadBuffers, boolean purgeWriteBuffers) throws IOException { - if (purgeReadBuffers) { + public boolean purgeHwBuffers(boolean purgeWriteBuffers, boolean purgeReadBuffers) throws IOException { + if (purgeWriteBuffers) { int result = mConnection.controlTransfer(FTDI_DEVICE_OUT_REQTYPE, SIO_RESET_REQUEST, SIO_RESET_PURGE_RX, mIndex, null, 0, USB_WRITE_TIMEOUT_MILLIS); if (result != 0) { - throw new IOException("Flushing RX failed: result=" + result); + throw new IOException("purge write buffer failed: result=" + result); } } - if (purgeWriteBuffers) { + if (purgeReadBuffers) { int result = mConnection.controlTransfer(FTDI_DEVICE_OUT_REQTYPE, SIO_RESET_REQUEST, SIO_RESET_PURGE_TX, mIndex, null, 0, USB_WRITE_TIMEOUT_MILLIS); if (result != 0) { - throw new IOException("Flushing RX failed: result=" + result); + throw new IOException("purge read buffer failed: result=" + result); } } return true; @@ -556,7 +556,7 @@ public class FtdiSerialDriver implements UsbSerialDriver { public static Map getSupportedDevices() { final Map supportedDevices = new LinkedHashMap(); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_FTDI), + supportedDevices.put(UsbId.VENDOR_FTDI, new int[] { UsbId.FTDI_FT232R, UsbId.FTDI_FT232H, diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/ProlificSerialDriver.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/ProlificSerialDriver.java index c3c8b23..24ae76e 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/ProlificSerialDriver.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/ProlificSerialDriver.java @@ -88,7 +88,7 @@ public class ProlificSerialDriver implements UsbSerialDriver { private static final int READ_ENDPOINT = 0x83; private static final int INTERRUPT_ENDPOINT = 0x81; - private static final int FLUSH_RX_REQUEST = 0x08; + private static final int FLUSH_RX_REQUEST = 0x08; // RX @ Prolific device = write @ usb-serial-for-android library private static final int FLUSH_TX_REQUEST = 0x09; private static final int SET_LINE_REQUEST = 0x20; @@ -553,22 +553,22 @@ public class ProlificSerialDriver implements UsbSerialDriver { } @Override - public boolean purgeHwBuffers(boolean purgeReadBuffers, boolean purgeWriteBuffers) throws IOException { - if (purgeReadBuffers) { + public boolean purgeHwBuffers(boolean purgeWriteBuffers, boolean purgeReadBuffers) throws IOException { + if (purgeWriteBuffers) { vendorOut(FLUSH_RX_REQUEST, 0, null); } - if (purgeWriteBuffers) { + if (purgeReadBuffers) { vendorOut(FLUSH_TX_REQUEST, 0, null); } - return purgeReadBuffers || purgeWriteBuffers; + return true; } } public static Map getSupportedDevices() { final Map supportedDevices = new LinkedHashMap(); - supportedDevices.put(Integer.valueOf(UsbId.VENDOR_PROLIFIC), + supportedDevices.put(UsbId.VENDOR_PROLIFIC, new int[] { UsbId.PROLIFIC_PL2303, }); return supportedDevices; } diff --git a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/UsbSerialPort.java b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/UsbSerialPort.java index 1341143..5cd3ca5 100644 --- a/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/UsbSerialPort.java +++ b/usbSerialForAndroid/src/main/java/com/hoho/android/usbserial/driver/UsbSerialPort.java @@ -216,13 +216,13 @@ public interface UsbSerialPort { public void setRTS(boolean value) throws IOException; /** - * Flush non-transmitted output data and / or non-read input data - * @param flushRX {@code true} to flush non-transmitted output data - * @param flushTX {@code true} to flush non-read input data + * purge non-transmitted output data and / or non-read input data + * @param purgeWriteBuffers {@code true} to discard non-transmitted output data + * @param purgeReadBuffers {@code true} to discard non-read input data * @return {@code true} if the operation was successful, or * {@code false} if the operation is not supported by the driver or device * @throws IOException if an error occurred during flush */ - public boolean purgeHwBuffers(boolean flushRX, boolean flushTX) throws IOException; + public boolean purgeHwBuffers(boolean purgeWriteBuffers, boolean purgeReadBuffers) throws IOException; }