|         |      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 #ifndef PROFILER_ITT_SAMPLER_H | 
|         |     19 #define PROFILER_ITT_SAMPLER_H | 
|         |     20  | 
|         |     21 #include "GeneralsConfig.h" | 
|         |     22  | 
|         |     23 #include <kern_priv.h> | 
|         |     24  | 
|         |     25 #include <piprofiler/ProfilerGenericClassesKrn.h> | 
|         |     26 #include <piprofiler/ProfilerTraces.h> | 
|         |     27 #include "GppSamplerImpl.h" | 
|         |     28 #include "IttEventHandler.h" | 
|         |     29  | 
|         |     30 // CONSTANTS | 
|         |     31 const TInt KITTSampleBufferSize = 256; | 
|         |     32  | 
|         |     33 // flags | 
|         |     34 #define ITT_EVENT_HANDLER   // enable event based ITT sampling | 
|         |     35  | 
|         |     36 /* | 
|         |     37  *	 | 
|         |     38  *	ITT sampler definition | 
|         |     39  *	 | 
|         |     40  */ | 
|         |     41 class DIttEventHandler; | 
|         |     42  | 
|         |     43 /* | 
|         |     44  * User side ITT sampler | 
|         |     45  */ | 
|         |     46 class IttSamplerImpl | 
|         |     47 { | 
|         |     48 public: | 
|         |     49 	IttSamplerImpl(); | 
|         |     50 	~IttSamplerImpl(); | 
|         |     51  | 
|         |     52 	TInt	SampleImpl(TUint32 pc,TUint32 sampleNum); | 
|         |     53 	TBool	SampleNeeded(TUint32 sampleNum); | 
|         |     54 	TInt 	CreateFirstSample(); | 
|         |     55 	void	Reset(); | 
|         |     56 	TInt    ProcessEvent(); | 
|         |     57 	 | 
|         |     58 	TUint8*         itt_sample; | 
|         |     59 	TInt            iIttSamplingPeriod; | 
|         |     60 	TInt            iIttSamplingPeriodDiv2; | 
|         |     61 	TBool           iTimeToSample; | 
|         |     62 #ifdef ITT_EVENT_HANDLER | 
|         |     63     TBool           iEventReceived; | 
|         |     64     TBool           iFirstSampleTaken; | 
|         |     65 #endif | 
|         |     66 	 | 
|         |     67 private: | 
|         |     68 #ifdef ITT_EVENT_HANDLER     | 
|         |     69     TInt            iCount; | 
|         |     70 #endif | 
|         |     71     TInt            currentLibCount; | 
|         |     72     TInt            currentProcCount; | 
|         |     73      | 
|         |     74 	TUint8          sample[KITTSampleBufferSize ]; | 
|         |     75 	TPtr8           sampleDescriptor; | 
|         |     76 		 | 
|         |     77 	TBuf8<64>		iVersionData; | 
|         |     78 	SDblQue* 		codeSegList; | 
|         |     79  | 
|         |     80 }; | 
|         |     81  | 
|         |     82 /* | 
|         |     83  * ITT sampler kernel part | 
|         |     84  *  | 
|         |     85  */ | 
|         |     86 template <int BufferSize> | 
|         |     87 class DProfilerIttSampler : public DProfilerGenericSampler<BufferSize> | 
|         |     88 { | 
|         |     89 public: | 
|         |     90 	DProfilerIttSampler(struct TProfilerGppSamplerData* gppSamplerDataIn); | 
|         |     91 	~DProfilerIttSampler(); | 
|         |     92  | 
|         |     93 	void	Sample(); | 
|         |     94 	TInt	Reset(DProfilerSampleStream* aStream, TUint32 aSyncOffset); | 
|         |     95 	TInt	PostSample(); | 
|         |     96 	TBool	PostSampleNeeded(); | 
|         |     97  | 
|         |     98 private: | 
|         |     99 #ifdef ITT_EVENT_HANDLER | 
|         |    100     DIttEventHandler*               iEventHandler; | 
|         |    101 #endif | 
|         |    102 	IttSamplerImpl					ittSamplerImpl; | 
|         |    103 	struct TProfilerGppSamplerData*     gppSamplerData; | 
|         |    104 	TBool							sampleInProgress; | 
|         |    105 	TBool							sampleNeeded; | 
|         |    106 }; | 
|         |    107  | 
|         |    108 /*   | 
|         |    109  *	ITT sampler implementation | 
|         |    110  *	 | 
|         |    111  */  | 
|         |    112 template <int BufferSize> | 
|         |    113 DProfilerIttSampler<BufferSize>::DProfilerIttSampler(struct TProfilerGppSamplerData* gppSamplerDataIn) : | 
|         |    114 	DProfilerGenericSampler<BufferSize>(PROFILER_ITT_SAMPLER_ID) | 
|         |    115 { | 
|         |    116 	this->gppSamplerData = (struct TProfilerGppSamplerData*)gppSamplerDataIn; | 
|         |    117 	this->sampleInProgress = false; | 
|         |    118 	LOGSTRING2("CProfilerIttSampler<%d>::CProfilerIttSampler",BufferSize);	 | 
|         |    119 } | 
|         |    120  | 
|         |    121 /* | 
|         |    122  *  DProfilerIttSampler::Reset() | 
|         |    123  *   | 
|         |    124  *  @param DProfilerSampleStream* sample stream | 
|         |    125  *  @param TUint32 Offset  | 
|         |    126  */ | 
|         |    127 template <int BufferSize> | 
|         |    128 TInt DProfilerIttSampler<BufferSize>::Reset(DProfilerSampleStream* aStream, TUint32 aSyncOffset) | 
|         |    129 { | 
|         |    130     Kern::Printf("DProfilerIttSampler<%d>::Reset - calling superclass reset",BufferSize); | 
|         |    131     DProfilerGenericSampler<BufferSize>::Reset(aStream); | 
|         |    132  | 
|         |    133     // check if reset called in stop (by driver) | 
|         |    134     if(aSyncOffset != 999999) | 
|         |    135         { | 
|         |    136 #ifdef ITT_EVENT_HANDLER | 
|         |    137         // Itt event handler | 
|         |    138         if(iEventHandler) | 
|         |    139             { | 
|         |    140             // stop previous sampling if still running | 
|         |    141             Kern::Printf("Stopping DIttEventHandler"); | 
|         |    142             iEventHandler->Stop(); | 
|         |    143             iEventHandler->Close(); | 
|         |    144             iEventHandler = NULL; | 
|         |    145             } | 
|         |    146      | 
|         |    147         Kern::Printf("Initiating DIttEventHandler"); | 
|         |    148         iEventHandler = new DIttEventHandler(this->iSampleBuffer, this->gppSamplerData); | 
|         |    149         if(iEventHandler) | 
|         |    150             { | 
|         |    151             Kern::Printf("Creating DIttEventHandler"); | 
|         |    152             TInt err(iEventHandler->Create()); | 
|         |    153             if(err != KErrNone) | 
|         |    154                 { | 
|         |    155                 Kern::Printf("Error in creation of DIttEventHandler, error %d", err); | 
|         |    156                 return err; | 
|         |    157                 } | 
|         |    158             } | 
|         |    159         else | 
|         |    160             { | 
|         |    161             Kern::Printf("Could not initiate DIttEventHandler"); | 
|         |    162             return KErrGeneral; | 
|         |    163             } | 
|         |    164      | 
|         |    165         // set first sample at the 10 ms, should be enough | 
|         |    166         this->ittSamplerImpl.iIttSamplingPeriod = 10; | 
|         |    167 #else | 
|         |    168         this->ittSamplerImpl.iIttSamplingPeriod = this->iSamplingPeriod; | 
|         |    169 #endif | 
|         |    170         this->ittSamplerImpl.iIttSamplingPeriodDiv2 = (TInt)(this->ittSamplerImpl.iIttSamplingPeriod / 2); | 
|         |    171         LOGSTRING3("CProfilerIttSampler<%d>::Reset - set ITT sampling period to %d", | 
|         |    172                                 BufferSize,this->ittSamplerImpl.iIttSamplingPeriod); | 
|         |    173         } | 
|         |    174     else | 
|         |    175         { | 
|         |    176         LOGSTRING2("DProfilerIttSampler<%d>::Reset - reset in stop", BufferSize); | 
|         |    177 #ifdef ITT_EVENT_HANDLER | 
|         |    178         // destroy memory event handler | 
|         |    179         if(iEventHandler) | 
|         |    180             { | 
|         |    181             // stop previous sampling if still running | 
|         |    182             iEventHandler->Stop(); | 
|         |    183             iEventHandler->Close(); | 
|         |    184             iEventHandler = NULL; | 
|         |    185             } | 
|         |    186 #endif | 
|         |    187         return KErrNone;    // return if reset called in stop | 
|         |    188         } | 
|         |    189  | 
|         |    190     TInt length(ittSamplerImpl.CreateFirstSample()); | 
|         |    191     this->iSampleBuffer->AddSample((TUint8*)&length,1); | 
|         |    192     this->iSampleBuffer->AddSample(ittSamplerImpl.itt_sample, length); | 
|         |    193     this->sampleInProgress = false; | 
|         |    194     this->sampleNeeded = false; | 
|         |    195     //LOGSTRING("DProfilerIttSampler::Reset - exit"); | 
|         |    196 	this->ittSamplerImpl.Reset(); | 
|         |    197     return KErrNone; | 
|         |    198  | 
|         |    199 } | 
|         |    200  | 
|         |    201 /* | 
|         |    202  * DProfilerIttSampler::PostSample | 
|         |    203  *  | 
|         |    204  * Function for finishing sample | 
|         |    205  */ | 
|         |    206 template <int BufferSize>  | 
|         |    207 TInt DProfilerIttSampler<BufferSize>::PostSample() | 
|         |    208 { | 
|         |    209 #ifdef ITT_EVENT_HANDLER | 
|         |    210     if(!ittSamplerImpl.iFirstSampleTaken)   // if we haven't read the initial state | 
|         |    211     { | 
|         |    212 #endif | 
|         |    213         if(sampleNeeded) | 
|         |    214         { | 
|         |    215             this->sampleNeeded = false; | 
|         |    216             //LOGSTRING3("CProfilerIttSampler<%d>::PostSample - state %d",BufferSize,this->iSampleBuffer->GetBufferStatus()); | 
|         |    217             //Kern::Printf("DProfilerIttSampler<%d>::PostSample - state %d",BufferSize,this->iSampleBuffer->GetBufferStatus()); | 
|         |    218      | 
|         |    219             TInt length = this->ittSamplerImpl.SampleImpl(this->gppSamplerData->lastPcValue, | 
|         |    220                                                           this->gppSamplerData->sampleNumber); | 
|         |    221             if(length != 0) | 
|         |    222             {		 | 
|         |    223                 LOGSTRING("ITT sampler PostSample - starting to sample"); | 
|         |    224      | 
|         |    225                 while(length > 0) | 
|         |    226                 { | 
|         |    227                     this->iSampleBuffer->AddSample(ittSamplerImpl.itt_sample,length); | 
|         |    228                     length = this->ittSamplerImpl.SampleImpl( this->gppSamplerData->lastPcValue, | 
|         |    229                                                           this->gppSamplerData->sampleNumber );	 | 
|         |    230                     if(length == 0)  | 
|         |    231                     { | 
|         |    232                         LOGSTRING("MEM sampler PostSample - all samples generated!"); | 
|         |    233                     } | 
|         |    234                 } | 
|         |    235                 LOGSTRING("ITT sampler PostSample - finished sampling"); | 
|         |    236             } | 
|         |    237             this->sampleInProgress = false; | 
|         |    238         } | 
|         |    239 #ifdef ITT_EVENT_HANDLER | 
|         |    240     }    | 
|         |    241         if(!iEventHandler->Tracking()) | 
|         |    242             { | 
|         |    243             iEventHandler->Start(); | 
|         |    244             Kern::Printf("DProfilerITTSampler<%d>::PostSample - ITT handler started",BufferSize); | 
|         |    245             } | 
|         |    246  | 
|         |    247 #endif     | 
|         |    248 	 | 
|         |    249     LOGSTRING2("ITT sampler PostSample - finished sampling, time: %d", gppSamplerData->sampleNumber); | 
|         |    250      | 
|         |    251 	// finally perform superclass postsample | 
|         |    252 	TInt i(this->DProfilerGenericSampler<BufferSize>::PostSample()); | 
|         |    253 	return i; | 
|         |    254 } | 
|         |    255  | 
|         |    256 /* | 
|         |    257  *  DProfilerIttSampler::PostSampleNeeded() | 
|         |    258  *   | 
|         |    259  *  Function for deciding if sample handling is needed  | 
|         |    260  */ | 
|         |    261 template <int BufferSize>  | 
|         |    262 TBool DProfilerIttSampler<BufferSize>::PostSampleNeeded() | 
|         |    263 { | 
|         |    264 	LOGSTRING3("CProfilerIttSampler<%d>::PostSampleNeeded - state %d",BufferSize,this->iSampleBuffer->GetBufferStatus()); | 
|         |    265  | 
|         |    266 	TUint32 status = this->iSampleBuffer->iBufferStatus; | 
|         |    267  | 
|         |    268 	if(status == DProfilerSampleBuffer::BufferCopyAsap || status == DProfilerSampleBuffer::BufferFull || this->sampleNeeded == true) | 
|         |    269 	{ | 
|         |    270 		return true; | 
|         |    271 	} | 
|         |    272 	 | 
|         |    273 	return false; | 
|         |    274 } | 
|         |    275  | 
|         |    276 /* | 
|         |    277  * DProfilerIttSampler::Sample | 
|         |    278  *  | 
|         |    279  * Function for initiating sampling | 
|         |    280  */ | 
|         |    281 template <int BufferSize> | 
|         |    282 void DProfilerIttSampler<BufferSize>::Sample() | 
|         |    283 { | 
|         |    284 	LOGSTRING2("CProfilerIttSampler<%d>::Sample",BufferSize);	 | 
|         |    285 	 | 
|         |    286 	//#ifdef ITT_TEST | 
|         |    287 	LOGSTRING2("CProfilerIttSampler<%d>::Sample",BufferSize);	 | 
|         |    288 	 | 
|         |    289 	if(ittSamplerImpl.SampleNeeded(this->gppSamplerData->sampleNumber) && this->sampleInProgress == false)  | 
|         |    290 	{ | 
|         |    291 		this->sampleInProgress = true; | 
|         |    292 		this->sampleNeeded = true; | 
|         |    293  | 
|         |    294 		LOGSTRING2("CProfilerIttSampler<%d>::Sample - sample needed",BufferSize);	 | 
|         |    295 	}	 | 
|         |    296 #ifdef ITT_EVENT_HANDLER | 
|         |    297     // call this to increase the time stamp | 
|         |    298     else if(iEventHandler->SampleNeeded()) | 
|         |    299         { | 
|         |    300         // set the flag for post sampling | 
|         |    301         this->sampleNeeded = true; | 
|         |    302         } | 
|         |    303 #endif | 
|         |    304  | 
|         |    305 	LOGSTRING2("CProfilerIttSampler<%d>::Sample",BufferSize); | 
|         |    306 	return; | 
|         |    307 } | 
|         |    308  | 
|         |    309 /* | 
|         |    310  * Destructor | 
|         |    311  */ | 
|         |    312 template <int BufferSize> | 
|         |    313 DProfilerIttSampler<BufferSize>::~DProfilerIttSampler() | 
|         |    314 { | 
|         |    315 	LOGSTRING2("CProfilerIttSampler<%d>::~CProfilerIttSampler",BufferSize); | 
|         |    316 #ifdef ITT_EVENT_HANDLER | 
|         |    317      if(iEventHandler) | 
|         |    318          { | 
|         |    319          // stop previous sampling if still running | 
|         |    320          iEventHandler->Stop(); | 
|         |    321          iEventHandler->Close(); | 
|         |    322          iEventHandler = NULL; | 
|         |    323          } | 
|         |    324 #endif | 
|         |    325 } | 
|         |    326 #endif | 
|         |    327 // end of file |