Chameleon-Mini
CryptoTDEA.h
1 /*
2  * CryptoDES.h
3  *
4  * Created on: 18.10.2016
5  * Author: dev_zzo
6  */
7 
8 #ifndef CRYPTODES_H_
9 #define CRYPTODES_H_
10 
11 #include <stdint.h>
12 #include "../Common.h"
13 
14 /* Notes on cryptography in DESFire cards
15 
16 The EV0 was the first chip in the DESFire series. It makes use of the TDEA
17 encryption to secure the comms. It also employs CBC to make things more secure.
18 
19 CBC is used in two "modes": "send mode" and "receive mode".
20 - Sending data uses the same structure as conventional encryption with CBC
21  (XOR with the IV then apply block cipher)
22 - Receiving data uses the same structure as conventional decryption with CBC
23  (apply block cipher then XOR with the IV)
24 
25 Both operations employ TDEA encryption on the PICC's side and decryption on
26 PCD's side.
27 
28 */
29 
30 /* Key sizes, in bytes */
31 #define CRYPTO_DES_KEY_SIZE 8 /* Bytes */
32 #define CRYPTO_2KTDEA_KEY_SIZE (CRYPTO_DES_KEY_SIZE * 2)
33 #define CRYPTO_3KTDEA_KEY_SIZE (CRYPTO_DES_KEY_SIZE * 3)
34 
35 typedef uint8_t Crypto2KTDEAKeyType[CRYPTO_2KTDEA_KEY_SIZE];
36 typedef uint8_t Crypto3KTDEAKeyType[CRYPTO_3KTDEA_KEY_SIZE];
37 
38 #define CRYPTO_DES_BLOCK_SIZE 8 /* Bytes */
39 #define CRYPTO_2KTDEA_BLOCK_SIZE (CRYPTO_DES_BLOCK_SIZE)
40 #define CRYPTO_3KTDEA_BLOCK_SIZE (CRYPTO_DES_BLOCK_SIZE)
41 
42 /* Prototype the CBC function pointer in case anyone needs it */
43 typedef void (*CryptoTDEACBCFuncType)(uint16_t Count, const void *Plaintext, void *Ciphertext, void *IV, const uint8_t *Keys);
44 typedef void (*CryptoTDEAFuncType)(const void *PlainText, void *Ciphertext, const uint8_t *Keys);
45 
46 void CryptoEncryptDEA(void *Plaintext, void *Ciphertext, const uint8_t *Keys);
47 void CryptoDecryptDEA(void *Plaintext, void *Ciphertext, const uint8_t *Keys);
48 void EncryptDESBuffer(uint16_t Count, const void *Plaintext, void *Ciphertext, const uint8_t *Keys);
49 void DecryptDESBuffer(uint16_t Count, void *Plaintext, const void *Ciphertext, const uint8_t *Keys);
50 
57 void CryptoEncrypt2KTDEA(const void *Plaintext, void *Ciphertext, const uint8_t *Keys);
58 void CryptoDecrypt2KTDEA(const void *Plaintext, void *Ciphertext, const uint8_t *Keys);
59 
60 void CryptoEncrypt3KTDEA(void *Plaintext, void *Ciphertext, const uint8_t *Keys);
61 void CryptoDecrypt3KTDEA(void *Plaintext, void *Ciphertext, const uint8_t *Keys);
62 
63 void Encrypt3DESBuffer(uint16_t Count, const void *Plaintext, void *Ciphertext, const uint8_t *Keys);
64 void Decrypt3DESBuffer(uint16_t Count, void *Plaintext, const void *Ciphertext, const uint8_t *Keys);
65 
66 
75 void CryptoEncrypt2KTDEA_CBCSend(uint16_t Count, const void *Input, void *Output, void *IV, const uint8_t *Keys);
76 void CryptoDecrypt2KTDEA_CBCSend(uint16_t Count, const void *Input, void *Output, void *IV, const uint8_t *Keys);
77 
86 void CryptoEncrypt2KTDEA_CBCReceive(uint16_t Count, const void *Input, void *Output, void *IV, const uint8_t *Keys);
87 void CryptoDecrypt2KTDEA_CBCReceive(uint16_t Count, const void *Input, void *Output, void *IV, const uint8_t *Keys);
88 
89 
98 void CryptoEncrypt3KTDEA_CBCSend(uint16_t Count, const void *Plaintext, void *Ciphertext, void *IV, const uint8_t *Keys);
99 void CryptoDecrypt3KTDEA_CBCReceive(uint16_t Count, const void *Plaintext, void *Ciphertext, void *IV, const uint8_t *Keys);
100 
101 /* Spec for more generic send/recv encrypt/decrypt schemes: */
102 typedef struct {
103  CryptoTDEAFuncType cryptFunc;
104  uint16_t blockSize;
105 } CryptoTDEA_CBCSpec;
106 
107 void CryptoTDEA_CBCSend(uint16_t Count, void *Plaintext, void *Ciphertext,
108  void *IV, const uint8_t *Keys, CryptoTDEA_CBCSpec CryptoSpec);
109 void CryptoTDEA_CBCRecv(uint16_t Count, void *Plaintext, void *Ciphertext,
110  void *IV, const uint8_t *Keys, CryptoTDEA_CBCSpec CryptoSpec);
111 
112 uint8_t TransferEncryptTDEASend(uint8_t *Buffer, uint8_t Count);
113 uint8_t TransferEncryptTDEAReceive(uint8_t *Buffer, uint8_t Count);
114 
121 INLINE void CryptoPaddingTDEA(uint8_t *Buffer, uint8_t BytesInBuffer, bool FirstPaddingBitSet) {
122  uint8_t PaddingByte = FirstPaddingBitSet << 7;
123  uint8_t i;
124 
125  for (i = BytesInBuffer; i < CRYPTO_DES_BLOCK_SIZE; ++i) {
126  Buffer[i] = PaddingByte;
127  PaddingByte = 0x00;
128  }
129 }
130 
131 #endif /* CRYPTODES_H_ */