From 011f973e7ff145ee0f6ccf58c850765513c43d04 Mon Sep 17 00:00:00 2001 From: Philippe Teuwen Date: Fri, 24 Apr 2020 18:21:38 +0200 Subject: [PATCH] make style --- armsrc/Standalone/hf_msdsal.c | 295 ++++++++++++++++------------------ client/src/proxmark3.c | 2 +- 2 files changed, 136 insertions(+), 161 deletions(-) diff --git a/armsrc/Standalone/hf_msdsal.c b/armsrc/Standalone/hf_msdsal.c index d5aa1805e..38416307c 100644 --- a/armsrc/Standalone/hf_msdsal.c +++ b/armsrc/Standalone/hf_msdsal.c @@ -7,7 +7,7 @@ //----------------------------------------------------------------------------- // Code for reading and emulating 14a technology aka MSDSal by Salvador Mendoza //----------------------------------------------------------------------------- -#include "standalone.h" +#include "standalone.h" #include "proxmark3_arm.h" #include "appmain.h" #include "fpgaloader.h" @@ -29,9 +29,9 @@ void ModInfo(void) { * The initial mode is reading with LED A as guide. * In this mode, the Proxmark expects a Visa Card, * and will act as card reader. Trying to find track 2. -* +* * If the Proxmark found a track 2, it will change to emulation mode (LED C) automatically. -* During this mode the Proxmark will behave as card, emulating a Visa MSD transaction +* During this mode the Proxmark will behave as card, emulating a Visa MSD transaction * using the pre-saved track2 from the previous reading. * * It is possible to jump from mode to another by simply pressing the button. @@ -47,81 +47,74 @@ void ModInfo(void) { * LED B = receiving/sending commands, activity * * -* Reading or emulating ISO-14443A technology is not limited to payment cards. This example -* was not only designed to make a replay attack, but to open new possibilities in the ISO-14443A +* Reading or emulating ISO-14443A technology is not limited to payment cards. This example +* was not only designed to make a replay attack, but to open new possibilities in the ISO-14443A * technologies. Be brave enough to share your knowledge & inspire others. Salvador Mendoza. */ -uint8_t ppdol [255] = {0x80, 0xA8, 0x00, 0x00, 0x02, 0x83, 0x00}; // Default GET PROCESSING +uint8_t ppdol [255] = {0x80, 0xA8, 0x00, 0x00, 0x02, 0x83, 0x00}; // Default GET PROCESSING -uint8_t treatPDOL(uint8_t* apdu){ //Generate GET PROCESSING - uint8_t plen = 7; - //PDOL Format: 80 A8 00 00 + (PDOL Length+2) + 83 + PDOL Length + PDOL + 00 - for (uint8_t i = 1; i <= apdu[0]; i++){ //Magic stuff, the generation order is important - if (apdu[i] == 0x9F && apdu[i+1] == 0x66){ //Terminal Transaction Qualifiers - ppdol[plen] = 0xF6; - ppdol[plen+1] = 0x20; - ppdol[plen+2] = 0xC0; - ppdol[plen+3] = 0x00; - plen += 4; - i += 2; +uint8_t treatPDOL(uint8_t *apdu) { //Generate GET PROCESSING + uint8_t plen = 7; + //PDOL Format: 80 A8 00 00 + (PDOL Length+2) + 83 + PDOL Length + PDOL + 00 + for (uint8_t i = 1; i <= apdu[0]; i++) { //Magic stuff, the generation order is important + if (apdu[i] == 0x9F && apdu[i + 1] == 0x66) { //Terminal Transaction Qualifiers + ppdol[plen] = 0xF6; + ppdol[plen + 1] = 0x20; + ppdol[plen + 2] = 0xC0; + ppdol[plen + 3] = 0x00; + plen += 4; + i += 2; + } else if (apdu[i] == 0x9F && apdu[i + 1] == 0x1A) { //Terminal Country Code + ppdol[plen] = 0x9F; + ppdol[plen + 1] = 0x1A; + plen += 2; + i += 2; + } else if (apdu[i] == 0x5F && apdu[i + 1] == 0x2A) { //Transaction Currency Code + ppdol[plen] = 0x5F; + ppdol[plen + 1] = 0x2A; + plen += 2; + i += 2; + } else if (apdu[i] == 0x9A) { //Transaction Date + ppdol[plen] = 0x9A; + ppdol[plen + 1] = 0x9A; + ppdol[plen + 2] = 0x9A; + plen += 3; + i += 1; + } else if (apdu[i] == 0x95) { //Terminal Verification Results + ppdol[plen] = 0x95; + ppdol[plen + 1] = 0x95; + ppdol[plen + 2] = 0x95; + ppdol[plen + 3] = 0x95; + ppdol[plen + 4] = 0x95; + plen += 5; + i += 1; + } else if (apdu[i] == 0x9C) { //Transaction Type + ppdol[plen] = 0x9C; + plen += 1; + i += 1; + } else if (apdu[i] == 0x9F && apdu[i + 1] == 0x37) { //Unpredictable Number + ppdol[plen] = 0x9F; + ppdol[plen + 1] = 0x37; + ppdol[plen + 2] = 0x9F; + ppdol[plen + 3] = 0x37; + plen += 4; + i += 2; + } else { //To the others, add "0" to complete the format depending on its range + uint8_t u = apdu[i + 2]; + while (u > 0) { + ppdol[plen] = 0; + plen += 1; + u--; + } + i += 2; + } } - else if(apdu[i] == 0x9F && apdu[i+1] == 0x1A){ //Terminal Country Code - ppdol[plen] = 0x9F; - ppdol[plen+1] = 0x1A; - plen += 2; - i += 2; - } - else if(apdu[i] == 0x5F && apdu[i+1] == 0x2A){ //Transaction Currency Code - ppdol[plen] = 0x5F; - ppdol[plen+1] = 0x2A; - plen += 2; - i += 2; - } - else if(apdu[i] == 0x9A){ //Transaction Date - ppdol[plen] = 0x9A; - ppdol[plen+1] = 0x9A; - ppdol[plen+2] = 0x9A; - plen += 3; - i += 1; - } - else if(apdu[i] == 0x95){ //Terminal Verification Results - ppdol[plen] = 0x95; - ppdol[plen+1] = 0x95; - ppdol[plen+2] = 0x95; - ppdol[plen+3] = 0x95; - ppdol[plen+4] = 0x95; - plen += 5; - i += 1; - } - else if(apdu[i] == 0x9C){ //Transaction Type - ppdol[plen] = 0x9C; - plen += 1; - i += 1; - } - else if(apdu[i] == 0x9F && apdu[i+1] == 0x37){ //Unpredictable Number - ppdol[plen] = 0x9F; - ppdol[plen+1] = 0x37; - ppdol[plen+2] = 0x9F; - ppdol[plen+3] = 0x37; - plen += 4; - i += 2; - } - else { //To the others, add "0" to complete the format depending on its range - uint8_t u = apdu[i+2]; - while (u > 0){ - ppdol[plen] = 0; - plen += 1; - u--; - } - i += 2; - } - } - ppdol[4] = (plen + 2) - 7; // Length of PDOL + 2 - ppdol[6] = plen - 7; // Real length - plen++; // +1 because the last 0 - ppdol[plen] = 0x00; // Add the last 0 to the challenge - return plen; + ppdol[4] = (plen + 2) - 7; // Length of PDOL + 2 + ppdol[6] = plen - 7; // Real length + plen++; // +1 because the last 0 + ppdol[plen] = 0x00; // Add the last 0 to the challenge + return plen; } void RunMod() { @@ -135,11 +128,11 @@ void RunMod() { //Specific for Visa cards: select ppse, select Visa AID, GET PROCESSING, SFI uint8_t ppse[20] = {0x00, 0xA4, 0x04, 0x00, 0x0e, 0x32, 0x50, 0x41, 0x59, 0x2e, 0x53, 0x59, 0x53, 0x2e, 0x44, 0x44, 0x46, 0x30, 0x31, 0x00}; - uint8_t visa[13] = {0x00, 0xA4, 0x04, 0x00, 0x07, 0xa0, 0x00, 0x00, 0x00, 0x03, 0x10, 0x10, 0x00}; + uint8_t visa[13] = {0x00, 0xA4, 0x04, 0x00, 0x07, 0xa0, 0x00, 0x00, 0x00, 0x03, 0x10, 0x10, 0x00}; uint8_t processing [8] = {0x80, 0xA8, 0x00, 0x00, 0x02, 0x83, 0x00, 0x00}; uint8_t sfi[5] = {0x00, 0xb2, 0x01, 0x0c, 0x00}; - uint8_t *apdus[4] = {ppse, visa, processing, sfi}; + uint8_t *apdus[4] = {ppse, visa, processing, sfi}; uint8_t apdusLen [4] = { sizeof(ppse), sizeof(visa), sizeof(processing), sizeof(sfi)}; uint8_t pdol[50], plen = 8; @@ -157,7 +150,7 @@ void RunMod() { // // It is possible to initialize directly the emulation mode, having "token" with data and set "chktoken" = true ;) // - char token[19]={0x00}; + char token[19] = {0x00}; bool chktoken = false; //For emulation steps @@ -175,7 +168,7 @@ void RunMod() { uint8_t flags = FLAG_4B_UID_IN_DATA; //UID 4 bytes(could be 7 bytes if needed it) uint8_t data[PM3_CMD_DATA_SIZE] = {0x00}; // in case there is a read command received we shouldn't break - uint8_t visauid[7] = {0x01, 0x02, 0x03, 0x04}; + uint8_t visauid[7] = {0x01, 0x02, 0x03, 0x04}; memcpy(data, visauid, 4); // to initialize the emulation @@ -198,10 +191,10 @@ void RunMod() { // handler - command responses tag_response_info_t dynamic_response_info = { - .response = dynamic_response_buffer, - .response_n = 0, - .modulation = dynamic_modulation_buffer, - .modulation_n = 0 + .response = dynamic_response_buffer, + .response_n = 0, + .modulation = dynamic_modulation_buffer, + .modulation_n = 0 }; // States for standalone @@ -211,12 +204,11 @@ void RunMod() { uint8_t state = STATE_READ; //Checking if the user wants to go directly to emulation mode using a hardcoded track 2 - if (chktoken == true && token[0] != 0x00){ + if (chktoken == true && token[0] != 0x00) { state = STATE_EMU; Dbprintf(_YELLOW_("[") "Initialized emulation mode " _YELLOW_("]")); DbpString("\n"_YELLOW_("!!") "Waiting for a card reader..."); - } - else{ + } else { DbpString(_YELLOW_("[") "Initialized reading mode " _YELLOW_("]")); DbpString("\n"_YELLOW_("!!") "Waiting for a Visa card..."); } @@ -233,15 +225,13 @@ void RunMod() { if (button_pressed == 1) //Holding down the button break; else if (button_pressed == -1) { //Pressing one time change between reading & emulation - if (state == STATE_READ){ - if (chktoken == true && token[0] != 0x00){ //Only change to emulation if it saved a track 2 in memory + if (state == STATE_READ) { + if (chktoken == true && token[0] != 0x00) { //Only change to emulation if it saved a track 2 in memory state = STATE_EMU; Dbprintf(_YELLOW_("[") "In emulation mode " _YELLOW_("]")); - } - else + } else Dbprintf(_YELLOW_("!!") "Nothing in memory to emulate"); - } - else { + } else { state = STATE_READ; Dbprintf(_YELLOW_("[") "In reading mode " _YELLOW_("]")); } @@ -249,7 +239,7 @@ void RunMod() { SpinDelay(500); - if (state == STATE_READ){ + if (state == STATE_READ) { LED_A_ON(); if (chktoken) LED_C_ON(); @@ -260,7 +250,7 @@ void RunMod() { Dbprintf(_YELLOW_("+") "Found ISO 14443 Type A!"); - for (uint8_t i = 0; i < 4; i++){ + for (uint8_t i = 0; i < 4; i++) { chktoken = false; LED_C_OFF(); LED_B_ON(); @@ -270,42 +260,40 @@ void RunMod() { Dbprintf(_YELLOW_("[") "Proxmark command " _YELLOW_("]")); Dbhexdump(apdusLen[i], apdus[i], false); Dbprintf(_GREEN_("[") "Card answer " _GREEN_("]")); - Dbhexdump(apdulen-2, apdubuffer, false); + Dbhexdump(apdulen - 2, apdubuffer, false); Dbprintf("----"); for (uint8_t u = 0; u < apdulen; u++) { - if (i == 1){ - if (apdubuffer[u] == 0x9F && apdubuffer[u+1] == 0x38){ //Check for PDOL - for (uint8_t e = 0; e <= apdubuffer[u+2]; e++) - pdol[e] = apdubuffer[u+e+2]; - - plen = treatPDOL(pdol); //Generate a challenge - apdus[2] = ppdol; - apdusLen[2] = plen; - existpdol = true; - } - } - else if (i == 3){ - if (apdubuffer[u] == 0x57 && apdubuffer[u+1] == 0x13 && !chktoken){ //Find track 2 - chktoken = true; - memcpy(&token, &apdubuffer[u+2], 19); - break; - } + if (i == 1) { + if (apdubuffer[u] == 0x9F && apdubuffer[u + 1] == 0x38) { //Check for PDOL + for (uint8_t e = 0; e <= apdubuffer[u + 2]; e++) + pdol[e] = apdubuffer[u + e + 2]; + + plen = treatPDOL(pdol); //Generate a challenge + apdus[2] = ppdol; + apdusLen[2] = plen; + existpdol = true; + } + } else if (i == 3) { + if (apdubuffer[u] == 0x57 && apdubuffer[u + 1] == 0x13 && !chktoken) { //Find track 2 + chktoken = true; + memcpy(&token, &apdubuffer[u + 2], 19); + break; + } } } - if (i == 1){ + if (i == 1) { Dbprintf(_GREEN_("[") "Challenge generated " _GREEN_("]")); Dbhexdump(plen, existpdol ? ppdol : processing, false); } - } - else{ - Dbprintf(_YELLOW_("!!") "Error reading the card"); + } else { + Dbprintf(_YELLOW_("!!") "Error reading the card"); } LED_B_OFF(); } - if(chktoken){ + if (chktoken) { Dbprintf(_RED_("[") "Track 2 " _RED_("]")); Dbhexdump(19, (uint8_t *)token, false); Dbprintf(_YELLOW_("!!") "Card number"); @@ -317,8 +305,7 @@ void RunMod() { DbpString("\n"_YELLOW_("!!") "Waiting for a card reader..."); } } - } - else if(state == STATE_EMU){ + } else if (state == STATE_EMU) { LED_A_OFF(); LED_C_ON(); @@ -363,85 +350,73 @@ void RunMod() { if (receivedCmd[0] == ISO14443A_CMD_REQA && len == 1) { // Received a REQUEST DbpString(_YELLOW_("+") "REQUEST Received"); p_response = &responses[ATQA]; - } - else if (receivedCmd[0] == ISO14443A_CMD_HALT && len == 4) { // Received a HALT + } else if (receivedCmd[0] == ISO14443A_CMD_HALT && len == 4) { // Received a HALT DbpString(_YELLOW_("+") "Received a HALT"); p_response = NULL; - } - else if (receivedCmd[0] == ISO14443A_CMD_WUPA && len == 1) { // Received a WAKEUP //Este!! + } else if (receivedCmd[0] == ISO14443A_CMD_WUPA && len == 1) { // Received a WAKEUP //Este!! DbpString(_YELLOW_("+") "WAKEUP Received"); p_response = &responses[ATQA]; prevCmd = 0; - } - else if (receivedCmd[1] == 0x20 && receivedCmd[0] == ISO14443A_CMD_ANTICOLL_OR_SELECT && len == 2) { // Received request for UID (cascade 1) + } else if (receivedCmd[1] == 0x20 && receivedCmd[0] == ISO14443A_CMD_ANTICOLL_OR_SELECT && len == 2) { // Received request for UID (cascade 1) DbpString(_YELLOW_("+") "Request for UID C1"); p_response = &responses[UIDC1]; - } - else if (receivedCmd[1] == 0x70 && receivedCmd[0] == ISO14443A_CMD_ANTICOLL_OR_SELECT && len == 9) { // Received a SELECT (cascade 1) + } else if (receivedCmd[1] == 0x70 && receivedCmd[0] == ISO14443A_CMD_ANTICOLL_OR_SELECT && len == 9) { // Received a SELECT (cascade 1) DbpString(_YELLOW_("+") "Request for SELECT S1"); p_response = &responses[SAKC1]; - } - else if (receivedCmd[0] == ISO14443A_CMD_RATS && len == 4) { // Received a RATS request + } else if (receivedCmd[0] == ISO14443A_CMD_RATS && len == 4) { // Received a RATS request DbpString(_YELLOW_("+") "Request for RATS"); p_response = &responses[RATS]; - } - else { + } else { Dbprintf(_YELLOW_("[") "Card reader command " _YELLOW_("]")); Dbhexdump(len, receivedCmd, false); - if (receivedCmd[0] == 0x02 || receivedCmd[0] == 0x03){ //Emulate a Visa MSD(Magnetic stripe data) card - uint8_t ppsea[39] = {0x6F,0x23,0x84,0x0E,0x32,0x50,0x41,0x59,0x2E,0x53,0x59,0x53,0x2E,0x44,0x44,0x46,0x30,0x31,0xA5,0x11,0xBF,0x0C,0x0E,0x61,0x0C,0x4F,0x07,0xA0,0x00,0x00,0x00,0x03,0x10,0x10,0x87,0x01,0x01,0x90,0x00}; - uint8_t processing[10] = {0x80,0x06,0x00,0x80,0x08,0x01,0x01,0x00,0x90,0x00}; - uint8_t visauid[34] = {0x6F,0x1E,0x84,0x07,0xA0,0x00,0x00,0x00,0x03,0x10,0x10,0xA5,0x13,0x50,0x0B,0x56,0x49,0x53,0x41,0x20,0x43,0x52,0x45,0x44,0x49,0x54,0x9F,0x38,0x03,0x9F,0x66,0x02,0x90,0x00}; - - uint8_t last[4] = {0x70,0x15,0x57,0x13}; + if (receivedCmd[0] == 0x02 || receivedCmd[0] == 0x03) { //Emulate a Visa MSD(Magnetic stripe data) card + uint8_t ppsea[39] = {0x6F, 0x23, 0x84, 0x0E, 0x32, 0x50, 0x41, 0x59, 0x2E, 0x53, 0x59, 0x53, 0x2E, 0x44, 0x44, 0x46, 0x30, 0x31, 0xA5, 0x11, 0xBF, 0x0C, 0x0E, 0x61, 0x0C, 0x4F, 0x07, 0xA0, 0x00, 0x00, 0x00, 0x03, 0x10, 0x10, 0x87, 0x01, 0x01, 0x90, 0x00}; + uint8_t processing[10] = {0x80, 0x06, 0x00, 0x80, 0x08, 0x01, 0x01, 0x00, 0x90, 0x00}; + uint8_t visauid[34] = {0x6F, 0x1E, 0x84, 0x07, 0xA0, 0x00, 0x00, 0x00, 0x03, 0x10, 0x10, 0xA5, 0x13, 0x50, 0x0B, 0x56, 0x49, 0x53, 0x41, 0x20, 0x43, 0x52, 0x45, 0x44, 0x49, 0x54, 0x9F, 0x38, 0x03, 0x9F, 0x66, 0x02, 0x90, 0x00}; + + uint8_t last[4] = {0x70, 0x15, 0x57, 0x13}; uint8_t card[25]; - uint8_t statusapdu[2] = {0x90,0x00}; - - uint8_t finished[2] = {0x6f,0x00}; + uint8_t statusapdu[2] = {0x90, 0x00}; + + uint8_t finished[2] = {0x6f, 0x00}; memcpy(&card[0], last, sizeof(last)); memcpy(&card[4], token, sizeof(token)); memcpy(&card[23], statusapdu, sizeof(statusapdu)); - dynamic_response_info.response[0] = receivedCmd[0]; + dynamic_response_info.response[0] = receivedCmd[0]; //Depending on card reader commands, the Proxmark will answer to fool the reader - if (receivedCmd[2] == 0xA4 && receivedCmd[6] == 0x32 && prevCmd == 0){ //Respond with PPSE + if (receivedCmd[2] == 0xA4 && receivedCmd[6] == 0x32 && prevCmd == 0) { //Respond with PPSE memcpy(&dynamic_response_info.response[1], ppsea, sizeof(ppsea)); - dynamic_response_info.response_n = sizeof(ppsea)+1; + dynamic_response_info.response_n = sizeof(ppsea) + 1; prevCmd++; - } - else if(receivedCmd[2] == 0xA4 && receivedCmd[10] == 0x03 && receivedCmd[11] == 0x10 && prevCmd == 1){ //Respond Visa AID + } else if (receivedCmd[2] == 0xA4 && receivedCmd[10] == 0x03 && receivedCmd[11] == 0x10 && prevCmd == 1) { //Respond Visa AID memcpy(&dynamic_response_info.response[1], visauid, sizeof(visauid)); - dynamic_response_info.response_n = sizeof(visauid)+1; + dynamic_response_info.response_n = sizeof(visauid) + 1; prevCmd++; - } - else if(receivedCmd[1] == 0x80 && receivedCmd[2] == 0xA8 && receivedCmd[6] == 0x83 && prevCmd == 2){ //GET PROCESSING + } else if (receivedCmd[1] == 0x80 && receivedCmd[2] == 0xA8 && receivedCmd[6] == 0x83 && prevCmd == 2) { //GET PROCESSING memcpy(&dynamic_response_info.response[1], processing, sizeof(processing)); - dynamic_response_info.response_n = sizeof(processing)+1; + dynamic_response_info.response_n = sizeof(processing) + 1; prevCmd++; - } - else if(receivedCmd[1] == 0x00 && receivedCmd[2] == 0xB2 && prevCmd == 3){ //SFI + } else if (receivedCmd[1] == 0x00 && receivedCmd[2] == 0xB2 && prevCmd == 3) { //SFI memcpy(&dynamic_response_info.response[1], card, sizeof(card)); - dynamic_response_info.response_n = sizeof(card)+1; + dynamic_response_info.response_n = sizeof(card) + 1; prevCmd++; - } - else { + } else { memcpy(&dynamic_response_info.response[1], finished, sizeof(finished)); - dynamic_response_info.response_n = sizeof(finished)+1; - if (prevCmd == 5){ + dynamic_response_info.response_n = sizeof(finished) + 1; + if (prevCmd == 5) { prevCmd = 0; } } - } - else { + } else { Dbprintf(_YELLOW_("!!") "Received unknown command!"); - if (prevCmd < 4){ - memcpy(dynamic_response_info.response,receivedCmd,len); + if (prevCmd < 4) { + memcpy(dynamic_response_info.response, receivedCmd, len); dynamic_response_info.response_n = len; - } - else{ + } else { dynamic_response_info.response_n = 0; } } diff --git a/client/src/proxmark3.c b/client/src/proxmark3.c index 6bc88435a..4b6cf4fad 100644 --- a/client/src/proxmark3.c +++ b/client/src/proxmark3.c @@ -117,7 +117,7 @@ static const char *prompt_dev = ""; static const char *prompt_ctx = ""; static void prompt_compose(char *buf, size_t buflen, const char *prompt_ctx, const char *prompt_dev) { - snprintf(buf, buflen-1, PROXPROMPT_COMPOSE, prompt_dev, prompt_ctx); + snprintf(buf, buflen - 1, PROXPROMPT_COMPOSE, prompt_dev, prompt_ctx); } static int check_comm(void) {