1 /* |
|
2 * Copyright (c) 2010 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 "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 #include <coemain.h> |
|
19 #include <eikenv.h> |
|
20 #include <pathinfo.h> |
|
21 #include <apgtask.h> |
|
22 #include <bautils.h> |
|
23 |
|
24 #include "launchertraces.h" |
|
25 #include "e32image.h" |
|
26 #include "launcherxmlparser.h" |
|
27 #include "launcherdllparser.h" |
|
28 #include "launcherengine.h" |
|
29 |
|
30 _LIT(KLogFileName, "LauncherLog.txt"); |
|
31 _LIT(KBCLogFileName, "LauncherBCLog.txt"); |
|
32 _LIT(KSystemDllsFileName, "SystemDlls.txt"); |
|
33 _LIT(KRequiredDllsFileName, "RequiredDlls.xml"); |
|
34 _LIT(KDotXML,".xml"); |
|
35 _LIT(KDotLauncherXML,".launcherxml"); |
|
36 |
|
37 _LIT(KFileSeparator, "\t"); |
|
38 _LIT(KFileNewLine, "\r\n"); |
|
39 |
|
40 _LIT(KNewLine, "\n"); |
|
41 |
|
42 const TInt KMaxAppsArraySize=250; |
|
43 const TInt KMaxDllArraySize=5000; |
|
44 const TInt KLauncherLogBufferSize = 4096; |
|
45 |
|
46 // After this many issues, issues are buffered and printed |
|
47 // in the end of analysis |
|
48 const TInt KBigBufferUsageThreshold=10; |
|
49 |
|
50 // Buffer allocation unit |
|
51 const TInt KBigBufferAllocBytes=1024; |
|
52 |
|
53 // --------------------------------------------------------------------------- |
|
54 |
|
55 CLauncherEngine* CLauncherEngine::NewL(MLauncherUI *aLauncherUI) |
|
56 { |
|
57 CLauncherEngine* self = new(ELeave) CLauncherEngine; |
|
58 CleanupStack::PushL(self); |
|
59 self->ConstructL(aLauncherUI); |
|
60 CleanupStack::Pop(); |
|
61 return self; |
|
62 } |
|
63 |
|
64 // --------------------------------------------------------------------------- |
|
65 |
|
66 CLauncherEngine::CLauncherEngine() : CActive(EActivePriorityIpcEventsHigh) |
|
67 { |
|
68 } |
|
69 |
|
70 // --------------------------------------------------------------------------- |
|
71 |
|
72 template <typename T> |
|
73 void AppendLogBufferL(const TDesC& aText, T*& aBuf, TInt aIncreaseStep = KLauncherLogBufferSize) |
|
74 { |
|
75 if( aBuf == 0 ) |
|
76 { |
|
77 aBuf = T::NewL(aIncreaseStep); |
|
78 } |
|
79 |
|
80 TInt currentMaxLength = aBuf->Des().MaxLength(); |
|
81 if( aBuf->Des().Length() + aText.Length() > currentMaxLength ) |
|
82 { |
|
83 TInt increaseSize = Max(aText.Length(), aIncreaseStep); |
|
84 aBuf = aBuf->ReAllocL(aBuf->Des().MaxLength() + increaseSize ); |
|
85 } |
|
86 aBuf->Des().Append(aText); |
|
87 } |
|
88 |
|
89 // --------------------------------------------------------------------------- |
|
90 |
|
91 void CLauncherEngine::ConstructL(MLauncherUI *aLauncherUI) |
|
92 { |
|
93 LOGSTRING("Launcher: CLauncherEngine::ConstructL"); |
|
94 |
|
95 User::LeaveIfNull( aLauncherUI ); |
|
96 |
|
97 iLauncherUI = aLauncherUI; |
|
98 |
|
99 |
|
100 iEnv = CEikonEnv::Static(); |
|
101 iLaunchingIsActive = EFalse; |
|
102 iDLLAnalysisIsActive = EFalse; |
|
103 iSkipHiddenAndEmbedOnly = ETrue; |
|
104 |
|
105 User::LeaveIfError(iTimer.CreateLocal()); |
|
106 |
|
107 User::LeaveIfError(iLs.Connect()); |
|
108 User::LeaveIfError(iWs.Connect()); |
|
109 |
|
110 iAppThreadChecker = CAppThreadChecker::NewL(this); |
|
111 iAppRunningChecker = CAppRunningChecker::NewL(this); |
|
112 |
|
113 iAllAppsArray = new(ELeave) CDesCArrayFlat(KMaxAppsArraySize); |
|
114 iAppsArray = new(ELeave) CDesCArrayFlat(KMaxAppsArraySize); |
|
115 iSystemDllArray = new(ELeave) CDesCArrayFlat(KMaxDllArraySize); |
|
116 |
|
117 iLogWriteBuf = HBufC8::NewL(KLauncherLogBufferSize); |
|
118 |
|
119 iLogFilePath = PathInfo::PhoneMemoryRootPath(); |
|
120 iLogFilePath.Append( KLogFileName ); |
|
121 |
|
122 iBCLogFilePath = PathInfo::PhoneMemoryRootPath(); |
|
123 iBCLogFilePath.Append( KBCLogFileName ); |
|
124 |
|
125 iSystemDllsFilePath = PathInfo::PhoneMemoryRootPath(); |
|
126 iSystemDllsFilePath.Append( KSystemDllsFileName ); |
|
127 |
|
128 iRequiredDllsFilePath = PathInfo::PhoneMemoryRootPath(); |
|
129 iRequiredDllsFilePath.Append( KRequiredDllsFileName ); |
|
130 |
|
131 iDLLParser = CLauncherDLLParser::NewL(); |
|
132 |
|
133 CActiveScheduler::Add(this); |
|
134 } |
|
135 |
|
136 // --------------------------------------------------------------------------- |
|
137 |
|
138 CLauncherEngine::~CLauncherEngine() |
|
139 { |
|
140 LOGSTRING("Launcher: CLauncherEngine::~CLauncherEngine"); |
|
141 |
|
142 Cancel(); |
|
143 |
|
144 // close the log |
|
145 iLogFile.Close(); |
|
146 iBCLogFile.Close(); |
|
147 if (iLogWriteBuf) |
|
148 delete iLogWriteBuf; |
|
149 |
|
150 if (iAppRunningChecker) |
|
151 delete iAppRunningChecker; |
|
152 |
|
153 if (iAppThreadChecker) |
|
154 delete iAppThreadChecker; |
|
155 |
|
156 if (iSystemDllArray) |
|
157 { |
|
158 iSystemDllArray->Reset(); |
|
159 delete iSystemDllArray; |
|
160 } |
|
161 |
|
162 if (iAppsArray) |
|
163 { |
|
164 iAppsArray->Reset(); |
|
165 delete iAppsArray; |
|
166 } |
|
167 |
|
168 |
|
169 if (iAllAppsArray) |
|
170 { |
|
171 iAllAppsArray->Reset(); |
|
172 delete iAllAppsArray; |
|
173 } |
|
174 |
|
175 delete iXMLParser; |
|
176 // delete iDLLParser; |
|
177 //delete iDLLElement; |
|
178 delete iBCIssuesBigBuffer; |
|
179 |
|
180 iWs.Close(); |
|
181 iLs.Close(); |
|
182 iTimer.Close(); |
|
183 } |
|
184 |
|
185 // --------------------------------------------------------------------------- |
|
186 |
|
187 void CLauncherEngine::DoCancel() |
|
188 { |
|
189 LOGSTRING("Launcher: CLauncherEngine::DoCancel"); |
|
190 |
|
191 if( iXMLParser ) |
|
192 { |
|
193 iXMLParser->Cancel(); |
|
194 } |
|
195 iTimer.Cancel(); |
|
196 |
|
197 } |
|
198 |
|
199 // --------------------------------------------------------------------------- |
|
200 |
|
201 void CLauncherEngine::RunL() |
|
202 { |
|
203 |
|
204 LOGSTRING("Launcher: CLauncherEngine::RunL"); |
|
205 TInt err = iStatus.Int(); |
|
206 User::LeaveIfError(err); |
|
207 |
|
208 // write full app path to the log file |
|
209 WriteInitialStuffToTheLogL(iAppsArray->MdcaPoint(iAppLaunchCounter), iLogFile); |
|
210 |
|
211 // get the uid of the current app |
|
212 iCurrentAppUid = KNullUid; |
|
213 TApaAppInfo appInfo; |
|
214 iLs.GetAllApps(); |
|
215 while (iLs.GetNextApp(appInfo) == KErrNone) |
|
216 { |
|
217 if (appInfo.iFullName.CompareF( iAppsArray->MdcaPoint(iAppLaunchCounter) ) == 0) |
|
218 { |
|
219 iCurrentAppUid = appInfo.iUid; |
|
220 break; |
|
221 } |
|
222 } |
|
223 |
|
224 if (iCurrentAppUid == KNullUid) |
|
225 { |
|
226 iLogWriteBuf->Des().Append(_L("[WARN: App has no UID] ")); |
|
227 } |
|
228 |
|
229 // parse the filename |
|
230 TParse nameParser; |
|
231 nameParser.SetNoWild(iAppsArray->MdcaPoint(iAppLaunchCounter), NULL, NULL); |
|
232 iCurrentAppNameAndExt.Copy(nameParser.Drive()); |
|
233 iCurrentAppNameAndExt.Append(nameParser.NameAndExt()); |
|
234 |
|
235 // do not try to launch these apps |
|
236 if (iAppsArray->MdcaPoint(iAppLaunchCounter).FindF(_L("\\Launcher.")) != KErrNotFound |
|
237 || iAppsArray->MdcaPoint(iAppLaunchCounter).FindF(_L("\\Phone.")) != KErrNotFound |
|
238 || iAppsArray->MdcaPoint(iAppLaunchCounter).FindF(_L("\\Startup.")) != KErrNotFound |
|
239 || iAppsArray->MdcaPoint(iAppLaunchCounter).FindF(_L("\\SplashScreen.")) != KErrNotFound |
|
240 || iAppsArray->MdcaPoint(iAppLaunchCounter).FindF(_L("\\eshell.")) != KErrNotFound) |
|
241 { |
|
242 |
|
243 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
244 iLauncherUI->PrintText(_L(": SKIPPED automatically\n")); |
|
245 |
|
246 iLogWriteBuf->Des().Append(_L("[SKIPPED automatically] ")); |
|
247 iLogWriteBuf->Des().Append(KFileNewLine); |
|
248 iLogFile.Write(iLogWriteBuf->Des()); |
|
249 |
|
250 iSkippedCases++; |
|
251 CheckForMoreAppsL(); |
|
252 } |
|
253 |
|
254 else |
|
255 { |
|
256 |
|
257 // dependency check not needed if the app is in the ROM/ROFS, because they'll be checked automatically |
|
258 // when the rom image is built |
|
259 |
|
260 if (iCurrentAppNameAndExt[0] != 'Z' && iCurrentAppNameAndExt[0] != 'z') |
|
261 { |
|
262 |
|
263 if (iCurrentAppNameAndExt[2] == '[') // this is quite likely a Java application, no dependency test needed |
|
264 { |
|
265 iLogWriteBuf->Des().Append(_L("[Dependency check not done] ")); |
|
266 } |
|
267 else |
|
268 { // otherwise check depencies |
|
269 |
|
270 #ifdef __WINS__ |
|
271 |
|
272 // emulator not supported |
|
273 |
|
274 #else |
|
275 |
|
276 // ELF binaries |
|
277 |
|
278 CDesCArray* missingDllArray = NULL; |
|
279 |
|
280 TRAPD(err, missingDllArray = DependencyCheckForE32ImageL()); |
|
281 |
|
282 // some error happened while processing the E32 image |
|
283 if (err != KErrNone) |
|
284 { |
|
285 |
|
286 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
287 iLauncherUI->PrintText(_L(": unable to read import table!\n")); |
|
288 |
|
289 iLogWriteBuf->Des().Append(_L("[Unable to read import table!] ")); |
|
290 } |
|
291 |
|
292 // print missing dependencies |
|
293 else if (err==KErrNone && missingDllArray) |
|
294 { |
|
295 if (missingDllArray->MdcaCount() > 0) |
|
296 { |
|
297 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
298 iLauncherUI->PrintText(_L(": missing dependencies: ")); |
|
299 |
|
300 iLogWriteBuf->Des().Append(_L("[Missing dependencies: ")); |
|
301 |
|
302 for (TInt k=0; k<missingDllArray->MdcaCount(); k++) |
|
303 { |
|
304 iLauncherUI->PrintText(missingDllArray->MdcaPoint(k)); |
|
305 iLauncherUI->PrintText(_L(" ")); |
|
306 |
|
307 iLogWriteBuf->Des().Append(missingDllArray->MdcaPoint(k)); |
|
308 iLogWriteBuf->Des().Append(_L(" ")); |
|
309 } |
|
310 |
|
311 iLauncherUI->PrintText(_L("\n")); |
|
312 |
|
313 iLogWriteBuf->Des().Append(_L("] ")); |
|
314 } |
|
315 } |
|
316 |
|
317 if (missingDllArray) |
|
318 delete missingDllArray; |
|
319 |
|
320 #endif |
|
321 |
|
322 } // if '[' |
|
323 } // if 'Z' |
|
324 |
|
325 |
|
326 |
|
327 // check if the app is already running |
|
328 TApaTaskList taskList(iWs); |
|
329 TApaTask thisTask = taskList.FindApp(iCurrentAppUid); |
|
330 if (thisTask.Exists()) |
|
331 { |
|
332 iLogWriteBuf->Des().Append(_L(" [OK: App already running]")); |
|
333 iLogWriteBuf->Des().Append(KFileNewLine); |
|
334 iLogFile.Write(iLogWriteBuf->Des()); |
|
335 |
|
336 iOkCases++; |
|
337 CheckForMoreAppsL(); |
|
338 } |
|
339 |
|
340 else |
|
341 { |
|
342 // check the program's capabilities |
|
343 TApaAppCapabilityBuf buf; |
|
344 iLs.GetAppCapability(buf, iCurrentAppUid); |
|
345 TApaAppCapability cap = buf(); |
|
346 |
|
347 // if it's embeddable only, don't launch if setting is enabled |
|
348 if (cap.iEmbeddability == TApaAppCapability::EEmbeddableOnly && SkipHiddenAndEmbedOnly()) |
|
349 { |
|
350 |
|
351 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
352 iLauncherUI->PrintText(_L(": SKIPPED: embeddable only\n")); |
|
353 |
|
354 iLogWriteBuf->Des().Append(_L("[SKIPPED: embeddable only] ")); |
|
355 iLogWriteBuf->Des().Append(KFileNewLine); |
|
356 iLogFile.Write(iLogWriteBuf->Des()); |
|
357 |
|
358 iSkippedCases++; |
|
359 CheckForMoreAppsL(); |
|
360 } |
|
361 |
|
362 // if it's hidden, don't launch if setting is enabled |
|
363 else if (cap.iAppIsHidden && SkipHiddenAndEmbedOnly()) |
|
364 { |
|
365 |
|
366 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
367 iLauncherUI->PrintText(_L(": SKIPPED: hidden\n")); |
|
368 |
|
369 iLogWriteBuf->Des().Append(_L("[SKIPPED: hidden] ")); |
|
370 iLogWriteBuf->Des().Append(KFileNewLine); |
|
371 iLogFile.Write(iLogWriteBuf->Des()); |
|
372 |
|
373 iSkippedCases++; |
|
374 CheckForMoreAppsL(); |
|
375 } |
|
376 |
|
377 // otherwise do the normal launch test |
|
378 else |
|
379 { |
|
380 LaunchApplicationL(); |
|
381 } |
|
382 |
|
383 } //if (thisTask.Exists()) |
|
384 |
|
385 } //if (iAppsArray->MdcaPoint(iAppLaunchCounter).FindF |
|
386 |
|
387 } |
|
388 |
|
389 // --------------------------------------------------------------------------- |
|
390 |
|
391 CDesCArray* CLauncherEngine::ListOfAllAppsL() |
|
392 { |
|
393 LOGSTRING("Launcher: CLauncherEngine::ListOfAllAppsL"); |
|
394 |
|
395 // find all DLLs from the system |
|
396 iSystemDllArray->Reset(); |
|
397 TRAP_IGNORE( FindFiles(_L("*.dll"), _L("\\sys\\bin\\")) ); |
|
398 |
|
399 // write the list of DLLs to a file |
|
400 RFile dllFile; |
|
401 if (dllFile.Replace(iEnv->FsSession(), iSystemDllsFilePath, EFileWrite) == KErrNone) |
|
402 { |
|
403 TBuf8<KMaxFileName> dllName; |
|
404 |
|
405 for (TInt i=0; i<iSystemDllArray->MdcaCount(); i++) |
|
406 { |
|
407 dllName.Copy( iSystemDllArray->MdcaPoint(i) ); |
|
408 dllName.Append( KFileNewLine ); |
|
409 |
|
410 dllFile.Write( dllName ); |
|
411 } |
|
412 |
|
413 dllFile.Close(); |
|
414 } |
|
415 |
|
416 // reset the apps list |
|
417 iAllAppsArray->Reset(); |
|
418 |
|
419 // search all apps |
|
420 TApaAppInfo appInfo; |
|
421 iLs.GetAllApps(); |
|
422 |
|
423 while (iLs.GetNextApp(appInfo) == KErrNone) |
|
424 { |
|
425 iAllAppsArray->AppendL(appInfo.iFullName); |
|
426 } |
|
427 |
|
428 |
|
429 // remove launcher.app / launcher.exe from the list |
|
430 for (TInt i=0; i<iAllAppsArray->MdcaCount(); i++) |
|
431 { |
|
432 if (iAllAppsArray->MdcaPoint(i).FindF(_L("\\Launcher.")) != KErrNotFound) |
|
433 { |
|
434 iAllAppsArray->Delete(i); |
|
435 iAllAppsArray->Compress(); |
|
436 break; |
|
437 } |
|
438 } |
|
439 |
|
440 // sort the elements |
|
441 iAllAppsArray->Sort(); |
|
442 |
|
443 return iAllAppsArray; |
|
444 } |
|
445 |
|
446 // --------------------------------------------------------------------------- |
|
447 |
|
448 TInt CLauncherEngine::FindFiles(const TDesC& aFileName, const TDesC& aPath) |
|
449 { |
|
450 TFindFile fileFinder(iEnv->FsSession()); |
|
451 CDir* fileList; |
|
452 TInt err = fileFinder.FindWildByDir(aFileName, aPath, fileList); |
|
453 |
|
454 while (err == KErrNone) |
|
455 { |
|
456 for (TInt i=0; i<fileList->Count(); i++) |
|
457 { |
|
458 TParse fullentry; |
|
459 fullentry.Set((*fileList)[i].iName, &fileFinder.File(), NULL); |
|
460 |
|
461 TRAP(err, iSystemDllArray->AppendL(fullentry.NameAndExt())); |
|
462 } |
|
463 |
|
464 delete fileList; |
|
465 err = fileFinder.FindWild(fileList); |
|
466 } |
|
467 return err; |
|
468 } |
|
469 |
|
470 // --------------------------------------------------------------------------- |
|
471 |
|
472 |
|
473 void CLauncherEngine::StartAppLaunchingL(const CArrayFix<TInt>* aSelectedApps, TBool aAutoClose) |
|
474 { |
|
475 LOGSTRING("Launcher: CLauncherEngine::StartAppLaunchingL"); |
|
476 |
|
477 // check that we have something to launch |
|
478 if (aSelectedApps->Count() <= 0) |
|
479 { |
|
480 _LIT(message, "Nothing selected"); |
|
481 iLauncherUI->ShowErrorMessage(message); |
|
482 } |
|
483 else |
|
484 { |
|
485 // update the list of applications to be tested |
|
486 iAppsArray->Reset(); |
|
487 |
|
488 TInt ref(0); |
|
489 TKeyArrayFix key(0, ECmpTUint16); |
|
490 TInt index(0); |
|
491 |
|
492 for (TInt i=0; i<iAllAppsArray->MdcaCount(); i++) |
|
493 { |
|
494 ref = i; |
|
495 |
|
496 // if the application is selected, append it to the apps array |
|
497 if (aSelectedApps->Find(ref, key, index) == 0) |
|
498 { |
|
499 iAppsArray->AppendL(iAllAppsArray->MdcaPoint(i)); |
|
500 } |
|
501 } |
|
502 |
|
503 |
|
504 // to make sure that our algorithm works correctly |
|
505 if (iAppsArray->MdcaCount() != aSelectedApps->Count()) |
|
506 { |
|
507 _LIT(message, "Something went wrong..."); |
|
508 iLauncherUI->ShowErrorMessage(message); |
|
509 } |
|
510 |
|
511 |
|
512 // init |
|
513 Cancel(); |
|
514 iLaunchingIsActive = ETrue; |
|
515 iAutoClose = aAutoClose; |
|
516 iAppLaunchCounter = 0; |
|
517 iFailedCases = 0; |
|
518 iOkCases = 0; |
|
519 iSkippedCases = 0; |
|
520 iTotalNumberOfCases = iAppsArray->MdcaCount(); |
|
521 iCurrentAppUid = KNullUid; |
|
522 |
|
523 // open the log file for writing |
|
524 if (iLogFile.Open(iEnv->FsSession(), iLogFilePath, EFileWrite) != KErrNone) |
|
525 { |
|
526 iEnv->FsSession().MkDirAll(iLogFilePath); |
|
527 iLogFile.Replace(iEnv->FsSession(), iLogFilePath, EFileWrite); |
|
528 } |
|
529 else |
|
530 { |
|
531 // file opens correctly, seek to the end |
|
532 TInt fileSize=0; |
|
533 iLogFile.Size(fileSize); |
|
534 iLogFile.Seek(ESeekCurrent, fileSize); |
|
535 } |
|
536 |
|
537 // change focus to output view!! |
|
538 iLauncherUI->ChangeFocusToOutputView(); |
|
539 |
|
540 //text to log |
|
541 iLauncherUI->PrintText(_L("New test started.\n")); |
|
542 |
|
543 // start the first launch! |
|
544 IssueLaunch(); |
|
545 |
|
546 } |
|
547 } |
|
548 |
|
549 // --------------------------------------------------------------------------- |
|
550 |
|
551 void CLauncherEngine::IssueLaunch() |
|
552 { |
|
553 LOGSTRING("Launcher: CLauncherEngine::IssueLaunch"); |
|
554 |
|
555 __ASSERT_ALWAYS(!IsActive(), User::Panic(_L("Timing error?"), 100)); |
|
556 |
|
557 // this should keep the backlight on |
|
558 User::ResetInactivityTime(); |
|
559 |
|
560 iDLLAnalysisIsActive = EFalse; |
|
561 // some delay |
|
562 iTimer.After(iStatus, 1000000); |
|
563 SetActive(); |
|
564 } |
|
565 |
|
566 // --------------------------------------------------------------------------- |
|
567 |
|
568 // --------------------------------------------------------------------------- |
|
569 |
|
570 void CLauncherEngine::WriteInitialStuffToTheLogL(const TDesC& aOwnData, RFile& aFile) |
|
571 { |
|
572 LOGSTRING("Launcher: CLauncherEngine::WriteInitialStuffToTheLog"); |
|
573 |
|
574 TTime time; |
|
575 time.HomeTime(); |
|
576 TBuf<32> currentTime; |
|
577 TBuf<32> currentDate; |
|
578 |
|
579 // current date |
|
580 _LIT(KCurrentDate,"%D%M%Y%/0%1%/1%2%/2%3%/3"); |
|
581 time.FormatL(currentDate, KCurrentDate); |
|
582 iLogWriteBuf->Des().Copy(currentDate); |
|
583 AppendLogBufferL(KFileSeparator(), iLogWriteBuf); |
|
584 |
|
585 // current time |
|
586 _LIT(KCurrentTime,"%-B%:0%J%:1%T%:2%S%:3%+B"); |
|
587 time.FormatL(currentTime, KCurrentTime); |
|
588 AppendLogBufferL(currentTime, iLogWriteBuf); |
|
589 AppendLogBufferL(KFileSeparator(), iLogWriteBuf); |
|
590 |
|
591 // available RAM memory |
|
592 TMemoryInfoV1Buf memory; |
|
593 UserHal::MemoryInfo(memory); |
|
594 iLogWriteBuf->Des().AppendNum(memory().iFreeRamInBytes); |
|
595 AppendLogBufferL(KFileSeparator(), iLogWriteBuf); |
|
596 |
|
597 // own data, eg. application name |
|
598 AppendLogBufferL(aOwnData, iLogWriteBuf); |
|
599 AppendLogBufferL(KFileSeparator(), iLogWriteBuf); |
|
600 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
601 |
|
602 // write the buffer to the file |
|
603 aFile.Write(iLogWriteBuf->Des()); |
|
604 |
|
605 // clear the buffer |
|
606 iLogWriteBuf->Des().Copy(_L("")); |
|
607 } |
|
608 |
|
609 // --------------------------------------------------------------------------- |
|
610 |
|
611 |
|
612 void CLauncherEngine::CheckForMoreAppsL() |
|
613 { |
|
614 LOGSTRING("Launcher: CLauncherEngine::CheckForMoreAppsL"); |
|
615 |
|
616 // make sure the launcher app is in the foreground |
|
617 TApaTaskList taskList(iWs); |
|
618 TUid launcherAppUid; |
|
619 launcherAppUid.iUid = 0x101FB74F; |
|
620 TApaTask launcherTask = taskList.FindApp(launcherAppUid); |
|
621 launcherTask.BringToForeground(); |
|
622 |
|
623 |
|
624 // check if we have more test to be executed |
|
625 if ( iAppLaunchCounter >= iTotalNumberOfCases-1 ) |
|
626 { |
|
627 |
|
628 // all done, show stats |
|
629 TBuf<200> message; |
|
630 message.Append( _L("Done: ") ); |
|
631 message.AppendNum( iOkCases ); |
|
632 message.Append( _L(" ok, ") ); |
|
633 message.AppendNum( iFailedCases ); |
|
634 message.Append( _L(" failed, ") ); |
|
635 message.AppendNum( iSkippedCases ); |
|
636 message.Append( _L(" skipped.") ); |
|
637 |
|
638 // print the message to the output screen |
|
639 iLauncherUI->PrintText(message); |
|
640 iLauncherUI->PrintText(_L("\n\n")); |
|
641 |
|
642 //write same stuff to the log |
|
643 WriteInitialStuffToTheLogL(message, iLogFile); |
|
644 iLogWriteBuf->Des().Copy(KFileNewLine); |
|
645 iLogWriteBuf->Des().Append(KFileNewLine); |
|
646 iLogFile.Write(iLogWriteBuf->Des()); |
|
647 |
|
648 // close the log |
|
649 iLogFile.Close(); |
|
650 |
|
651 iLaunchingIsActive = EFalse; |
|
652 |
|
653 // all apps launched |
|
654 _LIT(KAllDoneMessage, "All apps launched"); |
|
655 iLauncherUI->ShowInfoMessage(KAllDoneMessage); |
|
656 } |
|
657 else |
|
658 { |
|
659 // more apps to be launched, maintain requests |
|
660 iAppLaunchCounter++; |
|
661 IssueLaunch(); |
|
662 } |
|
663 |
|
664 } |
|
665 |
|
666 // --------------------------------------------------------------------------- |
|
667 |
|
668 void CLauncherEngine::LaunchApplicationL() |
|
669 { |
|
670 LOGSTRING("Launcher: CLauncherEngine::LaunchApplication"); |
|
671 LOGSTRING3("Launcher: Trying to launch %S, UID: %d", &iCurrentAppNameAndExt, iCurrentAppUid.iUid); |
|
672 |
|
673 TRAPD(err, DoLaunchApplicationL()); |
|
674 |
|
675 if (err!=KErrNone) |
|
676 { |
|
677 iLogWriteBuf->Des().Append(_L("[FAIL: Cannot launch the app] ")); |
|
678 |
|
679 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
680 iLauncherUI->PrintText(_L(": cannot launch\n")); |
|
681 |
|
682 // write the buffer to the log |
|
683 iLogWriteBuf->Des().Append(KFileNewLine); |
|
684 iLogFile.Write(iLogWriteBuf->Des()); |
|
685 |
|
686 // this application isn't even launchable, go to next one |
|
687 iFailedCases++; |
|
688 CheckForMoreAppsL(); |
|
689 } |
|
690 |
|
691 } |
|
692 // --------------------------------------------------------------------------- |
|
693 |
|
694 |
|
695 void CLauncherEngine::DoLaunchApplicationL() |
|
696 { |
|
697 LOGSTRING("Launcher: CLauncherEngine::DoLaunchApplicationL"); |
|
698 |
|
699 // create a new handle |
|
700 RThread newThreadHandle; |
|
701 iCurrentAppThread = newThreadHandle; |
|
702 |
|
703 |
|
704 // Find the task with uid3 |
|
705 TApaTaskList tasklist(iWs); |
|
706 TApaTask task=tasklist.FindApp(iCurrentAppUid); |
|
707 |
|
708 if (task.Exists()) |
|
709 // Task exists, bring it to foreground |
|
710 { |
|
711 task.BringToForeground(); |
|
712 } |
|
713 else |
|
714 // Task doesn't exist, launch a new instance of an application |
|
715 { |
|
716 TApaAppInfo appInfo; |
|
717 User::LeaveIfError(iLs.GetAppInfo(appInfo, iCurrentAppUid)); |
|
718 TApaAppCapabilityBuf capBuf; |
|
719 User::LeaveIfError(iLs.GetAppCapability(capBuf, iCurrentAppUid)); |
|
720 TApaAppCapability& caps = capBuf(); |
|
721 |
|
722 CApaCommandLine* cmdLine=CApaCommandLine::NewLC(); |
|
723 cmdLine->SetExecutableNameL(appInfo.iFullName); |
|
724 |
|
725 if ( caps.iLaunchInBackground ) |
|
726 // Apps capability defines that the app is launched in background |
|
727 { |
|
728 cmdLine->SetCommandL(EApaCommandBackground); |
|
729 } |
|
730 else |
|
731 { |
|
732 cmdLine->SetCommandL(EApaCommandRun); |
|
733 } |
|
734 |
|
735 // start the app |
|
736 User::LeaveIfError(iLs.StartApp(*cmdLine, iCurrentAppThreadId)); |
|
737 |
|
738 // activate thread checker active object |
|
739 iAppThreadChecker->ActivateChecking(); |
|
740 |
|
741 // now open a handle to the thread and register death notifier |
|
742 TInt err = iCurrentAppThread.Open(iCurrentAppThreadId); |
|
743 if (err == KErrNone) |
|
744 iCurrentAppThread.Logon(iAppThreadChecker->iStatus); |
|
745 else |
|
746 { |
|
747 iCurrentAppThread.Close(); |
|
748 TRequestStatus* status = &iAppThreadChecker->iStatus; |
|
749 User::RequestComplete(status, KErrNone); |
|
750 iAppThreadChecker->Cancel(); |
|
751 User::Leave(err); |
|
752 } |
|
753 |
|
754 CleanupStack::PopAndDestroy(); // cmdLine |
|
755 } |
|
756 |
|
757 // the application is now running, start a check to see if it's still alive |
|
758 iAppRunningChecker->StartTesting(); |
|
759 |
|
760 } |
|
761 |
|
762 // --------------------------------------------------------------------------- |
|
763 |
|
764 void CLauncherEngine::CheckIfAppIsRunningL() |
|
765 { |
|
766 LOGSTRING("Launcher: CLauncherEngine::CheckIfAppIsRunningL"); |
|
767 |
|
768 // cancel the death notifier since it isn't needed anymore |
|
769 if( iCurrentAppThread.Handle() != 0 ) |
|
770 { |
|
771 iCurrentAppThread.LogonCancel(iAppThreadChecker->iStatus); |
|
772 } |
|
773 |
|
774 // cancel checkers |
|
775 iAppThreadChecker->Cancel(); |
|
776 iAppRunningChecker->Cancel(); |
|
777 |
|
778 |
|
779 |
|
780 // check from the window server if the app is running |
|
781 TApaTaskList taskList(iWs); |
|
782 TApaTask thisTask = taskList.FindApp(iCurrentAppUid); |
|
783 |
|
784 if( !thisTask.Exists() ) // application not running -> FAIL |
|
785 { |
|
786 // check from the thread why it quit |
|
787 CheckWhyThreadDiedL(); |
|
788 |
|
789 // --> CheckForMoreApps() and all the other stuff called from CheckWhyThreadDied() ! |
|
790 |
|
791 } |
|
792 else |
|
793 { |
|
794 // app is running! |
|
795 iOkCases++; |
|
796 |
|
797 // close handle to the thread |
|
798 iCurrentAppThread.Close(); |
|
799 |
|
800 |
|
801 iLogWriteBuf->Des().Append(_L(" [OK]")); |
|
802 iLogWriteBuf->Des().Append(KFileNewLine); |
|
803 iLogFile.Write(iLogWriteBuf->Des()); |
|
804 |
|
805 |
|
806 // close the running application if needed |
|
807 if (iAutoClose) |
|
808 { |
|
809 // since the application is still open, let's close it |
|
810 thisTask.EndTask(); |
|
811 //User::After(1000); |
|
812 //thisTask.SendSystemEvent(EApaSystemEventShutdown); |
|
813 //thisTask.KillTask(); |
|
814 //User::After(1000); |
|
815 } |
|
816 |
|
817 // this app is done now, move to the next one! |
|
818 CheckForMoreAppsL(); |
|
819 |
|
820 } |
|
821 } |
|
822 |
|
823 // --------------------------------------------------------------------------- |
|
824 |
|
825 void CLauncherEngine::CheckWhyThreadDiedL() |
|
826 { |
|
827 LOGSTRING("Launcher: CLauncherEngine::CheckWhyThreadDiedL"); |
|
828 |
|
829 // cancel the death notifier since it isn't needed anymore |
|
830 if( iCurrentAppThread.Handle() != 0 ) |
|
831 { |
|
832 iCurrentAppThread.LogonCancel(iAppThreadChecker->iStatus); |
|
833 } |
|
834 |
|
835 // make sure all checkers are cancelled |
|
836 iAppRunningChecker->Cancel(); |
|
837 iAppThreadChecker->Cancel(); |
|
838 |
|
839 TBuf<256> outputText; |
|
840 outputText.Append(_L("App.Closed. ")); |
|
841 |
|
842 |
|
843 if (iCurrentAppThread.ExitType() == EExitKill) |
|
844 { |
|
845 outputText.Append(_L("\"EExitKill\"")); |
|
846 } |
|
847 else if (iCurrentAppThread.ExitType() == EExitTerminate) |
|
848 { |
|
849 outputText.Append(_L("\"EExitTerminate\"")); |
|
850 } |
|
851 else if (iCurrentAppThread.ExitType() == EExitPanic) |
|
852 { |
|
853 outputText.Append(_L("\"EExitPanic\"")); |
|
854 } |
|
855 else if (iCurrentAppThread.ExitType() == EExitPending) |
|
856 { |
|
857 outputText.Append(_L("\"EExitPending\"")); |
|
858 } |
|
859 else // unknown reason |
|
860 { |
|
861 outputText.Append(_L("\"Exit_Unknown_Reason\"")); |
|
862 } |
|
863 |
|
864 outputText.Append(_L(" code:")); |
|
865 TInt exitReason = iCurrentAppThread.ExitReason(); |
|
866 outputText.AppendNum(exitReason); |
|
867 outputText.Append(_L(" \"")); |
|
868 |
|
869 TPtrC exitCategory = iCurrentAppThread.ExitCategory(); |
|
870 outputText.Append(exitCategory); |
|
871 |
|
872 outputText.Append(_L("\"")); |
|
873 |
|
874 |
|
875 // print to screen |
|
876 iLauncherUI->PrintText(iCurrentAppNameAndExt); |
|
877 iLauncherUI->PrintText(_L(": ")); |
|
878 iLauncherUI->PrintText(outputText); |
|
879 iLauncherUI->PrintText(_L("\n")); |
|
880 |
|
881 // write to the log also |
|
882 iLogWriteBuf->Des().Append(_L(" [FAIL: ")); |
|
883 iLogWriteBuf->Des().Append(outputText); |
|
884 iLogWriteBuf->Des().Append(_L("]")); |
|
885 iLogWriteBuf->Des().Append(KFileNewLine); |
|
886 |
|
887 iLogFile.Write(iLogWriteBuf->Des()); |
|
888 |
|
889 // close handle to the thread |
|
890 //iCurrentAppThread.Close(); <-- not safe the close the handle because of the "App.Closed" dialog |
|
891 // somehow takes ownership of the thread or something |
|
892 |
|
893 // nothing to do anymore, move to the next app |
|
894 iFailedCases++; |
|
895 CheckForMoreAppsL(); |
|
896 } |
|
897 |
|
898 // --------------------------------------------------------------------------- |
|
899 // --------------------------------------------------------------------------- |
|
900 |
|
901 CDesCArray* CLauncherEngine::DependencyCheckForE32ImageL() |
|
902 { |
|
903 LOGSTRING("Launcher: CLauncherEngine::DependencyCheckForE32ImageL"); |
|
904 |
|
905 // create an empty array for the missing dll names |
|
906 CDesCArray* missingDllArray = new(ELeave) CDesCArrayFlat(100); |
|
907 CleanupStack::PushL(missingDllArray); |
|
908 |
|
909 // get a list of DLLs from the E32 image file |
|
910 E32ImageReader* reader = E32ImageReader::NewLC(); |
|
911 CDesCArray* dllArray = reader->ListOfDLLsL( iAppsArray->MdcaPoint(iAppLaunchCounter) ); |
|
912 CleanupStack::PopAndDestroy(); // reader |
|
913 CleanupStack::PushL(dllArray); |
|
914 |
|
915 // compare system DLL and image DLL arrays |
|
916 TInt pos(0); |
|
917 for (TInt j=0; j<dllArray->MdcaCount(); j++) |
|
918 { |
|
919 if (iSystemDllArray->Find(dllArray->MdcaPoint(j), pos, ECmpFolded) != 0) |
|
920 { |
|
921 // DLL not found, append the name to the list of missing DLLs |
|
922 missingDllArray->AppendL(dllArray->MdcaPoint(j)); |
|
923 } |
|
924 } |
|
925 |
|
926 CleanupStack::PopAndDestroy(); // dllArray |
|
927 CleanupStack::Pop(); // missingDllArray |
|
928 |
|
929 LOGSTRING("Launcher: CLauncherEngine::DependencyCheckForE32ImageL returns"); |
|
930 |
|
931 return missingDllArray; |
|
932 } |
|
933 |
|
934 // --------------------------------------------------------------------------- |
|
935 |
|
936 TInt CLauncherEngine::DeleteLogFile() |
|
937 { |
|
938 LOGSTRING("Launcher: CLauncherEngine::DeleteLogFile"); |
|
939 return BaflUtils::DeleteFile(iEnv->FsSession(), iLogFilePath); |
|
940 } |
|
941 |
|
942 // --------------------------------------------------------------------------- |
|
943 |
|
944 void CLauncherEngine::StopLaunchingL() |
|
945 { |
|
946 LOGSTRING("Launcher: CLauncherEngine::StopLaunchingL"); |
|
947 if(iLaunchingIsActive) |
|
948 { |
|
949 //write to the log |
|
950 WriteInitialStuffToTheLogL(_L("Cancelled by the user !!! "), iLogFile); |
|
951 iLogWriteBuf->Des().Copy(KFileNewLine); |
|
952 iLogWriteBuf->Des().Append(KFileNewLine); |
|
953 iLogFile.Write(iLogWriteBuf->Des()); |
|
954 |
|
955 // close the log |
|
956 iLogFile.Close(); |
|
957 |
|
958 // print to the screen |
|
959 iLauncherUI->PrintText(_L("Launching cancelled.\n\n")); |
|
960 |
|
961 // cancel all active objects |
|
962 if( iCurrentAppThread.Handle() != 0 ) |
|
963 { |
|
964 iCurrentAppThread.LogonCancel(iAppThreadChecker->iStatus); |
|
965 } |
|
966 Cancel(); |
|
967 iAppRunningChecker->Cancel(); |
|
968 iAppThreadChecker->Cancel(); |
|
969 |
|
970 iLaunchingIsActive = EFalse; |
|
971 |
|
972 _LIT(KMessage, "Launching cancelled"); |
|
973 iLauncherUI->ShowInfoMessage(KMessage); |
|
974 |
|
975 } |
|
976 } |
|
977 |
|
978 // --------------------------------------------------------------------------- |
|
979 |
|
980 TBool CLauncherEngine::LogFileExists() |
|
981 { |
|
982 LOGSTRING("Launcher: CLauncherEngine::LogFileExists"); |
|
983 return BaflUtils::FileExists(iEnv->FsSession(), iLogFilePath); |
|
984 } |
|
985 |
|
986 // --------------------------------------------------------------------------- |
|
987 |
|
988 TInt CLauncherEngine::DeleteBCLogFile() |
|
989 { |
|
990 LOGSTRING("Launcher: CLauncherEngine::DeleteBCLogFile"); |
|
991 return BaflUtils::DeleteFile(iEnv->FsSession(), iBCLogFilePath); |
|
992 } |
|
993 |
|
994 |
|
995 // --------------------------------------------------------------------------- |
|
996 |
|
997 TBool CLauncherEngine::BCLogFileExists() |
|
998 { |
|
999 LOGSTRING("Launcher: CLauncherEngine::BCLogFileExists"); |
|
1000 return BaflUtils::FileExists(iEnv->FsSession(), iBCLogFilePath); |
|
1001 } |
|
1002 |
|
1003 // --------------------------------------------------------------------------- |
|
1004 void CLauncherEngine::AnalyseDLLsL( const TDesC& aFileName ) |
|
1005 { |
|
1006 LOGSTRING("Launcher: CLauncherEngine::AnalyseDLLsL"); |
|
1007 _LIT(KStartSeparator, "******************************"); |
|
1008 _LIT(KStartingAnalysis, "Starting BC Analysis for DLLs."); |
|
1009 _LIT(KInputFileSelected, "Input file selected: "); |
|
1010 |
|
1011 // Reset found issues counter and buffer |
|
1012 iFoundBCIssues = 0; |
|
1013 delete iBCIssuesBigBuffer; |
|
1014 iBCIssuesBigBuffer = 0; |
|
1015 |
|
1016 // Reset log writing buffer: |
|
1017 iLogWriteBuf->Des().Zero(); |
|
1018 |
|
1019 if( IsActive() ) |
|
1020 { |
|
1021 Cancel(); |
|
1022 } |
|
1023 |
|
1024 iRequiredDllsFilePath = aFileName; |
|
1025 |
|
1026 if( BaflUtils::FileExists(iEnv->FsSession(), iRequiredDllsFilePath) == EFalse ) |
|
1027 { |
|
1028 LOGSTRING2("Launcher: CLauncherEngine::AnalyseDLLsL - can't find input file: %S", &iRequiredDllsFilePath); |
|
1029 User::Leave( KErrNotFound ); |
|
1030 } |
|
1031 |
|
1032 // open the log file for writing |
|
1033 if (iBCLogFile.Open(iEnv->FsSession(), iBCLogFilePath, EFileWrite) != KErrNone) |
|
1034 { |
|
1035 iEnv->FsSession().MkDirAll(iLogFilePath); |
|
1036 User::LeaveIfError( iBCLogFile.Replace(iEnv->FsSession(), iBCLogFilePath, EFileWrite) ); |
|
1037 } |
|
1038 else |
|
1039 { |
|
1040 // file opens correctly, seek to the end |
|
1041 TInt fileSize=0; |
|
1042 iBCLogFile.Size(fileSize); |
|
1043 iBCLogFile.Seek(ESeekCurrent, fileSize); |
|
1044 } |
|
1045 |
|
1046 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1047 AppendLogBufferL(KStartSeparator(), iLogWriteBuf); |
|
1048 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1049 iBCLogFile.Write(iLogWriteBuf->Des()); |
|
1050 iLogWriteBuf->Des().Zero(); |
|
1051 |
|
1052 // Resolve file type. Should we use XML parsing or just compare DLL list |
|
1053 TBool xmlParsing = |
|
1054 KDotXML().Compare(iRequiredDllsFilePath.Right(KDotXML().Length())) == 0 || |
|
1055 KDotLauncherXML().Compare(iRequiredDllsFilePath.Right(KDotLauncherXML().Length())) == 0; |
|
1056 |
|
1057 // Log analysis starting time and selected input file: |
|
1058 WriteInitialStuffToTheLogL(KStartingAnalysis, iBCLogFile); |
|
1059 AppendLogBufferL(KInputFileSelected(), iLogWriteBuf); |
|
1060 AppendLogBufferL(iRequiredDllsFilePath, iLogWriteBuf); |
|
1061 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1062 iBCLogFile.Write(iLogWriteBuf->Des()); |
|
1063 iLogWriteBuf->Des().Zero(); |
|
1064 |
|
1065 if( xmlParsing ) |
|
1066 { |
|
1067 iLauncherUI->ChangeFocusToOutputView(); |
|
1068 DoBCAnalysisL(); |
|
1069 } |
|
1070 else |
|
1071 { |
|
1072 DoCompareDLLListsL(); |
|
1073 } |
|
1074 } |
|
1075 |
|
1076 // --------------------------------------------------------------------------- |
|
1077 |
|
1078 void CLauncherEngine::DoBCAnalysisL() |
|
1079 { |
|
1080 LOGSTRING("Launcher: CLauncherEngine::DoBCAnalysisL"); |
|
1081 if( iXMLParser == 0 ) |
|
1082 { |
|
1083 iXMLParser = CLauncherXMLParser::NewL(iEnv->FsSession()); |
|
1084 } |
|
1085 |
|
1086 TEntry entry; |
|
1087 User::LeaveIfError(iEnv->FsSession().Entry(iRequiredDllsFilePath, entry)); |
|
1088 TInt fileSize = entry.iSize; |
|
1089 |
|
1090 _LIT(KAnalysing,"Analysing DLLs"); |
|
1091 iLauncherUI->ShowProgressBar(KAnalysing, 0, fileSize); |
|
1092 iDLLAnalysisIsActive = ETrue; |
|
1093 |
|
1094 iXMLParser->ParseL(iRequiredDllsFilePath, this); |
|
1095 } |
|
1096 |
|
1097 // --------------------------------------------------------------------------- |
|
1098 |
|
1099 void CLauncherEngine::CancelBCAnalysis() |
|
1100 { |
|
1101 LOGSTRING("Launcher: CLauncherEngine::CancelBCAnalysis"); |
|
1102 if( iXMLParser ) |
|
1103 { |
|
1104 iXMLParser->Cancel(); |
|
1105 } |
|
1106 iLauncherUI->PrintText(_L("\nAnalysis cancelled.\n\n")); |
|
1107 WriteInitialStuffToTheLogL(_L("Analysis cancelled by user"), iBCLogFile); |
|
1108 iLogWriteBuf->Des().Zero(); |
|
1109 iBCLogFile.Close(); |
|
1110 } |
|
1111 |
|
1112 // --------------------------------------------------------------------------- |
|
1113 |
|
1114 void CLauncherEngine::DoCompareDLLListsL() |
|
1115 { |
|
1116 LOGSTRING("Launcher: CLauncherEngine::DoCompareDLLListsL"); |
|
1117 |
|
1118 RFile file; |
|
1119 CleanupClosePushL(file); |
|
1120 |
|
1121 // Show progress bar |
|
1122 _LIT(KAnalysing,"Analysing DLLs"); |
|
1123 iLauncherUI->ShowWaitDialog(KAnalysing); |
|
1124 |
|
1125 if(file.Open(iEnv->FsSession(), iRequiredDllsFilePath, EFileRead) != KErrNone) |
|
1126 { |
|
1127 // Hide wait dialog |
|
1128 iLauncherUI->HideWaitDialog(); |
|
1129 |
|
1130 iLauncherUI->ChangeFocusToOutputView(); |
|
1131 |
|
1132 TBuf<200> msg; |
|
1133 |
|
1134 |
|
1135 msg.Format(_L("Unable to open %S for reading!\n\n"), &iRequiredDllsFilePath); |
|
1136 iLauncherUI->PrintText( msg ); |
|
1137 } |
|
1138 else |
|
1139 { |
|
1140 |
|
1141 CDesCArray* requiredDllArray = new(ELeave) CDesCArrayFlat(KMaxDllArraySize); |
|
1142 CleanupStack::PushL(requiredDllArray); |
|
1143 |
|
1144 // read all lines the text file |
|
1145 TFileName dllName; |
|
1146 TInt i(0); |
|
1147 while( ReadLineFromFileL(file, dllName) == KErrNone && i<KMaxDllArraySize ) |
|
1148 { |
|
1149 dllName.TrimAll(); |
|
1150 |
|
1151 if (dllName.Length() > 1) |
|
1152 requiredDllArray->AppendL(dllName); |
|
1153 |
|
1154 i++; |
|
1155 } |
|
1156 |
|
1157 if (requiredDllArray->MdcaCount() == 0) |
|
1158 { |
|
1159 // Hide wait dialog |
|
1160 iLauncherUI->HideWaitDialog(); |
|
1161 |
|
1162 iLauncherUI->ChangeFocusToOutputView(); |
|
1163 |
|
1164 TBuf<200> msg; |
|
1165 msg.Format(_L("File %S is empty!\n\n"), &iRequiredDllsFilePath); |
|
1166 iLauncherUI->PrintText( msg ); |
|
1167 } |
|
1168 else |
|
1169 { |
|
1170 // compare the arrays and print any missing items |
|
1171 CDesCArray* missingDllArray = new(ELeave) CDesCArrayFlat(KMaxDllArraySize); |
|
1172 CleanupStack::PushL(missingDllArray); |
|
1173 |
|
1174 TInt pos(0); |
|
1175 for (TInt j=0; j<requiredDllArray->MdcaCount(); j++) |
|
1176 { |
|
1177 if (iSystemDllArray->Find(requiredDllArray->MdcaPoint(j), pos, ECmpFolded) != 0) |
|
1178 { |
|
1179 // DLL not found, append the name to the list of missing DLLs |
|
1180 missingDllArray->AppendL(requiredDllArray->MdcaPoint(j)); |
|
1181 } |
|
1182 } |
|
1183 |
|
1184 |
|
1185 if (missingDllArray->MdcaCount() == 0) |
|
1186 { |
|
1187 _LIT(KMessage, "No missing files found"); |
|
1188 AppendLogBufferL(KMessage(), iLogWriteBuf); |
|
1189 iLauncherUI->ShowInfoMessage(KMessage); |
|
1190 } |
|
1191 else |
|
1192 { |
|
1193 iLauncherUI->ChangeFocusToOutputView(); |
|
1194 _LIT(KMissingFiles, "Missing files:\n"); |
|
1195 |
|
1196 //iLauncherUI->PrintText( KMissingFiles ); |
|
1197 AppendLogBufferL(KMissingFiles(), iBCIssuesBigBuffer, KBigBufferAllocBytes); |
|
1198 |
|
1199 AppendLogBufferL(KMissingFiles(), iLogWriteBuf); |
|
1200 |
|
1201 for (TInt i=0; i<missingDllArray->MdcaCount(); i++) |
|
1202 { |
|
1203 //iLauncherUI->PrintText( missingDllArray->MdcaPoint(i) ); |
|
1204 AppendLogBufferL(missingDllArray->MdcaPoint(i), iBCIssuesBigBuffer, KBigBufferAllocBytes); |
|
1205 //iLauncherUI->PrintText( _L("\n") ); |
|
1206 AppendLogBufferL(KNewLine(), iBCIssuesBigBuffer, KBigBufferAllocBytes); |
|
1207 |
|
1208 AppendLogBufferL(missingDllArray->MdcaPoint(i), iLogWriteBuf); |
|
1209 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1210 } |
|
1211 AppendLogBufferL(KNewLine(), iBCIssuesBigBuffer, KBigBufferAllocBytes); |
|
1212 iLauncherUI->PrintText( iBCIssuesBigBuffer->Des() ); |
|
1213 } |
|
1214 |
|
1215 // Hide wait dialog |
|
1216 iLauncherUI->HideWaitDialog(); |
|
1217 |
|
1218 CleanupStack::PopAndDestroy(); // missingDllArray |
|
1219 } |
|
1220 |
|
1221 CleanupStack::PopAndDestroy(); // requiredDllArray |
|
1222 } |
|
1223 |
|
1224 CleanupStack::PopAndDestroy(); //file |
|
1225 iBCLogFile.Write(iLogWriteBuf->Des()); |
|
1226 iLogWriteBuf->Des().Zero(); |
|
1227 iBCLogFile.Close(); |
|
1228 } |
|
1229 |
|
1230 // --------------------------------------------------------------------------- |
|
1231 |
|
1232 void CLauncherEngine::ParsingProgressedL(TInt aBytes) |
|
1233 { |
|
1234 LOGSTRING2("Launcher: CLauncherEngine::ParsingProgressedL - Bytes: %d", aBytes); |
|
1235 iLauncherUI->SetProgressBarValue(aBytes); |
|
1236 } |
|
1237 |
|
1238 // --------------------------------------------------------------------------- |
|
1239 |
|
1240 |
|
1241 void CLauncherEngine::ElementParsedL(const CLauncherDLLElement& aDllElement) |
|
1242 { |
|
1243 LOGSTRING("Launcher: CLauncherEngine::ElementParsedL"); |
|
1244 User::ResetInactivityTime(); |
|
1245 |
|
1246 _LIT(KIndent, " "); |
|
1247 _LIT(KIssuesFound, "Binary compatibility issues found:"); |
|
1248 _LIT(KDLLMissing,"DLL is missing"); |
|
1249 _LIT(KUID1Changed,"UID1 changed"); |
|
1250 _LIT(KUID2Changed,"UID2 changed"); |
|
1251 _LIT(KUID3Changed,"UID3 changed"); |
|
1252 _LIT(KSIDChanged,"SID changed"); |
|
1253 _LIT(KCapabilityChanged,"Capability changed"); |
|
1254 |
|
1255 if( iDLLElement == 0 ) |
|
1256 { |
|
1257 iDLLElement = CLauncherDLLElement::NewL(); |
|
1258 } |
|
1259 |
|
1260 TFindFile fileFinder(iEnv->FsSession()); |
|
1261 _LIT(KDLLPath, "\\sys\\bin\\"); |
|
1262 TInt err = fileFinder.FindByPath(aDllElement.Name(), &KDLLPath); |
|
1263 |
|
1264 TBuf<256> issueStr; |
|
1265 |
|
1266 if( err == KErrNotFound ) |
|
1267 { |
|
1268 if( iFoundBCIssues++ == 0 ) |
|
1269 { |
|
1270 iLauncherUI->PrintText( KIssuesFound ); |
|
1271 iLauncherUI->PrintText( KNewLine ); |
|
1272 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1273 AppendLogBufferL(KIssuesFound(), iLogWriteBuf); |
|
1274 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1275 } |
|
1276 issueStr.Copy(aDllElement.Name()); |
|
1277 issueStr.Append(KNewLine); |
|
1278 issueStr.Append(KIndent); |
|
1279 issueStr.Append(KDLLMissing); |
|
1280 issueStr.Append(KNewLine); |
|
1281 |
|
1282 AppendLogBufferL(issueStr, iLogWriteBuf); |
|
1283 |
|
1284 TFileName dllName = aDllElement.Name(); |
|
1285 LOGSTRING2("Launcher: DLL not found: %S", &dllName); |
|
1286 if( iFoundBCIssues > KBigBufferUsageThreshold ) |
|
1287 { |
|
1288 if( iBCIssuesBigBuffer == 0) |
|
1289 { |
|
1290 iBCIssuesBigBuffer = HBufC::NewL(KBigBufferAllocBytes); |
|
1291 } |
|
1292 TInt maxSize = iBCIssuesBigBuffer->Des().Length() + issueStr.Length(); |
|
1293 if( maxSize >= iBCIssuesBigBuffer->Des().MaxLength()) |
|
1294 { |
|
1295 iBCIssuesBigBuffer = iBCIssuesBigBuffer->ReAllocL(maxSize + KBigBufferAllocBytes ); |
|
1296 } |
|
1297 TPtr ptr(iBCIssuesBigBuffer->Des()); |
|
1298 ptr += issueStr; |
|
1299 } |
|
1300 else |
|
1301 { |
|
1302 iLauncherUI->PrintText( issueStr); |
|
1303 } |
|
1304 } |
|
1305 else if( err == KErrNone) |
|
1306 { |
|
1307 // File is found, so let's try to open it: |
|
1308 RFile dllFile; |
|
1309 CleanupClosePushL(dllFile); |
|
1310 if( dllFile.Open(iEnv->FsSession(), fileFinder.File(), EFileRead) == KErrNone ) |
|
1311 { |
|
1312 // Parse DLL: |
|
1313 iDLLParser->ParseL(iEnv->FsSession(), dllFile, *iDLLElement); |
|
1314 CleanupStack::PopAndDestroy(); // dllFile |
|
1315 RArray<CLauncherDLLElement::TDifference> diffs; |
|
1316 CleanupClosePushL(diffs); |
|
1317 |
|
1318 // Compare DLLs: |
|
1319 if( iDLLElement->CompareL(aDllElement, diffs)) |
|
1320 { |
|
1321 if( iFoundBCIssues++ == 0 ) |
|
1322 { |
|
1323 iLauncherUI->PrintText( KIssuesFound ); |
|
1324 iLauncherUI->PrintText( KNewLine ); |
|
1325 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1326 AppendLogBufferL(KIssuesFound(), iLogWriteBuf); |
|
1327 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1328 } |
|
1329 // Differencies found: |
|
1330 for( TInt i = 0; i < diffs.Count(); ++i ) |
|
1331 { |
|
1332 // Print DLL name: |
|
1333 if( i == 0 ) |
|
1334 { |
|
1335 issueStr.Copy(aDllElement.Name()); |
|
1336 issueStr.Append(KNewLine); |
|
1337 } |
|
1338 |
|
1339 // Print differencies: |
|
1340 issueStr.Append(KIndent); |
|
1341 switch(diffs[i]) |
|
1342 { |
|
1343 case CLauncherDLLElement::EDifference_UID1: |
|
1344 issueStr.Append(KUID1Changed); |
|
1345 break; |
|
1346 case CLauncherDLLElement::EDifference_UID2: |
|
1347 issueStr.Append( KUID2Changed ); |
|
1348 break; |
|
1349 case CLauncherDLLElement::EDifference_UID3: |
|
1350 issueStr.Append( KUID3Changed ); |
|
1351 break; |
|
1352 case CLauncherDLLElement::EDifference_SID: |
|
1353 issueStr.Append( KSIDChanged ); |
|
1354 break; |
|
1355 case CLauncherDLLElement::EDifference_Capability: |
|
1356 issueStr.Append( KCapabilityChanged ); |
|
1357 break; |
|
1358 } |
|
1359 issueStr.Append( KNewLine ); |
|
1360 } |
|
1361 AppendLogBufferL(issueStr, iLogWriteBuf); |
|
1362 if( iFoundBCIssues > KBigBufferUsageThreshold ) |
|
1363 { |
|
1364 // To improve performance, don't print issues to output anymore. |
|
1365 // Instead, store the issues in buffer and print them when analysis is done. |
|
1366 if( iBCIssuesBigBuffer == 0) |
|
1367 { |
|
1368 iBCIssuesBigBuffer = HBufC::NewL(KBigBufferAllocBytes); |
|
1369 } |
|
1370 TInt maxSize = iBCIssuesBigBuffer->Des().Length() + issueStr.Length(); |
|
1371 if( maxSize >= iBCIssuesBigBuffer->Des().MaxLength()) |
|
1372 { |
|
1373 TInt increaseSize = Max(issueStr.Length(), KBigBufferAllocBytes); |
|
1374 iBCIssuesBigBuffer = iBCIssuesBigBuffer->ReAllocL(maxSize + increaseSize ); |
|
1375 } |
|
1376 TPtr ptr(iBCIssuesBigBuffer->Des()); |
|
1377 ptr += issueStr; |
|
1378 } |
|
1379 else |
|
1380 { |
|
1381 iLauncherUI->PrintText( issueStr); |
|
1382 } |
|
1383 } |
|
1384 CleanupStack::Pop(); // diffs |
|
1385 diffs.Close(); |
|
1386 } |
|
1387 else |
|
1388 { |
|
1389 CleanupStack::PopAndDestroy(); // dllFile |
|
1390 } |
|
1391 } |
|
1392 } |
|
1393 |
|
1394 // --------------------------------------------------------------------------- |
|
1395 void CLauncherEngine::DocumentParsedL(TInt aErrorCode) |
|
1396 { |
|
1397 LOGSTRING2("Launcher: CLauncherEngine::DocumentParsedL (Error code: %d)", aErrorCode); |
|
1398 |
|
1399 iDLLAnalysisIsActive = EFalse; |
|
1400 _LIT(KParseError, "Parse error: "); |
|
1401 _LIT(KNoIssues, "No binary compatibility issues found"); |
|
1402 |
|
1403 if( IsActive() ) |
|
1404 { |
|
1405 Cancel(); |
|
1406 } |
|
1407 |
|
1408 //hide progress bar |
|
1409 iLauncherUI->HideProgressBar(); |
|
1410 |
|
1411 if( aErrorCode != KErrNone ) |
|
1412 { |
|
1413 TBuf<16> errorCodeString; |
|
1414 errorCodeString.AppendNum(aErrorCode); |
|
1415 iLauncherUI->PrintText( KNewLine ); |
|
1416 iLauncherUI->PrintText( KParseError ); |
|
1417 iLauncherUI->PrintText( errorCodeString ); |
|
1418 iLauncherUI->PrintText( KNewLine ); |
|
1419 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1420 AppendLogBufferL(KParseError(), iLogWriteBuf); |
|
1421 AppendLogBufferL(errorCodeString, iLogWriteBuf); |
|
1422 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1423 } |
|
1424 else if(iFoundBCIssues == 0) |
|
1425 { |
|
1426 iLauncherUI->PrintText( KNoIssues ); |
|
1427 iLauncherUI->PrintText( KNewLine ); |
|
1428 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1429 AppendLogBufferL(KNoIssues(), iLogWriteBuf); |
|
1430 AppendLogBufferL(KFileNewLine(), iLogWriteBuf); |
|
1431 } |
|
1432 else if( iBCIssuesBigBuffer && iBCIssuesBigBuffer->Des().Length() > 0 ) |
|
1433 { |
|
1434 iLauncherUI->PrintText(iBCIssuesBigBuffer->Des()); |
|
1435 delete iBCIssuesBigBuffer; |
|
1436 iBCIssuesBigBuffer = 0; |
|
1437 } |
|
1438 if( iLogWriteBuf->Length() > 0 && iBCLogFile.SubSessionHandle() != 0) |
|
1439 { |
|
1440 iBCLogFile.Write(iLogWriteBuf->Des()); |
|
1441 } |
|
1442 WriteInitialStuffToTheLogL(_L("Analysis ready"), iBCLogFile); |
|
1443 iLogWriteBuf->Des().Zero(); |
|
1444 iBCLogFile.Close(); |
|
1445 } |
|
1446 |
|
1447 // --------------------------------------------------------------------------- |
|
1448 |
|
1449 TInt CLauncherEngine::ReadLineFromFileL(RFile& aFile, TDes& aReadBuf) |
|
1450 { |
|
1451 LOGSTRING("Launcher: CLauncherEngine::ReadLineFromFile"); |
|
1452 |
|
1453 _LIT8(KImcvCRLF, "\r\n"); |
|
1454 TInt err(KErrNone); |
|
1455 |
|
1456 HBufC8* tempLine = HBufC8::NewLC(1000); |
|
1457 TPtr8 buffer = tempLine->Des(); |
|
1458 |
|
1459 // clear the target buffer |
|
1460 aReadBuf.Zero(); |
|
1461 |
|
1462 // get the current file position |
|
1463 TInt filePos(0); |
|
1464 aFile.Seek(ESeekCurrent, filePos); |
|
1465 |
|
1466 // read the buffer |
|
1467 err = aFile.Read(buffer); |
|
1468 |
|
1469 // check if it's the end of file |
|
1470 TInt s = buffer.Length(); |
|
1471 if (s == 0) |
|
1472 err = KErrEof; |
|
1473 |
|
1474 if (err == KErrNone) |
|
1475 { |
|
1476 // copy to the lfcr and then set the file pointer to the point after that |
|
1477 TInt pos = buffer.Find(KImcvCRLF); |
|
1478 if (pos != -1) |
|
1479 { |
|
1480 TFileName tempBuf; |
|
1481 buffer.SetLength(pos); |
|
1482 tempBuf.Copy(buffer); |
|
1483 aReadBuf.Justify(tempBuf, pos, ELeft, ' '); |
|
1484 filePos += (pos+2); |
|
1485 |
|
1486 // set the file pointer back to after the lfcr |
|
1487 aFile.Seek(ESeekStart, filePos); |
|
1488 } |
|
1489 |
|
1490 // else fill the whole buffer |
|
1491 else |
|
1492 { |
|
1493 aReadBuf.Copy(buffer); |
|
1494 } |
|
1495 } |
|
1496 |
|
1497 CleanupStack::PopAndDestroy(); // tempLine |
|
1498 return err; |
|
1499 } |
|
1500 |
|
1501 |
|
1502 // --------------------------------------------------------------------------- |
|
1503 // --------------------------------------------------------------------------- |
|
1504 |
|
1505 |
|
1506 ////////////////////////////////////////////////////////////////////////////////////// |
|
1507 |
|
1508 // --------------------------------------------------------------------------- |
|
1509 |
|
1510 CAppThreadChecker* CAppThreadChecker::NewL(CLauncherEngine* aLauncherEngine) |
|
1511 { |
|
1512 LOGSTRING("Launcher: CAppThreadChecker::NewL"); |
|
1513 |
|
1514 CAppThreadChecker* self = new(ELeave) CAppThreadChecker; |
|
1515 CleanupStack::PushL(self); |
|
1516 self->ConstructL(aLauncherEngine); |
|
1517 CleanupStack::Pop(); |
|
1518 return self; |
|
1519 } |
|
1520 |
|
1521 // --------------------------------------------------------------------------- |
|
1522 |
|
1523 CAppThreadChecker::CAppThreadChecker() : CActive(EActivePriorityIpcEventsHigh) |
|
1524 { |
|
1525 } |
|
1526 |
|
1527 // --------------------------------------------------------------------------- |
|
1528 |
|
1529 void CAppThreadChecker::ConstructL(CLauncherEngine* aLauncherEngine) |
|
1530 { |
|
1531 LOGSTRING("Launcher: CAppThreadChecker::ConstructL"); |
|
1532 |
|
1533 iEnv = CEikonEnv::Static(); |
|
1534 |
|
1535 iLauncherEngine = aLauncherEngine; |
|
1536 |
|
1537 CActiveScheduler::Add(this); |
|
1538 } |
|
1539 |
|
1540 // --------------------------------------------------------------------------- |
|
1541 |
|
1542 CAppThreadChecker::~CAppThreadChecker() |
|
1543 { |
|
1544 LOGSTRING("Launcher: CAppThreadChecker::~CAppThreadChecker"); |
|
1545 |
|
1546 Cancel(); |
|
1547 } |
|
1548 |
|
1549 // --------------------------------------------------------------------------- |
|
1550 |
|
1551 void CAppThreadChecker::ActivateChecking() |
|
1552 { |
|
1553 LOGSTRING("Launcher: CAppThreadChecker::ActivateChecking"); |
|
1554 |
|
1555 __ASSERT_ALWAYS(!IsActive(), User::Panic(_L("Thread Checker"), 300)); |
|
1556 |
|
1557 SetActive(); |
|
1558 } |
|
1559 |
|
1560 // --------------------------------------------------------------------------- |
|
1561 |
|
1562 void CAppThreadChecker::RunL() |
|
1563 { |
|
1564 LOGSTRING("Launcher: CAppThreadChecker::RunL"); |
|
1565 |
|
1566 // check the state of the thread |
|
1567 iLauncherEngine->CheckWhyThreadDiedL(); |
|
1568 } |
|
1569 |
|
1570 // --------------------------------------------------------------------------- |
|
1571 |
|
1572 void CAppThreadChecker::DoCancel() |
|
1573 { |
|
1574 LOGSTRING("Launcher: CAppThreadChecker::DoCancel"); |
|
1575 } |
|
1576 |
|
1577 // --------------------------------------------------------------------------- |
|
1578 |
|
1579 |
|
1580 |
|
1581 // --------------------------------------------------------------------------- |
|
1582 |
|
1583 ////////////////////////////////////////////////////////////////////////////////////// |
|
1584 |
|
1585 // --------------------------------------------------------------------------- |
|
1586 |
|
1587 CAppRunningChecker* CAppRunningChecker::NewL(CLauncherEngine* aLauncherEngine) |
|
1588 { |
|
1589 LOGSTRING("Launcher: CAppRunningChecker::NewL"); |
|
1590 |
|
1591 CAppRunningChecker* self = new(ELeave) CAppRunningChecker; |
|
1592 CleanupStack::PushL(self); |
|
1593 self->ConstructL(aLauncherEngine); |
|
1594 CleanupStack::Pop(); |
|
1595 return self; |
|
1596 } |
|
1597 |
|
1598 // --------------------------------------------------------------------------- |
|
1599 |
|
1600 CAppRunningChecker::CAppRunningChecker() : CActive(EActivePriorityIpcEventsHigh) |
|
1601 { |
|
1602 } |
|
1603 |
|
1604 // --------------------------------------------------------------------------- |
|
1605 |
|
1606 void CAppRunningChecker::ConstructL(CLauncherEngine* aLauncherEngine) |
|
1607 { |
|
1608 LOGSTRING("Launcher: CAppRunningChecker::ConstructL"); |
|
1609 |
|
1610 iEnv = CEikonEnv::Static(); |
|
1611 User::LeaveIfError(iTimer.CreateLocal()); |
|
1612 |
|
1613 iLauncherEngine = aLauncherEngine; |
|
1614 |
|
1615 CActiveScheduler::Add(this); |
|
1616 } |
|
1617 |
|
1618 // --------------------------------------------------------------------------- |
|
1619 |
|
1620 CAppRunningChecker::~CAppRunningChecker() |
|
1621 { |
|
1622 LOGSTRING("Launcher: CAppRunningChecker::~CAppRunningChecker"); |
|
1623 |
|
1624 Cancel(); |
|
1625 |
|
1626 iTimer.Close(); |
|
1627 } |
|
1628 |
|
1629 // --------------------------------------------------------------------------- |
|
1630 |
|
1631 void CAppRunningChecker::StartTesting() |
|
1632 { |
|
1633 LOGSTRING("Launcher: CAppRunningChecker::StartTesting"); |
|
1634 |
|
1635 __ASSERT_ALWAYS(!IsActive(), User::Panic(_L("Running Checker"), 200)); |
|
1636 |
|
1637 // async delay of seven seconds |
|
1638 iTimer.After(iStatus, 7000000); |
|
1639 SetActive(); |
|
1640 } |
|
1641 |
|
1642 // --------------------------------------------------------------------------- |
|
1643 |
|
1644 void CAppRunningChecker::RunL() |
|
1645 { |
|
1646 LOGSTRING("Launcher: CAppRunningChecker::RunL"); |
|
1647 |
|
1648 // check if the application is running |
|
1649 iLauncherEngine->CheckIfAppIsRunningL(); |
|
1650 } |
|
1651 |
|
1652 // --------------------------------------------------------------------------- |
|
1653 |
|
1654 void CAppRunningChecker::DoCancel() |
|
1655 { |
|
1656 LOGSTRING("Launcher: CAppRunningChecker::DoCancel"); |
|
1657 iTimer.Cancel(); |
|
1658 } |
|
1659 |
|
1660 // --------------------------------------------------------------------------- |
|
1661 |
|
1662 |
|
1663 |
|
1664 ////////////////////////////////////////////////////////////////////////////////////// |
|
1665 |
|