]> cvs.zerfleddert.de Git - proxmark3-svn/commitdiff
revert change "hf list topaz" to "hf list nfc"
authorpwpiwi <pwpiwi@users.noreply.github.com>
Tue, 17 Mar 2015 06:41:08 +0000 (07:41 +0100)
committerpwpiwi <pwpiwi@users.noreply.github.com>
Tue, 17 Mar 2015 06:41:08 +0000 (07:41 +0100)
refactored Startbit detection in MillerDecoding()
relaxed startbit detection in MillerDecoding()
fixed CRC checking and CRC bytes marking in hf list
fixed topaz multi frame command listing in hf list topaz

armsrc/iso14443a.c
armsrc/iso14443a.h
client/cmdhf.c

index a78dae6eebadfea59dbe3ea26cee4f8e7eef450e..06a134f6b56f519d076295ef15885461ed2c96bc 100644 (file)
@@ -248,8 +248,7 @@ void UartReset()
        Uart.parityLen = 0;                                     // number of decoded parity bytes
        Uart.shiftReg = 0;                                      // shiftreg to hold decoded data bits
        Uart.parityBits = 0;                            // holds 8 parity bits
-       Uart.twoBits = 0x0000;                          // buffer for 2 Bits
-       Uart.highCnt = 0;
+       Uart.fourBits = 0x00000000;                     // buffer for 4 Bits
        Uart.startTime = 0;
        Uart.endTime = 0;
 }
@@ -265,40 +264,34 @@ void UartInit(uint8_t *data, uint8_t *parity)
 static RAMFUNC bool MillerDecoding(uint8_t bit, uint32_t non_real_time)
 {
 
-       Uart.twoBits = (Uart.twoBits << 8) | bit;
+       Uart.fourBits = (Uart.fourBits << 8) | bit;
        
        if (Uart.state == STATE_UNSYNCD) {                                                                                      // not yet synced
        
-               if (Uart.highCnt < 1) {                                                                                                 // wait for a stable unmodulated signal
-                       if (Uart.twoBits == 0xffff) {
-                               Uart.highCnt++;
-                       } else {
-                               Uart.highCnt = 0;
-                       }
-               } else {        
-                       Uart.syncBit = 0xFFFF;                                                                                          // not set
-                                                                                                                                                               // we look for a ...1111111100x11111xxxxxx pattern (the start bit)
-                       if              ((Uart.twoBits & 0xDF00) == 0x1F00) Uart.syncBit = 8;           // mask is   11x11111 xxxxxxxx, 
-                                                                                                                                                               // check for 00x11111 xxxxxxxx
-                       else if ((Uart.twoBits & 0xEF80) == 0x8F80) Uart.syncBit = 7;           // both masks shifted right one bit, left padded with '1'
-                       else if ((Uart.twoBits & 0xF7C0) == 0xC7C0) Uart.syncBit = 6;           // ...
-                       else if ((Uart.twoBits & 0xFBE0) == 0xE3E0) Uart.syncBit = 5;
-                       else if ((Uart.twoBits & 0xFDF0) == 0xF1F0) Uart.syncBit = 4;
-                       else if ((Uart.twoBits & 0xFEF8) == 0xF8F8) Uart.syncBit = 3;
-                       else if ((Uart.twoBits & 0xFF7C) == 0xFC7C) Uart.syncBit = 2;
-                       else if ((Uart.twoBits & 0xFFBE) == 0xFE3E) Uart.syncBit = 1;
-                       if (Uart.syncBit != 0xFFFF) {                                                                           // found a sync bit
-                               Uart.startTime = non_real_time?non_real_time:(GetCountSspClk() & 0xfffffff8);
-                               Uart.startTime -= Uart.syncBit;
-                               Uart.endTime = Uart.startTime;
-                               Uart.state = STATE_START_OF_COMMUNICATION;
-                       }
+               Uart.syncBit = 9999;                                                                                                    // not set
+               // we look for a ...xxxx1111111100x11111xxxxxx pattern 
+               // (unmodulated, followed by the start bit = 8 '1's followed by 2 '0's, eventually followed by another '0', followed by 5 '1's)
+#define ISO14443A_STARTBIT_MASK                0x007FEF80                                                                      // mask is    00000000 01111111 11101111 10000000
+#define ISO14443A_STARTBIT_PATTERN     0x007F8F80                                                                      // pattern is 00000000 01111111 10001111 10000000
+               if              ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 0 == ISO14443A_STARTBIT_PATTERN >> 0) Uart.syncBit = 7;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 1 == ISO14443A_STARTBIT_PATTERN >> 1) Uart.syncBit = 6;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 2 == ISO14443A_STARTBIT_PATTERN >> 2) Uart.syncBit = 5;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 3 == ISO14443A_STARTBIT_PATTERN >> 3) Uart.syncBit = 4;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 4 == ISO14443A_STARTBIT_PATTERN >> 4) Uart.syncBit = 3;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 5 == ISO14443A_STARTBIT_PATTERN >> 5) Uart.syncBit = 2;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 6 == ISO14443A_STARTBIT_PATTERN >> 6) Uart.syncBit = 1;
+               else if ((Uart.fourBits & ISO14443A_STARTBIT_MASK) >> 7 == ISO14443A_STARTBIT_PATTERN >> 7) Uart.syncBit = 0;
+               if (Uart.syncBit != 9999) {                                                                                             // found a sync bit
+                       Uart.startTime = non_real_time?non_real_time:(GetCountSspClk() & 0xfffffff8);
+                       Uart.startTime -= Uart.syncBit;
+                       Uart.endTime = Uart.startTime;
+                       Uart.state = STATE_START_OF_COMMUNICATION;
                }
 
        } else {
 
-               if (IsMillerModulationNibble1(Uart.twoBits >> Uart.syncBit)) {                  
-                       if (IsMillerModulationNibble2(Uart.twoBits >> Uart.syncBit)) {          // Modulation in both halves - error
+               if (IsMillerModulationNibble1(Uart.fourBits >> Uart.syncBit)) {                 
+                       if (IsMillerModulationNibble2(Uart.fourBits >> Uart.syncBit)) {         // Modulation in both halves - error
                                UartReset();
                        } else {                                                                                                                        // Modulation in first half = Sequence Z = logic "0"
                                if (Uart.state == STATE_MILLER_X) {                                                             // error - must not follow after X
@@ -322,7 +315,7 @@ static RAMFUNC bool MillerDecoding(uint8_t bit, uint32_t non_real_time)
                                }
                        }
                } else {
-                       if (IsMillerModulationNibble2(Uart.twoBits >> Uart.syncBit)) {          // Modulation second half = Sequence X = logic "1"
+                       if (IsMillerModulationNibble2(Uart.fourBits >> Uart.syncBit)) {         // Modulation second half = Sequence X = logic "1"
                                Uart.bitCount++;
                                Uart.shiftReg = (Uart.shiftReg >> 1) | 0x100;                                   // add a 1 to the shiftreg
                                Uart.state = STATE_MILLER_X;
@@ -358,12 +351,10 @@ static RAMFUNC bool MillerDecoding(uint8_t bit, uint32_t non_real_time)
                                                return TRUE;                                                                                    // we are finished with decoding the raw data sequence
                                        } else {
                                                UartReset();                                                                                    // Nothing received - start over
-                                               Uart.highCnt = 1;
                                        }
                                }
                                if (Uart.state == STATE_START_OF_COMMUNICATION) {                               // error - must not follow directly after SOC
                                        UartReset();
-                                       Uart.highCnt = 1;
                                } else {                                                                                                                // a logic "0"
                                        Uart.bitCount++;
                                        Uart.shiftReg = (Uart.shiftReg >> 1);                                           // add a 0 to the shiftreg
index d99236b291a349853c83170592504a908d7c0de5..ec99ab99a4f7426628d73ace74f10237b81838c3 100644 (file)
@@ -63,8 +63,7 @@ typedef struct {
        uint16_t syncBit;
        uint8_t  parityBits;
        uint8_t  parityLen;
-       uint16_t highCnt;
-       uint16_t twoBits;
+       uint32_t fourBits;
        uint32_t startTime, endTime;
     uint8_t *output;
        uint8_t *parity;
index f4d762104ab25551f27ccdfd71461c41f086a268..960dcf7f5ef72154ad861a2649a1efb71a91d216 100644 (file)
@@ -189,7 +189,34 @@ void annotateIso14443b(char *exp, size_t size, uint8_t* cmd, uint8_t cmdsize)
 }
 
 /**
- * @brief iso14443B_CRC_Ok Checks CRC in command or response
+ * @brief iso14443A_CRC_check Checks CRC in command or response
+ * @param isResponse
+ * @param data
+ * @param len
+ * @return  0 : CRC-command, CRC not ok
+ *          1 : CRC-command, CRC ok
+ *          2 : Not crc-command
+ */
+
+uint8_t iso14443A_CRC_check(bool isResponse, uint8_t* data, uint8_t len)
+{
+       uint8_t b1,b2;
+
+       if(len <= 2) return 2;
+
+       if(isResponse & (len < 6)) return 2;
+       
+       ComputeCrc14443(CRC_14443_A, data, len-2, &b1, &b2);
+       if (b1 != data[len-2] || b2 != data[len-1]) {
+               return 0;
+       } else {
+               return 1;
+       }
+}
+
+
+/**
+ * @brief iso14443B_CRC_check Checks CRC in command or response
  * @param isResponse
  * @param data
  * @param len
@@ -206,9 +233,10 @@ uint8_t iso14443B_CRC_check(bool isResponse, uint8_t* data, uint8_t len)
 
        ComputeCrc14443(CRC_14443_B, data, len-2, &b1, &b2);
        if(b1 != data[len-2] || b2 != data[len-1]) {
-         return 0;
+               return 0;
+       } else {
+               return 1;
        }
-       return 1;
 }
 
 /**
@@ -287,33 +315,42 @@ bool next_record_is_response(uint16_t tracepos, uint8_t *trace)
 }
 
 
-void merge_topaz_reader_frames(uint32_t timestamp, uint32_t *duration, uint16_t *tracepos, uint16_t traceLen, uint8_t *trace, uint8_t *frame, uint8_t *topaz_reader_command, uint16_t *data_len)
+bool merge_topaz_reader_frames(uint32_t timestamp, uint32_t *duration, uint16_t *tracepos, uint16_t traceLen, uint8_t *trace, uint8_t *frame, uint8_t *topaz_reader_command, uint16_t *data_len)
 {
 
 #define MAX_TOPAZ_READER_CMD_LEN       9
 
        uint32_t last_timestamp = timestamp + *duration;
 
-       memcpy(topaz_reader_command, frame, MIN(*data_len, MAX_TOPAZ_READER_CMD_LEN));
+       if ((*data_len != 1) || (frame[0] == TOPAZ_WUPA) || (frame[0] == TOPAZ_REQA)) return false;
+
+       memcpy(topaz_reader_command, frame, *data_len);
 
        while (!is_last_record(*tracepos, trace, traceLen) && !next_record_is_response(*tracepos, trace)) {
                uint32_t next_timestamp = *((uint32_t *)(trace + *tracepos));
                *tracepos += sizeof(uint32_t);
-               last_timestamp = next_timestamp + *((uint16_t *)(trace + *tracepos));
+               uint16_t next_duration = *((uint16_t *)(trace + *tracepos));
                *tracepos += sizeof(uint16_t);
                uint16_t next_data_len = *((uint16_t *)(trace + *tracepos)) & 0x7FFF;
                *tracepos += sizeof(uint16_t);
                uint8_t *next_frame = (trace + *tracepos);
                *tracepos += next_data_len;
-               if (*data_len + next_data_len <= MAX_TOPAZ_READER_CMD_LEN) {
+               if ((next_data_len == 1) && (*data_len + next_data_len <= MAX_TOPAZ_READER_CMD_LEN)) {
                        memcpy(topaz_reader_command + *data_len, next_frame, next_data_len);
                        *data_len += next_data_len;
-                       }
+                       last_timestamp = next_timestamp + next_duration;
+               } else {
+                       // rewind and exit
+                       *tracepos = *tracepos - next_data_len - sizeof(uint16_t) - sizeof(uint16_t) - sizeof(uint32_t);
+                       break;
+               }
                uint16_t next_parity_len = (next_data_len-1)/8 + 1;
                *tracepos += next_parity_len;
        }
 
        *duration = last_timestamp - timestamp;
+       
+       return true;
 }
 
 
@@ -354,32 +391,27 @@ uint16_t printTraceLine(uint16_t tracepos, uint16_t traceLen, uint8_t *trace, ui
        tracepos += parity_len;
 
        if (protocol == TOPAZ && !isResponse) {
-               // topaz reader commands come in 1 or 9 separate frames with 8 Bits each.
+               // topaz reader commands come in 1 or 9 separate frames with 7 or 8 Bits each.
                // merge them:
-               merge_topaz_reader_frames(timestamp, &duration, &tracepos, traceLen, trace, frame, topaz_reader_command, &data_len);
-               frame = topaz_reader_command;
+               if (merge_topaz_reader_frames(timestamp, &duration, &tracepos, traceLen, trace, frame, topaz_reader_command, &data_len)) {
+                       frame = topaz_reader_command;
+               }
        }
        
        //Check the CRC status
        uint8_t crcStatus = 2;
 
        if (data_len > 2) {
-               uint8_t b1, b2;
                switch (protocol) {
                        case ICLASS:
                                crcStatus = iclass_CRC_check(isResponse, frame, data_len);
                                break;
                        case ISO_14443B:
-                       case TOPAZ:                     
+                       case TOPAZ:
                                crcStatus = iso14443B_CRC_check(isResponse, frame, data_len); 
                                break;
                        case ISO_14443A:
-                               ComputeCrc14443(CRC_14443_A, frame, data_len-2, &b1, &b2);
-                               if (b1 != frame[data_len-2] || b2 != frame[data_len-1]) {
-                                       if(!(isResponse & (data_len < 6))) {
-                                               crcStatus = 0;
-                                       }
-                               }
+                               crcStatus = iso14443A_CRC_check(isResponse, frame, data_len);
                                break;
                        default: 
                                break;
@@ -403,19 +435,18 @@ uint16_t printTraceLine(uint16_t tracepos, uint16_t traceLen, uint8_t *trace, ui
                }
                uint8_t parityBits = parityBytes[j>>3];
                if (isResponse && (oddparity != ((parityBits >> (7-(j&0x0007))) & 0x01))) {
-                       snprintf(line[j/16]+(( j % 16) * 4),110, "%02x! ", frame[j]);
-
+                       snprintf(line[j/16]+(( j % 16) * 4), 110, " %02x!", frame[j]);
                } else {
-                       snprintf(line[j/16]+(( j % 16) * 4),110, "%02x  ", frame[j]);
+                       snprintf(line[j/16]+(( j % 16) * 4), 110, " %02x ", frame[j]);
                }
 
        }
-       if(crcStatus == 1 || crcStatus == 2)
+       if(crcStatus == 0 || crcStatus == 1)
        {//CRC-command
-               char *pos1 = line[(data_len-2)/16]+(((data_len-2) % 16) * 4)-1;
+               char *pos1 = line[(data_len-2)/16]+(((data_len-2) % 16) * 4);
                (*pos1) = '[';
-               char *pos2 = line[(data_len)/16]+(((data_len) % 16) * 4)-2;
-               (*pos2) = ']';
+               char *pos2 = line[(data_len)/16]+(((data_len) % 16) * 4);
+               sprintf(pos2, "%c", ']');
        }
        if(data_len == 0)
        {
@@ -443,7 +474,7 @@ uint16_t printTraceLine(uint16_t tracepos, uint16_t traceLen, uint8_t *trace, ui
        int num_lines = MIN((data_len - 1)/16 + 1, 16);
        for (int j = 0; j < num_lines ; j++) {
                if (j == 0) {
-                       PrintAndLog(" %9d | %9d | %s | %-64s| %s| %s",
+                       PrintAndLog(" %9d | %9d | %s |%-64s | %s| %s",
                                (timestamp - first_timestamp),
                                (EndOfTransmissionTimestamp - first_timestamp),
                                (isResponse ? "Tag" : "Rdr"),
@@ -451,7 +482,7 @@ uint16_t printTraceLine(uint16_t tracepos, uint16_t traceLen, uint8_t *trace, ui
                                (j == num_lines-1) ? crc : "    ",
                                (j == num_lines-1) ? explanation : "");
                } else {
-                       PrintAndLog("           |           |     | %-64s| %s| %s",
+                       PrintAndLog("           |           |     |%-64s | %s| %s",
                                line[j],
                                (j == num_lines-1) ? crc : "    ",
                                (j == num_lines-1) ? explanation : "");
@@ -498,7 +529,7 @@ int CmdHFList(const char *Cmd)
                        protocol = ISO_14443A;
                } else if(strcmp(type, "14b") == 0)     {
                        protocol = ISO_14443B;
-               } else if(strcmp(type,"nfc")== 0) {
+               } else if(strcmp(type,"topaz")== 0) {
                        protocol = TOPAZ;
                } else if(strcmp(type,"raw")== 0) {
                        protocol = -1;//No crc, no annotations
Impressum, Datenschutz