/[pcsclite]/trunk/Drivers/ccid/src/ccid_usb.c
ViewVC logotype

Contents of /trunk/Drivers/ccid/src/ccid_usb.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2359 - (hide annotations) (download)
Sat Jan 27 13:31:33 2007 UTC (6 years, 4 months ago) by rousseau
File MIME type: text/plain
File size: 22563 byte(s)
Bogus_firmwares[]: the driver now contains patches to circumvent the
Oz776 reader. It is then declared bogus only if O2MICRO_OZ776_PATCH is
not defined
1 rousseau 269 /*
2     ccid_usb.c: USB access routines using the libusb library
3 rousseau 649 Copyright (C) 2003-2004 Ludovic Rousseau
4 rousseau 269
5 rousseau 1399 This library is free software; you can redistribute it and/or
6     modify it under the terms of the GNU Lesser General Public
7     License as published by the Free Software Foundation; either
8     version 2.1 of the License, or (at your option) any later version.
9 rousseau 269
10 rousseau 1399 This library is distributed in the hope that it will be useful,
11 rousseau 269 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 rousseau 1399 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13     Lesser General Public License for more details.
14 rousseau 269
15 rousseau 1399 You should have received a copy of the GNU Lesser General Public
16     License along with this library; if not, write to the Free Software
17     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 rousseau 269 */
19    
20     /*
21     * $Id$
22     */
23    
24     #define __CCID_USB__
25    
26     #include <stdio.h>
27 rousseau 2152 #include <string.h>
28 rousseau 269 #include <errno.h>
29 rousseau 1052 # ifdef S_SPLINT_S
30     # include <sys/types.h>
31     # endif
32 rousseau 269 #include <usb.h>
33    
34 rousseau 2014 #include "misc.h"
35 rousseau 878 #include "ccid.h"
36 rousseau 269 #include "config.h"
37     #include "debug.h"
38 rousseau 878 #include "defs.h"
39 rousseau 269 #include "utils.h"
40     #include "parser.h"
41 rousseau 878 #include "ccid_ifdhandler.h"
42 rousseau 269
43    
44 rousseau 570 /* write timeout
45     * we don't have to wait a long time since the card was doing nothing */
46     #define USB_WRITE_TIMEOUT (5 * 1000) /* 5 seconds timeout */
47    
48 rousseau 762 /*
49     * Proprietary USB Class (0xFF) are (or are not) accepted
50     * A proprietary class is used for devices released before the final CCID
51     * specifications were ready.
52     * We should not have problems with non CCID devices becasue the
53     * Manufacturer and Product ID are also used to identify the device */
54     #define ALLOW_PROPRIETARY_CLASS
55 rousseau 570
56 rousseau 269 #define BUS_DEVICE_STRSIZE 32
57    
58     typedef struct
59     {
60     usb_dev_handle *handle;
61 rousseau 2294 char *dirname;
62     char *filename;
63 rousseau 1327 int interface;
64 rousseau 269
65     /*
66     * Endpoints
67     */
68     int bulk_in;
69     int bulk_out;
70 rousseau 406
71 rousseau 1791 /* Number of slots using the same device */
72     int real_nb_opened_slots;
73     int *nb_opened_slots;
74    
75 rousseau 406 /*
76     * CCID infos common to USB and serial
77     */
78     _ccid_descriptor ccid;
79    
80 rousseau 269 } _usbDevice;
81    
82 rousseau 406 /* The _usbDevice structure must be defined before including ccid_usb.h */
83 rousseau 269 #include "ccid_usb.h"
84    
85 rousseau 878 static int get_end_points(struct usb_device *dev, _usbDevice *usb_device);
86 rousseau 1287 int ccid_check_firmware(struct usb_device *dev);
87 rousseau 2293 static unsigned int *get_data_rates(unsigned int reader_index,
88     struct usb_device *dev);
89 rousseau 878
90 rousseau 892 /* ne need to initialize to 0 since it is static */
91 rousseau 1077 static _usbDevice usbDevice[CCID_DRIVER_MAX_READERS];
92 rousseau 269
93     #define PCSCLITE_MANUKEY_NAME "ifdVendorID"
94     #define PCSCLITE_PRODKEY_NAME "ifdProductID"
95     #define PCSCLITE_NAMEKEY_NAME "ifdFriendlyName"
96    
97 rousseau 1287 struct _bogus_firmware
98     {
99     int vendor; /* idVendor */
100     int product; /* idProduct */
101     int firmware; /* bcdDevice: previous firmwares have bugs */
102     };
103 rousseau 649
104 rousseau 1287 static struct _bogus_firmware Bogus_firmwares[] = {
105 rousseau 2359 #ifndef O2MICRO_OZ776_PATCH
106 rousseau 2107 { 0x0b97, 0x7762, 0x0111 }, /* Oz776S */ /* the firmware version is not correct since I do not have received a working reader yet */
107 rousseau 2359 #endif
108 rousseau 1312 { 0x04e6, 0xe001, 0x0516 }, /* SCR 331 */
109     { 0x04e6, 0x5111, 0x0620 }, /* SCR 331-DI */
110 rousseau 1287 { 0x04e6, 0x5115, 0x0514 }, /* SCR 335 */
111 rousseau 2048 { 0x04e6, 0xe003, 0x0510 }, /* SPR 532 */
112 rousseau 1325 { 0x0D46, 0x3001, 0x0037 }, /* KAAN Base */
113     { 0x0D46, 0x3002, 0x0037 }, /* KAAN Advanced */
114 rousseau 1875 { 0x09C3, 0x0008, 0x0203 }, /* ActivCard V2 */
115 rousseau 2002 { 0x0DC3, 0x1004, 0x0502 }, /* ASE IIIe USBv2 */
116     { 0x0DC3, 0x1102, 0x0607 }, /* ASE IIIe KB USB */
117 rousseau 2154 { 0x058F, 0x9520, 0x0102 }, /* Alcor AU9520-G */
118 rousseau 1287 };
119    
120 rousseau 1808 /* data rates supported by the secondary slots on the GemCore Pos Pro & SIM Pro */
121     unsigned int SerialCustomDataRates[] = { GEMPLUS_CUSTOM_DATA_RATES, 0 };
122 rousseau 1287
123 rousseau 1808
124 rousseau 269 /*****************************************************************************
125     *
126     * OpenUSB
127     *
128     ****************************************************************************/
129 rousseau 1106 status_t OpenUSB(unsigned int reader_index, /*@unused@*/ int Channel)
130 rousseau 269 {
131 rousseau 1106 return OpenUSBByName(reader_index, NULL);
132 rousseau 649 } /* OpenUSB */
133    
134    
135     /*****************************************************************************
136     *
137     * OpenUSBByName
138     *
139     ****************************************************************************/
140 rousseau 1106 status_t OpenUSBByName(unsigned int reader_index, /*@null@*/ char *device)
141 rousseau 649 {
142 rousseau 269 static struct usb_bus *busses = NULL;
143     int alias = 0;
144     struct usb_bus *bus;
145     struct usb_dev_handle *dev_handle;
146     char keyValue[TOKEN_MAX_VALUE_SIZE];
147 rousseau 1569 unsigned int vendorID, productID;
148 rousseau 301 char infofile[FILENAME_MAX];
149 rousseau 892 unsigned int device_vendor, device_product;
150 rousseau 781 char *dirname = NULL, *filename = NULL;
151 rousseau 1151 static int previous_reader_index = -1;
152 rousseau 269
153 rousseau 1106 DEBUG_COMM3("Reader index: %X, Device: %s", reader_index, device);
154 rousseau 269
155 rousseau 662 /* device name specified */
156     if (device)
157     {
158 rousseau 781 /* format: usb:%04x/%04x, vendor, product */
159 rousseau 662 if (strncmp("usb:", device, 4) != 0)
160     {
161     DEBUG_CRITICAL2("device name does not start with \"usb:\": %s",
162     device);
163     return STATUS_UNSUCCESSFUL;
164     }
165    
166     if (sscanf(device, "usb:%x/%x", &device_vendor, &device_product) != 2)
167     {
168     DEBUG_CRITICAL2("device name can't be parsed: %s", device);
169     return STATUS_UNSUCCESSFUL;
170     }
171 rousseau 781
172     /* format usb:%04x/%04x:libusb:%s
173     * with %s set to %s:%s, dirname, filename */
174     if ((dirname = strstr(device, "libusb:")) != NULL)
175     {
176     /* dirname points to the first char after libusb: */
177     dirname += strlen("libusb:");
178    
179     /* search the : (separation) char */
180     filename = strchr(dirname, ':');
181    
182     if (filename)
183     {
184     /* end the dirname string */
185     *filename = '\0';
186    
187     /* filename points to the first char after : */
188     filename++;
189     }
190     else
191     {
192     /* parse failed */
193     dirname = NULL;
194    
195     DEBUG_CRITICAL2("can't parse using libusb scheme: %s", device);
196     }
197     }
198 rousseau 662 }
199    
200 rousseau 269 if (busses == NULL)
201     usb_init();
202    
203     usb_find_busses();
204     usb_find_devices();
205    
206     busses = usb_get_busses();
207    
208     if (busses == NULL)
209     {
210     DEBUG_CRITICAL("No USB busses found");
211     return STATUS_UNSUCCESSFUL;
212     }
213    
214 rousseau 1106 /* is the reader_index already used? */
215     if (usbDevice[reader_index].handle != NULL)
216 rousseau 269 {
217 rousseau 1106 DEBUG_CRITICAL2("USB driver with index %X already in use",
218     reader_index);
219 rousseau 269 return STATUS_UNSUCCESSFUL;
220     }
221    
222 rousseau 301 /* Info.plist full patch filename */
223 rousseau 406 snprintf(infofile, sizeof(infofile), "%s/%s/Contents/Info.plist",
224     PCSCLITE_HP_DROPDIR, BUNDLE);
225 rousseau 301
226 rousseau 269 /* general driver info */
227 rousseau 301 if (!LTPBundleFindValueWithKey(infofile, "ifdManufacturerString", keyValue, 0))
228 rousseau 774 {
229 rousseau 1792 DEBUG_INFO2("Manufacturer: %s", keyValue);
230 rousseau 774 }
231 rousseau 269 else
232     {
233 rousseau 1792 DEBUG_INFO2("LTPBundleFindValueWithKey error. Can't find %s?",
234 rousseau 301 infofile);
235 rousseau 269 return STATUS_UNSUCCESSFUL;
236     }
237 rousseau 301 if (!LTPBundleFindValueWithKey(infofile, "ifdProductString", keyValue, 0))
238 rousseau 774 {
239 rousseau 1792 DEBUG_INFO2("ProductString: %s", keyValue);
240 rousseau 774 }
241 rousseau 269 else
242     return STATUS_UNSUCCESSFUL;
243 rousseau 301 if (!LTPBundleFindValueWithKey(infofile, "Copyright", keyValue, 0))
244 rousseau 774 {
245 rousseau 1792 DEBUG_INFO2("Copyright: %s", keyValue);
246 rousseau 774 }
247 rousseau 269 else
248     return STATUS_UNSUCCESSFUL;
249     vendorID = strlen(keyValue);
250 rousseau 2083 alias = 0x1C;
251 rousseau 269 for (; vendorID--;)
252     alias ^= keyValue[vendorID];
253    
254     /* for any supported reader */
255 rousseau 301 while (LTPBundleFindValueWithKey(infofile, PCSCLITE_MANUKEY_NAME, keyValue, alias) == 0)
256 rousseau 269 {
257 rousseau 1079 vendorID = strtoul(keyValue, NULL, 0);
258 rousseau 269
259 rousseau 301 if (LTPBundleFindValueWithKey(infofile, PCSCLITE_PRODKEY_NAME, keyValue, alias))
260 rousseau 269 goto end;
261 rousseau 1079 productID = strtoul(keyValue, NULL, 0);
262 rousseau 269
263 rousseau 301 if (LTPBundleFindValueWithKey(infofile, PCSCLITE_NAMEKEY_NAME, keyValue, alias))
264 rousseau 269 goto end;
265    
266 rousseau 662 /* go to next supported reader for next round */
267     alias++;
268    
269     /* the device was specified but is not the one we are trying to find */
270     if (device
271     && (vendorID != device_vendor || productID != device_product))
272     continue;
273    
274 rousseau 269 /* on any USB buses */
275     for (bus = busses; bus; bus = bus->next)
276     {
277     struct usb_device *dev;
278    
279     /* any device on this bus */
280     for (dev = bus->devices; dev; dev = dev->next)
281     {
282 rousseau 781 /* device defined by name? */
283     if (dirname && (strcmp(dirname, bus->dirname)
284     || strcmp(filename, dev->filename)))
285     continue;
286    
287 rousseau 269 if (dev->descriptor.idVendor == vendorID
288     && dev->descriptor.idProduct == productID)
289     {
290     int r, already_used;
291 rousseau 662 struct usb_interface *usb_interface = NULL;
292     int interface;
293 rousseau 269
294     /* is it already opened? */
295     already_used = FALSE;
296 rousseau 649
297 rousseau 2295 DEBUG_COMM3("Checking device: %s/%s",
298     bus->dirname, dev->filename);
299 rousseau 1077 for (r=0; r<CCID_DRIVER_MAX_READERS; r++)
300 rousseau 269 {
301 rousseau 2294 if (usbDevice[r].handle)
302 rousseau 269 {
303 rousseau 662 /* same busname, same filename */
304 rousseau 2294 if (strcmp(usbDevice[r].dirname, bus->dirname) == 0 && strcmp(usbDevice[r].filename, dev->filename) == 0)
305 rousseau 662 already_used = TRUE;
306 rousseau 269 }
307     }
308    
309 rousseau 662 /* this reader is already managed by us */
310     if (already_used)
311 rousseau 269 {
312 rousseau 1151 if ((previous_reader_index != -1)
313 rousseau 2294 && usbDevice[previous_reader_index].handle
314     && (strcmp(usbDevice[previous_reader_index].dirname, bus->dirname) == 0)
315     && (strcmp(usbDevice[previous_reader_index].filename, dev->filename) == 0)
316 rousseau 1151 && usbDevice[previous_reader_index].ccid.bCurrentSlotIndex < usbDevice[previous_reader_index].ccid.bMaxSlotIndex)
317     {
318     /* we reuse the same device
319     * and the reader is multi-slot */
320     usbDevice[reader_index] = usbDevice[previous_reader_index];
321 rousseau 1808 /* the other slots do not have the same data rates */
322     if ((GEMCOREPOSPRO == usbDevice[reader_index].ccid.readerID)
323     || (GEMCORESIMPRO == usbDevice[reader_index].ccid.readerID))
324     {
325     usbDevice[reader_index].ccid.arrayOfSupportedDataRates = SerialCustomDataRates;
326     usbDevice[reader_index].ccid.dwMaxDataRate = 125000;
327     }
328    
329 rousseau 1791 *usbDevice[reader_index].nb_opened_slots += 1;
330 rousseau 1151 usbDevice[reader_index].ccid.bCurrentSlotIndex++;
331     DEBUG_INFO2("Opening slot: %d",
332     usbDevice[reader_index].ccid.bCurrentSlotIndex);
333     goto end;
334     }
335     else
336     {
337     DEBUG_INFO3("USB device %s/%s already in use."
338     " Checking next one.",
339     bus->dirname, dev->filename);
340     }
341 rousseau 301
342 rousseau 662 continue;
343     }
344 rousseau 269
345 rousseau 662 DEBUG_COMM3("Trying to open USB bus/device: %s/%s",
346     bus->dirname, dev->filename);
347 rousseau 269
348 rousseau 662 dev_handle = usb_open(dev);
349     if (dev_handle == NULL)
350     {
351     DEBUG_CRITICAL4("Can't usb_open(%s/%s): %s",
352     bus->dirname, dev->filename, strerror(errno));
353 rousseau 650
354 rousseau 662 continue;
355     }
356 rousseau 579
357 rousseau 662 /* now we found a free reader and we try to use it */
358     if (dev->config == NULL)
359     {
360 rousseau 1585 usb_close(dev_handle);
361 rousseau 662 DEBUG_CRITICAL3("No dev->config found for %s/%s",
362     bus->dirname, dev->filename);
363     return STATUS_UNSUCCESSFUL;
364     }
365 rousseau 269
366 rousseau 662 usb_interface = get_ccid_usb_interface(dev);
367     if (usb_interface == NULL)
368     {
369 rousseau 1585 usb_close(dev_handle);
370 rousseau 662 DEBUG_CRITICAL3("Can't find a CCID interface on %s/%s",
371     bus->dirname, dev->filename);
372     return STATUS_UNSUCCESSFUL;
373 rousseau 2152 }
374 rousseau 269
375 rousseau 662 if (usb_interface->altsetting->extralen != 54)
376     {
377 rousseau 1585 usb_close(dev_handle);
378 rousseau 662 DEBUG_CRITICAL4("Extra field for %s/%s has a wrong length: %d", bus->dirname, dev->filename, usb_interface->altsetting->extralen);
379     return STATUS_UNSUCCESSFUL;
380 rousseau 269 }
381 rousseau 662
382     interface = usb_interface->altsetting->bInterfaceNumber;
383     if (usb_claim_interface(dev_handle, interface) < 0)
384 rousseau 269 {
385 rousseau 1585 usb_close(dev_handle);
386 rousseau 662 DEBUG_CRITICAL4("Can't claim interface %s/%s: %s",
387     bus->dirname, dev->filename, strerror(errno));
388     return STATUS_UNSUCCESSFUL;
389 rousseau 269 }
390 rousseau 662
391     DEBUG_INFO4("Found Vendor/Product: %04X/%04X (%s)",
392     dev->descriptor.idVendor,
393     dev->descriptor.idProduct, keyValue);
394     DEBUG_INFO3("Using USB bus/device: %s/%s",
395     bus->dirname, dev->filename);
396    
397 rousseau 1287 /* check for firmware bugs */
398     if (ccid_check_firmware(dev))
399 rousseau 1585 {
400     usb_close(dev_handle);
401 rousseau 1287 return STATUS_UNSUCCESSFUL;
402 rousseau 1585 }
403 rousseau 1287
404 rousseau 662 /* Get Endpoints values*/
405 rousseau 1106 get_end_points(dev, &usbDevice[reader_index]);
406 rousseau 662
407     /* store device information */
408 rousseau 1106 usbDevice[reader_index].handle = dev_handle;
409 rousseau 2294 usbDevice[reader_index].dirname = strdup(bus->dirname);
410     usbDevice[reader_index].filename = strdup(dev->filename);
411 rousseau 1327 usbDevice[reader_index].interface = interface;
412 rousseau 1791 usbDevice[reader_index].real_nb_opened_slots = 1;
413     usbDevice[reader_index].nb_opened_slots = &usbDevice[reader_index].real_nb_opened_slots;
414 rousseau 662
415     /* CCID common informations */
416 rousseau 1149 usbDevice[reader_index].ccid.real_bSeq = 0;
417     usbDevice[reader_index].ccid.pbSeq = &usbDevice[reader_index].ccid.real_bSeq;
418 rousseau 1106 usbDevice[reader_index].ccid.readerID =
419 rousseau 662 (dev->descriptor.idVendor << 16) +
420     dev->descriptor.idProduct;
421 rousseau 1106 usbDevice[reader_index].ccid.dwFeatures = dw2i(usb_interface->altsetting->extra, 40);
422     usbDevice[reader_index].ccid.bPINSupport = usb_interface->altsetting->extra[52];
423     usbDevice[reader_index].ccid.dwMaxCCIDMessageLength = dw2i(usb_interface->altsetting->extra, 44);
424     usbDevice[reader_index].ccid.dwMaxIFSD = dw2i(usb_interface->altsetting->extra, 28);
425     usbDevice[reader_index].ccid.dwDefaultClock = dw2i(usb_interface->altsetting->extra, 10);
426 rousseau 1485 usbDevice[reader_index].ccid.dwMaxDataRate = dw2i(usb_interface->altsetting->extra, 23);
427 rousseau 1106 usbDevice[reader_index].ccid.bMaxSlotIndex = usb_interface->altsetting->extra[4];
428     usbDevice[reader_index].ccid.bCurrentSlotIndex = 0;
429 rousseau 1453 usbDevice[reader_index].ccid.readTimeout = DEFAULT_COM_READ_TIMEOUT;
430 rousseau 2293 usbDevice[reader_index].ccid.arrayOfSupportedDataRates = get_data_rates(reader_index, dev);
431 rousseau 662 goto end;
432 rousseau 269 }
433     }
434     }
435     }
436     end:
437 rousseau 1106 if (usbDevice[reader_index].handle == NULL)
438 rousseau 269 return STATUS_UNSUCCESSFUL;
439    
440 rousseau 1151 /* memorise the current reader_index so we can detect
441     * a new OpenUSBByName on a multi slot reader */
442     previous_reader_index = reader_index;
443    
444 rousseau 269 return STATUS_SUCCESS;
445 rousseau 649 } /* OpenUSBByName */
446 rousseau 269
447    
448     /*****************************************************************************
449     *
450     * WriteUSB
451     *
452     ****************************************************************************/
453 rousseau 1106 status_t WriteUSB(unsigned int reader_index, unsigned int length,
454     unsigned char *buffer)
455 rousseau 269 {
456     int rv;
457     char debug_header[] = "-> 121234 ";
458    
459 rousseau 1106 sprintf(debug_header, "-> %06X ", (int)reader_index);
460 rousseau 269
461     DEBUG_XXD(debug_header, buffer, length);
462    
463 rousseau 1106 rv = usb_bulk_write(usbDevice[reader_index].handle,
464     usbDevice[reader_index].bulk_out, (char *)buffer, length,
465     USB_WRITE_TIMEOUT);
466 rousseau 269
467     if (rv < 0)
468     {
469 rousseau 2294 DEBUG_CRITICAL4("usb_bulk_write(%s/%s): %s",
470     usbDevice[reader_index].dirname, usbDevice[reader_index].filename,
471     strerror(errno));
472 rousseau 1547
473 rousseau 2206 if (ENODEV == errno)
474     return STATUS_NO_SUCH_DEVICE;
475    
476 rousseau 269 return STATUS_UNSUCCESSFUL;
477     }
478    
479     return STATUS_SUCCESS;
480     } /* WriteUSB */
481    
482    
483     /*****************************************************************************
484     *
485     * ReadUSB
486     *
487     ****************************************************************************/
488 rousseau 1106 status_t ReadUSB(unsigned int reader_index, unsigned int * length,
489     unsigned char *buffer)
490 rousseau 269 {
491     int rv;
492     char debug_header[] = "<- 121234 ";
493 rousseau 2083 _ccid_descriptor *ccid_descriptor = get_ccid_descriptor(reader_index);
494 rousseau 269
495 rousseau 2083 read_again:
496 rousseau 1106 sprintf(debug_header, "<- %06X ", (int)reader_index);
497 rousseau 269
498 rousseau 1106 rv = usb_bulk_read(usbDevice[reader_index].handle,
499     usbDevice[reader_index].bulk_in, (char *)buffer, *length,
500 rousseau 1453 usbDevice[reader_index].ccid.readTimeout * 1000);
501 rousseau 269
502     if (rv < 0)
503     {
504 rousseau 895 *length = 0;
505 rousseau 2294 DEBUG_CRITICAL4("usb_bulk_read(%s/%s): %s",
506     usbDevice[reader_index].dirname, usbDevice[reader_index].filename,
507     strerror(errno));
508 rousseau 2119
509 rousseau 2206 if (ENODEV == errno)
510     return STATUS_NO_SUCH_DEVICE;
511    
512 rousseau 269 return STATUS_UNSUCCESSFUL;
513     }
514    
515 rousseau 895 *length = rv;
516    
517 rousseau 269 DEBUG_XXD(debug_header, buffer, *length);
518    
519 rousseau 2083 #define BSEQ_OFFSET 6
520 rousseau 2097 if ((*length >= BSEQ_OFFSET)
521     && (buffer[BSEQ_OFFSET] < *ccid_descriptor->pbSeq -1))
522 rousseau 2083 {
523     DEBUG_INFO("Duplicate frame detected");
524     goto read_again;
525     }
526    
527 rousseau 269 return STATUS_SUCCESS;
528     } /* ReadUSB */
529    
530    
531     /*****************************************************************************
532     *
533     * CloseUSB
534     *
535     ****************************************************************************/
536 rousseau 1106 status_t CloseUSB(unsigned int reader_index)
537 rousseau 269 {
538     /* device not opened */
539 rousseau 2294 if (usbDevice[reader_index].handle == NULL)
540 rousseau 269 return STATUS_UNSUCCESSFUL;
541    
542 rousseau 662 DEBUG_COMM3("Closing USB device: %s/%s",
543 rousseau 2294 usbDevice[reader_index].dirname,
544     usbDevice[reader_index].filename);
545 rousseau 269
546 rousseau 1807 if (usbDevice[reader_index].ccid.arrayOfSupportedDataRates
547     && (usbDevice[reader_index].ccid.bCurrentSlotIndex == 0))
548     {
549     free(usbDevice[reader_index].ccid.arrayOfSupportedDataRates);
550     usbDevice[reader_index].ccid.arrayOfSupportedDataRates = NULL;
551     }
552    
553 rousseau 1791 /* one slot closed */
554     (*usbDevice[reader_index].nb_opened_slots)--;
555 rousseau 1446
556 rousseau 1791 /* release the allocated ressources for the last slot only */
557     if (0 == *usbDevice[reader_index].nb_opened_slots)
558     {
559     DEBUG_COMM("Last slot closed. Release resources");
560 rousseau 892
561 rousseau 1791 /* reset so that bSeq starts at 0 again */
562     if (DriverOptions & DRIVER_OPTION_RESET_ON_CLOSE)
563     usb_reset(usbDevice[reader_index].handle);
564    
565     usb_release_interface(usbDevice[reader_index].handle,
566     usbDevice[reader_index].interface);
567     usb_close(usbDevice[reader_index].handle);
568 rousseau 2296
569     free(usbDevice[reader_index].dirname);
570     free(usbDevice[reader_index].filename);
571 rousseau 1791 }
572    
573 rousseau 269 /* mark the resource unused */
574 rousseau 1106 usbDevice[reader_index].handle = NULL;
575 rousseau 2294 usbDevice[reader_index].dirname = NULL;
576     usbDevice[reader_index].filename = NULL;
577 rousseau 1327 usbDevice[reader_index].interface = 0;
578 rousseau 269
579     return STATUS_SUCCESS;
580     } /* CloseUSB */
581    
582    
583 rousseau 301 /*****************************************************************************
584     *
585 rousseau 406 * get_ccid_descriptor
586 rousseau 301 *
587     ****************************************************************************/
588 rousseau 1106 _ccid_descriptor *get_ccid_descriptor(unsigned int reader_index)
589 rousseau 269 {
590 rousseau 1106 return &usbDevice[reader_index].ccid;
591 rousseau 406 } /* get_ccid_descriptor */
592 rousseau 269
593    
594 rousseau 301 /*****************************************************************************
595     *
596     * get_end_points
597     *
598     ****************************************************************************/
599 rousseau 878 static int get_end_points(struct usb_device *dev, _usbDevice *usb_device)
600 rousseau 269 {
601     int i;
602     int bEndpointAddress;
603 rousseau 650 struct usb_interface *usb_interface = get_ccid_usb_interface(dev);
604 rousseau 2152
605 rousseau 269 /*
606     * 3 Endpoints maximum: Interrupt In, Bulk In, Bulk Out
607     */
608     for (i=0; i<3; i++)
609     {
610 rousseau 650 if (usb_interface->altsetting->endpoint[i].bmAttributes != USB_ENDPOINT_TYPE_BULK)
611 rousseau 269 continue;
612    
613 rousseau 650 bEndpointAddress = usb_interface->altsetting->endpoint[i].bEndpointAddress;
614 rousseau 269
615     if ((bEndpointAddress & USB_ENDPOINT_DIR_MASK) == USB_ENDPOINT_IN)
616     usb_device->bulk_in = bEndpointAddress;
617    
618     if ((bEndpointAddress & USB_ENDPOINT_DIR_MASK) == USB_ENDPOINT_OUT)
619     usb_device->bulk_out = bEndpointAddress;
620     }
621    
622     return 0;
623     } /* get_end_points */
624    
625 rousseau 650
626     /*****************************************************************************
627     *
628     * get_ccid_usb_interface
629     *
630     ****************************************************************************/
631 rousseau 2014 /*@null@*/ EXTERNAL struct usb_interface * get_ccid_usb_interface(struct usb_device *dev)
632 rousseau 650 {
633 rousseau 2152 struct usb_interface *usb_interface = NULL;
634 rousseau 1818 int i;
635 rousseau 650
636     /* if multiple interfaces use the first one with CCID class type */
637 rousseau 1818 for (i=0; i<dev->config->bNumInterfaces; i++)
638 rousseau 650 {
639 rousseau 1818 /* CCID Class? */
640     if (dev->config->interface[i].altsetting->bInterfaceClass == 0xb
641 rousseau 738 #ifdef ALLOW_PROPRIETARY_CLASS
642 rousseau 1818 || dev->config->interface[i].altsetting->bInterfaceClass == 0xff
643 rousseau 738 #endif
644 rousseau 1818 )
645     {
646     usb_interface = &dev->config->interface[i];
647     break;
648 rousseau 650 }
649     }
650    
651 rousseau 1256 #ifdef O2MICRO_OZ776_PATCH
652     if (usb_interface != NULL
653     && (OZ776 == (dev->descriptor.idVendor << 16)
654     + dev->descriptor.idProduct)
655     && (0 == usb_interface->altsetting->extralen)) /* this is the bug */
656     {
657     for (i=0; i<usb_interface->altsetting->bNumEndpoints; i++)
658     {
659     /* find the extra[] array */
660     if (54 == usb_interface->altsetting->endpoint[i].extralen)
661     {
662     /* get the extra[] from the endpoint */
663     usb_interface->altsetting->extralen = 54;
664     usb_interface->altsetting->extra =
665     usb_interface->altsetting->endpoint[i].extra;
666     break;
667     }
668     }
669     }
670     #endif
671    
672 rousseau 650 return usb_interface;
673     } /* get_ccid_usb_interface */
674    
675 rousseau 1287
676     /*****************************************************************************
677     *
678     * ccid_check_firmware
679     *
680     ****************************************************************************/
681     int ccid_check_firmware(struct usb_device *dev)
682     {
683     int i;
684    
685     for (i=0; i<sizeof(Bogus_firmwares)/sizeof(Bogus_firmwares[0]); i++)
686     {
687     if (dev->descriptor.idVendor != Bogus_firmwares[i].vendor)
688     continue;
689    
690     if (dev->descriptor.idProduct != Bogus_firmwares[i].product)
691     continue;
692    
693     /* firmware too old and buggy */
694     if (dev->descriptor.bcdDevice < Bogus_firmwares[i].firmware)
695     {
696     if (DriverOptions & DRIVER_OPTION_USE_BOGUS_FIRMWARE)
697     {
698     DEBUG_INFO3("Firmware (%X.%02X) is bogus! but you choosed to use it",
699     dev->descriptor.bcdDevice >> 8,
700     dev->descriptor.bcdDevice & 0xFF);
701     return FALSE;
702     }
703     else
704     {
705     DEBUG_CRITICAL3("Firmware (%X.%02X) is bogus! Upgrade the reader firmware or get a new reader.",
706     dev->descriptor.bcdDevice >> 8,
707     dev->descriptor.bcdDevice & 0xFF);
708     return TRUE;
709     }
710     }
711     }
712    
713     /* by default the firmware is not bogus */
714     return FALSE;
715     } /* ccid_check_firmware */
716    
717 rousseau 1446 /*****************************************************************************
718     *
719     * get_data_rates
720     *
721     ****************************************************************************/
722 rousseau 2293 static unsigned int *get_data_rates(unsigned int reader_index,
723     struct usb_device *dev)
724 rousseau 1446 {
725 rousseau 1608 int n, i, len;
726 rousseau 1446 unsigned char buffer[256*sizeof(int)]; /* maximum is 256 records */
727     unsigned int *int_array;
728    
729     /* See CCID 3.7.3 page 25 */
730     n = usb_control_msg(usbDevice[reader_index].handle,
731     0xA1, /* request type */
732     0x03, /* GET_DATA_RATES */
733     0x00, /* value */
734 rousseau 1467 usbDevice[reader_index].interface, /* interface */
735 rousseau 1460 (char *)buffer,
736 rousseau 1446 sizeof(buffer),
737 rousseau 1453 usbDevice[reader_index].ccid.readTimeout * 1000);
738 rousseau 1446
739 rousseau 1486 /* we got an error? */
740     if (n <= 0)
741 rousseau 1446 {
742 rousseau 1486 DEBUG_INFO2("IFD does not support GET_DATA_RATES request: %s",
743     strerror(errno));
744     return NULL;
745     }
746 rousseau 1476
747 rousseau 1486 /* we got a strange value */
748     if (n % 4)
749     {
750     DEBUG_INFO2("Wrong GET DATA RATES size: %d", n);
751     return NULL;
752 rousseau 1446 }
753    
754     /* allocate the buffer (including the end marker) */
755     n /= sizeof(int);
756 rousseau 1608
757     /* we do not get the expected number of data rates */
758 rousseau 2293 len = get_ccid_usb_interface(dev)->altsetting->extra[27]; /* bNumDataRatesSupported */
759 rousseau 1641 if ((n != len) && len)
760 rousseau 1608 {
761     DEBUG_INFO3("Got %d data rates but was expecting %d", n, len);
762    
763     /* we got more data than expected */
764     if (n > len)
765     n = len;
766     }
767    
768 rousseau 1446 int_array = calloc(n+1, sizeof(int));
769 rousseau 1475 if (NULL == int_array)
770 rousseau 1446 {
771     DEBUG_CRITICAL("Memory allocation failed");
772     return NULL;
773     }
774    
775     /* convert in correct endianess */
776     for (i=0; i<n; i++)
777     {
778     int_array[i] = dw2i(buffer, i*4);
779     DEBUG_INFO2("declared: %d bps", int_array[i]);
780     }
781    
782     /* end of array marker */
783     int_array[i] = 0;
784    
785     return int_array;
786     }
787    

Properties

Name Value
svn:eol-style native
svn:keywords Author Date Id Revision

  ViewVC Help
Powered by ViewVC 1.1.5