1 /* ****************************************************************************
2  *                                                                          *
3  * C-Sky Microsystems Confidential                                          *
4  * -------------------------------                                          *
5  * This file and all its contents are properties of C-Sky Microsystems. The *
6  * information contained herein is confidential and proprietary and is not  *
7  * to be disclosed outside of C-Sky Microsystems except under a             *
8  * Non-Disclosured Agreement (NDA).                                         *
9  *                                                                          *
10  ****************************************************************************/
11 
12 #include <stdint.h>
13 #include <stddef.h>
14 #include <string.h>
15 #include "mbedtls/aes.h"
16 #include "aos/kernel.h"
17 #include "mbedtls/platform_util.h"
18 #if defined(CONFIG_TEE_AES)
19 #include "drv/tee.h"
20 #endif
21 
22 #if defined(MBEDTLS_AES_ALT)
23 
24 /* Parameter validation macros based on platform_util.h */
25 #define AES_VALIDATE_RET( cond )    \
26     MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_AES_BAD_INPUT_DATA )
27 #define AES_VALIDATE( cond )        \
28     MBEDTLS_INTERNAL_VALIDATE( cond )
29 
mbedtls_zeroize(void * v,size_t n)30 static void mbedtls_zeroize(void *v, size_t n)
31 {
32     volatile unsigned char *p = (unsigned char *)v;
33 
34     while (n--) {
35         *p++ = 0;
36     }
37 }
38 
mbedtls_aes_init(mbedtls_aes_context * ctx)39 void mbedtls_aes_init(mbedtls_aes_context *ctx)
40 {
41     mbedtls_zeroize(ctx, sizeof(mbedtls_aes_context));
42     sc_aes_init(&ctx->sc_ctx, 0);
43 }
44 
mbedtls_aes_free(mbedtls_aes_context * ctx)45 void mbedtls_aes_free(mbedtls_aes_context *ctx)
46 {
47     if (ctx == NULL) {
48         return;
49     }
50 
51     sc_aes_uninit(&ctx->sc_ctx);
52     mbedtls_zeroize(ctx, sizeof(mbedtls_aes_context));
53 }
54 
mbedtls_aes_setkey_enc(mbedtls_aes_context * ctx,const unsigned char * key,unsigned int keybits)55 int mbedtls_aes_setkey_enc(mbedtls_aes_context *ctx, const unsigned char *key, unsigned int keybits)
56 {
57     sc_aes_key_bits_t bits = SC_AES_KEY_LEN_BITS_128;
58     if (keybits == 128) {
59         bits = SC_AES_KEY_LEN_BITS_128;
60     } else if (keybits == 192) {
61         bits = SC_AES_KEY_LEN_BITS_192;
62     } else if (keybits == 256) {
63         bits = SC_AES_KEY_LEN_BITS_256;
64     } else {
65         return -1;
66     }
67 
68 #if defined(CONFIG_TEE_AES)
69     memcpy(ctx->key, key, keybits / 8);
70     ctx->key_len = keybits / 8;
71 #endif
72     sc_aes_set_encrypt_key(&ctx->sc_ctx, (void *)key, bits);
73     return (0);
74 }
75 
76 /*
77  * AES key schedule (decryption)
78  */
mbedtls_aes_setkey_dec(mbedtls_aes_context * ctx,const unsigned char * key,unsigned int keybits)79 int mbedtls_aes_setkey_dec(mbedtls_aes_context *ctx, const unsigned char *key, unsigned int keybits)
80 {
81     sc_aes_key_bits_t bits = SC_AES_KEY_LEN_BITS_128;
82     if (keybits == 128) {
83         bits = SC_AES_KEY_LEN_BITS_128;
84     } else if (keybits == 192) {
85         bits = SC_AES_KEY_LEN_BITS_192;
86     } else if (keybits == 256) {
87         bits = SC_AES_KEY_LEN_BITS_256;
88     } else {
89         return -1;
90     }
91 
92 #if defined(CONFIG_TEE_AES)
93     return mbedtls_aes_setkey_enc(ctx, key, keybits);
94 #endif
95     sc_aes_set_decrypt_key(&ctx->sc_ctx, (void *)key, bits);
96     return 0;
97 }
98 
99 /*
100  * AES-ECB block encryption/decryption
101  */
mbedtls_aes_crypt_ecb(mbedtls_aes_context * ctx,int mode,const unsigned char input[16],unsigned char output[16])102 int mbedtls_aes_crypt_ecb(mbedtls_aes_context *ctx, int mode, const unsigned char input[16],
103                           unsigned char output[16])
104 {
105 
106     if (mode == MBEDTLS_AES_ENCRYPT) {
107         sc_aes_ecb_encrypt(&ctx->sc_ctx, (void *)input, output, 16);
108     } else if (mode == MBEDTLS_AES_DECRYPT) {
109         sc_aes_ecb_decrypt(&ctx->sc_ctx, (void *)input, output, 16);
110     }
111 
112 #if defined(CONFIG_TEE_AES)
113     if (mode == MBEDTLS_AES_ENCRYPT) {
114          csi_tee_aes_encrypt_ecb(input, 16, ctx->key, ctx->key_len, output);
115     } else if (mode == MBEDTLS_AES_DECRYPT) {
116          csi_tee_aes_decrypt_ecb(input, 16, ctx->key, ctx->key_len, output);
117     }
118 #endif
119     return 0;
120 }
121 /*
122  * AES-CBC buffer encryption/decryption
123  */
mbedtls_aes_crypt_cbc(mbedtls_aes_context * ctx,int mode,size_t length,unsigned char iv[16],const unsigned char * input,unsigned char * output)124 int mbedtls_aes_crypt_cbc(mbedtls_aes_context *ctx, int mode, size_t length, unsigned char iv[16],
125                           const unsigned char *input, unsigned char *output)
126 {
127     int           i;
128     unsigned char temp[16];
129     if (mode == MBEDTLS_AES_DECRYPT) {
130         while (length > 0) {
131             memcpy(temp, input, 16);
132             aos_kernel_sched_suspend();
133             mbedtls_aes_crypt_ecb(ctx, mode, input, output);
134             aos_kernel_sched_resume();
135             for (i = 0; i < 16; i++)
136                 output[i] = (unsigned char)(output[i] ^ iv[i]);
137 
138             memcpy(iv, temp, 16);
139 
140             input += 16;
141             output += 16;
142             length -= 16;
143         }
144     } else {
145         while (length > 0) {
146             for (i = 0; i < 16; i++)
147                 output[i] = (unsigned char)(input[i] ^ iv[i]);
148 
149             mbedtls_aes_crypt_ecb(ctx, mode, output, output);
150             memcpy(iv, output, 16);
151 
152             input += 16;
153             output += 16;
154             length -= 16;
155         }
156     }
157     return (0);
158 }
159 
160 #if defined(MBEDTLS_CIPHER_MODE_CTR)
161 /*
162  * AES-CTR buffer encryption/decryption
163  */
mbedtls_aes_crypt_ctr(mbedtls_aes_context * ctx,size_t length,size_t * nc_off,unsigned char nonce_counter[16],unsigned char stream_block[16],const unsigned char * input,unsigned char * output)164 int mbedtls_aes_crypt_ctr(mbedtls_aes_context *ctx, size_t length, size_t *nc_off,
165                           unsigned char nonce_counter[16], unsigned char stream_block[16],
166                           const unsigned char *input, unsigned char *output)
167 {
168     int    c, i;
169     size_t n = *nc_off;
170 
171     while (length--) {
172         if (n == 0) {
173             mbedtls_aes_crypt_ecb(ctx, MBEDTLS_AES_ENCRYPT, nonce_counter, stream_block);
174 
175             for (i = 16; i > 0; i--)
176                 if (++nonce_counter[i - 1] != 0)
177                     break;
178         }
179         c         = *input++;
180         *output++ = (unsigned char)(c ^ stream_block[n]);
181 
182         n = (n + 1) & 0x0F;
183     }
184 
185     *nc_off = n;
186 
187     return (0);
188 }
189 #endif /* MBEDTLS_CIPHER_MODE_CTR */
190 
191 
192 #if defined(MBEDTLS_CIPHER_MODE_CFB)
193 /*
194  * AES-CFB128 buffer encryption/decryption
195  */
mbedtls_aes_crypt_cfb128(mbedtls_aes_context * ctx,int mode,size_t length,size_t * iv_off,unsigned char iv[16],const unsigned char * input,unsigned char * output)196 int mbedtls_aes_crypt_cfb128( mbedtls_aes_context *ctx,
197                        int mode,
198                        size_t length,
199                        size_t *iv_off,
200                        unsigned char iv[16],
201                        const unsigned char *input,
202                        unsigned char *output )
203 {
204     int c;
205     size_t n;
206 
207     AES_VALIDATE_RET( ctx != NULL );
208     AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
209                       mode == MBEDTLS_AES_DECRYPT );
210     AES_VALIDATE_RET( iv_off != NULL );
211     AES_VALIDATE_RET( iv != NULL );
212     AES_VALIDATE_RET( input != NULL );
213     AES_VALIDATE_RET( output != NULL );
214 
215     n = *iv_off;
216 
217     if( n > 15 )
218         return( MBEDTLS_ERR_AES_BAD_INPUT_DATA );
219 
220     if( mode == MBEDTLS_AES_DECRYPT )
221     {
222         while( length-- )
223         {
224             if( n == 0 )
225                 mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
226 
227             c = *input++;
228             *output++ = (unsigned char)( c ^ iv[n] );
229             iv[n] = (unsigned char) c;
230 
231             n = ( n + 1 ) & 0x0F;
232         }
233     }
234     else
235     {
236         while( length-- )
237         {
238             if( n == 0 )
239                 mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
240 
241             iv[n] = *output++ = (unsigned char)( iv[n] ^ *input++ );
242 
243             n = ( n + 1 ) & 0x0F;
244         }
245     }
246 
247     *iv_off = n;
248 
249     return( 0 );
250 }
251 
252 /*
253  * AES-CFB8 buffer encryption/decryption
254  */
mbedtls_aes_crypt_cfb8(mbedtls_aes_context * ctx,int mode,size_t length,unsigned char iv[16],const unsigned char * input,unsigned char * output)255 int mbedtls_aes_crypt_cfb8( mbedtls_aes_context *ctx,
256                             int mode,
257                             size_t length,
258                             unsigned char iv[16],
259                             const unsigned char *input,
260                             unsigned char *output )
261 {
262     unsigned char c;
263     unsigned char ov[17];
264 
265     AES_VALIDATE_RET( ctx != NULL );
266     AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
267                       mode == MBEDTLS_AES_DECRYPT );
268     AES_VALIDATE_RET( iv != NULL );
269     AES_VALIDATE_RET( input != NULL );
270     AES_VALIDATE_RET( output != NULL );
271     while( length-- )
272     {
273         memcpy( ov, iv, 16 );
274         mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
275 
276         if( mode == MBEDTLS_AES_DECRYPT )
277             ov[16] = *input;
278 
279         c = *output++ = (unsigned char)( iv[0] ^ *input++ );
280 
281         if( mode == MBEDTLS_AES_ENCRYPT )
282             ov[16] = c;
283 
284         memcpy( iv, ov + 1, 16 );
285     }
286 
287     return( 0 );
288 }
289 #endif /* MBEDTLS_CIPHER_MODE_CFB */
290 
291 #endif
292