a386652879d56f9ab390a4b68e59eaee9e7e20b0
[platform/core/security/key-manager.git] / src / manager / service / key-provider.h
1 #pragma once
2
3 #include <string.h>
4 #include <stdint.h>
5 #include <openssl/rand.h>
6 #include <openssl/err.h>
7 #include <openssl/evp.h>
8 #include <openssl/sha.h>
9 #include <memory>
10
11 #include <ckm/ckm-type.h>
12 #include <dpl/exception.h>
13
14 #ifndef SUCCESS
15 #define SUCCESS               0
16 #endif
17 #ifndef ERROR
18 #define ERROR                -1
19 #endif
20 #ifndef INVALID_ARGUMENTS
21 #define INVALID_ARGUMENTS    -2
22 #endif
23 #ifndef VERIFY_DATA_ERROR
24 #define VERIFY_DATA_ERROR    -3
25 #endif
26 #ifndef OPENSSL_ENGINE_ERROR
27 #define OPENSSL_ENGINE_ERROR -4
28 #endif
29 #ifndef UNKNOWN_ERROR
30 #define UNKNOWN_ERROR        -5
31 #endif
32
33 #define AES256_KEY_LEN_BITS   256
34 #define AES256_KEY_LEN_BYTSE  (AES256_KEY_LEN_BITS / 8)
35 // Unused
36 //#define AES_GCM_TAG_SIZE      32
37
38 #define PBKDF2_SALT_LEN       16
39 #define PBKDF2_ITERATIONS     4096
40
41 #define MAX_IV_SIZE           16
42 #define MAX_SALT_SIZE         16
43 #define MAX_KEY_SIZE          32
44 #define MAX_WRAPPED_KEY_SIZE  32
45 #define MAX_LABEL_SIZE        32
46 #define DOMAIN_NAME_SIZE      32
47 #define APP_LABEL_SIZE        32
48
49 namespace CKM {
50
51 typedef struct KeyComponentsInfo_ {
52     uint32_t keyLength;
53     char label[MAX_LABEL_SIZE];
54     uint8_t salt[MAX_SALT_SIZE];
55     uint8_t iv[MAX_IV_SIZE];
56     uint8_t tag[MAX_IV_SIZE];
57 } KeyComponentsInfo;
58
59 typedef struct KeyAndInfo_ {
60     KeyComponentsInfo keyInfo;
61     uint8_t key[MAX_KEY_SIZE];
62 } KeyAndInfo;
63
64 typedef struct WrappedKeyAndInfo_ {
65     KeyComponentsInfo keyInfo;
66     uint8_t wrappedKey[MAX_WRAPPED_KEY_SIZE];
67 } WrappedKeyAndInfo;
68
69 class WrappedKeyAndInfoContainer{
70 public:
71     WrappedKeyAndInfoContainer();
72     WrappedKeyAndInfoContainer(const unsigned char*);
73     WrappedKeyAndInfo& getWrappedKeyAndInfo();
74     void setKeyInfoKeyLength(const unsigned int);
75     void setKeyInfoLabel(const std::string);
76     void setKeyInfoSalt(const unsigned char*, const int);
77     void setKeyInfo(const KeyComponentsInfo*);
78     ~WrappedKeyAndInfoContainer();
79 private:
80     WrappedKeyAndInfo *wrappedKeyAndInfo;
81 };
82
83 class KeyAndInfoContainer{
84 public:
85     class Exception{
86     public:
87         DECLARE_EXCEPTION_TYPE(CKM::Exception, Base)
88     };
89     KeyAndInfoContainer();
90     KeyAndInfoContainer(const unsigned char*);
91     KeyAndInfo& getKeyAndInfo();
92     void setKeyInfoKeyLength(const unsigned int);
93     void setKeyInfo(const KeyComponentsInfo*);
94     ~KeyAndInfoContainer();
95 private:
96     KeyAndInfo *keyAndInfo;
97 };
98
99
100 // This is internal api so all functions should throw exception on errors.
101 class KeyProvider {
102 public:
103     class Exception {
104     public:
105         DECLARE_EXCEPTION_TYPE(CKM::Exception, Base)
106         DECLARE_EXCEPTION_TYPE(Base, InitFailed)
107         DECLARE_EXCEPTION_TYPE(Base, GenFailed)
108         DECLARE_EXCEPTION_TYPE(Base, WrapFailed)
109         DECLARE_EXCEPTION_TYPE(Base, UnwrapFailed)
110         DECLARE_EXCEPTION_TYPE(Base, PassWordError)
111         DECLARE_EXCEPTION_TYPE(Base, InputParamError)
112         DECLARE_EXCEPTION_TYPE(Base, OpensslEngineError)
113     };
114
115     // To store in std containers
116     KeyProvider();
117     // In constructor you must check if SKMM is initialized. On error -> exception
118     // keyInWrapForm should be used like this:
119     // if (keyInWrapForm.size() != sizeof(WrappedKeyAndInfo))
120     //     throw exception; // buffer does not have proper size to store WrappedKeyAndInfo
121     // WrappedKeyAndInfo *wkm = static_cast<WrappedKeyAndInfo>(keyInWrapForm.data());
122     KeyProvider(const RawBuffer &domainKEKInWrapForm, const Password &password);
123
124     KeyProvider(KeyProvider &&);
125     KeyProvider(const KeyProvider &) = delete;
126     KeyProvider& operator=(const KeyProvider &) = delete;
127     KeyProvider& operator=(KeyProvider &&);
128
129     bool isInitialized();
130
131     // Returns Key used to decrypt database.
132     RawBuffer getPureDomainKEK();
133
134     // Returns Key in form used to store key in file
135     // Requied by Control::resetPassword(const RawBuffer &newPassword);
136     // This api should be used only on Tizen 2.2.1
137     RawBuffer getWrappedDomainKEK(const Password &password);
138
139     // EncryptedKey key extracted from database. Used to encrypt application data.
140     // This key will be used to decrypt/encrypt data in ROW
141     RawBuffer getPureDEK(const RawBuffer &DEKInWrapForm);
142
143     // Returns WRAPPED DEK. This will be written to datbase.
144     // This key will be used to encrypt all application information.
145     // All application are identified by smackLabel.
146     RawBuffer generateDEK(const std::string &smackLabel);
147
148     // used by change user password. On error -> exception
149     static RawBuffer reencrypt(
150         const RawBuffer &domainKEKInWrapForm,
151         const Password &oldPass,
152         const Password &newPass);
153
154     // First run of application for some user. DomainKEK was not created yet. We must create one.
155     // This key will be used to encrypt user database.
156     static RawBuffer generateDomainKEK(const std::string &user, const Password &userPassword);
157
158     // This will be called by framework at the begin of the program
159     static int initializeLibrary();
160     // This will be called by framework at the end of the program
161     static int closeLibrary();
162
163     virtual ~KeyProvider();
164 private:
165     // KeyAndInfoContainer class
166     std::shared_ptr<KeyAndInfoContainer> m_kmcDKEK;
167     bool m_isInitialized;
168
169     static int encryptAes256Gcm(
170         const unsigned char *plaintext,
171         int plaintext_len,
172         const unsigned char *key,
173         const unsigned char *iv,
174         unsigned char *ciphertext,
175         unsigned char *tag);
176
177     static int decryptAes256Gcm(
178         const unsigned char *ciphertext,
179         int ciphertext_len,
180         unsigned char *tag,
181         const unsigned char *key,
182         const unsigned char *iv,
183         unsigned char *plaintext);
184
185     static char * concat_password_user(
186         const char *user,
187         const char *password);
188
189 };
190
191 } // namespace CKM