--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/kerneltest/e32test/secure/t_platsecconfig.cpp Mon Oct 19 15:55:17 2009 +0100
@@ -0,0 +1,486 @@
+// Copyright (c) 2001-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\secure\t_platsecconfig.cpp
+// This test checks the correct functioning of the Platform Security configuration.
+// To use this test for verification of the features, perform the following steps
+// On the WINS Emulator
+// 1. Run "T_PLATSECCONFIG.EXE"
+// Check that the results reported are:
+// PlatSecEnforcement is OFF
+// Disabled Capabilites: NONE
+// Check EPOCWIND.OUT and verify that it contains no diagnostic messages. (These will start with the text "*PlatSec* ")
+// 2. Run "T_PLATSECCONFIG.EXE -mt_platsecconfig --"
+// Check that the results reported are:
+// PlatSecEnforcement is ON
+// Disabled Capabilites: CommDD MultimediaDD WriteDeviceData TrustedUI DiskAdmin AllFiles NetworkServices ReadUserData Location (These are all ODD numbered capabilities)
+// Check EPOCWIND.OUT and verify that it contains two lines starting with "*PlatSec* ERROR - Capability check failed"
+// On reference hardware
+// 3. Build a Text Shell ROM contining the E32 tests. E.g.
+// cd \cedar\generic\base\e32\rombuild
+// rom -v=lubbock -t=e32test
+// Boot this ROM and run "T_PLATSECCONFIG.EXE"
+// Check that the results reported are:
+// PlatSecEnforcement is OFF
+// Disabled Capabilites: NONE
+// Check the output of the debug port and verify that it contains no diagnostic messages.
+// (These will start with the text "*PlatSec* ")
+// 4. Build a Text Shell ROM using the T_PLATSECCONFIG.OBY file. E.g.
+// cd \cedar\generic\base\e32\rombuild
+// rom -v=lubbock -t=t_platsecconfig
+// Boot this ROM and run "T_PLATSECCONFIG.EXE"
+// Check that the results reported are:
+// PlatSecEnforcement is ON
+// Disabled Capabilites: CommDD MultimediaDD WriteDeviceData TrustedUI DiskAdmin AllFiles NetworkServices ReadUserData Location (These are all ODD numbered capabilities)
+// Check the output of the debug port and verify that it contains two lines with "*PlatSec* ERROR - Capability check failed"
+// To check ROMBUILD configuration
+// 5. Build a Text Shell ROM using the T_PLATSECCONFIG_WARNIG.OBY file. E.g.
+// cd \cedar\generic\base\e32\rombuild
+// rom -v=lubbock -t=t_platsecconfig_warning
+// This should produce the following warning:
+// WARNING: *PlatSec* WARNING - Capability check failed. Can't load \Epoc32\RELEASE\ARM4\UDEB\t_psc_static.exebecause it links to t_psc_dll{00010000}.dll which has the following capabilities missing: TCB PowerMgmt ReadDeviceData DRM ProtServ NetworkControl SwEvent LocalServices WriteUserData
+// 6. Build a Text Shell ROM using the T_PLATSECCONFIG_ERROR.OBY file. E.g.
+// cd \cedar\generic\base\e32\rombuild
+// rom -v=lubbock -t=t_platsecconfig_error
+// This should produce the following error:
+// ERROR: *PlatSec* ERROR - Capability check failed. Can't load \Epoc32\RELEASE\ARM4\UDEB\t_psc_static.exe because it links to t_psc_dll{00010000}.dll which has the following capabilities missing: TCB PowerMgmt ReadDeviceData DRM ProtServ NetworkControl SwEvent LocalServices WriteUserData
+//
+//
+
+/**
+ @file
+*/
+
+#define __INCLUDE_CAPABILITY_NAMES__
+
+#include <e32test.h>
+
+LOCAL_D RTest test(_L("T_PLATSECCONFIG"));
+
+enum TTestProcessFunctions
+ {
+ ETestProcessServer,
+ ETestProcessLoadLib,
+ };
+
+#include "testprocess.h"
+
+TInt StartServer();
+
+TInt DoTestProcess(TInt aTestNum,TInt aArg1,TInt aArg2)
+ {
+ (void)aArg1;
+ (void)aArg2;
+
+ switch(aTestNum)
+ {
+
+ case ETestProcessServer:
+ return StartServer();
+
+ case ETestProcessLoadLib:
+ {
+ RLibrary lib;
+ TInt r = lib.Load(_L("T_PSC_DLL"));
+ lib.Close();
+ return r;
+ }
+
+ default:
+ User::Panic(_L("T_PLATSECCONFIG"),1);
+ }
+
+ return KErrNone;
+ }
+
+
+
+//
+// RTestThread
+//
+
+class RTestThread : public RThread
+ {
+public:
+ void Create(TThreadFunction aFunction,TAny* aArg=0);
+ };
+
+void RTestThread::Create(TThreadFunction aFunction,TAny* aArg)
+ {
+ TInt r=RThread::Create(_L(""),aFunction,KDefaultStackSize,KDefaultStackSize,KDefaultStackSize,aArg);
+ test(r==KErrNone);
+ }
+
+
+//
+// CTestSession
+//
+
+class CTestSession : public CSession2
+ {
+public:
+ enum {EShutdown,EGetSecurityInfo};
+public:
+ CTestSession();
+ virtual void ServiceL(const RMessage2& aMessage);
+public:
+ };
+
+CTestSession::CTestSession()
+ : CSession2()
+ {}
+
+void CTestSession::ServiceL(const RMessage2& aMessage)
+ {
+ RMessagePtr2 m(aMessage);
+ switch (aMessage.Function())
+ {
+ case CTestSession::EGetSecurityInfo:
+ {
+ TSecurityInfo info;
+ info.Set(RProcess());
+ TInt r = aMessage.Write(0,TPtrC8((TUint8*)&info,sizeof(info)));
+ m.Complete(r);
+ }
+ break;
+
+ case CTestSession::EShutdown:
+ CActiveScheduler::Stop();
+ break;
+
+ default:
+ m.Complete(KErrNotSupported);
+ break;
+ }
+ }
+
+
+
+//
+// CTestServer
+//
+
+class CTestServer : public CServer2
+ {
+public:
+ CTestServer(TInt aPriority);
+ virtual CSession2* NewSessionL(const TVersion& aVersion,const RMessage2& aMessage) const;
+ };
+
+CTestServer::CTestServer(TInt aPriority)
+ : CServer2(aPriority)
+ {
+ }
+
+CSession2* CTestServer::NewSessionL(const TVersion& /*aVersion*/,const RMessage2& /*aMessage*/) const
+ {
+ return new (ELeave) CTestSession();
+ }
+
+
+
+//
+// CTestActiveScheduler
+//
+
+class CTestActiveScheduler : public CActiveScheduler
+ {
+public:
+ virtual void Error(TInt anError) const;
+ };
+
+void CTestActiveScheduler::Error(TInt anError) const
+ {
+ User::Panic(_L("TestServer Error"),anError);
+ }
+
+
+
+//
+// Server thread
+//
+
+_LIT(KServerName,"T_PLATSECCONFIG-server");
+const TInt KServerRendezvous = KRequestPending+1;
+
+void DoStartServer()
+ {
+ CTestActiveScheduler* activeScheduler = new (ELeave) CTestActiveScheduler;
+ CActiveScheduler::Install(activeScheduler);
+ CleanupStack::PushL(activeScheduler);
+
+ CTestServer* server = new (ELeave) CTestServer(0);
+ CleanupStack::PushL(server);
+
+ User::LeaveIfError(server->Start(KServerName));
+
+ RProcess::Rendezvous(KServerRendezvous);
+
+ CActiveScheduler::Start();
+
+ CleanupStack::PopAndDestroy(2);
+ }
+
+TInt StartServer()
+ {
+ CTrapCleanup* cleanupStack = CTrapCleanup::New();
+ if(!cleanupStack)
+ return KErrNoMemory;
+ TRAPD(leaveError,DoStartServer())
+ delete cleanupStack;
+ return leaveError;
+ }
+
+
+
+//
+// RTestSession
+//
+
+class RTestSession : public RSessionBase
+ {
+public:
+ inline TInt Connect()
+ { return CreateSession(KServerName,TVersion());}
+ inline TInt Send(TInt aFunction)
+ { return RSessionBase::SendReceive(aFunction); }
+ inline TInt Send(TInt aFunction,const TIpcArgs& aArgs)
+ { return RSessionBase::SendReceive(aFunction,aArgs); }
+ inline void Send(TInt aFunction,TRequestStatus& aStatus)
+ { RSessionBase::SendReceive(aFunction,aStatus); }
+ inline void Send(TInt aFunction,const TIpcArgs& aArgs,TRequestStatus& aStatus)
+ { RSessionBase::SendReceive(aFunction,aArgs,aStatus); }
+ };
+
+
+
+RTestSession Session;
+
+
+
+void CheckCapabilitySetEqual(const TCapabilitySet& a1,const TCapabilitySet& a2)
+ {
+ TInt i;
+ for(i=0; i<ECapability_Limit; i++)
+ test((!a1.HasCapability((TCapability)i))==(!a2.HasCapability((TCapability)i)));
+ }
+
+TBuf8<1024> CapabilityNameBuffer;
+TBool PlatSecEnforcement=0;
+
+TPtrC16 CapabilityList(const TCapabilitySet& aCaps)
+ {
+ TCapabilitySet allCaps;
+ allCaps.SetAllSupported();
+ CapabilityNameBuffer.Zero();
+ TBool odd=ETrue;
+ TBool even=ETrue;
+ TInt i;
+ for(i=0; i<ECapability_Limit; i++)
+ {
+ if(!aCaps.HasCapability((TCapability)i))
+ {
+ if(allCaps.HasCapability((TCapability)i))
+ {
+ if(i&1)
+ odd = EFalse;
+ else
+ even = EFalse;
+ }
+ continue;
+ }
+ TUint8* ptr=(TUint8*)CapabilityNames[i];
+ TPtrC8 name(ptr,User::StringLength(ptr));
+ CapabilityNameBuffer.Append(name);
+ CapabilityNameBuffer.Append((TChar)' ');
+ }
+ if(!CapabilityNameBuffer.Length())
+ CapabilityNameBuffer.Append(_L8("NONE"));
+ if(even)
+ CapabilityNameBuffer.Append(_L8("(These are all EVEN numbered capabilities)"));
+ if(odd)
+ CapabilityNameBuffer.Append(_L8("(These are all ODD numbered capabilities)"));
+ return CapabilityNameBuffer.Expand();
+}
+
+void TestPlatSecDisabledCaps()
+ {
+ TSecurityInfo info;
+ TPckg<TSecurityInfo> infoPtr(info);
+
+ test.Start(_L("Get disabled capabilities set"));
+ TCapabilitySet disabled;
+ disabled.SetDisabled();
+ TPtrC16 list(CapabilityList(disabled));
+ test.Printf(_L(" %S\n"),&list);
+
+ test.Next(_L("Get capabilites from this EXE"));
+ Mem::FillZ(&info,sizeof(info));
+ info.SetToCurrentInfo();
+
+ test.Next(_L("Check capabilities are same as disabled set"));
+ CheckCapabilitySetEqual(info.iCaps,disabled);
+
+ test.Next(_L("Get capabilites from other EXE"));
+ Mem::FillZ(&info,sizeof(info));
+ TInt r = Session.Send(CTestSession::EGetSecurityInfo,TIpcArgs(&infoPtr));
+ test(r==KErrNone);
+
+ test.Next(_L("Check capabilities are same as disabled set"));
+ CheckCapabilitySetEqual(info.iCaps,disabled);
+
+ test.Next(_L("Test PlatSec::IsCapabilityEnforced is consistant with our findings"));
+ TCapabilitySet notEnforced;
+ notEnforced.SetEmpty();
+ for(TInt i=0; i<ECapability_HardLimit; i++)
+ if(!PlatSec::IsCapabilityEnforced((TCapability)i))
+ notEnforced.AddCapability((TCapability)i);
+ if(!PlatSec::ConfigSetting(PlatSec::EPlatSecEnforcement))
+ disabled.SetAllSupported();
+ CheckCapabilitySetEqual(notEnforced,disabled);
+
+ test.End();
+ }
+
+_LIT(KRomExe,"T_PLATSECCONFIG2.EXE");
+_LIT(KOn,"ON");
+_LIT(KOff,"OFF");
+
+void TestPlatSecEnforcement()
+ {
+ RProcess process;
+ TInt r;
+
+ test.Start(_L("Getting PlatSecEnforcement setting"));
+ PlatSecEnforcement = PlatSec::ConfigSetting(PlatSec::EPlatSecEnforcement);
+ test.Printf(_L(" PlatSecEnforcement setting returns %S\n"),PlatSecEnforcement?&KOn:&KOff);
+
+ test.Next(_L("Check dynamic linkage without required capabilities"));
+ TBuf<10> arg;
+ arg.Num((TInt)ETestProcessLoadLib);
+ r=process.Create(_L("T_PSC_DYNAMIC"),arg);
+ test(r==KErrNone);
+ TRequestStatus logon;
+ process.Logon(logon);
+ process.Resume();
+ User::WaitForRequest(logon);
+ test(process.ExitType()==EExitKill);
+ r=logon.Int();
+ CLOSE_AND_WAIT(process);
+ if(PlatSecEnforcement)
+ test(r==KErrPermissionDenied);
+ else
+ test(r==KErrNone);
+
+ test.Next(_L("Check static linkage without required capabilities"));
+ r=process.Create(_L("T_PSC_STATIC"),_L(""));
+ if(PlatSecEnforcement)
+ test(r==KErrPermissionDenied);
+ else
+ {
+ test(r==KErrNone);
+ process.Kill(0);
+ CLOSE_AND_WAIT(process);
+ }
+
+ test.End();
+ }
+
+#include <e32svr.h>
+IMPORT_C void dummyExport();
+
+GLDEF_C TInt E32Main()
+ {
+#ifdef STATIC_TEST_LINK
+ dummyExport(); // Use dummy export from staticly linked DLL
+#endif
+ TBuf16<512> cmd;
+ User::CommandLine(cmd);
+ if(cmd.Length() && TChar(cmd[0]).IsDigit())
+ {
+ TInt function = -1;
+ TInt arg1 = -1;
+ TInt arg2 = -1;
+ TLex lex(cmd);
+
+ lex.Val(function);
+ lex.SkipSpace();
+ lex.Val(arg1);
+ lex.SkipSpace();
+ lex.Val(arg2);
+ return DoTestProcess(function,arg1,arg2);
+ }
+
+ test.Title();
+
+ test.Start(_L("Starting test server"));
+ RTestProcess server;
+ TRequestStatus rendezvous;
+ TBuf<10> arg;
+ arg.Num((TInt)ETestProcessServer);
+ TInt r=server.RProcess::Create(KRomExe,arg);
+ test(r==KErrNone);
+ server.Rendezvous(rendezvous);
+ server.Resume();
+ User::WaitForRequest(rendezvous);
+ test(rendezvous==KServerRendezvous);
+
+ test.Next(_L("Openning server session"));
+ r = Session.Connect();
+ RDebug::Print(_L("%d"),r);
+ test(r==KErrNone);
+
+ test.Next(_L("Test PlatSecDisabledCaps"));
+ TestPlatSecDisabledCaps();
+
+ test.Next(_L("Test PlatSecEnforcement"));
+ TestPlatSecEnforcement();
+
+ test.Next(_L("Closing server session"));
+ Session.Send(CTestSession::EShutdown);
+ Session.Close();
+ CLOSE_AND_WAIT(server);
+
+ // Show results requiring manual inspection
+ _LIT(KSeperatorText,"----------------------------------------------------------------------------\n");
+ test.Printf(_L("\n"));
+ test.Printf(_L("RESULTS (To be checked against expected values)\n"));
+ test.Printf(KSeperatorText);
+ test.Printf(_L("* PlatSecEnforcement is %S\n"),PlatSecEnforcement?&KOn:&KOff);
+ test.Printf(KSeperatorText);
+ TCapabilitySet disabled;
+ disabled.SetDisabled();
+ TPtrC16 list(CapabilityList(disabled));
+ test.Printf(_L("* Disabled Capabilites: %S\n"),&list);
+ test.Printf(KSeperatorText);
+
+ // Wait for a while, or for a key press
+ test.Printf(_L("Waiting a short while for key press...\n"));
+ TRequestStatus keyStat;
+ test.Console()->Read(keyStat);
+ RTimer timer;
+ test(timer.CreateLocal()==KErrNone);
+ TRequestStatus timerStat;
+ timer.After(timerStat,20*1000000);
+ User::WaitForRequest(timerStat,keyStat);
+ TInt key = 0;
+ if(keyStat!=KRequestPending)
+ key = test.Console()->KeyCode();
+ timer.Cancel();
+ test.Console()->ReadCancel();
+ User::WaitForAnyRequest();
+
+ test.End();
+ return(0);
+ }
+