2 * Copyright (c) 2000 - 2014 Samsung Electronics Co., Ltd All Rights Reserved
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
8 * http://www.apache.org/licenses/LICENSE-2.0
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
18 * @author Bartlomiej Grzelewski (b.grzelewski@samsung.com)
20 * @brief Sample service implementation.
22 #include <dpl/serialization.h>
23 #include <dpl/log/log.h>
24 #include <ckm/ckm-error.h>
25 #include <ckm/ckm-type.h>
26 #include <key-provider.h>
27 #include <file-system.h>
28 #include <CryptoService.h>
29 #include <ckm-logic.h>
33 const char * const CERT_SYSTEM_DIR = "/etc/ssl/certs";
34 } // anonymous namespace
40 int retCode = FileSystem::init();
41 // TODO what can I do when init went wrong? exit(-1) ??
43 LogError("Fatal error in FileSystem::init()");
46 if (CKM_API_SUCCESS != m_certStore.setSystemCertificateDir(CERT_SYSTEM_DIR)) {
47 LogError("Fatal error in CertificateStore::setSystemCertificateDir. Chain creation will not work");
50 cc_mode_status = CCModeState::CC_MODE_OFF;
53 CKMLogic::~CKMLogic(){}
55 RawBuffer CKMLogic::unlockUserKey(uid_t user, const Password &password) {
56 // TODO try catch for all errors that should be supported by error code
57 int retCode = CKM_API_SUCCESS;
60 if (0 == m_userDataMap.count(user) || !(m_userDataMap[user].keyProvider.isInitialized())) {
61 auto &handle = m_userDataMap[user];
63 auto wrappedDomainKEK = fs.getDKEK();
65 if (wrappedDomainKEK.empty()) {
66 wrappedDomainKEK = KeyProvider::generateDomainKEK(std::to_string(user), password);
67 fs.saveDKEK(wrappedDomainKEK);
70 handle.keyProvider = KeyProvider(wrappedDomainKEK, password);
72 auto wrappedDatabaseDEK = fs.getDBDEK();
74 if (wrappedDatabaseDEK.empty()) {
75 wrappedDatabaseDEK = handle.keyProvider.generateDEK(std::to_string(user));
76 fs.saveDBDEK(wrappedDatabaseDEK);
79 RawBuffer key = handle.keyProvider.getPureDEK(wrappedDatabaseDEK);
80 handle.database = DBCrypto(fs.getDBPath(), key);
81 handle.crypto = CryptoLogic();
83 // remove data of removed apps during locked state
84 AppLabelVector removedApps = fs.clearRemovedsApps();
85 for(auto& appSmackLabel : removedApps) {
86 handle.database.deleteKey(appSmackLabel);
91 } catch (const KeyProvider::Exception::PassWordError &e) {
92 LogError("Incorrect Password " << e.GetMessage());
93 retCode = CKM_API_ERROR_AUTHENTICATION_FAILED;
94 } catch (const KeyProvider::Exception::Base &e) {
95 LogError("Error in KeyProvider " << e.GetMessage());
96 retCode = CKM_API_ERROR_SERVER_ERROR;
97 } catch (const CryptoLogic::Exception::Base &e) {
98 LogError("CryptoLogic error: " << e.GetMessage());
99 retCode = CKM_API_ERROR_SERVER_ERROR;
100 } catch (const CKM::Exception &e) {
101 LogError("CKM::Exception: " << e.GetMessage());
102 retCode = CKM_API_ERROR_SERVER_ERROR;
105 if(retCode != CKM_API_SUCCESS) {
106 // When not successful, UserData in m_userDataMap should be erased.
107 // Because other operations make decision based on the existence of UserData in m_userDataMap.
108 m_userDataMap.erase(user);
111 return MessageBuffer::Serialize(retCode).Pop();
114 RawBuffer CKMLogic::setCCModeStatus(CCModeState mode_status) {
116 int retCode = CKM_API_SUCCESS;
117 int fipsModeStatus = 0;
120 if((mode_status != CCModeState:: CC_MODE_OFF) && (mode_status != CCModeState:: CC_MODE_ON)) {
121 retCode = CKM_API_ERROR_INPUT_PARAM;
124 cc_mode_status = mode_status;
125 fipsModeStatus = FIPS_mode();
127 if(cc_mode_status == CCModeState:: CC_MODE_ON) {
128 if(fipsModeStatus == 0) { // If FIPS mode off
129 rc = FIPS_mode_set(1); // Change FIPS_mode from off to on
131 LogError("Error in FIPS_mode_set function");
135 if(fipsModeStatus == 1) { // If FIPS mode on
136 rc = FIPS_mode_set(0); // Change FIPS_mode from on to off
138 LogError("Error in FIPS_mode_set function");
143 return MessageBuffer::Serialize(retCode).Pop();
146 RawBuffer CKMLogic::lockUserKey(uid_t user) {
147 int retCode = CKM_API_SUCCESS;
148 // TODO try catch for all errors that should be supported by error code
149 m_userDataMap.erase(user);
151 return MessageBuffer::Serialize(retCode).Pop();
155 RawBuffer CKMLogic::removeUserData(uid_t user) {
156 int retCode = CKM_API_SUCCESS;
157 // TODO try catch for all errors that should be supported by error code
158 m_userDataMap.erase(user);
163 return MessageBuffer::Serialize(retCode).Pop();
166 RawBuffer CKMLogic::changeUserPassword(
168 const Password &oldPassword,
169 const Password &newPassword)
171 int retCode = CKM_API_SUCCESS;
174 auto wrappedDomainKEK = fs.getDKEK();
175 if (wrappedDomainKEK.empty()) {
176 retCode = CKM_API_ERROR_BAD_REQUEST;
178 wrappedDomainKEK = KeyProvider::reencrypt(wrappedDomainKEK, oldPassword, newPassword);
179 fs.saveDKEK(wrappedDomainKEK);
181 } catch (const KeyProvider::Exception::PassWordError &e) {
182 LogError("Incorrect Password " << e.GetMessage());
183 retCode = CKM_API_ERROR_AUTHENTICATION_FAILED;
184 } catch (const KeyProvider::Exception::Base &e) {
185 LogError("Error in KeyProvider " << e.GetMessage());
186 retCode = CKM_API_ERROR_SERVER_ERROR;
187 } catch (const CKM::Exception &e) {
188 LogError("CKM::Exception: " << e.GetMessage());
189 retCode = CKM_API_ERROR_SERVER_ERROR;
192 return MessageBuffer::Serialize(retCode).Pop();
195 RawBuffer CKMLogic::resetUserPassword(
197 const Password &newPassword)
199 int retCode = CKM_API_SUCCESS;
201 if (0 == m_userDataMap.count(user)) {
202 retCode = CKM_API_ERROR_BAD_REQUEST;
204 auto &handler = m_userDataMap[user];
206 fs.saveDKEK(handler.keyProvider.getWrappedDomainKEK(newPassword));
209 return MessageBuffer::Serialize(retCode).Pop();
212 RawBuffer CKMLogic::removeApplicationData(const std::string &smackLabel) {
213 int retCode = CKM_API_SUCCESS;
217 if (smackLabel.empty()) {
218 retCode = CKM_API_ERROR_INPUT_PARAM;
220 UidVector uids = FileSystem::getUIDsFromDBFile();
221 for (auto userId : uids) {
222 if (0 == m_userDataMap.count(userId)) {
223 FileSystem fs(userId);
224 fs.addRemovedApp(smackLabel);
226 auto &handle = m_userDataMap[userId];
227 handle.database.deleteKey(smackLabel);
232 } catch (const DBCrypto::Exception::InternalError &e) {
233 LogError("DBCrypto couldn't remove data: " << e.GetMessage());
234 retCode = CKM_API_ERROR_DB_ERROR;
235 } catch (const DBCrypto::Exception::TransactionError &e) {
236 LogError("DBCrypto transaction failed with message " << e.GetMessage());
237 retCode = CKM_API_ERROR_DB_ERROR;
240 return MessageBuffer::Serialize(retCode).Pop();
243 int CKMLogic::saveDataHelper(
247 const RawBuffer &key,
248 const PolicySerializable &policy)
250 if (0 == m_userDataMap.count(cred.uid))
251 return CKM_API_ERROR_DB_LOCKED;
253 // proceed to data save
254 DBRow row = { alias, cred.smackLabel,
255 policy.extractable, dataType, DBCMAlgType::NONE,
256 0, RawBuffer(), static_cast<int>(key.size()), key, RawBuffer() };
258 auto &handler = m_userDataMap[cred.uid];
259 DBCrypto::Transaction transaction(&handler.database);
260 if (!handler.crypto.haveKey(cred.smackLabel)) {
262 auto key_optional = handler.database.getKey(cred.smackLabel);
264 LogDebug("No Key in database found. Generating new one for label: "
266 key = handler.keyProvider.generateDEK(cred.smackLabel);
267 handler.database.saveKey(cred.smackLabel, key);
269 LogDebug("Key from DB");
273 key = handler.keyProvider.getPureDEK(key);
274 handler.crypto.pushKey(cred.smackLabel, key);
277 // Do not encrypt data with password during cc_mode on
278 if(cc_mode_status == CCModeState::CC_MODE_ON) {
279 handler.crypto.encryptRow("", row);
281 handler.crypto.encryptRow(policy.password, row);
284 handler.database.saveDBRow(row);
285 transaction.commit();
286 return CKM_API_SUCCESS;
289 void CKMLogic::verifyBinaryData(DBDataType dataType, const RawBuffer &input_data) const
291 // verify the data integrity
294 case DBDataType::KEY_RSA_PUBLIC:
295 case DBDataType::KEY_RSA_PRIVATE:
296 case DBDataType::KEY_ECDSA_PUBLIC:
297 case DBDataType::KEY_ECDSA_PRIVATE:
298 case DBDataType::KEY_DSA_PUBLIC:
299 case DBDataType::KEY_DSA_PRIVATE:
300 case DBDataType::KEY_AES:
302 KeyShPtr output_key = CKM::Key::create(input_data);
303 if(output_key.get() == NULL)
304 ThrowMsg(CKMLogic::Exception::InputDataInvalid, "provided binary data is not valid key data");
308 case DBDataType::CERTIFICATE:
310 CertificateShPtr cert = CKM::Certificate::create(input_data, DataFormat::FORM_DER);
311 if(cert.get() == NULL)
312 ThrowMsg(CKMLogic::Exception::InputDataInvalid, "provided binary data is not valid certificate data");
316 // TODO: add here BINARY_DATA verification, i.e: max size etc.
322 RawBuffer CKMLogic::saveData(
327 const RawBuffer &key,
328 const PolicySerializable &policy)
330 int retCode = CKM_API_SUCCESS;
332 verifyBinaryData(dataType, key);
334 retCode = saveDataHelper(cred, dataType, alias, key, policy);
335 LogDebug("SaveDataHelper returned: " << retCode);
336 } catch (const CKMLogic::Exception::InputDataInvalid &e) {
337 LogError("Provided data invalid: " << e.GetMessage());
338 retCode = CKM_API_ERROR_INPUT_PARAM;
339 } catch (const KeyProvider::Exception::Base &e) {
340 LogError("KeyProvider failed with message: " << e.GetMessage());
341 retCode = CKM_API_ERROR_SERVER_ERROR;
342 } catch (const CryptoLogic::Exception::Base &e) {
343 LogError("CryptoLogic failed with message: " << e.GetMessage());
344 retCode = CKM_API_ERROR_SERVER_ERROR;
345 } catch (const DBCrypto::Exception::InternalError &e) {
346 LogError("DBCrypto failed with message: " << e.GetMessage());
347 retCode = CKM_API_ERROR_DB_ERROR;
348 } catch (const DBCrypto::Exception::AliasExists &e) {
349 LogError("DBCrypto couldn't save duplicate alias");
350 retCode = CKM_API_ERROR_DB_ALIAS_EXISTS;
351 } catch (const DBCrypto::Exception::TransactionError &e) {
352 LogError("DBCrypto transaction failed with message " << e.GetMessage());
353 retCode = CKM_API_ERROR_DB_ERROR;
356 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::SAVE),
359 static_cast<int>(dataType));
360 return response.Pop();
363 RawBuffer CKMLogic::removeData(
368 const std::string &label)
370 int retCode = CKM_API_SUCCESS;
372 if (0 < m_userDataMap.count(cred.uid)) {
374 // use client label if not explicitly provided
375 const std::string & label_to_use = label.empty()?cred.smackLabel:label;
377 // verify alias and label are correct
378 if (true == checkAliasAndLabelValid(alias, label_to_use))
380 auto erased = m_userDataMap[cred.uid].database.deleteDBRow(alias, label_to_use);
381 // check if the data existed or not
383 LogError("No row for given alias and label");
384 retCode = CKM_API_ERROR_DB_ALIAS_UNKNOWN;
389 LogError("Invalid label or alias format");
390 retCode = CKM_API_ERROR_INPUT_PARAM;
392 } Catch (DBCrypto::Exception::PermissionDenied) {
393 LogError("Error: not enough permissions!");
394 retCode = CKM_API_ERROR_ACCESS_DENIED;
395 } Catch (CKM::Exception) {
396 LogError("Error in deleting row!");
397 retCode = CKM_API_ERROR_DB_ERROR;
400 retCode = CKM_API_ERROR_DB_LOCKED;
403 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::REMOVE),
406 static_cast<int>(dataType));
407 return response.Pop();
410 bool CKMLogic::checkAliasAndLabelValid(const Alias &alias, const std::string &label)
412 // verify the alias is valid
413 if(alias.find(':') != std::string::npos)
416 // verify the label is valid
417 if(label.find(LABEL_ALIAS_SEPARATOR) != std::string::npos)
423 int CKMLogic::getDataHelper(
427 const std::string &label,
428 const Password &password,
431 if (0 == m_userDataMap.count(cred.uid))
432 return CKM_API_ERROR_DB_LOCKED;
434 auto &handler = m_userDataMap[cred.uid];
436 // use client label if not explicitly provided
437 const std::string & label_to_use = label.empty()?cred.smackLabel:label;
439 // verify alias and label are correct
440 if (true != checkAliasAndLabelValid(alias, label_to_use))
441 return CKM_API_ERROR_INPUT_PARAM;
443 DBCrypto::DBRowOptional row_optional;
444 if (dataType == DBDataType::CERTIFICATE || dataType == DBDataType::BINARY_DATA)
446 row_optional = handler.database.getDBRow(alias, label_to_use, dataType);
448 else if ((static_cast<int>(dataType) >= static_cast<int>(DBDataType::DB_KEY_FIRST)) &&
449 (static_cast<int>(dataType) <= static_cast<int>(DBDataType::DB_KEY_LAST)))
451 row_optional = handler.database.getKeyDBRow(alias, label_to_use);
454 LogError("Unknown type of requested data" << (int)dataType);
455 return CKM_API_ERROR_BAD_REQUEST;
458 LogError("No row for given alias, label and type");
459 return CKM_API_ERROR_DB_ALIAS_UNKNOWN;
464 if (!handler.crypto.haveKey(row.smackLabel)) {
466 auto key_optional = handler.database.getKey(row.smackLabel);
468 LogError("No key for given label in database");
469 return CKM_API_ERROR_DB_ERROR;
472 key = handler.keyProvider.getPureDEK(key);
473 handler.crypto.pushKey(cred.smackLabel, key);
475 handler.crypto.decryptRow(password, row);
477 return CKM_API_SUCCESS;
480 RawBuffer CKMLogic::getData(
485 const std::string &label,
486 const Password &password)
488 int retCode = CKM_API_SUCCESS;
492 retCode = getDataHelper(cred, dataType, alias, label, password, row);
493 } catch (const KeyProvider::Exception::Base &e) {
494 LogError("KeyProvider failed with error: " << e.GetMessage());
495 retCode = CKM_API_ERROR_SERVER_ERROR;
496 } catch (const CryptoLogic::Exception::Base &e) {
497 LogError("CryptoLogic failed with message: " << e.GetMessage());
498 retCode = CKM_API_ERROR_SERVER_ERROR;
499 } catch (const DBCrypto::Exception::PermissionDenied &e) {
500 LogError("DBCrypto failed with message: " << e.GetMessage());
501 retCode = CKM_API_ERROR_ACCESS_DENIED;
502 } catch (const DBCrypto::Exception::Base &e) {
503 LogError("DBCrypto failed with message: " << e.GetMessage());
504 retCode = CKM_API_ERROR_DB_ERROR;
507 if (CKM_API_SUCCESS != retCode) {
509 row.dataType = dataType;
512 if ((CKM_API_SUCCESS == retCode) && (row.exportable == 0)) {
514 retCode = CKM_API_ERROR_NOT_EXPORTABLE;
517 // Prevent extracting private keys during cc-mode on
518 if((cc_mode_status == CCModeState::CC_MODE_ON) && (row.dataType == DBDataType::KEY_RSA_PRIVATE || row.dataType == DBDataType::KEY_ECDSA_PRIVATE || row.dataType == DBDataType::KEY_DSA_PRIVATE)) {
520 retCode = CKM_API_ERROR_BAD_REQUEST;
523 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::GET),
526 static_cast<int>(row.dataType),
528 return response.Pop();
531 RawBuffer CKMLogic::getDataList(
536 int retCode = CKM_API_SUCCESS;
537 LabelAliasVector labelAliasVector;
539 if (0 < m_userDataMap.count(cred.uid)) {
540 auto &handler = m_userDataMap[cred.uid];
542 if (dataType == DBDataType::CERTIFICATE || dataType == DBDataType::BINARY_DATA) {
543 handler.database.getAliases(cred.smackLabel, dataType, labelAliasVector);
545 handler.database.getKeyAliases(cred.smackLabel, labelAliasVector);
547 } Catch (CKM::Exception) {
548 LogError("Failed to get aliases");
549 retCode = CKM_API_ERROR_DB_ERROR;
552 retCode = CKM_API_ERROR_DB_LOCKED;
555 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::GET_LIST),
558 static_cast<int>(dataType),
560 return response.Pop();
564 int CKMLogic::createKeyPairHelper(
566 const KeyType key_type,
567 const int additional_param,
568 const Alias &aliasPrivate,
569 const Alias &aliasPublic,
570 const PolicySerializable &policyPrivate,
571 const PolicySerializable &policyPublic)
573 if (0 >= m_userDataMap.count(cred.uid))
574 return CKM_API_ERROR_DB_LOCKED;
576 auto &handler = m_userDataMap[cred.uid];
581 case KeyType::KEY_RSA_PUBLIC:
582 case KeyType::KEY_RSA_PRIVATE:
583 retCode = CryptoService::createKeyPairRSA(additional_param, prv, pub);
586 case KeyType::KEY_DSA_PUBLIC:
587 case KeyType::KEY_DSA_PRIVATE:
588 retCode = CryptoService::createKeyPairDSA(additional_param, prv, pub);
591 case KeyType::KEY_ECDSA_PUBLIC:
592 case KeyType::KEY_ECDSA_PRIVATE:
593 retCode = CryptoService::createKeyPairECDSA(static_cast<ElipticCurve>(additional_param), prv, pub);
597 return CKM_API_ERROR_INPUT_PARAM;
600 if (CKM_CRYPTO_CREATEKEY_SUCCESS != retCode)
602 LogDebug("CryptoService error with code: " << retCode);
603 return CKM_API_ERROR_SERVER_ERROR; // TODO error code
606 DBCrypto::Transaction transaction(&handler.database);
607 retCode = saveDataHelper(cred,
608 toDBDataType(prv.getType()),
613 if (CKM_API_SUCCESS != retCode)
616 retCode = saveDataHelper(cred,
617 toDBDataType(pub.getType()),
622 if (CKM_API_SUCCESS != retCode)
625 transaction.commit();
630 RawBuffer CKMLogic::createKeyPair(
632 LogicCommand protocol_cmd,
634 const int additional_param,
635 const Alias &aliasPrivate,
636 const Alias &aliasPublic,
637 const PolicySerializable &policyPrivate,
638 const PolicySerializable &policyPublic)
640 int retCode = CKM_API_SUCCESS;
642 KeyType key_type = KeyType::KEY_NONE;
645 case LogicCommand::CREATE_KEY_PAIR_RSA:
646 key_type = KeyType::KEY_RSA_PUBLIC;
648 case LogicCommand::CREATE_KEY_PAIR_DSA:
649 key_type = KeyType::KEY_DSA_PUBLIC;
651 case LogicCommand::CREATE_KEY_PAIR_ECDSA:
652 key_type = KeyType::KEY_ECDSA_PUBLIC;
659 retCode = createKeyPairHelper(
668 } catch (DBCrypto::Exception::AliasExists &e) {
669 LogDebug("DBCrypto error: alias exists: " << e.GetMessage());
670 retCode = CKM_API_ERROR_DB_ALIAS_EXISTS;
671 } catch (DBCrypto::Exception::TransactionError &e) {
672 LogDebug("DBCrypto error: transaction error: " << e.GetMessage());
673 retCode = CKM_API_ERROR_DB_ERROR;
674 } catch (CKM::CryptoLogic::Exception::Base &e) {
675 LogDebug("CryptoLogic error: " << e.GetMessage());
676 retCode = CKM_API_ERROR_SERVER_ERROR;
677 } catch (DBCrypto::Exception::InternalError &e) {
678 LogDebug("DBCrypto internal error: " << e.GetMessage());
679 retCode = CKM_API_ERROR_DB_ERROR;
682 return MessageBuffer::Serialize(static_cast<int>(protocol_cmd), commandId, retCode).Pop();
685 RawBuffer CKMLogic::getCertificateChain(
688 const RawBuffer &certificate,
689 const RawBufferVector &untrustedRawCertVector)
693 CertificateImpl cert(certificate, DataFormat::FORM_DER);
694 CertificateImplVector untrustedCertVector;
695 CertificateImplVector chainVector;
696 RawBufferVector chainRawVector;
698 for (auto &e: untrustedRawCertVector)
699 untrustedCertVector.push_back(CertificateImpl(e, DataFormat::FORM_DER));
701 LogDebug("Cert is empty: " << cert.empty());
703 int retCode = m_certStore.verifyCertificate(cert, untrustedCertVector, chainVector);
705 if (retCode == CKM_API_SUCCESS) {
706 for (auto &e : chainVector)
707 chainRawVector.push_back(e.getDER());
710 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::GET_CHAIN_CERT),
714 return response.Pop();
717 RawBuffer CKMLogic::getCertificateChain(
720 const RawBuffer &certificate,
721 const AliasVector &aliasVector)
723 int retCode = CKM_API_SUCCESS;
724 RawBufferVector chainRawVector;
726 CertificateImpl cert(certificate, DataFormat::FORM_DER);
727 CertificateImplVector untrustedCertVector;
728 CertificateImplVector chainVector;
732 retCode = CKM_API_ERROR_SERVER_ERROR;
736 for (auto &i: aliasVector) {
737 retCode = getDataHelper(cred, DBDataType::CERTIFICATE, i, std::string(), Password(), row);
739 if (retCode != CKM_API_SUCCESS)
742 untrustedCertVector.push_back(CertificateImpl(row.data, DataFormat::FORM_DER));
745 retCode = m_certStore.verifyCertificate(cert, untrustedCertVector, chainVector);
747 if (retCode != CKM_API_SUCCESS)
750 for (auto &i: chainVector)
751 chainRawVector.push_back(i.getDER());
753 } catch (const CryptoLogic::Exception::Base &e) {
754 LogError("DBCyptorModule failed with message: " << e.GetMessage());
755 retCode = CKM_API_ERROR_SERVER_ERROR;
756 } catch (const DBCrypto::Exception::PermissionDenied &e) {
757 LogError("DBCrypto failed with message: " << e.GetMessage());
758 retCode = CKM_API_ERROR_ACCESS_DENIED;
759 } catch (const DBCrypto::Exception::Base &e) {
760 LogError("DBCrypto failed with message: " << e.GetMessage());
761 retCode = CKM_API_ERROR_DB_ERROR;
763 LogError("Unknown error.");
767 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::GET_CHAIN_ALIAS),
771 return response.Pop();
774 RawBuffer CKMLogic::createSignature(
777 const Alias &privateKeyAlias,
778 const Password &password, // password for private_key
779 const RawBuffer &message,
780 const HashAlgorithm hash,
781 const RSAPaddingAlgorithm padding)
787 int retCode = CKM_API_SUCCESS;
791 retCode = getDataHelper(cred, DBDataType::DB_KEY_FIRST, privateKeyAlias, std::string(), password, row);
792 if (CKM_API_SUCCESS != retCode) {
793 LogError("getDataHelper return error");
797 KeyImpl keyParsed(row.data, Password());
798 if (keyParsed.empty())
799 retCode = CKM_API_ERROR_SERVER_ERROR;
801 retCode = cs.createSignature(keyParsed, message, hash, padding, signature);
803 } catch (const KeyProvider::Exception::Base &e) {
804 LogError("KeyProvider failed with message: " << e.GetMessage());
805 retCode = CKM_API_ERROR_SERVER_ERROR;
806 } catch (const CryptoLogic::Exception::Base &e) {
807 LogError("CryptoLogic failed with message: " << e.GetMessage());
808 retCode = CKM_API_ERROR_SERVER_ERROR;
809 } catch (const DBCrypto::Exception::PermissionDenied &e) {
810 LogError("DBCrypto failed with message: " << e.GetMessage());
811 retCode = CKM_API_ERROR_ACCESS_DENIED;
812 } catch (const DBCrypto::Exception::Base &e) {
813 LogError("DBCrypto failed with message: " << e.GetMessage());
814 retCode = CKM_API_ERROR_DB_ERROR;
815 } catch (const CKM::Exception &e) {
816 LogError("Unknown CKM::Exception: " << e.GetMessage());
817 retCode = CKM_API_ERROR_SERVER_ERROR;
820 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::CREATE_SIGNATURE),
824 return response.Pop();
827 RawBuffer CKMLogic::verifySignature(
830 const Alias &publicKeyOrCertAlias,
831 const Password &password, // password for public_key (optional)
832 const RawBuffer &message,
833 const RawBuffer &signature,
834 const HashAlgorithm hash,
835 const RSAPaddingAlgorithm padding)
837 int retCode = CKM_API_ERROR_VERIFICATION_FAILED;
845 retCode = getDataHelper(cred, DBDataType::DB_KEY_FIRST, publicKeyOrCertAlias, std::string(), password, row);
847 if (retCode == CKM_API_SUCCESS) {
848 key = KeyImpl(row.data);
849 } else if (retCode == CKM_API_ERROR_DB_ALIAS_UNKNOWN) {
850 retCode = getDataHelper(cred, DBDataType::CERTIFICATE, publicKeyOrCertAlias, std::string(), password, row);
851 if (retCode != CKM_API_SUCCESS)
853 CertificateImpl cert(row.data, DataFormat::FORM_DER);
854 key = cert.getKeyImpl();
860 retCode = CKM_API_ERROR_SERVER_ERROR;
864 retCode = cs.verifySignature(key, message, signature, hash, padding);
866 } catch (const CryptoService::Exception::Crypto_internal &e) {
867 LogError("KeyProvider failed with message: " << e.GetMessage());
868 retCode = CKM_API_ERROR_SERVER_ERROR;
869 } catch (const CryptoService::Exception::opensslError &e) {
870 LogError("KeyProvider failed with message: " << e.GetMessage());
871 retCode = CKM_API_ERROR_SERVER_ERROR;
872 } catch (const KeyProvider::Exception::Base &e) {
873 LogError("KeyProvider failed with error: " << e.GetMessage());
874 retCode = CKM_API_ERROR_SERVER_ERROR;
875 } catch (const CryptoLogic::Exception::Base &e) {
876 LogError("CryptoLogic failed with message: " << e.GetMessage());
877 retCode = CKM_API_ERROR_SERVER_ERROR;
878 } catch (const DBCrypto::Exception::PermissionDenied &e) {
879 LogError("DBCrypto failed with message: " << e.GetMessage());
880 retCode = CKM_API_ERROR_ACCESS_DENIED;
881 } catch (const DBCrypto::Exception::Base &e) {
882 LogError("DBCrypto failed with message: " << e.GetMessage());
883 retCode = CKM_API_ERROR_DB_ERROR;
884 } catch (const CKM::Exception &e) {
885 LogError("Unknown CKM::Exception: " << e.GetMessage());
886 retCode = CKM_API_ERROR_SERVER_ERROR;
889 auto response = MessageBuffer::Serialize(static_cast<int>(LogicCommand::VERIFY_SIGNATURE),
892 return response.Pop();
895 RawBuffer CKMLogic::allowAccess(
899 const Alias &item_alias,
900 const std::string &accessor_label,
901 const AccessRight req_rights)
903 int retCode = CKM_API_ERROR_VERIFICATION_FAILED;
905 if (0 < m_userDataMap.count(cred.uid))
908 retCode = m_userDataMap[cred.uid].database.setAccessRights(cred.smackLabel, item_alias, accessor_label, req_rights);
909 } Catch (DBCrypto::Exception::InvalidArgs) {
910 LogError("Error: invalid args!");
911 retCode = CKM_API_ERROR_INPUT_PARAM;
912 } Catch (DBCrypto::Exception::PermissionDenied) {
913 LogError("Error: not enough permissions!");
914 retCode = CKM_API_ERROR_ACCESS_DENIED;
915 } Catch (CKM::Exception) {
916 LogError("Error in set row!");
917 retCode = CKM_API_ERROR_DB_ERROR;
920 retCode = CKM_API_ERROR_DB_LOCKED;
923 return MessageBuffer::Serialize(command, msgID, retCode).Pop();
926 RawBuffer CKMLogic::denyAccess(
930 const Alias &item_alias,
931 const std::string &accessor_label)
933 int retCode = CKM_API_ERROR_VERIFICATION_FAILED;
935 if (0 < m_userDataMap.count(cred.uid))
938 retCode = m_userDataMap[cred.uid].database.clearAccessRights(cred.smackLabel, item_alias, accessor_label);
939 } Catch (DBCrypto::Exception::PermissionDenied) {
940 LogError("Error: not enough permissions!");
941 retCode = CKM_API_ERROR_ACCESS_DENIED;
942 } Catch (DBCrypto::Exception::InvalidArgs) {
943 LogError("Error: permission not found!");
944 retCode = CKM_API_ERROR_INPUT_PARAM;
945 } Catch (CKM::Exception) {
946 LogError("Error in deleting row!");
947 retCode = CKM_API_ERROR_DB_ERROR;
950 retCode = CKM_API_ERROR_DB_LOCKED;
953 return MessageBuffer::Serialize(command, msgID, retCode).Pop();