diff -r a179b74831c9 -r c1f20ce4abcf kerneltest/e32test/misc/ccthrash.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/kerneltest/e32test/misc/ccthrash.cpp Tue Aug 31 16:34:26 2010 +0300 @@ -0,0 +1,217 @@ +// Copyright (c) 2009-2009 Nokia Corporation and/or its subsidiary(-ies). +// All rights reserved. +// This component and the accompanying materials are made available +// under the terms of the License "Eclipse Public License v1.0" +// which accompanies this distribution, and is available +// at the URL "http://www.eclipse.org/legal/epl-v10.html". +// +// Initial Contributors: +// Nokia Corporation - initial contribution. +// +// Contributors: +// +// Description: +// e32test\misc\ccthrash.cpp +// +// + +#define __E32TEST_EXTENSION__ + +#include +#include +#include +#include +#include "u32std.h" +#include "prbs.h" + +RTest test(_L("Core Control Thrasher")); + +TInt NumberOfCpus() + { + TInt r = UserSvr::HalFunction(EHalGroupKernel, EKernelHalNumLogicalCpus, 0, 0); + test(r>0); + return r; + } + +const TInt NCPU = NumberOfCpus(); +volatile TInt STFU = 1; + +TInt NumberOfActiveCpus(TInt* a) + { + SCpuStates s; + TInt r = UserSvr::HalFunction(EHalGroupKernel, EKernelHalCpuStates, &s, 0); + test_KErrNone(r); + TUint32 ta = s.iTA; + TUint32 ia = s.iIA; + if (a) + *a = __e32_bit_count_32(ta); + return __e32_bit_count_32(ia); + } + +TInt StableState() + { + SCpuStates s; + TInt r = UserSvr::HalFunction(EHalGroupKernel, EKernelHalCpuStates, &s, 0); + test_KErrNone(r); + if (s.iCU || s.iDC) + return KErrNotReady; + if (s.iTA != s.iIA) + return KErrNotReady; + if (s.iGD & s.iIA) + return KErrNotReady; + TInt i; + for (i=0; iConstruct(); + if (r!=KErrNone) + { + delete p; + return 0; + } + return p; + } + +TInt CThrasher::ChangeNumberOfCores(TInt aNum, TInt* aCores) + { + TUint32 initial = User::NTickCount(); + TUint32 final = initial; + TUint32 elapsed = 0; + TInt n = -1; + TInt r = UserSvr::HalFunction(EHalGroupKernel, EKernelHalSetNumberOfCpus, (TAny*)aNum, 0); + test_KErrNone(r); + FOREVER + { + n = StableState(); + final = User::NTickCount(); + elapsed = final - initial; + if (n<0 || elapsed=0) + return elapsed; + return KErrTimedOut; + } + +void CThrasher::Run() + { + TUint x = Random(iSeed); + x %= iPeriod; + x += 1; + x *= 1000; + User::AfterHighRes(x); + TUint y = Random(iSeed); + y %= TUint(NCPU); + y += 1; + TInt n = 0; + TInt t = ChangeNumberOfCores(y, &n); + if (t < 0) + { + ++iTimeouts; + iTotalTime += TUint64(iTimeoutPeriod); + } + else + { + iTotalTime += TUint64(t); + if (TUint(n) != y) + ++iDiff; + } + ++iRunCount; + TUint32 now = User::NTickCount(); + TUint32 elapsed = now - iLastDisplay; + if (elapsed >= iDisplayPeriod) + { + iLastDisplay = now; + Display(); + } + } + +void CThrasher::Display() + { + TUint64 avg = iTotalTime; + avg *= TUint64(100); + avg += TUint64(50); + avg /= iRunCount; + TUint32 frac = TUint32(avg % TUint64(100)); + TUint32 integer = TUint32(avg / TUint64(100)); + TUint32 rc32 = (TUint32)iRunCount; + test.Printf(_L("RC:%10u AVG:%10u.%02u TO:%10u D:%10u\n"), rc32, integer, frac, iTimeouts, iDiff); + } + +GLDEF_C TInt E32Main() + { + test.Title(); + RThread().SetPriority(EPriorityAbsoluteHigh); + + if (NCPU==1) + { + test.Printf(_L("Only works on SMP systems\n")); + return 0; + } + + CThrasher* p = CThrasher::New(); + test_NotNull(p); + while(STFU) + { + p->Run(); + } + + + return 0; + } +