Fix prevent issues in FSecurity
[platform/framework/native/appfw.git] / src / security / pkcs / FSecPkcs_Pkcs05PbMacParametersImpl.cpp
1 //
2 // Open Service Platform
3 // Copyright (c) 2013 Samsung Electronics Co., Ltd.
4 //
5 // Licensed under the Apache License, Version 2.0 (the License);
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 //     http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17
18 /**
19  * @file                FSecPkcsPkcs05PbMacParameters.cpp
20  * @brief               This is the implementation file for Pkcs05PbMacParameters class.
21  *
22  * This header file contains the implementation of Pkcs05PbMacParameters class.
23  *
24  */
25
26 #include <new>
27 #include <openssl/evp.h>
28 #include <openssl/crypto.h>
29 #include <openssl/x509.h>
30 #include <openssl/hmac.h>
31 #include <openssl/objects.h>
32 #include <openssl/obj_mac.h>
33 #include <unique_ptr.h>
34 #include <FBaseSysLog.h>
35 #include <FBaseByteBuffer.h>
36 #include <FBaseResult.h>
37 #include <FSecPkcsIAlgorithmParameters.h>
38 #include <FSecPkcsPkcs05PbKdf2Parameters.h>
39 #include <FSecPkcsAlgorithmIdentifier.h>
40 #include <FSecPkcsTypes.h>
41 #include <FSecPkcsPkcs05PbMacParameters.h>
42 #include "FSecPkcs_PkcsUtility.h"
43 #include "FSecPkcs_Pkcs05PbMacParametersImpl.h"
44
45 using namespace Tizen::Base;
46
47 namespace Tizen { namespace Security { namespace Pkcs
48 {
49
50
51 _Pkcs05PbMacParametersImpl::_Pkcs05PbMacParametersImpl(void)
52 {
53
54 }
55
56
57
58 _Pkcs05PbMacParametersImpl::~_Pkcs05PbMacParametersImpl(void)
59 {
60         //do nothing
61 }
62
63 result
64 _Pkcs05PbMacParametersImpl::Construct(const Tizen::Base::ByteBuffer& encodedData)
65 {
66         result r = E_SUCCESS;
67         const byte* pBuffer = null;
68         const unsigned char* pBuf = null;
69         int bufferLen = 0;
70         int nidMacAlgo = 0;
71         int paramLen = 0;
72         PBE2PARAM* pMacObj = null;
73         std::unique_ptr< ByteBuffer > pKdfParam;
74         Tizen::Base::String macOid = null;
75         ASN1_TYPE* pParam = null;
76         std::unique_ptr< Pkcs05PbKdf2Parameters > pKdf2Parameters;
77
78         pBuffer = encodedData.GetPointer();
79         SysTryReturnResult(NID_SEC_CRYPTO, pBuffer != null, E_INVALID_ARG, "The specified input parameter is invalid.");
80
81         bufferLen = encodedData.GetRemaining();
82         SysTryReturnResult(NID_SEC_CRYPTO, bufferLen > 0, E_INVALID_ARG, "The specified input parameter is invalid.");
83
84         pMacObj = d2i_PBE2PARAM(null, reinterpret_cast< const unsigned char** >(&pBuffer), bufferLen);
85         SysTryReturnResult(NID_SEC_CRYPTO, pMacObj != null, E_INVALID_ARG, "The specified input parameter is invalid.");
86
87         SysTryCatch(NID_SEC_CRYPTO, OBJ_obj2nid(pMacObj->keyfunc->algorithm) == NID_id_pbkdf2, r = E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
88
89         pParam = pMacObj->keyfunc->parameter;
90         SysTryReturn(NID_SEC_CRYPTO, !((!pParam) || (pParam->type != V_ASN1_SEQUENCE)), E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
91
92         pBuf = pParam->value.sequence->data;
93         SysTryCatch(NID_SEC_CRYPTO, pBuf != null, r = E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
94
95         paramLen = pParam->value.sequence->length;
96         SysTryCatch(NID_SEC_CRYPTO, paramLen > 0, r = E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
97
98         pKdfParam = std::unique_ptr< ByteBuffer >(new (std::nothrow) ByteBuffer());
99         SysTryCatch(NID_SEC_CRYPTO, pKdfParam, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
100
101         r = pKdfParam->Construct(paramLen);
102         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
103
104         r = pKdfParam->SetArray(pBuf, 0, paramLen);
105         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_INVALID_ARG, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
106
107         pKdfParam->Flip();
108
109         pKdf2Parameters = std::unique_ptr< Pkcs05PbKdf2Parameters >(new (std::nothrow) Pkcs05PbKdf2Parameters());
110         SysTryCatch(NID_SEC_CRYPTO, pKdf2Parameters, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
111
112         r = pKdf2Parameters->Construct(*pKdfParam);
113         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
114
115         __keyDerivationFunction.Construct(OID_PBKDF2, pKdf2Parameters.get());
116         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
117
118         nidMacAlgo = OBJ_obj2nid(pMacObj->encryption->algorithm);
119         macOid = _PkcsUtility::ConvertToOid(nidMacAlgo);
120
121         r = GetLastResult();
122         SysTryCatch(NID_SEC_CRYPTO, r != E_UNSUPPORTED_ALGORITHM, r = E_UNSUPPORTED_ALGORITHM, E_UNSUPPORTED_ALGORITHM, "[E_UNSUPPORTED_ALGORITHM] The input algorithm is not supported.");
123
124         r = __messageAuthScheme.Construct(macOid, null);
125         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
126
127 CATCH:
128
129         PBE2PARAM_free(pMacObj);
130         return r;
131 }
132
133 result
134 _Pkcs05PbMacParametersImpl::Construct(const AlgorithmIdentifier& keyDerivationFunction, const AlgorithmIdentifier& messageAuthScheme)
135 {
136         result r = E_SUCCESS;
137
138         std::unique_ptr< IAlgorithmParameters > pParam(keyDerivationFunction.GetParametersN());
139         SysTryReturn(NID_SEC_CRYPTO, pParam != null, r, r, "[%s] Failed to get the parameters.", GetErrorMessage(r));
140
141         r = __keyDerivationFunction.Construct(keyDerivationFunction.GetAlgorithmObjectId(), pParam.get());
142         SysTryReturn(NID_SEC_CRYPTO, !IsFailed(r), r, r, "[%s] Failed to construct the algorithm identifier.", GetErrorMessage(r));
143
144         std::unique_ptr< IAlgorithmParameters > pAuthParam(messageAuthScheme.GetParametersN());
145         SysTryReturn(NID_SEC_CRYPTO, pParam != null, r, r, "[%s] Failed to get the parameters.", GetErrorMessage(r));
146
147         r = __messageAuthScheme.Construct(messageAuthScheme.GetAlgorithmObjectId(), pAuthParam.get());
148         SysTryReturn(NID_SEC_CRYPTO, !IsFailed(r), r, r, "[%s] Failed to construct the algorithm identifier.", GetErrorMessage(r));
149
150         return r;
151 }
152
153
154 ByteBuffer*
155 _Pkcs05PbMacParametersImpl::GetEncodedDataN(void) const
156 {
157
158         result r = E_SUCCESS;
159         PBE2PARAM* pMacObj = null;
160         byte* pTemp = {0, };
161         int value = 0;
162         int algoNid = 0;
163         int prfNid = 0;
164         int ret = 0;
165         Tizen::Base::String keyOid = null;
166         Tizen::Base::String macAlgo = null;
167         Tizen::Base::String prfOid = null;
168         std::unique_ptr< Pkcs05PbKdf2Parameters > pKeyParams;
169         std::unique_ptr< ByteBuffer > pSalt;
170         std::unique_ptr< ByteBuffer > pEncMacParam;
171
172         SysAssertf(__keyDerivationFunction.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
173         SysAssertf(__messageAuthScheme.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
174
175         keyOid = __keyDerivationFunction.GetAlgorithmObjectId();
176
177         macAlgo = __messageAuthScheme.GetAlgorithmObjectId();
178
179         pKeyParams = std::unique_ptr< Pkcs05PbKdf2Parameters >(dynamic_cast< Pkcs05PbKdf2Parameters* >(__keyDerivationFunction.GetParametersN()));
180         SysTryReturn(NID_SEC_CRYPTO, pKeyParams, null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
181
182         pSalt = std::unique_ptr< ByteBuffer >(new (std::nothrow) ByteBuffer());
183         SysTryCatch(NID_SEC_CRYPTO, pSalt != null, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
184
185         SysTryCatch(NID_SEC_CRYPTO, pKeyParams->GetSaltValue().GetRemaining() > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] The method cannot proceed due to a severe system error.");
186
187         r = pSalt->Construct(pKeyParams->GetSaltValue());
188         SysTryReturn(NID_SEC_CRYPTO, !IsFailed(r), null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
189
190         pMacObj = PBE2PARAM_new();
191         SysTryReturn(NID_SEC_CRYPTO, pMacObj != null, null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
192
193         prfOid = (pKeyParams->GetPrf()).GetAlgorithmObjectId();
194         prfNid = _PkcsUtility::ConvertToNid(prfOid);
195
196         pMacObj->keyfunc = _PkcsUtility::GenerateKdfParametersN(pKeyParams->GetIterationCount(), const_cast< unsigned char* >(pSalt->GetPointer()), pSalt->GetRemaining(), prfNid, pKeyParams->GetDerivedKeyLength());
197         SysTryCatch(NID_SEC_CRYPTO, pMacObj->keyfunc != null, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] The method cannot proceed due to a severe system error.");
198
199         algoNid = _PkcsUtility::ConvertToNid(macAlgo);
200
201         pMacObj->encryption = X509_ALGOR_new();
202         SysTryCatch(NID_SEC_CRYPTO, (pMacObj->encryption != null), r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
203
204         ret = X509_ALGOR_set0(pMacObj->encryption, OBJ_nid2obj(algoNid), V_ASN1_NULL, NULL);
205         SysTryCatch(NID_SEC_CRYPTO, ret > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] The method cannot proceed due to a severe system error.");
206
207         // encode the PBE2PARAM structure
208
209         value = i2d_PBE2PARAM(pMacObj, &pTemp);
210         SysTryCatch(NID_SEC_CRYPTO, value > 0, r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] The method cannot proceed due to a severe system error.");
211
212         pEncMacParam = std::unique_ptr< ByteBuffer >(new (std::nothrow) ByteBuffer());
213         SysTryCatch(NID_SEC_CRYPTO, pEncMacParam, r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
214
215         r = pEncMacParam->Construct(value);
216         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_OUT_OF_MEMORY, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] The memory is insufficient.");
217
218         r = pEncMacParam->SetArray(pTemp, 0, value);
219         SysTryCatch(NID_SEC_CRYPTO, !IsFailed(r), r = E_SYSTEM, E_SYSTEM, "[E_SYSTEM] The method cannot proceed due to a severe system error.");
220
221         pEncMacParam->Flip();
222
223 CATCH:
224
225         if (IsFailed(r))
226         {
227                 pEncMacParam.reset(null);
228         }
229         PBE2PARAM_free(pMacObj);
230         OPENSSL_free(pTemp);
231         SetLastResult(r);
232         return pEncMacParam.release();
233
234 }
235
236
237
238 const AlgorithmIdentifier&
239 _Pkcs05PbMacParametersImpl::GetKeyDerivationAlgorithm(void) const
240 {
241         ClearLastResult();
242
243         SysAssertf(__keyDerivationFunction.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
244         SysAssertf(__messageAuthScheme.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
245
246         return __keyDerivationFunction;
247 }
248
249 const AlgorithmIdentifier&
250 _Pkcs05PbMacParametersImpl::GetMacAlgorithm(void) const
251 {
252         ClearLastResult();
253
254         SysAssertf(__keyDerivationFunction.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
255         SysAssertf(__messageAuthScheme.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
256
257         return __messageAuthScheme;
258 }
259
260 PkcsAlgorithmParameterType
261 _Pkcs05PbMacParametersImpl::GetType(void) const
262 {
263         ClearLastResult();
264         return PKCS_ALGO_PARAM_TYPE_PKCS05_MAC;
265 }
266
267 bool
268 _Pkcs05PbMacParametersImpl::Equals(const Object& obj) const
269 {
270         bool value = false;
271
272         SysAssertf(__keyDerivationFunction.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
273         SysAssertf(__messageAuthScheme.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
274
275         const _Pkcs05PbMacParametersImpl* pOther = dynamic_cast< const _Pkcs05PbMacParametersImpl* >(&obj);
276
277         SysTryReturn(NID_SEC_CRYPTO, pOther != null, false, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
278
279         if (pOther == this)
280         {
281                 return true;
282         }
283
284         SysTryReturn(NID_SEC_CRYPTO, pOther->GetKeyDerivationAlgorithm().GetAlgorithmObjectId().GetLength() > 0, false, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
285         SysTryReturn(NID_SEC_CRYPTO, pOther->GetMacAlgorithm().GetAlgorithmObjectId().GetLength() > 0, false, E_INVALID_ARG, "[E_INVALID_ARG] The specified input parameter is invalid.");
286
287         value = (__keyDerivationFunction.Equals(pOther->GetKeyDerivationAlgorithm())) && (__messageAuthScheme.Equals(pOther->GetMacAlgorithm()));
288
289         return value;
290
291 }
292
293 int
294 _Pkcs05PbMacParametersImpl::GetHashCode(void) const
295 {
296         SysAssertf(__keyDerivationFunction.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
297         SysAssertf(__messageAuthScheme.GetAlgorithmObjectId().GetLength() > 0, "Not yet constructed. Construct () should be called before use.");
298
299         return __keyDerivationFunction.GetHashCode() + __messageAuthScheme.GetHashCode();
300 }
301
302 _Pkcs05PbMacParametersImpl*
303 _Pkcs05PbMacParametersImpl::GetInstance(Pkcs05PbMacParameters& pkcs05PbMacParameters)
304 {
305         return pkcs05PbMacParameters.__pPkcs05PbMacParametersImpl;
306 }
307
308 const _Pkcs05PbMacParametersImpl*
309 _Pkcs05PbMacParametersImpl::GetInstance(const Pkcs05PbMacParameters& pkcs05PbMacParameters)
310 {
311         return pkcs05PbMacParameters.__pPkcs05PbMacParametersImpl;
312 }
313
314 } } } // end of namespace Pkcs