fixed automake/autoconf files to allow clean firmware compilation
[librfid] / src / rfid_reader_openpcd.c
1 /* OpenPCD specific RC632 transport layer 
2  *
3  * (C) 2006 by Harald Welte <laforge@gnumonks.org>
4  *
5  * The OpenPCD is an Atmel AT91SAM7Sxx based USB RFID reader.
6  * It's CL RC632 is connected via SPI.  OpenPCD has multiple firmware
7  * images.  This driver is for the "main_dumbreader" firmware.
8  *
9  * TODO:
10  * - put hdl from static variable into asic transport or reader handle 
11  */
12
13 /*
14  *  This program is free software; you can redistribute it and/or modify
15  *  it under the terms of the GNU General Public License version 2 
16  *  as published by the Free Software Foundation
17  *
18  *  This program is distributed in the hope that it will be useful,
19  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
20  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
21  *  GNU General Public License for more details.
22  *
23  *  You should have received a copy of the GNU General Public License
24  *  along with this program; if not, write to the Free Software
25  *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
26  */
27
28 #include <stdlib.h>
29 #include <unistd.h>
30 #include <string.h>
31 #include <errno.h>
32
33 #include <librfid/rfid.h>
34 #include <librfid/rfid_reader.h>
35 #include <librfid/rfid_asic.h>
36 #include <librfid/rfid_asic_rc632.h>
37 #include <librfid/rfid_reader_openpcd.h>
38 #include <librfid/rfid_layer2.h>
39 #include <librfid/rfid_protocol.h>
40
41 /* FIXME */
42 #include "rc632.h"
43
44 #define SENDBUF_LEN     (256+4+10) /* 256bytes max FSD/FSC, plus 4 bytes header,
45                                     plus 10 bytes reserve */
46 #define RECVBUF_LEN     SENDBUF_LEN
47
48 static char snd_buf[SENDBUF_LEN];
49 static char rcv_buf[RECVBUF_LEN];
50 static struct openpcd_hdr *snd_hdr;
51 static struct openpcd_hdr *rcv_hdr;
52
53 #ifndef LIBRFID_FIRMWARE
54
55 #ifdef  __MINGW32__
56 #include "libusb_dyn.h"
57 #else /*__MINGW32__*/
58 #include <usb.h>
59 #endif/*__MINGW32__*/
60
61 static struct usb_device *dev;
62 static struct usb_dev_handle *hdl;
63
64 static int openpcd_send_command(u_int8_t cmd, u_int8_t reg, u_int8_t val,
65                                 u_int16_t len, const unsigned char *data)
66 {
67         int ret;
68         u_int16_t cur;
69
70         snd_hdr->cmd = cmd;
71         snd_hdr->reg = reg;
72         snd_hdr->val = val;
73         snd_hdr->flags = OPENPCD_FLAG_RESPOND;
74         if (data && len)
75                 memcpy(snd_hdr->data, data, len);
76
77         cur = sizeof(*snd_hdr) + len;
78
79         return usb_bulk_write(hdl, OPENPCD_OUT_EP, (char *)snd_hdr, cur, 1000);
80 }
81
82 static int openpcd_recv_reply(void)
83 {
84         int ret;
85
86         ret = usb_bulk_read(hdl, OPENPCD_IN_EP, rcv_buf, sizeof(rcv_buf), 1000);
87
88         return ret;
89 }
90
91 static int openpcd_xcv(u_int8_t cmd, u_int8_t reg, u_int8_t val,
92                         u_int16_t len, const unsigned char *data)
93 {
94         int ret;
95         
96         ret = openpcd_send_command(cmd, reg, val, len, data);
97         if (ret < 0)
98                 return ret;
99         if (ret < sizeof(struct openpcd_hdr))
100                 return -EINVAL;
101
102         return openpcd_recv_reply();
103 }
104
105 struct usb_id {
106         u_int16_t vid;
107         u_int16_t pid;
108 };
109
110 static const struct usb_id opcd_usb_ids[] = {
111         { .vid = 0x2342, .pid = 0x0001 },       /* prototypes */
112         { .vid = 0x16c0, .pid = 0x076b },       /* first official device id */
113 };
114
115 static struct usb_device *find_opcd_device(void)
116 {
117         struct usb_bus *bus;
118
119         for (bus = usb_get_busses(); bus; bus = bus->next) {
120                 struct usb_device *dev;
121                 for (dev = bus->devices; dev; dev = dev->next) {
122                         int i;
123                         for (i = 0; i < ARRAY_SIZE(opcd_usb_ids); i++) {
124                                 const struct usb_id *id = &opcd_usb_ids[i];
125                                 if (dev->descriptor.idVendor == id->vid &&
126                                     dev->descriptor.idProduct == id->pid)
127                                         return dev;
128                         }
129                 }
130         }
131         return NULL;
132 }
133
134 /* RC632 access primitives for librfid inside reader firmware */
135
136 static int openpcd_reg_write(struct rfid_asic_transport_handle *rath,
137                              unsigned char reg, unsigned char value)
138 {
139         int ret;
140
141         DEBUGP("reg=0x%02x, val=%02x: ", reg, value);
142
143         ret = openpcd_xcv(OPENPCD_CMD_WRITE_REG, reg, value, 0, NULL);
144         if (ret < 0)
145                 DEBUGPC("ERROR sending command\n");
146         else
147                 DEBUGPC("OK\n");
148
149         return ret;
150 }
151
152 static int openpcd_reg_read(struct rfid_asic_transport_handle *rath,
153                             unsigned char reg,
154                             unsigned char *value)
155 {
156         int ret;        
157
158         DEBUGP("reg=0x%02x, ", reg);
159
160         ret = openpcd_xcv(OPENPCD_CMD_READ_REG, reg, 0, 0, NULL);
161         if (ret < 0) {
162                 DEBUGPC("ERROR sending command\n");
163                 return ret;
164         }
165
166         if (ret < sizeof(struct openpcd_hdr)) {
167                 DEBUGPC("ERROR: short packet\n");
168                 return ret;
169         }
170
171         *value = rcv_hdr->val;
172         DEBUGPC("val=%02x: OK\n", *value);
173
174         return ret;
175 }
176
177 static int openpcd_fifo_read(struct rfid_asic_transport_handle *rath,
178                              unsigned char num_bytes,
179                              unsigned char *buf)
180 {
181         int ret;
182
183         DEBUGP(" ");
184
185         ret = openpcd_xcv(OPENPCD_CMD_READ_FIFO, 0x00, num_bytes, 0, NULL);
186         if (ret < 0) {
187                 DEBUGPC("ERROR sending command\n");
188                 return ret;
189         }
190         DEBUGPC("ret = %d\n", ret);
191
192         memcpy(buf, rcv_hdr->data, ret - sizeof(struct openpcd_hdr));
193         DEBUGPC("len=%d val=%s: OK\n", ret - sizeof(struct openpcd_hdr),
194                 rfid_hexdump(rcv_hdr->data, ret - sizeof(struct openpcd_hdr)));
195
196         return ret;
197 }
198
199 static int openpcd_fifo_write(struct rfid_asic_transport_handle *rath,
200                              unsigned char len,
201                              const unsigned char *bytes,
202                              unsigned char flags)
203 {
204         int ret;
205
206         DEBUGP("len=%u, data=%s\n", len, rfid_hexdump(bytes, len));
207         ret = openpcd_xcv(OPENPCD_CMD_WRITE_FIFO, 0, 0, len, bytes);
208
209         return ret;
210 }
211
212 const struct rfid_asic_transport openpcd_rat = {
213         .name = "OpenPCD Dumb USB Protocol",
214         .priv.rc632 = {
215                 .fn = {
216                         .reg_write      = &openpcd_reg_write,
217                         .reg_read       = &openpcd_reg_read,
218                         .fifo_write     = &openpcd_fifo_write,
219                         .fifo_read      = &openpcd_fifo_read,
220                 },
221         },
222 };
223
224 static int openpcd_get_api_version(struct rfid_reader_handle *rh, u_int8_t *version)
225 {
226         int ret;
227         
228         // preset version result to zero
229         rcv_hdr->val=0;
230     
231         ret = openpcd_xcv(OPENPCD_CMD_GET_API_VERSION, 0, 0, 0, NULL);
232         if (ret < 0) {
233                 DEBUGPC("ERROR sending command [%i]\n", ret);
234                 return ret;
235         }
236
237         if (ret < sizeof(struct openpcd_hdr)) {
238                 DEBUGPC("ERROR: short packet [%i]\n", ret);
239                 return -EINVAL;
240         }
241
242         *version = rcv_hdr->val;
243         
244         return ret;
245 }
246
247 static int openpcd_get_environment(
248     struct rfid_reader_handle *rh,
249     unsigned char num_bytes,
250     unsigned char *buf)
251 {
252         int ret;
253
254         DEBUGP(" ");
255
256         ret = openpcd_xcv(OPENPCD_CMD_GET_ENVIRONMENT, 0x00, num_bytes, 0, NULL);
257         if (ret < 0) {
258                 DEBUGPC("ERROR sending command [%i]\n",ret);
259                 return ret;
260         }
261         DEBUGPC("ret = %d\n", ret);
262
263         memcpy(buf, rcv_hdr->data, ret - sizeof(struct openpcd_hdr));
264         DEBUGPC("len=%d val=%s: OK\n", ret - sizeof(struct openpcd_hdr),
265                 rfid_hexdump(rcv_hdr->data, ret - sizeof(struct openpcd_hdr)));
266
267         return ret;
268 }
269
270 static int openpcd_set_environment(
271     struct rfid_reader_handle *rh, 
272     const unsigned char num_bytes,
273     unsigned char *buf)
274 {
275         int ret;
276         
277         ret = openpcd_xcv(OPENPCD_CMD_SET_ENVIRONMENT, 0, 0, num_bytes, buf);
278         if (ret < 0) {
279                 DEBUGPC("ERROR sending command [%i]\n",ret);
280                 return ret;
281         }
282
283         if (ret < sizeof(struct openpcd_hdr)) {
284                 DEBUGPC("ERROR: short packet [%i]\n", ret);
285                 return -EINVAL;
286         }
287
288         return rcv_hdr->val;
289 }
290
291 static int openpcd_reset(struct rfid_reader_handle *rh)
292 {
293         int ret;
294
295         DEBUGP("reset ");
296         ret = openpcd_xcv(OPENPCD_CMD_RESET, 0, 0, 0, 0);
297
298         return ret;
299 }
300
301 #else
302 /* RC632 access primitives for librfid inside reader firmware */
303
304 static int openpcd_reg_write(struct rfid_asic_transport_handle *rath,
305                              unsigned char reg, unsigned char value)
306 {
307         return opcd_rc632_reg_write(rath, reg, value);
308 }
309
310 static int openpcd_reg_read(struct rfid_asic_transport_handle *rath,
311                             unsigned char reg,
312                             unsigned char *value)
313 {
314         return opcd_rc632_reg_read(rath, reg, value);
315 }
316
317
318 static int openpcd_fifo_read(struct rfid_asic_transport_handle *rath,
319                              unsigned char num_bytes,
320                              unsigned char *buf)
321 {
322         return opcd_rc632_fifo_read(rath, num_bytes, buf);
323 }
324
325 static int openpcd_fifo_write(struct rfid_asic_transport_handle *rath,
326                              unsigned char len,
327                              const unsigned char *bytes,
328                              unsigned char flags)
329 {
330         return opcd_rc632_fifo_write(rath, len, bytes, flags);
331 }
332
333 const struct rfid_asic_transport openpcd_rat = {
334         .name = "OpenPCD Firmware RC632 Access",
335         .priv.rc632 = {
336                 .fn = {
337                         .reg_write      = &openpcd_reg_write,
338                         .reg_read       = &openpcd_reg_read,
339                         .fifo_write     = &openpcd_fifo_write,
340                         .fifo_read      = &openpcd_fifo_read,
341                 },
342         },
343 };
344
345 #endif /* LIBRFID_FIRMWARE */
346
347 static int openpcd_transceive(struct rfid_reader_handle *rh,
348                              enum rfid_frametype frametype,
349                              const unsigned char *tx_data, unsigned int tx_len,
350                              unsigned char *rx_data, unsigned int *rx_len,
351                              u_int64_t timeout, unsigned int flags)
352 {
353         return rh->ah->asic->priv.rc632.fn.transceive(rh->ah, frametype,
354                                                       tx_data, tx_len, 
355                                                       rx_data, rx_len,
356                                                       timeout, flags);
357 }
358
359 static int openpcd_transceive_sf(struct rfid_reader_handle *rh,
360                                unsigned char cmd, struct iso14443a_atqa *atqa)
361 {
362         return rh->ah->asic->priv.rc632.fn.iso14443a.transceive_sf(rh->ah,
363                                                                    cmd,
364                                                                    atqa);
365 }
366
367 static int
368 openpcd_transceive_acf(struct rfid_reader_handle *rh,
369                       struct iso14443a_anticol_cmd *cmd,
370                       unsigned int *bit_of_col)
371 {
372         return rh->ah->asic->priv.rc632.fn.iso14443a.transceive_acf(rh->ah,
373                                                          cmd, bit_of_col);
374 }
375
376 static int
377 openpcd_14443a_init(struct rfid_reader_handle *rh)
378 {
379         return rh->ah->asic->priv.rc632.fn.iso14443a.init(rh->ah);
380 }
381
382 static int
383 openpcd_14443a_set_speed(struct rfid_reader_handle *rh, 
384                         unsigned int tx,
385                         unsigned int speed)
386 {
387         u_int8_t rate;
388         
389         DEBUGP("setting rate: ");
390         switch (speed) {
391         case RFID_14443A_SPEED_106K:
392                 rate = 0x00;
393                 DEBUGPC("106K\n");
394                 break;
395         case RFID_14443A_SPEED_212K:
396                 rate = 0x01;
397                 DEBUGPC("212K\n");
398                 break;
399         case RFID_14443A_SPEED_424K:
400                 rate = 0x02;
401                 DEBUGPC("424K\n");
402                 break;
403         case RFID_14443A_SPEED_848K:
404                 rate = 0x03;
405                 DEBUGPC("848K\n");
406                 break;
407         default:
408                 return -EINVAL;
409                 break;
410         }
411         return rh->ah->asic->priv.rc632.fn.iso14443a.set_speed(rh->ah,
412                                                                 tx, rate);
413 }
414
415 static int
416 openpcd_14443b_init(struct rfid_reader_handle *rh)
417 {
418         return rh->ah->asic->priv.rc632.fn.iso14443b.init(rh->ah);
419 }
420
421 static int
422 openpcd_15693_init(struct rfid_reader_handle *rh)
423 {
424         return rh->ah->asic->priv.rc632.fn.iso15693.init(rh->ah);
425 }
426
427 static int
428 openpcd_mifare_setkey(struct rfid_reader_handle *rh, const u_int8_t *key)
429 {
430         return rh->ah->asic->priv.rc632.fn.mifare_classic.setkey(rh->ah, key);
431 }
432
433 static int
434 openpcd_mifare_auth(struct rfid_reader_handle *rh, u_int8_t cmd, 
435                    u_int32_t serno, u_int8_t block)
436 {
437         return rh->ah->asic->priv.rc632.fn.mifare_classic.auth(rh->ah, 
438                                                         cmd, serno, block);
439 }
440
441 static struct rfid_reader_handle *
442 openpcd_open(void *data)
443 {
444         struct rfid_reader_handle *rh;
445         struct rfid_asic_transport_handle *rath;
446
447         snd_hdr = (struct openpcd_hdr *)snd_buf;
448         rcv_hdr = (struct openpcd_hdr *)rcv_buf;
449
450 #ifndef LIBRFID_FIRMWARE
451         usb_init();
452         if (usb_find_busses() < 0)
453                 return NULL;
454         if (usb_find_devices() < 0) 
455                 return NULL;
456         
457         dev = find_opcd_device();
458         if (!dev) {
459                 DEBUGP("No matching USB device found\n");
460                 return NULL;
461         }
462
463         hdl = usb_open(dev);
464         if (!hdl) {
465                 DEBUGP("Can't open USB device\n");
466                 return NULL;
467         }
468
469         if(usb_set_configuration(hdl, 1 ) < 0)
470         {
471             DEBUGP("setting config failed\n");
472             usb_close( hdl );
473             return NULL;
474         }
475                                                                         
476         if (usb_claim_interface(hdl, 0) < 0) {
477                 DEBUGP("Can't claim interface\n");
478                 usb_close(hdl);
479                 return NULL;
480         }
481 #endif
482
483         rh = malloc_reader_handle(sizeof(*rh));
484         if (!rh)
485                 return NULL;
486         memset(rh, 0, sizeof(*rh));
487
488         rath = malloc_rat_handle(sizeof(*rath));
489         if (!rath)
490                 goto out_rh;
491         memset(rath, 0, sizeof(*rath));
492
493         rath->rat = &openpcd_rat;
494         rh->reader = &rfid_reader_openpcd;
495
496         rh->ah = rc632_open(rath);
497         if (!rh->ah) 
498                 goto out_rath;
499
500         DEBUGP("returning %p\n", rh);
501         return rh;
502
503 out_rath:
504         free_rat_handle(rath);
505 out_rh:
506         free_reader_handle(rh);
507
508         return NULL;
509 }
510
511 static void
512 openpcd_close(struct rfid_reader_handle *rh)
513 {
514         struct rfid_asic_transport_handle *rath = rh->ah->rath;
515
516         rc632_close(rh->ah);
517         free_rat_handle(rath);
518         free_reader_handle(rh);
519
520 #ifndef LIBRFID_FIRMWARE
521         usb_close(hdl);
522 #endif
523 }
524
525 const struct rfid_reader rfid_reader_openpcd = {
526         .name   = "OpenPCD RFID Reader",
527         .id = RFID_READER_OPENPCD,
528         .open = &openpcd_open,
529         .close = &openpcd_close,
530         
531 #ifndef LIBRFID_FIRMWARE
532         .get_api_version = &openpcd_get_api_version,
533         .get_environment = &openpcd_get_environment,
534         .set_environment = &openpcd_set_environment,
535         .reset = &openpcd_reset,
536 #endif
537                                         
538         .transceive = &openpcd_transceive,
539         .l2_supported = (1 << RFID_LAYER2_ISO14443A) |
540                         (1 << RFID_LAYER2_ISO14443B) |
541                         (1 << RFID_LAYER2_ISO15693),
542         .proto_supported = (1 << RFID_PROTOCOL_TCL) |
543                         (1 << RFID_PROTOCOL_MIFARE_UL) |
544                         (1 << RFID_PROTOCOL_MIFARE_CLASSIC),
545         .iso14443a = {
546                 .init = &openpcd_14443a_init,
547                 .transceive_sf = &openpcd_transceive_sf,
548                 .transceive_acf = &openpcd_transceive_acf,
549                 .speed = RFID_14443A_SPEED_106K | RFID_14443A_SPEED_212K |
550                          RFID_14443A_SPEED_424K, //| RFID_14443A_SPEED_848K,
551                 .set_speed = &openpcd_14443a_set_speed,
552         },
553         .iso14443b = {
554                 .init = &openpcd_14443b_init,
555         },
556         .iso15693 = {
557                 .init = &openpcd_15693_init,
558         },
559         .mifare_classic = {
560                 .setkey = &openpcd_mifare_setkey,
561                 .auth = &openpcd_mifare_auth,
562         },
563 };