From 6a5f5218002e09d5771854537bd21a23df7a0aff Mon Sep 17 00:00:00 2001 From: TheJoKlLa Date: Thu, 1 Oct 2020 23:47:47 +0200 Subject: [PATCH] Added: Authenticate --- NFC/Mifare DESFire/MifareDESFire.cs | 76 ++++++++++++++++++++--------- 1 file changed, 52 insertions(+), 24 deletions(-) diff --git a/NFC/Mifare DESFire/MifareDESFire.cs b/NFC/Mifare DESFire/MifareDESFire.cs index c6617b7..0b38925 100644 --- a/NFC/Mifare DESFire/MifareDESFire.cs +++ b/NFC/Mifare DESFire/MifareDESFire.cs @@ -4,6 +4,7 @@ using PCSC.Iso7816; using System; using System.Collections.Generic; using System.IO; +using System.Linq; using System.Net.Http; using System.Text; @@ -81,7 +82,7 @@ namespace NFC.Mifare_DESFire /// public void Authenticate(byte key_id, byte[] key) { - APDUCommand cmd_getchallange = new APDUCommand(IsoCase.Case4Short) + APDUCommand cmd_challange_request = new APDUCommand(IsoCase.Case4Short) { CLA = 0x90, INS = (byte)0x1A, @@ -90,56 +91,83 @@ namespace NFC.Mifare_DESFire key_id } }; - APDUResponse response = _Card.Transmit(cmd_getchallange); + APDUResponse response = _Card.Transmit(cmd_challange_request); - byte[] challenge = response.Body; - Console.WriteLine("Challange: {0}", toHexString(challenge)); + byte[] rndB_enc = response.Body; + Console.WriteLine("rndB_enc: {0}", toHexString(rndB_enc)); + + DES des = new DES(); + byte[] rndB = des.Decrypt(rndB_enc, key, GenerateDefaultKey(8)); + Console.WriteLine("rndB: {0}", toHexString(rndB)); + + byte[] iv = new byte[8]; + rndB.CopyTo(iv, 0); + + byte[] rndB_rl = rotateLeft(rndB); + Console.WriteLine("rndB_enc: {0}", toHexString(rndB_rl)); byte[] rndA = new byte[] { - 0x92, 0x31, 0x34, 0x8B, 0x66, 0x35, 0xA8, 0xAF + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 }; Console.WriteLine("rndA: {0}", toHexString(rndA)); - TripleDES des = new TripleDES(); - byte[] rndB = des.Decrypt(challenge, key, GenerateDefaultKey(8)); - Console.WriteLine("rndB: {0}", toHexString(rndB)); + byte[] rndAB = concatenate(rndA, rndB_rl); + Console.WriteLine("rndAB: {0}", toHexString(rndAB)); - byte[] leftRotatedRndB = rotateLeft(rndB); - Console.WriteLine("leftRotatedRndB: {0}", toHexString(leftRotatedRndB)); + byte[] rndAB_enc = des.Encrypt(rndAB, key, rndB_enc); + Console.WriteLine("rndA_rndB_enc: {0}", toHexString(rndAB_enc)); + iv = lastBlock(rndAB_enc); - byte[] rndA_rndB = concatenate(rndA, leftRotatedRndB); - Console.WriteLine("rndA_rndB: {0}", toHexString(rndA_rndB)); - - byte[] challengeAnswer = des.Encrypt(rndA_rndB, key, GenerateDefaultKey(8)); - Console.WriteLine("challengeAnswer: {0}", toHexString(challengeAnswer)); - - APDUCommand cmd_answerchallange = new APDUCommand(IsoCase.Case4Short) + APDUCommand cmd_challange_response = new APDUCommand(IsoCase.Case4Short) { CLA = 0x90, INS = (byte)0xAF, - Data = challengeAnswer + Data = rndAB_enc }; - Console.WriteLine("cmd_answerchallange: {0}", toHexString(cmd_answerchallange.ToArray())); + Console.WriteLine("cmd_challange_response: {0}", toHexString(cmd_challange_response.ToArray())); - response = _Card.Transmit(cmd_answerchallange); + response = _Card.Transmit(cmd_challange_response); byte[] encryptedRndAFromCard = response.Body; Console.WriteLine("encryptedRndAFromCard: {0}", toHexString(encryptedRndAFromCard)); - byte[] rotatedRndAFromCard = des.Decrypt(encryptedRndAFromCard, key, GenerateDefaultKey(8)); + byte[] rotatedRndAFromCard = des.Decrypt(encryptedRndAFromCard, key, iv); Console.WriteLine("rotatedRndAFromCard: {0}", toHexString(rotatedRndAFromCard)); byte[] rndAFromCard = rotateRight(rotatedRndAFromCard); Console.WriteLine("rndAFromCard: {0}", toHexString(rndAFromCard)); - if (!rndA.Equals(rndAFromCard)) + if (!rndA.SequenceEqual(rndAFromCard)) { throw new Exception("???"); } } - private String toHexString(byte[] data) + public byte[] lastBlock(byte[] data) + { + byte[] block = new byte[8]; + + for(int i = 0; i < block.Length; i++) + { + block[i] = data[data.Length - block.Length + i]; + } + + return block; + } + public byte[] exclusiveOR(byte[] a, byte[] b) + { + byte[] c = new byte[a.Length]; + + for (int i = 0; i < a.Length; i++) + { + c[i] = (byte)(a[i] ^ b[i]); + } + + return c; + } + + private String toHexString(byte[] data) { return BitConverter.ToString(data).Replace("-", string.Empty); } @@ -165,7 +193,7 @@ namespace NFC.Mifare_DESFire data.CopyTo(rotate, 0); byte temp = rotate[rotate.Length - 1]; - for (var i = rotate.Length - 1; i > 1; i--) + for (var i = rotate.Length - 1; i > 0; i--) { rotate[i] = rotate[i - 1]; }