diff -r 4a8fed1c0ef6 -r 597aaf25e343 kerneltest/e32test/random/t_entropysources.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/kerneltest/e32test/random/t_entropysources.cpp Fri Mar 12 15:50:11 2010 +0200 @@ -0,0 +1,131 @@ +// Copyright (c) 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: +// Test suite to check whether the device has good enough entropy sources or not. +// More the no. of sources, high the quality of the random numbers (least predictable). +// +// + +/** + @file + @internalTechnology +*/ + +#define __E32TEST_EXTENSION__ +#include +#include +#include +#include "d_entropysources.h" + +//--------------------------------------------------------------------------------------------------------------------- +//! @SYMTestCaseID KBASE-entropysources-2703 +//! @SYMTestType UT +//! @SYMTestCaseDesc Verifies that entropy is contributed to the Secure RNG +//! @SYMPREQ PREQ211 +//! @SYMTestPriority High +//! @SYMTestActions +//! 1. TestReseed: tests that the interval between RNG reseeds is less than KMaxReseedTime, unless the platform is +//! known not to have a viable entropy source. +//! +//! +//! @SYMTestExpectedResults +//! 1. Properties checked: +//! 1) checks that there is a valid entropy source contrbuting entropy data. +//! 2) checks that the entropy collection framework is functioning correctly.. +//! +//--------------------------------------------------------------------------------------------------------------------- + +// In a worst case scenario, we expect the reseed to happen within ten minutes. +// This is approximately 1/10 of the actual reseed intervel time (97.8 rounded to => 98). +// ((2^24 (reseed intervel) * 350 (micro seconds per request)) / 1000000) / 60 => 97.8 minutes. +// +const TTimeIntervalMicroSeconds32 KMaxReseedTime = 10 * 60 * 1000000; + +REntropySources Ldd; + +LOCAL_D RTest test(_L("T_ENTROPYSOURCES")); + +LOCAL_C void TestReseed() + { + test.Next(_L("Loading test driver")); + TInt r = User::LoadLogicalDevice(KEntropySourcesName); + test(r==KErrNone || r==KErrAlreadyExists); + + test.Next(_L("Opening the logical channel")); + test_KErrNone(Ldd.Open()); + + RTimer timer; + test_KErrNone(timer.CreateLocal()); + + test.Next(_L("Testing reseed interval")); + // Wait for two reseeds, so we can prove the interval between them is ok + for (TInt i=0; i<2; ++i) + { + // Request notification of the next reseed, with a timeout + test.Next(_L("Requesting reseed notification")); + TRequestStatus reseed, timeout; + Ldd.ReseedTest(reseed); + timer.After(timeout, KMaxReseedTime); + + // Prod the RNG to make sure it's not idle, then wait for an event + test.Next(_L("Prod RNG and wait")); + Math::Random(); + User::WaitForRequest(reseed, timeout); + + // Check we didn't time out and cancel the timer + test_Equal(KRequestPending, timeout.Int()); + timer.Cancel(); + User::WaitForRequest(timeout); + test_Equal(KErrCancel, timeout.Int()); + test_KErrNone(reseed.Int()); + } + + Ldd.Close(); + + User::FreeLogicalDevice(KEntropySourcesName); + } + +LOCAL_C TBool HardwareRNGPresent() + { + TInt muid = 0; + const TInt r = HAL::Get(HAL::EMachineUid, muid); + if (r != KErrNone) return EFalse;; + return ((muid != HAL::EMachineUid_X86PC) && + (muid != HAL::EMachineUid_NE1_TB) && + (muid != HAL::EMachineUid_OmapH6) && + (muid != HAL::EMachineUid_OmapZoom) && + (muid != HAL::EMachineUid_Win32Emulator)); + } + +GLDEF_C TInt E32Main() + { + test.Title(); + test.Start(_L("Test periodic entropy source")); + + if(HardwareRNGPresent()) + { + __UHEAP_MARK; + + TestReseed(); + + __UHEAP_MARKEND; + } + else + { + test.Printf(_L("Test skipped, platform is known not to have a periodic entropy source\n")); + } + test.End(); + test.Close(); + + return 0; + }