|
1 /* |
|
2 * Copyright (c) 1998-2009 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of the License "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 #include "taction_build.h" |
|
20 #include "t_inputextra.h" |
|
21 |
|
22 _LIT(KRoot, "build\\CA3_root.crt"); |
|
23 _LIT(KCA2, "build\\CA2.crt"); |
|
24 _LIT(KCA1, "build\\CA1.crt"); |
|
25 _LIT(KEE, "build\\EE.crt"); |
|
26 |
|
27 _LIT(KRootStart, "<root>"); |
|
28 _LIT(KRootEnd, "</root>"); |
|
29 _LIT(KCertificateStart, "<certificate>"); |
|
30 _LIT(KCertificateEnd, "</certificate>"); |
|
31 _LIT(KLabelStart, "<label>"); |
|
32 _LIT(KLabelEnd, "</label>"); |
|
33 _LIT(KExtraStart, "<extra>"); |
|
34 _LIT(KExtraEnd, "</extra>"); |
|
35 _LIT(KInitStart, "<init>"); |
|
36 _LIT(KInitEnd, "</init>"); |
|
37 _LIT(KAddCallStart, "<addcall>"); |
|
38 _LIT(KAddCallEnd, "</addcall>"); |
|
39 |
|
40 _LIT(KAddCertStart, "<addcert>"); |
|
41 _LIT(KAddCertEnd, "</addcert>"); |
|
42 |
|
43 _LIT(KCertPath, "\\pkixtestdata\\"); |
|
44 |
|
45 CAddCall* CAddCall::NewL(const TDesC& aBuf) |
|
46 { |
|
47 CAddCall* self = CAddCall::NewLC(aBuf); |
|
48 CleanupStack::Pop(); |
|
49 return self; |
|
50 } |
|
51 |
|
52 CAddCall* CAddCall::NewLC(const TDesC& aBuf) |
|
53 { |
|
54 CAddCall* self = new(ELeave) CAddCall; |
|
55 CleanupStack::PushL(self); |
|
56 self->ConstructL(aBuf); |
|
57 return self; |
|
58 } |
|
59 |
|
60 CAddCall::~CAddCall() |
|
61 { |
|
62 delete iCertsToAdd; |
|
63 } |
|
64 |
|
65 CAddCall::CAddCall() |
|
66 { |
|
67 } |
|
68 |
|
69 void CAddCall::ConstructL(const TDesC& aBuf) |
|
70 { |
|
71 iCertsToAdd = new(ELeave) CDesCArrayFlat (1); |
|
72 TInt pos = 0; |
|
73 while(AddCert(aBuf, KAddCertStart, KAddCertEnd, pos, *iCertsToAdd)) |
|
74 { |
|
75 } |
|
76 } |
|
77 |
|
78 TBool CAddCall::AddCert(const TDesC& aBuf, const TDesC& aStart, const TDesC& aEnd, TInt& aPos, CDesCArray& aCerts) |
|
79 { |
|
80 TPtrC certBuf = Input::ParseElement(aBuf, aStart, aEnd, aPos); |
|
81 if (certBuf != KNullDesC) |
|
82 { |
|
83 aCerts.AppendL(certBuf); |
|
84 return ETrue; |
|
85 } |
|
86 |
|
87 return EFalse; |
|
88 } |
|
89 |
|
90 CTestAction* CTestActionBuild::NewL(RFs& aFs, |
|
91 CConsoleBase& aConsole, |
|
92 Output& aOut, |
|
93 const TTestActionSpec& aTestActionSpec) |
|
94 { |
|
95 CTestAction* self = CTestActionBuild::NewLC(aFs, aConsole, |
|
96 aOut, aTestActionSpec); |
|
97 CleanupStack::Pop(self); |
|
98 return self; |
|
99 } |
|
100 |
|
101 CTestAction* CTestActionBuild::NewLC(RFs& aFs, |
|
102 CConsoleBase& aConsole, |
|
103 Output& aOut, |
|
104 const TTestActionSpec& aTestActionSpec) |
|
105 { |
|
106 CTestActionBuild* self = new(ELeave) CTestActionBuild(aFs, aConsole, |
|
107 aOut); |
|
108 CleanupStack::PushL(self); |
|
109 self->ConstructL(aTestActionSpec); |
|
110 return self; |
|
111 } |
|
112 |
|
113 CTestActionBuild::~CTestActionBuild() |
|
114 { |
|
115 delete iUnifiedCertStore; |
|
116 delete iCertUtils; |
|
117 delete iChain; |
|
118 delete iExtraCertsFileName; |
|
119 delete iExtraCertsLabel; |
|
120 delete iInitCertsFileName; |
|
121 delete iInitCertsLabel; |
|
122 iAddCalls.ResetAndDestroy(); |
|
123 iAddCalls.Close(); |
|
124 delete iValidationResult; |
|
125 } |
|
126 |
|
127 CTestActionBuild::CTestActionBuild(RFs& aFs, |
|
128 CConsoleBase& aConsole, |
|
129 Output& aOut) |
|
130 : CTestAction(aConsole, aOut), iFs(aFs) |
|
131 { |
|
132 } |
|
133 |
|
134 void CTestActionBuild::ConstructL(const TTestActionSpec& aTestActionSpec) |
|
135 { |
|
136 CTestAction::ConstructL(aTestActionSpec); |
|
137 |
|
138 TInt pos = 0; |
|
139 TInt err = KErrNone; |
|
140 HBufC* aBody = HBufC::NewLC(aTestActionSpec.iActionBody.Length()); |
|
141 aBody->Des().Copy(aTestActionSpec.iActionBody); |
|
142 TPtrC rootCert(Input::ParseElement(*aBody, |
|
143 KRootStart, KRootEnd, pos, err)); |
|
144 TInt dummyPos = 0; |
|
145 iRootCertFileName = Input::ParseElement(rootCert, KCertificateStart, |
|
146 KCertificateEnd, dummyPos); |
|
147 iRootCertLabel = Input::ParseElement(rootCert, KLabelStart, |
|
148 KLabelEnd, dummyPos); |
|
149 |
|
150 iExtraCertsFileName = new(ELeave) CDesCArrayFlat(1); |
|
151 iExtraCertsLabel = new(ELeave) CDesCArrayFlat(1); |
|
152 while(AddCert(*aBody, KExtraStart, KExtraEnd, pos, *iExtraCertsFileName, |
|
153 *iExtraCertsLabel)) |
|
154 { |
|
155 } |
|
156 |
|
157 iInitCertsFileName = new(ELeave) CDesCArrayFlat(1); |
|
158 iInitCertsLabel = new(ELeave) CDesCArrayFlat(1); |
|
159 while(AddCert(*aBody, KInitStart, KInitEnd, pos, *iInitCertsFileName, |
|
160 *iInitCertsLabel)) |
|
161 { |
|
162 } |
|
163 |
|
164 while(AddAddCalls(*aBody, pos)) |
|
165 { |
|
166 } |
|
167 |
|
168 iValidationResult = CPKIXValidationResult::NewL(); |
|
169 |
|
170 TDriveUnit sysDrive (RFs::GetSystemDrive()); |
|
171 TDriveName driveName(sysDrive.Name()); |
|
172 iCertPath.Copy(driveName); |
|
173 iCertPath.Append(KCertPath); |
|
174 |
|
175 CleanupStack::PopAndDestroy(aBody); |
|
176 } |
|
177 |
|
178 void CTestActionBuild::DoPerformPrerequisite(TRequestStatus& aStatus) |
|
179 { |
|
180 iActionState = EAction; |
|
181 TRequestStatus* status = &aStatus; |
|
182 User::RequestComplete(status, KErrNone); |
|
183 } |
|
184 |
|
185 void CTestActionBuild::DoPerformPostrequisite(TRequestStatus& aStatus) |
|
186 { |
|
187 TRequestStatus* status = &aStatus; |
|
188 User::RequestComplete(status, KErrNone); |
|
189 } |
|
190 |
|
191 void CTestActionBuild::PerformAction(TRequestStatus& aStatus) |
|
192 { |
|
193 switch (iState) |
|
194 { |
|
195 case EInitCertStoreManager1: |
|
196 __ASSERT_DEBUG(!iUnifiedCertStore, User::Panic(_L("CPKIXCertTest"), 1)); |
|
197 iUnifiedCertStore = CUnifiedCertStore::NewL(iFs, ETrue); // We open the store for writing |
|
198 iUnifiedCertStore->Initialize(aStatus); |
|
199 iState = ERemoveCertsBeforeTest; |
|
200 break; |
|
201 |
|
202 case ERemoveCertsBeforeTest: |
|
203 // A new iCertUtils is created and destroyed for each test because |
|
204 // we need to close before validating as the chain won't be able to |
|
205 // open the store manager if it is already open for write elsewhere |
|
206 __ASSERT_DEBUG(!iCertUtils, User::Panic(_L("CPKIXCertTest"), 1)); |
|
207 iCertUtils = CCertUtils::NewL(iFs); |
|
208 iCertUtils->RemoveCertsL(*iUnifiedCertStore, aStatus); |
|
209 iState = EAddRoot; |
|
210 break; |
|
211 |
|
212 case EAddRoot: |
|
213 { |
|
214 TUid uid = { 1 }; |
|
215 TRAPD(err, iCertUtils->RemoveApplicationL(uid)); |
|
216 iCertUtils->AddApplicationL(_L("testpkix"), uid); |
|
217 TUid uid2 = { 2 }; |
|
218 TRAP(err, iCertUtils->RemoveApplicationL(uid2)); |
|
219 iCertUtils->AddApplicationL(_L("testpkix"), uid2); |
|
220 iCertUtils->AddCert(iRootCertLabel, EX509Certificate, ECACertificate, |
|
221 1, iCertPath, iRootCertFileName, *iUnifiedCertStore, aStatus);//1 is trusted for our use |
|
222 iState = EAddIntermediateCerts; |
|
223 } |
|
224 break; |
|
225 |
|
226 case EAddIntermediateCerts: |
|
227 iCertUtils->AddCACertsL(*iExtraCertsFileName, |
|
228 *iExtraCertsLabel, EX509Certificate, |
|
229 2, iCertPath, *iUnifiedCertStore, aStatus); // 2 not trusted for our use |
|
230 iState = EDoBuildTestStart; |
|
231 break; |
|
232 |
|
233 case EDoBuildTestStart: |
|
234 { |
|
235 // We have to close the store manager because it is open for write |
|
236 // and CPKIXCertChain won't be able to open it if we don't close it |
|
237 // iCertUtils muts also be deleted since it uses this store manager |
|
238 delete iCertUtils; |
|
239 iCertUtils = 0; |
|
240 delete iUnifiedCertStore; |
|
241 iUnifiedCertStore = 0; |
|
242 |
|
243 __ASSERT_DEBUG(!iChain, User::Panic(_L("CPKIXCertTest"), 1)); |
|
244 |
|
245 HBufC8* initCerts = |
|
246 InputExtra::ReadFilesLC(*iInitCertsFileName, iCertPath, iFs); |
|
247 TUid testUid = TUid::Uid(1); |
|
248 iChain = CPKIXCertChain::NewL(iFs, *initCerts, testUid); |
|
249 CleanupStack::PopAndDestroy(initCerts); // initCerts |
|
250 |
|
251 TInt addCount = iAddCalls.Count(); |
|
252 for (TInt i = 0; i < addCount; i++) |
|
253 { |
|
254 const CAddCall* addCall = iAddCalls[i]; |
|
255 HBufC8* addCerts = InputExtra::ReadFilesLC(*(addCall->iCertsToAdd), |
|
256 iCertPath, iFs); |
|
257 // the root of the chain is set when the certificate chain is getting created through the CPKIXCertChainAO |
|
258 // via CPKIXChainBuilder. If the chain has the root certificate then the iChainHasRoot is set which is returned |
|
259 // through this method. If the corresponding certificate does not have the issuer certificate in the chain then |
|
260 // the extra certificates provided in the test script would be added for completing the chain. |
|
261 if (!(iChain->ChainHasRoot())) |
|
262 { |
|
263 iChain->AddCertL(*addCerts); |
|
264 } |
|
265 CleanupStack::PopAndDestroy(); // addCerts |
|
266 } |
|
267 |
|
268 iTime.HomeTime(); |
|
269 |
|
270 iChain->ValidateL(*iValidationResult, iTime, aStatus); |
|
271 |
|
272 iState = EDoBuildTestFinished; |
|
273 } |
|
274 break; |
|
275 |
|
276 case EDoBuildTestFinished: |
|
277 { |
|
278 iResult = CompareChainsL(*iChain); |
|
279 delete iChain; |
|
280 iChain = 0; |
|
281 iState = EInitCertStoreManager2; |
|
282 TRequestStatus* status = &aStatus; |
|
283 User::RequestComplete(status, KErrNone); |
|
284 } |
|
285 break; |
|
286 |
|
287 case EInitCertStoreManager2: |
|
288 __ASSERT_DEBUG(!iChain, User::Panic(_L("CPKIXCertTest"), 1)); |
|
289 //TRAP(err, HandleEDoBuildTests_SingleTest_InitCertStoreManager2L()); |
|
290 iUnifiedCertStore = CUnifiedCertStore::NewL(iFs, ETrue); // We open the store for writing |
|
291 iUnifiedCertStore->Initialize(aStatus); |
|
292 iState = ERemoveCertsAfterTest; |
|
293 break; |
|
294 |
|
295 case ERemoveCertsAfterTest: |
|
296 __ASSERT_DEBUG(!iCertUtils, User::Panic(_L("CPKIXCertTest"), 1)); |
|
297 iCertUtils = CCertUtils::NewL(iFs); |
|
298 iCertUtils->RemoveCertsL(*iUnifiedCertStore, aStatus); |
|
299 iState = EEnd; |
|
300 break; |
|
301 |
|
302 case EEnd: |
|
303 { |
|
304 delete iCertUtils; |
|
305 iCertUtils = 0; |
|
306 delete iUnifiedCertStore; |
|
307 iUnifiedCertStore = 0; |
|
308 TRequestStatus* status = &aStatus; |
|
309 iFinished = ETrue; |
|
310 User::RequestComplete(status, KErrNone); |
|
311 } |
|
312 break; |
|
313 } |
|
314 } |
|
315 |
|
316 TBool CTestActionBuild::TestResult(TInt /*aError*/) |
|
317 { |
|
318 return 0; |
|
319 } |
|
320 |
|
321 void CTestActionBuild::PerformCancel() |
|
322 { |
|
323 } |
|
324 |
|
325 void CTestActionBuild::Reset() |
|
326 { |
|
327 } |
|
328 |
|
329 void CTestActionBuild::DoReportAction() |
|
330 { |
|
331 iConsole.Printf(_L("u")); |
|
332 } |
|
333 |
|
334 void CTestActionBuild::DoCheckResult(TInt /*aError*/) |
|
335 { |
|
336 } |
|
337 |
|
338 TBool CTestActionBuild::AddCert(const TDesC& aBuf, |
|
339 const TDesC& aStart, |
|
340 const TDesC& aEnd, TInt& aPos, |
|
341 CDesCArray& aCertsFileName, |
|
342 CDesCArray& aCertsLabel) |
|
343 { |
|
344 TPtrC certBuf = Input::ParseElement(aBuf, aStart, aEnd, aPos); |
|
345 TInt dummyPos = 0; |
|
346 if (certBuf != KNullDesC) |
|
347 { |
|
348 aCertsFileName.AppendL(Input::ParseElement(certBuf, KCertificateStart, |
|
349 KCertificateEnd, dummyPos)); |
|
350 aCertsLabel.AppendL(Input::ParseElement(certBuf, KLabelStart, |
|
351 KLabelEnd, dummyPos)); |
|
352 return ETrue; |
|
353 } |
|
354 return EFalse; |
|
355 } |
|
356 |
|
357 TBool CTestActionBuild::AddAddCalls(const TDesC& aBuf, TInt& aPos) |
|
358 { |
|
359 TPtrC addCallsBuf = Input::ParseElement(aBuf, KAddCallStart, KAddCallEnd, aPos); |
|
360 if (addCallsBuf != KNullDesC) |
|
361 { |
|
362 CAddCall* addCall = CAddCall::NewL(addCallsBuf); |
|
363 iAddCalls.Append(addCall); |
|
364 return ETrue; |
|
365 } |
|
366 return EFalse; |
|
367 } |
|
368 |
|
369 TBool CTestActionBuild::CompareChainsL(const CPKIXCertChain& aChain) |
|
370 { |
|
371 if (aChain.Count() != 4) |
|
372 { |
|
373 return EFalse; |
|
374 } |
|
375 if ( (!CompareCertL(aChain.Cert(0), KEE)) || |
|
376 (!CompareCertL(aChain.Cert(1), KCA1)) || |
|
377 (!CompareCertL(aChain.Cert(2), KCA2)) || |
|
378 (!CompareCertL(aChain.Cert(3), KRoot)) ) |
|
379 { |
|
380 return EFalse; |
|
381 } |
|
382 else |
|
383 { |
|
384 return ETrue; |
|
385 } |
|
386 } |
|
387 |
|
388 TBool CTestActionBuild::CompareCertL(const CX509Certificate& aCert, const TDesC& aFilename) |
|
389 { |
|
390 HBufC8* correct = Input::ReadFileLC(aFilename, iCertPath, iFs); |
|
391 TBool res = (correct->Des() == aCert.Encoding()); |
|
392 CleanupStack::PopAndDestroy(); |
|
393 return res; |
|
394 } |