9df23751bd2213a4b970cb189bb27f08e3167a88
[platform/framework/native/appfw.git] / src / security / cert / FSecCert_CertDbManager.cpp
1 //
2 // Open Service Platform
3 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
4 //
5 // Licensed under the Apache License, Version 2.0 (the License);
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 //     http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17
18 /**
19  * @file                FSecCert_CertDbManager.cpp
20  * @brief               This file contains implementation of X509 Certificate Db Manager APIs.
21 */
22
23 #include <stdio.h>
24 #include <string.h>
25 #include <stdlib.h>
26 #include <error.h>
27 #include <new>
28 #include <sys/stat.h>
29 #include <assert.h>
30 #include <dirent.h>
31 #include <openssl/evp.h>
32 #include <openssl/pem.h>
33 #include <unique_ptr.h>
34 #include <pthread.h>
35 #include <FIoFile.h>
36 #include <FBaseSysLog.h>
37 #include <FBaseByteBuffer.h>
38 #include <FBaseResult.h>
39 #include <FBase_StringConverter.h>
40 #include "FSecCert_CertDbStore.h"
41 #include "FSecCert_CertFileStore.h"
42 #include "FSecCert_CertDbManager.h"
43 #include "FSecCert_Base64.h"
44 #include "FSecCert_CertService.h"
45 #include "FSecCert_CertManager.h"
46
47 using namespace Tizen::Base;
48 using namespace Tizen::Io;
49
50 namespace Tizen { namespace Security { namespace Cert
51 {
52 _CertDbManager* _CertDbManager::__pCertDb = null;
53
54 _CertDbManager::_CertDbManager(void)
55 {
56 }
57
58 _CertDbManager::~_CertDbManager(void)
59 {
60 }
61
62 void
63 _CertDbManager::Construct(void)
64 {
65         static _CertDbManager certDb;
66         __pCertDb = &certDb;
67 }
68
69
70 _CertDbManager*
71 _CertDbManager::GetInstance(void)
72 {
73         static pthread_once_t once_block = PTHREAD_ONCE_INIT;
74         if (__pCertDb == null)
75         {
76                 pthread_once(&once_block, Construct);
77         }
78
79         return __pCertDb;
80 }
81
82 result
83 _CertDbManager::CreateCertificateTables(void)
84 {
85         result r = E_SUCCESS;
86
87         r = __caCertDbStore.CreateCertificateTables();
88         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM,  "Failed to create certificate tables in database.");
89
90         return E_SUCCESS;
91 }
92
93 bool
94 _CertDbManager::IsCertificateTablesCreated(void)
95 {
96         result r = E_SUCCESS;
97
98         r = __caCertDbStore.IsRootCaCertTableCreated();
99         if( r != E_SUCCESS )
100         {
101                 SetLastResult(E_SYSTEM);
102                 return false;
103         }
104
105         r = __userCertDbStore.IsUserCertTableCreated();
106         if( r != E_SUCCESS )
107         {
108                 SetLastResult(E_SYSTEM);
109                 return false;
110         }
111
112         return true;
113 }
114
115 result
116 _CertDbManager::ResetCertificateTables(void)
117 {
118         result r = E_SUCCESS;
119
120         r = __caCertDbStore.DropCertificateTables();
121         SysTryReturn(NID_SEC_CERT, !IsFailed(r), false, E_SYSTEM, "[E_SYSTEM] Failed to drop certificate tables in database.");
122
123         r = __caCertDbStore.CreateCertificateTables();
124         SysTryReturn(NID_SEC_CERT, !IsFailed(r), false, E_SYSTEM, "[E_SYSTEM] Failed to create certificate tables in database.");
125
126         return E_SUCCESS;
127 }
128
129 result
130 _CertDbManager::RemoveCertificateTables(void)
131 {
132         result r = E_SUCCESS;
133         r = __caCertDbStore.DropCertificateTables();
134         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM,  "Failed to delete all the certificate tables in database.");
135         return E_SUCCESS;
136 }
137
138 result
139 _CertDbManager::RemoveCaCertificateByType(_CaCertType certType)
140 {
141         result r = E_SUCCESS;
142         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
143         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
144
145         sprintf(condition, "certType = %d and installed = '%s'", certType, installed);
146
147         r = __caCertDbStore.RemoveAllCertificateByCondition(reinterpret_cast< byte* >(condition));
148         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to delete all the certificate tables in database.");
149
150         return E_SUCCESS;
151 }
152
153 result
154 _CertDbManager::RemoveUserCaCertificateByCertId(int certId)
155 {
156         result r = E_SUCCESS;
157         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
158         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
159
160         sprintf(condition, "certId = %d and certType = %d and installed = '%s'", certId, _CERT_TYPE_ROOT_CA_BY_USER, installed);
161         r = __caCertDbStore.RemoveAllCertificateByCondition(reinterpret_cast< byte* >(condition));
162         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to delete all the certificate tables in database.");
163
164         return E_SUCCESS;
165 }
166
167 result
168 _CertDbManager::InsertDefaultCaCertificateFromBuffer(_CaCertType certType, _CertFormat certFormat, byte* pCertBuf, int certLen)
169 {
170         return InsertCaCertificateFromBuffer(certType, certFormat, pCertBuf, certLen, false);
171 }
172
173 result
174 _CertDbManager::InsertCaCertificateFromBuffer(_CaCertType certType, _CertFormat certFormat, byte* pCertBuf, int certLen, bool checkValidity)
175 {
176         result r = E_SUCCESS;
177         String tempFileName;
178         CaCertRecord certRecord = {0, };
179         _CertFileStore fileStore;
180         _CertFormat certBufFormat = _CERT_UNKNOWN;
181         _CertEncodingType encodingType = _CERT_ENC_TYPE_UNKNOWN;
182         int lenSubjectName = 0;
183         int lenIssuerName = 0;
184         int lenSerialNo = 0;
185         int certId = 0;
186         int derCertBufferLength = 0;
187         char serialName[_MAX_SERIAL_NUMBER_SIZE] = {0, };
188         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
189         char subjectName[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
190         char issuerName[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
191         byte* pDerCert = null;
192         byte* pSerial = null;
193         _X509TbsCert* pTbsCert = null;
194
195         r = __caCertDbStore.IsRootCaCertTableCreated();
196         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Root certificate tables are not created in database.");
197
198         std::unique_ptr <_X509Certificate> pCert (new (std::nothrow) _X509Certificate());
199         SysTryReturnResult(NID_SEC_CERT, pCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
200
201         certBufFormat = _CertManager::GetEncodedCertBuffer(pCertBuf, certLen, &pDerCert, &derCertBufferLength, &encodingType);
202         std::unique_ptr <byte[]> pDerCertBuffer(pDerCert);
203         pDerCert = null;
204         SysTryReturnResult(NID_SEC_CERT, pDerCertBuffer != null, E_INVALID_CONDITION, "Input certificate buffer.");
205         SysTryReturnResult(NID_SEC_CERT, certBufFormat == _CERT_X509, E_INVALID_CONDITION, "Unsupported certificate format.");
206         SysTryReturnResult(NID_SEC_CERT, derCertBufferLength > 0, E_INVALID_CONDITION, "Invalid certificate length.");
207
208         r = pCert->Parse(pDerCertBuffer.get(), derCertBufferLength);
209         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_DECODING_FAILED, "Decoding failed.");
210
211         pTbsCert = pCert->GetTbsCertInstance();
212         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null,E_SYSTEM, "Failed to get certificate to be signed instance.");
213
214         lenSubjectName = strlen(reinterpret_cast< const char* >(pTbsCert->GetSubjectName()));
215         lenIssuerName = strlen(reinterpret_cast< const char* >(pTbsCert->GetIssuerName()));
216
217         SysTryReturnResult(NID_SEC_CERT, lenSubjectName < _MAX_ISSUER_SUBJECT_NAME_SIZE,E_SYSTEM, "Subject name is more then maximum specified length.");
218         SysTryReturnResult(NID_SEC_CERT, lenIssuerName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_SYSTEM, "Subject name is more then maximum specified length.");
219
220         strcpy(subjectName, reinterpret_cast< const char* >(pTbsCert->GetSubjectName()));
221         strcpy(issuerName, reinterpret_cast< const char* >(pTbsCert->GetIssuerName()));
222
223         pTbsCert->GetSerialNumber(pSerial, reinterpret_cast< int& >(lenSerialNo));
224         if ((lenSerialNo <= 0) || (lenSerialNo > _MAX_SERIAL_NUMBER_SIZE))
225         {
226                 memset(pSerial, 0, _MAX_SERIAL_NUMBER_SIZE);
227                 lenSerialNo = 1;
228         }
229         else
230         {
231                 memcpy(serialName, pSerial, lenSerialNo);
232         }
233
234         if (checkValidity)
235         {
236                 if (pCert->IsSelfSigned())
237                 {
238                         r = pCert->VerifySignature(null, 0);
239                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INVALID_CONTENT, "Invalid data.");
240                 }
241 #ifdef _CERT_VERIFY_AND_INSTALL_CERTIFICATE
242                 //Open this code - if u want to support installation of Intermediate CA Certificate with verification using this API.(ideally it should check if installing intermediate CA) (09082011)
243                 else if (pCert->IsCaCertificate())
244                 {
245                         std::unique_ptr <_CertChain> pCertChain (new (std::nothrow) _CertChain());
246                         SysTryReturnResult(NID_SEC_CERT, pCertChain != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
247
248                         r = pCertChain->AddCertificate(certFormat, pDerCertBuffer.get(), derCertBufferLength);
249                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INVALID_CONTENT, "AddCertificate failed.");
250
251                         r = pCertChain->MoveHead();
252                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INVALID_CONTENT, "MoveHead failed.");
253
254
255                         // It support only RSA, For ECC Certificate if you want to omit this, block this call or check as per algo id
256                         //(there are ECC certificate installation which we support for china model. hence these comments)
257                         r = pCertChain->VerifyCertChainWithDb();
258                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to verify certificate chain.");
259                 }
260 #endif
261
262 #ifdef _CERT_INSTALL_ONLY_CA_CERTIFICATE
263                 //Open this code - if u want to support only CA Certificate installation using this API.(ideally it should check)
264                 else
265                 {
266                         return E_UNSUPPORTED_OPERATION;
267                 }
268 #endif
269
270         }
271
272         r = __caCertDbStore.CheckDuplicateCertificate(certType, reinterpret_cast< byte* >(subjectName), lenSubjectName);
273         if(r == E_SUCCESS)
274         {
275                 return E_FILE_ALREADY_EXIST;
276         }
277         //Get the last installed certificate id from db table
278         __caCertDbStore.GetCurrentCertId(certId);
279         //Calculate the new (std::nothrow) certificate id for installation
280         certId = certId + 1;
281         fileStore.GetFileNameFromHandle(certId, _CERT_PATH_CA_CERT, tempFileName);
282
283         memset(&certRecord, 0, sizeof(certRecord));
284         certRecord.certType = static_cast< int >(certType);
285         certRecord.certFormat = static_cast< int >(certFormat);
286
287         std::unique_ptr <char[]> pFileName(Tizen::Base::_StringConverter::CopyToCharArrayN(tempFileName));
288         SysTryReturnResult(NID_SEC_CERT, pFileName != null, E_SYSTEM, "Failed to get file attributes.");
289
290         strcpy(certRecord.fileName, pFileName.get());
291
292         certRecord.subjectNameLen = lenSubjectName;
293         memcpy(certRecord.subjectName, subjectName, lenSubjectName);
294         certRecord.issuerNameLen = lenIssuerName;
295         memcpy(certRecord.issuerName, issuerName, lenIssuerName);
296         certRecord.parentCa = certId;
297         strcpy(certRecord.installed, installed);
298         memcpy(certRecord.serialNo, serialName, lenSerialNo);
299         certRecord.serialNoLen = lenSerialNo;
300
301         r = __caCertDbStore.InsertCaCertificate(&certRecord);
302         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Certificate record insertion failed.", GetErrorMessage(r));
303
304         fileStore.SetFilePath(tempFileName);
305
306         r = fileStore.WriteToFile(pDerCertBuffer.get(), derCertBufferLength);
307         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INACCESSIBLE_PATH, "Path inaccessible.");
308
309         return r;
310
311 }
312
313 result
314 _CertDbManager::UpdateCaCertificateFromBuffer(_CaCertType certType, _CertFormat certFormat, byte* pCurCertBuf, int curCertLen, byte* pNewCertBuf, int newCertLen)
315 {
316         result r = E_SUCCESS;
317         String tempFileName;
318         CaCertRecord certRecord = {0, };
319         CaCertRecord certRecord1 = {0, };
320         _CertFileStore fileStore;
321         _X509TbsCert* pTbsCert = null;
322         _X509TbsCert* pNewTbsCert = null;
323         int lenSubjectName = 0;
324         int lenNewSubjectName = 0;
325         int lenIssuerName = 0;
326         int lenNewIssuerName = 0;
327         int lenNewSerialNo = 0;
328         int certId = 0;
329         int subjNameB64len = 0;
330         char subjectNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
331         char newSubjectName[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
332         char newIssuerName[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
333         char newSerialName[_MAX_SERIAL_NUMBER_SIZE] = {0, };
334         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
335         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE] = {0, };
336         byte* pNewSerial = null;
337
338         r = __caCertDbStore.IsRootCaCertTableCreated();
339         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Root certificate tables are not created in database.");
340
341         std::unique_ptr<_X509Certificate> pCert (new (std::nothrow) _X509Certificate());
342         SysTryReturnResult(NID_SEC_CERT, pCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
343
344         r = pCert->Parse(pCurCertBuf, curCertLen);
345         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_DECODING_FAILED, "Parse failed.");
346
347         pTbsCert = pCert->GetTbsCertInstance();
348         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
349
350         lenSubjectName = strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName()));
351         lenIssuerName = strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName()));
352
353         SysTryReturnResult(NID_SEC_CERT, lenSubjectName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_SYSTEM, "Subject name exceeds allowable length.");
354         SysTryReturnResult(NID_SEC_CERT, lenIssuerName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_SYSTEM, "Subject name exceeds allowable length.");
355
356         r = __caCertDbStore.CheckDuplicateCertificate(certType, pTbsCert->GetSubjectName(), lenSubjectName);
357         if (!IsFailed(r)) //checkit
358         {
359                 subjNameB64len = _Base64::GetEncodedSize(lenSubjectName);
360                 SysTryReturnResult(NID_SEC_CERT, subjNameB64len >= 0, E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
361
362                 memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
363
364                 r = _Base64::Encode(pTbsCert->GetSubjectName(), lenSubjectName, subjectNameBase64, subjNameB64len);
365                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
366
367                 sprintf(condition, "subjectName = '%s' and certType = %d and installed = '%s'", subjectNameBase64, certType, installed);
368                 r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
369                 SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
370
371                 certId = certRecord.parentCa;
372
373                 fileStore.GetFileNameFromHandle(certId, _CERT_PATH_CA_CERT, tempFileName);
374                 fileStore.SetFilePath(tempFileName);
375
376                 if (certFormat == _CERT_X509)
377                 {
378                         std::unique_ptr <_X509Certificate> pNewCert(new (std::nothrow) _X509Certificate());
379                         SysTryReturnResult(NID_SEC_CERT, pNewCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
380
381                         r = pNewCert->Parse(pNewCertBuf, newCertLen);
382                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_DECODING_FAILED, "Decoding failed.");
383
384                         pNewTbsCert = pNewCert->GetTbsCertInstance();
385                         SysTryReturnResult(NID_SEC_CERT, pNewTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
386
387                         strcpy(newSubjectName, reinterpret_cast< const char* >(pNewTbsCert->GetSubjectName()));
388                         strcpy(newIssuerName, reinterpret_cast< const char* >((pNewTbsCert->GetIssuerName())));
389
390                         lenNewSubjectName = strlen(newSubjectName);
391                         lenNewIssuerName = strlen(newIssuerName);
392
393                         pNewTbsCert->GetSerialNumber(pNewSerial, reinterpret_cast< int& >(lenNewSerialNo));
394                         if ((lenNewSerialNo <= 0) || (lenNewSerialNo > _MAX_SERIAL_NUMBER_SIZE))
395                         {
396                                 memset(pNewSerial, 0, _MAX_SERIAL_NUMBER_SIZE);
397                                 lenNewSerialNo = 1;
398
399                         }
400                         else
401                         {
402                                 memcpy(newSerialName, pNewSerial, lenNewSerialNo);
403                         }
404
405                         SysTryReturnResult(NID_SEC_CERT, lenNewSubjectName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_SYSTEM, "Subject name length exceeds specified length.");
406                         SysTryReturnResult(NID_SEC_CERT, lenNewIssuerName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_SYSTEM, "Subject name length exceeds specified length.");
407                 }
408                 certRecord1.certType = static_cast< int >(certType);
409                 certRecord1.certFormat = static_cast< int >(certFormat);
410
411                 std::unique_ptr <char[]> pFileName(Tizen::Base::_StringConverter::CopyToCharArrayN(tempFileName));
412                 SysTryReturnResult(NID_SEC_CERT, pFileName != null, E_OPERATION_FAILED, "Failed to get file name.");
413
414                 strcpy(certRecord1.fileName, pFileName.get());
415
416                 certRecord1.subjectNameLen = lenNewSubjectName;
417                 memcpy(certRecord1.subjectName, newSubjectName, lenNewSubjectName);
418                 certRecord1.issuerNameLen = lenIssuerName;
419                 memcpy(certRecord1.issuerName, newIssuerName, lenNewIssuerName);
420                 certRecord1.parentCa = certId;
421                 strcpy(certRecord1.installed, certRecord.installed);
422                 memcpy(certRecord1.serialNo, newSerialName, lenNewSerialNo);
423                 certRecord1.serialNoLen = lenNewSerialNo;
424
425                 r = __caCertDbStore.UpdateCaCertificate(&certRecord, &certRecord1);
426                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OPERATION_FAILED, "Failed to update ca certificate.");
427
428                 fileStore.DeleteFile();
429
430                 r = fileStore.WriteToFile(pNewCertBuf, newCertLen);
431                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INACCESSIBLE_PATH, "Path does not exist.");
432                 //No need to update record as only file data changed.
433                 return E_SUCCESS;
434         }
435         else
436         {
437                 return E_FILE_ALREADY_EXIST;
438         }
439
440         return r;
441 }
442
443 result
444 _CertDbManager::RemoveCaCertificateFromBuffer(_CaCertType certType, _CertFormat certFormat, byte* pCertBuf, int certLen)
445 {
446         result r = E_SUCCESS;
447         _X509TbsCert* pTbsCert = null;
448         String fileName;
449         _CertFileStore fileStore;
450         int certId = 0;
451
452         //Check certType missing
453
454         r = __caCertDbStore.IsRootCaCertTableCreated();
455         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OBJ_NOT_FOUND, "No root certificate tables are create in databased.");
456
457         std::unique_ptr <_X509Certificate> pCert (new (std::nothrow) _X509Certificate());
458         SysTryReturnResult(NID_SEC_CERT, pCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
459
460         r = pCert->Parse(pCertBuf, certLen);
461         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Parsing failed.");
462
463         pTbsCert = pCert->GetTbsCertInstance();
464         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
465
466         r = __caCertDbStore.CheckDuplicateCertificate(certType, pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())));
467         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OBJ_NOT_FOUND, "Certificate not found in db.");
468
469         r = GetCaCertificateId(pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())),
470                                                   pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
471                                                   certId, certType);
472         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get ca certificate id.", GetErrorMessage(r));
473
474
475         r = __caCertDbStore.RemoveCertificateById(certId);
476         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to delete certificate with certificate id (%d).", certId);
477
478         //Delete File
479         fileStore.GetFileNameFromHandle(certId, _CERT_PATH_CA_CERT, fileName);
480         Tizen::Io::File::Remove(fileName);
481
482         return r;
483 }
484
485
486 result
487 _CertDbManager::RemoveCertificateChainByCertId(int certId)
488 {
489         result r = E_SUCCESS;
490         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE] = {0, };
491         UserCertRecord userCertRecord = {0, };
492
493         memset(&userCertRecord, 0, sizeof(userCertRecord));
494         memset(condition, 0, _MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE);
495
496         sprintf(condition, "certId = %d", certId);
497         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &userCertRecord);
498         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r) || r == E_DATA_NOT_FOUND, E_SYSTEM, "Failed to get certificate record.");
499         SysTryReturnResult(NID_SEC_CERT, r != E_DATA_NOT_FOUND, E_SUCCESS, "No such record found.");
500
501         r = DeleteCertificateChain(userCertRecord.certId, userCertRecord.parentCa);
502         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "File deletion failed for certificate Id (%d).", certId);
503
504         return r;
505 }
506
507
508 result
509 _CertDbManager::GetCaCertificateId(byte* pSubjectName, int subjectNameSize, byte* pIssuerName, int issuerNameSize, int& certId, _CaCertType certType)
510 {
511         result r = E_SUCCESS;
512         int subjNameB64len = 0;
513         int issuerB64len = 0;
514         char subjectNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
515         char issuerNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
516         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE] = {0, };
517         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
518         CaCertRecord caCertRecord = {0, };
519
520         SysTryReturnResult(NID_SEC_CERT, pSubjectName != null, E_INVALID_ARG, "Invalid subject name.");
521         SysTryReturnResult(NID_SEC_CERT, subjectNameSize > 0, E_INVALID_ARG, "Invalid subject name length.");
522
523         subjNameB64len = _Base64::GetEncodedSize(subjectNameSize);
524         memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
525
526         r = _Base64::Encode(pSubjectName, subjectNameSize, subjectNameBase64, subjNameB64len);
527         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
528
529         memset(condition, 0, sizeof(condition));
530
531         if (pIssuerName != null && issuerNameSize > 0)
532         {
533                 issuerB64len = _Base64::GetEncodedSize(issuerNameSize);
534                 memset(issuerNameBase64, 0, sizeof(issuerNameBase64));
535
536                 r = _Base64::Encode(pIssuerName, issuerNameSize, issuerNameBase64, issuerB64len);
537                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
538
539                 if (certType == _CERT_TYPE_NOT_BOUNDED)
540                 {
541                         sprintf(condition, "subjectName = '%s' and issuerName = '%s' and installed = '%s'", subjectNameBase64, issuerNameBase64, installed);
542                 }
543                 else
544                 {
545                         sprintf(condition, "subjectName = '%s' and issuerName = '%s' and certType = %d and installed = '%s'", subjectNameBase64, issuerNameBase64, certType, installed);
546                 }
547         }
548         else
549         {
550                 if (certType == _CERT_TYPE_NOT_BOUNDED)
551                 {
552                         sprintf(condition, "subjectName = '%s' and installed = '%s'", subjectNameBase64, installed);
553                 }
554                 else
555                 {
556                         sprintf(condition, "subjectName = '%s' and certType = %d and installed = '%s'", subjectNameBase64, certType, installed);
557                 }
558         }
559
560         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &caCertRecord);
561         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
562
563         certId = caCertRecord.certId;
564
565         return E_SUCCESS;
566 }
567
568 result
569 _CertDbManager::GetUserCertificateId(byte* pSubjectName, int subjectNameSize, byte* pIssuerName, int issuerNameSize, int& certId)
570 {
571         result r = E_SUCCESS;
572         int subjNameB64len = 0;
573         int issuerB64len = 0;
574         char subjectNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
575         char issuerNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
576         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
577         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
578         UserCertRecord userCertRecord = {0, };
579
580         SysTryReturnResult(NID_SEC_CERT, pSubjectName != null, E_INVALID_ARG, "Invalid subject name.");
581         SysTryReturnResult(NID_SEC_CERT, subjectNameSize > 0, E_INVALID_ARG, "Invalid subject name length.");
582
583         subjNameB64len = _Base64::GetEncodedSize(subjectNameSize);
584         memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
585
586         r = _Base64::Encode(reinterpret_cast< byte* >(pSubjectName), subjectNameSize, subjectNameBase64, subjNameB64len);
587         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
588
589         memset(condition, 0, sizeof(condition));
590
591         if (pIssuerName != null && issuerNameSize > 0)
592         {
593                 issuerB64len = _Base64::GetEncodedSize(issuerNameSize);
594                 memset(issuerNameBase64, 0, sizeof(issuerNameBase64));
595
596                 r = _Base64::Encode(reinterpret_cast< byte* >(pIssuerName), issuerNameSize, issuerNameBase64, issuerB64len);
597                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
598
599                 sprintf(condition, "subjectName = '%s' and issuerName = '%s' and installed = '%s'", subjectNameBase64, issuerNameBase64, installed);
600         }
601         else
602         {
603                 sprintf(condition, "subjectName = '%s' and installed = '%s'", subjectNameBase64, installed);
604         }
605
606         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &userCertRecord);
607         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate record.", GetErrorMessage(r));
608
609         certId = userCertRecord.certId;
610
611         return E_SUCCESS;
612 }
613
614 result
615 _CertDbManager::RemoveAllUserCertificate(void)
616 {
617         __userCertDbStore.DeleteUserCertFiles();
618
619         return E_SUCCESS;
620 }
621
622 result
623 _CertDbManager::DeleteCertificateChain(int devCertId, int devParentCA)
624 {
625         result r = E_SUCCESS;
626         CaCertRecord certRecord = {0, };
627         int recCount = 0;
628         int caCertId = 0;
629         int caParentCa = 0;
630         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
631         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE] = {0, };
632         bool devCert = true;
633
634         SysTryReturnResult(NID_SEC_CERT, devCertId > 0, E_INVALID_ARG, "Invalid input argument.");
635         SysTryReturnResult(NID_SEC_CERT, devParentCA > 0, E_INVALID_ARG, "Invalid input argument.");
636
637         memset(condition, 0, _MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE);
638
639         sprintf(condition, "parentCa = %d and installed = '%s'", devParentCA, installed);
640         //Check if any other device certificate has same parent as of referred device certificare. If it is yes then we
641         //delete only device certificate and return. We cannot disturb another chain.
642         __userCertDbStore.GetCountByCondition(reinterpret_cast< byte* >(&condition), recCount);
643         //More than one device certificate found which is referring same intermidiate CA or ROOT CA. So just delete device certificate and return.
644         if (recCount > 1)
645         {
646                 r = DeleteCertificateByIdNTableName(devCertId, _CERT_USER_CERT_TABLE);
647                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OPERATION_FAILED, "Failed to delete certificate.");
648
649                 return E_SUCCESS;
650         }
651         //Now there is not two device certificate with same intermidiate CA,
652         //so go ahead to intermidiate CA and delete device certificate.
653         caParentCa = devParentCA;
654         caCertId = devCertId;
655         do
656         {
657                 if (__caCertDbStore.CheckIfSameParent(caParentCa) == E_SUCCESS)
658                 {
659                         if (devCert)
660                         {
661                                 r = DeleteCertificateByIdNTableName(caCertId, _CERT_USER_CERT_TABLE);
662                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OPERATION_FAILED, "Failed to delete certificate.");
663
664                                 devCert = false; //Device certificate is deleted here now go to CA certificate for deletion
665                                 SysLog(NID_SEC_CERT, "Device certificate is deleted here now go to CA certificate for deletion.");
666                                 break; // break here next certificate has dependency
667                         }
668                         else
669                         {
670                                 r = DeleteCertificateByIdNTableName(caCertId, _CERT_ROOT_CA_CERT_TABLE);
671                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OPERATION_FAILED, "Failed to delete certificate.");
672
673                                 break; // break here next certificate has dependency
674                         }
675                 }
676                 else // The caCertId's parent is no more parent of any other certificate so delete caCertId from Db.
677                 {
678                         if (devCert) //If it is device certificate
679                         {
680                                 r = DeleteCertificateByIdNTableName(caCertId, _CERT_USER_CERT_TABLE);
681                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_OPERATION_FAILED, "Failed to delete certificate table.");
682
683                                 devCert = false; //Device certificate is deleted here now go to CA certificate for deletion
684                                 SysLog(NID_SEC_CERT, "Device certificate is deleted here now go to CA certificate for deletion.");
685                         }
686                         else //If it is CA certificate and there is no dependency
687                         {
688                                 r = DeleteCertificateByIdNTableName(caCertId, _CERT_ROOT_CA_CERT_TABLE);
689                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to delete certificate table.");
690
691                                 SysLog(NID_SEC_CERT, "It is CA certificate and there is no dependency.");
692                         }
693                         caCertId = caParentCa; // Now look for next certificate in chain
694                         memset(condition, 0, _MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE);
695                         sprintf(condition, "certId = %d and installed = '%s'", devParentCA, installed);
696                         memset(&certRecord, 0, sizeof(certRecord));
697                         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
698                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r) || r == E_DATA_NOT_FOUND, E_SYSTEM, "Failed to get certificate record.");
699                         SysTryReturnResult(NID_SEC_CERT, r != E_DATA_NOT_FOUND, E_SUCCESS, "No such record found.");
700
701                         caParentCa = certRecord.parentCa;
702                 }
703         }
704         while (caCertId != caParentCa);
705
706         return E_SUCCESS;
707 }
708
709 result
710 _CertDbManager::GetCertificateListByFormat(_CertFormat certFormat, _CertificateListInfo** ppCertList, int& count)
711 {
712         result r = E_SUCCESS;
713         CaCertRecord certRecord = {0, };
714         _CertificateListInfo* pHoldList = null;
715         _CertFileStore fileStore;
716         int certCount = 0;
717         int certLength = 0;
718         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
719         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
720
721         sprintf(condition, "certFormat = %d and certType != %d and installed = '%s'", certFormat, _CERT_TYPE_INTERMIDIATE_CA, installed);
722
723         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
724         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r) || r == E_DATA_NOT_FOUND, E_SYSTEM, "Failed to get certificate record.");
725         SysTryReturnResult(NID_SEC_CERT, r != E_DATA_NOT_FOUND, E_SUCCESS, "No such record found.");
726
727         std::unique_ptr <_CertificateListInfo> pCertList (new (std::nothrow) _CertificateListInfo);
728         SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
729
730         memset(pCertList.get(), 0, sizeof(*pCertList.get()));
731         pCertList->pNext = null;
732         r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_CA_CERT);
733         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
734
735         r = fileStore.ReadFromFile(pCertList->certificate, certLength);
736         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
737
738         pCertList->length = certLength;
739         pCertList->certFileId = certRecord.certId;
740         pCertList->format = static_cast< _CertFormat >(certRecord.certFormat);
741         pCertList->certType = static_cast< _CaCertType >(certRecord.certType);
742         certCount++;
743
744         pHoldList = pCertList.release();
745         *ppCertList = pHoldList;
746
747         while (__caCertDbStore.GetNextRecordByCondition(reinterpret_cast< byte* >(condition), &certRecord, certRecord.certId) == E_SUCCESS)
748         {
749                 std::unique_ptr <_CertificateListInfo> pCertList (new (std::nothrow) _CertificateListInfo);
750                 SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
751
752                 memset(pCertList.get(), 0, sizeof(*pCertList.get()));
753
754                 r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_CA_CERT);
755                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
756
757                 r = fileStore.ReadFromFile(pCertList->certificate, certLength);
758                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
759
760                 pCertList->pNext = null;
761                 pCertList->length = certLength;
762                 pCertList->certFileId = certRecord.certId;
763                 pCertList->format = (_CertFormat) certRecord.certFormat;
764                 pCertList->certType = static_cast< _CaCertType >(certRecord.certType);
765
766                 pHoldList->pNext = pCertList.release();
767                 pHoldList = pHoldList->pNext;
768
769                 certCount++;
770         }
771
772         count = certCount;
773
774
775         return r;
776 }
777
778 result
779 _CertDbManager::GetUserCertificateListByFormat(_CertFormat certFormat, _CertificateListInfo** ppCertList, int& count)
780 {
781         result r = E_SUCCESS;
782         UserCertRecord certRecord = {0, };
783         _CertificateListInfo* pHoldList = null;
784         _CertFileStore fileStore;
785         int certCount = 0;
786         int certLength = 0;
787         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
788         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
789
790         *ppCertList = null;
791
792         sprintf(condition, "certFormat = %d and installed = '%s'", certFormat, installed);
793
794         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
795         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r) || r == E_DATA_NOT_FOUND, E_SYSTEM, "Failed to get certificate record.");
796         SysTryReturnResult(NID_SEC_CERT, r != E_DATA_NOT_FOUND, E_SUCCESS, "No such record found.");
797
798         std::unique_ptr<_CertificateListInfo> pCertList (new (std::nothrow) _CertificateListInfo);
799         SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
800
801         memset(pCertList.get(), 0, sizeof(*pCertList.get()));
802         pCertList->pNext = null;
803
804         r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_USER_CERT);
805         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
806
807         r = fileStore.ReadFromFile(pCertList->certificate, certLength);
808         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
809
810         pCertList->length = certLength;
811         pCertList->certFileId = certRecord.certId;
812         pCertList->format = static_cast< _CertFormat >(certRecord.certFormat);
813         pCertList->certType = _CERT_TYPE_USER_CERT;
814         certCount++;
815
816         pHoldList = pCertList.release();
817         *ppCertList = pHoldList;
818
819         while (__userCertDbStore.GetNextRecordByCondition(reinterpret_cast< byte* >(condition), &certRecord, certRecord.certId) == E_SUCCESS)
820         {
821                 std::unique_ptr<_CertificateListInfo> pCertList (new (std::nothrow) _CertificateListInfo);
822                 SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
823
824                 memset(pCertList.get(), 0, sizeof(*pCertList.get()));
825
826                 r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_USER_CERT);
827                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
828
829                 r = fileStore.ReadFromFile(pCertList->certificate, certLength);
830                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
831
832                 pCertList->pNext = null;
833                 pCertList->length = certLength;
834                 pCertList->certFileId = certRecord.certId;
835                 pCertList->format = static_cast< _CertFormat >(certRecord.certFormat);
836                 pCertList->certType = _CERT_TYPE_USER_CERT;
837
838                 pHoldList->pNext = pCertList.release();
839                 pHoldList = pHoldList->pNext;
840
841                 certCount++;
842         }
843
844         count = certCount;
845
846         return E_SUCCESS;
847 }
848
849 result
850 _CertDbManager::GetCaCertificateListByCertId(int certId, _CertificateListInfo** ppCertList)
851 {
852         result r = E_SUCCESS;
853         CaCertRecord certRecord = {0, };
854         _CertFileStore fileStore;
855         int certLength = 0;
856         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
857         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
858
859         *ppCertList = null;
860         sprintf(condition, "certId = %d and certType != %d and installed = '%s'", certId, _CERT_TYPE_INTERMIDIATE_CA, installed);
861
862         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
863         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate record.", GetErrorMessage(r));
864
865         std::unique_ptr <_CertificateListInfo> pCertList (new (std::nothrow) _CertificateListInfo);
866         SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
867
868         memset(pCertList.get(), 0, sizeof(*pCertList.get()));
869
870         pCertList->pNext = null;
871         r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_CA_CERT);
872         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
873
874         r = fileStore.ReadFromFile(pCertList->certificate, certLength);
875         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
876
877         pCertList->length = certLength;
878         pCertList->certFileId = certRecord.certId;
879         pCertList->format = static_cast< _CertFormat >(certRecord.certFormat);
880         pCertList->certType = static_cast< _CaCertType >(certRecord.certType);
881
882         *ppCertList = pCertList.release();
883
884         return r;
885 }
886
887 result
888 _CertDbManager::GetUserCertificateListByCertId(int certId, _CertificateListInfo** ppCertList)
889 {
890         result r = E_SUCCESS;
891         _CertFileStore fileStore;
892         UserCertRecord certRecord = {0, };
893         int priKeyLen = 0;
894         int certLength = 0;
895         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
896         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
897
898         *ppCertList = null;
899
900         SysTryReturnResult(NID_SEC_CERT, ppCertList != null, E_INVALID_ARG, "Invalid input arguments.");
901         SysTryReturnResult(NID_SEC_CERT, certId > 0, E_INVALID_ARG, "Invalid input arguments.");
902
903         sprintf(condition, "certId = %d and installed = '%s'", certId, installed);
904         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
905         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate record.", GetErrorMessage(r));
906
907         std::unique_ptr <_CertificateListInfo> pCertList (new (std::nothrow) _CertificateListInfo);
908         SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
909
910         memset(pCertList.get(), 0, sizeof(*pCertList.get()));
911
912         pCertList->pNext = null;
913
914         r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_USER_CERT);
915         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
916
917         r = fileStore.ReadFromFile(pCertList->certificate, certLength);
918         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
919
920         pCertList->length = certLength;
921         pCertList->certFileId = certRecord.certId;
922         pCertList->format = static_cast< _CertFormat >(certRecord.certFormat);
923         pCertList->certType = _CERT_TYPE_USER_CERT;
924
925         std::unique_ptr <_CertPrivateKeyInfo> pPriKey (new (std::nothrow) _CertPrivateKeyInfo());
926         SysTryReturnResult(NID_SEC_CERT, pPriKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
927
928         std::unique_ptr <byte[]> pPrivateKey (new (std::nothrow) byte[_MAX_CERT_PRIVATE_KEY_SIZE]);
929         SysTryReturnResult(NID_SEC_CERT, pPrivateKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
930
931         memset(pPrivateKey.get(), 0, _MAX_CERT_PRIVATE_KEY_SIZE);
932
933         r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_PRIVATE_KEY);
934         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
935
936         r = fileStore.ReadFromFile(pPrivateKey.get(), priKeyLen);
937         if (!IsFailed(r) && priKeyLen != 0)
938         {
939                 byte* pPrivateTempKey = null;
940                 pPriKey->SetPrivateKey(priKeyLen, pPrivateKey.get());
941
942                 pPrivateKey.reset(null);
943
944                 pPriKey->GetPkcs8EncDecKeyN(priKeyLen, &pPrivateTempKey, 0);
945                 SysTryReturnResult(NID_SEC_CERT, pPrivateTempKey != null, E_SYSTEM, "Failed to get private key buffer.");
946
947                 std::unique_ptr<byte[]> pPrivateKeyAuto(pPrivateTempKey);
948
949                 memcpy(pCertList->privatekey, pPrivateTempKey, priKeyLen);
950         }
951         pCertList->priKeyLen = priKeyLen;
952
953         *ppCertList = pCertList.release();
954
955         return r;
956 }
957
958 result
959 _CertDbManager::FindIssuerCertificateAndTypeN(_CertFormat certFormat, char* pIssuerName, byte** ppCert, int& certLen, _CaCertType& certType)
960 {
961         result r = E_SUCCESS;
962         CaCertRecord certRecord = {0, };
963         _CertFileStore fileStore;
964         String filePath;
965         int issuerNameB64len = 0;
966         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_OFFSET_CONST_SIZE] = {0, };
967         char issuerNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_OFFSET_SIZE] = {0, };
968         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
969
970         SysTryReturnResult(NID_SEC_CERT, certFormat == _CERT_X509, E_INVALID_ARG, "Invalid certificate format.");
971         SysTryReturnResult(NID_SEC_CERT, pIssuerName != null, E_INVALID_ARG, "Invalid input arguments.");
972         SysTryReturnResult(NID_SEC_CERT, ppCert != null, E_INVALID_ARG, "Invalid input arguments.");
973
974         issuerNameB64len = _Base64::GetEncodedSize(strlen(pIssuerName));
975         SysTryReturnResult(NID_SEC_CERT, issuerNameB64len >= 0, E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
976
977         memset(issuerNameBase64, 0, sizeof(issuerNameBase64));
978
979         r = _Base64::Encode(reinterpret_cast< byte* >(pIssuerName), strlen(pIssuerName), issuerNameBase64, issuerNameB64len);
980         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
981
982         sprintf(condition, "subjectName = '%s' and certFormat = %d and installed = '%s'", issuerNameBase64, certFormat, installed);
983
984         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
985         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate record.", GetErrorMessage(r));
986
987         filePath = reinterpret_cast< char* >(certRecord.fileName);
988
989         fileStore.SetFilePath(filePath);
990
991         *ppCert = new (std::nothrow) byte[_MAX_CERTIFICATE_SIZE];
992         SysTryReturnResult(NID_SEC_CERT, *ppCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
993
994         r = fileStore.ReadFromFile(*ppCert, certLen);
995         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to read from file.", GetErrorMessage(r));
996
997         certType = static_cast< _CaCertType >(certRecord.certType); //Get the type of certificate
998
999         return r;
1000 }
1001
1002 result
1003 _CertDbManager::FindIssuerCertificateByTypeN(_CertFormat certFormat, _CaCertType certType, char* pIssuerName, byte** ppCert, int& certLen)
1004 {
1005         result r = E_SUCCESS;
1006         String filePath;
1007         CaCertRecord certRecord = {0, };
1008         _CertFileStore fileStore;
1009         int issuerNameB64len = 0;
1010         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_CONDITION_SIZE] = {0, };
1011         char issuerNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_NAME_OFFSET] = {0, };
1012         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
1013
1014         SysTryReturnResult(NID_SEC_CERT, certType > _CERT_TYPE_NOT_BOUNDED, E_INVALID_ARG, "Invalid certificate type.");
1015         SysTryReturnResult(NID_SEC_CERT, certType < _CERT_TYPE_MAX, E_INVALID_ARG, "Invalid certificate type.");
1016         SysTryReturnResult(NID_SEC_CERT, certFormat == _CERT_X509, E_INVALID_ARG, "Invalid certificate format.");
1017         SysTryReturnResult(NID_SEC_CERT, pIssuerName != null, E_INVALID_ARG, "Invalid input arguments.");
1018         SysTryReturnResult(NID_SEC_CERT, ppCert != null, E_INVALID_ARG, "Invalid input arguments.");
1019
1020         issuerNameB64len = _Base64::GetEncodedSize(strlen(pIssuerName));
1021         SysTryReturnResult(NID_SEC_CERT, issuerNameB64len >= 0, E_ENCODING_FAILED, "Failed to get encoded size.");
1022
1023         memset(issuerNameBase64, 0, sizeof(issuerNameBase64));
1024
1025         r = _Base64::Encode(reinterpret_cast< byte* >(pIssuerName), strlen(pIssuerName), issuerNameBase64, issuerNameB64len);
1026         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1027
1028         sprintf(condition, "subjectName = '%s' and certFormat = %d and certType = %d and installed = '%s'", issuerNameBase64, certFormat, certType, installed);
1029         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
1030         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate record.", GetErrorMessage(r));
1031
1032         if (certRecord.certId == 0)
1033         {
1034                 return E_SUCCESS;
1035         }
1036
1037         filePath = static_cast< char* >(certRecord.fileName);
1038         fileStore.SetFilePath(filePath);
1039
1040         std::unique_ptr <byte[]> pCert (new (std::nothrow) byte[_MAX_CERTIFICATE_SIZE]);
1041         SysTryReturnResult(NID_SEC_CERT, pCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1042
1043         r = fileStore.ReadFromFile(pCert.get(), certLen);
1044         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to read from file.", GetErrorMessage(r));
1045
1046         certType = static_cast< _CaCertType >(certRecord.certType); //Get the type of certificate
1047
1048         *ppCert = pCert.release();
1049
1050         return r;
1051 }
1052
1053 result
1054 _CertDbManager::FindCertType(_CertFormat certFormat, char* pIssuerName, char* pSubjectName, _CaCertType* pCertType)
1055 {
1056         result r = E_SUCCESS;
1057         CaCertRecord certRecord = {0, };
1058         _CertFileStore fileStore;
1059         int subjectNameB64len = 0;
1060         int issuerNameB64len = 0;
1061         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_CONDITION_CONST_SIZE] = {0, };
1062         char subjectNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_OFFSET_SIZE] = {0, };
1063         char issuerNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_OFFSET_SIZE] = {0, };
1064         char installed[_MAX_TYPE_RECORD_SIZE] = "T\0";
1065
1066         SysTryReturnResult(NID_SEC_CERT, certFormat == _CERT_X509, E_INVALID_ARG, "Invalid certificate format.");
1067         SysTryReturnResult(NID_SEC_CERT, pIssuerName != null, E_INVALID_ARG, "Invalid input arguments.");
1068         SysTryReturnResult(NID_SEC_CERT, pSubjectName != null, E_INVALID_ARG, "Invalid input arguments.");
1069         SysTryReturnResult(NID_SEC_CERT, pCertType != null, E_INVALID_ARG, "Invalid input arguments.");
1070
1071         issuerNameB64len = _Base64::GetEncodedSize(strlen(pIssuerName));
1072         SysTryReturnResult(NID_SEC_CERT, issuerNameB64len >= 0, E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1073
1074         memset(issuerNameBase64, 0, sizeof(issuerNameBase64));
1075
1076         r = _Base64::Encode(reinterpret_cast< byte* >(pIssuerName), strlen(pIssuerName), issuerNameBase64, issuerNameB64len);
1077         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1078
1079         subjectNameB64len = _Base64::GetEncodedSize(strlen(pSubjectName));
1080         SysTryReturnResult(NID_SEC_CERT, subjectNameB64len >= 0, E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1081
1082         memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
1083         r = _Base64::Encode(reinterpret_cast< byte* >(pSubjectName), strlen(pSubjectName), subjectNameBase64, subjectNameB64len);
1084         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1085
1086         sprintf(condition, "certFormat = %d and issuerName = '%s' and subjectName = '%s' and installed = '%s'", certFormat, issuerNameBase64, subjectNameBase64, installed);
1087         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
1088         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate record.", GetErrorMessage(r));
1089
1090         *pCertType = static_cast< _CaCertType >(certRecord.certType);  //Get the type of certificate
1091         return E_SUCCESS;
1092 }
1093
1094 result
1095 _CertDbManager::DeleteCertificateByIdNTableName(int certId, String tableName)
1096 {
1097         result r = E_SUCCESS;
1098         _CertFileStore fileStore;
1099         String fileName;
1100
1101         SysTryReturnResult(NID_SEC_CERT, certId > 0, E_INVALID_ARG, "Invalid input argument.");
1102
1103         if (tableName.CompareTo(_CERT_USER_CERT_TABLE) == 0)
1104         {
1105                 String keyfileName;
1106
1107                 r = __userCertDbStore.RemoveCertificateById(certId);
1108                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Error in deleting certificate.");
1109
1110                 //Remove certificate file
1111                 fileStore.GetFileNameFromHandle(certId, _CERT_PATH_USER_CERT, fileName);
1112                 r = Tizen::Io::File::Remove(fileName);
1113                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_FILE_NOT_FOUND, "Error in deleting file.");
1114
1115                 //Remove private key file
1116                 //Don't check return type here as it is not necessary that private key is present.
1117                 fileStore.GetFileNameFromHandle(certId, _CERT_PATH_PRIVATE_KEY, keyfileName);
1118                 r = Tizen::Io::File::Remove(keyfileName);
1119         }
1120         else if (tableName.CompareTo(_CERT_ROOT_CA_CERT_TABLE) == 0)
1121         {
1122                 r = __caCertDbStore.RemoveCertificateById(certId);
1123                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Delete certificate failed.");
1124
1125                 //Remove certificate file
1126                 fileStore.GetFileNameFromHandle(certId, _CERT_PATH_CA_CERT, fileName);
1127                 r = Tizen::Io::File::Remove(fileName);
1128                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_FILE_NOT_FOUND, "Error in deleting file.");
1129         }
1130         return E_SUCCESS;
1131 }
1132
1133 result
1134 _CertDbManager::GetHashOfCertFile(byte* pFilePath, int* pLen, char* pBuf)
1135 {
1136         result r = E_SUCCESS;
1137         String fileName(reinterpret_cast< char* >(pFilePath));
1138         FileAttributes attr;
1139         File file;
1140         long fileSize = 0;
1141         int readCnt = 0;
1142         int certLen = 0;
1143         int outLen = _MAX_CERT_SHA1_DIGEST_SIZE;
1144         int resValue = 0;
1145
1146         SysTryReturnResult(NID_SEC_CERT, pFilePath != null, E_INVALID_ARG, "Invalid inpur arguments.");
1147         SysTryReturnResult(NID_SEC_CERT, pLen != null, E_INVALID_ARG, "Invalid inpur arguments.");
1148         SysTryReturnResult(NID_SEC_CERT, pBuf != null, E_INVALID_ARG, "Invalid inpur arguments.");
1149
1150         r = File::GetAttributes(fileName, attr);
1151         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to get attributes.");
1152
1153         fileSize = attr.GetFileSize();
1154         SysTryReturn(NID_SEC_CERT, fileSize >= 0, r, r, "[%s] Failed to get file attributes.", GetErrorMessage(r));
1155         SysTryReturn(NID_SEC_CERT, fileSize < _MAX_CERTIFICATE_SIZE, r, r, "[%s] File size exceeds maximum specified length.", GetErrorMessage(r));
1156
1157         // Open file
1158         r = file.Construct(fileName, L"r");
1159         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to construct file.");
1160
1161         std::unique_ptr <byte[]> pCertBuf (new (std::nothrow) byte[fileSize + 1]);
1162         SysTryReturnResult(NID_SEC_CERT, pCertBuf != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1163
1164         memset(pCertBuf.get(), 0, fileSize + 1);
1165         readCnt = file.Read(pCertBuf.get(), fileSize);
1166         r = GetLastResult();
1167         SysTryReturn(NID_SEC_CERT, (readCnt == fileSize) || (!IsFailed(r)), r, r, "[%s] Failed to read file.", GetErrorMessage(r));
1168
1169         certLen = readCnt;
1170         std::unique_ptr <byte[]> pOutBuf (new (std::nothrow) byte[outLen]);
1171         SysTryReturnResult(NID_SEC_CERT, pOutBuf != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1172
1173         memset(pOutBuf.get(), 0, outLen);
1174         //As per OpenSSL APIs, it takes input as unsigned data types
1175         resValue = EVP_Digest(pCertBuf.get(), static_cast< int >(certLen), pOutBuf.get(), reinterpret_cast< unsigned int* >(&outLen), EVP_sha1(), 0);
1176         SysTryReturnResult(NID_SEC_CERT, resValue == 1, E_SYSTEM, "Failed to create digest.");
1177
1178         memcpy(pBuf, pOutBuf.get(), outLen);
1179         *pLen = outLen;
1180
1181         return r;
1182 }
1183
1184 //User Certificate APIs
1185
1186 result
1187 _CertDbManager::InsertCertChain(_CertFormat certFormat, _CertChain* pCertChain)
1188 {
1189         result r = E_SUCCESS;
1190         _CaCertType certType = _CERT_TYPE_NOT_BOUNDED;
1191         int curCACertId = 0;
1192         int lastCACertId = 0;
1193         int curDevCertId = 0;
1194         bool updateUserParentCa = false;
1195
1196         SysTryReturnResult(NID_SEC_CERT, pCertChain != null, E_INVALID_ARG, "Invalid input parameter.");
1197         SysTryReturnResult(NID_SEC_CERT, certFormat == _CERT_X509, E_INVALID_ARG, "Invalid certificate format.");
1198
1199         //Check for CA certificate table creation
1200         r = __caCertDbStore.IsRootCaCertTableCreated();
1201         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Certificate table are not not created.");
1202
1203
1204         //Check if the chain is valid or not
1205         r = pCertChain->Verify();
1206         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INVALID_ARG, "Invalid certificate chain.");
1207
1208         r = pCertChain->MoveHead();
1209         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to move head in certificate chain.");
1210
1211         if (certFormat == _CERT_X509)
1212         {
1213                 _X509Certificate* pCurCert = null;
1214                 _X509Certificate* pUserCert = null;
1215                 _X509TbsCert* pTbsCert = null;
1216                 byte* pX509Buff = null;
1217                 int x509BuffSize = 0;
1218
1219                 pUserCert = pCertChain->GetCurrentCertificate();
1220                 SysTryReturnResult(NID_SEC_CERT, pUserCert != null, E_SYSTEM, "Failed to get certificate from chain, broken certificate chain.");
1221
1222                 pTbsCert = pUserCert->GetTbsCertInstance();
1223                 SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1224
1225                 pUserCert->GetCertBuffer(pX509Buff, x509BuffSize);
1226                 SysTryReturn(NID_SEC_CERT, pX509Buff != null, E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Failed to get certificate buffer.");
1227
1228                 r = InsertUserCertificateFromBuffer(certFormat, pX509Buff, x509BuffSize, null, 0);
1229                 SysTryReturn(NID_SEC_CERT, !(IsFailed(r) && (r != E_OBJ_ALREADY_EXIST) && (r != E_FILE_ALREADY_EXIST)), r, r, "[%s] Failed insert user certificate chain.", GetErrorMessage(r));
1230
1231                 updateUserParentCa = true;
1232
1233                 r = GetUserCertificateId(pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())),
1234                                                                  pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1235                                                                  curDevCertId);
1236                 SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get user certificate id.", GetErrorMessage(r));
1237
1238                 //Insert certificate chain in CA certificate store
1239                 while (pCertChain->MoveNext() == E_SUCCESS)
1240                 {
1241
1242                         pCurCert = pCertChain->GetCurrentCertificate();
1243                         SysTryReturnResult(NID_SEC_CERT, pCurCert != null, E_SYSTEM, "Failed to get certificate from chain, broken certificate chain.");
1244
1245                         if (!pCurCert->IsSelfSigned())
1246                         {
1247                                 certType = _CERT_TYPE_INTERMIDIATE_CA;
1248                         }
1249                         else
1250                         {
1251                                 //This parameter need to pass from certificate manager about its type
1252                                 certType = _CERT_TYPE_ROOT_CA;
1253                         }
1254
1255                         pTbsCert = pCurCert->GetTbsCertInstance();
1256                         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1257
1258                         if (E_SUCCESS != __caCertDbStore.CheckDuplicateCertificate(certType, reinterpret_cast< byte* >(pTbsCert->GetSubjectName()), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName()))))
1259                         {
1260                                 pX509Buff = null;
1261                                 x509BuffSize = 0;
1262
1263                                 pCurCert->GetCertBuffer(pX509Buff, x509BuffSize);
1264                                 SysTryReturnResult(NID_SEC_CERT, pX509Buff != null, E_SYSTEM, "Failed to get certificate buffer.");
1265
1266                                 r = InsertCaCertificateFromBuffer(certType, certFormat, pX509Buff, x509BuffSize);
1267                                 SysTryReturn(NID_SEC_CERT, !(IsFailed(r) && r != E_FILE_ALREADY_EXIST), r, r, "[E_SYSTEM] Failed to insert ca certificate.");
1268                         }
1269                         // CA certificate already present or properly installed in CA certificate store,
1270                         // get the certificate id of certificate
1271                         r = GetCaCertificateId(pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())),
1272                                                                   pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1273                                                                   curCACertId, certType);
1274                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get Ca certificate id.", GetErrorMessage(r));
1275
1276                         if (updateUserParentCa)
1277                         {
1278                                 __userCertDbStore.UpdateParentCa(curDevCertId, curCACertId);
1279                                 updateUserParentCa = false;
1280                                 lastCACertId = curCACertId;
1281                         }
1282                         else
1283                         {
1284                                 __caCertDbStore.UpdateParentCa(lastCACertId, curCACertId);
1285                                 lastCACertId = curCACertId;
1286                         }
1287
1288                         //If it is root certificate then its parent is itself
1289                         if (pCurCert->IsSelfSigned())
1290                         {
1291                                 __caCertDbStore.UpdateParentCa(curCACertId, curCACertId);
1292                         }
1293
1294                 } //end of while
1295
1296                 if (updateUserParentCa)
1297                 {
1298                         r = pCertChain->MoveHead();
1299                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to move head in certificate chain.");
1300
1301                         pCurCert = pCertChain->GetCurrentCertificate();
1302                         SysTryReturnResult(NID_SEC_CERT, pCurCert != null, E_SYSTEM, "Failed to get certificate from chain, broken certificate chain.");
1303
1304                         pTbsCert = pCurCert->GetTbsCertInstance();
1305                         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1306
1307                         r = GetCaCertificateId(pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1308                                                                   null, 0, curCACertId);
1309                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get Ca certificate id.", GetErrorMessage(r));
1310
1311                         __userCertDbStore.UpdateParentCa(curDevCertId, curCACertId);
1312                         updateUserParentCa = false;
1313                         lastCACertId = curCACertId;
1314                 }
1315                 else if (!pCurCert->IsSelfSigned())
1316                 {
1317                         pTbsCert = pCurCert->GetTbsCertInstance();
1318                         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1319
1320                         r = GetCaCertificateId(pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1321                                                                   null, 0, curCACertId);
1322                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get Ca certificate id.", GetErrorMessage(r));
1323
1324                         __caCertDbStore.UpdateParentCa(lastCACertId, curCACertId);
1325                         lastCACertId = curCACertId;
1326                 }
1327         }
1328
1329         return r;
1330 }
1331
1332 result
1333 _CertDbManager::InsertCertificateChain(_CertFormat certFormat, _CertChain* pCertChain, _CertPrivateKeyInfo* pPrivateKeyInfo)
1334 {
1335         result r = E_SUCCESS;
1336         _CaCertType certType = _CERT_TYPE_NOT_BOUNDED;
1337         int prvKeyLen = 0;
1338         int curCACertId = 0;
1339         int lastCACertId = 0;
1340         int curDevCertId = 0;
1341
1342         bool updateUserParentCa = false;
1343         byte* pPrvKey = null;
1344         std::unique_ptr <byte[]> pPrvKeyBuffer;
1345
1346         SysTryReturnResult(NID_SEC_CERT, pCertChain != null, E_INVALID_ARG, "Invalid input parameter.");
1347         SysTryReturnResult(NID_SEC_CERT, certFormat == _CERT_X509, E_INVALID_ARG, "Invalid certificate format.");
1348
1349         r = __userCertDbStore.IsUserCertTableCreated();
1350         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to create certificate table.");
1351
1352         //Check for CA certificate table creation
1353         r = __caCertDbStore.IsRootCaCertTableCreated();
1354         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to create certificate table.");
1355
1356         //Check if the chain is valid or not
1357         r = pCertChain->Verify();
1358         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to verify certificate.", GetErrorMessage(r));
1359
1360         r = pCertChain->MoveHead();
1361         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to move head in certificate chain.");
1362
1363         if (certFormat == _CERT_X509)
1364         {
1365                 _X509Certificate* pCurCert = null;
1366                 _X509Certificate* pUserCert = null;
1367                 _X509TbsCert* pTbsCert = null;
1368                 byte* pX509Buff = null;
1369                 int x509BuffSize = 0;
1370
1371                 pUserCert = pCertChain->GetCurrentCertificate();
1372                 SysTryReturnResult(NID_SEC_CERT, pUserCert != null, E_SYSTEM, "Failed to get certificate from chain, broken certificate chain.");
1373
1374                 pTbsCert = pUserCert->GetTbsCertInstance();
1375                 SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1376
1377                 byte* pSubjectName = pTbsCert->GetSubjectName();
1378                 SysTryReturn(NID_SEC_CERT, pSubjectName != null, E_OBJ_NOT_FOUND, E_OBJ_NOT_FOUND, "[E_OBJ_NOT_FOUND] Subjectname not present.");
1379
1380                 int subjectNameLen = strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName()));
1381
1382                 r = __userCertDbStore.CheckDuplicateCertificate(pSubjectName, subjectNameLen);
1383                 if (IsFailed(r))
1384                 {
1385                         if (pPrivateKeyInfo != null)
1386                         {
1387                                 pPrivateKeyInfo->GetPkcs8EncDecKeyN(prvKeyLen, &pPrvKey, 1);
1388                                 SysTryReturnResult(NID_SEC_CERT, prvKeyLen > 0, E_INVALID_KEY, "Invalid key length .");
1389
1390                                 pPrvKeyBuffer = std::unique_ptr <byte[]> (pPrvKey);
1391                                 pPrvKey = null;
1392
1393                         }
1394
1395                         pUserCert->GetCertBuffer(pX509Buff, x509BuffSize);
1396                         SysTryReturnResult(NID_SEC_CERT, pX509Buff != null, E_SYSTEM, "Failed to get certificate buffer.");
1397
1398                         r = _CertDbManager::InsertUserCertificateFromBuffer(certFormat, pX509Buff, x509BuffSize, pPrvKeyBuffer.get(), static_cast< int >(prvKeyLen));
1399                         if (IsFailed(r) && r != E_OBJ_ALREADY_EXIST && r != E_FILE_ALREADY_EXIST)
1400                         {
1401                                 return r;
1402                         }
1403                         else
1404                         {
1405                                 updateUserParentCa = true;
1406
1407                                 r = GetUserCertificateId(pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())),
1408                                                                                  pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1409                                                                                  curDevCertId);
1410                                 SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get user certificate id.", GetErrorMessage(r));
1411
1412                                 if (pPrvKeyBuffer != null)
1413                                 {
1414                                         _CertFileStore fileStore;
1415                                         String privateKeyFile;
1416
1417                                         fileStore.GetFileNameFromHandle(curDevCertId, _CERT_PATH_PRIVATE_KEY, privateKeyFile);
1418                                         fileStore.SetFilePath(privateKeyFile);
1419
1420
1421                                         r = fileStore.WriteToFile(pPrvKeyBuffer.get(), prvKeyLen);
1422                                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INACCESSIBLE_PATH, "Failed to write in file.");
1423
1424                                 }
1425                         }
1426                 }
1427                 else
1428                 {
1429                         return r;
1430                 }
1431
1432                 if (pUserCert->IsSelfSigned())
1433                 {
1434                         __userCertDbStore.UpdateParentCa(curDevCertId, curDevCertId);
1435                         return r;
1436                 }
1437
1438                 //Insert certificate chain in CA certificate store
1439                 while (pCertChain->MoveNext() == E_SUCCESS)
1440                 {
1441                         pCurCert = pCertChain->GetCurrentCertificate();
1442                         SysTryReturnResult(NID_SEC_CERT, pCurCert != null, E_SYSTEM, "Failed to get certificate from chain, broken certificate chain.");
1443
1444                         if (!pCurCert->IsSelfSigned())
1445                         {
1446                                 certType = _CERT_TYPE_INTERMIDIATE_CA;
1447                         }
1448                         else
1449                         {
1450                                 //This parameter need to pass from certificate manager about its type
1451                                 certType = _CERT_TYPE_ROOT_CA;
1452                         }
1453
1454                         pTbsCert = pCurCert->GetTbsCertInstance();
1455                         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1456
1457                         r = __caCertDbStore.CheckDuplicateCertificate(certType, pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())));
1458                         if (IsFailed(r))
1459                         {
1460                                 pX509Buff = null;
1461                                 x509BuffSize = 0;
1462
1463                                 pCurCert->GetCertBuffer(pX509Buff, x509BuffSize);
1464                                 SysTryReturnResult(NID_SEC_CERT, pX509Buff != null, E_SYSTEM, "Failed to get certificate buffer.");
1465
1466                                 r = _CertDbManager::InsertCaCertificateFromBuffer(certType, certFormat, pX509Buff, x509BuffSize);
1467                                 SysTryReturn(NID_SEC_CERT, !(IsFailed(r) && r != E_FILE_ALREADY_EXIST), r, r, "[E_SYSTEM] Failed to insert ca certificate.");
1468
1469                         }
1470                         // CA certificate already present or properly install in CA certificate store,
1471                         // get the certificate id of certificate
1472
1473                         r = GetCaCertificateId(pTbsCert->GetSubjectName(), strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName())),
1474                                                                   pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1475                                                                   curCACertId, certType);
1476                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get Ca certificate id.", GetErrorMessage(r));
1477
1478                         if (updateUserParentCa)
1479                         {
1480                                 __userCertDbStore.UpdateParentCa(curDevCertId, curCACertId);
1481                                 updateUserParentCa = false;
1482                                 lastCACertId = curCACertId;
1483                         }
1484                         else
1485                         {
1486                                 __caCertDbStore.UpdateParentCa(lastCACertId, curCACertId);
1487                                 lastCACertId = curCACertId;
1488                         }
1489
1490                         //If it is root certificate then its parent is itself
1491                         if (pCurCert->IsSelfSigned())
1492                         {
1493                                 __caCertDbStore.UpdateParentCa(curCACertId, curCACertId);
1494                         }
1495                 }
1496
1497                 if (updateUserParentCa)
1498                 {
1499                         r = pCertChain->MoveHead();
1500                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to move head in certificate chain.");
1501
1502                         pCurCert = pCertChain->GetCurrentCertificate();
1503                         SysTryReturnResult(NID_SEC_CERT, pCurCert != null, E_SYSTEM, "Failed to get certificate from chain, broken certificate chain.");
1504
1505                         pTbsCert = pCurCert->GetTbsCertInstance();
1506                         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1507
1508                         r = GetCaCertificateId(pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1509                                                                   null, 0, curCACertId);
1510                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get Ca certificate id.", GetErrorMessage(r));
1511
1512                         __userCertDbStore.UpdateParentCa(curDevCertId, curCACertId);
1513                         updateUserParentCa = false;
1514                         lastCACertId = curCACertId;
1515                 }
1516                 else if (!pCurCert->IsSelfSigned())
1517                 {
1518                         pTbsCert = pCurCert->GetTbsCertInstance();
1519                         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1520
1521                         r = GetCaCertificateId(pTbsCert->GetIssuerName(), strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName())),
1522                                                                  null, 0, curCACertId);
1523                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed get Ca certificate id.", GetErrorMessage(r));
1524
1525                         __caCertDbStore.UpdateParentCa(lastCACertId, curCACertId);
1526                         lastCACertId = curCACertId;
1527                 }
1528         }
1529
1530         return r;
1531 }
1532
1533 result
1534 _CertDbManager::InsertUserCertificateFromBuffer(_CertFormat certFormat, byte* pCertBuffer, int certLength, byte* pPrivateKey, int privateKeyLen, int parentCa)
1535 {
1536         result r = E_SUCCESS;
1537         _X509TbsCert* pTbsCert = null;
1538         _CertFileStore fileStore;
1539         UserCertRecord certRecord = {0, };
1540         String privateKeyFile;
1541         String tempFileName;
1542         int lenSubjectName = 0;
1543         int lenIssuerName = 0;
1544         int lenSerialNo = 0;
1545         int certId = 0;
1546         int keyIdB64Length = 0;
1547         char* pFileName = null;
1548         char* pPriKeyFileName = null;
1549         char subjectNameBuffer[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
1550         char szIssuerName[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
1551         char serialName[_MAX_SERIAL_NUMBER_SIZE] = {0, };
1552         char installedRecord[_MAX_TYPE_RECORD_SIZE] = "T\0";
1553         byte* pKeyId = null;
1554         byte* pSerial = null;
1555
1556         //pPrivateKey, privateKeyLen, parentca are optional parameter, no need to sanity check for them.
1557         SysTryReturnResult(NID_SEC_CERT, pCertBuffer != null, E_INVALID_ARG, "Invalid input parameter.");
1558         SysTryReturnResult(NID_SEC_CERT, certFormat == _CERT_X509, E_INVALID_ARG, "Invalid certificate format.");
1559         SysTryReturnResult(NID_SEC_CERT, certLength > 0, E_INVALID_ARG, "Invalid input parameter.");
1560
1561         r = __userCertDbStore.IsUserCertTableCreated();
1562         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to create user certificate.");
1563
1564         std::unique_ptr <_X509Certificate> pCert (new (std::nothrow) _X509Certificate());
1565         SysTryReturnResult(NID_SEC_CERT, pCert != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1566
1567         r = pCert->Parse(pCertBuffer, certLength);
1568         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Parsing failed.", GetErrorMessage(r));
1569
1570         pTbsCert = pCert->GetTbsCertInstance();
1571         SysTryReturnResult(NID_SEC_CERT, pTbsCert != null, E_SYSTEM, "Failed to get certificate to be signed instance.");
1572
1573         lenSubjectName = strlen(reinterpret_cast< char* >(pTbsCert->GetSubjectName()));
1574         lenIssuerName = strlen(reinterpret_cast< char* >(pTbsCert->GetIssuerName()));
1575
1576         SysTryReturnResult(NID_SEC_CERT, lenSubjectName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_DATABASE, "Length is greater than maximum allowed length.");
1577         SysTryReturnResult(NID_SEC_CERT, lenIssuerName < _MAX_ISSUER_SUBJECT_NAME_SIZE, E_DATABASE, "Length is greater than maximum allowed length.");
1578
1579         strcpy(subjectNameBuffer, reinterpret_cast< char* >(pTbsCert->GetSubjectName()));
1580         strcpy(szIssuerName, reinterpret_cast< char* >(pTbsCert->GetIssuerName()));
1581
1582         pTbsCert->GetSerialNumber(pSerial, static_cast< int& >(lenSerialNo));
1583         if ((lenSerialNo <= 0) || (lenSerialNo > _MAX_SERIAL_NUMBER_SIZE))
1584         {
1585                 if (pSerial != null)
1586                 {
1587                         memset(pSerial, 0, _MAX_SERIAL_NUMBER_SIZE);
1588                         lenSerialNo = 1;
1589                 }
1590         }
1591         else
1592         {
1593                 memcpy(serialName, pSerial, lenSerialNo);
1594         }
1595
1596         //Get Device ID
1597         r = pCert->GetKeyIdN(&pKeyId);
1598         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_DECODING_FAILED, "Failed to get key Id.");
1599
1600         std::unique_ptr <byte[]> pKeyIdBuffer (pKeyId);
1601
1602         keyIdB64Length = _Base64::GetEncodedSize(_MAX_CERT_SHA1_DIGEST_SIZE);
1603         SysTryReturnResult(NID_SEC_CERT, keyIdB64Length >= 0, E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1604
1605         std::unique_ptr <char[]> pId64 (new (std::nothrow) char[keyIdB64Length]);
1606         SysTryReturnResult(NID_SEC_CERT, pId64 != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1607
1608         memset(pId64.get(), 0, keyIdB64Length);
1609         r = _Base64::Encode(reinterpret_cast< byte* >(pKeyIdBuffer.get()), _MAX_CERT_SHA1_DIGEST_SIZE, pId64.get(), keyIdB64Length);
1610         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_DECODING_FAILED, "Decoding failed.");
1611
1612         r = __userCertDbStore.CheckDuplicateCertificate(reinterpret_cast< byte* >(subjectNameBuffer), lenSubjectName);
1613         SysTryReturnResult(NID_SEC_CERT, IsFailed(r), E_FILE_ALREADY_EXIST, "File already exists.");
1614
1615         //Get the last installed certificate id from db table
1616         __userCertDbStore.GetCurrentCertId(certId);
1617
1618         //Calculate the new certificate id for installation
1619         certId = certId + 1;
1620
1621         if (pPrivateKey != null)
1622         {
1623                 //Get file name for private key and store private key into file.
1624                 fileStore.GetFileNameFromHandle(certId, _CERT_PATH_PRIVATE_KEY, privateKeyFile);
1625         }
1626         else
1627         {
1628                 pPriKeyFileName = null;
1629                 privateKeyLen = 0;
1630         }
1631
1632         //Get file name for certificate and write device certificate to file
1633         fileStore.GetFileNameFromHandle(certId, _CERT_PATH_USER_CERT, tempFileName);
1634
1635         //Insert Record into Database
1636         //It is generated automatically by sequence
1637         memset(&certRecord, 0, sizeof(certRecord));
1638
1639         memcpy(certRecord.certPubKeyHash, pId64.get(), keyIdB64Length); //Base64 encoded device id
1640         certRecord.certFormat = static_cast< int >(certFormat);
1641
1642         pFileName = Tizen::Base::_StringConverter::CopyToCharArrayN(tempFileName);
1643         SysTryReturnResult(NID_SEC_CERT, pFileName != null, E_SYSTEM, "Failed to get attributes.");
1644
1645         strcpy(certRecord.fileName, pFileName);
1646         certRecord.subjectNameLen = lenSubjectName;
1647
1648         memcpy(certRecord.subjectName, subjectNameBuffer, lenSubjectName);
1649         certRecord.issuerNameLen = lenIssuerName;
1650         memcpy(certRecord.issuerName, szIssuerName, lenIssuerName);
1651
1652         pPriKeyFileName = Tizen::Base::_StringConverter::CopyToCharArrayN(privateKeyFile);
1653         SysTryReturnResult(NID_SEC_CERT, pPriKeyFileName != null, E_SYSTEM, "Failed to get attributes.");
1654
1655         strcpy(certRecord.prvKeyPath, pPriKeyFileName);
1656         certRecord.prvKeyLen = privateKeyLen;
1657         certRecord.parentCa = certId;
1658         strcpy(certRecord.installed, installedRecord);
1659
1660         memcpy(certRecord.serialNo, serialName, lenSerialNo);
1661
1662         certRecord.serialNoLen = lenSerialNo;
1663
1664         r = __userCertDbStore.InsertUserCertificate(&certRecord);
1665         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_DATABASE, "Failed to insert user certificate.");
1666
1667         fileStore.SetFilePath(tempFileName);
1668
1669         r = fileStore.WriteToFile(pCertBuffer, certLength);
1670         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INACCESSIBLE_PATH, "Failed to write in file.");
1671
1672         if (pPrivateKey != null)
1673         {
1674                 fileStore.SetFilePath(privateKeyFile);
1675
1676                 r = fileStore.WriteToFile(pPrivateKey, privateKeyLen);
1677                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_INACCESSIBLE_PATH, "Failed to write in file.");
1678         }
1679
1680         return r;
1681 }
1682
1683 result
1684 _CertDbManager::GetUserCertificateChain(char* pIssuerName, int issuerNameLen, char* pSubjectName, int subjectNameLen, _CertEncodingType encodingType, _CertificateListInfo** ppCertListInfoTypes)
1685 {
1686         result r = E_SUCCESS;
1687         CaCertRecord certRecord = {0, };
1688         UserCertRecord userCertRecord = {0, };
1689         _CertificateListInfo* pHoldList = null;
1690         BIO* pBio = null;
1691         X509* pCert = null;
1692         EVP_PKEY* pKey = null;
1693         int certCount = 0;
1694         int recordCount = 0;
1695         int subjectNameBase64Len = 0;
1696         int count = 0;
1697         int readLength = 0;
1698         int priKeyLen = 0;
1699         int subNameLen = 0;
1700         int curCertId = 0;
1701         int certificateBase64Len = 0;
1702         char installedRecord[_MAX_TYPE_RECORD_SIZE] = "T\0";
1703         char condition[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE] = {0};
1704         byte issuerNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_OFFSET_SIZE] = {0, };
1705         byte subjectNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_OFFSET_SIZE] = {0, };
1706         byte subName[_MAX_ISSUER_SUBJECT_NAME_SIZE] = {0, };
1707         bool isIssuerNameInList = false;
1708
1709         subjectNameBase64Len = _Base64::GetEncodedSize(issuerNameLen);
1710         memset(issuerNameBase64, 0, sizeof(issuerNameBase64));
1711         r = _Base64::Encode(reinterpret_cast< byte* >(pIssuerName), issuerNameLen, reinterpret_cast< char* >(issuerNameBase64), subjectNameBase64Len);
1712         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r),E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1713
1714         if ((pSubjectName != null) && (subjectNameLen > 0))
1715         {
1716                 subjectNameBase64Len = _Base64::GetEncodedSize(subjectNameLen);
1717                 memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
1718                 r = _Base64::Encode(reinterpret_cast< byte* >(pSubjectName), subjectNameLen, reinterpret_cast< char* >(subjectNameBase64), subjectNameBase64Len);
1719                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r),E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1720                 sprintf(condition, "subjectName = '%s' and installed = '%s'", subjectNameBase64, installedRecord);
1721         }
1722         else
1723         {
1724                 r = __userCertDbStore.GetNumberOfCertificates(recordCount);
1725                 SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates.", GetErrorMessage(r));
1726                 SysTryReturnResult(NID_SEC_CERT, recordCount > 0, E_OBJ_NOT_FOUND, "Failed to get certificate records.");
1727                 sprintf(condition, "installed = '%s'", installedRecord);
1728         }
1729
1730         memset(&userCertRecord, 0, sizeof(userCertRecord));
1731         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &userCertRecord);
1732         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
1733
1734         std::unique_ptr <_CertPrivateKeyInfo> pPriKey (new (std::nothrow) _CertPrivateKeyInfo());
1735         SysTryReturnResult(NID_SEC_CERT, pPriKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1736         do
1737         {
1738                 std::unique_ptr <_CertFileStore> pFileStore (new (std::nothrow) _CertFileStore());
1739                 SysTryReturnResult(NID_SEC_CERT, pFileStore != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1740
1741                 std::unique_ptr<_CertificateListInfo> pCertList(new (std::nothrow) _CertificateListInfo);
1742                 SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1743
1744                 memset(pCertList.get(), 0, sizeof(*pCertList.get()));
1745
1746                 pCertList->pNext = null;
1747
1748                 r = pFileStore->SetFileHandle(userCertRecord.certId, _CERT_PATH_USER_CERT);
1749                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
1750
1751                 r = pFileStore->ReadFromFile(reinterpret_cast< byte* >(pCertList->certificate), pCertList->length);
1752                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
1753                 certificateBase64Len = _Base64::GetEncodedSize(pCertList->length);
1754
1755                 if (encodingType == _CERT_ENC_TYPE_PEM)
1756                 {
1757                         const byte* pCertBuffer = pCertList->certificate;
1758                 
1759                         pBio = BIO_new(BIO_s_mem());
1760                         SysTryReturnResult(NID_SEC_CERT, pBio != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1761         
1762                         pCert = d2i_X509(null, &pCertBuffer, pCertList->length);
1763                         SysTryCatch(NID_SEC_CERT, pCert != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate convertion failed.");
1764
1765                         readLength = PEM_write_bio_X509(pBio, pCert);
1766                         SysTryCatch(NID_SEC_CERT, readLength > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate conversion failed");
1767
1768                         pCertList->length = certificateBase64Len + (2 * _MAX_PEM_HEADER);
1769
1770                         readLength = BIO_read(pBio, pCertList->certificate, pCertList->length);
1771                         SysTryCatch(NID_SEC_CERT, readLength > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate conversion failed");
1772
1773                         pCertList->length = readLength;
1774
1775                         BIO_free(pBio);
1776                         pBio = null;
1777                         
1778                         X509_free(pCert);
1779                         pCert = null;
1780
1781                 }
1782                 else if (encodingType == _CERT_ENC_TYPE_BASE64)
1783                 {
1784                         int certLen = _Base64::GetEncodedSize(pCertList->length);
1785                         memset(pCertList->certificate + pCertList->length, 0, sizeof(pCertList->certificate) - pCertList->length);
1786                         r = _Base64::Encode(reinterpret_cast< byte* >(pCertList->certificate), pCertList->length, reinterpret_cast< char* >(pCertList->certificate), certLen);
1787                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1788
1789                         pCertList->length = certLen;
1790                 }
1791
1792                 std::unique_ptr <byte[]> pPrivateKey (new (std::nothrow) byte[_MAX_CERT_PRIVATE_KEY_SIZE]);
1793                 SysTryReturnResult(NID_SEC_CERT, pPrivateKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1794
1795                 memset(pPrivateKey.get(), 0, _MAX_CERT_PRIVATE_KEY_SIZE);
1796                 pCertList->format = static_cast< _CertFormat >(userCertRecord.certFormat);
1797                 pCertList->certFileId = userCertRecord.certId;
1798
1799                 r = pFileStore->SetFileHandle(userCertRecord.certId, _CERT_PATH_PRIVATE_KEY);
1800                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
1801
1802                 priKeyLen = 0;
1803
1804                 r = pFileStore->ReadFromFile(reinterpret_cast< byte* >(pPrivateKey.get()), priKeyLen);
1805                 if (!IsFailed(r) && priKeyLen != 0)
1806                 {
1807                         byte* pPrivateTempKey = null;
1808                         pPriKey->SetPrivateKey(priKeyLen, pPrivateKey.get());
1809                         pCertList->priKeyLen = _Base64::GetEncodedSize(priKeyLen) + _MAX_PEM_HEADER;
1810
1811                         pPrivateKey.reset(null);
1812                         priKeyLen = 0;
1813
1814                         pPriKey->GetPkcs8EncDecKeyN(priKeyLen, &pPrivateTempKey, 0);
1815                         SysTryReturnResult(NID_SEC_CERT, pPrivateTempKey != null, E_SYSTEM, "Failed to get private key buffer.");
1816                         
1817                         pPrivateKey = std::unique_ptr<byte[]>(pPrivateTempKey);
1818
1819                         if (encodingType == _CERT_ENC_TYPE_PEM)
1820                         {
1821                                 const byte* pKeyBuffer = pPrivateKey.get();
1822                                 pBio = BIO_new(BIO_s_mem());
1823                                 SysTryReturnResult(NID_SEC_CERT, pBio != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1824
1825                                 pKey = d2i_PrivateKey(EVP_PKEY_RSA, null, &pKeyBuffer, priKeyLen);
1826                                 SysTryCatch(NID_SEC_CERT, pKey != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Private key conversion failed");
1827
1828                                 PEM_write_bio_PrivateKey(pBio, pKey, null, null, 0, 0, null);
1829                                 SysTryCatch(NID_SEC_CERT, pBio != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Private key to bio conversion failed");
1830
1831                                 readLength = BIO_read(pBio, pCertList->privatekey, pCertList->priKeyLen);
1832
1833                                 SysTryCatch(NID_SEC_CERT, readLength > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Private Key conversion failed");
1834
1835                                 pCertList->priKeyLen = readLength;
1836
1837                                 BIO_free(pBio);
1838                                 pBio = null;
1839
1840                                 X509_free(pCert);
1841                                 pCert = null;
1842                         }
1843                         else if (encodingType == _CERT_ENC_TYPE_BASE64)
1844                         {
1845                                 pCertList->priKeyLen = _Base64::GetEncodedSize(priKeyLen);
1846                                 memset(pCertList->privatekey, 0, sizeof(pCertList->privatekey));
1847
1848                                 r = _Base64::Encode(reinterpret_cast< byte* >(pPrivateKey.get()), priKeyLen, reinterpret_cast< char* >(pCertList->privatekey), pCertList->priKeyLen);
1849                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1850                         }
1851                         else
1852                         {
1853                                 memcpy(pCertList->privatekey, pPrivateKey.get(), priKeyLen);
1854                                 pCertList->priKeyLen = priKeyLen;
1855                         }
1856                 }
1857
1858                 pPrivateKey.reset(null);
1859
1860                 pHoldList = pCertList.release();
1861                 *ppCertListInfoTypes = pHoldList;
1862
1863                 certCount++;
1864
1865                 memset(subName, 0, _MAX_ISSUER_SUBJECT_NAME_SIZE);
1866                 memcpy(subName, userCertRecord.issuerName, userCertRecord.issuerNameLen);
1867                 subNameLen = userCertRecord.issuerNameLen;
1868
1869                 do
1870                 {
1871                         subjectNameBase64Len = _Base64::GetEncodedSize(subNameLen);
1872                         memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
1873                         r = _Base64::Encode(reinterpret_cast< byte* >(subName), subNameLen, reinterpret_cast< char* >(subjectNameBase64), subjectNameBase64Len);
1874                         SysTryCatch(NID_SEC_CERT, !IsFailed(r), , r, "[%s] Failed to encode data in base 64 encoding.", GetErrorMessage(r));
1875                         sprintf(condition, "subjectName = '%s' and installed = '%s'", subjectNameBase64, installedRecord);
1876
1877                         if (strcmp(reinterpret_cast< char* >(issuerNameBase64), reinterpret_cast< char* >(subjectNameBase64)) == 0)
1878                         {
1879                                 isIssuerNameInList = true;
1880                         }
1881
1882                         memset(&certRecord, 0, sizeof(certRecord));
1883                         r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
1884                         SysTryCatch(NID_SEC_CERT, !IsFailed(r), , r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
1885
1886                         if (strcmp(certRecord.issuerName, certRecord.subjectName) != 0)
1887                         {
1888                                 std::unique_ptr<_CertificateListInfo> pCertList(new (std::nothrow) _CertificateListInfo());
1889                                 SysTryReturnResult(NID_SEC_CERT, pCertList != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1890
1891                                 memset(pCertList.get(), 0, sizeof(*pCertList.get()));
1892                                 pCertList->pNext = null;
1893
1894                                 r = pFileStore->SetFileHandle(certRecord.certId, _CERT_PATH_CA_CERT);
1895                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
1896
1897                                 r = pFileStore->ReadFromFile(reinterpret_cast< byte* >(pCertList->certificate), pCertList->length);
1898                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to read from file.");
1899                                 certificateBase64Len = _Base64::GetEncodedSize(pCertList->length);
1900
1901                                 if (encodingType == _CERT_ENC_TYPE_PEM)
1902                                 {
1903                                         const byte* pCertBuffer = pCertList->certificate;
1904
1905                                         pBio = BIO_new(BIO_s_mem());
1906                                         SysTryReturnResult(NID_SEC_CERT, pBio != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
1907
1908                                         pCert = d2i_X509(null, &pCertBuffer, pCertList->length);
1909                                         SysTryCatch(NID_SEC_CERT, pCert != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate convertion failed.");
1910
1911                                         readLength = PEM_write_bio_X509(pBio, pCert);
1912                                         SysTryCatch(NID_SEC_CERT, readLength > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate conversion failed");
1913
1914                                         pCertList->length = certificateBase64Len + (2 * _MAX_PEM_HEADER);
1915
1916                                         readLength = BIO_read(pBio, pCertList->certificate, pCertList->length);
1917                                         SysTryCatch(NID_SEC_CERT, readLength > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate conversion failed");
1918
1919                                         pCertList->length = readLength;
1920
1921                                         BIO_free(pBio);
1922                                         pBio = null;
1923
1924                                         X509_free(pCert);
1925                                         pCert = null;
1926                                 }
1927                                 else if (encodingType == _CERT_ENC_TYPE_BASE64)
1928                                 {
1929                                         int certLen = _Base64::GetEncodedSize(pCertList->length);
1930                                         memset(pCertList->certificate + pCertList->length, 0, sizeof(pCertList->certificate) - pCertList->length);
1931                                         r = _Base64::Encode(reinterpret_cast< byte* >(pCertList->certificate), pCertList->length, reinterpret_cast< char* >(pCertList->certificate), certLen);
1932                                         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r),E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
1933                                         pCertList->length = certLen;
1934                                 }
1935                                 pCertList->format = (_CertFormat) certRecord.certFormat;
1936                                 pCertList->certType = (_CaCertType) certRecord.certType;
1937                                 pCertList->certFileId = certRecord.certId;
1938
1939                                 pHoldList->pNext = pCertList.release();
1940                                 pHoldList = pHoldList->pNext;
1941
1942                                 certCount++;
1943
1944                                 memset(subName, 0, _MAX_ISSUER_SUBJECT_NAME_SIZE);
1945                                 memcpy(subName, certRecord.issuerName, certRecord.issuerNameLen);
1946                                 subNameLen = certRecord.issuerNameLen;
1947                         }
1948
1949                 }
1950                 while (strcmp(certRecord.issuerName, certRecord.subjectName));
1951
1952                 if (!isIssuerNameInList)
1953                 {
1954                         if (*ppCertListInfoTypes != null)
1955                         {
1956                                 _CertService::FreeCertList(*ppCertListInfoTypes);
1957                                 *ppCertListInfoTypes = null;
1958                         }
1959
1960                         memset(condition, 0, sizeof(condition));
1961                         sprintf(condition, "installed = '%s'", installedRecord);
1962
1963                         count++;
1964
1965                         memset(&userCertRecord, 0, sizeof(userCertRecord));
1966                         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &userCertRecord);
1967                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
1968
1969                         curCertId = userCertRecord.certId;
1970
1971                         for (readLength = 0; readLength < count; readLength++)
1972                         {
1973
1974                                 memset(&userCertRecord, 0, sizeof(userCertRecord));
1975                                 r = __userCertDbStore.GetNextRecordByCondition(reinterpret_cast< byte* >(condition), &userCertRecord, curCertId);
1976                                 SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificate records.", GetErrorMessage(r));
1977                                 curCertId = userCertRecord.certId;
1978                         }
1979                 }
1980
1981         }
1982         while (isIssuerNameInList != true);
1983
1984 CATCH:
1985         if (pBio != null)
1986         {
1987                 BIO_free(pBio);
1988         }
1989         if (pCert != null)
1990         {
1991                 X509_free(pCert);
1992         }
1993         if (pKey != null)
1994         {
1995                 EVP_PKEY_free(pKey);
1996         }
1997
1998         return r;
1999 }
2000
2001 result
2002 _CertDbManager::GetUserCertificateChain(_CertFormat certFormat, _CertChain* pCertChain, _CertPrivateKeyInfo* pPrivateKeyInfo, char* pSubjectName)
2003 {
2004         result r = E_SUCCESS;
2005         UserCertRecord userCertRecord = {0, };
2006         CaCertRecord caCertRecord = {0, };
2007         int subjNameB64len = 0;
2008         int parentCa = 0;
2009         char subjectNameBase64[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_ISSUER_OFFSET_SIZE] = {0, };
2010         char conditonRecord[_MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE] = {0, };
2011         char installedRecord[_MAX_TYPE_RECORD_SIZE] = "T\0";
2012
2013         subjNameB64len = _Base64::GetEncodedSize(strlen(pSubjectName));
2014         memset(subjectNameBase64, 0, sizeof(subjectNameBase64));
2015         r = _Base64::Encode(reinterpret_cast< byte* >(pSubjectName), strlen(pSubjectName), subjectNameBase64, subjNameB64len);
2016         SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
2017         sprintf(conditonRecord, "subjectName = '%s' and installed = '%s'", subjectNameBase64, installedRecord);
2018
2019         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(conditonRecord), &userCertRecord);
2020         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
2021
2022         if (pPrivateKeyInfo != null)
2023         {
2024                 pPrivateKeyInfo->SetPrivateKey(userCertRecord.prvKeyPath);
2025         }
2026
2027         r = pCertChain->AddCertificate(certFormat, userCertRecord.fileName);
2028         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] AddCertificate failed.", GetErrorMessage(r));
2029
2030         parentCa = userCertRecord.parentCa;
2031
2032         do
2033         {
2034                 memset(&caCertRecord, 0, sizeof(caCertRecord));
2035                 memset(conditonRecord, 0, _MAX_ISSUER_SUBJECT_NAME_SIZE + _MAX_SUBJECT_OFFSET_SIZE);
2036                 sprintf(conditonRecord, "certId = %d and installed = '%s'", parentCa, installedRecord);
2037
2038                 r = __caCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(conditonRecord), &caCertRecord);
2039                 SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
2040
2041                 parentCa = caCertRecord.parentCa;
2042                 if (caCertRecord.certId != caCertRecord.parentCa) //Exclude root certificate from the chain
2043                 {
2044                         r = pCertChain->AddCertificate(certFormat, caCertRecord.fileName);
2045                         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to add certificate in chain.", GetErrorMessage(r));
2046                 }
2047
2048         }
2049         while (caCertRecord.certId != caCertRecord.parentCa);
2050
2051         return E_SUCCESS;
2052 }
2053
2054 result
2055 _CertDbManager::GetUserCertificateInfoByCertId(int certId, int* pSubjectLength, byte* pSubjectName, int* pIssuerLength, byte* pIssuerName)
2056 {
2057         result r = E_SUCCESS;
2058         UserCertRecord userCertRecord = {0, };
2059         char installedRecord[_MAX_TYPE_RECORD_SIZE] = "T\0";
2060         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
2061
2062         sprintf(condition, "certId = %d and installed = '%s'", certId, installedRecord);
2063
2064         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &userCertRecord);
2065         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
2066
2067         *pSubjectLength = userCertRecord.subjectNameLen;
2068         memcpy(pSubjectName, userCertRecord.subjectName, userCertRecord.subjectNameLen);
2069         *pIssuerLength = userCertRecord.issuerNameLen;
2070         memcpy(pIssuerName, userCertRecord.issuerName, userCertRecord.issuerNameLen);
2071
2072         return E_SUCCESS;
2073
2074 }
2075
2076 result
2077 _CertDbManager::GetUserCertificateInfoByCertId(int certId, _CertEncodingType encodingType, _CertInfo** ppUserCertInfo)
2078 {
2079         result r = E_SUCCESS;
2080         char condition[_MAX_TYPE_CONST_SIZE] = {0, };
2081         char installedRecord[_MAX_TYPE_RECORD_SIZE] = "T\0";
2082         int priKeyLen = 0;
2083         int readCount = 0;
2084         int certBufferLen = 0;
2085         int keyBufferLen = 0;
2086         int certificateBase64Len = 0;
2087         const byte* pCertBuffer = null;
2088         const byte* pKeyBuffer = null;
2089         byte* pPrivateTempKey = null;
2090         UserCertRecord certRecord = {0, };
2091         _CertFileStore fileStore;
2092         std::unique_ptr <_CertPrivateKeyInfo> pPriKey;
2093         BIO* pBio = null;
2094         X509* pCert = null;
2095         EVP_PKEY* pKey = null;
2096
2097         *ppUserCertInfo = null;
2098
2099         SysTryReturnResult(NID_SEC_CERT, certId > 0, E_INVALID_ARG, "Invalid input parameter.");
2100         sprintf(condition, "certId = %d and installed = '%s'", certId, installedRecord);
2101
2102         r = __userCertDbStore.GetFirstRecordByConditions(reinterpret_cast< byte* >(condition), &certRecord);
2103         SysTryReturn(NID_SEC_CERT, !IsFailed(r), r, r, "[%s] Failed to get certificates record.", GetErrorMessage(r));
2104
2105         std::unique_ptr <_CertInfo> pCertInfo (new (std::nothrow) _CertInfo);
2106         SysTryCatch(NID_SEC_CERT, pCertInfo != null, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to allocate memory.");
2107
2108         memset(pCertInfo.get(), 0, sizeof(*pCertInfo.get()));
2109
2110         r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_USER_CERT);
2111         SysTryCatch(NID_SEC_CERT, !IsFailed(r), r = E_SYSTEM, E_SYSTEM, "[%s] Failed to set file handle.", GetErrorMessage(r));
2112
2113         r = fileStore.ReadFromFile(reinterpret_cast< byte* >(pCertInfo->certificate), pCertInfo->certLength);
2114         SysTryCatch(NID_SEC_CERT, !IsFailed(r), r = E_SYSTEM, E_SYSTEM, "[%s] Failed to read from file.", GetErrorMessage(r));
2115         certificateBase64Len = _Base64::GetEncodedSize(pCertInfo->certLength);
2116
2117         if (encodingType == _CERT_ENC_TYPE_PEM)
2118         {
2119                 pBio = BIO_new(BIO_s_mem());
2120                 SysTryCatch(NID_SEC_CERT, pBio != null, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to allocate memory.");
2121
2122                 pCertBuffer = new (std::nothrow) byte[pCertInfo->certLength];
2123                 SysTryCatch(NID_SEC_CERT, pCertBuffer != null, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to allocate memory.");
2124
2125                 memcpy((void*) pCertBuffer, pCertInfo->certificate, pCertInfo->certLength);
2126                 certBufferLen = pCertInfo->certLength;
2127
2128                 pCert = d2i_X509(null, &pCertBuffer, certBufferLen);
2129                 SysTryCatch(NID_SEC_CERT, pCert != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate convertion failed.");
2130
2131                 readCount = PEM_write_bio_X509(pBio, pCert);
2132                 SysTryCatch(NID_SEC_CERT, readCount > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate conversion failed");
2133
2134                 pCertInfo->certLength = certificateBase64Len + (2 * _MAX_PEM_HEADER);
2135                 readCount = BIO_read(pBio, pCertInfo->certificate, pCertInfo->certLength);
2136                 SysTryCatch(NID_SEC_CERT, readCount > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Certificate conversion failed");
2137
2138                 pCertInfo->certLength = readCount;
2139         }
2140         else if (encodingType == _CERT_ENC_TYPE_BASE64)
2141         {
2142                 int certLen = _Base64::GetEncodedSize(pCertInfo->certLength);
2143                 memset(pCertInfo->certificate + pCertInfo->certLength, 0, sizeof(pCertInfo->certificate) - pCertInfo->certLength);
2144                 r = _Base64::Encode(reinterpret_cast< byte* >(pCertInfo->certificate), pCertInfo->certLength, reinterpret_cast< char* >(pCertInfo->certificate), certLen);
2145                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
2146                 pCertInfo->certLength = certLen;
2147         }
2148         pCertInfo->certId = certRecord.certId;
2149         pCertInfo->certFormat = (_CertFormat) certRecord.certFormat;
2150         pCertInfo->certType = _CERT_TYPE_USER_CERT;
2151
2152         if (certRecord.prvKeyLen > 0)
2153         {
2154                 pPriKey = std::unique_ptr <_CertPrivateKeyInfo> (new (std::nothrow) _CertPrivateKeyInfo());
2155                 SysTryReturnResult(NID_SEC_CERT, pPriKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
2156
2157                 std::unique_ptr <byte[]> pPrivateKey (new (std::nothrow) byte[_MAX_CERT_PRIVATE_KEY_SIZE]);
2158                 SysTryReturnResult(NID_SEC_CERT, pPrivateKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
2159
2160                 memset(pPrivateKey.get(), 0, _MAX_CERT_PRIVATE_KEY_SIZE);
2161                 r = fileStore.SetFileHandle(certRecord.certId, _CERT_PATH_PRIVATE_KEY);
2162                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_SYSTEM, "Failed to set file handle.");
2163
2164                 r = fileStore.ReadFromFile(reinterpret_cast< byte* >(pPrivateKey.get()), priKeyLen);
2165                 if (!IsFailed(r) && priKeyLen != 0)
2166                 {
2167                         pPriKey->SetPrivateKey(priKeyLen, pPrivateKey.get());
2168
2169                         pCertInfo->privateKeyLen = _Base64::GetEncodedSize(priKeyLen) + _MAX_PEM_HEADER;
2170
2171                         priKeyLen = 0;
2172
2173                         pPrivateKey.reset(null);
2174
2175                         pPriKey->GetPkcs8EncDecKeyN(priKeyLen, &pPrivateTempKey, 0);
2176                         SysTryReturnResult(NID_SEC_CERT, pPrivateTempKey != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
2177
2178                         pPrivateKey = std::unique_ptr<byte[]>(pPrivateTempKey);
2179
2180                         if (encodingType == _CERT_ENC_TYPE_PEM)
2181                         {
2182                                 BIO_free(pBio);
2183
2184                                 pBio = BIO_new(BIO_s_mem());
2185                                 SysTryReturnResult(NID_SEC_CERT, pBio != null, E_OUT_OF_MEMORY, "Failed to allocate memory.");
2186
2187                                 pKeyBuffer = new (std::nothrow) byte[priKeyLen];
2188                                 SysTryCatch(NID_SEC_CERT, pKeyBuffer != null, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Failed to allocate memory.");
2189
2190                                 memcpy((void*) pKeyBuffer, pPrivateKey.get(), priKeyLen);
2191                                 keyBufferLen = priKeyLen;
2192
2193                                 pKey = d2i_PrivateKey(EVP_PKEY_RSA, null, &pKeyBuffer, keyBufferLen);
2194                                 SysTryCatch(NID_SEC_CERT, pKey != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Private key conversion failed");
2195
2196                                 PEM_write_bio_PrivateKey(pBio, pKey, null, null, 0, 0, null);
2197
2198                                 readCount = BIO_read(pBio, pCertInfo->privatekey, pCertInfo->privateKeyLen);
2199                                 SysTryCatch(NID_SEC_CERT, readCount > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] Private Key conversion failed");
2200
2201                                 pCertInfo->privateKeyLen = readCount;
2202                         }
2203                         else if (encodingType == _CERT_ENC_TYPE_BASE64)
2204                         {
2205                                 pCertInfo->privateKeyLen = _Base64::GetEncodedSize(priKeyLen);
2206                                 memset(pCertInfo->privatekey, 0, sizeof(pCertInfo->privatekey));
2207                                 r = _Base64::Encode(reinterpret_cast< byte* >(pPrivateKey.get()), priKeyLen, reinterpret_cast< char* >(pCertInfo->privatekey), pCertInfo->privateKeyLen);
2208                                 SysTryReturnResult(NID_SEC_CERT, !IsFailed(r), E_ENCODING_FAILED, "Failed to encode data in base 64 encoding.");
2209
2210                         }
2211                         else
2212                         {
2213                                 memcpy(pCertInfo->privatekey, pPrivateKey.get(), priKeyLen);
2214                                 pCertInfo->privateKeyLen = priKeyLen;
2215                         }
2216                 }
2217         }
2218
2219         *ppUserCertInfo = pCertInfo.release();
2220
2221 CATCH:
2222
2223         if (encodingType == _CERT_ENC_TYPE_PEM)
2224         {
2225                 BIO_free(pBio);
2226                 X509_free(pCert);
2227                 EVP_PKEY_free(pKey);
2228         }
2229
2230         {
2231         }
2232         return r;
2233 }
2234
2235
2236 } } } //Tizen::Security::Cert