📄 performance.cpp
字号:
//
// Performance.cpp - Performance example
//
// Copyright (C) UIQ Technology AB, 2007
//
// This material is provided "as is" without any warranty to its performance or functionality.
// In no event shall UIQ Technology be liable for any damages whatsoever arising out of the
// use or inabilty to use this material.
//
#include "Performance.h"
#include "Performance.hrh"
#include <Performance.rsg>
#include <QikViewBase.h>
#include <QikCommand.h>
#include <eikstart.h>
#include <e32math.h>
//////////////////////////////////////////////////////////////////////////////
// The application Uid here MUST match UID3 defined in the MMP file
// This is a development UID and must NOT be used in production type software
const TUid KAppSpecificUid={0xEDEAD020};
// internal secondary view id, must be unique amongst this applications views
const TUid KUidListView={0x00000001};
// views within applications are fully identified by the app Uid and secondary view id
#define KViewIdListView TVwsViewId(KAppSpecificUid,KUidListView)
///////////////////////////////////////////////////////////////////////////
// A simple regular C like function
LOCAL_D TInt lFunctionCount;
LOCAL_D void IncFunctionCount()
{
lFunctionCount++;
}
///////////////////////////////////////////////////////////////////////////
// This class is typical of a compute intensive task we might set up within
// an application.
class CPerformanceTestBase : public CActive
{
protected:
// from CActive
void DoCancel();
void RunL();
// new methods
void RequestComplete();
public:
~CPerformanceTestBase();
CPerformanceTestBase();
void IncMethodCount();
void IntegerCalc();
void FloatingPointCalc();
void StartRunLTest();
virtual void VirtualIncMethodCount()=0;
void TrapCalc();
void GranularityTestPart1L();
void GranularityTestPart2L();
void GranularityTestPart3L();
void GranularityTestPart4L();
void ArrayTest();
void CArrayTestPart1L();
void CArrayTestPart2();
void RArrayTestPart1L();
void RArrayTestPart2();
void FileWriteTest1();
void FileWriteTest2();
void FileReadTest1Part1();
void FileReadTest1Part2();
void FileReadTest1Part3();
void FileReadTest1Part4();
protected:
TInt iMethodCount;
TInt iRunLCount;
TInt iAdd;
TInt iSubtract;
TReal iFloatingPointVal;
// arrays for array performance test
CArrayFixFlat<TInt>* iCArray;
RArray<TInt>* iRArray;
TInt iArray[1000];
// buffer used for file i/o performance test
TBuf8<10000> iBuffer;
};
CPerformanceTestBase::~CPerformanceTestBase()
{
Cancel();
delete(iCArray);
if (iRArray)
iRArray->Close();
}
CPerformanceTestBase::CPerformanceTestBase() :
CActive(CActive::EPriorityLow)
//
// Note that we set our priority to EPriorityLow. This means we are near the end
// of the priority ordered linked list of active objects. This in turn means that
// if UI events arrive they will be processed before we are given the opportunity
// to perform any processing.
//
{
CActiveScheduler::Add(this);
for (TInt i=0;i<1000;i++)
iArray[i]=i;
for (TInt i=0;i<10000;i++)
iBuffer.Append(i);
}
void CPerformanceTestBase::DoCancel()
// Were always complete so nothing to actually cancel. If you had a long running
// task you probably want to record the fact that the calculation was cancelled as
// opposed to completing.
{
}
void CPerformanceTestBase::RequestComplete()
// Signal ourselves. If we are the highest priority active object
// we will get to run next loop around the schedular.
// If higher priority active objects have outstanding events they will get to run before us.
// Once the higher priortity ones have completed, we get to run
{
TRequestStatus* q=(&iStatus);
User::RequestComplete(q,KErrNone);
SetActive();
}
void CPerformanceTestBase::RunL()
// The schduler has called our code to perform next slice of processing.
{
iRunLCount++;
if (iRunLCount<500000) // 5 hundred thousand
RequestComplete();
else
// calling CActiveScheduler::Stop is really only valid for test code - should not be in real apps.
CActiveScheduler::Stop();
}
void CPerformanceTestBase::IncMethodCount()
// Simple, non virtual method to see how many times/sec we can be called
{
iMethodCount++;
}
void CPerformanceTestBase::IntegerCalc()
// Perform some integer calcs to give some benchmarks. Note the i++ means 3 integer calcs per loop
// and it could be argued the i<10000.. is a 4th integer calc. But we only want a ball park
// figure.
{
iAdd=0;
iSubtract=10000000;
for (TInt i=0;i<10000000;i++)
{
iAdd++;
iSubtract--;
}
}
void CPerformanceTestBase::TrapCalc()
// Give a clue about the effect of TRAP in method calling
{
iMethodCount=0;
for (TInt i=0;i<1000000;i++)
{ // 1 million calls
TRAPD(err,IncMethodCount());
}
}
void CPerformanceTestBase::FloatingPointCalc()
{ // perform a reasonably simple floating point calc to give some idea
// of the sort of performance occuring
iFloatingPointVal=KPi;
for (TInt i=0;i<1000000;i++) // 1 million - sqrt and *
Math::Sqrt(iFloatingPointVal,iFloatingPointVal*iFloatingPointVal);
}
void CPerformanceTestBase::StartRunLTest()
// We need to set ourselves as now being 'active' and cause our RunL to be
// called by the scheduler when there is spare processing capacity.
{
RequestComplete();
// calling Start() is only reasonable for this test code
CActiveScheduler::Start();
}
void CPerformanceTestBase::GranularityTestPart1L()
// Create and add entries to a CArray, granularity 1
{
CArrayFixFlat<TInt>* q=new(ELeave)CArrayFixFlat<TInt>(1);
CleanupStack::PushL(q);
for (TInt j=0;j<10;j++)
{
for (TInt i=0;i<100000;i++)
q->AppendL(i);
q->Reset();
}
CleanupStack::PopAndDestroy(q);
}
void CPerformanceTestBase::GranularityTestPart2L()
// Create and add entries to a CArray, granularity 100000
{
CArrayFixFlat<TInt>* q=new(ELeave)CArrayFixFlat<TInt>(100000);
CleanupStack::PushL(q);
for (TInt j=0;j<10;j++)
{
for (TInt i=0;i<100000;i++)
q->AppendL(i);
q->Reset();
}
CleanupStack::PopAndDestroy(q);
}
void CPerformanceTestBase::GranularityTestPart3L()
// Create and add entries to a RArray, granularity 1
{
RArray<TInt>* q=new(ELeave)RArray<TInt>(1);
CleanupDeletePushL(q);
CleanupClosePushL(*q);
for (TInt j=0;j<10;j++)
{
for (TInt i=0;i<100000;i++)
q->AppendL(i);
q->Reset();
}
CleanupStack::PopAndDestroy(2);
}
void CPerformanceTestBase::GranularityTestPart4L()
// Create and add entries to a RArray, granularity 100000
{
RArray<TInt>* q=new(ELeave)RArray<TInt>(100000);
CleanupDeletePushL(q);
CleanupClosePushL(*q);
for (TInt j=0;j<10;j++)
{
for (TInt i=0;i<100000;i++)
q->AppendL(i);
q->Reset();
}
CleanupStack::PopAndDestroy(2);
}
void CPerformanceTestBase::ArrayTest()
{
for (TInt i=0;i<10000;i++)
{ // 10 million flat acceses
for (TInt j=0;j<1000;j++)
{
if (iArray[j]!=j)
break;
}
}
}
void CPerformanceTestBase::CArrayTestPart1L()
// Create and add 10,000 entries to a CArray
{
CArrayFixFlat<TInt>* q=new(ELeave)CArrayFixFlat<TInt>(32);
CleanupStack::PushL(q);
for (TInt i=0;i<10000;i++)
q->AppendL(i);
iCArray=q;
CleanupStack::Pop(q);
}
void CPerformanceTestBase::CArrayTestPart2()
{
TInt count=iCArray->Count();
for (TInt i=0;i<1000;i++)
{ // 10 million acceses (1000*10,000 array entries)
for (TInt j=0;j<count;j++)
{
if (iCArray->At(j)!=j)
break;
}
}
delete(iCArray);
iCArray=NULL;
}
void CPerformanceTestBase::RArrayTestPart1L()
// Create and add 10,000 entries to a CArray
{
RArray<TInt>* q=new(ELeave)RArray<TInt>(32);
CleanupClosePushL(*q);
for (TInt i=0;i<10000;i++)
q->AppendL(i);
iRArray=q;
CleanupStack::Pop(q);
}
void CPerformanceTestBase::RArrayTestPart2()
{
TInt count=iRArray->Count();
for (TInt i=0;i<1000;i++)
{ // 10 million acceses (1000*10,000 array entries)
for (TInt j=0;j<count;j++)
{
if ((*iRArray)[j]!=j)
break;
}
}
iRArray->Close();
delete(iRArray);
iRArray=NULL;
}
_LIT(KTestFileName,"C:\\FileWriteTest.txt");
void CPerformanceTestBase::FileWriteTest1()
//
// Write 0.5mb, 100 bytes at a time to the file.
//
{
RFile file;
TInt ret=file.Replace(CEikonEnv::Static()->FsSession(),KTestFileName,EFileShareExclusive|EFileWrite|EFileStream);
if (ret!=KErrNone)
User::Panic(KTestFileName,0);
// have a relatively small buffer - 100 bytes
TInt i;
TBuf8<100> buffer;
for (i=0;i<100;i++)
buffer.Append(i);
for (i=0;i<5000;i++)
{ // 0.5 MB
ret=file.Write(buffer);
if (ret!=KErrNone)
User::Panic(KTestFileName,1);
if (i>0 && (i%100)==0)
{ // do seeks every 10k, same as FileWriteTest2()
TInt pos=0;
ret=file.Seek(ESeekStart,pos);
if (ret!=KErrNone)
User::Panic(KTestFileName,2);
}
}
file.Close();
CEikonEnv::Static()->FsSession().Delete(KTestFileName);
}
void CPerformanceTestBase::FileWriteTest2()
//
// Write 5mb, 10000 bytes at a time to the file.
//
{
RFile file;
TInt ret=file.Replace(CEikonEnv::Static()->FsSession(),KTestFileName,EFileShareExclusive|EFileWrite|EFileStream);
if (ret!=KErrNone)
User::Panic(KTestFileName,3);
for (TInt i=0;i<500;i++)
{ // 5 MB
ret=file.Write(iBuffer);
if (ret!=KErrNone)
User::Panic(KTestFileName,4);
TInt pos=0;
ret=file.Seek(ESeekStart,pos);
if (ret!=KErrNone)
User::Panic(KTestFileName,5);
}
file.Close();
CEikonEnv::Static()->FsSession().Delete(KTestFileName);
}
void CPerformanceTestBase::FileReadTest1Part1()
//
// Create a 5mb file which we will subsequently read
//
{
RFile file;
TInt ret=file.Replace(CEikonEnv::Static()->FsSession(),KTestFileName,EFileShareExclusive|EFileWrite|EFileStream);
if (ret!=KErrNone)
User::Panic(KTestFileName,6);
for (TInt i=0;i<500;i++)
{ // 5 MB
ret=file.Write(iBuffer);
if (ret!=KErrNone)
User::Panic(KTestFileName,7);
}
file.Close();
}
void CPerformanceTestBase::FileReadTest1Part2()
//
// Read 5mb from disk, 100 bytes at a time
//
{
RFile file;
TInt ret=file.Open(CEikonEnv::Static()->FsSession(),KTestFileName,EFileShareExclusive|EFileRead|EFileStream);
if (ret!=KErrNone)
User::Panic(KTestFileName,8);
TBuf8<100> buffer;
for (TInt i=0;i<50000;i++)
// replace above with this for 1k test
// TBuf8<1000> buffer;
// for (TInt i=0;i<5000;i++)
{ // 5 MB
ret=file.Read(buffer);
if (ret!=KErrNone)
User::Panic(KTestFileName,9);
}
file.Close();
}
void CPerformanceTestBase::FileReadTest1Part3()
//
// Read 5mb from disk, 10000 bytes at a time
//
{
RFile file;
TInt ret=file.Open(CEikonEnv::Static()->FsSession(),KTestFileName,EFileShareExclusive|EFileRead|EFileStream);
if (ret!=KErrNone)
User::Panic(KTestFileName,10);
for (TInt i=0;i<500;i++)
{ // 5 MB
ret=file.Read(iBuffer);
if (ret!=KErrNone)
User::Panic(KTestFileName,11);
}
file.Close();
}
void CPerformanceTestBase::FileReadTest1Part4()
{
// tidy up the 5mb file !!
CEikonEnv::Static()->FsSession().Delete(KTestFileName);
}
///////////////////////////////////////////////////////////////////////////
// implementation of a pure virtual method
class CPerformanceTest : public CPerformanceTestBase
{
protected:
// from CPerformanceTestBase
void VirtualIncMethodCount();
public:
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -