Migrate to openssl 1.1
[platform/core/security/drm-service-core-tizen.git] / tadcore / TADCInterface / TADC_IF.cpp
1 /*
2  * Copyright (c) 2000-2019 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Flora License, Version 1.1 (the License);
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *     http://floralicense.org/license/
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an AS IS BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 //#define _SLP_SIMUL
18 #include "TADC_IF.h"
19 #include "TADC_Util.h"
20 #include "TADC_ErrorCode.h"
21
22 #include "drm_intf_tapps.h"
23
24 #include <openssl/aes.h>
25 #include <openssl/sha.h>
26 #include <openssl/dh.h>
27 #include <openssl/bn.h>
28 #include <openssl/modes.h>
29
30 //2011.03.08 to verify signature
31 #include <openssl/x509.h>
32 #include <openssl/x509_vfy.h>
33 #include <openssl/evp.h>
34 #include <openssl/rsa.h>
35 #include <openssl/err.h>
36 #include <openssl/pem.h>
37
38 #include <dirent.h>
39
40 #include <cerrno>
41 #include <memory>
42
43 #include "DUIDGenerator.h"
44
45
46 int TADC_IF_GetDUID(char *Duid)
47 {
48         if (!Duid) {
49                 DRM_TAPPS_EXCEPTION("Invalid argument.");
50                 return TADC_GETDUID_ERROR;
51         }
52
53         char *duid = NULL;
54
55         if (get_duid(&duid) < 0 || !duid) {
56                 DRM_TAPPS_EXCEPTION("Failed to get DUID.");
57                 return TADC_GETDUID_ERROR;
58         }
59
60         DRM_TAPPS_LOG("DUID is [%s]", duid);
61         memcpy(Duid, duid, strlen(duid) + 1);
62
63         free(duid);
64
65         return TADC_SUCCESS;
66 }
67
68 int TADC_IF_GetDHKey(T_DH_INFO *t_dhinfo)
69 {
70         DH *pDH = NULL;
71         TADC_IF_MemSet(t_dhinfo, 0, sizeof(t_dh_info));
72
73         // Debug
74         DRM_TAPPS_LOG("After TADC_IF_MemSet(t_dhinfo, 0, sizeof(t_dh_info))");
75
76         //1. dh new
77         if ((pDH = DH_new()) == NULL) {
78                 DRM_TAPPS_EXCEPTION("DH_new() error!");
79                 return -1;
80         }
81
82         // Debug
83         DRM_TAPPS_LOG("After DH_new");
84
85         //2. Set the Prime and Generator Value
86         BYTE prime64[64] = {
87                 0xAE, 0xD9, 0x65, 0x3C, 0x86, 0x3E, 0xD9, 0x6F, 0x31, 0x6E,
88                 0xF6, 0x08, 0x35, 0xD5, 0x01, 0xC1, 0x41, 0x2E, 0xDD, 0x7E,
89                 0xE9, 0x09, 0x99, 0x73, 0xF3, 0xB3, 0xAB, 0x1F, 0x80, 0x85,
90                 0x44, 0x22, 0xDA, 0x07, 0x32, 0x18, 0xC1, 0xF8, 0xC4, 0xED,
91                 0x9F, 0x66, 0x88, 0xCF, 0xD6, 0x18, 0x8B, 0x28, 0x56, 0xA5,
92                 0xB3, 0x6A, 0x8E, 0xBB, 0xC4, 0x2B, 0x2B, 0x3A, 0x9C, 0x20,
93                 0x4E, 0xF7, 0x7F, 0xC3
94         };
95         BYTE generator[1] = {DH_GENERATOR_5};
96
97         DH_set0_pqg(pDH, BN_bin2bn(prime64, 64, NULL), nullptr,
98                         BN_bin2bn(generator, 1, NULL));
99
100         /* Set a to run with normal modexp and b to use constant time */
101         DH_clear_flags(pDH, DH_FLAG_NO_EXP_CONSTTIME);
102
103         // Debug
104         DRM_TAPPS_LOG("After Set the Prime and Generator Value");
105
106         //3. Generate DH Key
107         if (!DH_generate_key(pDH)) {
108                 DRM_TAPPS_EXCEPTION("DH_generate_key() error!");
109                 return -1;
110         }
111
112         // Debug
113         DRM_TAPPS_LOG("After DH_generate_key");
114
115         //4. Save DH Infos ( p, g, A, a )
116         TADC_IF_MemCpy(t_dhinfo->p, prime64, 64);
117         t_dhinfo->pSize = 64;
118         t_dhinfo->g = DH_GENERATOR_5;
119         t_dhinfo->ASize = BN_bn2bin(DH_get0_pub_key(pDH), t_dhinfo->A);
120         t_dhinfo->aSize = BN_bn2bin(DH_get0_priv_key(pDH), t_dhinfo->a);
121
122         //5. DH Free
123         DH_free(pDH);
124
125         // Debug
126         DRM_TAPPS_LOG("After DH_free");
127
128         return 0;
129 }
130
131 int TADC_IF_GetDHKey_K(T_DH_INFO *t_dhinfo)
132 {
133         DH *pDH = NULL;
134         BIGNUM *pPubKey = NULL;
135
136         char tempbuf[DHKey_SIZE + 1];
137         int i = 0;
138
139         unsigned char tempG[1];
140
141         TADC_IF_MemSet(tempbuf, 0, sizeof(tempbuf));
142
143         //1. dh new
144         if ((pDH = DH_new()) == NULL) {
145                 DRM_TAPPS_EXCEPTION("DH_new() error!");
146                 return -1;
147         }
148
149         //2.Set DH Info to pDH
150         tempG[0] = t_dhinfo->g;
151         DH_set0_pqg(pDH, BN_bin2bn(t_dhinfo->p, t_dhinfo->pSize, NULL), nullptr,
152                         BN_bin2bn(tempG, 1, NULL));
153         DH_clear_flags(pDH, DH_FLAG_NO_EXP_CONSTTIME);
154         DH_set0_key(pDH, BN_bin2bn(t_dhinfo->A, t_dhinfo->ASize, NULL),
155                         BN_bin2bn(t_dhinfo->a, t_dhinfo->aSize, NULL));
156
157         //3. Set Public Key of Server
158         pPubKey = BN_bin2bn(t_dhinfo->B, t_dhinfo->BSize, NULL);
159
160         //4. Compute DH Session Key
161         if ((i = DH_compute_key((BYTE *)tempbuf, pPubKey, pDH)) < 0) {
162                 DRM_TAPPS_EXCEPTION("DH_compute_key() error! \n");
163                 return -1;
164         }
165
166         for (i = 0; i < (t_dhinfo -> BSize / 2); i++) {
167                 t_dhinfo->K[i] = tempbuf[i * 2] ^ tempbuf[(i * 2) + 1];
168         }
169
170         //5. DH Free
171         DH_free(pDH);
172         BN_free(pPubKey);
173
174         return 0;
175 }
176
177 /* Only handles 128 bit aes key */
178 int TADC_IF_AES_CTR(unsigned char *pKey, int ivLen, unsigned char *pIV,
179                                         int inLen, unsigned char *in, int *pOutLen, unsigned char *out)
180 {
181         AES_KEY stKey;
182         UINT num;
183         TADC_U8 ecount[16];
184         TADC_U8 chain[16];
185
186         AES_set_encrypt_key(pKey, 128, &stKey);
187
188         num = 0;
189
190         TADC_IF_MemSet(ecount, 0, sizeof(ecount));
191         TADC_IF_MemSet(chain, 0, sizeof(chain));
192         TADC_IF_MemCpy(chain, pIV, ivLen);
193
194         CRYPTO_ctr128_encrypt(in, out, inLen, &stKey, chain, ecount, &num, (block128_f)AES_encrypt);
195
196         *pOutLen = inLen;
197
198         return 0;
199 }
200
201 int TADC_IF_SHA1(unsigned char *in, int inLen, unsigned char *out)
202 {
203         SHA_CTX AlgInfo;
204
205         SHA1_Init(&AlgInfo);
206         SHA1_Update(&AlgInfo, in, inLen);
207         SHA1_Final(out, &AlgInfo);
208
209         return 0;
210 }
211
212 int TADC_IF_VerifySignature(unsigned char *inData, int inLen,
213                                                         unsigned char *sigData, int sigLen,
214                                                         unsigned char *cert, int certLen)
215 {
216         unsigned char hashValue[20];
217         int iRet = 0;
218
219         X509 *pX509 = NULL;
220         EVP_PKEY *pKey = NULL;
221         RSA *pRsa = NULL;
222
223         //Check parameters
224         if (inData == NULL || sigData == NULL || cert == NULL || inLen < 1 ||
225                         sigLen < 1 || certLen < 1) {
226                 DRM_TAPPS_EXCEPTION("Parameter error!");
227                 return -1;
228         }
229
230         iRet = 0;
231
232         //1. Make Hash value of indata by using SHA1
233         TADC_IF_SHA1(inData, inLen, hashValue);
234
235         //2. Get RSA Public Key from cert data ( DER )
236         pX509 = d2i_X509(NULL, (const unsigned char **)&cert, certLen);
237
238         if (pX509 == NULL) {
239                 DRM_TAPPS_EXCEPTION("Get RSA Public Key from cert data!");
240                 return -1;
241         }
242
243         pKey = X509_get_pubkey(pX509);
244
245         if (pKey == NULL) {
246                 DRM_TAPPS_EXCEPTION("X509_get_pubkey!");
247                 return -1;
248         }
249
250         pRsa = EVP_PKEY_get1_RSA(pKey);
251
252         if (pRsa == NULL) {
253                 DRM_TAPPS_EXCEPTION("EVP_PKEY_get1_RSA!");
254
255                 if (NULL != pKey) {
256                         EVP_PKEY_free(pKey);
257                 }
258
259                 return -1;
260         }
261
262         //3. Verify RSA Sign
263         iRet = RSA_verify(NID_sha1, hashValue, 20, sigData, sigLen, pRsa);
264
265         if (1 != iRet) {
266                 int err = 0;
267                 char tmpBuf[120] = { 0, };
268
269                 while ((err = ERR_get_error()) != 0)
270                         DRM_TAPPS_EXCEPTION("RSA_verify error(%s)", ERR_error_string(err, tmpBuf));
271
272                 if (NULL != pKey)
273                         EVP_PKEY_free(pKey);
274
275                 return -1;
276         }
277
278         if (NULL != pKey)
279                 EVP_PKEY_free(pKey);
280
281         return 0;
282 }
283
284 int AddCertUntrustedCerts(STACK_OF(X509)* untrustedCerts, unsigned char *cert,
285                                                   int certLen)
286 {
287         X509 *pstX509 = NULL;
288
289         if (untrustedCerts == NULL || cert == NULL || certLen < 1) {
290                 DRM_TAPPS_EXCEPTION("AddCertSTORE Error : Parameter error!");
291                 return -1;
292         }
293
294         pstX509 = d2i_X509(NULL, (const unsigned char **) &cert, certLen);
295
296         if (pstX509 == NULL) {
297                 DRM_TAPPS_EXCEPTION("AddCertSTORE Error : d2i_X509 error!");
298                 return -1;
299         }
300
301         sk_X509_push(untrustedCerts, pstX509);
302
303         return 0;
304 }
305
306 int AddCertSTOREFromFile(X509_STORE *pstStore, const char *filePath)
307 {
308         X509 *pstX509 = NULL;
309         FILE *file = NULL;
310         int ret = 0;
311
312         file = fopen(filePath, "r");
313
314         if (!file) {
315                 DRM_TAPPS_EXCEPTION("Parameter error! Fail to open a cert file.");
316                 ret = -1;
317                 goto error;
318         }
319
320         pstX509 = PEM_read_X509(file, NULL, NULL, NULL);
321
322         if (pstX509 == NULL) {
323                 DRM_TAPPS_EXCEPTION("d2i_X509 error!");
324                 ret = -1;
325                 goto error;
326         }
327
328         X509_STORE_add_cert(pstStore, pstX509);
329
330 error:
331
332         if (file != NULL)
333                 fclose(file);
334
335         return ret;
336 }
337
338 int AddCertSTOREFromDir(X509_STORE *pstStore, const char *dirPath)
339 {
340         int ret = 0;
341
342         DIR *dir = NULL;
343         struct dirent *result = nullptr;
344         char file_path_buff[512];
345
346         if (pstStore == NULL || dirPath == NULL) {
347                 DRM_TAPPS_EXCEPTION("Parameter error!");
348                 ret = -1;
349                 goto error;
350         }
351
352         dir = opendir(dirPath);
353
354         if (dir == NULL) {
355                 DRM_TAPPS_EXCEPTION("cannot open directory(%s)!", dirPath);
356                 ret = -1;
357                 goto error;
358         }
359
360         while (true) {
361                 errno = 0;
362                 result = readdir(dir);
363                 if (result == NULL) {
364                         if (errno != 0) {
365                                 DRM_TAPPS_EXCEPTION("fail to read entries from a directory(%s)!",
366                                                                         dirPath);
367                                 ret = -1;
368                                 goto error;
369                         } else {
370                                 // end of stream
371                                 break;
372                         }
373                 }
374
375                 if (result->d_type == DT_REG) {
376                         // regular file
377                         memset(file_path_buff, 0, sizeof(file_path_buff));
378                         snprintf(file_path_buff, sizeof(file_path_buff), "%s/%s", dirPath,
379                                          result->d_name);
380
381                         if (AddCertSTOREFromFile(pstStore, file_path_buff) == 0) {
382                                 DRM_TAPPS_LOG("Add root cert : file=%s", file_path_buff);
383                         } else {
384                                 DRM_TAPPS_LOG("Fail to add root cert : file=%s", file_path_buff);
385                         }
386                 }
387         }
388
389 error:
390
391         if (dir != NULL)
392                 closedir(dir);
393
394         return ret;
395 }
396
397 int TADC_IF_VerifyCertChain(unsigned char *rica, int ricaLen,
398                                                         unsigned char *cert, int certLen)
399 {
400         X509_STORE *pstStore = X509_STORE_new();
401
402         if (pstStore == NULL)
403                 return -1;
404
405         std::unique_ptr<X509_STORE, void(*)(X509_STORE *)>
406         _scoped_x509_store(pstStore, X509_STORE_free);
407
408         STACK_OF(X509) *untrustedCerts = sk_X509_new_null();
409
410         if (untrustedCerts == NULL)
411                 return -1;
412
413         std::unique_ptr<STACK_OF(X509), std::function<void(STACK_OF(X509) *)>>
414         _scoped_x509_stack(untrustedCerts, [](STACK_OF(X509) *s) {
415                 sk_X509_free(s);
416         });
417
418         //Add RICA Cert to certchain
419         if (AddCertUntrustedCerts(untrustedCerts, rica, ricaLen) != 0) {
420                 DRM_TAPPS_EXCEPTION("Add RICA Cert to certchain!");
421                 return -1;
422         }
423
424         //Add Root CA Cert
425         if (AddCertSTOREFromDir(pstStore, RO_ISSUER_ROOT_CERTS_DIR) != 0) {
426                 DRM_TAPPS_EXCEPTION("Add Root CA Cert!");
427                 return -1;
428         }
429
430         //Get Cert
431         X509 *pstX509 = d2i_X509(NULL, (const unsigned char **)&cert, certLen);
432
433         if (pstX509 == NULL) {
434                 DRM_TAPPS_EXCEPTION("Get Cert d2i_X509 error!");
435                 return -1;
436         }
437
438         X509_STORE_set_flags(pstStore, X509_V_FLAG_CB_ISSUER_CHECK);
439         X509_STORE_CTX *pstStoreCtx = X509_STORE_CTX_new();
440
441         if (pstStoreCtx == NULL) {
442                 DRM_TAPPS_EXCEPTION("509_STORE_CTX_new error!");
443                 return -1;
444         }
445
446         std::unique_ptr<X509_STORE_CTX, void(*)(X509_STORE_CTX *)>
447         _scoped_x509_store_ctx(pstStoreCtx, X509_STORE_CTX_free);
448
449         //init
450         if(!X509_STORE_CTX_init(pstStoreCtx, pstStore, pstX509, untrustedCerts)) {
451                 DRM_TAPPS_EXCEPTION("509_STORE_CTX_init error!");
452                 return -1;
453     }
454
455         //Set Flag
456         X509_STORE_CTX_set_flags(pstStoreCtx, X509_V_FLAG_CB_ISSUER_CHECK);
457
458         //verify
459         switch (X509_verify_cert(pstStoreCtx)) {
460         case 1:
461                 DRM_TAPPS_LOG("TADC_IF_VerifyCertChain Success!");
462                 return 0;
463
464         case 0:
465                 DRM_TAPPS_EXCEPTION("TADC_IF_VerifyCertChain Failed: %s",
466                                                         X509_verify_cert_error_string(
467                                                                 X509_STORE_CTX_get_error(pstStoreCtx)));
468                 return -1;
469
470         default:
471                 DRM_TAPPS_EXCEPTION("TADC_IF_VerifyCertChain Error: X509_verify_cert error!");
472                 return -1;
473         }
474 }
475
476 size_t TADC_IF_StrLen(const char *string)
477 {
478         return strlen(string);
479 }
480
481 int TADC_IF_StrCmp(const char *string1, const char *string2)
482 {
483         return strcmp(string1, string2);
484 }
485
486 int TADC_IF_StrNCmp(const char *string1, const char *string2, size_t count)
487 {
488         return strncmp(string1, string2, count);
489 }
490
491 char *TADC_IF_StrNCpy(char *strDestination, const char *strSource, size_t count)
492 {
493         return strncpy(strDestination, strSource, count);
494 }
495
496 unsigned long TADC_IF_StrtOul(const char *nptr, char **endptr, int base)
497 {
498         return strtoul(nptr, endptr, base);
499 }
500
501 int TADC_IF_MemCmp(const void *buf1, const void *buf2, size_t count)
502 {
503         return memcmp(buf1, buf2, count);
504 }
505
506 void TADC_IF_MemCpy(void *dest, const void *src, size_t count)
507 {
508         memcpy(dest, src, count);
509 }
510
511 void TADC_IF_MemSet(void *dest, int c, size_t count)
512 {
513         memset(dest, c, count);
514 }
515
516 void *TADC_IF_Malloc(size_t size)
517 {
518         return malloc(size);
519 }
520
521 void TADC_IF_Free(void *memblock)
522 {
523         if (memblock != NULL)
524                 free(memblock);
525 }
526
527 int TADC_IF_AtoI(char *str)
528 {
529         return atoi(str);
530 }