libftdi: (tomj) FTDICHIP-ID read support
authorThomas Jarosch <opensource@intra2net.com>
Fri, 19 Oct 2007 08:31:15 +0000 (08:31 +0000)
committerThomas Jarosch <opensource@intra2net.com>
Fri, 19 Oct 2007 08:31:15 +0000 (08:31 +0000)
ChangeLog
examples/simple.c
src/ftdi.c
src/ftdi.h

index 8b17f1a..e21a965 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,8 @@
+New in 0.11
+-----------
+* Detection of R-type chips
+* FTDIChip-ID read support (Peter Holik)
+
 New in 0.10
 -----------
 * Examples for libftdi_usb_find_all and CBUS mode
index 4156a92..d3599c5 100644 (file)
@@ -19,6 +19,13 @@ int main(int argc, char **argv)
         return EXIT_FAILURE;
     }
 
+    // Read out FTDIChip-ID of R type chips
+    if (ftdic.type == TYPE_R) {
+        unsigned int chipid;
+        printf("ftdi_read_chipid: %d\n", ftdi_read_chipid(&ftdic, &chipid));
+        printf("FTDI chipid: %X\n", chipid);
+    }
+
     ftdi_usb_close(&ftdic);
     ftdi_deinit(&ftdic);
 
index 096a03d..b029b01 100644 (file)
@@ -315,7 +315,8 @@ int ftdi_usb_open_dev(struct ftdi_context *ftdi, struct usb_device *dev)
         ftdi->type = TYPE_2232C;
         if (!ftdi->index)
             ftdi->index = INTERFACE_A;
-    }
+    } else if (dev->descriptor.bcdDevice == 0x600)
+        ftdi->type = TYPE_R;
 
     ftdi_error_return(0, "all fine");
 }
@@ -1227,6 +1228,56 @@ int ftdi_read_eeprom(struct ftdi_context *ftdi, unsigned char *eeprom)
     return 0;
 }
 
+/*
+    ftdi_read_chipid_shift does the bitshift operation needed for the FTDIChip-ID
+    Function is only used internally
+    \internal
+*/
+static unsigned char ftdi_read_chipid_shift(unsigned char value)
+{
+    return ((value & 1) << 1) |
+            ((value & 2) << 5) |
+            ((value & 4) >> 2) |
+            ((value & 8) << 4) |
+            ((value & 16) >> 1) |
+            ((value & 32) >> 1) |
+            ((value & 64) >> 4) |
+            ((value & 128) >> 2);
+}
+
+/**
+    Read the FTDIChip-ID from R-type devices
+
+    \param ftdi pointer to ftdi_context
+    \param chipid Pointer to store FTDIChip-ID
+
+    \retval  0: all fine
+    \retval -1: read failed
+*/
+int ftdi_read_chipid(struct ftdi_context *ftdi, unsigned int *chipid)
+{
+    unsigned int a = 0, b = 0, result = -1;
+
+    if (usb_control_msg(ftdi->usb_dev, 0xC0, 0x90, 0, 0x43, (char *)&a, 2, ftdi->usb_read_timeout) == 2)
+    {
+        a = a << 8 | a >> 8;
+        if (usb_control_msg(ftdi->usb_dev, 0xC0, 0x90, 0, 0x44, (char *)&b, 2, ftdi->usb_read_timeout) == 2)
+        {
+            b = b << 8 | b >> 8;
+            a = (a << 16) | b;
+            a = ftdi_read_chipid_shift(a) | ftdi_read_chipid_shift(a>>8)<<8;
+            a |= ftdi_read_chipid_shift(a>>16)<<16 | ftdi_read_chipid_shift(a>>24)<<24;
+            *chipid = a ^ 0xa5f0f7d1;
+            result = 0;
+        }
+    }
+
+    if (result != 0)
+        ftdi_error_return(result, "read of FTDIChip-ID failed");
+
+    return 0;
+}
+
 /**
     Write eeprom
 
index fd0d357..6d3c98d 100644 (file)
@@ -20,7 +20,7 @@
 #include <usb.h>
 
 /// FTDI chip type
-enum ftdi_chip_type { TYPE_AM=0, TYPE_BM=1, TYPE_2232C=2 };
+enum ftdi_chip_type { TYPE_AM=0, TYPE_BM=1, TYPE_2232C=2, TYPE_R=3 };
 /// Parity mode for ftdi_set_line_property()
 enum ftdi_parity_type { NONE=0, ODD=1, EVEN=2, MARK=3, SPACE=4 };
 /// Number of stop bits for ftdi_set_line_property()
@@ -266,6 +266,7 @@ extern "C" {
     // "eeprom" needs to be valid 128 byte eeprom (generated by the eeprom generator)
     // the checksum of the eeprom is valided
     int ftdi_read_eeprom(struct ftdi_context *ftdi, unsigned char *eeprom);
+    int ftdi_read_chipid(struct ftdi_context *ftdi, unsigned int *chipid);
     int ftdi_write_eeprom(struct ftdi_context *ftdi, unsigned char *eeprom);
     int ftdi_erase_eeprom(struct ftdi_context *ftdi);