Modify encryption scheme
[platform/core/security/key-manager.git] / src / manager / service / db-crypto.h
1 /*
2  * Copyright (c) 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        db-crypto.h
18  * @author      Zofia Abramowska (z.abramowska@samsung.com)
19  * @version     1.0
20  * @brief       Header of encrypted db access layer
21  */
22
23 #ifndef DB_CRYPTO_H
24 #define DB_CRYPTO_H
25
26 #include <vector>
27 #include <string>
28
29 #include <dpl/db/sql_connection.h>
30
31 #include <ckm/ckm-type.h>
32 #include <db-row.h>
33 #include <permission.h>
34 #include <protocols.h>
35
36 #pragma GCC diagnostic push
37 #pragma GCC diagnostic warning "-Wdeprecated-declarations"
38
39 namespace CKM {
40 namespace DB {
41     class Crypto {
42          public:
43             typedef boost::optional<Row> RowOptional;
44             typedef boost::optional<RawBuffer> RawBufferOptional;
45             class Exception
46             {
47             public:
48                 DECLARE_EXCEPTION_TYPE(CKM::Exception, Base)
49                 DECLARE_EXCEPTION_TYPE(Base, InternalError)
50                 DECLARE_EXCEPTION_TYPE(Base, TransactionError)
51                 DECLARE_EXCEPTION_TYPE(Base, InvalidArgs)
52             };
53             Crypto() :
54                 m_connection(NULL),
55                 m_inUserTransaction(false)
56               {};
57             // user name instead of path?
58             Crypto(const std::string &path, const RawBuffer &rawPass);
59             Crypto(const Crypto &other) = delete;
60             Crypto(Crypto &&other);
61
62             Crypto& operator=(const Crypto& ) = delete;
63             Crypto& operator=(Crypto&& other);
64
65             virtual ~Crypto();
66
67             void saveRow(
68                     const Row &row);
69
70             void saveRows(
71                     const Name &name,
72                     const Label &owner,
73                     const RowVector &rows);
74
75             void updateRow(
76                     const Row &row);
77
78             bool isNameLabelPresent(
79                     const Name &name,
80                     const Label &owner) const;
81
82             RowOptional getRow(
83                     const Name &name,
84                     const Label &ownerLabel,
85                     DataType type);
86
87             RowOptional getRow(
88                     const Name &name,
89                     const Label &ownerLabel,
90                     DataType typeRangeStart,
91                     DataType typeRangeStop);
92
93             void getRows(
94                     const Name &name,
95                     const Label &ownerLabel,
96                     DataType type,
97                     RowVector &output);
98
99             void getRows(
100                     const Name &name,
101                     const Label &ownerLabel,
102                     DataType typeRangeStart,
103                     DataType typeRangeStop,
104                     RowVector &output);
105
106             void listNames(
107                     const Label &smackLabel,
108                     LabelNameVector& labelNameVector,
109                     DataType type);
110
111             void listNames(
112                     const Label &smackLabel,
113                     LabelNameVector& labelNameVector,
114                     DataType typeRangeStart,
115                     DataType typeRangeStop);
116
117             bool deleteRow(
118                     const Name &name,
119                     const Label &ownerLabel);
120
121             // keys
122             void saveKey(const Label& label, const RawBuffer &key);
123             RawBufferOptional getKey(const Label& label);
124             void deleteKey(const Label& label);
125
126
127             // permissions
128             void setPermission(
129                     const Name &name,
130                     const Label &ownerLabel,
131                     const Label &accessorLabel,
132                     const PermissionMask permissionMask);
133
134             PermissionMaskOptional getPermissionRow(
135                     const Name &name,
136                     const Label &ownerLabel,
137                     const Label &accessorLabel) const;
138
139
140             // transactions
141             int beginTransaction();
142             int commitTransaction();
143             int rollbackTransaction();
144
145             class Transaction {
146             public:
147                 Transaction(Crypto *db)
148                     : m_db(db),
149                       m_inTransaction(false) {
150                     if(!m_db->m_inUserTransaction) {
151                         Try {
152                             m_db->m_connection->ExecCommand("BEGIN EXCLUSIVE");
153                             m_db->m_inUserTransaction = true;
154                             m_inTransaction = true;
155                         } Catch (SqlConnection::Exception::InternalError) {
156                             LogError("sqlite got into infinite busy state");
157                             ReThrow(Crypto::Exception::TransactionError);
158                         } Catch (SqlConnection::Exception::Base) {
159                             LogError("Couldn't begin transaction");
160                             ReThrow(Crypto::Exception::TransactionError);
161                         }
162                     }
163                 }
164                 void commit() {
165                     if(m_inTransaction) {
166                         Try {
167                             m_db->m_connection->CommitTransaction();
168                             m_db->m_inUserTransaction = false;
169                             m_inTransaction = false;
170                         } Catch (SqlConnection::Exception::InternalError) {
171                             LogError("sqlite got into infinite busy state");
172                             ReThrow(Crypto::Exception::TransactionError);
173                         } Catch (SqlConnection::Exception::Base) {
174                             LogError("Couldn't commit transaction");
175                             ReThrow(Crypto::Exception::TransactionError);
176                         }
177                     }
178                 }
179                 void rollback() {
180                     if(m_inTransaction) {
181                         Try {
182                             m_db->m_connection->RollbackTransaction();
183                             m_db->m_inUserTransaction = false;
184                             m_inTransaction = false;
185                         } Catch (SqlConnection::Exception::InternalError) {
186                             LogError("sqlite got into infinite busy state");
187                             ReThrow(Crypto::Exception::TransactionError);
188                         } Catch (SqlConnection::Exception::Base) {
189                             LogError("Couldn't rollback transaction");
190                             ReThrow(Crypto::Exception::TransactionError);
191                         }
192                     }
193                 }
194                 ~Transaction() {
195                     Try {
196                         if(m_inTransaction) {
197                             m_db->m_inUserTransaction = false;
198                             m_db->m_connection->RollbackTransaction();
199                         }
200                     } Catch (SqlConnection::Exception::InternalError) {
201                         LogError("sqlite got into infinite busy state");
202                         ReThrow(Crypto::Exception::TransactionError);
203                     } Catch (SqlConnection::Exception::Base) {
204                         LogError("Transaction rollback failed!");
205                     }
206                 }
207             private:
208                 Crypto *m_db;
209                 bool m_inTransaction;
210             };
211
212          protected:
213             SqlConnection* m_connection;
214          private:
215             bool m_inUserTransaction;
216
217             void resetDB();
218             void initDatabase();
219             void createDBSchema();
220             /**
221              * return current database version
222              *
223              * @param[out] schemaVersion    if success, will contain DB schema version code
224              *
225              * @return false on DB empty or corrupted, true if information read
226              */
227             bool getDBVersion(int & schemaVersion);
228             typedef boost::optional<std::string> ScriptOptional;
229             ScriptOptional getScript(const std::string &scriptName) const;
230             ScriptOptional getMigrationScript(int db_version) const;
231
232             Row getRow(
233                     const SqlConnection::DataCommandUniquePtr &selectCommand) const;
234
235             void createTable(
236                     const char *create_cmd,
237                     const char *table_name);
238
239             void createView(
240                     const char* create_cmd);
241
242             class SchemaInfo {
243             public:
244                 explicit SchemaInfo(const Crypto *db) : m_db(db) {}
245
246                 void        setVersionInfo();
247                 bool        getVersionInfo(int & version) const;
248
249             private:
250                 const Crypto *m_db;
251             };
252
253         public:
254             class NameTable {
255             public:
256                 explicit NameTable(SqlConnection* connection) : m_connection(connection) {}
257
258                 void addRow(
259                         const Name &name,
260                         const Label &ownerLabel);
261
262                 void deleteRow(
263                         const Name &name,
264                         const Label &ownerLabel);
265
266                 void deleteAllRows(
267                         const Label &ownerLabel);
268
269                 bool isPresent(
270                         const Name &name,
271                         const Label &ownerLabel) const;
272
273             private:
274                 SqlConnection* m_connection;
275             };
276
277             class ObjectTable {
278             public:
279                 explicit ObjectTable(SqlConnection* connection) : m_connection(connection) {}
280
281                 void addRow(
282                         const Row &row);
283                 void updateRow(
284                         const Row &row);
285
286             private:
287                 SqlConnection* m_connection;
288             };
289
290             class PermissionTable {
291             public:
292                 explicit PermissionTable(SqlConnection* connection) : m_connection(connection) {}
293
294                 void setPermission(
295                         const Name &name,
296                         const Label &ownerLabel,
297                         const Label &accessorLabel,
298                         const PermissionMask permissionMask);
299
300                 PermissionMaskOptional getPermissionRow(
301                         const Name &name,
302                         const Label &ownerLabel,
303                         const Label &accessorLabel) const;
304
305             private:
306                 SqlConnection* m_connection;
307             };
308     };
309 } // namespace DB
310 } // namespace CKM
311
312 #pragma GCC diagnostic pop
313 #endif //DB_CRYPTO_H
314