There are lots of questions about Desfire EV1 cards here on Stackoverflow.
But if you search for some example data the only place where you will find a few bytes is in Ridrix Blog. But this is quite incomplete.
A lot of people wrote their problems there while developing code for Desfire cards. But mostly when they solved their problem they were too lazy to post the solution. So you find many questions but very few answers with data examples.
Even if you have the Desfire EV1 documentation (I dont have it, I studied easypay code), you will need more than that. A documentation is only theory. But what is the reason that your card returns an Authentication Error or an Integrity Error or an unexpected CMAC?
- Is the Session key OK ?
- Is CBC working in the correct mode ?
- Is the CMAC calculated correctly ?
- Is the CRC32 correct ?
- Is the IV of the session key correct before / after a function call ?
Without examples you are completely lost.
After spending several weeks with Desfire EV1 development I decided to post some examples for all those who need input data to feed their complex cryprographic functions and compare the output with the expected data. I know that this is EXTREMELY helpfull.
Here you find some Debug output from the most important Desfire EV1 operations.
Currently you cannot find this information in internet.
If I would have had these examples I would have saved a LOT of time developing my code.
Pitfalls for ISO and AES authenticated sessions
In ISO and AES mode EVERY encryption/decryption goes through CBC.
The IV of the session key is reset to zero only ONCE when the key is created after authentication.
The IV of the authentication key is reset only ONCE when authentication starts.
During authentication:
- Random B is received from the card with RECEIVE + DECIPHER
- Random AB is sent to the card with SEND + ENCIPHER
- Random A is received with RECEIVE + DECIPHER
The CMAC is a copy of the IV of the session key.
The CMAC must mostly be calculated for data sent to the card and for data returned from the card.
But all commands that do a CBC encryption (e.g. ChangeKeySettings) differ from that scheme.
Commands that send/receive multiple frames (e.g. GetApplicationIDs) must calculate the CMAC over the data of all frames that have been sent/received (not including the 0xAF status byte).
For TX data the CMAC is calculated over the command byte + all parameter bytes.
For RX data the CMAC is calculated over all response bytes + the last status byte (always 00 = Success) that must be appended at the end!
The authentication is invalidated:
- when an error occures (status != 00 and != AF),
- when SelectApplication is executed,
- after the same key has been changed that was used for authentication,
- when another card comes into the RF field (don't forget to reset your variables).
In these cases the session key is no longer valid and so a CMAC must not be calculated.
The CRC32 of the new key is calculated only over the key data itself.
The CRC32 of the cryptogram is calculated over command, key number and the not yet encrypted cryptogram.
The following debug output has been generated by my code running in a Teensy 3.2 with a PN532 board from Adafruit.
For further details see my source code.
The source code has been written for Arduino/Teensy, but it has been designed multiplatform so that it requires only changing a few lines to compile it on Visual Studio, Linux or other platforms.
In the following examples all keys have key version 0x10.
ISO Authentication with 2K3DES default key #0
*** Authenticate(KeyNo= 0, Key= 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 (DES))
Sending: <1A 00>
Response: <AF B8 90 04 7F 2D C8 D6 8B>
* RndB_enc: B8 90 04 7F 2D C8 D6 8B
* RndB: 74 B8 43 5F CB A0 B6 75
* RndB_rot: B8 43 5F CB A0 B6 75 74
* RndA: 92 31 34 8B 66 35 A8 AF
* RndAB: 92 31 34 8B 66 35 A8 AF B8 43 5F CB A0 B6 75 74
* RndAB_enc: 7C 84 6A 50 7B 9B 6E 68 64 BC 33 72 A3 06 A8 C1
Sending: <AF 7C 84 6A 50 7B 9B 6E 68 64 BC 33 72 A3 06 A8 C1>
Response: <00 B7 96 DD 3F 81 15 45 F3>
* RndA_enc: B7 96 DD 3F 81 15 45 F3
* RndA_dec: 31 34 8B 66 35 A8 AF 92
* RndA_rot: 31 34 8B 66 35 A8 AF 92
* SessKey: 92 30 34 8A 74 B8 42 5E 92 30 34 8A 74 B8 42 5E (DES)
Change 2K3DES default key #0
*** ChangeKey(KeyNo= 0)
* SessKey: B4 28 2E FA 9E B8 2C AE B4 28 2E FA 9E B8 2C AE (DES)
* SessKey IV: 00 00 00 00 00 00 00 00
* New Key: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 (2K3DES)
* CRC Crypto: 0x5001FFC5
* Cryptogram: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 C5 FF 01 50 00 00 00 00
* CryptogrEnc: 87 99 59 11 8B D7 7C 70 10 7B CD B0 C0 9C C7 DA 82 15 04 AA 1E 36 04 9C
Sending: <C4 00 87 99 59 11 8B D7 7C 70 10 7B CD B0 C0 9C C7 DA 82 15 04 AA 1E 36 04 9C>
Response: <00>
Change 2K3DES default key #1
*** ChangeKey(KeyNo= 1)
* SessKey: 9C 70 56 82 5C 08 9E C8 9C 70 56 82 5C 08 9E C8 (DES)
* SessKey IV: 00 00 00 00 00 00 00 00
* New Key: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 (2K3DES)
* Cur Key: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 (DES)
* CRC Crypto: 0xD7A73486
* CRC New Key: 0xC4EF3A3A
* Cryptogram: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 86 34 A7 D7 3A 3A EF C4
* CryptogrEnc: 7D 83 D3 4E FB 6C 84 98 48 E2 D6 37 AD A2 D0 87 14 36 1A E6 C4 63 14 52
Sending: <C4 01 7D 83 D3 4E FB 6C 84 98 48 E2 D6 37 AD A2 D0 87 14 36 1A E6 C4 63 14 52>
Response: <00 1D 5C 27 97 10 86 30 8D>
CMAC: 1D 5C 27 97 10 86 30 8D
ISO Authentication with 3K3DES default key #0
*** Authenticate(KeyNo= 0, Key= 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 (3K3DES))
Sending: <1A 00>
Response: <AF 14 65 76 AC 1B 7D B8 CA 24 84 C5 69 7F 80 12 E1>
* RndB_enc: 14 65 76 AC 1B 7D B8 CA 24 84 C5 69 7F 80 12 E1
* RndB: BA 91 37 BB 7A 18 33 E7 39 F0 5E 8F 07 87 D0 C4
* RndB_rot: 91 37 BB 7A 18 33 E7 39 F0 5E 8F 07 87 D0 C4 BA
* RndA: F5 68 6F 3A 39 1C D3 8E BD 10 77 22 81 44 5B F6
* RndAB: F5 68 6F 3A 39 1C D3 8E BD 10 77 22 81 44 5B F6 91 37 BB 7A 18 33 E7 39 F0 5E 8F 07 87 D0 C4 BA
* RndAB_enc: D0 55 BD 5E A0 1E BF C3 02 93 D4 8A 54 A0 51 B4 0A 66 57 7A 38 3C 58 ED 77 5C 51 BC 97 D4 FA BD
Sending: <AF D0 55 BD 5E A0 1E BF C3 02 93 D4 8A 54 A0 51 B4 0A 66 57 7A 38 3C 58 ED 77 5C 51 BC 97 D4 FA BD>
Response: <00 E1 EE 93 F0 12 C8 D6 72 11 D4 33 7C AD 56 6A 40>
* RndA_enc: E1 EE 93 F0 12 C8 D6 72 11 D4 33 7C AD 56 6A 40
* RndA_dec: 68 6F 3A 39 1C D3 8E BD 10 77 22 81 44 5B F6 F5
* RndA_rot: 68 6F 3A 39 1C D3 8E BD 10 77 22 81 44 5B F6 F5
* SessKey: F4 68 6E 3A BA 90 36 BA D2 8E BC 10 32 E6 38 F0 80 44 5A F6 06 86 D0 C4 (3K3DES)
Change 3K3DES default key #0
*** ChangeKey(KeyNo= 0)
* SessKey: F4 68 6E 3A BA 90 36 BA D2 8E BC 10 32 E6 38 F0 80 44 5A F6 06 86 D0 C4 (3K3DES)
* SessKey IV: 00 00 00 00 00 00 00 00
* New Key: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 70 60 50 40 30 20 10 00 (3K3DES)
* CRC Crypto: 0xA2003ED6
* Cryptogram: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 70 60 50 40 30 20 10 00 D6 3E 00 A2 00 00 00 00
* CryptogrEnc: 7F 88 90 C7 CA B9 A4 22 81 73 A6 41 B6 5F 0F 43 FD 40 4A 01 13 71 A9 90 4A 62 9E 3C 20 B2 FF 63
Sending: <C4 00 7F 88 90 C7 CA B9 A4 22 81 73 A6 41 B6 5F 0F 43 FD 40 4A 01 13 71 A9 90 4A 62 9E 3C 20 B2 FF 63>
Response: <00>
Change 3K3DES default key #1
*** ChangeKey(KeyNo= 1)
* SessKey: 9C 52 0E 3C B4 5A B2 A4 A2 00 C4 DA 72 2C 0E F4 38 FE 8A 48 F8 18 9E 56 (3K3DES)
* SessKey IV: 00 00 00 00 00 00 00 00
* New Key: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 70 60 50 40 30 20 10 00 (3K3DES)
* Cur Key: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 (3K3DES)
* CRC Crypto: 0x078BAED8
* CRC New Key: 0x12A6733E
* Cryptogram: 00 10 20 31 40 50 60 70 80 90 A0 B0 B0 A0 90 80 70 60 50 40 30 20 10 00 D8 AE 8B 07 3E 73 A6 12
* CryptogrEnc: 72 18 2F 5B 0C F1 7E A0 86 A5 AE A5 64 ED 98 7A F3 90 CD B3 78 36 4E 2B C2 45 8B 3A E3 23 98 4D
Sending: <C4 01 72 18 2F 5B 0C F1 7E A0 86 A5 AE A5 64 ED 98 7A F3 90 CD B3 78 36 4E 2B C2 45 8B 3A E3 23 98 4D>
Response: <00 D2 E3 BD 0D 09 47 72 ED>
CMAC: D2 E3 BD 0D 09 47 72 ED
AES Authentication with AES default key #0
*** Authenticate(KeyNo= 0, Key= 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 (AES))
Sending: <AA 00>
Response: <AF FF 0A FB 10 B4 3F 3B 34 23 36 57 0F 7A 0E 8B 74>
* RndB_enc: FF 0A FB 10 B4 3F 3B 34 23 36 57 0F 7A 0E 8B 74
* RndB: 1F 45 19 27 E7 C0 FC DE 60 9E E8 02 EF 69 76 04
* RndB_rot: 45 19 27 E7 C0 FC DE 60 9E E8 02 EF 69 76 04 1F
* RndA: 73 AE 5D 30 17 42 21 64 FB 16 25 D8 1F 2A 69 8C
* RndAB: 73 AE 5D 30 17 42 21 64 FB 16 25 D8 1F 2A 69 8C 45 19 27 E7 C0 FC DE 60 9E E8 02 EF 69 76 04 1F
* RndAB_enc: B3 11 34 03 F5 73 95 35 CA 1A 5D 4B D4 38 BE 03 2B 54 28 32 3D 0A 83 4D 11 8F 35 06 C4 2C 5B 01
Sending: <AF B3 11 34 03 F5 73 95 35 CA 1A 5D 4B D4 38 BE 03 2B 54 28 32 3D 0A 83 4D 11 8F 35 06 C4 2C 5B 01>
Response: <00 E2 AE 7D 31 29 48 19 69 E9 A0 C7 CC 89 1E DF 58>
* RndA_enc: E2 AE 7D 31 29 48 19 69 E9 A0 C7 CC 89 1E DF 58
* RndA_dec: AE 5D 30 17 42 21 64 FB 16 25 D8 1F 2A 69 8C 73
* RndA_rot: AE 5D 30 17 42 21 64 FB 16 25 D8 1F 2A 69 8C 73
* SessKey: 73 AE 5D 30 1F 45 19 27 1F 2A 69 8C EF 69 76 04 (AES)
Change AES default key #0
*** ChangeKey(KeyNo= 0)
* SessKey: 73 AE 5D 30 1F 45 19 27 1F 2A 69 8C EF 69 76 04 (AES)
* SessKey IV: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
* New Key: 00 10 20 30 40 50 60 70 80 90 A0 B0 B0 A0 90 80 (AES)
* CRC Crypto: 0x6BE6C6D2
* Cryptogram: 00 10 20 30 40 50 60 70 80 90 A0 B0 B0 A0 90 80 10 D2 C6 E6 6B 00 00 00 00 00 00 00 00 00 00 00
* CryptogrEnc: 97 41 8E 6C C0 1C 4E 6F AD 4D 87 4D 8D 42 5C EA 32 51 36 11 47 2C DA 04 E3 5E FB 77 9A 7D A0 E4
Sending: <C4 00 97 41 8E 6C C0 1C 4E 6F AD 4D 87 4D 8D 42 5C EA 32 51 36 11 47 2C DA 04 E3 5E FB 77 9A 7D A0 E4>
Response: <00>
Change AES default key #1
*** ChangeKey(KeyNo= 1)
* SessKey: 1C D3 8E BD 95 F3 1C 8A B8 7F 0A C9 C4 EB 64 C6 (AES)
* SessKey IV: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
* New Key: 00 10 20 30 40 50 60 70 80 90 A0 B0 B0 A0 90 80 (AES)
* Cur Key: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 (AES)
* CRC Crypto: 0x84B47033
* CRC New Key: 0x1979E3BF
* Cryptogram: 00 10 20 30 40 50 60 70 80 90 A0 B0 B0 A0 90 80 10 33 70 B4 84 BF E3 79 19 00 00 00 00 00 00 00
* CryptogrEnc: 30 23 FA 06 2D 25 0A 04 35 BA E9 45 CA BE 96 5D 62 2A 47 1D 32 5D 1D 42 EA 81 44 41 CB 1A 20 C3
Sending: <C4 01 30 23 FA 06 2D 25 0A 04 35 BA E9 45 CA BE 96 5D 62 2A 47 1D 32 5D 1D 42 EA 81 44 41 CB 1A 20 C3>
Response: <00 9B 68 30 91 50 E0 72 5E>
CMAC: 9B 68 30 91 50 E0 72 5E
CMAC Calculation for AES 128
From: NIST
AES Key: 2b 7e 15 16 28 ae d2 a6 ab f7 15 88 09 cf 4f 3c
SubKey1: fb ee d6 18 35 71 33 66 7c 85 e0 8f 72 36 a8 de
SubKey2: f7 dd ac 30 6a e2 66 cc f9 0b c1 1e e4 6d 51 3b
Message: <empty>
CMAC: bb 1d 69 29 e9 59 37 28 7f a3 7d 12 9b 75 67 46
Message: 6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a
CMAC: 07 0a 16 b4 6b 4d 41 44 f7 9b dd 9d d0 4a 28 7c
Message: 6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a ae 2d 8a 57 1e 03 ac 9c 9e b7 6f ac 45 af 8e 51 30 c8 1c 46 a3 5c e4 11
CMAC: df a6 67 47 de 9a e6 30 30 ca 32 61 14 97 c8 27
If you need more examples (also for CreateApplication, SelectApplication, DeleteApplication, GetApplicationIDs, GetKeyVersion, GetKeySettings, ChangeKeySettings, GetCardVersion, FormatCard, CreateStdDataFile, GetFileIDs, GetFileSettings, WriteFileData, ReadFileData, DeleteFile) download the ZIP file on Codeproject where you find a HTML file with the entire selftest that tests all these commands.