1 /* |
|
2 * Copyright (c) 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 "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 "SamplerController.h" |
|
20 //#include <piprofiler/EngineUIDs.h> |
|
21 |
|
22 // CONSTANTS |
|
23 const TInt KMaxSamplerPluginCount = 20; |
|
24 const TInt KMaxExtraSettingsItemCount = 6; |
|
25 |
|
26 // LITERALS |
|
27 _LIT8(KSamplingPeriod, "sampling_period_ms"); |
|
28 _LIT8(KNewLine8, "\n"); |
|
29 _LIT8(KEquals8, "="); |
|
30 _LIT8(KSettingsText, " settings"); |
|
31 _LIT(KNewLine, "\n"); |
|
32 _LIT(KEquals, "="); |
|
33 _LIT(KCommentSeparator, " ; "); |
|
34 |
|
35 CSamplerController* CSamplerController::NewL(CProfilerSampleStream& aStream) |
|
36 { |
|
37 CSamplerController* self = new( ELeave ) CSamplerController(aStream); |
|
38 CleanupStack::PushL( self ); |
|
39 self->ConstructL( ); |
|
40 CleanupStack::Pop( self ); |
|
41 return self; |
|
42 } |
|
43 |
|
44 void CSamplerController::ConstructL() |
|
45 { |
|
46 // initiate sampler plugin list |
|
47 InitialiseSamplerListL(); |
|
48 } |
|
49 |
|
50 |
|
51 CSamplerController::CSamplerController(CProfilerSampleStream& aStream) : |
|
52 iStream(aStream) |
|
53 { |
|
54 } |
|
55 |
|
56 void CSamplerController::InitialiseSamplerListL() |
|
57 { |
|
58 // create new sampler plugin array |
|
59 iPluginArray = new (ELeave) CArrayPtrFlat<CSamplerPluginInterface>( KMaxSamplerPluginCount ); |
|
60 |
|
61 // create plugin loader instance |
|
62 iPluginLoader = CSamplerPluginLoader::NewL(); |
|
63 |
|
64 // register sampler controller to get notifications of succesfull plugin load |
|
65 iPluginLoader->SetObserver( this ); |
|
66 |
|
67 // load sampler plugins asynchronously |
|
68 iPluginLoader->LoadAsyncL( iPluginArray ); |
|
69 |
|
70 LOGTEXT(_L(" RSamplerController::InitialiseUserSideSamplerList - exit")); |
|
71 } |
|
72 |
|
73 CSamplerController::~CSamplerController() |
|
74 { |
|
75 LOGTEXT(_L("CSamplerController::~CSamplerController - entry" )); |
|
76 |
|
77 if ( iPluginArray ) |
|
78 { |
|
79 // destroy the plugin instances |
|
80 // empty loaded plugins from array |
|
81 for(TInt i(0);i<iPluginArray->Count();i++) |
|
82 { |
|
83 if(iPluginArray->At(i)) |
|
84 { |
|
85 delete iPluginArray->At(i); |
|
86 iPluginArray->At(i) = NULL; |
|
87 } |
|
88 } |
|
89 iPluginArray->Reset(); |
|
90 delete iPluginArray; |
|
91 iPluginArray = NULL; |
|
92 } |
|
93 |
|
94 if ( iPluginLoader ) |
|
95 { |
|
96 iPluginLoader->AbortAsyncLoad(); |
|
97 delete iPluginLoader; |
|
98 iPluginLoader = NULL; |
|
99 } |
|
100 |
|
101 LOGTEXT(_L("CSamplerController::~CSamplerController - exit" )); |
|
102 } |
|
103 |
|
104 void CSamplerController::SetObserver(MSamplerControllerObserver* aObserver) |
|
105 { |
|
106 iObserver = aObserver; |
|
107 } |
|
108 |
|
109 TInt CSamplerController::UpdateSavedSamplerAttributesL(CDesC8ArrayFlat* aSavedLineArray, CArrayFixFlat<TSamplerAttributes>* aAttributes) |
|
110 { |
|
111 TInt err(KErrNone); |
|
112 TInt count(iPluginArray->Count()); |
|
113 // all plugins get their own settings among whole lump of setting strings |
|
114 CSamplerPluginInterface* plugin = NULL; |
|
115 |
|
116 // loop through the plugin array |
|
117 for(TInt i(0);i<count;i++) |
|
118 { |
|
119 // get each plugin at a time |
|
120 plugin = iPluginArray->At(i); |
|
121 |
|
122 // call each plugin to sort out its own settings |
|
123 err = plugin->ConvertRawSettingsToAttributes(aSavedLineArray); |
|
124 |
|
125 // get plugin specific attributes, array may contain attributes of several sub samplers |
|
126 plugin->GetAttributesL(aAttributes); |
|
127 } |
|
128 |
|
129 return err; |
|
130 } |
|
131 |
|
132 TInt CSamplerController::SetSamplerSettingsL(TInt aUid, TSamplerAttributes aAttributes) |
|
133 { |
|
134 // parse right plugin based on UID |
|
135 CSamplerPluginInterface* plugin = GetPlugin(TUid::Uid(aUid)); |
|
136 |
|
137 // set the sampler attributes of a sampler plugin |
|
138 plugin->SetAttributesL(aAttributes); |
|
139 |
|
140 return KErrNone; |
|
141 } |
|
142 |
|
143 void CSamplerController::GetSamplerAttributesL(CArrayFixFlat<TSamplerAttributes>* aAttributes) |
|
144 { |
|
145 CSamplerPluginInterface* plugin = NULL; |
|
146 |
|
147 TInt count(iPluginArray->Count()); |
|
148 |
|
149 // get first all the attributes from all the sampler plugins listed in iPluginArray |
|
150 for(TInt i(0);i<count;i++) |
|
151 { |
|
152 // get the plugin first |
|
153 plugin = iPluginArray->At(i); |
|
154 |
|
155 // get plugin specific attributes, array may contain attributes of several sub samplers |
|
156 plugin->GetAttributesL(aAttributes); |
|
157 } |
|
158 } |
|
159 |
|
160 void CSamplerController::ComposeAttributesToSettingsFileFormat(RFile& aFile, CArrayFixFlat<TSamplerAttributes>* aAttributes) |
|
161 { |
|
162 // write immediately to settings file |
|
163 ComposeSettingsText(aFile, aAttributes); |
|
164 } |
|
165 |
|
166 void CSamplerController::ComposeSettingsText(RFile& aFile, CArrayFixFlat<TSamplerAttributes>* aAttrArray) |
|
167 { |
|
168 // temporary buffer for a setting line |
|
169 TBuf<384> settingLine; |
|
170 TBuf8<384> settingLine8; |
|
171 TInt itemCount(0); |
|
172 TBuf<266> tBuf; |
|
173 |
|
174 TSamplerAttributes attr; |
|
175 |
|
176 for(TInt i(0);i<aAttrArray->Count();i++) |
|
177 { |
|
178 // get the attribute container |
|
179 attr = aAttrArray->At(i); |
|
180 |
|
181 // add the name and description of the sampler in brackets first |
|
182 settingLine8.Copy(KBracketOpen); |
|
183 settingLine8.Append(attr.iShortName); |
|
184 settingLine8.Append(KBracketClose); |
|
185 settingLine8.Append(KCommentSeparator()); |
|
186 settingLine8.Append(attr.iName); |
|
187 settingLine8.Append(KSettingsText); |
|
188 settingLine8.Append(KNewLine8); |
|
189 aFile.Write(settingLine8); |
|
190 |
|
191 // enabled |
|
192 settingLine8.Copy(KEnabled); |
|
193 settingLine8.Append(KEquals8); |
|
194 settingLine8.Append(Bool2Str(attr.iEnabled)); |
|
195 settingLine8.Append(KNewLine8); |
|
196 aFile.Write(settingLine8); |
|
197 |
|
198 // sampling rate (if set) |
|
199 if( attr.iSampleRate != -1 ) |
|
200 { |
|
201 settingLine8.Copy(KSamplingPeriod); |
|
202 settingLine8.Append(KEquals8); |
|
203 settingLine8.Append(Int2Str(attr.iSampleRate)); |
|
204 settingLine8.Append(KNewLine8); |
|
205 aFile.Write(settingLine8); |
|
206 } |
|
207 |
|
208 itemCount = attr.iItemCount; |
|
209 |
|
210 // check if item count set is sane, max extra settings item count 6 |
|
211 if(itemCount > KMaxExtraSettingsItemCount) |
|
212 { |
|
213 // probably forgot to set the item count value in plugin => safe to set it 0 |
|
214 itemCount = 0; |
|
215 } |
|
216 |
|
217 // setting items |
|
218 for (TInt j(0);j<itemCount;j++) |
|
219 { |
|
220 switch(j) |
|
221 { |
|
222 case 0: // settingItem1 |
|
223 { |
|
224 settingLine.Copy(attr.iSettingItem1.iSettingText); |
|
225 settingLine.Append(KEquals()); |
|
226 settingLine.Append(attr.iSettingItem1.iValue); |
|
227 settingLine.Append(KCommentSeparator()); |
|
228 settingLine.Append(attr.iSettingItem1.iUIText); |
|
229 settingLine.Append(KNewLine()); |
|
230 CnvUtfConverter::ConvertFromUnicodeToUtf8(settingLine8, settingLine); |
|
231 aFile.Write(settingLine8); |
|
232 break; |
|
233 } |
|
234 case 1: // settingItem2 |
|
235 { |
|
236 settingLine.Copy(attr.iSettingItem2.iSettingText); |
|
237 settingLine.Append(KEquals()); |
|
238 settingLine.Append(attr.iSettingItem2.iValue); |
|
239 settingLine.Append(KCommentSeparator()); |
|
240 settingLine.Append(attr.iSettingItem2.iUIText); |
|
241 settingLine.Append(KNewLine()); |
|
242 CnvUtfConverter::ConvertFromUnicodeToUtf8(settingLine8, settingLine); |
|
243 aFile.Write(settingLine8); |
|
244 break; |
|
245 } |
|
246 case 2: // settingItem3 |
|
247 { |
|
248 settingLine.Copy(attr.iSettingItem3.iSettingText); |
|
249 settingLine.Append(KEquals()); |
|
250 settingLine.Append(attr.iSettingItem3.iValue); |
|
251 settingLine.Append(KCommentSeparator()); |
|
252 settingLine.Append(attr.iSettingItem3.iUIText); |
|
253 settingLine.Append(KNewLine()); |
|
254 CnvUtfConverter::ConvertFromUnicodeToUtf8(settingLine8, settingLine); |
|
255 aFile.Write(settingLine8); |
|
256 break; |
|
257 } |
|
258 case 3: // settingItem4 |
|
259 { |
|
260 settingLine.Copy(attr.iSettingItem4.iSettingText); |
|
261 settingLine.Append(KEquals()); |
|
262 settingLine.Append(attr.iSettingItem4.iValue); |
|
263 settingLine.Append(KCommentSeparator()); |
|
264 settingLine.Append(attr.iSettingItem4.iUIText); |
|
265 settingLine.Append(KNewLine()); |
|
266 CnvUtfConverter::ConvertFromUnicodeToUtf8(settingLine8, settingLine); |
|
267 aFile.Write(settingLine8); |
|
268 break; |
|
269 } |
|
270 case 4: // settingItem5 |
|
271 { |
|
272 settingLine.Copy(attr.iSettingItem5.iSettingText); |
|
273 settingLine.Append(KEquals()); |
|
274 settingLine.Append(attr.iSettingItem5.iValue); |
|
275 settingLine.Append(KCommentSeparator()); |
|
276 settingLine.Append(attr.iSettingItem5.iUIText); |
|
277 settingLine.Append(KNewLine()); |
|
278 CnvUtfConverter::ConvertFromUnicodeToUtf8(settingLine8, settingLine); |
|
279 aFile.Write(settingLine8); |
|
280 break; |
|
281 } |
|
282 case 5: // settingItem6 |
|
283 { |
|
284 settingLine.Copy(attr.iSettingItem6.iSettingText); |
|
285 settingLine.Append(KEquals()); |
|
286 settingLine.Append(attr.iSettingItem6.iValue); |
|
287 settingLine.Append(KCommentSeparator()); |
|
288 settingLine.Append(attr.iSettingItem6.iUIText); |
|
289 settingLine.Append(KNewLine()); |
|
290 CnvUtfConverter::ConvertFromUnicodeToUtf8(settingLine8, settingLine); |
|
291 aFile.Write(settingLine8); |
|
292 break; |
|
293 } |
|
294 } |
|
295 } |
|
296 } |
|
297 } |
|
298 |
|
299 // ---------------------------------------------------------------------------- |
|
300 // Converts given descriptor into TBool value. |
|
301 // ---------------------------------------------------------------------------- |
|
302 // |
|
303 inline void CSamplerController::Str2Bool(const TDesC8& aBuf, TBool& aValue) |
|
304 { |
|
305 if (aBuf.CompareF(KFalse) == 0) |
|
306 aValue = EFalse; |
|
307 else |
|
308 aValue = ETrue; |
|
309 } |
|
310 |
|
311 // ---------------------------------------------------------------------------- |
|
312 // Converts given descriptor into TInt value. |
|
313 // ---------------------------------------------------------------------------- |
|
314 // |
|
315 inline void CSamplerController::Str2Int(const TDesC8& aBuf, TInt& aValue) |
|
316 { |
|
317 TLex8 conv; |
|
318 conv.Assign(aBuf); |
|
319 |
|
320 if (conv.Val(aValue) != KErrNone) |
|
321 aValue = 0; |
|
322 } |
|
323 |
|
324 // ---------------------------------------------------------------------------- |
|
325 // Converts given descriptor into TInt value. |
|
326 // ---------------------------------------------------------------------------- |
|
327 // |
|
328 inline void CSamplerController::Str2Int(const TDesC8& aBuf, TUint32& aValue) |
|
329 { |
|
330 TInt temp(0); |
|
331 |
|
332 TLex8 conv; |
|
333 conv.Assign(aBuf); |
|
334 |
|
335 if (conv.Val(temp) != KErrNone) |
|
336 aValue = 0; |
|
337 else |
|
338 aValue = (TUint32)temp; |
|
339 } |
|
340 |
|
341 // ---------------------------------------------------------------------------- |
|
342 // Converts given boolean into a descriptor. |
|
343 // ---------------------------------------------------------------------------- |
|
344 // |
|
345 inline TBuf8<16> CSamplerController::Bool2Str(const TBool& aValue) |
|
346 { |
|
347 TBuf8<16> buf; |
|
348 |
|
349 if (aValue) |
|
350 buf.Copy(KTrue); |
|
351 else |
|
352 buf.Copy(KFalse); |
|
353 |
|
354 return buf; |
|
355 } |
|
356 |
|
357 // ---------------------------------------------------------------------------- |
|
358 // Converts given integer into a descriptor. |
|
359 // ---------------------------------------------------------------------------- |
|
360 // |
|
361 inline TBuf8<16> CSamplerController::Int2Str(const TInt& aValue) |
|
362 { |
|
363 TBuf8<16> buf; |
|
364 buf.AppendNum(aValue); |
|
365 |
|
366 return buf; |
|
367 } |
|
368 |
|
369 |
|
370 void CSamplerController::HandlePluginLoaded( KSamplerPluginLoaderStatus aStatus ) |
|
371 { |
|
372 |
|
373 // process status value |
|
374 switch(aStatus) |
|
375 { |
|
376 case 0: |
|
377 LOGSTRING2("RSamplerController - one plugin loaded, status: %d", aStatus); |
|
378 break; |
|
379 case 1: |
|
380 LOGSTRING2("RSamplerController - a plugin load failed: %d", aStatus); |
|
381 break; |
|
382 case 2: |
|
383 LOGSTRING2("RSamplerController - plugin loading aborted: %d", aStatus); |
|
384 break; |
|
385 case 3: |
|
386 LOGSTRING2("RSamplerController - all plugins loaded: %d", aStatus); |
|
387 TRAPD(err, iPluginLoader->SortPluginsL(iPluginArray)); |
|
388 if(err != KErrNone) |
|
389 { |
|
390 LOGTEXT(_L("Sampler controller unable to sort plugins")); |
|
391 } |
|
392 |
|
393 // call engine to finalize the startup |
|
394 TRAPD(result, iObserver->HandleSamplerControllerReadyL();); |
|
395 if(result != KErrNone) |
|
396 { |
|
397 LOGTEXT(_L("Failed to notify engine")); |
|
398 } |
|
399 break; |
|
400 case 4: |
|
401 LOGSTRING2("RSamplerController - error in loading plugins: %d", aStatus); |
|
402 break; |
|
403 default: |
|
404 break; |
|
405 } |
|
406 } |
|
407 |
|
408 |
|
409 CSamplerPluginInterface* CSamplerController::GetPlugin(TUid aUid) |
|
410 { |
|
411 LOGTEXT(_L("RSamplerController::GetPlugin - entry")); |
|
412 // check that plugin array contains samplers |
|
413 if( iPluginArray && iPluginArray->Count() > 0 ) |
|
414 { |
|
415 for(TInt i=0;i<iPluginArray->Count();i++) |
|
416 { |
|
417 CSamplerPluginInterface* plugin = iPluginArray->At(i); |
|
418 TUid uid = plugin->Id(-1); // get parent uid first |
|
419 if(uid == aUid) |
|
420 { |
|
421 LOGTEXT(_L("CSamplerController::GetPlugin() - main plug-in found!")); |
|
422 return plugin; |
|
423 } |
|
424 |
|
425 if(plugin->SubId(aUid) != KErrNotFound) |
|
426 { |
|
427 LOGTEXT(_L("CSamplerController::GetPlugin() - subsampler found!")); |
|
428 return plugin; |
|
429 } |
|
430 } |
|
431 } |
|
432 LOGTEXT(_L("CSamplerController::GetPlugin() - No plug-in found for UID")); |
|
433 |
|
434 return (CSamplerPluginInterface*)0; |
|
435 } |
|
436 |
|
437 // start user mode samplers |
|
438 void CSamplerController::StartSamplerPluginsL() |
|
439 { |
|
440 CSamplerPluginInterface* plugin = NULL; |
|
441 |
|
442 if( iPluginArray ) |
|
443 { |
|
444 TInt count(iPluginArray->Count()); |
|
445 |
|
446 for(TInt i(0);i<count;i++) |
|
447 { |
|
448 plugin = iPluginArray->At(i); |
|
449 // check if some error received when starting profiling |
|
450 TRAPD(err, plugin->ResetAndActivateL(iStream)); |
|
451 LOGSTRING2(" RSamplerController::StartSamplerPlugin - plugin activated (0x%X)", plugin->Id(-1)); |
|
452 if( err != KErrNone) |
|
453 { |
|
454 LOGSTRING2(" RSamplerController::StartSamplerPlugin - error %d", i); |
|
455 // handle received error, need to update UI! |
|
456 iObserver->HandleError(err); |
|
457 } |
|
458 } |
|
459 } |
|
460 } |
|
461 |
|
462 // stop user mode samplers |
|
463 TInt CSamplerController::StopSamplerPlugins() |
|
464 { |
|
465 TInt count(0); |
|
466 |
|
467 if( iPluginArray && iPluginArray->Count() > 0 ) |
|
468 { |
|
469 TInt i(0); |
|
470 CSamplerPluginInterface* plugin = NULL; |
|
471 // stop kernel mode samplers |
|
472 for(;i<iPluginArray->Count();i++) |
|
473 { |
|
474 plugin = iPluginArray->At(i); |
|
475 TUint32 id = plugin->Id(-1).iUid; |
|
476 LOGSTRING2(" CSamplerController::StopSamplerPlugins - traceId = %d", |
|
477 id); |
|
478 // stop only started samplers |
|
479 if(plugin->Enabled()) |
|
480 { |
|
481 // stop selected plugin |
|
482 plugin->StopSampling(); |
|
483 // check if user mode sampler, special flush needed to direct data to stream |
|
484 if(plugin->GetSamplerType() == PROFILER_USER_MODE_SAMPLER) |
|
485 { |
|
486 LOGTEXT(_L(" CSamplerController::StopSamplerPlugins - flushing user mode sampler stream")); |
|
487 plugin->Flush(); |
|
488 } |
|
489 } |
|
490 count++; |
|
491 } |
|
492 } |
|
493 return count; |
|
494 } |
|
495 |
|
496 // end of file |
|
497 |
|
498 |
|
499 |
|
500 |
|