1 //Peter Fillmore - 2014
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
7 //--------------------------------------------------------------------------------
8 //--------------------------------------------------------------------------------
9 //Routines to support EMV transactions
10 //--------------------------------------------------------------------------------
13 static emvtags currentcard
; //use to hold emv tags for the reader/card during communications
16 // The FPGA will report its internal sending delay in
17 uint16_t FpgaSendQueueDelay
;
18 //variables used for timing purposes:
19 //these are in ssp_clk cycles:
20 //static uint32_t NextTransferTime;
21 static uint32_t LastTimeProxToAirStart
;
22 //static uint32_t LastProxToAirDuration;
24 //load individual tag into current card
25 void EMVloadvalue(uint32_t tag
, uint8_t *datain
){
26 //Dbprintf("TAG=%i\n", tag);
27 //Dbprintf("DATA=%s\n", datain);
28 emv_settag(tag
, datain
, ¤tcard
);
31 void EMVReadRecord(uint8_t arg0
, uint8_t arg1
,emvtags
*currentcard
)
33 uint8_t record
= arg0
;
34 uint8_t sfi
= arg1
& 0x0F; //convert arg1 to number
35 uint8_t receivedAnswer
[MAX_FRAME_SIZE
];
37 //uint8_t receivedAnswerPar[MAX_PARITY_SIZE];
40 tlvtag inputtag
; //create the tag structure
42 //write the result to the provided card
43 if(!emv_readrecord(record
,sfi
,receivedAnswer
)) {
44 if(EMV_DBGLEVEL
>= 1) Dbprintf("readrecord failed");
46 if(*(receivedAnswer
+1) == 0x70){
47 decode_ber_tlv_item(receivedAnswer
+1, &inputtag
);
48 emv_decode_field(inputtag
.value
, inputtag
.valuelength
, currentcard
);
53 Dbprintf("Record not found SFI=%i RECORD=%i", sfi
, record
);
58 void EMVSelectAID(uint8_t *AID
, uint8_t AIDlen
, emvtags
* inputcard
)
60 uint8_t receivedAnswer
[MAX_FRAME_SIZE
];
61 //uint8_t receivedAnswerPar[MAX_PARITY_SIZE];
64 tlvtag inputtag
; //create the tag structure
66 if(!emv_select(AID
, AIDlen
, receivedAnswer
)){
67 if(EMV_DBGLEVEL
>= 1) Dbprintf("AID Select failed");
70 //write the result to the provided card
71 if(*(receivedAnswer
+1) == 0x6F){
72 //decode the 6F template
73 decode_ber_tlv_item(receivedAnswer
+1, &inputtag
);
74 //store 84 and A5 tags
75 emv_decode_field(inputtag
.value
, inputtag
.valuelength
, ¤tcard
);
77 if(currentcard
.tag_A5_len
> 0)
78 emv_decode_field(currentcard
.tag_A5
, currentcard
.tag_A5_len
, ¤tcard
);
80 //copy this result to the DFName
81 if(currentcard
.tag_84_len
== 0)
82 memcpy(currentcard
.tag_DFName
, currentcard
.tag_84
, currentcard
.tag_84_len
);
84 //decode the BF0C result, assuming 1 directory entry for now
85 if(currentcard
.tag_BF0C_len
!=0){
86 emv_decode_field(currentcard
.tag_BF0C
, currentcard
.tag_BF0C_len
, ¤tcard
);}
87 //retrieve the AID, use the AID to decide what transaction flow to use
88 if(currentcard
.tag_61_len
!=0){
89 emv_decode_field(currentcard
.tag_61
, currentcard
.tag_61_len
, ¤tcard
);}
92 DbpString("SELECT AID COMPLETED");
95 int EMVGetProcessingOptions(uint8_t *PDOL
, uint8_t PDOLlen
, emvtags
* inputcard
)
97 uint8_t receivedAnswer
[MAX_FRAME_SIZE
];
98 //uint8_t receivedAnswerPar[MAX_PARITY_SIZE];
101 tlvtag inputtag
; //create the tag structure
103 if(!emv_getprocessingoptions(PDOL
, PDOLlen
, receivedAnswer
)){
104 if(EMV_DBGLEVEL
>= 1) Dbprintf("get processing options failed");
107 //write the result to the provided card
109 if(receivedAnswer
[1] == 0x80){
112 decode_ber_tlv_item(receivedAnswer
+1, &inputtag
);
113 memcpy(currentcard
.tag_82
, &inputtag
.value
, sizeof(currentcard
.tag_82
));
114 memcpy(currentcard
.tag_94
, &inputtag
.value
[2], inputtag
.valuelength
- sizeof(currentcard
.tag_82
));
115 currentcard
.tag_94_len
= inputtag
.valuelength
- sizeof(currentcard
.tag_82
);
117 else if(receivedAnswer
[1] == 0x77){
118 //decode the 77 template
119 decode_ber_tlv_item(receivedAnswer
+1, &inputtag
);
120 //store 82 and 94 tags (AIP, AFL)
121 emv_decode_field(inputtag
.value
, inputtag
.valuelength
, ¤tcard
);
123 if(EMV_DBGLEVEL
>= 2)
124 DbpString("GET PROCESSING OPTIONS COMPLETE");
128 int EMVGetChallenge(emvtags
* inputcard
)
130 uint8_t receivedAnswer
[MAX_FRAME_SIZE
];
131 //uint8_t receivedAnswerPar[MAX_PARITY_SIZE];
133 //tlvtag inputtag; //create the tag structure
135 if(!emv_getchallenge(receivedAnswer
)){
136 if(EMV_DBGLEVEL
>= 1) Dbprintf("get processing options failed");
142 int EMVGenerateAC(uint8_t refcontrol
, emvtags
* inputcard
)
144 uint8_t receivedAnswer
[MAX_FRAME_SIZE
];
145 uint8_t cdolcommand
[MAX_FRAME_SIZE
];
146 uint8_t cdolcommandlen
= 0;
149 //uint8_t receivedAnswerPar[MAX_PARITY_SIZE];
150 if(currentcard
.tag_8C_len
> 0) {
151 emv_generateDOL(currentcard
.tag_8C
, currentcard
.tag_8C_len
, ¤tcard
, cdolcommand
, &cdolcommandlen
); }
153 //cdolcommand = NULL; //cdol val is null
157 //tlvtag inputtag; //create the tag structure
159 if(!emv_generateAC(refcontrol
, cdolcommand
, cdolcommandlen
,receivedAnswer
)){
160 if(EMV_DBGLEVEL
>= 1) Dbprintf("get processing options failed");
163 if(receivedAnswer
[2] == 0x77) //format 2 data field returned
165 decode_ber_tlv_item(&receivedAnswer
[2], &temptag
);
166 emv_decode_field(temptag
.value
, temptag
.valuelength
, ¤tcard
);
172 //function to perform paywave transaction
173 //takes in TTQ, amount authorised, unpredicable number and transaction currency code
174 int EMV_PaywaveTransaction()
176 uint8_t cardMode
= 0;
177 //determine mode of transaction from TTQ
178 if((currentcard
.tag_9F66
[0] & 0x40) == 0x40) {
181 else if((currentcard
.tag_9F66
[0] & 0x20) == 0x20) {
182 cardMode
= VISA_FDDA
;
184 else if((currentcard
.tag_9F66
[0] & 0x80) == 0x80) {
185 if((currentcard
.tag_9F66
[1] & 0x80) == 1) { //CVN17
186 cardMode
= VISA_CVN17
;
189 cardMode
= VISA_DCVV
;
193 EMVSelectAID(currentcard
.tag_4F
,currentcard
.tag_4F_len
, ¤tcard
); //perform second AID command
196 uint8_t pdolcommand
[20]; //20 byte buffer for pdol data
197 uint8_t pdolcommandlen
= 0;
198 if(currentcard
.tag_9F38_len
> 0) {
199 emv_generateDOL(currentcard
.tag_9F38
, currentcard
.tag_9F38_len
, ¤tcard
, pdolcommand
, &pdolcommandlen
);
201 Dbhexdump(pdolcommandlen
, pdolcommand
,false);
203 if(!EMVGetProcessingOptions(pdolcommand
,pdolcommandlen
, ¤tcard
)) {
204 if(EMV_DBGLEVEL
>= 1) Dbprintf("PDOL failed");
209 Dbhexdump(currentcard
.tag_94_len
, currentcard
.tag_94
,false);
211 Dbhexdump(2, currentcard
.tag_82
, false);
212 emv_decodeAIP(currentcard
.tag_82
);
214 // //decode the AFL list and read records
217 uint8_t recordstart
= 0;
218 uint8_t recordend
= 0;
219 if(currentcard
.tag_94_len
> 0){
220 while( i
< currentcard
.tag_94_len
){
221 sfi
= (currentcard
.tag_94
[i
++] & 0xF8) >> 3;
222 recordstart
= currentcard
.tag_94
[i
++];
223 recordend
= currentcard
.tag_94
[i
++];
224 for(int j
=recordstart
; j
<(recordend
+1); j
++){
226 EMVReadRecord(j
,sfi
, ¤tcard
);
227 //while(responsebuffer[0] == 0xF2) {
228 // EMVReadRecord(j,sfi, ¤tcard);
235 EMVReadRecord(1,1,¤tcard
);
236 EMVReadRecord(1,2,¤tcard
);
237 EMVReadRecord(1,3,¤tcard
);
238 EMVReadRecord(2,1,¤tcard
);
239 EMVReadRecord(2,2,¤tcard
);
240 EMVReadRecord(2,3,¤tcard
);
241 EMVReadRecord(3,1,¤tcard
);
242 EMVReadRecord(3,3,¤tcard
);
243 EMVReadRecord(4,2,¤tcard
);
245 //EMVGetChallenge(¤tcard);
246 //memcpy(currentcard.tag_9F4C,&responsebuffer[1],8); // ICC UN
247 EMVGenerateAC(0x81,¤tcard
);
249 Dbprintf("CARDMODE=%i",cardMode
);
254 int EMV_PaypassTransaction()
256 //uint8_t *responsebuffer = emv_get_bigbufptr();
257 //tlvtag temptag; //buffer for decoded tags
258 //get the current block counter
259 //select the AID (Mastercard
260 EMVSelectAID(currentcard
.tag_4F
,currentcard
.tag_4F_len
, ¤tcard
);
263 uint8_t pdolcommand
[20]; //20 byte buffer for pdol data
264 uint8_t pdolcommandlen
= 0;
265 if(currentcard
.tag_9F38_len
> 0) {
266 emv_generateDOL(currentcard
.tag_9F38
, currentcard
.tag_9F38_len
, ¤tcard
, pdolcommand
, &pdolcommandlen
);
268 if(EMVGetProcessingOptions(pdolcommand
,pdolcommandlen
, ¤tcard
)) {
269 if(EMV_DBGLEVEL
>= 1) Dbprintf("PDOL failed");
274 Dbhexdump(currentcard
.tag_94_len
, currentcard
.tag_94
,false);
276 Dbhexdump(2, currentcard
.tag_82
, false);
277 emv_decodeAIP(currentcard
.tag_82
);
279 //decode the AFL list and read records
282 uint8_t recordstart
= 0;
283 uint8_t recordend
= 0;
285 while( i
< currentcard
.tag_94_len
){
286 sfi
= (currentcard
.tag_94
[i
++] & 0xF8) >> 3;
287 recordstart
= currentcard
.tag_94
[i
++];
288 recordend
= currentcard
.tag_94
[i
++];
289 for(int j
=recordstart
; j
<(recordend
+1); j
++){
291 EMVReadRecord(j
,sfi
, ¤tcard
);
292 //while(responsebuffer[0] == 0xF2) {
293 // EMVReadRecord(j,sfi, ¤tcard);
298 /* get ICC dynamic data */
299 if((currentcard
.tag_82
[0] & AIP_CDA_SUPPORTED
) == AIP_CDA_SUPPORTED
)
301 //DDA supported, so perform GENERATE AC
302 //generate the iCC UN
303 EMVGetChallenge(¤tcard
);
304 //memcpy(currentcard.tag_9F4C,&responsebuffer[1],8); // ICC UN
305 EMVGenerateAC(0x80,¤tcard
);
309 //if(currentcard.tag_8D_len > 0) {
310 // emv_generateDOL(currentcard.tag_8D, currentcard.tag_8D_len, ¤tcard, cdolcommand, &cdolcommandlen); }
312 // //cdolcommand = NULL; //cdol val is null
313 // cdolcommandlen = 0;
315 //emv_generateAC(0x80, cdolcommand,cdolcommandlen, ¤tcard);
317 //if(responsebuffer[1] == 0x77) //format 2 data field returned
319 // decode_ber_tlv_item(&responsebuffer[1], &temptag);
320 // emv_decode_field(temptag.value, temptag.valuelength, ¤tcard);
323 //generate cryptographic checksum
324 //uint8_t udol[4] = {0x00,0x00,0x00,0x00};
325 //emv_computecryptogram(udol, sizeof(udol));
326 //if(responsebuffer[1] == 0x77) //format 2 data field returned
328 // decode_ber_tlv_item(&responsebuffer[1], &temptag);
329 // emv_decode_field(temptag.value, temptag.valuelength, ¤tcard);
334 void EMVTransaction()
337 uint8_t uid
[10] = {0x00};
341 BigBuf_free(); BigBuf_Clear_ext(false);
349 iso14443a_setup(FPGA_HF_ISO14443A_READER_LISTEN
);
351 if(!iso14443a_select_card(uid
,NULL
,&cuid
)) {
352 if(EMV_DBGLEVEL
>= 1) Dbprintf("Can't select card");
356 EMVSelectAID((uint8_t *)DF_PSE
, 14, ¤tcard
); //hard coded len
358 if (!memcmp(currentcard
.tag_4F
, AID_MASTERCARD
, sizeof(AID_MASTERCARD
))){
359 Dbprintf("Mastercard Paypass Card Detected");
360 EMV_PaypassTransaction();
362 else if (!memcmp(currentcard
.tag_4F
, AID_VISA
, sizeof(AID_VISA
))){
363 Dbprintf("VISA Paywave Card Detected");
364 EMV_PaywaveTransaction();
366 //TODO: add other card schemes like AMEX, JCB, China Unionpay etc
369 if (EMV_DBGLEVEL
>= 2) DbpString("EMV TRANSACTION FINISHED");
371 FpgaWriteConfWord(FPGA_MAJOR_MODE_OFF
);
375 void EMVdumpcard(void){
376 dumpCard(¤tcard
);
380 //-----------------------------------------------------------------------------
381 // Main loop of simulated tag: receive commands from reader, decide what
382 // response to send, and send it.
383 //-----------------------------------------------------------------------------
384 void SimulateEMVcard()
386 //uint8_t sak; //select ACKnowledge
387 uint16_t readerPacketLen
= 64; //reader packet length - provided by RATS, default to 64 bytes if RATS not supported
389 // The first response contains the ATQA (note: bytes are transmitted in reverse order).
390 //uint8_t atqapacket[2];
392 // The second response contains the (mandatory) first 24 bits of the UID
393 uint8_t uid0packet
[5] = {0x00};
394 memcpy(uid0packet
, currentcard
.UID
, sizeof(uid0packet
));
395 // Check if the uid uses the (optional) part
396 uint8_t uid1packet
[5] = {0x00};
397 memcpy(uid1packet
, currentcard
.UID
, sizeof(uid1packet
));
399 // Calculate the BitCountCheck (BCC) for the first 4 bytes of the UID.
400 uid0packet
[4] = uid0packet
[0] ^ uid0packet
[1] ^ uid0packet
[2] ^ uid0packet
[3];
402 // Prepare the mandatory SAK (for 4 and 7 byte UID)
403 uint8_t sak0packet
[3] = {0x00};
404 memcpy(sak0packet
,¤tcard
.SAK1
,1);
405 ComputeCrc14443(CRC_14443_A
, sak0packet
, 1, &sak0packet
[1], &sak0packet
[2]);
406 uint8_t sak1packet
[3] = {0x00};
407 memcpy(sak1packet
,¤tcard
.SAK2
,1);
408 // Prepare the optional second SAK (for 7 byte UID), drop the cascade bit
409 ComputeCrc14443(CRC_14443_A
, sak1packet
, 1, &sak1packet
[1], &sak1packet
[2]);
411 uint8_t authanspacket
[] = { 0x00, 0x00, 0x00, 0x00 }; // Very random tag nonce
412 //setup response to ATS
413 uint8_t ratspacket
[currentcard
.ATS_len
];
414 memcpy(ratspacket
,currentcard
.ATS
, currentcard
.ATS_len
);
415 AppendCrc14443a(ratspacket
,sizeof(ratspacket
)-2);
417 // Format byte = 0x58: FSCI=0x08 (FSC=256), TA(1) and TC(1) present,
418 // TA(1) = 0x80: different divisors not supported, DR = 1, DS = 1
419 // TB(1) = not present. Defaults: FWI = 4 (FWT = 256 * 16 * 2^4 * 1/fc = 4833us), SFGI = 0 (SFG = 256 * 16 * 2^0 * 1/fc = 302us)
420 // TC(1) = 0x02: CID supported, NAD not supported
421 //ComputeCrc14443(CRC_14443_A, response6, 4, &response6[4], &response6[5]);
423 //Receive Acknowledge responses differ by PCB byte
424 uint8_t rack0packet
[] = {0xa2,0x00,0x00};
425 AppendCrc14443a(rack0packet
,1);
426 uint8_t rack1packet
[] = {0xa3,0x00,0x00};
427 AppendCrc14443a(rack1packet
,1);
428 //Negative Acknowledge
429 uint8_t rnak0packet
[] = {0xb2,0x00,0x00};
430 uint8_t rnak1packet
[] = {0xb3,0x00,0x00};
431 AppendCrc14443a(rnak0packet
,1);
432 AppendCrc14443a(rnak1packet
,1);
434 //Protocol and parameter selection response, just say yes
435 uint8_t ppspacket
[] = {0xd0,0x00,0x00};
436 AppendCrc14443a(ppspacket
,1);
438 //hardcoded WTX packet - set to max time (49)
439 uint8_t wtxpacket
[] ={0xf2,0x31,0x00,0x00};
440 AppendCrc14443a(wtxpacket
,2);
442 //added additional responses for different readers, namely protocol parameter select and Receive acknowledments. - peter fillmore.
443 //added defininitions for predone responses to aid readability
455 #define PPSresponse 11
458 #define TAG_RESPONSE_COUNT 13
459 tag_response_info_t responses
[TAG_RESPONSE_COUNT
] = {
460 { .response
= currentcard
.ATQA
, .response_n
= sizeof(currentcard
.ATQA
) }, // Answer to request - respond with card type
461 { .response
= uid0packet
, .response_n
= sizeof(uid0packet
) }, // Anticollision cascade1 - respond with uid
462 { .response
= uid1packet
, .response_n
= sizeof(uid1packet
) }, // Anticollision cascade2 - respond with 2nd half of uid if asked
463 { .response
= sak0packet
, .response_n
= sizeof(sak0packet
) }, // Acknowledge select - cascade 1
464 { .response
= sak1packet
, .response_n
= sizeof(sak1packet
) }, // Acknowledge select - cascade 2
465 { .response
= authanspacket
, .response_n
= sizeof(authanspacket
) }, // Authentication answer (random nonce)
466 { .response
= ratspacket
, .response_n
= sizeof(ratspacket
) }, // dummy ATS (pseudo-ATR), answer to RATS
467 { .response
= rack0packet
, .response_n
= sizeof(rack0packet
) }, //R(ACK)0
468 { .response
= rack1packet
, .response_n
= sizeof(rack1packet
) }, //R(ACK)0
469 { .response
= rnak0packet
, .response_n
= sizeof(rnak0packet
) }, //R(NAK)0
470 { .response
= rnak1packet
, .response_n
= sizeof(rnak1packet
) }, //R(NAK)1
471 { .response
= ppspacket
, .response_n
= sizeof(ppspacket
)}, //PPS packet
472 { .response
= wtxpacket
, .response_n
= sizeof(wtxpacket
)}, //WTX packet
475 //calculated length of predone responses
476 uint16_t allocatedtaglen
= 0;
477 for(int i
=0;i
<TAG_RESPONSE_COUNT
;i
++){
478 allocatedtaglen
+= responses
[i
].response_n
;
480 //uint8_t selectOrder = 0;
482 BigBuf_free_keep_EM();
483 // Allocate 512 bytes for the dynamic modulation, created when the reader queries for it
484 // Such a response is less time critical, so we can prepare them on the fly
486 #define DYNAMIC_RESPONSE_BUFFER_SIZE 256 //max frame size
487 #define DYNAMIC_MODULATION_BUFFER_SIZE 2 + 9*DYNAMIC_RESPONSE_BUFFER_SIZE //(start and stop bit, 8 bit packet with 1 bit parity
489 //uint8_t dynamic_response_buffer[DYNAMIC_RESPONSE_BUFFER_SIZE];
490 //uint8_t dynamic_modulation_buffer[DYNAMIC_MODULATION_BUFFER_SIZE];
491 uint8_t *dynamic_response_buffer
= BigBuf_malloc(DYNAMIC_RESPONSE_BUFFER_SIZE
);
492 uint8_t *dynamic_modulation_buffer
= BigBuf_malloc(DYNAMIC_MODULATION_BUFFER_SIZE
);
494 tag_response_info_t dynamic_response_info
= {
495 .response
= dynamic_response_buffer
,
497 .modulation
= dynamic_modulation_buffer
,
500 // allocate buffers from BigBuf (so we're not in the stack)
501 uint8_t *receivedCmd
= BigBuf_malloc(MAX_FRAME_SIZE
);
502 uint8_t *receivedCmdPar
= BigBuf_malloc(MAX_PARITY_SIZE
);
503 //uint8_t* free_buffer_pointer;
504 //free_buffer_pointer = BigBuf_malloc((allocatedtaglen*8) +(allocatedtaglen) + (TAG_RESPONSE_COUNT * 3));
505 BigBuf_malloc((allocatedtaglen
*8) +(allocatedtaglen
) + (TAG_RESPONSE_COUNT
* 3));
510 // Prepare the responses of the anticollision phase
511 // there will be not enough time to do this at the moment the reader sends it REQA
512 for (size_t i
=0; i
<TAG_RESPONSE_COUNT
; i
++)
513 prepare_allocated_tag_modulation(&responses
[i
]);
517 // To control where we are in the protocol
520 int currentblock
= 1; //init to 1
521 int previousblock
= 0; //used to store previous block counter
523 // Just to allow some checks
528 // We need to listen to the high-frequency, peak-detected path.
529 iso14443a_setup(FPGA_HF_ISO14443A_TAGSIM_LISTEN
);
532 tag_response_info_t
* p_response
;
536 // Clean receive command buffer
538 if(!GetIso14443aCommandFromReader(receivedCmd
, receivedCmdPar
, &len
)) {
539 DbpString("Button press");
545 // Okay, look at the command now.
546 previousblock
= currentblock
; //get previous block
548 currentblock
= receivedCmd
[0] & 0x01;
550 if(receivedCmd
[0] == 0x26) { // Received a REQUEST
551 p_response
= &responses
[ATR
]; order
= REQA
;
552 } else if(receivedCmd
[0] == 0x52) { // Received a WAKEUP
553 p_response
= &responses
[ATR
]; order
= WUPA
;
554 } else if(receivedCmd
[1] == 0x20 && receivedCmd
[0] == 0x93) { // Received request for UID (cascade 1)
555 p_response
= &responses
[UID1
]; order
= SELUID1
;
556 } else if(receivedCmd
[1] == 0x20 && receivedCmd
[0] == 0x95) { // Received request for UID (cascade 2)
557 p_response
= &responses
[UID2
]; order
= SELUID2
;
558 } else if(receivedCmd
[1] == 0x70 && receivedCmd
[0] == 0x93) { // Received a SELECT (cascade 1)
559 p_response
= &responses
[SELACK1
]; order
= SEL1
;
560 } else if(receivedCmd
[1] == 0x70 && receivedCmd
[0] == 0x95) { // Received a SELECT (cascade 2)
561 p_response
= &responses
[SELACK2
]; order
= SEL2
;
562 } else if((receivedCmd
[0] & 0xA2) == 0xA2){ //R-Block received
563 if(previousblock
== currentblock
){ //rule 11, retransmit last block
564 p_response
= &dynamic_response_info
;
566 if((receivedCmd
[0] & 0xB2) == 0xB2){ //RNAK, rule 12
567 if(currentblock
== 0)
568 p_response
= &responses
[RACK0
];
570 p_response
= &responses
[RACK1
];
573 //TODO: implement chaining
577 else if(receivedCmd
[0] == 0xD0){ //Protocol and parameter selection response
578 p_response
= &responses
[PPSresponse
];
581 else if(receivedCmd
[0] == 0x30) { // Received a (plain) READ
582 //we're an EMV card - so no read commands
584 } else if(receivedCmd
[0] == 0x50) { // Received a HALT
585 LogTrace(receivedCmd
, Uart
.len
, Uart
.startTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.endTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.parity
, TRUE
);
588 } else if(receivedCmd
[0] == 0x60 || receivedCmd
[0] == 0x61) { // Received an authentication request
589 p_response
= &responses
[AUTH_ANS
];
591 } else if(receivedCmd
[0] == 0xE0) { // Received a RATS request
592 readerPacketLen
= GetReaderLength(receivedCmd
); //get length of supported packet
593 p_response
= &responses
[ATS
];
595 } else if (order
== AUTH
&& len
== 8) { // Received {nr] and {ar} (part of authentication)
596 LogTrace(receivedCmd
, Uart
.len
, Uart
.startTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.endTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.parity
, TRUE
);
597 uint32_t nr
= bytes_to_num(receivedCmd
,4);
598 uint32_t ar
= bytes_to_num(receivedCmd
+4,4);
599 Dbprintf("Auth attempt {nr}{ar}: %08x %08x",nr
,ar
);
601 // Check for ISO 14443A-4 compliant commands, look at left nibble
602 switch (receivedCmd
[0]) {
604 case 0x0A: // IBlock (command)
607 dynamic_response_info
.response_n
= 0;
608 dynamic_response_info
.response
[0] = receivedCmd
[0]; // copy PCB
609 //dynamic_response_info.response[1] = receivedCmd[1]; // copy PCB
610 dynamic_response_info
.response_n
++ ;
611 switch(receivedCmd
[1]) {
613 switch(receivedCmd
[2]){
615 if(receivedCmd
[5] == 0x0E){
617 else if(receivedCmd
[5] == 0x07){
620 else{ //send not supported msg
621 memcpy(dynamic_response_info
.response
+1, "\x6a\x82", 2);
622 dynamic_response_info
.response_n
+= 2;
625 case 0xB2: //read record
626 if(receivedCmd
[3] == 0x01 && receivedCmd
[4] == 0x0C){
627 dynamic_response_info
.response_n
+= 2;
628 Dbprintf("READ RECORD 1 1");
634 switch(receivedCmd
[2]){
635 case 0xA8: //get processing options
641 case 0x1B: { // Chaining command
642 dynamic_response_info
.response
[0] = 0xaa | ((receivedCmd
[0]) & 1);
643 dynamic_response_info
.response_n
= 2;
648 dynamic_response_info
.response
[0] = receivedCmd
[0] ^ 0x11;
649 dynamic_response_info
.response_n
= 2;
653 memcpy(dynamic_response_info
.response
,"\xAB\x00",2);
654 dynamic_response_info
.response_n
= 2;
658 case 0xC2: { // Readers sends deselect command
659 //we send the command back - this is what tags do in android implemenation i believe - peterfillmore
660 memcpy(dynamic_response_info
.response
,receivedCmd
,1);
661 dynamic_response_info
.response_n
= 1;
665 // Never seen this command before
666 LogTrace(receivedCmd
, Uart
.len
, Uart
.startTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.endTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.parity
, TRUE
);
667 Dbprintf("Received unknown command (len=%d):",len
);
668 Dbhexdump(len
,receivedCmd
,false);
670 dynamic_response_info
.response_n
= 0;
674 if (dynamic_response_info
.response_n
> 0) {
675 // Copy the CID from the reader query
676 //dynamic_response_info.response[1] = receivedCmd[1];
678 // Add CRC bytes, always used in ISO 14443A-4 compliant cards
679 AppendCrc14443a(dynamic_response_info
.response
,dynamic_response_info
.response_n
);
680 dynamic_response_info
.response_n
+= 2;
681 if(dynamic_response_info
.response_n
> readerPacketLen
){ //throw error if our reader doesn't support the send packet length
682 Dbprintf("Error: tag response is longer then what the reader supports, TODO:implement command chaining");
683 LogTrace(receivedCmd
, Uart
.len
, Uart
.startTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.endTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.parity
, TRUE
);
686 if (prepare_tag_modulation(&dynamic_response_info
,DYNAMIC_MODULATION_BUFFER_SIZE
) == false) {
687 Dbprintf("Error preparing tag response");
688 LogTrace(receivedCmd
, Uart
.len
, Uart
.startTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.endTime
*16 - DELAY_AIR2ARM_AS_TAG
, Uart
.parity
, TRUE
);
691 p_response
= &dynamic_response_info
;
695 // Count number of wakeups received after a halt
696 if(order
== HLTA
&& lastorder
== PPS
) { happened
++; }
698 // Count number of other messages after a halt
699 if(order
!= HLTA
&& lastorder
== PPS
) { happened2
++; }
701 if(cmdsRecvd
> 999) {
702 DbpString("1000 commands later...");
707 if (p_response
!= NULL
) {
708 EmSendCmd14443aRaw(p_response
->modulation
, p_response
->modulation_n
, receivedCmd
[0] == 0x52);
709 // do the tracing for the previous reader request and this tag answer:
710 uint8_t par
[MAX_PARITY_SIZE
] = {0x00};
711 GetParity(p_response
->response
, p_response
->response_n
, par
);
713 EmLogTrace(Uart
.output
,
715 Uart
.startTime
*16 - DELAY_AIR2ARM_AS_TAG
,
716 Uart
.endTime
*16 - DELAY_AIR2ARM_AS_TAG
,
718 p_response
->response
,
719 p_response
->response_n
,
720 LastTimeProxToAirStart
*16 + DELAY_ARM2AIR_AS_TAG
,
721 (LastTimeProxToAirStart
+ p_response
->ProxToAirDuration
)*16 + DELAY_ARM2AIR_AS_TAG
,
726 Dbprintf("Trace Full. Simulation stopped.");
731 Dbprintf("%x %x %x", happened
, happened2
, cmdsRecvd
);
733 BigBuf_free_keep_EM();