Fix implementation of ckmc_get_*_alias_list.
[platform/core/security/key-manager.git] / src / manager / client-capi / ckmc-manager.cpp
1 /*
2  *  Copyright (c) 2000 - 2014 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  *  Licensed under the Apache License, Version 2.0 (the "License");
5  *  you may not use this file except in compliance with the License.
6  *  You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  *  Unless required by applicable law or agreed to in writing, software
11  *  distributed under the License is distributed on an "AS IS" BASIS,
12  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  *  See the License for the specific language governing permissions and
14  *  limitations under the License
15  *
16  *
17  * @file        ckmc-control.h
18  * @author      Yuseok Jeon(yuseok.jeon@samsung.com)
19  * @version     1.0
20  * @brief       provides conversion methods to C from C++ for key-manager control functions.
21  */
22
23 #include <ckm/ckm-type.h>
24 #include <ckm/ckm-manager.h>
25 #include <ckmc/ckmc-type.h>
26 #include <ckmc/ckmc-manager.h>
27 #include <ckmc/ckmc-error.h>
28 #include <ckmc-type-converter.h>
29 #include <iostream>
30 #include <string.h>
31
32 CKM::Password _tostring(const char *str)
33 {
34         if(str == NULL)
35                 return CKM::Password();
36         return CKM::Password(str);
37 }
38
39 CKM::CertificateShPtr _toCkmCertificate(const ckmc_cert_s *cert)
40 {
41         CKM::RawBuffer buffer(cert->raw_cert, cert->raw_cert + cert->cert_size);
42         CKM::DataFormat dataFormat = static_cast<CKM::DataFormat>(static_cast<int>(cert->data_format));
43         return CKM::Certificate::create(buffer, dataFormat);
44 }
45
46 ckmc_cert_list_s *_toNewCkmCertList(CKM::CertificateShPtrVector &certVector)
47 {
48         int ret;
49         ckmc_cert_list_s *start = NULL;
50         ckmc_cert_list_s *plist = NULL;
51         CKM::CertificateShPtrVector::iterator it;
52         for(it = certVector.begin(); it != certVector.end(); it++) {
53                 CKM::RawBuffer rawBuffer = (*it)->getDER();
54                 unsigned char *rawCert = (unsigned char *) malloc(rawBuffer.size());
55                 memcpy(rawCert, rawBuffer.data(), rawBuffer.size());
56                 ckmc_cert_s *pcert;
57                 ret = ckmc_cert_new(rawCert, rawBuffer.size(), CKMC_FORM_DER, &pcert);
58                 if(pcert == NULL) {
59                         return NULL;
60                 }
61                 if(plist == NULL) {
62                         ret = ckmc_cert_list_new(pcert, &plist);
63                         start = plist; // save the pointer of the first element
64                 }else {
65                         ret = ckmc_cert_list_add(plist, pcert, &plist);
66                 }
67                 if(ret != CKMC_ERROR_NONE) {
68                         ckmc_cert_list_all_free(start);
69                         return NULL;
70                 }
71         }
72         return start;
73 }
74
75 KEY_MANAGER_CAPI
76 int ckmc_save_key(const char *alias, const ckmc_key_s key, const ckmc_policy_s policy)
77 {
78         CKM::ManagerShPtr mgr = CKM::Manager::create();
79
80         if(alias == NULL) {
81                 return CKMC_ERROR_INVALID_PARAMETER;
82         }
83         CKM::Alias ckmAlias(alias);
84
85         if(key.raw_key == NULL || key.key_size <= 0) {
86                         return CKMC_ERROR_INVALID_PARAMETER;
87         }
88         CKM::RawBuffer buffer(key.raw_key, key.raw_key + key.key_size);
89         CKM::KeyShPtr ckmKey = CKM::Key::create(buffer, _tostring(key.password));
90
91         if(ckmKey.get() == NULL) {
92                 return CKMC_ERROR_INVALID_FORMAT;
93         }
94
95         CKM::Policy storePolicy(_tostring(policy.password), policy.extractable, policy.restricted);
96
97         int ret =  mgr->saveKey(ckmAlias, ckmKey, storePolicy);
98         return to_ckmc_error(ret);
99 }
100
101
102 KEY_MANAGER_CAPI
103 int ckmc_remove_key(const char *alias)
104 {
105         CKM::ManagerShPtr mgr = CKM::Manager::create();
106
107         if(alias == NULL) {
108                 return CKMC_ERROR_INVALID_PARAMETER;
109         }
110         CKM::Alias ckmAlias(alias);
111
112         int ret =  mgr->removeKey(ckmAlias);
113         return to_ckmc_error(ret);
114 }
115
116 KEY_MANAGER_CAPI
117 int ckmc_get_key(const char *alias, const char *password, ckmc_key_s **key)
118 {
119         int ret;
120         CKM::KeyShPtr ckmKey;
121
122         if(alias == NULL || key == NULL) {
123                 return CKMC_ERROR_INVALID_PARAMETER;
124         }
125         CKM::Alias ckmAlias(alias);
126
127         CKM::ManagerShPtr mgr = CKM::Manager::create();
128         if( (ret = mgr->getKey(ckmAlias, _tostring(password), ckmKey)) != CKM_API_SUCCESS) {
129                 return to_ckmc_error(ret);
130         }
131
132         unsigned char *rawKey = reinterpret_cast<unsigned char*>(ckmKey->getDER().data());
133         ckmc_key_type_e keyType = static_cast<ckmc_key_type_e>(static_cast<int>(ckmKey->getType()));
134
135         ret = ckmc_key_new( rawKey, ckmKey->getDER().size(), keyType, NULL, key);
136
137         return to_ckmc_error(ret);
138 }
139
140 KEY_MANAGER_CAPI
141 int ckmc_get_key_alias_list(ckmc_alias_list_s** alias_list)
142 {
143     int ret;
144
145     if (alias_list == NULL) {
146         return CKMC_ERROR_INVALID_PARAMETER;
147     }
148
149     CKM::AliasVector aliasVector;
150     CKM::ManagerShPtr mgr = CKM::Manager::create();
151
152     if ((ret = mgr->getKeyAliasVector(aliasVector)) != CKM_API_SUCCESS) {
153         return to_ckmc_error(ret);
154     }
155
156     ckmc_alias_list_s *plist = NULL;
157
158     for (auto it = aliasVector.begin(); it != aliasVector.end(); it++) {
159         char *alias = strndup(it->c_str(), it->size());
160
161         if (plist == NULL) { // first
162             ret = ckmc_alias_list_new(alias, &plist);
163             *alias_list = plist; // save the pointer of the first element
164         } else {
165             ret = ckmc_alias_list_add(plist, alias, &plist);
166         }
167
168         if (ret != CKMC_ERROR_NONE) {
169             free(alias);
170             ckmc_alias_list_all_free(*alias_list);
171             return ret;
172         }
173     }
174
175     return CKMC_ERROR_NONE;
176 }
177
178 KEY_MANAGER_CAPI
179 int ckmc_save_cert(const char *alias, const ckmc_cert_s cert, const ckmc_policy_s policy)
180 {
181         if(alias == NULL) {
182                 return CKMC_ERROR_INVALID_PARAMETER;
183         }
184         CKM::Alias ckmAlias(alias);
185
186         if(cert.raw_cert == NULL || cert.cert_size <= 0) {
187                         return CKMC_ERROR_INVALID_PARAMETER;
188         }
189         CKM::CertificateShPtr ckmCert = _toCkmCertificate(&cert);
190         if(ckmCert.get() == NULL) {
191                 return CKMC_ERROR_INVALID_FORMAT;
192         }
193
194         CKM::Policy storePolicy(_tostring(policy.password), policy.extractable, policy.restricted);
195
196         CKM::ManagerShPtr mgr = CKM::Manager::create();
197         int ret = mgr->saveCertificate(ckmAlias, ckmCert, storePolicy);
198
199         return to_ckmc_error(ret);
200 }
201
202 KEY_MANAGER_CAPI
203 int ckmc_remove_cert(const char *alias)
204 {
205         if(alias == NULL) {
206                 return CKMC_ERROR_INVALID_PARAMETER;
207         }
208         CKM::Alias ckmAlias(alias);
209
210         CKM::ManagerShPtr mgr = CKM::Manager::create();
211         int ret = mgr->removeCertificate(ckmAlias);
212
213         return to_ckmc_error(ret);
214 }
215
216 KEY_MANAGER_CAPI
217 int ckmc_get_cert(const char *alias, const char *password, ckmc_cert_s **cert)
218 {
219         CKM::CertificateShPtr ckmCert;
220         int ret;
221
222         if(alias == NULL || cert == NULL) {
223                 return CKMC_ERROR_INVALID_PARAMETER;
224         }
225         CKM::Alias ckmAlias(alias);
226
227         CKM::ManagerShPtr mgr = CKM::Manager::create();
228         if( (ret = mgr->getCertificate(ckmAlias, _tostring(password), ckmCert)) != CKM_API_SUCCESS) {
229                 return to_ckmc_error(ret);
230         }
231
232         unsigned char *rawCert = reinterpret_cast<unsigned char*>(ckmCert->getDER().data());
233         ret = ckmc_cert_new( rawCert, ckmCert->getDER().size(), CKMC_FORM_DER, cert);
234
235         return ret;
236 }
237
238 KEY_MANAGER_CAPI
239 int ckmc_get_cert_alias_list(ckmc_alias_list_s** alias_list) {
240     int ret;
241
242     if (alias_list == NULL) {
243         return CKMC_ERROR_INVALID_PARAMETER;
244     }
245
246     *alias_list = NULL;
247
248     CKM::AliasVector aliasVector;
249     CKM::ManagerShPtr mgr = CKM::Manager::create();
250     if ((ret = mgr->getCertificateAliasVector(aliasVector)) != CKM_API_SUCCESS) {
251         return to_ckmc_error(ret);
252     }
253
254     ckmc_alias_list_s *plist = NULL;
255
256     for (auto it = aliasVector.begin(); it != aliasVector.end(); it++) {
257         char *alias = strndup(it->c_str(), it->size());
258
259         if (plist == NULL) { // first
260             ret  = ckmc_alias_list_new(alias, &plist);
261             *alias_list = plist; // save the pointer of the first element
262         } else {
263             ret = ckmc_alias_list_add(plist, alias, &plist);
264         }
265
266         if (ret != CKMC_ERROR_NONE) {
267             free(alias);
268             ckmc_alias_list_all_free(*alias_list);
269             return ret;
270         }
271     }
272
273     return CKMC_ERROR_NONE;
274 }
275
276 KEY_MANAGER_CAPI
277 int ckmc_save_data(const char *alias, ckmc_raw_buffer_s data, const ckmc_policy_s policy)
278 {
279         if(alias == NULL) {
280                 return CKMC_ERROR_INVALID_PARAMETER;
281         }
282         CKM::Alias ckmAlias(alias);
283
284         if(data.data == NULL || data.size <= 0) {
285                         return CKMC_ERROR_INVALID_PARAMETER;
286         }
287         CKM::RawBuffer buffer(data.data, data.data + data.size);
288
289         CKM::Policy storePolicy(_tostring(policy.password), policy.extractable, policy.restricted);
290
291         CKM::ManagerShPtr mgr = CKM::Manager::create();
292         int ret = mgr->saveData(ckmAlias, buffer, storePolicy);
293
294         return to_ckmc_error(ret);
295 }
296
297 KEY_MANAGER_CAPI
298 int ckmc_remove_data(const char *alias)
299 {
300         if(alias == NULL) {
301                 return CKMC_ERROR_INVALID_PARAMETER;
302         }
303         CKM::Alias ckmAlias(alias);
304
305         CKM::ManagerShPtr mgr = CKM::Manager::create();
306         int ret = mgr->removeData(ckmAlias);
307         return to_ckmc_error(ret);
308 }
309
310 KEY_MANAGER_CAPI
311 int ckmc_get_data(const char *alias, const char *password, ckmc_raw_buffer_s **data)
312 {
313         CKM::RawBuffer ckmBuff;
314         int ret;
315
316         if(alias == NULL || data == NULL) {
317                 return CKMC_ERROR_INVALID_PARAMETER;
318         }
319         CKM::Alias ckmAlias(alias);
320
321         CKM::ManagerShPtr mgr = CKM::Manager::create();
322         if( (ret = mgr->getData(ckmAlias, _tostring(password), ckmBuff)) != CKM_API_SUCCESS) {
323                 return to_ckmc_error(ret);
324         }
325
326         unsigned char *rawBuff = reinterpret_cast<unsigned char*>(ckmBuff.data());
327         ret = ckmc_buffer_new(rawBuff, ckmBuff.size(), data);
328
329         return ret;
330 }
331
332 KEY_MANAGER_CAPI
333 int ckmc_get_data_alias_list(ckmc_alias_list_s** alias_list){
334     int ret;
335
336     if(alias_list == NULL) {
337         return CKMC_ERROR_INVALID_PARAMETER;
338     }
339
340     *alias_list = NULL;
341
342     CKM::AliasVector aliasVector;
343     CKM::ManagerShPtr mgr = CKM::Manager::create();
344     if( (ret = mgr->getDataAliasVector(aliasVector)) != CKM_API_SUCCESS) {
345         return to_ckmc_error(ret);
346     }
347
348     ckmc_alias_list_s *plist = NULL;
349
350     for(auto it = aliasVector.begin(); it != aliasVector.end(); it++) {
351         char *alias = strndup(it->c_str(), it->size());
352
353         if (plist == NULL) { // first
354             ret = ckmc_alias_list_new(alias, &plist);
355             *alias_list = plist; // save the pointer of the first element
356         } else {
357             ret = ckmc_alias_list_add(plist, alias, &plist);
358         }
359
360         if (ret != CKMC_ERROR_NONE) {
361             free(alias);
362             ckmc_alias_list_all_free(*alias_list);
363             return ret;
364         }
365     }
366
367     return CKMC_ERROR_NONE;
368 }
369
370 KEY_MANAGER_CAPI
371 int ckmc_create_key_pair_rsa(const size_t size,
372                                                         const char *private_key_alias,
373                                                         const char *public_key_alias,
374                                                         const ckmc_policy_s policy_private_key,
375                                                         const ckmc_policy_s policy_public_key)
376 {
377         int ret;
378         CKM::ManagerShPtr mgr = CKM::Manager::create();
379
380         if(private_key_alias == NULL || public_key_alias == NULL) {
381                 return CKMC_ERROR_INVALID_PARAMETER;
382         }
383
384         CKM::Alias ckmPrivakeKeyAlias(private_key_alias);
385         CKM::Alias ckmPublicKeyAlias(public_key_alias);
386         CKM::Policy ckmPrivateKeyPolicy(_tostring(policy_private_key.password), policy_private_key.extractable, policy_private_key.restricted);
387         CKM::Policy ckmPublicKeyPolicy(_tostring(policy_public_key.password), policy_public_key.extractable, policy_public_key.restricted);
388
389         ret = mgr->createKeyPairRSA(size, ckmPrivakeKeyAlias, ckmPublicKeyAlias, ckmPrivateKeyPolicy, ckmPublicKeyPolicy);
390         return to_ckmc_error(ret);
391 }
392
393 KEY_MANAGER_CAPI
394 int ckmc_create_key_pair_ecdsa(const ckmc_ec_type_e type,
395                                                         const char *private_key_alias,
396                                                         const char *public_key_alias,
397                                                         const ckmc_policy_s policy_private_key,
398                                                         const ckmc_policy_s policy_public_key)
399 {
400         CKM::ManagerShPtr mgr = CKM::Manager::create();
401
402         if(private_key_alias == NULL || public_key_alias == NULL) {
403                 return CKMC_ERROR_INVALID_PARAMETER;
404         }
405
406         CKM::ElipticCurve ckmType = static_cast<CKM::ElipticCurve>(static_cast<int>(type));
407         CKM::Alias ckmPrivakeKeyAlias(private_key_alias);
408         CKM::Alias ckmPublicKeyAlias(public_key_alias);
409         CKM::Policy ckmPrivateKeyPolicy(_tostring(policy_private_key.password), policy_private_key.extractable, policy_private_key.restricted);
410         CKM::Policy ckmPublicKeyPolicy(_tostring(policy_public_key.password), policy_public_key.extractable, policy_public_key.restricted);
411
412         int ret = mgr->createKeyPairECDSA(ckmType, ckmPrivakeKeyAlias, ckmPublicKeyAlias, ckmPrivateKeyPolicy, ckmPublicKeyPolicy);
413         return to_ckmc_error(ret);
414 }
415
416 KEY_MANAGER_CAPI
417 int ckmc_create_signature(const char *private_key_alias,
418                                                         const char *password,
419                                                         const ckmc_raw_buffer_s message,
420                                                         const ckmc_hash_algo_e hash,
421                                                         const ckmc_rsa_padding_algo_e padding,
422                                                         ckmc_raw_buffer_s **signature)
423 {
424         int ret;
425         CKM::ManagerShPtr mgr = CKM::Manager::create();
426         CKM::RawBuffer ckmSignature;
427
428         if(private_key_alias == NULL || signature == NULL) {
429                 return CKMC_ERROR_INVALID_PARAMETER;
430         }
431
432         CKM::Alias ckmPrivakeKeyAlias(private_key_alias);
433         CKM::RawBuffer ckmMessage(message.data, message.data + message.size);
434         CKM::HashAlgorithm ckmHashAlgo = static_cast<CKM::HashAlgorithm>(static_cast<int>(hash));
435         CKM::RSAPaddingAlgorithm ckmPadding = static_cast<CKM::RSAPaddingAlgorithm>(static_cast<int>(padding));
436
437         if( (ret = mgr->createSignature(
438                         ckmPrivakeKeyAlias,
439                         _tostring(password),
440                         ckmMessage,
441                         ckmHashAlgo,
442                         ckmPadding,
443                         ckmSignature)) != CKM_API_SUCCESS) {
444                 return to_ckmc_error(ret);
445         }
446
447         unsigned char *rawBuff = reinterpret_cast<unsigned char*>(ckmSignature.data());
448         ret = ckmc_buffer_new( rawBuff, ckmSignature.size(), signature);
449
450         return ret;
451 }
452
453 KEY_MANAGER_CAPI
454 int ckmc_verify_signature(const char *public_key_alias,
455                                                         const char *password,
456                                                         const ckmc_raw_buffer_s message,
457                                                         const ckmc_raw_buffer_s signature,
458                                                         const ckmc_hash_algo_e hash,
459                                                         const ckmc_rsa_padding_algo_e padding)
460 {
461         int ret;
462         CKM::ManagerShPtr mgr = CKM::Manager::create();
463
464         if(public_key_alias == NULL) {
465                 return CKMC_ERROR_INVALID_PARAMETER;
466         }
467
468         CKM::Alias ckmPublicKeyAlias(public_key_alias);
469         CKM::RawBuffer ckmMessage(message.data, message.data + message.size);
470         CKM::RawBuffer ckmSignature(signature.data, signature.data + signature.size);
471         CKM::HashAlgorithm ckmHashAlgo = static_cast<CKM::HashAlgorithm>(static_cast<int>(hash));
472         CKM::RSAPaddingAlgorithm ckmPadding = static_cast<CKM::RSAPaddingAlgorithm>(static_cast<int>(padding));
473
474         if( (ret = mgr->verifySignature(
475                         ckmPublicKeyAlias,
476                         _tostring(password),
477                         ckmMessage,
478                         ckmSignature,
479                         ckmHashAlgo,
480                         ckmPadding)) != CKM_API_SUCCESS) {
481                 return to_ckmc_error(ret);
482         }
483
484         return CKMC_ERROR_NONE;
485 }
486
487 KEY_MANAGER_CAPI
488 int ckmc_get_cert_chain(const ckmc_cert_s *cert, const ckmc_cert_list_s *untrustedcerts, ckmc_cert_list_s **cert_chain_list)
489 {
490         int ret;
491         CKM::ManagerShPtr mgr = CKM::Manager::create();
492         CKM::CertificateShPtrVector ckmCertChain;
493
494         if(cert == NULL || cert->raw_cert == NULL || cert->cert_size <= 0 || cert_chain_list == NULL) {
495                 return CKMC_ERROR_INVALID_PARAMETER;
496         }
497
498         CKM::CertificateShPtr ckmCert = _toCkmCertificate(cert);
499
500         CKM::CertificateShPtrVector ckmUntrustedCerts;
501         if(untrustedcerts != NULL) {
502                 ckmc_cert_list_s *current = NULL;
503                 ckmc_cert_list_s *next = const_cast<ckmc_cert_list_s *>(untrustedcerts);
504                 do {
505                         current = next;
506                         next = current->next;
507
508                         if(current->cert == NULL){
509                                 continue;
510                         }
511
512                         CKM::CertificateShPtr tmpCkmCert = _toCkmCertificate(current->cert);
513                         ckmUntrustedCerts.push_back(tmpCkmCert);
514                 }while(next != NULL);
515         }
516
517         ret = mgr->getCertificateChain(ckmCert, ckmUntrustedCerts, ckmCertChain);
518         if( ret != CKM_API_SUCCESS) {
519                 return to_ckmc_error(ret);
520         }
521
522         *cert_chain_list = _toNewCkmCertList(ckmCertChain);
523
524         return CKMC_ERROR_NONE;
525 }
526
527 KEY_MANAGER_CAPI
528 int ckmc_get_cert_chain_with_alias(const ckmc_cert_s *cert, const ckmc_alias_list_s *untrustedcerts, ckmc_cert_list_s **cert_chain_list)
529 {
530         int ret;
531         CKM::ManagerShPtr mgr = CKM::Manager::create();
532         CKM::CertificateShPtrVector ckmCertChain;
533
534
535         if(cert == NULL || cert->raw_cert == NULL || cert->cert_size <= 0 || cert_chain_list == NULL) {
536                 return CKMC_ERROR_INVALID_PARAMETER;
537         }
538
539     CKM::CertificateShPtr ckmCert = _toCkmCertificate(cert);
540         if(ckmCert.get() == NULL) {
541                 return CKMC_ERROR_INVALID_FORMAT;
542         }
543
544         CKM::AliasVector ckmUntrustedAliases;
545         if(untrustedcerts != NULL) {
546                 ckmc_alias_list_s *current = NULL;
547                 ckmc_alias_list_s *next = const_cast<ckmc_alias_list_s *>(untrustedcerts);
548                 do {
549                         current = next;
550                         next = current->next;
551
552                         if(current->alias == NULL){
553                                 return CKMC_ERROR_INVALID_PARAMETER;
554                         }
555                         CKM::Alias ckmAlias(current->alias);
556                         ckmUntrustedAliases.push_back(ckmAlias);
557                 }while(next != NULL);
558         }
559
560         if( (ret = mgr->getCertificateChain(ckmCert, ckmUntrustedAliases, ckmCertChain)) != CKM_API_SUCCESS) {
561                 return to_ckmc_error(ret);
562         }
563
564         *cert_chain_list = _toNewCkmCertList(ckmCertChain);
565
566         return CKMC_ERROR_NONE;
567 }
568