00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00026 #ifdef HAVE_CONFIG_H
00027 # include "config.h"
00028 #endif // HAVE_CONFIG_H
00029
00030
00031
00032
00033
00034 #include <stdio.h>
00035 #include <stdlib.h>
00036 #include <usb.h>
00037 #include <string.h>
00038
00039 #include "../drivers.h"
00040 #include "../chips/pn53x.h"
00041
00042 #include <nfc/nfc.h>
00043 #include <nfc/nfc-messages.h>
00044
00045 #define BUFFER_LENGTH 256
00046 #define USB_TIMEOUT 30000
00047
00048
00049 void
00050 get_end_points (struct usb_device *dev, usb_spec_t * pus)
00051 {
00052 uint32_t uiIndex;
00053 uint32_t uiEndPoint;
00054 struct usb_interface_descriptor *puid = dev->config->interface->altsetting;
00055
00056
00057 for (uiIndex = 0; uiIndex < puid->bNumEndpoints; uiIndex++) {
00058
00059 if (puid->endpoint[uiIndex].bmAttributes != USB_ENDPOINT_TYPE_BULK)
00060 continue;
00061
00062
00063 uiEndPoint = puid->endpoint[uiIndex].bEndpointAddress;
00064
00065
00066 if ((uiEndPoint & USB_ENDPOINT_DIR_MASK) == USB_ENDPOINT_IN) {
00067 pus->uiEndPointIn = uiEndPoint;
00068 }
00069
00070 if ((uiEndPoint & USB_ENDPOINT_DIR_MASK) == USB_ENDPOINT_OUT) {
00071 pus->uiEndPointOut = uiEndPoint;
00072 }
00073 }
00074 }
00075
00076 bool
00077 pn53x_usb_list_devices (nfc_device_desc_t pnddDevices[], size_t szDevices, size_t * pszDeviceFound,
00078 usb_candidate_t candidates[], int num_candidates, char *target_name)
00079 {
00080 int ret,
00081 i;
00082
00083 struct usb_bus *bus;
00084 struct usb_device *dev;
00085 usb_dev_handle *udev;
00086 uint32_t uiBusIndex = 0;
00087 char string[256];
00088
00089 string[0] = '\0';
00090 usb_init ();
00091
00092
00093 if ((ret = usb_find_busses () < 0))
00094 return false;
00095
00096 if ((ret = usb_find_devices () < 0))
00097 return false;
00098
00099 *pszDeviceFound = 0;
00100
00101 for (bus = usb_get_busses (); bus; bus = bus->next) {
00102 for (dev = bus->devices; dev; dev = dev->next, uiBusIndex++) {
00103 for (i = 0; i < num_candidates; ++i) {
00104
00105 if (candidates[i].idVendor == dev->descriptor.idVendor && candidates[i].idProduct == dev->descriptor.idProduct) {
00106
00107
00108 if (dev->config == NULL || dev->config->interface == NULL || dev->config->interface->altsetting == NULL) {
00109
00110 continue;
00111 }
00112 if (dev->config->interface->altsetting->bNumEndpoints < 2) {
00113
00114 continue;
00115 }
00116 if (dev->descriptor.iManufacturer || dev->descriptor.iProduct) {
00117 udev = usb_open (dev);
00118 if (udev) {
00119 usb_get_string_simple (udev, dev->descriptor.iManufacturer, string, sizeof (string));
00120 if (strlen (string) > 0)
00121 strcpy (string + strlen (string), " / ");
00122 usb_get_string_simple (udev, dev->descriptor.iProduct, string + strlen (string),
00123 sizeof (string) - strlen (string));
00124 }
00125 usb_close (udev);
00126 }
00127 if (strlen (string) == 0)
00128 strcpy (pnddDevices[*pszDeviceFound].acDevice, target_name);
00129 else
00130 strcpy (pnddDevices[*pszDeviceFound].acDevice, string);
00131 pnddDevices[*pszDeviceFound].pcDriver = target_name;
00132 pnddDevices[*pszDeviceFound].uiBusIndex = uiBusIndex;
00133 (*pszDeviceFound)++;
00134
00135 if ((*pszDeviceFound) == szDevices) {
00136 return true;
00137 }
00138 }
00139 }
00140 }
00141 }
00142 if (*pszDeviceFound)
00143 return true;
00144 return false;
00145 }
00146
00147 nfc_device_t *
00148 pn53x_usb_connect (const nfc_device_desc_t * pndd, const char *target_name, int target_chip)
00149 {
00150 nfc_device_t *pnd = NULL;
00151 usb_spec_t *pus;
00152 usb_spec_t us;
00153 struct usb_bus *bus;
00154 struct usb_device *dev;
00155 uint32_t uiBusIndex;
00156
00157 us.uiEndPointIn = 0;
00158 us.uiEndPointOut = 0;
00159 us.pudh = NULL;
00160
00161 DBG ("Attempt to connect to %s device", target_name);
00162 usb_init ();
00163
00164 uiBusIndex = pndd->uiBusIndex;
00165
00166 for (bus = usb_get_busses (); bus; bus = bus->next) {
00167 for (dev = bus->devices; dev; dev = dev->next, uiBusIndex--) {
00168
00169 if (uiBusIndex == 0) {
00170
00171 us.pudh = usb_open (dev);
00172
00173 get_end_points (dev, &us);
00174 if (usb_set_configuration (us.pudh, 1) < 0) {
00175 DBG ("%s", "Setting config failed");
00176 usb_close (us.pudh);
00177
00178 return NULL;
00179 }
00180
00181 if (usb_claim_interface (us.pudh, 0) < 0) {
00182 DBG ("%s", "Can't claim interface");
00183 usb_close (us.pudh);
00184
00185 return NULL;
00186 }
00187
00188 pus = malloc (sizeof (usb_spec_t));
00189 *pus = us;
00190 pnd = malloc (sizeof (nfc_device_t));
00191 strcpy (pnd->acName, target_name);
00192 pnd->nc = target_chip;
00193 pnd->nds = (nfc_device_spec_t) pus;
00194 pnd->bActive = true;
00195 pnd->bCrc = true;
00196 pnd->bPar = true;
00197 pnd->ui8TxBits = 0;
00198 return pnd;
00199 }
00200 }
00201 }
00202
00203 DBG ("%s", "Device index not found!");
00204 return NULL;
00205 }
00206
00207 void
00208 pn53x_usb_disconnect (nfc_device_t * pnd)
00209 {
00210 usb_spec_t *pus = (usb_spec_t *) pnd->nds;
00211 int ret;
00212
00213 if ((ret = usb_release_interface (pus->pudh, 0)) < 0) {
00214 ERR ("usb_release_interface failed (%i)", ret);
00215 }
00216
00217 if ((ret = usb_close (pus->pudh)) < 0) {
00218 ERR ("usb_close failed (%i)", ret);
00219 }
00220
00221
00222
00223
00224
00225 free (pnd->nds);
00226 free (pnd);
00227 }
00228
00229 bool
00230 pn53x_usb_transceive (nfc_device_t * pnd, const byte_t * pbtTx, const size_t szTxLen, byte_t * pbtRx, size_t * pszRxLen)
00231 {
00232 size_t uiPos = 0;
00233 int ret = 0;
00234 byte_t abtTx[BUFFER_LENGTH] = { 0x00, 0x00, 0xff };
00235 byte_t abtRx[BUFFER_LENGTH];
00236 usb_spec_t *pus = (usb_spec_t *) pnd->nds;
00237
00238 uint8_t ack_frame[] = { 0x00, 0x00, 0xff, 0x00, 0xff, 0x00 };
00239
00240
00241 abtTx[3] = szTxLen;
00242
00243 abtTx[4] = 0x0100 - abtTx[3];
00244
00245 memmove (abtTx + 5, pbtTx, szTxLen);
00246
00247
00248 abtTx[szTxLen + 5] = 0;
00249 for (uiPos = 0; uiPos < szTxLen; uiPos++) {
00250 abtTx[szTxLen + 5] -= abtTx[uiPos + 5];
00251 }
00252
00253
00254 abtTx[szTxLen + 6] = 0;
00255
00256 #ifdef DEBUG
00257 PRINT_HEX ("TX", abtTx, szTxLen + 7);
00258 #endif
00259
00260 ret = usb_bulk_write (pus->pudh, pus->uiEndPointOut, (char *) abtTx, szTxLen + 7, USB_TIMEOUT);
00261 if (ret < 0) {
00262 DBG ("usb_bulk_write failed with error %d", ret);
00263 pnd->iLastError = DEIO;
00264 return false;
00265 }
00266
00267 ret = usb_bulk_read (pus->pudh, pus->uiEndPointIn, (char *) abtRx, BUFFER_LENGTH, USB_TIMEOUT);
00268 if (ret < 0) {
00269 DBG ("usb_bulk_read failed with error %d", ret);
00270 pnd->iLastError = DEIO;
00271 return false;
00272 }
00273 #ifdef DEBUG
00274 PRINT_HEX ("RX", abtRx, ret);
00275 #endif
00276
00277 if (!pn53x_transceive_check_ack_frame_callback (pnd, abtRx, ret))
00278 return false;
00279
00280 ret = usb_bulk_read (pus->pudh, pus->uiEndPointIn, (char *) abtRx, BUFFER_LENGTH, USB_TIMEOUT);
00281 if (ret < 0) {
00282 DBG ("usb_bulk_read failed with error %d", ret);
00283 pnd->iLastError = DEIO;
00284 return false;
00285 }
00286 #ifdef DEBUG
00287 PRINT_HEX ("RX", abtRx, ret);
00288 #endif
00289
00290 #ifdef DEBUG
00291 PRINT_HEX ("TX", ack_frame, 6);
00292 #endif
00293 usb_bulk_write (pus->pudh, pus->uiEndPointOut, (char *) ack_frame, 6, USB_TIMEOUT);
00294
00295 if (!pn53x_transceive_check_error_frame_callback (pnd, abtRx, ret))
00296 return false;
00297
00298
00299 if (pbtRx == NULL || pszRxLen == NULL)
00300 return true;
00301
00302
00303 if (ret < 9) {
00304 DBG ("%s", "No data");
00305 pnd->iLastError = DEINVAL;
00306 return false;
00307 }
00308
00309 *pszRxLen = ret - 7 - 2;
00310
00311
00312 if ((abtRx[5] == 0xd5) && (abtRx[6] == 0x07) && (*pszRxLen == 2)) {
00313
00314 *pszRxLen = (*pszRxLen) - 1;
00315 memcpy (pbtRx, abtRx + 8, *pszRxLen);
00316 return true;
00317 }
00318
00319 memcpy (pbtRx, abtRx + 7, *pszRxLen);
00320
00321 return true;
00322 }