]> git.zerfleddert.de Git - proxmark3-svn/blob - client/cmdsmartcard.c
Add smartcard protocol T=0 (RRG repository PRs 71,72,74,75 by @merlokk) (#757)
[proxmark3-svn] / client / cmdsmartcard.c
1 //-----------------------------------------------------------------------------
2 // Copyright (C) 2018 iceman
3 //
4 // This code is licensed to you under the terms of the GNU GPL, version 2 or,
5 // at your option, any later version. See the LICENSE.txt file for the text of
6 // the license.
7 //-----------------------------------------------------------------------------
8 // Proxmark3 RDV40 Smartcard module commands
9 //-----------------------------------------------------------------------------
10 #include "cmdsmartcard.h"
11
12 #include <ctype.h>
13
14 #include "ui.h"
15 #include "cmdparser.h"
16 #include "proxmark3.h"
17 #include "util.h"
18 #include "smartcard.h"
19 #include "comms.h"
20 #include "protocols.h"
21 #include "cmdhflist.h"
22 #include "emv/apduinfo.h" // APDUcode description
23 #include "emv/emvcore.h" // decodeTVL
24 #include "crypto/libpcrypto.h" // sha512hash
25 #include "emv/dump.h" // dump_buffer
26
27 #define SC_UPGRADE_FILES_DIRECTORY "sc_upgrade_firmware/"
28
29 static int CmdHelp(const char *Cmd);
30
31 static int usage_sm_raw(void) {
32 PrintAndLogEx(NORMAL, "Usage: sc raw [h|r|c] d <0A 0B 0C ... hex>");
33 PrintAndLogEx(NORMAL, " h : this help");
34 PrintAndLogEx(NORMAL, " r : do not read response");
35 PrintAndLogEx(NORMAL, " a : active smartcard without select (reset sc module)");
36 PrintAndLogEx(NORMAL, " s : active smartcard with select (get ATR)");
37 PrintAndLogEx(NORMAL, " t : executes TLV decoder if it possible");
38 PrintAndLogEx(NORMAL, " 0 : use protocol T=0");
39 PrintAndLogEx(NORMAL, " d <bytes> : bytes to send");
40 PrintAndLogEx(NORMAL, "");
41 PrintAndLogEx(NORMAL, "Examples:");
42 PrintAndLogEx(NORMAL, " sc raw s 0 d 00a404000e315041592e5359532e4444463031 - `1PAY.SYS.DDF01` PPSE directory with get ATR");
43 PrintAndLogEx(NORMAL, " sc raw 0 d 00a404000e325041592e5359532e4444463031 - `2PAY.SYS.DDF01` PPSE directory");
44 return 0;
45 }
46
47 static int usage_sm_reader(void) {
48 PrintAndLogEx(NORMAL, "Usage: sc reader [h|s]");
49 PrintAndLogEx(NORMAL, " h : this help");
50 PrintAndLogEx(NORMAL, " s : silent (no messages)");
51 PrintAndLogEx(NORMAL, "");
52 PrintAndLogEx(NORMAL, "Examples:");
53 PrintAndLogEx(NORMAL, " sc reader");
54 return 0;
55 }
56
57 static int usage_sm_info(void) {
58 PrintAndLogEx(NORMAL, "Usage: s info [h|s]");
59 PrintAndLogEx(NORMAL, " h : this help");
60 PrintAndLogEx(NORMAL, " s : silent (no messages)");
61 PrintAndLogEx(NORMAL, "");
62 PrintAndLogEx(NORMAL, "Examples:");
63 PrintAndLogEx(NORMAL, " sc info");
64 return 0;
65 }
66
67 static int usage_sm_upgrade(void) {
68 PrintAndLogEx(NORMAL, "Upgrade RDV4.0 Smartcard Socket Firmware");
69 PrintAndLogEx(NORMAL, "Usage: sc upgrade f <file name>");
70 PrintAndLogEx(NORMAL, " h : this help");
71 PrintAndLogEx(NORMAL, " f <filename> : firmware file name");
72 PrintAndLogEx(NORMAL, "");
73 PrintAndLogEx(NORMAL, "Examples:");
74 PrintAndLogEx(NORMAL, " sc upgrade f SIM010.BIN");
75 return 0;
76 }
77
78 static int usage_sm_setclock(void) {
79 PrintAndLogEx(NORMAL, "Usage: sc setclock [h] c <clockspeed>");
80 PrintAndLogEx(NORMAL, " h : this help");
81 PrintAndLogEx(NORMAL, " c <> : clockspeed (0 = 16mhz, 1=8mhz, 2=4mhz) ");
82 PrintAndLogEx(NORMAL, "");
83 PrintAndLogEx(NORMAL, "Examples:");
84 PrintAndLogEx(NORMAL, " sc setclock c 2");
85 return 0;
86 }
87
88 static int usage_sm_brute(void) {
89 PrintAndLogEx(NORMAL, "Tries to bruteforce SFI, ");
90 PrintAndLogEx(NORMAL, "Usage: sc brute [h]");
91 PrintAndLogEx(NORMAL, " h : this help");
92 PrintAndLogEx(NORMAL, "");
93 PrintAndLogEx(NORMAL, "Examples:");
94 PrintAndLogEx(NORMAL, " sc brute");
95 return 0;
96 }
97
98 uint8_t GetATRTA1(uint8_t *atr, size_t atrlen) {
99 if (atrlen > 2) {
100 uint8_t T0 = atr[1];
101 if (T0 & 0x10)
102 return atr[2];
103 }
104
105 return 0x11; // default value is 0x11, corresponding to fmax=5 MHz, Fi=372, Di=1.
106 }
107
108 int DiArray[] = {
109 0, // b0000 RFU
110 1, // b0001
111 2,
112 4,
113 8,
114 16,
115 32, // b0110
116 64, // b0111. This was RFU in ISO/IEC 7816-3:1997 and former. Some card readers or drivers may erroneously reject cards using this value
117 12,
118 20,
119 0, // b1010 RFU
120 0,
121 0, // ...
122 0,
123 0,
124 0 // b1111 RFU
125 };
126
127 int FiArray[] = {
128 372, // b0000 Historical note: in ISO/IEC 7816-3:1989, this was assigned to cards with internal clock
129 372, // b0001
130 558, // b0010
131 744, // b0011
132 1116, // b0100
133 1488, // b0101
134 1860, // b0110
135 0, // b0111 RFU
136 0, // b1000 RFU
137 512, // b1001
138 768, // b1010
139 1024, // b1011
140 1536, // b1100
141 2048, // b1101
142 0, // b1110 RFU
143 0 // b1111 RFU
144 };
145
146 float FArray[] = {
147 4, // b0000 Historical note: in ISO/IEC 7816-3:1989, this was assigned to cards with internal clock
148 5, // b0001
149 6, // b0010
150 8, // b0011
151 12, // b0100
152 16, // b0101
153 20, // b0110
154 0, // b0111 RFU
155 0, // b1000 RFU
156 5, // b1001
157 7.5, // b1010
158 10, // b1011
159 15, // b1100
160 20, // b1101
161 0, // b1110 RFU
162 0 // b1111 RFU
163 };
164
165 int GetATRDi(uint8_t *atr, size_t atrlen) {
166 uint8_t TA1 = GetATRTA1(atr, atrlen);
167
168 return DiArray[TA1 & 0x0f]; // The 4 low-order bits of TA1 (4th MSbit to 1st LSbit) encode Di
169 }
170
171 int GetATRFi(uint8_t *atr, size_t atrlen) {
172 uint8_t TA1 = GetATRTA1(atr, atrlen);
173
174 return FiArray[TA1 >> 4]; // The 4 high-order bits of TA1 (8th MSbit to 5th LSbit) encode fmax and Fi
175 }
176
177 float GetATRF(uint8_t *atr, size_t atrlen) {
178 uint8_t TA1 = GetATRTA1(atr, atrlen);
179
180 return FArray[TA1 >> 4]; // The 4 high-order bits of TA1 (8th MSbit to 5th LSbit) encode fmax and Fi
181 }
182
183 static int PrintATR(uint8_t *atr, size_t atrlen) {
184
185 uint8_t T0 = atr[1];
186 uint8_t K = T0 & 0x0F;
187 uint8_t TD1 = 0, T1len = 0, TD1len = 0, TDilen = 0;
188
189 if (T0 & 0x10) {
190 PrintAndLog("\t- TA1 (Maximum clock frequency, proposed bit duration) [ 0x%02x ]", atr[2 + T1len]);
191 T1len++;
192 }
193
194 if (T0 & 0x20) {
195 PrintAndLog("\t- TB1 (Deprecated: VPP requirements) [ 0x%02x ]", atr[2 + T1len]);
196 T1len++;
197 }
198
199 if (T0 & 0x40) {
200 PrintAndLog("\t- TC1 (Extra delay between bytes required by card) [ 0x%02x ]", atr[2 + T1len]);
201 T1len++;
202 }
203
204 if (T0 & 0x80) {
205 TD1 = atr[2 + T1len];
206 PrintAndLog("\t- TD1 (First offered transmission protocol, presence of TA2..TD2) [ 0x%02x ] Protocol T%d", TD1, TD1 & 0x0f);
207 T1len++;
208
209 if (TD1 & 0x10) {
210 PrintAndLog("\t- TA2 (Specific protocol and parameters to be used after the ATR) [ 0x%02x ]", atr[2 + T1len + TD1len]);
211 TD1len++;
212 }
213 if (TD1 & 0x20) {
214 PrintAndLog("\t- TB2 (Deprecated: VPP precise voltage requirement) [ 0x%02x ]", atr[2 + T1len + TD1len]);
215 TD1len++;
216 }
217 if (TD1 & 0x40) {
218 PrintAndLog("\t- TC2 (Maximum waiting time for protocol T=0) [ 0x%02x ]", atr[2 + T1len + TD1len]);
219 TD1len++;
220 }
221 if (TD1 & 0x80) {
222 uint8_t TDi = atr[2 + T1len + TD1len];
223 PrintAndLog("\t- TD2 (A supported protocol or more global parameters, presence of TA3..TD3) [ 0x%02x ] Protocol T%d", TDi, TDi & 0x0f);
224 TD1len++;
225
226 bool nextCycle = true;
227 uint8_t vi = 3;
228 while (nextCycle) {
229 nextCycle = false;
230 if (TDi & 0x10) {
231 PrintAndLog("\t- TA%d: 0x%02x", vi, atr[2 + T1len + TD1len + TDilen]);
232 TDilen++;
233 }
234 if (TDi & 0x20) {
235 PrintAndLog("\t- TB%d: 0x%02x", vi, atr[2 + T1len + TD1len + TDilen]);
236 TDilen++;
237 }
238 if (TDi & 0x40) {
239 PrintAndLog("\t- TC%d: 0x%02x", vi, atr[2 + T1len + TD1len + TDilen]);
240 TDilen++;
241 }
242 if (TDi & 0x80) {
243 TDi = atr[2 + T1len + TD1len + TDilen];
244 PrintAndLog("\t- TD%d [ 0x%02x ] Protocol T%d", vi, TDi, TDi & 0x0f);
245 TDilen++;
246
247 nextCycle = true;
248 vi++;
249 }
250 }
251 }
252 }
253
254 uint8_t vxor = 0;
255 for (int i = 1; i < atrlen; i++)
256 vxor ^= atr[i];
257
258 if (vxor)
259 PrintAndLogEx(WARNING, "Check summ error. Must be 0 got 0x%02X", vxor);
260 else
261 PrintAndLogEx(INFO, "Check summ OK.");
262
263 if (atr[0] != 0x3b)
264 PrintAndLogEx(WARNING, "Not a direct convention [ 0x%02x ]", atr[0]);
265
266
267 uint8_t calen = 2 + T1len + TD1len + TDilen + K;
268
269 if (atrlen != calen && atrlen != calen + 1) // may be CRC
270 PrintAndLogEx(ERR, "ATR length error. len: %d, T1len: %d, TD1len: %d, TDilen: %d, K: %d", atrlen, T1len, TD1len, TDilen, K);
271
272 if (K > 0)
273 PrintAndLogEx(INFO, "\nHistorical bytes | len 0x%02d | format %02x", K, atr[2 + T1len + TD1len + TDilen]);
274
275 if (K > 1) {
276 PrintAndLogEx(INFO, "\tHistorical bytes");
277 dump_buffer(&atr[2 + T1len + TD1len + TDilen], K, NULL, 1);
278 }
279
280 return 0;
281 }
282
283 static bool smart_select(bool silent) {
284 UsbCommand c = {CMD_SMART_ATR, {0, 0, 0}};
285 clearCommandBuffer();
286 SendCommand(&c);
287 UsbCommand resp;
288 if ( !WaitForResponseTimeout(CMD_ACK, &resp, 2500) ) {
289 if (!silent) PrintAndLogEx(WARNING, "smart card select failed");
290 return false;
291 }
292
293 uint8_t isok = resp.arg[0] & 0xFF;
294 if (!isok) {
295 if (!silent) PrintAndLogEx(WARNING, "smart card select failed");
296 return false;
297 }
298
299 if (!silent) {
300 smart_card_atr_t card;
301 memcpy(&card, (smart_card_atr_t *)resp.d.asBytes, sizeof(smart_card_atr_t));
302
303 PrintAndLogEx(INFO, "ISO7816-3 ATR : %s", sprint_hex(card.atr, card.atr_len));
304 }
305
306 return true;
307 }
308
309 static int smart_wait(uint8_t *data) {
310 UsbCommand resp;
311 if (!WaitForResponseTimeout(CMD_ACK, &resp, 2500)) {
312 PrintAndLogEx(WARNING, "smart card response timeout");
313 return -1;
314 }
315
316 uint32_t len = resp.arg[0];
317 if ( !len ) {
318 PrintAndLogEx(WARNING, "smart card response failed");
319 return -2;
320 }
321 memcpy(data, resp.d.asBytes, len);
322 if (len >= 2) {
323 PrintAndLogEx(SUCCESS, "%02X%02X | %s", data[len - 2], data[len - 1], GetAPDUCodeDescription(data[len - 2], data[len - 1]));
324 } else {
325 PrintAndLogEx(SUCCESS, " %d | %s", len, sprint_hex_inrow_ex(data, len, 8));
326 }
327
328 return len;
329 }
330
331 static int smart_response(uint8_t *data) {
332
333 int datalen = smart_wait(data);
334 bool needGetData = false;
335
336 if (datalen < 2 ) {
337 goto out;
338 }
339
340 if ( data[datalen - 2] == 0x61 || data[datalen - 2] == 0x9F ) {
341 needGetData = true;
342 }
343
344 if (needGetData) {
345 int len = data[datalen - 1];
346 PrintAndLogEx(INFO, "Requesting 0x%02X bytes response", len);
347 uint8_t getstatus[] = {0x00, ISO7816_GETSTATUS, 0x00, 0x00, len};
348 UsbCommand cStatus = {CMD_SMART_RAW, {SC_RAW, sizeof(getstatus), 0}};
349 memcpy(cStatus.d.asBytes, getstatus, sizeof(getstatus) );
350 clearCommandBuffer();
351 SendCommand(&cStatus);
352
353 datalen = smart_wait(data);
354
355 if (datalen < 2 ) {
356 goto out;
357 }
358
359 // data wo ACK
360 if (datalen != len + 2) {
361 // data with ACK
362 if (datalen == len + 2 + 1) { // 2 - response, 1 - ACK
363 if (data[0] != ISO7816_GETSTATUS) {
364 PrintAndLogEx(ERR, "GetResponse ACK error. len 0x%x | data[0] %02X", len, data[0]);
365 datalen = 0;
366 goto out;
367 }
368
369 datalen--;
370 memmove(data, &data[1], datalen);
371 } else {
372 // wrong length
373 PrintAndLogEx(WARNING, "GetResponse wrong length. Must be 0x%02X got 0x%02X", len, datalen - 3);
374 }
375 }
376 }
377
378 out:
379 return datalen;
380 }
381
382 int CmdSmartRaw(const char *Cmd) {
383
384 int hexlen = 0;
385 bool active = false;
386 bool active_select = false;
387 bool useT0 = false;
388 uint8_t cmdp = 0;
389 bool errors = false, reply = true, decodeTLV = false, breakloop = false;
390 uint8_t data[USB_CMD_DATA_SIZE] = {0x00};
391
392 while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
393 switch (tolower(param_getchar(Cmd, cmdp))) {
394 case 'h': return usage_sm_raw();
395 case 'r':
396 reply = false;
397 cmdp++;
398 break;
399 case 'a':
400 active = true;
401 cmdp++;
402 break;
403 case 's':
404 active_select = true;
405 cmdp++;
406 break;
407 case 't':
408 decodeTLV = true;
409 cmdp++;
410 break;
411 case '0':
412 useT0 = true;
413 cmdp++;
414 break;
415 case 'd': {
416 switch (param_gethex_to_eol(Cmd, cmdp+1, data, sizeof(data), &hexlen)) {
417 case 1:
418 PrintAndLogEx(WARNING, "Invalid HEX value.");
419 return 1;
420 case 2:
421 PrintAndLogEx(WARNING, "Too many bytes. Max %d bytes", sizeof(data));
422 return 1;
423 case 3:
424 PrintAndLogEx(WARNING, "Hex must have even number of digits.");
425 return 1;
426 }
427 cmdp++;
428 breakloop = true;
429 break;
430 }
431 default:
432 PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
433 errors = true;
434 break;
435 }
436
437 if ( breakloop )
438 break;
439 }
440
441 //Validations
442 if (errors || cmdp == 0 ) return usage_sm_raw();
443
444 // arg0 = RFU flags
445 // arg1 = length
446 UsbCommand c = {CMD_SMART_RAW, {0, hexlen, 0}};
447
448 if (active || active_select) {
449 c.arg[0] |= SC_CONNECT;
450 if (active_select)
451 c.arg[0] |= SC_SELECT;
452 }
453
454 if (hexlen > 0) {
455 if (useT0)
456 c.arg[0] |= SC_RAW_T0;
457 else
458 c.arg[0] |= SC_RAW;
459 }
460
461 memcpy(c.d.asBytes, data, hexlen );
462 clearCommandBuffer();
463 SendCommand(&c);
464
465 // reading response from smart card
466 if ( reply ) {
467
468 uint8_t* buf = calloc(USB_CMD_DATA_SIZE, sizeof(uint8_t));
469 if ( !buf )
470 return 1;
471
472 int len = smart_response(buf);
473 if ( len < 0 ) {
474 free(buf);
475 return 2;
476 }
477
478 if ( buf[0] == 0x6C ) {
479 data[4] = buf[1];
480
481 memcpy(c.d.asBytes, data, sizeof(data) );
482 clearCommandBuffer();
483 SendCommand(&c);
484 len = smart_response(buf);
485
486 data[4] = 0;
487 }
488
489 if (decodeTLV && len > 4)
490 TLVPrintFromBuffer(buf, len-2);
491
492 free(buf);
493 }
494 return 0;
495 }
496
497 int ExchangeAPDUSC(uint8_t *datain, int datainlen, bool activateCard, bool leaveSignalON, uint8_t *dataout, int maxdataoutlen, int *dataoutlen) {
498 *dataoutlen = 0;
499
500 if (activateCard)
501 smart_select(false);
502
503 PrintAndLogEx(DEBUG, "APDU SC");
504
505 UsbCommand c = {CMD_SMART_RAW, {SC_RAW_T0, datainlen, 0}};
506 if (activateCard) {
507 c.arg[0] |= SC_SELECT | SC_CONNECT;
508 }
509 memcpy(c.d.asBytes, datain, datainlen);
510 clearCommandBuffer();
511 SendCommand(&c);
512
513 int len = smart_response(dataout);
514
515 if ( len < 0 ) {
516 return 2;
517 }
518
519 // retry
520 if (len > 1 && dataout[len - 2] == 0x6c && datainlen > 4) {
521 UsbCommand c2 = {CMD_SMART_RAW, {SC_RAW_T0, datainlen, 0}};
522 memcpy(c2.d.asBytes, datain, 5);
523
524 // transfer length via T=0
525 c2.d.asBytes[4] = dataout[len - 1];
526
527 clearCommandBuffer();
528 SendCommand(&c2);
529
530 len = smart_response(dataout);
531 }
532 *dataoutlen = len;
533
534 return 0;
535 }
536
537
538 int CmdSmartUpgrade(const char *Cmd) {
539
540 PrintAndLogEx(NORMAL, "");
541 PrintAndLogEx(WARNING, "WARNING - RDV4.0 Smartcard Socket Firmware upgrade.");
542 PrintAndLogEx(WARNING, "A dangerous command, do wrong and you will brick the smart card socket");
543 PrintAndLogEx(NORMAL, "");
544
545 FILE *f;
546 char filename[FILE_PATH_SIZE] = {0};
547 uint8_t cmdp = 0;
548 bool errors = false;
549
550 while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
551 switch (tolower(param_getchar(Cmd, cmdp))) {
552 case 'f':
553 //File handling and reading
554 if ( param_getstr(Cmd, cmdp+1, filename, FILE_PATH_SIZE) >= FILE_PATH_SIZE ) {
555 PrintAndLogEx(FAILED, "Filename too long");
556 errors = true;
557 break;
558 }
559 cmdp += 2;
560 break;
561 case 'h':
562 return usage_sm_upgrade();
563 default:
564 PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
565 errors = true;
566 break;
567 }
568 }
569
570 //Validations
571 if (errors || cmdp == 0 ) return usage_sm_upgrade();
572
573 if (strchr(filename, '\\') || strchr(filename, '/')) {
574 PrintAndLogEx(FAILED, "Filename must not contain \\ or /. Firmware file will be found in client/sc_upgrade_firmware directory.");
575 return 1;
576 }
577
578 char sc_upgrade_file_path[strlen(get_my_executable_directory()) + strlen(SC_UPGRADE_FILES_DIRECTORY) + strlen(filename) + 1];
579 strcpy(sc_upgrade_file_path, get_my_executable_directory());
580 strcat(sc_upgrade_file_path, SC_UPGRADE_FILES_DIRECTORY);
581 strcat(sc_upgrade_file_path, filename);
582 if (strlen(sc_upgrade_file_path) >= FILE_PATH_SIZE ) {
583 PrintAndLogEx(FAILED, "Filename too long");
584 return 1;
585 }
586
587 char sha512filename[FILE_PATH_SIZE];
588 char *bin_extension = filename;
589 char *dot_position = NULL;
590 while ((dot_position = strchr(bin_extension, '.')) != NULL) {
591 bin_extension = dot_position + 1;
592 }
593 if (!strcmp(bin_extension, "BIN")
594 #ifdef _WIN32
595 || !strcmp(bin_extension, "bin")
596 #endif
597 ) {
598 strncpy(sha512filename, filename, strlen(filename) - strlen("bin"));
599 strcat(sha512filename, "sha512.txt");
600 } else {
601 PrintAndLogEx(FAILED, "Filename extension of Firmware Upgrade File must be .BIN");
602 return 1;
603 }
604
605 PrintAndLogEx(INFO, "Checking integrity using SHA512 File %s ...", sha512filename);
606 char sc_upgrade_sha512file_path[strlen(get_my_executable_directory()) + strlen(SC_UPGRADE_FILES_DIRECTORY) + strlen(sha512filename) + 1];
607 strcpy(sc_upgrade_sha512file_path, get_my_executable_directory());
608 strcat(sc_upgrade_sha512file_path, SC_UPGRADE_FILES_DIRECTORY);
609 strcat(sc_upgrade_sha512file_path, sha512filename);
610 if (strlen(sc_upgrade_sha512file_path) >= FILE_PATH_SIZE ) {
611 PrintAndLogEx(FAILED, "Filename too long");
612 return 1;
613 }
614
615 // load firmware file
616 f = fopen(sc_upgrade_file_path, "rb");
617 if ( !f ){
618 PrintAndLogEx(FAILED, "Firmware file not found or locked.");
619 return 1;
620 }
621
622 // get filesize in order to malloc memory
623 fseek(f, 0, SEEK_END);
624 size_t fsize = ftell(f);
625 fseek(f, 0, SEEK_SET);
626
627 if (fsize < 0) {
628 PrintAndLogEx(FAILED, "Could not determine size of firmware file");
629 fclose(f);
630 return 1;
631 }
632
633 uint8_t *dump = calloc(fsize, sizeof(uint8_t));
634 if (!dump) {
635 PrintAndLogEx(FAILED, "Could not allocate memory for firmware");
636 fclose(f);
637 return 1;
638 }
639
640 size_t firmware_size = fread(dump, 1, fsize, f);
641 if (f)
642 fclose(f);
643
644 // load sha512 file
645 f = fopen(sc_upgrade_sha512file_path, "rb");
646 if ( !f ){
647 PrintAndLogEx(FAILED, "SHA-512 file not found or locked.");
648 return 1;
649 }
650
651 // get filesize in order to malloc memory
652 fseek(f, 0, SEEK_END);
653 fsize = ftell(f);
654 fseek(f, 0, SEEK_SET);
655
656 if (fsize < 0) {
657 PrintAndLogEx(FAILED, "Could not determine size of SHA-512 file");
658 fclose(f);
659 return 1;
660 }
661
662 if (fsize < 128) {
663 PrintAndLogEx(FAILED, "SHA-512 file too short");
664 fclose(f);
665 return 1;
666 }
667
668 char hashstring[129];
669 size_t bytes_read = fread(hashstring, 1, 128, f);
670 hashstring[128] = '\0';
671
672 if (f)
673 fclose(f);
674
675 uint8_t hash1[64];
676 if (bytes_read != 128 || param_gethex(hashstring, 0, hash1, 128)) {
677 PrintAndLogEx(FAILED, "Couldn't read SHA-512 file");
678 return 1;
679 }
680
681 uint8_t hash2[64];
682 if (sha512hash(dump, firmware_size, hash2)) {
683 PrintAndLogEx(FAILED, "Couldn't calculate SHA-512 of Firmware");
684 return 1;
685 }
686
687 if (memcmp(hash1, hash2, 64)) {
688 PrintAndLogEx(FAILED, "Couldn't verify integrity of Firmware file (wrong SHA-512)");
689 return 1;
690 }
691
692 PrintAndLogEx(SUCCESS, "RDV4.0 Smartcard Socket Firmware uploading to PM3");
693
694 //Send to device
695 uint32_t index = 0;
696 uint32_t bytes_sent = 0;
697 uint32_t bytes_remaining = firmware_size;
698
699 while (bytes_remaining > 0){
700 uint32_t bytes_in_packet = MIN(USB_CMD_DATA_SIZE, bytes_remaining);
701 UsbCommand c = {CMD_SMART_UPLOAD, {index + bytes_sent, bytes_in_packet, 0}};
702
703 // Fill usb bytes with 0xFF
704 memset(c.d.asBytes, 0xFF, USB_CMD_DATA_SIZE);
705 memcpy(c.d.asBytes, dump + bytes_sent, bytes_in_packet);
706 clearCommandBuffer();
707 SendCommand(&c);
708 if ( !WaitForResponseTimeout(CMD_ACK, NULL, 2000) ) {
709 PrintAndLogEx(WARNING, "timeout while waiting for reply.");
710 free(dump);
711 return 1;
712 }
713
714 bytes_remaining -= bytes_in_packet;
715 bytes_sent += bytes_in_packet;
716 printf("."); fflush(stdout);
717 }
718 free(dump);
719 printf("\n");
720 PrintAndLogEx(SUCCESS, "RDV4.0 Smartcard Socket Firmware updating, don\'t turn off your PM3!");
721
722 // trigger the firmware upgrade
723 UsbCommand c = {CMD_SMART_UPGRADE, {firmware_size, 0, 0}};
724 clearCommandBuffer();
725 SendCommand(&c);
726 UsbCommand resp;
727 if ( !WaitForResponseTimeout(CMD_ACK, &resp, 2500) ) {
728 PrintAndLogEx(WARNING, "timeout while waiting for reply.");
729 return 1;
730 }
731 if ( (resp.arg[0] & 0xFF ) )
732 PrintAndLogEx(SUCCESS, "RDV4.0 Smartcard Socket Firmware upgraded successful");
733 else
734 PrintAndLogEx(FAILED, "RDV4.0 Smartcard Socket Firmware Upgrade failed");
735 return 0;
736 }
737
738 int CmdSmartInfo(const char *Cmd){
739 uint8_t cmdp = 0;
740 bool errors = false, silent = false;
741
742 while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
743 switch (tolower(param_getchar(Cmd, cmdp))) {
744 case 'h': return usage_sm_info();
745 case 's':
746 silent = true;
747 break;
748 default:
749 PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
750 errors = true;
751 break;
752 }
753 cmdp++;
754 }
755
756 //Validations
757 if (errors ) return usage_sm_info();
758
759 UsbCommand c = {CMD_SMART_ATR, {0, 0, 0}};
760 clearCommandBuffer();
761 SendCommand(&c);
762 UsbCommand resp;
763 if ( !WaitForResponseTimeout(CMD_ACK, &resp, 2500) ) {
764 if (!silent) PrintAndLogEx(WARNING, "smart card select failed");
765 return 1;
766 }
767
768 uint8_t isok = resp.arg[0] & 0xFF;
769 if (!isok) {
770 if (!silent) PrintAndLogEx(WARNING, "smart card select failed");
771 return 1;
772 }
773
774 smart_card_atr_t card;
775 memcpy(&card, (smart_card_atr_t *)resp.d.asBytes, sizeof(smart_card_atr_t));
776
777 // print header
778 PrintAndLogEx(INFO, "--- Smartcard Information ---------");
779 PrintAndLogEx(INFO, "-------------------------------------------------------------");
780 PrintAndLogEx(INFO, "ISO7618-3 ATR : %s", sprint_hex(card.atr, card.atr_len));
781 PrintAndLogEx(INFO, "\nhttp://smartcard-atr.appspot.com/parse?ATR=%s", sprint_hex_inrow(card.atr, card.atr_len) );
782
783 // print ATR
784 PrintAndLogEx(NORMAL, "");
785 PrintAndLogEx(INFO, "ATR");
786 PrintATR(card.atr, card.atr_len);
787
788 // print D/F (brom byte TA1 or defaults)
789 PrintAndLogEx(NORMAL, "");
790 PrintAndLogEx(INFO, "D/F (TA1)");
791 int Di = GetATRDi(card.atr, card.atr_len);
792 int Fi = GetATRFi(card.atr, card.atr_len);
793 float F = GetATRF(card.atr, card.atr_len);
794 if (GetATRTA1(card.atr, card.atr_len) == 0x11)
795 PrintAndLogEx(INFO, "Using default values...");
796
797 PrintAndLogEx(NORMAL, "\t- Di=%d", Di);
798 PrintAndLogEx(NORMAL, "\t- Fi=%d", Fi);
799 PrintAndLogEx(NORMAL, "\t- F=%.1f MHz", F);
800
801 if (Di && Fi) {
802 PrintAndLogEx(NORMAL, "\t- Cycles/ETU=%d", Fi/Di);
803 PrintAndLogEx(NORMAL, "\t- %.1f bits/sec at 4MHz", (float)4000000 / (Fi/Di));
804 PrintAndLogEx(NORMAL, "\t- %.1f bits/sec at Fmax=%.1fMHz", (F * 1000000) / (Fi/Di), F);
805 } else {
806 PrintAndLogEx(WARNING, "\t- Di or Fi is RFU.");
807 };
808
809 return 0;
810 }
811
812 int CmdSmartReader(const char *Cmd){
813 uint8_t cmdp = 0;
814 bool errors = false, silent = false;
815
816 while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
817 switch (tolower(param_getchar(Cmd, cmdp))) {
818 case 'h': return usage_sm_reader();
819 case 's':
820 silent = true;
821 break;
822 default:
823 PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
824 errors = true;
825 break;
826 }
827 cmdp++;
828 }
829
830 //Validations
831 if (errors ) return usage_sm_reader();
832
833 UsbCommand c = {CMD_SMART_ATR, {0, 0, 0}};
834 clearCommandBuffer();
835 SendCommand(&c);
836 UsbCommand resp;
837 if ( !WaitForResponseTimeout(CMD_ACK, &resp, 2500) ) {
838 if (!silent) PrintAndLogEx(WARNING, "smart card select failed");
839 return 1;
840 }
841
842 uint8_t isok = resp.arg[0] & 0xFF;
843 if (!isok) {
844 if (!silent) PrintAndLogEx(WARNING, "smart card select failed");
845 return 1;
846 }
847 smart_card_atr_t card;
848 memcpy(&card, (smart_card_atr_t *)resp.d.asBytes, sizeof(smart_card_atr_t));
849
850 PrintAndLogEx(INFO, "ISO7816-3 ATR : %s", sprint_hex(card.atr, card.atr_len));
851 return 0;
852 }
853
854 int CmdSmartSetClock(const char *Cmd){
855 uint8_t cmdp = 0;
856 bool errors = false;
857 uint8_t clock = 0;
858 while (param_getchar(Cmd, cmdp) != 0x00 && !errors) {
859 switch (tolower(param_getchar(Cmd, cmdp))) {
860 case 'h': return usage_sm_setclock();
861 case 'c':
862 clock = param_get8ex(Cmd, cmdp+1, 2, 10);
863 if ( clock > 2)
864 errors = true;
865
866 cmdp += 2;
867 break;
868 default:
869 PrintAndLogEx(WARNING, "Unknown parameter '%c'", param_getchar(Cmd, cmdp));
870 errors = true;
871 break;
872 }
873 }
874
875 //Validations
876 if (errors || cmdp == 0) return usage_sm_setclock();
877
878 UsbCommand c = {CMD_SMART_SETCLOCK, {clock, 0, 0}};
879 clearCommandBuffer();
880 SendCommand(&c);
881 UsbCommand resp;
882 if ( !WaitForResponseTimeout(CMD_ACK, &resp, 2500) ) {
883 PrintAndLogEx(WARNING, "smart card select failed");
884 return 1;
885 }
886
887 uint8_t isok = resp.arg[0] & 0xFF;
888 if (!isok) {
889 PrintAndLogEx(WARNING, "smart card set clock failed");
890 return 1;
891 }
892
893 switch (clock) {
894 case 0:
895 PrintAndLogEx(SUCCESS, "Clock changed to 16mhz giving 10800 baudrate");
896 break;
897 case 1:
898 PrintAndLogEx(SUCCESS, "Clock changed to 8mhz giving 21600 baudrate");
899 break;
900 case 2:
901 PrintAndLogEx(SUCCESS, "Clock changed to 4mhz giving 86400 baudrate");
902 break;
903 default:
904 break;
905 }
906 return 0;
907 }
908
909 int CmdSmartList(const char *Cmd) {
910 CmdHFList("7816");
911 return 0;
912 }
913
914 int CmdSmartBruteforceSFI(const char *Cmd) {
915
916 char ctmp = tolower(param_getchar(Cmd, 0));
917 if (ctmp == 'h') return usage_sm_brute();
918
919 uint8_t data[5] = {0x00, 0xB2, 0x00, 0x00, 0x00};
920
921 PrintAndLogEx(INFO, "Selecting card");
922 if ( !smart_select(false) ) {
923 return 1;
924 }
925
926 PrintAndLogEx(INFO, "Selecting PPSE aid");
927 CmdSmartRaw("s 0 t d 00a404000e325041592e5359532e4444463031");
928 CmdSmartRaw("0 t d 00a4040007a000000004101000"); // mastercard
929 // CmdSmartRaw("0 t d 00a4040007a0000000031010"); // visa
930
931 PrintAndLogEx(INFO, "starting");
932
933 UsbCommand c = {CMD_SMART_RAW, {SC_RAW, sizeof(data), 0}};
934 uint8_t* buf = malloc(USB_CMD_DATA_SIZE);
935 if ( !buf )
936 return 1;
937
938 for (uint8_t i=1; i < 4; i++) {
939 for (int p1=1; p1 < 5; p1++) {
940
941 data[2] = p1;
942 data[3] = (i << 3) + 4;
943
944 memcpy(c.d.asBytes, data, sizeof(data) );
945 clearCommandBuffer();
946 SendCommand(&c);
947
948 smart_response(buf);
949
950 if ( buf[0] == 0x6C ) {
951 data[4] = buf[1];
952
953 memcpy(c.d.asBytes, data, sizeof(data) );
954 clearCommandBuffer();
955 SendCommand(&c);
956 uint8_t len = smart_response(buf);
957
958 // TLV decoder
959 if (len > 4)
960 TLVPrintFromBuffer(buf+1, len-3);
961
962 data[4] = 0;
963 }
964 memset(buf, 0x00, USB_CMD_DATA_SIZE);
965 }
966 }
967 free(buf);
968 return 0;
969 }
970
971 static command_t CommandTable[] = {
972 {"help", CmdHelp, 1, "This help"},
973 {"list", CmdSmartList, 0, "List ISO 7816 history"},
974 {"info", CmdSmartInfo, 0, "Tag information"},
975 {"reader", CmdSmartReader, 0, "Act like an IS07816 reader"},
976 {"raw", CmdSmartRaw, 0, "Send raw hex data to tag"},
977 {"upgrade", CmdSmartUpgrade, 0, "Upgrade firmware"},
978 {"setclock", CmdSmartSetClock, 0, "Set clock speed"},
979 {"brute", CmdSmartBruteforceSFI, 0, "Bruteforce SFI"},
980 {NULL, NULL, 0, NULL}
981 };
982
983 int CmdSmartcard(const char *Cmd) {
984 clearCommandBuffer();
985 CmdsParse(CommandTable, Cmd);
986 return 0;
987 }
988
989 int CmdHelp(const char *Cmd) {
990 CmdsHelp(CommandTable);
991 return 0;
992 }
Impressum, Datenschutz