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

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

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1561 - (show annotations) (download)
Thu Jun 16 14:06:16 2005 UTC (7 years, 11 months ago) by rousseau
File MIME type: text/plain
File size: 9726 byte(s)
pares bClassGetResponse
1 /*
2 parse.c: parse CCID structure
3 Copyright (C) 2003-2004 Ludovic Rousseau
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 */
19
20 /*
21 * $Id$
22 */
23
24 #include <stdio.h>
25 #include <string.h>
26 # ifdef S_SPLINT_S
27 # include <sys/types.h>
28 # endif
29 #include <usb.h>
30
31 #include <ifdhandler.h>
32 #include "defs.h"
33 #include "ccid_ifdhandler.h"
34 #include "ccid.h"
35
36 #ifndef TRUE
37 #define TRUE 1
38 #define FALSE 0
39 #endif
40
41 static int ccid_parse_interface_descriptor(usb_dev_handle *handle,
42 struct usb_device *dev);
43
44
45 /*****************************************************************************
46 *
47 * main
48 *
49 ****************************************************************************/
50 int main(/*@unused@*/ int argc, /*@unused@*/ char *argv[])
51 {
52 status_t res;
53 unsigned int channel;
54
55 for (channel=0; channel<CCID_DRIVER_MAX_READERS; channel++)
56 {
57 res = IFDHCreateChannel(channel<<16, channel);
58 if (res != IFD_SUCCESS)
59 {
60 fprintf(stderr, "ccid_OpenUSB: %d\n", res);
61 break;
62 }
63 else
64 {
65 usb_dev_handle *handle;
66 struct usb_device *dev;
67
68 if (get_desc(channel<<16, &handle, &dev))
69 res = ccid_parse_interface_descriptor(handle, dev);
70 else
71 fprintf(stderr, "Reader %d not found\n", channel);
72 }
73 }
74
75 if (channel == 0)
76 printf("No known CCID reader found\n");
77 else
78 for (channel--; channel!=0; channel--)
79 (void)IFDHCloseChannel(channel<<16);
80
81 return 0;
82 } /* main */
83
84
85 /*****************************************************************************
86 *
87 * Parse a CCID USB Descriptor
88 *
89 ****************************************************************************/
90 static int ccid_parse_interface_descriptor(usb_dev_handle *handle,
91 struct usb_device *dev)
92 {
93 struct usb_interface_descriptor *usb_interface;
94 unsigned char *extra;
95 char buffer[255];
96
97 /*
98 * Interface Descriptor
99 */
100 printf("Parsing Interface Descriptor for device: %s/%s\n",
101 dev->bus->dirname, dev->filename);
102
103 /*
104 * Vendor/model name
105 */
106 printf(" idVendor: 0x%04X\n", dev->descriptor.idVendor);
107 if (usb_get_string_simple(handle, dev->descriptor.iManufacturer,
108 buffer, sizeof(buffer)) < 0)
109 printf(" Can't get iManufacturer string\n");
110 else
111 printf(" iManufacturer: %s\n", buffer);
112
113 printf(" idProduct: 0x%04X\n", dev->descriptor.idProduct);
114 if (usb_get_string_simple(handle, dev->descriptor.iProduct,
115 buffer, sizeof(buffer)) < 0)
116 printf(" Can't get iProduct string\n");
117 else
118 printf(" iProduct: %s\n", buffer);
119
120 printf(" bcdDevice: %X.%02X (firmware release?)\n",
121 dev->descriptor.bcdDevice >> 8, dev->descriptor.bcdDevice & 0xFF);
122
123 usb_interface = get_ccid_usb_interface(dev)->altsetting;
124
125 printf(" bLength: %d\n", usb_interface->bLength);
126
127 printf(" bDescriptorType: %d\n", usb_interface->bDescriptorType);
128
129 printf(" bInterfaceNumber: %d\n", usb_interface->bInterfaceNumber);
130
131 printf(" bAlternateSetting: %d\n", usb_interface->bAlternateSetting);
132
133 printf(" bNumEndpoints: %d\n", usb_interface->bNumEndpoints);
134
135 printf(" bInterfaceClass: 0x%02X", usb_interface->bInterfaceClass);
136 if (usb_interface->bInterfaceClass == 0x0b)
137 printf(" [Chip Card Interface Device Class (CCID)]\n");
138 else
139 {
140 printf("\n NOT A CCID DEVICE\n");
141 if (usb_interface->bInterfaceClass != 0xFF)
142 return TRUE;
143 else
144 printf(" Class is 0xFF (proprietary)\n");
145 }
146
147 printf(" bInterfaceSubClass: %d\n", usb_interface->bInterfaceSubClass);
148 if (usb_interface->bInterfaceSubClass)
149 printf(" UNSUPPORTED SubClass\n");
150
151 printf(" bInterfaceProtocol: %d\n", usb_interface->bInterfaceProtocol);
152 if (usb_interface->bInterfaceProtocol)
153 printf(" UNSUPPORTED InterfaceProtocol\n");
154
155 printf(" iInterface: %d\n", usb_interface->iInterface);
156
157 if (usb_interface->extralen < 54)
158 {
159 printf("USB extra length is too short: %d\n", usb_interface->extralen);
160 printf("\n NOT A CCID DEVICE\n");
161 return TRUE;
162 }
163
164 /*
165 * CCID Class Descriptor
166 */
167 printf(" CCID Class Descriptor\n");
168 extra = usb_interface->extra;
169
170 printf(" bLength: 0x%02X\n", extra[0]);
171 if (extra[0] != 0x36)
172 {
173 printf(" UNSUPPORTED bLength\n");
174 return TRUE;
175 }
176
177 printf(" bDescriptorType: 0x%02X\n", extra[1]);
178 if (extra[1] != 0x21)
179 {
180 if (0xFF == extra[1])
181 printf(" PROPRIETARY bDescriptorType\n");
182 else
183 {
184 printf(" UNSUPPORTED bDescriptorType\n");
185 return TRUE;
186 }
187 }
188
189 printf(" bcdCCID: %X.%02X\n", extra[3], extra[2]);
190 printf(" bMaxSlotIndex: 0x%02X\n", extra[4]);
191 printf(" bVoltageSupport: 0x%02X\n", extra[5]);
192 if (extra[5] & 0x01)
193 printf(" 5.0V\n");
194 if (extra[5] & 0x02)
195 printf(" 3.0V\n");
196 if (extra[5] & 0x04)
197 printf(" 1.8V\n");
198
199 printf(" dwProtocols: 0x%02X%02X 0x%02X%02X\n", extra[9], extra[8],
200 extra[7],extra[6]);
201 if (extra[6] & 0x01)
202 printf(" T=0\n");
203 if (extra[6] & 0x02)
204 printf(" T=1\n");
205
206 printf(" dwDefaultClock: %.3f MHz\n", dw2i(extra, 10)/1000.0);
207 printf(" dwMaximumClock: %.3f MHz\n", dw2i(extra, 14)/1000.0);
208 printf(" bNumClockSupported: 0x%02X\n", extra[18]);
209 {
210 unsigned char buffer[256*sizeof(int)]; /* maximum is 256 records */
211 int n;
212
213 /* See CCID 3.7.2 page 25 */
214 n = usb_control_msg(handle,
215 0xA1, /* request type */
216 0x02, /* GET CLOCK FREQUENCIES */
217 0x00, /* value */
218 usb_interface->bInterfaceNumber, /* interface */
219 (char *)buffer,
220 sizeof(buffer),
221 2 * 1000);
222
223 /* we got an error? */
224 if (n <= 0)
225 printf(" IFD does not support GET CLOCK FREQUENCIES request\n");
226 else
227 if (n % 4) /* not a multiple of 4 */
228 printf(" wrong size for GET CLOCK FREQUENCIES: %d\n", n);
229 else
230 {
231 int i;
232
233 for (i=0; i<n; i+=4)
234 printf(" Support %d kHz\n", dw2i(buffer, i));
235 }
236 }
237 printf(" dwDataRate: %d bps\n", dw2i(extra, 19));
238 printf(" dwMaxDataRate: %d bps\n", dw2i(extra, 23));
239 printf(" bNumDataRatesSupported: %d\n", extra[27]);
240 {
241 unsigned char buffer[256*sizeof(int)]; /* maximum is 256 records */
242 int n;
243
244 /* See CCID 3.7.3 page 25 */
245 n = usb_control_msg(handle,
246 0xA1, /* request type */
247 0x03, /* GET DATA RATES */
248 0x00, /* value */
249 usb_interface->bInterfaceNumber, /* interface */
250 (char *)buffer,
251 sizeof(buffer),
252 2 * 1000);
253
254 /* we got an error? */
255 if (n <= 0)
256 printf(" IFD does not support GET_DATA_RATES request\n");
257 else
258 if (n % 4) /* not a multiple of 4 */
259 printf(" wrong size for GET_DATA_RATES: %d\n", n);
260 else
261 {
262 int i;
263
264 for (i=0; i<n; i+=4)
265 printf(" Support %d bps\n", dw2i(buffer, i));
266 }
267 }
268 printf(" dwMaxIFSD: %d\n", dw2i(extra, 28));
269 printf(" dwSynchProtocols: 0x%08X\n", dw2i(extra, 32));
270 if (extra[35] & 0x01)
271 printf(" 2-wire protocol\n");
272 if (extra[35] & 0x02)
273 printf(" 3-wire protocol\n");
274 if (extra[35] & 0x04)
275 printf(" I2C protocol\n");
276
277 printf(" dwMechanical: 0x%08X\n", dw2i(extra, 36));
278 if (extra[36] == 0)
279 printf(" No special characteristics\n");
280 if (extra[36] & 0x01)
281 printf(" Card accept mechanism\n");
282 if (extra[36] & 0x02)
283 printf(" Card ejection mechanism\n");
284 if (extra[36] & 0x04)
285 printf(" Card capture mechanism\n");
286 if (extra[36] & 0x08)
287 printf(" Card lock/unlock mechanism\n");
288
289 printf(" dwFeatures: 0x%08X\n", dw2i(extra, 40));
290 if (dw2i(extra, 40) == 0)
291 printf(" No special characteristics\n");
292 if (extra[40] & 0x02)
293 printf(" ....02 Automatic parameter configuration based on ATR data\n");
294 if (extra[40] & 0x04)
295 printf(" ....04 Automatic activation of ICC on inserting\n");
296 if (extra[40] & 0x08)
297 printf(" ....08 Automatic ICC voltage selection\n");
298 if (extra[40] & 0x10)
299 printf(" ....10 Automatic ICC clock frequency change according to parameters\n");
300 if (extra[40] & 0x20)
301 printf(" ....20 Automatic baud rate change according to frequency and Fi, Di params\n");
302 if (extra[40] & 0x40)
303 printf(" ....40 Automatic parameters negotiation made by the CCID\n");
304 if (extra[40] & 0x80)
305 printf(" ....80 Automatic PPS made by the CCID\n");
306 if (extra[41] & 0x01)
307 printf(" ..01.. CCID can set ICC in clock stop mode\n");
308 if (extra[41] & 0x02)
309 printf(" ..02.. NAD value other than 00 accepted (T=1)\n");
310 if (extra[41] & 0x04)
311 printf(" ..04.. Automatic IFSD exchange as first exchange (T=1)\n");
312 switch (extra[42] & 0x07)
313 {
314 case 0x00:
315 printf(" 00.... Character level exchange\n");
316 break;
317
318 case 0x01:
319 printf(" 01.... TPDU level exchange\n");
320 break;
321
322 case 0x02:
323 printf(" 02.... Short APDU level exchange\n");
324 break;
325
326 case 0x04:
327 printf(" 04.... Short and Extended APDU level exchange\n");
328 break;
329 }
330
331 printf(" dwMaxCCIDMessageLength: %d bytes\n", dw2i(extra, 44));
332 printf(" bClassGetResponse: 0x%02X\n", extra[48]);
333 if (0xFF == extra[48])
334 printf(" echoes the APDU class\n");
335 printf(" bClassEnveloppe: %d\n", extra[49]);
336 printf(" wLcdLayout: 0x%04X\n", (extra[51] << 8)+extra[50]);
337 printf(" bPINSupport: 0x%02X\n", extra[52]);
338 if (extra[52] & 0x01)
339 printf(" PIN Verification supported\n");
340 if (extra[52] & 0x02)
341 printf(" PIN Modification supported\n");
342 printf(" bMaxCCIDBusySlots: %d\n", extra[53]);
343
344 return FALSE;
345 } /* ccid_parse_interface_descriptor */
346

Properties

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

  ViewVC Help
Powered by ViewVC 1.1.5