}
}
}
+
static int EmSendCmd14443aRaw(uint8_t *resp, int respLen, int correctionNeeded);
+int EmSend4bitEx(uint8_t resp, int correctionNeeded);
+int EmSend4bit(uint8_t resp);
+int EmSendCmdExPar(uint8_t *resp, int respLen, int correctionNeeded, uint32_t par);
+int EmSendCmdExPar(uint8_t *resp, int respLen, int correctionNeeded, uint32_t par);
+int EmSendCmdEx(uint8_t *resp, int respLen, int correctionNeeded);
+int EmSendCmd(uint8_t *resp, int respLen);
+int EmSendCmdPar(uint8_t *resp, int respLen, uint32_t par);
//-----------------------------------------------------------------------------
// Main loop of simulated tag: receive commands from reader, decide what
// response to send, and send it.
//-----------------------------------------------------------------------------
-void SimulateIso14443aTag(int tagType, int uid_1st, int uid_2nd)
+void SimulateIso14443aTag(int tagType, int uid_1st, int uid_2nd, byte_t* data)
{
// Enable and clear the trace
tracing = TRUE;
// Response to a read request - not implemented atm
uint8_t *resp4 = (((uint8_t *)BigBuf) + FREE_BUFFER_OFFSET + (166*4));
- int resp4Len;
+// int resp4Len;
// Authenticate response - nonce
uint8_t *resp5 = (((uint8_t *)BigBuf) + FREE_BUFFER_OFFSET + (166*5));
int cmdsRecvd = 0;
uint8_t* respdata = NULL;
int respsize = 0;
- uint8_t nack = 0x04;
+// uint8_t nack = 0x04;
memset(receivedCmd, 0x44, RECV_CMD_SIZE);
// Strange answer is an example of rare message size (3 bits)
CodeStrangeAnswerAsTag();
- memcpy(resp4, ToSend, ToSendMax); resp4Len = ToSendMax;
+ memcpy(resp4, ToSend, ToSendMax);// resp4Len = ToSendMax;
// Authentication answer (random nonce)
CodeIso14443aAsTag(response5, sizeof(response5));
DbpString("button press");
break;
}
+
+ if (tracing) {
+ LogTrace(receivedCmd,len, 0, Uart.parityBits, TRUE);
+ }
+
// doob - added loads of debug strings so we can see what the reader is saying to us during the sim as hi14alist is not populated
// Okay, look at the command now.
lastorder = order;
respdata = response3a;
respsize = sizeof(response3a);
} else if(receivedCmd[0] == 0x30) { // Received a (plain) READ
- resp = resp4; respLen = resp4Len; order = 4; // Do nothing
+// resp = resp4; respLen = resp4Len; order = 4; // Do nothing
+// respdata = &nack;
+// respsize = sizeof(nack); // 4-bit answer
+ EmSendCmdEx(data+(4*receivedCmd[0]),16,false);
Dbprintf("Read request from reader: %x %x",receivedCmd[0],receivedCmd[1]);
- respdata = &nack;
- respsize = sizeof(nack); // 4-bit answer
+ // We already responded, do not send anything with the EmSendCmd14443aRaw() that is called below
+ respLen = 0;
} else if(receivedCmd[0] == 0x50) { // Received a HALT
// DbpString("Reader requested we HALT!:");
// Do not respond
}
if (tracing) {
- LogTrace(receivedCmd,len, 0, Uart.parityBits, TRUE);
if (respdata != NULL) {
LogTrace(respdata,respsize, 0, SwapBits(GetParity(respdata,respsize),respsize), FALSE);
}
}
//-----------------------------------------------------------------------------
-// Code a 7-bit command without parity bit
-// This is especially for 0x26 and 0x52 (REQA and WUPA)
+// Prepare reader command (in bits, support short frames) to send to FPGA
//-----------------------------------------------------------------------------
-void ShortFrameFromReader(const uint8_t bt)
-{
- int j;
- int last;
- uint8_t b;
-
- ToSendReset();
-
- // Start of Communication (Seq. Z)
- ToSend[++ToSendMax] = SEC_Z;
- last = 0;
-
- b = bt;
- for(j = 0; j < 7; j++) {
- if(b & 1) {
- // Sequence X
- ToSend[++ToSendMax] = SEC_X;
- last = 1;
- } else {
- if(last == 0) {
- // Sequence Z
- ToSend[++ToSendMax] = SEC_Z;
- }
- else {
- // Sequence Y
- ToSend[++ToSendMax] = SEC_Y;
- last = 0;
- }
- }
- b >>= 1;
- }
-
- // End of Communication
- if(last == 0) {
- // Sequence Z
- ToSend[++ToSendMax] = SEC_Z;
- }
- else {
- // Sequence Y
- ToSend[++ToSendMax] = SEC_Y;
- last = 0;
- }
- // Sequence Y
- ToSend[++ToSendMax] = SEC_Y;
-
- // Just to be sure!
- ToSend[++ToSendMax] = SEC_Y;
- ToSend[++ToSendMax] = SEC_Y;
- ToSend[++ToSendMax] = SEC_Y;
-
- // Convert from last character reference to length
- ToSendMax++;
-}
-
-//-----------------------------------------------------------------------------
-// Prepare reader command to send to FPGA
-//
-//-----------------------------------------------------------------------------
-void CodeIso14443aAsReaderPar(const uint8_t * cmd, int len, uint32_t dwParity)
+void CodeIso14443aBitsAsReaderPar(const uint8_t * cmd, int bits, uint32_t dwParity)
{
int i, j;
int last;
ToSend[++ToSendMax] = SEC_Z;
last = 0;
+ size_t bytecount = nbytes(bits);
// Generate send structure for the data bits
- for (i = 0; i < len; i++) {
+ for (i = 0; i < bytecount; i++) {
// Get the current byte to send
b = cmd[i];
+ size_t bitsleft = MIN((bits-(i*8)),8);
- for (j = 0; j < 8; j++) {
+ for (j = 0; j < bitsleft; j++) {
if (b & 1) {
// Sequence X
ToSend[++ToSendMax] = SEC_X;
b >>= 1;
}
- // Get the parity bit
- if ((dwParity >> i) & 0x01) {
- // Sequence X
- ToSend[++ToSendMax] = SEC_X;
- last = 1;
- } else {
- if (last == 0) {
- // Sequence Z
- ToSend[++ToSendMax] = SEC_Z;
+ // Only transmit (last) parity bit if we transmitted a complete byte
+ if (j == 8) {
+ // Get the parity bit
+ if ((dwParity >> i) & 0x01) {
+ // Sequence X
+ ToSend[++ToSendMax] = SEC_X;
+ last = 1;
} else {
- // Sequence Y
- ToSend[++ToSendMax] = SEC_Y;
- last = 0;
+ if (last == 0) {
+ // Sequence Z
+ ToSend[++ToSendMax] = SEC_Z;
+ } else {
+ // Sequence Y
+ ToSend[++ToSendMax] = SEC_Y;
+ last = 0;
+ }
}
}
}
ToSendMax++;
}
+//-----------------------------------------------------------------------------
+// Prepare reader command to send to FPGA
+//-----------------------------------------------------------------------------
+void CodeIso14443aAsReaderPar(const uint8_t * cmd, int len, uint32_t dwParity)
+{
+ CodeIso14443aBitsAsReaderPar(cmd,len*8,dwParity);
+}
+
//-----------------------------------------------------------------------------
// Wait for commands from reader
// Stop when button is pressed (return 1) or field was gone (return 2)
}
}
-void ReaderTransmitShort(const uint8_t* bt)
+void ReaderTransmitBitsPar(uint8_t* frame, int bits, uint32_t par)
{
int wait = 0;
int samples = 0;
-
- ShortFrameFromReader(*bt);
-
- // Select the card
- TransmitFor14443a(ToSend, ToSendMax, &samples, &wait);
-
- // Store reader command in buffer
- if (tracing) LogTrace(bt,1,0,GetParity(bt,1),TRUE);
-}
-
-void ReaderTransmitPar(uint8_t* frame, int len, uint32_t par)
-{
- int wait = 0;
- int samples = 0;
-
+
// This is tied to other size changes
// uint8_t* frame_addr = ((uint8_t*)BigBuf) + 2024;
- CodeIso14443aAsReaderPar(frame,len,par);
-
+ CodeIso14443aBitsAsReaderPar(frame,bits,par);
+
// Select the card
TransmitFor14443a(ToSend, ToSendMax, &samples, &wait);
if(trigger)
LED_A_ON();
-
+
// Store reader command in buffer
- if (tracing) LogTrace(frame,len,0,par,TRUE);
+ if (tracing) LogTrace(frame,nbytes(bits),0,par,TRUE);
}
+void ReaderTransmitPar(uint8_t* frame, int len, uint32_t par)
+{
+ ReaderTransmitBitsPar(frame,len*8,par);
+}
void ReaderTransmit(uint8_t* frame, int len)
{
// Generate parity and redirect
- ReaderTransmitPar(frame,len,GetParity(frame,len));
+ ReaderTransmitBitsPar(frame,len*8,GetParity(frame,len));
}
int ReaderReceive(uint8_t* receivedAnswer)
int len;
// Broadcast for a card, WUPA (0x52) will force response from all cards in the field
- ReaderTransmitShort(wupa);
+ ReaderTransmitBitsPar(wupa,7,0);
// Receive the ATQA
if(!ReaderReceive(resp)) return 0;
// Dbprintf("atqa: %02x %02x",resp[0],resp[1]);