os/graphics/graphicstest/uibench/src/tmultiptreventhandlingperf.cpp
changeset 0 bde4ae8d615e
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/os/graphics/graphicstest/uibench/src/tmultiptreventhandlingperf.cpp	Fri Jun 15 03:10:57 2012 +0200
     1.3 @@ -0,0 +1,523 @@
     1.4 +// Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies).
     1.5 +// All rights reserved.
     1.6 +// This component and the accompanying materials are made available
     1.7 +// under the terms of "Eclipse Public License v1.0"
     1.8 +// which accompanies this distribution, and is available
     1.9 +// at the URL "http://www.eclipse.org/legal/epl-v10.html".
    1.10 +//
    1.11 +// Initial Contributors:
    1.12 +// Nokia Corporation - initial contribution.
    1.13 +//
    1.14 +// Contributors:
    1.15 +//
    1.16 +// Description:
    1.17 +//
    1.18 +
    1.19 +/**
    1.20 + @file
    1.21 + @test
    1.22 + @internalComponent - Internal Symbian test code 
    1.23 +*/
    1.24 +
    1.25 +#include "tmultiptreventhandlingperf.h"
    1.26 +#include <hal.h>
    1.27 +
    1.28 +_LIT(KPerformanceTimingChunk, "PerformanceTimingChunk");
    1.29 +
    1.30 +// Number of iterations for eventset
    1.31 +const TInt KNumOfIterations = 100;
    1.32 +
    1.33 +// Maximum descriptor length for results
    1.34 +const TInt KMaxDescLength = 528;
    1.35 +
    1.36 +// Static variables used for synchronisation between threads
    1.37 +GLDEF_D TInt NumOfEventsAdded = 0;
    1.38 +GLDEF_D RMutex Mutex;
    1.39 +GLDEF_D RCondVar ConVar;
    1.40 +
    1.41 +void MultiPtrPerfPanic(TInt aPanic)
    1.42 +	{
    1.43 +	User::Panic(_L("MultiPterEventHanldingPerformancePanic"), aPanic);
    1.44 +	}
    1.45 +
    1.46 +// This function opens the chunk and adds the failure description followed by '*'
    1.47 +TInt CMultiPtrPerfTestControl::Failed(TPoint3D aExp3DPoint, TPoint3D aActual3DPoint, TInt aErrorCode, TInt aExpPtrNum, TInt aActPtrNum)
    1.48 +	{
    1.49 +	TInt ret = iChunk.OpenGlobal(KPerformanceTimingChunk, ETrue);
    1.50 +	if (ret != KErrNone)
    1.51 +		{
    1.52 +		return ret;
    1.53 +		}
    1.54 +	TUint8* desPtr = iChunk.Base() + iChunkOffset;
    1.55 +	TPtr8 ptrDes(desPtr, 0, KMaxDescLength);
    1.56 +	
    1.57 +	TBuf<80> buf;
    1.58 +	if (aExpPtrNum != aActPtrNum)
    1.59 +		{
    1.60 +		_LIT(KFailedPointerNum, "Failed Expected Pointer Num = %d Actual Pointer Num = %d*");
    1.61 +		buf.AppendFormat(KFailedPointerNum, aExpPtrNum, aActPtrNum);
    1.62 +		ptrDes.Append(buf);
    1.63 +		} 
    1.64 +	else if (aErrorCode != KErrNone)
    1.65 +		{
    1.66 +		_LIT(KFailedErrorCode, "Failed Errorcode = %d*");
    1.67 +		buf.AppendFormat(KFailedErrorCode, aErrorCode);
    1.68 +		ptrDes.Append(buf);
    1.69 +		}
    1.70 +	else
    1.71 +		{
    1.72 +		_LIT(KFailedWrongCoord, "Failed Coordinates Expected = [%d, %d, %d] Actual = [%d, %d, %d]*");
    1.73 +		buf.AppendFormat(KFailedWrongCoord, aExp3DPoint.iX, aExp3DPoint.iY, aExp3DPoint.iZ, aActual3DPoint.iX, aActual3DPoint.iY, aActual3DPoint.iZ);
    1.74 +		ptrDes.Append(buf);
    1.75 +		}
    1.76 +	
    1.77 +	iChunk.Close();
    1.78 +	return ret;
    1.79 +	}
    1.80 +
    1.81 +// This function opens the chunk and adds a pointer event not supported message followed by '#'
    1.82 +TInt CMultiPtrPerfTestControl::PointerEventsNotSupported()
    1.83 +    {
    1.84 +    iPointerEventNotSupported = ETrue;
    1.85 +    TInt ret = iChunk.OpenGlobal(KPerformanceTimingChunk, ETrue);
    1.86 +        if (ret != KErrNone)
    1.87 +            {
    1.88 +            return ret;
    1.89 +            }
    1.90 +    TUint8* desPtr = iChunk.Base() + iChunkOffset;
    1.91 +    TPtr8 ptrDes(desPtr, 0, KMaxDescLength);
    1.92 +    TBuf<80> buf;
    1.93 +    _LIT(KPointerEventsNotSupported, "Test Skipped As Pointer Events Are Not Supported By This Configuration#");
    1.94 +    buf.AppendFormat(KPointerEventsNotSupported);
    1.95 +    ptrDes.Append(buf);
    1.96 +    iChunk.Close();
    1.97 +    return ret;
    1.98 +    }
    1.99 +
   1.100 +// This function calulates the average latency, opens the chunk and appends
   1.101 +// the same in descriptor form. Then close the child thread and calls function 
   1.102 +// for creating new thread for events. 
   1.103 +// If all the events have been tested then stops the tests
   1.104 +// by calling active CActiveScheduler::Stop. 
   1.105 +TInt CMultiPtrPerfTestControl::CalculateLatencyAndStartThread()
   1.106 +	{
   1.107 +	TInt ret = KErrNone;
   1.108 +	switch (iPtrAppUi->TestCaseNum())
   1.109 +		{
   1.110 +		case 1:
   1.111 +		case 5:
   1.112 +		case 9:
   1.113 +		case 13:	
   1.114 +			iAverageLatency = iLatency/(4*KNumOfIterations);
   1.115 +			break;
   1.116 +		case 2:
   1.117 +		case 6:
   1.118 +		case 10:
   1.119 +		case 14:
   1.120 +			iAverageLatency = iLatency/(8*KNumOfIterations);
   1.121 +			break;
   1.122 +		case 3:
   1.123 +		case 7:
   1.124 +		case 11:
   1.125 +		case 15:
   1.126 +			iAverageLatency = iLatency/(16*KNumOfIterations);
   1.127 +			break;
   1.128 +		case 4:
   1.129 +		case 8:
   1.130 +		case 12:
   1.131 +		case 16:
   1.132 +			iAverageLatency = iLatency/(32*KNumOfIterations);
   1.133 +			break;
   1.134 +		default:
   1.135 +			MultiPtrPerfPanic(EMultiPtrPerfPanicWrongTest);
   1.136 +		}
   1.137 +
   1.138 +	ret = iChunk.OpenGlobal(KPerformanceTimingChunk, ETrue);
   1.139 +	if (ret != KErrNone)
   1.140 +		{
   1.141 +		return ret;
   1.142 +		}
   1.143 +	TUint8* desPtr = iChunk.Base() + iChunkOffset;
   1.144 +	TPtr8 ptrDes(desPtr, iLatLenInLetters, KMaxDescLength);
   1.145 +	
   1.146 +	TBuf<66> buf;
   1.147 +	buf.Num(iAverageLatency);
   1.148 +	buf.Append(',');
   1.149 +	ptrDes.Append(buf);
   1.150 +	
   1.151 +	// reset the iLatency for next set of test
   1.152 +	iLatency = 0;	
   1.153 +	
   1.154 +	// For writing the next latency in chunk memory
   1.155 +	iLatLenInLetters = ptrDes.Length();
   1.156 +	
   1.157 +	iChunk.Close();
   1.158 +	
   1.159 +	// Before calling the thread Function close the current thread and then call the function
   1.160 +	// here when we kill the child thread it releases both mutex and condvar that it holds
   1.161 +	iPtrAppUi->ChildThread().Kill(KErrNone);
   1.162 +	iPtrAppUi->ChildThread().Close();
   1.163 +	
   1.164 +	if (iPtrAppUi->TestCaseNum() == 16)
   1.165 +		{
   1.166 +		// It it is the last test case then stop the active scheduler
   1.167 +		CActiveScheduler::Stop();
   1.168 +		return ret;
   1.169 +		}
   1.170 +	else
   1.171 +		{
   1.172 +		return iPtrAppUi->CreateEventSimulatingThreads();
   1.173 +		}
   1.174 +	}
   1.175 +
   1.176 +// This function is called by Cone whenever a event is outstanding
   1.177 +// Here we check if the sent event is same as the expected event in array.
   1.178 +// Then resumes the thread for next set of events. When all the events are completed
   1.179 +// calls CalculateLatencyAndStartThread
   1.180 +void CMultiPtrPerfTestControl::HandlePointerEventL(const TPointerEvent& aPointerEvent)
   1.181 +	{
   1.182 +    ASSERT(!iPointerEventNotSupported);
   1.183 +	// The event that is received is (0,0,0) then it is the first event that the test code is sending
   1.184 +	const TAdvancedPointerEvent* advancedPointerEvent = aPointerEvent.AdvancedPointerEvent();
   1.185 +	
   1.186 +	if (iPtrAppUi->TestCaseNum() == 0)
   1.187 +		{
   1.188 +		if (advancedPointerEvent->PointerNumber() == 0 && advancedPointerEvent->Position3D() == TPoint3D())
   1.189 +			{
   1.190 +			iPtrAppUi->CreateEventSimulatingThreads();
   1.191 +			return;
   1.192 +			}
   1.193 +		else
   1.194 +			{
   1.195 +			return;	// ignore other events before starting the tests
   1.196 +			}
   1.197 +		}
   1.198 +
   1.199 +	// Get the current time.
   1.200 +	// Subtract from the test start time.
   1.201 +	TTime currentTime;
   1.202 +	currentTime.UniversalTime();
   1.203 +	TInt64 curTime64 = currentTime.Int64();
   1.204 +	TInt timeSinceTestStart = curTime64 - iPtrAppUi->TestStartTime();
   1.205 +	
   1.206 +	// Get the event, get the time stored in Z corodinate
   1.207 +	// Then subtract the calculated time from Z coordinate
   1.208 +	iLatency += timeSinceTestStart - advancedPointerEvent->ProximityAndPressure(); 
   1.209 +	
   1.210 +	// Get the current event from buffer and compare it with got event
   1.211 +	TAdvancedPointerEvent expectedPtrEvent;
   1.212 +	if(0 == iEventBuffer.Remove(&expectedPtrEvent))
   1.213 +		{
   1.214 +		iPtrAppUi->Failed(TPoint3D(), TPoint3D(), KErrNotFound);
   1.215 +		return;
   1.216 +		}
   1.217 +	
   1.218 +	// Here Z corodinate is not checked.
   1.219 +	if (expectedPtrEvent.iPosition != advancedPointerEvent->iPosition)
   1.220 +		{
   1.221 +		iPtrAppUi->Failed(expectedPtrEvent.Position3D(), advancedPointerEvent->Position3D(), KErrNone);
   1.222 +		return;
   1.223 +		}
   1.224 +	
   1.225 +	if (expectedPtrEvent.PointerNumber() != advancedPointerEvent->PointerNumber())
   1.226 +		{
   1.227 +		iPtrAppUi->Failed(TPoint3D(), TPoint3D(), KErrNone, expectedPtrEvent.PointerNumber(), advancedPointerEvent->PointerNumber());
   1.228 +		return;
   1.229 +		}
   1.230 +	
   1.231 +	iPtrAppUi->DecrementEventCount();
   1.232 +	NumOfEventsAdded--;
   1.233 +	
   1.234 +	// Event count is zero when all the events have been tested
   1.235 +	if (iPtrAppUi->EventCount() == 0)
   1.236 +		{
   1.237 +		TInt ret = CalculateLatencyAndStartThread(); 
   1.238 +		if (ret != KErrNone)
   1.239 +			{
   1.240 +			iPtrAppUi->Failed(TPoint3D(), TPoint3D(), ret);
   1.241 +			return;
   1.242 +			}
   1.243 +		}
   1.244 +	else if (NumOfEventsAdded == 0) 
   1.245 +		{
   1.246 +		ConVar.Signal();
   1.247 +		}
   1.248 +	}
   1.249 +
   1.250 +void CMultiPtrPerfTestControl::AddExpectedEvent(TAdvancedPointerEvent& aExpEvent)
   1.251 +	{
   1.252 +	iEventBuffer.Add(&aExpEvent);
   1.253 +	}
   1.254 +
   1.255 +CMultiPtrPerfTestControl::~CMultiPtrPerfTestControl()
   1.256 +	{
   1.257 +	iChunk.Close();
   1.258 +	}
   1.259 +
   1.260 +void CMultiPtrPerfTestControl::ConstructL()
   1.261 +	{
   1.262 +    iPointerEventNotSupported = EFalse;
   1.263 +	ConstructL(TPoint(), ControlEnv()->ScreenDevice()->SizeInPixels());
   1.264 +	}
   1.265 +
   1.266 +void CMultiPtrPerfTestControl::ConstructL(TPoint aOrigin, TSize aSize)
   1.267 +	{
   1.268 +    iEventBuffer.SetLengthL(EEventBufferSize);
   1.269 +    
   1.270 +    iPtrAppUi = static_cast<CMultiPtrPerfTestAppUi*>(ControlEnv()->AppUi());
   1.271 +        
   1.272 +    CreateWindowL();
   1.273 +    Window().EnableAdvancedPointers();
   1.274 +    EnableDragEvents();
   1.275 +    SetExtent(aOrigin, aSize);
   1.276 +    ActivateL();
   1.277 +    
   1.278 + 	// Get the cmdline argument of this process in descriptor
   1.279 + 	// convert the descriptor to number and store it in iChunkOffset
   1.280 + 	TBuf<128> buf;
   1.281 + 	User::CommandLine(buf);
   1.282 + 	TLex lex(buf);
   1.283 + 	User::LeaveIfError(lex.Val(iChunkOffset));
   1.284 +	}
   1.285 +
   1.286 +// This function gets the current time and subtracts it from the time when the whole test was started.
   1.287 +// Simulates the event and suspends the thread if aWaitAfterEachEvent is ETrue
   1.288 +// If aWaitAfterEachEvent is EFalse then it suspends the thread after each set of event i,e after 4, 8, 16 and 32 events 
   1.289 +void SimulatePointerEvents(TInt aCount, CMultiPtrPerfTestAppUi* appUi, TBool aMultiPtrEvent = EFalse, TBool aWaitAfterEachEvent = ETrue)
   1.290 +	{
   1.291 +	TRawEvent rawEvent;
   1.292 +	TPoint ptrPos;
   1.293 +	TTime currentTime;
   1.294 +	TInt64 testStartTime = appUi->TestStartTime();
   1.295 +	TInt ptrNum = 0;
   1.296 +	TInt ptrMax = 0;
   1.297 +	// HAL as already been tested at the start of these tests. So no need to test once again
   1.298 +	HAL::Get(HALData::EPointerNumberOfPointers, ptrMax);
   1.299 +	
   1.300 +	appUi->SetNumberOfEvents((KNumOfIterations*aCount)-1);
   1.301 +
   1.302 +	// For testing time taken for each event and for each set of events we make use of RMutex and RConvar.
   1.303 +	// RMutex is used not to preempt this thread until events has been added
   1.304 +	// RConVar is used to hold this thread until the events have been tested
   1.305 +	for (TInt loop = 0; loop < KNumOfIterations; loop++)
   1.306 +		{
   1.307 +		ptrNum = 0;
   1.308 +		ptrPos.iX = ptrPos.iY = 0;
   1.309 +		Mutex.Wait();
   1.310 +		for (TInt count = 0; count < aCount/2; count++, ptrNum++)
   1.311 +			{
   1.312 +			if (ptrNum >= ptrMax)
   1.313 +				{
   1.314 +				ptrNum = 0;
   1.315 +				}			
   1.316 +			ptrPos.iX += 2;
   1.317 +			ptrPos.iY += 1;
   1.318 +			
   1.319 +			TWsEvent event;
   1.320 +			event.InitAdvancedPointerEvent(TPointerEvent::EButton1Down, 0, TPoint3D(ptrPos.iX, ptrPos.iY, 0), (aMultiPtrEvent ? ptrNum : 0));
   1.321 +			appUi->AddExpectedEvent(*event.Pointer());
   1.322 +			currentTime.UniversalTime();
   1.323 +			TInt64 curTime64 = currentTime.Int64();
   1.324 +			TInt timeSinceTestStart = curTime64 - testStartTime;
   1.325 +			rawEvent.Set(TRawEvent::EButton1Down, ptrPos.iX, ptrPos.iY, timeSinceTestStart, (aMultiPtrEvent ? ptrNum : 0));
   1.326 +			UserSvr::AddEvent(rawEvent);
   1.327 +			NumOfEventsAdded++;
   1.328 +			if (aWaitAfterEachEvent)
   1.329 +				{
   1.330 +				while(NumOfEventsAdded)
   1.331 +					ConVar.Wait(Mutex);
   1.332 +				}
   1.333 +			
   1.334 +			event.InitAdvancedPointerEvent(TPointerEvent::EButton1Up, 0, TPoint3D(ptrPos.iX, ptrPos.iY, 0), (aMultiPtrEvent ? ptrNum : 0));
   1.335 +			appUi->AddExpectedEvent(*event.Pointer());
   1.336 +			currentTime.UniversalTime();
   1.337 +			curTime64 = currentTime.Int64();
   1.338 +			timeSinceTestStart = curTime64 - testStartTime;
   1.339 +			rawEvent.Set(TRawEvent::EButton1Up, ptrPos.iX, ptrPos.iY, timeSinceTestStart, (aMultiPtrEvent ? ptrNum : 0));
   1.340 +			UserSvr::AddEvent(rawEvent);
   1.341 +			NumOfEventsAdded++;
   1.342 +			if (aWaitAfterEachEvent)
   1.343 +				{
   1.344 +				while(NumOfEventsAdded)
   1.345 +					ConVar.Wait(Mutex);
   1.346 +				}
   1.347 +			}
   1.348 +		if (!aWaitAfterEachEvent)
   1.349 +			{
   1.350 +			while(NumOfEventsAdded)
   1.351 +				ConVar.Wait(Mutex);
   1.352 +			}
   1.353 +		Mutex.Signal();
   1.354 +		}
   1.355 +	}
   1.356 +
   1.357 +TInt EventSimulatingThreadStartFunc(TAny* aAny)
   1.358 +	{
   1.359 +	CMultiPtrPerfTestAppUi* appUi = static_cast<CMultiPtrPerfTestAppUi*>(aAny);
   1.360 +
   1.361 +	switch(appUi->TestCaseNum()++)
   1.362 +		{
   1.363 +		case 0:
   1.364 +			SimulatePointerEvents(4, appUi);
   1.365 +			break;
   1.366 +		case 1:
   1.367 +			SimulatePointerEvents(8, appUi);
   1.368 +			break;
   1.369 +		case 2:
   1.370 +			SimulatePointerEvents(16, appUi);
   1.371 +			break;
   1.372 +		case 3:
   1.373 +			SimulatePointerEvents(32, appUi);
   1.374 +			break;
   1.375 +		case 4:
   1.376 +			SimulatePointerEvents(4, appUi, ETrue);
   1.377 +			break;
   1.378 +		case 5:
   1.379 +			SimulatePointerEvents(8, appUi, ETrue);
   1.380 +			break;
   1.381 +		case 6:
   1.382 +			SimulatePointerEvents(16, appUi, ETrue);
   1.383 +			break;
   1.384 +		case 7:
   1.385 +			SimulatePointerEvents(32, appUi, ETrue);
   1.386 +			break;
   1.387 +		case 8:
   1.388 +			SimulatePointerEvents(4, appUi, EFalse, EFalse);
   1.389 +			break;
   1.390 +		case 9:
   1.391 +			SimulatePointerEvents(8, appUi, EFalse, EFalse);
   1.392 +			break;
   1.393 +		case 10:
   1.394 +			SimulatePointerEvents(16, appUi, EFalse, EFalse);
   1.395 +			break;
   1.396 +		case 11:
   1.397 +			SimulatePointerEvents(32, appUi, EFalse, EFalse);
   1.398 +			break;
   1.399 +		case 12:
   1.400 +			SimulatePointerEvents(4, appUi, ETrue, EFalse);
   1.401 +			break;
   1.402 +		case 13:
   1.403 +			SimulatePointerEvents(8, appUi, ETrue, EFalse);
   1.404 +			break;
   1.405 +		case 14:
   1.406 +			SimulatePointerEvents(16, appUi, ETrue, EFalse);
   1.407 +			break;
   1.408 +		case 15:
   1.409 +			SimulatePointerEvents(32, appUi, ETrue, EFalse);
   1.410 +			break;		
   1.411 +		default:
   1.412 +			break;
   1.413 +		}
   1.414 +	return KErrNone;
   1.415 +	}
   1.416 +
   1.417 +TInt CMultiPtrPerfTestAppUi::CreateEventSimulatingThreads()
   1.418 +	{
   1.419 +	// Depending upon the iTestCase number create thread and simulate events in that thread function
   1.420 +	TInt ret = KErrNone;
   1.421 +	_LIT(KSimulateEventsThread, "Events simulating thread");
   1.422 +	ret = iThread.Create(KSimulateEventsThread, EventSimulatingThreadStartFunc, KDefaultStackSize, 0x4000, 0x4000, this, EOwnerThread);
   1.423 +	if (ret == KErrNone)
   1.424 +		{
   1.425 +		iThread.Resume();
   1.426 +		}
   1.427 +	return ret;
   1.428 +	}
   1.429 +
   1.430 +void CMultiPtrPerfTestAppUi::AddExpectedEvent(TAdvancedPointerEvent& aExpEvent)
   1.431 +	{
   1.432 +	iControl->AddExpectedEvent(aExpEvent);
   1.433 +	}
   1.434 +
   1.435 +void CMultiPtrPerfTestAppUi::Failed(TPoint3D aExp3DPoint, TPoint3D aActual3DPoint, TInt aErrorCode, TInt aExpPtrNum, TInt aActPtrNum)
   1.436 +	{
   1.437 +	// Write error description in the memory of shared chunk 
   1.438 +	// so that the main performance test just stops by saying that it failed
   1.439 +	// and then stop the active scheduler.
   1.440 +	iControl->Failed(aExp3DPoint, aActual3DPoint, aErrorCode, aExpPtrNum, aActPtrNum);
   1.441 +	CActiveScheduler::Stop();
   1.442 +	}
   1.443 +
   1.444 +void CMultiPtrPerfTestAppUi::PointerEventsNotSupported()
   1.445 +    {
   1.446 +    // Write a pointer events not supported message in the memory of shared chunk 
   1.447 +    // so that the main performance test just skips the pointer test
   1.448 +    iControl->PointerEventsNotSupported();
   1.449 +    }
   1.450 +
   1.451 +CMultiPtrPerfTestAppUi::CMultiPtrPerfTestAppUi()
   1.452 +	{
   1.453 +	}
   1.454 +
   1.455 +CMultiPtrPerfTestAppUi::~CMultiPtrPerfTestAppUi()
   1.456 +	{
   1.457 +	RemoveFromStack(iControl);
   1.458 +	delete iControl;
   1.459 +	}
   1.460 +
   1.461 +void CMultiPtrPerfTestAppUi::ConstructL()
   1.462 +	{
   1.463 +	CCoeAppUi::ConstructL();
   1.464 +	
   1.465 +	TTime testStartTime;
   1.466 +	testStartTime.UniversalTime();
   1.467 +	iTestStartTime = testStartTime.Int64();
   1.468 +	
   1.469 +	iControl = new (ELeave) CMultiPtrPerfTestControl();
   1.470 +	iControl->ConstructL();
   1.471 +	AddToStackL(iControl);
   1.472 +	}
   1.473 +
   1.474 +void ConstructControlEnvironmentL(CCoeEnv* aCoe)
   1.475 +	{
   1.476 + 	aCoe->ConstructL();
   1.477 + 	CMultiPtrPerfTestAppUi* appUi=new(ELeave) CMultiPtrPerfTestAppUi();
   1.478 + 	CleanupStack::PushL(appUi);			// If it leaves after this then there is no way of deleting the appui
   1.479 + 	aCoe->SetAppUi(appUi);				// So pushed it on to cleanup stack
   1.480 + 	aCoe->WsSession().SetAutoFlush(ETrue);
   1.481 + 	appUi->ConstructL();
   1.482 + 	User::LeaveIfError(Mutex.CreateLocal(EOwnerProcess));
   1.483 + 	User::LeaveIfError(ConVar.CreateLocal(EOwnerProcess));
   1.484 + 	CleanupStack::Pop(appUi);
   1.485 +	}
   1.486 +
   1.487 +GLDEF_C TInt E32Main()
   1.488 +	{
   1.489 +	__UHEAP_MARK;
   1.490 +	CCoeEnv* coe = new CCoeEnv;
   1.491 +	if (!coe)
   1.492 +		{
   1.493 +		return KErrNoMemory; 
   1.494 +		}
   1.495 +	TRAPD(err, ConstructControlEnvironmentL(coe));
   1.496 +	if (err != KErrNone)
   1.497 +		{
   1.498 +		delete coe;
   1.499 +		}
   1.500 +	else	// If KErrNone then no need to delte coe as it is taken care by ConEnv
   1.501 +		{
   1.502 +        // Check whether the configuration supports pointer events.
   1.503 +        // If it dosn't support pointer events then the pointer cursor area will be empty,
   1.504 +        // in this case skip the test and inform the test framework that the test has been skipped
   1.505 +        TRect pointerCursorArea = coe->WsSession().PointerCursorArea();
   1.506 +        if(pointerCursorArea.IsEmpty())
   1.507 +            {
   1.508 +            RDebug::Printf("PointerCursorArea is Empty");
   1.509 +            CMultiPtrPerfTestAppUi* appUi = static_cast<CMultiPtrPerfTestAppUi*>(coe->AppUi());
   1.510 +            appUi->PointerEventsNotSupported();
   1.511 +            }
   1.512 +        else
   1.513 +            {
   1.514 +            // First event which starts the test from HandlePointerEventL
   1.515 +            TRawEvent rawEvent;
   1.516 +            rawEvent.Set(TRawEvent::EButton1Down, 0, 0, 0, 0);
   1.517 +            UserSvr::AddEvent(rawEvent);
   1.518 +            coe->ExecuteD();
   1.519 +            }
   1.520 +		Mutex.Close();
   1.521 +		ConVar.Close();
   1.522 +	 	}
   1.523 +	
   1.524 +	__UHEAP_MARKEND;
   1.525 +	return err;
   1.526 +	}