Simplify implementation of ServiceThread
[platform/core/security/key-manager.git] / src / manager / service / ckm-service.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        ckm-service.cpp
18  * @author      Bartlomiej Grzelewski (b.grzelewski@samsung.com)
19  * @version     1.0
20  * @brief       CKM service implementation.
21  */
22
23 #include <protocols.h>
24
25 #include <dpl/serialization.h>
26 #include <dpl/log/log.h>
27
28 #include <ckm-service.h>
29 #include <ckm-logic.h>
30
31 namespace {
32 const CKM::InterfaceID SOCKET_ID_CONTROL = 0;
33 const CKM::InterfaceID SOCKET_ID_STORAGE = 1;
34 } // namespace anonymous
35
36 namespace CKM {
37
38 CKMService::CKMService()
39   : m_logic(new CKMLogic)
40 {}
41
42 CKMService::~CKMService() {
43     delete m_logic;
44 }
45
46 GenericSocketService::ServiceDescriptionVector CKMService::GetServiceDescription()
47 {
48     return ServiceDescriptionVector {
49         {SERVICE_SOCKET_CKM_CONTROL, "key-manager::api-control", SOCKET_ID_CONTROL},
50         {SERVICE_SOCKET_CKM_STORAGE, "key-manager::api-storage", SOCKET_ID_STORAGE}
51     };
52 }
53
54 bool CKMService::ProcessOne(
55     const ConnectionID &conn,
56     ConnectionInfo &info)
57 {
58     LogDebug ("process One");
59     RawBuffer response;
60
61     Try {
62         if (!info.buffer.Ready())
63             return false;
64
65         if (info.interfaceID == SOCKET_ID_CONTROL)
66             response = ProcessControl(info.buffer);
67         else
68             response = ProcessStorage(info.credentials, info.buffer);
69
70         m_serviceManager->Write(conn, response);
71
72         return true;
73     } Catch (MessageBuffer::Exception::Base) {
74         LogError("Broken protocol. Closing socket.");
75     } Catch (Exception::BrokenProtocol) {
76         LogError("Broken protocol. Closing socket.");
77     } catch (const DataType::Exception::Base &e) {
78         LogError("Closing socket. DBDataType::Exception: " << e.DumpToString());
79     } catch (const std::string &e) {
80         LogError("String exception(" << e << "). Closing socket");
81     } catch (const std::exception &e) {
82         LogError("Std exception:: " << e.what());
83     } catch (...) {
84         LogError("Unknown exception. Closing socket.");
85     }
86
87     m_serviceManager->Close(conn);
88     return false;
89 }
90
91 RawBuffer CKMService::ProcessControl(MessageBuffer &buffer) {
92     int command = 0;
93     uid_t user = 0;
94     ControlCommand cc;
95     Password newPass, oldPass;
96     Label smackLabel;
97
98     buffer.Deserialize(command);
99
100     LogDebug("Process control. Command: " << command);
101
102     cc = static_cast<ControlCommand>(command);
103
104     switch(cc) {
105     case ControlCommand::UNLOCK_USER_KEY:
106         buffer.Deserialize(user, newPass);
107         return m_logic->unlockUserKey(user, newPass);
108     case ControlCommand::LOCK_USER_KEY:
109         buffer.Deserialize(user);
110         return m_logic->lockUserKey(user);
111     case ControlCommand::REMOVE_USER_DATA:
112         buffer.Deserialize(user);
113         return m_logic->removeUserData(user);
114     case ControlCommand::CHANGE_USER_PASSWORD:
115         buffer.Deserialize(user, oldPass, newPass);
116         return m_logic->changeUserPassword(user, oldPass, newPass);
117     case ControlCommand::RESET_USER_PASSWORD:
118         buffer.Deserialize(user, newPass);
119         return m_logic->resetUserPassword(user, newPass);
120     case ControlCommand::REMOVE_APP_DATA:
121         buffer.Deserialize(smackLabel);
122         return m_logic->removeApplicationData(smackLabel);
123     case ControlCommand::UPDATE_CC_MODE:
124         return m_logic->updateCCMode();
125     case ControlCommand::SET_PERMISSION:
126     {
127         Name name;
128         Label label;
129         Label accessorLabel;
130         PermissionMask permissionMask = 0;
131
132         buffer.Deserialize(user, name, label, accessorLabel, permissionMask);
133         Credentials cred = { user, label };
134         return m_logic->setPermission(
135             cred,
136             command,
137             0, // dummy
138             name,
139             label,
140             accessorLabel,
141             permissionMask);
142     }
143     default:
144         Throw(Exception::BrokenProtocol);
145     }
146 }
147
148 RawBuffer CKMService::ProcessStorage(Credentials &cred, MessageBuffer &buffer)
149 {
150     int command = 0;
151     int msgID = 0;
152     int tmpDataType = 0;
153     Name name;
154     Label label, accessorLabel;
155     std::string user;
156
157     buffer.Deserialize(command);
158     buffer.Deserialize(msgID);
159
160     // This is a workaround solution for locktype=None in Tizen 2.2.1
161     // When locktype is None, lockscreen app doesn't interfere with unlocking process.
162     // Therefor lockscreen app cannot notify unlock events to key-manager when locktype is None.
163     // So, to unlock user data when lock type is None, key-manager always try to unlock user data with null password.
164     // Even if the result is fail, it will be ignored.
165     Password nullPassword("");
166     m_logic->unlockUserKey(cred.uid, nullPassword, false);
167
168     LogDebug("Process storage. Command: " << command);
169
170     switch(static_cast<LogicCommand>(command)) {
171         case LogicCommand::SAVE:
172         {
173             RawBuffer rawData;
174             PolicySerializable policy;
175             buffer.Deserialize(tmpDataType, name, label, rawData, policy);
176             return m_logic->saveData(
177                 cred,
178                 msgID,
179                 name,
180                 label,
181                 rawData,
182                 DataType(tmpDataType),
183                 policy);
184         }
185         case LogicCommand::SAVE_PKCS12:
186         {
187             RawBuffer rawData;
188             PKCS12Serializable pkcs;
189             PolicySerializable keyPolicy, certPolicy;
190             buffer.Deserialize(name, label, pkcs, keyPolicy, certPolicy);
191             return m_logic->savePKCS12(
192                 cred,
193                 msgID,
194                 name,
195                 label,
196                 pkcs,
197                 keyPolicy,
198                 certPolicy);
199         }
200         case LogicCommand::REMOVE:
201         {
202             buffer.Deserialize(name, label);
203             return m_logic->removeData(
204                 cred,
205                 msgID,
206                 name,
207                 label);
208         }
209         case LogicCommand::GET:
210         {
211             Password password;
212             buffer.Deserialize(tmpDataType, name, label, password);
213             return m_logic->getData(
214                 cred,
215                 msgID,
216                 DataType(tmpDataType),
217                 name,
218                 label,
219                 password);
220         }
221         case LogicCommand::GET_PKCS12:
222         {
223             Password passKey;
224             Password passCert;
225             buffer.Deserialize(name,
226                                label,
227                                passKey,
228                                passCert);
229             return m_logic->getPKCS12(
230                 cred,
231                 msgID,
232                 name,
233                 label,
234                 passKey,
235                 passCert);
236         }
237         case LogicCommand::GET_LIST:
238         {
239             buffer.Deserialize(tmpDataType);
240             return m_logic->getDataList(
241                 cred,
242                 msgID,
243                 DataType(tmpDataType));
244         }
245         case LogicCommand::CREATE_KEY_PAIR_RSA:
246         case LogicCommand::CREATE_KEY_PAIR_DSA:
247         case LogicCommand::CREATE_KEY_PAIR_ECDSA:
248         {
249             int additional_param = 0;
250             Name privateKeyName;
251             Label privateKeyLabel;
252             Name publicKeyName;
253             Label publicKeyLabel;
254             PolicySerializable policyPrivateKey;
255             PolicySerializable policyPublicKey;
256             buffer.Deserialize(additional_param,
257                                policyPrivateKey,
258                                policyPublicKey,
259                                privateKeyName,
260                                privateKeyLabel,
261                                publicKeyName,
262                                publicKeyLabel);
263             return m_logic->createKeyPair(
264                 cred,
265                 static_cast<LogicCommand>(command),
266                 msgID,
267                 additional_param,
268                 privateKeyName,
269                 privateKeyLabel,
270                 publicKeyName,
271                 publicKeyLabel,
272                 policyPrivateKey,
273                 policyPublicKey);
274         }
275         case LogicCommand::GET_CHAIN_CERT:
276         {
277             RawBuffer certificate;
278             RawBufferVector untrustedVector;
279             RawBufferVector trustedVector;
280             bool systemCerts;
281             buffer.Deserialize(certificate, untrustedVector, trustedVector, systemCerts);
282             return m_logic->getCertificateChain(
283                 cred,
284                 msgID,
285                 certificate,
286                 untrustedVector,
287                 trustedVector,
288                 systemCerts);
289         }
290         case LogicCommand::GET_CHAIN_ALIAS:
291         {
292             RawBuffer certificate;
293             LabelNameVector untrustedVector;
294             LabelNameVector trustedVector;
295             bool systemCerts;
296             buffer.Deserialize(certificate, untrustedVector, trustedVector, systemCerts);
297             return m_logic->getCertificateChain(
298                 cred,
299                 msgID,
300                 certificate,
301                 untrustedVector,
302                 trustedVector,
303                 systemCerts);
304         }
305         case LogicCommand::CREATE_SIGNATURE:
306         {
307             Password password;        // password for private_key
308             RawBuffer message;
309             int padding = 0, hash = 0;
310             buffer.Deserialize(name, label, password, message, hash, padding);
311             return m_logic->createSignature(
312                   cred,
313                   msgID,
314                   name,
315                   label,
316                   password,           // password for private_key
317                   message,
318                   static_cast<HashAlgorithm>(hash),
319                   static_cast<RSAPaddingAlgorithm>(padding));
320         }
321         case LogicCommand::VERIFY_SIGNATURE:
322         {
323             Password password;           // password for public_key (optional)
324             RawBuffer message;
325             RawBuffer signature;
326             //HashAlgorithm hash;
327             //RSAPaddingAlgorithm padding;
328             int padding = 0, hash = 0;
329             buffer.Deserialize(name,
330                                label,
331                                password,
332                                message,
333                                signature,
334                                hash,
335                                padding);
336             return m_logic->verifySignature(
337                 cred,
338                 msgID,
339                 name,
340                 label,
341                 password,           // password for public_key (optional)
342                 message,
343                 signature,
344                 static_cast<const HashAlgorithm>(hash),
345                 static_cast<const RSAPaddingAlgorithm>(padding));
346         }
347         case LogicCommand::SET_PERMISSION:
348         {
349             PermissionMask permissionMask = 0;
350             buffer.Deserialize(name, label, accessorLabel, permissionMask);
351             return m_logic->setPermission(
352                 cred,
353                 command,
354                 msgID,
355                 name,
356                 label,
357                 accessorLabel,
358                 permissionMask);
359         }
360         default:
361             Throw(Exception::BrokenProtocol);
362     }
363 }
364
365 } // namespace CKM
366