--- a/featuremgmt/featuremgr/bwins/featmgru.def Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/bwins/featmgru.def Fri Mar 12 15:51:02 2010 +0200
@@ -46,4 +46,9 @@
?DeleteFeature@RFeatureControl@@QAEHVTUid@@@Z @ 45 NONAME ; int RFeatureControl::DeleteFeature(class TUid)
?SWIEnd@RFeatureControl@@QAEHXZ @ 46 NONAME ; int RFeatureControl::SWIEnd(void)
?SWIStart@RFeatureControl@@QAEHXZ @ 47 NONAME ; int RFeatureControl::SWIStart(void)
+ ?SetHeapFailure@TFeatMgrResourceTester@@SAXHH@Z @ 48 NONAME ; void TFeatMgrResourceTester::SetHeapFailure(int, int)
+ ?Mark@TFeatMgrResourceTester@@SAXXZ @ 49 NONAME ; void TFeatMgrResourceTester::Mark(void)
+ ?Check@TFeatMgrResourceTester@@SAXXZ @ 50 NONAME ; void TFeatMgrResourceTester::Check(void)
+ ?Count@TFeatMgrResourceTester@@SAHXZ @ 51 NONAME ; int TFeatMgrResourceTester::Count(void)
+ ?GetClientCount@@YAHXZ @ 52 NONAME ; int GetClientCount(void)
--- a/featuremgmt/featuremgr/eabi/featmgru.def Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/eabi/featmgru.def Fri Mar 12 15:51:02 2010 +0200
@@ -51,5 +51,10 @@
_ZN15Dummy10Reserved16E4TUid @ 50 NONAME ABSENT
_ZN15RFeatureControl13DeleteFeatureE4TUid @ 51 NONAME
_ZN15RFeatureControl6SWIEndEv @ 52 NONAME
- _ZN15RFeatureControl8SWIStartEv @ 53 NONAME
+ _ZN15RFeatureControl8SWIStartEv @ 53 NONAME
+ _Z14GetClientCountv @ 54 NONAME
+ _ZN22TFeatMgrResourceTester14SetHeapFailureEii @ 55 NONAME
+ _ZN22TFeatMgrResourceTester4MarkEv @ 56 NONAME
+ _ZN22TFeatMgrResourceTester5CheckEv @ 57 NONAME
+ _ZN22TFeatMgrResourceTester5CountEv @ 58 NONAME
--- a/featuremgmt/featuremgr/group/featmgr.mmp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/group/featmgr.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -32,6 +32,7 @@
SOURCE featurecontrol.cpp
SOURCE featmgrtlsdata.cpp
SOURCE featurenotifier.cpp
+SOURCE featmgrresourcetester.cpp
SOURCEPATH ../src/shared
SOURCE featurecmn.cpp
--- a/featuremgmt/featuremgr/group/featmgrserver.mmp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/group/featmgrserver.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -40,6 +40,7 @@
SOURCE featmgrpatchdata.cpp
SOURCE burstate.cpp
SOURCE swilistener.cpp
+SOURCE featmgrstartup.cpp
SOURCEPATH ../src/shared
SOURCE featurecmn.cpp
--- a/featuremgmt/featuremgr/src/clientdll/featmgrclient.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/clientdll/featmgrclient.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -614,11 +614,37 @@
// ========================== OTHER EXPORTED FUNCTIONS =========================
-
-
// DEBUG only API functions
#ifdef EXTENDED_FEATURE_MANAGER_TEST
+/**
+*/
+void RFeatMgrClient::ResourceMark()
+ {
+ (void)SendReceive(EFeatMgrResourceMark);
+ }
+
+/**
+*/
+void RFeatMgrClient::ResourceCheck()
+ {
+ (void)SendReceive(EFeatMgrResourceCheck);
+ }
+
+/**
+*/
+TInt RFeatMgrClient::ResourceCount()
+ {
+ return SendReceive(EFeatMgrResourceCount);
+ }
+
+/**
+*/
+void RFeatMgrClient::SetHeapFailure(TInt aAllocFailType, TInt aRate)
+ {
+ (void)SendReceive(EFeatMgrSetHeapFailure, TIpcArgs(aAllocFailType, aRate));
+ }
+
// -----------------------------------------------------------------------------
// RFeatMgrClient::NumberOfNotifyFeatures()
// -----------------------------------------------------------------------------
--- a/featuremgmt/featuremgr/src/clientdll/featmgrclient.h Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/clientdll/featmgrclient.h Fri Mar 12 15:51:02 2010 +0200
@@ -84,7 +84,7 @@
TInt SWIStart() const;
TInt SWIEnd() const;
-
+
private:
/**
@@ -112,7 +112,10 @@
#ifdef EXTENDED_FEATURE_MANAGER_TEST
// Public DEBUG API functions
public:
-
+ void ResourceMark();
+ void ResourceCheck();
+ TInt ResourceCount();
+ void SetHeapFailure(TInt aAllocFailType, TInt aRate);
TInt NumberOfNotifyFeatures( void ) const;
TInt CountAllocCells( void ) const;
#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/src/clientdll/featmgrresourcetester.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,68 @@
+// Copyright (c) 2007-2009 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#include <e32std.h>
+#include "featmgrtlsdata.h"
+#include "featmgrresourcetester.h"
+
+#define UNUSED_ARG(arg) arg = arg
+
+//Defined in featurecontrol.cpp
+extern CFeatMgrTlsData* TlsData();
+
+/**
+*/
+EXPORT_C void TFeatMgrResourceTester::Mark()
+ {
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ CFeatMgrTlsData* tlsData = ::TlsData();
+ tlsData->ResourceMark();
+#endif
+ }
+
+/**
+*/
+EXPORT_C void TFeatMgrResourceTester::Check()
+ {
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ CFeatMgrTlsData* tlsData = ::TlsData();
+ tlsData->ResourceCheck();
+#endif
+ }
+
+/**
+*/
+EXPORT_C TInt TFeatMgrResourceTester::Count()
+ {
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ CFeatMgrTlsData* tlsData = ::TlsData();
+ return tlsData->ResourceCount();
+#else
+ return -1;
+#endif
+ }
+
+/**
+*/
+EXPORT_C void TFeatMgrResourceTester::SetHeapFailure(TInt aAllocFailType, TInt aRate)
+ {
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ CFeatMgrTlsData* tlsData = ::TlsData();
+ return tlsData->SetHeapFailure(aAllocFailType, aRate);
+#else
+ UNUSED_ARG(aAllocFailType);
+ UNUSED_ARG(aRate);
+#endif
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/src/clientdll/featmgrresourcetester.h Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,37 @@
+// 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 "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:
+//
+//
+
+#ifndef FEATMGRRESOURCETESTER_H
+#define FEATMGRRESOURCETESTER_H
+
+/**
+TFeatMgrResourceTester class is used internally by the FeatMgr server out of memory and resource leaking
+tests.
+It provides methods for heap allocation failure simulation and resource checking and counting.
+
+@internalAll
+@released
+*/
+class TFeatMgrResourceTester
+ {
+public:
+ IMPORT_C static void Mark();
+ IMPORT_C static void Check();
+ IMPORT_C static TInt Count();
+ IMPORT_C static void SetHeapFailure(TInt aAllocFailType, TInt aRate);
+ };
+
+#endif //FEATMGRRESOURCETESTER_H
--- a/featuremgmt/featuremgr/src/clientdll/featmgrtlsdata.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/clientdll/featmgrtlsdata.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -30,7 +30,20 @@
return tlsData;
}
-
+
+
+EXPORT_C TInt GetClientCount( )
+ {
+ CFeatMgrTlsData* tlsData = STATIC_CAST( CFeatMgrTlsData*, Dll::Tls() );
+ if (tlsData)
+ {
+ return tlsData->ClientCount();
+ }
+ else
+ {
+ return 0;
+ }
+ }
// ============================ MEMBER FUNCTIONS ===============================
@@ -120,6 +133,14 @@
}
// -----------------------------------------------------------------------------
+// CFeatMgrTlsData::ClientCount()
+// -----------------------------------------------------------------------------
+//
+TInt CFeatMgrTlsData::ClientCount()
+ {
+ return iClientCount;
+ }
+// -----------------------------------------------------------------------------
// CFeatMgrTlsData::FeatureSupported()
// -----------------------------------------------------------------------------
//
@@ -275,10 +296,39 @@
return iFeatMgrClient.SWIEnd();
}
+/////////////////////////////////////////////////////////////////////////////////
// debug only API functions
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
-#ifdef EXTENDED_FEATURE_MANAGER_TEST
+/**
+*/
+void CFeatMgrTlsData::ResourceMark()
+ {
+ iFeatMgrClient.ResourceMark();
+ }
+
+/**
+*/
+void CFeatMgrTlsData::ResourceCheck()
+ {
+ iFeatMgrClient.ResourceCheck();
+ }
+
+/**
+*/
+TInt CFeatMgrTlsData::ResourceCount()
+ {
+ return iFeatMgrClient.ResourceCount();
+ }
+
+/**
+*/
+void CFeatMgrTlsData::SetHeapFailure(TInt aAllocFailType, TInt aRate)
+ {
+ iFeatMgrClient.SetHeapFailure(aAllocFailType, aRate);
+ }
+
// -----------------------------------------------------------------------------
// CFeatMgrTlsData::NumberOfNotifyFeatures()
// -----------------------------------------------------------------------------
--- a/featuremgmt/featuremgr/src/clientdll/featmgrtlsdata.h Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/clientdll/featmgrtlsdata.h Fri Mar 12 15:51:02 2010 +0200
@@ -30,6 +30,9 @@
// FORWARD DECLARATIONS
class MFeatureObserver;
+//Exported function for test purpose only
+IMPORT_C TInt GetClientCount();
+
// CLASS DECLARATION
/**
@@ -67,6 +70,11 @@
* Decrease client count for this thread
*/
void DecreaseClientCount();
+
+ /**
+ * Get client count for this thread. Used for testing purpose only
+ */
+ int ClientCount();
/**
* From MFeatureClient
@@ -128,6 +136,10 @@
#ifdef EXTENDED_FEATURE_MANAGER_TEST
// Debug only API functions
public:
+ void ResourceMark();
+ void ResourceCheck();
+ TInt ResourceCount();
+ void SetHeapFailure(TInt aAllocFailType, TInt aRate);
TInt NumberOfNotifyFeatures( void ) const;
TInt CountAllocCells( void ) const;
#endif
--- a/featuremgmt/featuremgr/src/clientdll/featurecontrol.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/clientdll/featurecontrol.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -26,7 +26,7 @@
// ============================= LOCAL FUNCTIONS ===============================
-static CFeatMgrTlsData* TlsData( )
+CFeatMgrTlsData* TlsData( )
{
CFeatMgrTlsData* tlsData = STATIC_CAST( CFeatMgrTlsData*, Dll::Tls() );
--- a/featuremgmt/featuremgr/src/inc/featmgrclientserver.h Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/inc/featmgrclientserver.h Fri Mar 12 15:51:02 2010 +0200
@@ -173,7 +173,13 @@
* Software Installation ended
*
*/
- EFeatMgrSWIEnd
+ EFeatMgrSWIEnd,
+
+ EFeatMgrResourceMark,
+ EFeatMgrResourceCheck,
+ EFeatMgrResourceCount,
+ EFeatMgrSetHeapFailure
+
};
--- a/featuremgmt/featuremgr/src/serverexe/featmgrsecuritypolicy.h Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/serverexe/featmgrsecuritypolicy.h Fri Mar 12 15:51:02 2010 +0200
@@ -40,8 +40,8 @@
const TInt KFeatMgrPlatSecRanges[KFeatMgrPlatSecRangeCount] =
{
0, // IPC 0-7 Always passed
- 8, // IPC 8-13 WriteDeviceData
- 16 // IPC Not supported 16 ->
+ 8, // IPC 8-19 WriteDeviceData
+ 20 // IPC Not supported: 20 = 16 messages + 4 "resource check" messages
};
@@ -51,8 +51,8 @@
const TUint8 KFeatMgrPlatSecElementsIndex[KFeatMgrPlatSecRangeCount] =
{
CPolicyServer::EAlwaysPass, // IPC 0-3
- 0, // IPC 8-13
- CPolicyServer::ENotSupported // IPC 16 ->
+ 0, // IPC 8-19
+ CPolicyServer::ENotSupported // IPC 20 ->
};
#else
@@ -69,8 +69,8 @@
const TInt KFeatMgrPlatSecRanges[KFeatMgrPlatSecRangeCount] =
{
0, // IPC 0-9 Always passed
- 10, // IPC 10-15 WriteDeviceData
- 18 // IPC Not supported 18 ->
+ 10, // IPC 10-21 WriteDeviceData
+ 22 // IPC Not supported 22 ->
};
/**
* IPC segments and their capability requirements
@@ -78,8 +78,8 @@
const TUint8 KFeatMgrPlatSecElementsIndex[KFeatMgrPlatSecRangeCount] =
{
CPolicyServer::EAlwaysPass, // IPC 0-3
- 0, // IPC 10-15
- CPolicyServer::ENotSupported // IPC 18 ->
+ 0, // IPC 10-21
+ CPolicyServer::ENotSupported // IPC 22 ->
};
#endif
--- a/featuremgmt/featuremgr/src/serverexe/featmgrserver.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/serverexe/featmgrserver.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -35,9 +35,6 @@
_LIT( KPanicCategory, "FeatMgrServer" );
#endif // EXTENDED_FEATURE_MANAGER_TEST
-// LOCAL FUNCTION PROTOTYPES
-TInt E32Main(); // Process entry point
-
// ============================ MEMBER FUNCTIONS ===============================
// -----------------------------------------------------------------------------
@@ -49,7 +46,7 @@
CFeatMgrServer::CFeatMgrServer( const TInt aPriority, const TServerType aType )
:
CPolicyServer( aPriority, KFeatMgrPlatSecPolicy, aType ), iBurState(this),
- iBackupInProgress(EFalse),
+ iBURInProgress(EFalse),
iPluginsReady(EFalse),
iPluginsDeleted( EFalse ),
iPendingRequests( ETrue ),
@@ -444,10 +441,10 @@
// -----------------------------------------------------------------------------
// CFeatMgrServer::BackupIsInProgress()
// -----------------------------------------------------------------------------
-TBool CFeatMgrServer::BackupIsInProgress() const
+TBool CFeatMgrServer::BURIsInProgress() const
{
FUNC_LOG
- return(iBackupInProgress);
+ return(iBURInProgress);
}
// -----------------------------------------------------------------------------
@@ -681,7 +678,7 @@
switch( aCurrent )
{
case( EFeatMgrBURState_BackupStarted ) :
- iBackupInProgress = EFalse;
+ iBURInProgress = EFalse;
ServicePendingRequests();
break;
case( EFeatMgrBURState_RestoreStarted ) :
@@ -711,7 +708,7 @@
BURStatus CFeatMgrServer::Goto_StartBackupState( BURStatus /* aCurrent */ )
{
BURStatus aNewState = EFeatMgrBURState_BackupStarted; // state++
- iBackupInProgress = ETrue;
+ iBURInProgress = ETrue;
return aNewState;
}
@@ -719,7 +716,7 @@
{
BURStatus aNewState = EFeatMgrBURState_BackupEnded; // state++
- iBackupInProgress = EFalse;
+ iBURInProgress = EFalse;
ServicePendingRequests();
// no error from ServicePendingRequests() is possible
@@ -730,7 +727,7 @@
{
// remarkably like Goto_StartBackupState
BURStatus aNewState = EFeatMgrBURState_RestoreStarted; // state++
- iPluginsReady = EFalse;
+ iBURInProgress = ETrue;
return aNewState;
}
@@ -738,6 +735,7 @@
{
BURStatus aNewState = EFeatMgrBURState_Error; // fail safe
TInt err( KErrNone );
+ iBURInProgress = EFalse;
iPluginsReady = EFalse;
iPluginsDeleted = EFalse;
iPendingRequests = ETrue;
@@ -858,68 +856,4 @@
return;
}
-
-// ============================= LOCAL FUNCTIONS ===============================
-
-// -----------------------------------------------------------------------------
-// Function that starts the FeatMgrServer.
-// -----------------------------------------------------------------------------
-//
-static void RunServerL()
- {
- FUNC_LOG
-
- // Naming the server thread after the startup helps to debug panics
- User::LeaveIfError( User::RenameProcess( KServerProcessName ) );
-
- User::LeaveIfError( User::RenameThread( KServerProcessName ) );
-
- // Create and install the active scheduler we need
- CActiveScheduler* scheduler = new(ELeave) CActiveScheduler;
- CleanupStack::PushL( scheduler );
-
- CActiveScheduler::Install( scheduler );
-
- // Now we are ready to instantiate the actual CServer2 instance
- CFeatMgrServer* server = CFeatMgrServer::NewLC( KServerCActivePriority );
-
- // Initialisation complete, now signal the client
- RProcess::Rendezvous(KErrNone);
-
- INFO_LOG( "RunServerL() - Starting scheduler..." );
-
- // Ready to run
- CActiveScheduler::Start();
-
- INFO_LOG( "RunServerL() - Scheduler stopped" );
-
- // Cleanup the server and scheduler
- CleanupStack::PopAndDestroy( server );
- CleanupStack::PopAndDestroy( scheduler );
- }
-
-// -----------------------------------------------------------------------------
-// Main function
-// -----------------------------------------------------------------------------
-//
-TInt E32Main()
- {
- FUNC_LOG
-
- __UHEAP_MARK;
-
- CTrapCleanup* cleanup = CTrapCleanup::New();
- TInt ret = KErrNoMemory;
-
- if ( cleanup )
- {
- TRAP( ret, RunServerL() );
- delete cleanup;
- }
-
- __UHEAP_MARKEND;
-
- return ret;
- }
-
// End of File
--- a/featuremgmt/featuremgr/src/serverexe/featmgrserver.h Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/serverexe/featmgrserver.h Fri Mar 12 15:51:02 2010 +0200
@@ -116,7 +116,7 @@
Else returns EFalse.
@return backup status
*/
- TBool BackupIsInProgress() const;
+ TBool BURIsInProgress() const;
#ifdef EXTENDED_FEATURE_MANAGER_TEST
/**
@@ -278,7 +278,7 @@
CBurState iBurState;
// ETrue when backup in progress
- TBool iBackupInProgress;
+ TBool iBURInProgress;
// ETrue when feature info received from all plugins
TBool iPluginsReady;
--- a/featuremgmt/featuremgr/src/serverexe/featmgrsession.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/serverexe/featmgrsession.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -130,12 +130,21 @@
{
FUNC_LOG
// If plugins are not ready all request will be queued.
- // During backup operation, all write request e.g. EnableFeature will be queued
+ // During backup & restore operation, all write request
+ // e.g. EnableFeature will return with KErrServerBusy
TInt msgCmd = aMessage.Function();
- if ( !iFeatMgrServer.PluginsReady() || ( iFeatMgrServer.BackupIsInProgress() && IsWriteOperation( msgCmd ) ) )
+ if ( !iFeatMgrServer.PluginsReady() || ( iFeatMgrServer.BURIsInProgress() && IsWriteOperation( msgCmd ) ) )
{
- INFO_LOG( "CFeatMgrSession::ServiceL() - plugins not ready or backup is in progress" );
- iList.AddLast( *CFeatMgrPendingRequest::NewL( aMessage ) );
+ if ( iFeatMgrServer.BURIsInProgress() )
+ {
+ INFO_LOG( "CFeatMgrSession::ServiceL() - backup/restore is in progress - no write operation allowed" );
+ aMessage.Complete( KErrServerBusy );
+ }
+ else
+ {
+ INFO_LOG( "CFeatMgrSession::ServiceL() - plugins not ready" );
+ iList.AddLast( *CFeatMgrPendingRequest::NewL( aMessage ) );
+ }
}
else
{
@@ -525,8 +534,39 @@
break;
}
+
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
-#ifdef EXTENDED_FEATURE_MANAGER_TEST
+ case EFeatMgrResourceMark:
+ ResourceCountMarkStart();
+ break;
+
+ case EFeatMgrResourceCheck:
+ ResourceCountMarkEnd(aMessage);
+ break;
+
+ case EFeatMgrResourceCount:
+ {
+ TInt retCode = CountResources();
+ User::Leave(retCode);
+ }
+ break;
+
+ case EFeatMgrSetHeapFailure:
+ {
+ RAllocator::TAllocFail mode = static_cast <RAllocator::TAllocFail> (aMessage.Int0());
+ TInt failAllocNum = aMessage.Int1();
+ if(mode == RHeap::EBurstFailNext || mode == RHeap::EBurstRandom || mode == RHeap::EBurstTrueRandom || mode == RHeap::EBurstDeterministic)
+ {
+ User::__DbgSetBurstAllocFail(RHeap::EUser, mode, failAllocNum, 20);
+ }
+ else
+ {
+ User::__DbgSetAllocFail(RHeap::EUser, mode, failAllocNum);
+ }
+ }
+ break;
+
// debug only API
// returns the size of the iNotifyFeatures array
case EFeatMgrNumberOfNotifyFeatures:
@@ -590,6 +630,10 @@
}
}
+TInt CFeatMgrSession::CountResources()
+ {
+ return User::CountAllocCells();
+ }
// ============================= LOCAL FUNCTIONS ===============================
--- a/featuremgmt/featuremgr/src/serverexe/featmgrsession.h Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/src/serverexe/featmgrsession.h Fri Mar 12 15:51:02 2010 +0200
@@ -139,6 +139,7 @@
* @param aMessage The message containing the client request
*/
virtual void ServiceL( const RMessage2& aMessage );
+ virtual TInt CountResources();
private:
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/src/serverexe/featmgrstartup.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,79 @@
+// Copyright (c) 2007-2009 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#include "featmgrserver.h"
+#include "featmgrdebug.h"
+#include "featmgrconfiguration.h"
+
+// -----------------------------------------------------------------------------
+// Function that starts the FeatMgrServer.
+// -----------------------------------------------------------------------------
+//
+static void RunServerL()
+ {
+ FUNC_LOG
+
+ // Naming the server thread after the startup helps to debug panics
+ User::LeaveIfError( User::RenameProcess( KServerProcessName ) );
+
+ User::LeaveIfError( User::RenameThread( KServerProcessName ) );
+
+ // Create and install the active scheduler we need
+ CActiveScheduler* scheduler = new(ELeave) CActiveScheduler;
+ CleanupStack::PushL( scheduler );
+
+ CActiveScheduler::Install( scheduler );
+
+ // Now we are ready to instantiate the actual CServer2 instance
+ CFeatMgrServer* server = CFeatMgrServer::NewLC( KServerCActivePriority );
+
+ // Initialisation complete, now signal the client
+ RProcess::Rendezvous(KErrNone);
+
+ INFO_LOG( "RunServerL() - Starting scheduler..." );
+
+ // Ready to run
+ CActiveScheduler::Start();
+
+ INFO_LOG( "RunServerL() - Scheduler stopped" );
+
+ // Cleanup the server and scheduler
+ CleanupStack::PopAndDestroy( server );
+ CleanupStack::PopAndDestroy( scheduler );
+ }
+
+// -----------------------------------------------------------------------------
+// Main function
+// -----------------------------------------------------------------------------
+//
+TInt E32Main()
+ {
+ FUNC_LOG
+
+ __UHEAP_MARK;
+
+ CTrapCleanup* cleanup = CTrapCleanup::New();
+ TInt ret = KErrNoMemory;
+
+ if ( cleanup )
+ {
+ TRAP( ret, RunServerL() );
+ delete cleanup;
+ }
+
+ __UHEAP_MARKEND;
+
+ return ret;
+ }
--- a/featuremgmt/featuremgr/test/group/bld.inf Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/test/group/bld.inf Fri Mar 12 15:51:02 2010 +0200
@@ -21,9 +21,22 @@
#include "../helper/helping_exe/group/bld.inf"
PRJ_TESTMMPFILES
-//RTest project files
-//../rtest/group/t_fmgrbackupmod.mmp
-//../rtest/group/t_fmgrbackupquery.mmp
+//Rtest project files
+// These backup and restore tests are techview tests, therefore need to be marked as manual for ONB purpose.
+../rtest/group/t_fmgrbackupresponse.mmp manual
+../rtest/group/t_fmgrrestoreresponse.mmp manual
+
+// RTest for Textshell
+../rtest/group/t_fmgrapi.mmp
+../rtest/group/t_fmgroom.mmp
+../rtest/group/t_fmgrstartup.mmp
+../rtest/group/t_fmgrpanic.mmp
+../rtest/group/t_fmgrbadclient.mmp manual
+../rtest/group/t_fmgrsecurity1.mmp
+../rtest/group/t_fmgrnotify.mmp
+../rtest/group/t_fmgrperformance.mmp
+../rtest/group/t_fmgrswi.mmp
+../rtest/group/t_fmgrunitrefcount.mmp
//TEF project files
../tef/tef_feature_generator/group/tef_feature_generator.mmp manual
@@ -69,9 +82,9 @@
../tef/tef_efm_configured/data/partial.dat z:/test/efm/scripts/partial.dat
//iby files for the test components
-featmgr_test.iby /epoc32/rom/include/featmgr_test.iby
-../rtest/group/featmgr_rtest.iby /epoc32/rom/include/featmgr_rtest.iby
-../tef/tef_efm_configured/group/efm_configured_testserver.iby /epoc32/rom/include/efm_configured_testserver.iby
+featmgr_techview_test.iby /epoc32/rom/include/featmgr_techview_test.iby
+featmgr_textshell_test.iby /epoc32/rom/include/featmgr_textshell_test.iby
+../tef/tef_efm_configured/group/efm_configured_testserver.iby /epoc32/rom/include/efm_configured_testserver.iby
../tef/tef_efm_normal/group/efm_normal_testserver.iby /epoc32/rom/include/efm_normal_testserver.iby
../tef/tef_efm_unit/group/efm_unit_testserver.iby /epoc32/rom/include/efm_unit_testserver.iby
../tef/tef_feature_generator/group/tef_feature_generator.iby /epoc32/rom/include/tef_feature_generator.iby
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/group/featmgr_techview_test.iby Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,44 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+// For all Techview tests (TEF + RTest).
+//
+
+#ifndef __FEATMGR_TEST_IBY__
+#define __FEATMGR_TEST_IBY__
+
+// Make sure that the feature manager production code is included in the ROM.
+#include "featmgr.iby"
+
+// Techview RTests.
+file=ABI_DIR\BUILD_DIR\t_fmgrbackupresponse.exe test\t_fmgrbackupresponse.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrrestoreresponse.exe test\t_fmgrrestoreresponse.exe
+
+//main efm test script
+data=DATAZ_\test\efm\scripts\tef_featmgr.script test\efm\scripts\tef_featmgr.script
+
+//tef tests .iby files
+#include "efm_configured_testserver.iby"
+#include "efm_normal_testserver.iby"
+#include "efm_unit_testserver.iby"
+#include "tef_feature_generator.iby"
+#include "tef_efm_bursuite.iby"
+
+// helper .iby files
+#include "test_efm.iby"
+#include "pluginhelper.iby"
+#include "test_plugins.iby"
+#include "dummyswi.iby"
+#include "helping_exe.iby"
+
+#endif //__FEATMGR_TEST_IBY__
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/group/featmgr_textshell_test.iby Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,30 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#ifndef __FEATMGR_RTEST_IBY__
+#define __FEATMGR_RTEST_IBY__
+
+file=ABI_DIR\BUILD_DIR\t_fmgrapi.exe test\t_fmgrapi.exe
+file=ABI_DIR\BUILD_DIR\t_fmgroom.exe test\t_fmgroom.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrstartup.exe test\t_fmgrstartup.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrpanic.exe test\t_fmgrpanic.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrbadclient.exe test\t_fmgrbadclient.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrsecurity1.exe test\t_fmgrsecurity1.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrnotify.exe test\t_fmgrnotify.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrperformance.exe test\t_fmgrperformance.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrswi.exe test\t_fmgrswi.exe
+file=ABI_DIR\BUILD_DIR\t_fmgrunitrefcount.exe test\t_fmgrunitrefcount.exe
+
+#endif // __FEATMGR_RTEST_IBY__
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/group/featmgrtests.bat Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,28 @@
+@rem
+@rem Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+@rem All rights reserved.
+@rem This component and the accompanying materials are made available
+@rem under the terms of "Eclipse Public License v1.0"
+@rem which accompanies this distribution, and is available
+@rem at the URL "http://www.eclipse.org/legal/epl-v10.html".
+@rem
+@rem Initial Contributors:
+@rem Nokia Corporation - initial contribution.
+@rem
+@rem Contributors:
+@rem
+@rem Description:
+@rem
+
+t_fmgrbackupresponse.exe
+t_fmgrrestoreresponse.exe
+t_fmgrapi.exe
+t_fmgroom.exe
+t_fmgrstartup.exe
+t_fmgrpanic.exe
+t_fmgrbadclient.exe
+t_fmgrsecurity1.exe
+t_fmgrnotify.exe
+t_fmgrperformance.exe
+t_fmgrswi.exe
+t_fmgrunitrefcount.exe
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrapi.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,34 @@
+// 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 "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:
+//
+
+TARGET t_fmgrapi.exe
+TARGETTYPE exe
+
+CAPABILITY WriteDeviceData
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrapi.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrbackupresponse.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,36 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+TARGET t_fmgrbackupresponse.exe
+TARGETTYPE EXE
+CAPABILITY ReadDeviceData WriteDeviceData AllFiles
+
+USERINCLUDE ../inc
+
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrbursim.cpp
+SOURCE t_fmgrbackupresponse.cpp
+
+LIBRARY euser.lib
+LIBRARY bafl.lib
+LIBRARY efsrv.lib
+LIBRARY featmgr.lib
+
+UID 0 0x10281e17
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrbadclient.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,34 @@
+// 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 "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:
+//
+
+TARGET t_fmgrbadclient.exe
+TARGETTYPE exe
+
+CAPABILITY WriteDeviceData
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrbadclient.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrnotify.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,34 @@
+// 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 "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:
+//
+
+TARGET t_fmgrnotify.exe
+TARGETTYPE exe
+
+CAPABILITY WriteDeviceData
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrnotify.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgroom.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,36 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+TARGET t_fmgroom.exe
+TARGETTYPE exe
+
+CAPABILITY WriteDeviceData ProtServ ReadDeviceData AllFiles
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgroom.cpp
+
+LIBRARY euser.lib
+LIBRARY efsrv.lib
+LIBRARY bafl.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrpanic.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,34 @@
+// 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 "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:
+//
+
+TARGET t_fmgrpanic.exe
+TARGETTYPE exe
+
+CAPABILITY WriteDeviceData
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrpanic.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrperformance.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,35 @@
+// 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 "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:
+//
+
+TARGET t_fmgrperformance.exe
+TARGETTYPE exe
+
+CAPABILITY WriteDeviceData
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrperformance.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+LIBRARY hal.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrrestoreresponse.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,36 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+TARGET t_fmgrrestoreresponse.exe
+TARGETTYPE EXE
+CAPABILITY ReadDeviceData WriteDeviceData AllFiles
+
+USERINCLUDE ../inc
+
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrbursim.cpp
+SOURCE t_fmgrrestoreresponse.cpp
+
+LIBRARY euser.lib
+LIBRARY bafl.lib
+LIBRARY efsrv.lib
+LIBRARY featmgr.lib
+
+UID 0 0x10281e17
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrsecurity1.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,34 @@
+// 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 "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:
+//
+
+TARGET t_fmgrsecurity1.exe
+TARGETTYPE exe
+
+CAPABILITY None
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrsecurity1.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrstartup.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,54 @@
+// 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 "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:
+//
+
+TARGET t_fmgrstartup.exe
+TARGETTYPE exe
+
+MACRO EXTENDED_FEATURE_MANAGER_TEST
+
+CAPABILITY ProtServ ReadDeviceData AllFiles
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+USERINCLUDE ../../../src/inc
+USERINCLUDE ../../../src/serverexe
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrstartup.cpp
+
+SOURCEPATH ../../../src/serverexe
+SOURCE featmgrfeatureregistry.cpp
+SOURCE featmgrfeatureentry.cpp
+SOURCE featmgrsession.cpp
+SOURCE featmgrserver.cpp
+SOURCE burstate.cpp
+SOURCE swilistener.cpp
+SOURCE featmgrpluginhandler.cpp
+SOURCE featmgrtimer.cpp
+SOURCE featmgrpatchdata.cpp
+
+SOURCEPATH ../../../src/shared
+SOURCE featurecmn.cpp
+
+LIBRARY efsrv.lib
+LIBRARY estor.lib
+LIBRARY euser.lib
+LIBRARY ecom.lib
+LIBRARY bafl.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrswi.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,36 @@
+// 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 "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:
+//
+
+TARGET t_fmgrswi.exe
+TARGETTYPE exe
+UID 0x0 0x101F7295
+
+CAPABILITY All -Tcb
+
+USERINCLUDE .
+USERINCLUDE ../../../inc
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../src
+SOURCE t_fmgrswi.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+LIBRARY efsrv.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/group/t_fmgrunitrefcount.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,38 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+TARGET t_fmgrunitrefcount.exe
+TARGETTYPE EXE
+CAPABILITY WriteDeviceData
+
+USERINCLUDE ../inc
+USERINCLUDE ../../../src/clientdll
+USERINCLUDE ../../../src/inc
+USERINCLUDE ../../../inc
+
+OS_LAYER_SYSTEMINCLUDE
+
+SOURCEPATH ../src
+SOURCE t_fmgrunitrefcount.cpp
+
+LIBRARY euser.lib
+LIBRARY featmgr.lib
+LIBRARY featdiscovery.lib
+
+
+UID 0 0
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrapi.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,443 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include <featurecontrol.h>
+#include <featdiscovery.h>
+
+using namespace NFeature;
+
+const TInt KInvalidFeatureId1 = 90901671;
+const TInt KInvalidNegFeatureId2 = -90901671;
+const TUid KInvalidFeatureUid1 = {KInvalidFeatureId1};
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgrapi"));
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4059
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureSupportedTestL()
+ {
+ FeatureManager::InitializeLibL();
+ FeatureManager::InitializeLibL();
+
+ //Feature, default present
+ TBool rc = FeatureManager::FeatureSupported(KConnectivity.iUid);
+ TEST(rc);
+ //Feature, default not present
+ rc = FeatureManager::FeatureSupported(KPrint.iUid);
+ TEST(rc);
+
+ //Ivalid feature UID
+ rc = FeatureManager::FeatureSupported(KInvalidFeatureId1);
+ TEST(!rc);
+ //Ivalid feature UID - negative
+ rc = FeatureManager::FeatureSupported(KInvalidNegFeatureId2);
+ TEST(!rc);
+
+ FeatureManager::UnInitializeLib();
+ FeatureManager::UnInitializeLib();
+ FeatureManager::UnInitializeLib();//it should be safe to call UnInitializeLib() even without matching InitializeLibL() call
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4060
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureControlTest1()
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+ /////////////////////////////////////////////////////////////
+ RFeatureUidArray farray;
+ err = ctrl.ListSupportedFeatures(farray);
+ TEST2(err, KErrNone);
+ TheTest.Printf(_L("RFeatureControl::ListSupportedFeatures()\r\n"));
+ for(TInt i=0;i<farray.Count();++i)
+ {
+ TheTest.Printf(_L(" Feature: %08X\r\n"), farray[i].iUid);
+ }
+ /////////////////////////////////////////////////////////////
+ RFeatureArray farray2;
+ for(TInt i=0;i<farray.Count();++i)
+ {
+ err = farray2.Append(farray[i]);
+ TEST2(err, KErrNone);
+ }
+
+ err = ctrl.FeaturesSupported(farray2);
+ TEST2(err, KErrNone);
+
+ TheTest.Printf(_L("RFeatureControl::FeaturesSupported()\r\n"));
+ for(TInt i=0;i<farray2.Count();++i)
+ {
+ TheTest.Printf(_L(" Feature: %08X, Flags: %08X, Data: %08X\r\n"), farray2[i].FeatureUid(), farray2[i].FeatureFlags().iFlags, farray2[i].FeatureData());
+ }
+
+ RFeatureArray farray3;
+ err = ctrl.FeaturesSupported(farray3);
+ TEST2(err, KErrArgument);
+
+ /////////////////////////////////////////////////////////////
+ farray2.Close();
+ farray.Close();
+ ctrl.Close();
+ ctrl.Close();//It should be safe to call Close() again
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4061
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureControlTest2()
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+ /////////////////////////////////////////////////////////////
+ RFeatureUidArray farray;
+ err = ctrl.ListSupportedFeatures(farray);
+ TEST2(err, KErrNone);
+ for(TInt i=0;i<farray.Count();++i)
+ {
+ err = ctrl.FeatureSupported(farray[i]);
+ TEST2(err, KFeatureSupported);
+
+ TFeatureEntry feat(farray[i]);
+ err = ctrl.FeatureSupported(feat);
+ TEST2(err, KFeatureSupported);
+ }
+
+ err = ctrl.FeatureSupported(TUid::Uid(KInvalidFeatureId1));
+ TEST2(err, KErrNotFound);
+
+ TFeatureEntry feat1(TUid::Uid(KInvalidFeatureId1));
+ err = ctrl.FeatureSupported(feat1);
+ TEST2(err, KErrNotFound);
+
+ const TUint KFlags = 0x0134357;
+ const TUint KData = 0xAB5234;
+ TFeatureEntry feat2(TUid::Uid(KInvalidFeatureId1), KFlags, KData);
+ err = ctrl.FeatureSupported(feat2);
+ TEST2(err, KErrNotFound);
+
+ /////////////////////////////////////////////////////////////
+ farray.Close();
+ ctrl.Close();
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4062
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureControlTest3()
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ //Retrieve a uid list of all supported features
+ RFeatureUidArray farray;
+ err = ctrl.ListSupportedFeatures(farray);
+ TEST2(err, KErrNone);
+ //Retrieve a TFeaureEntry list of all supported features
+ RFeatureArray farray2;
+ for(TInt i=0;i<farray.Count();++i)
+ {
+ err = farray2.Append(farray[i]);
+ TEST2(err, KErrNone);
+ }
+ err = ctrl.FeaturesSupported(farray2);
+ TEST2(err, KErrNone);
+ //Play with EnableFeature()/DisableFeature() calls. If the EFeatureModifiable flag is not set then
+ //the feature cannot be enabled or disabled.
+ for(TInt i=0;i<farray2.Count();++i)
+ {
+ const TFeatureEntry& fentry = farray2[i];
+ TBitFlags32 flags = fentry.FeatureFlags();
+
+ err = ctrl.DisableFeature(fentry.FeatureUid());
+ TEST2(err, flags.IsSet(EFeatureModifiable) ? KErrNone : KErrAccessDenied);
+
+ err = ctrl.EnableFeature(fentry.FeatureUid());
+ TEST2(err, flags.IsSet(EFeatureModifiable) ? KErrNone : KErrAccessDenied);
+ }
+ //It is impossible to set non-existing feature
+ const TUid KNewFeatureUid = {0x7888ABCD};
+ err = ctrl.SetFeature(KNewFeatureUid, ETrue, 0x0);
+ TEST2(err, KErrNotFound);
+ //It is impossible to set non-modifiable feature
+ TBitFlags32 flags = farray2[0].FeatureFlags();
+ err = ctrl.SetFeature(farray2[0].FeatureUid(), ETrue, 0x0);
+ TEST2(err, flags.IsSet(EFeatureModifiable) ? KErrNone : KErrAccessDenied);
+ //Add new feature
+ flags.ClearAll();
+ flags.Set(EFeatureSupported);
+ flags.Set(EFeatureModifiable);
+ TFeatureEntry fentry(KNewFeatureUid, flags, 0x0);
+ err = ctrl.AddFeature(fentry);
+ TEST2(err, KErrNone);
+ //Retrieve the new feature and check flags
+ err = ctrl.FeatureSupported(fentry);
+ TEST2(err, KFeatureSupported);
+ flags = fentry.FeatureFlags();
+ TEST(flags.IsSet(EFeatureSupported));
+ TEST(flags.IsSet(EFeatureModifiable));
+ //Now, it should be possible to set the new feature - it is modifiable.
+ err = ctrl.SetFeature(fentry.FeatureUid(), ETrue, 0x0);
+ TEST2(err, KErrNone);
+ err = ctrl.SetFeature(fentry.FeatureUid(), EFalse, 0x0);
+ TEST2(err, KErrNone);
+ //Enable/disable
+ err = ctrl.EnableFeature(fentry.FeatureUid());
+ TEST2(err, KErrNone);
+ err = ctrl.DisableFeature(fentry.FeatureUid());
+ TEST2(err, KErrNone);
+ //Delete the added feature
+ err = ctrl.DeleteFeature(fentry.FeatureUid());
+ TEST2(err, KErrNone);
+ err = ctrl.DeleteFeature(fentry.FeatureUid());
+ TEST2(err, KErrNotFound);
+
+ /////////////////////////////////////////////////////////////
+ farray2.Close();
+ farray.Close();
+ ctrl.Close();
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4063
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureDiscoveryTest1L()
+ {
+ TBool rc = CFeatureDiscovery::IsFeatureSupportedL(KInvalidFeatureId1);
+ TEST(!rc);
+ rc = CFeatureDiscovery::IsFeatureSupportedL(KLocationManagement.iUid);
+ TEST(rc);
+
+ rc = CFeatureDiscovery::IsFeatureSupportedL(KInvalidFeatureUid1);
+ TEST(!rc);
+ rc = CFeatureDiscovery::IsFeatureSupportedL(KLocationManagement);
+ TEST(rc);
+
+ CFeatureDiscovery* fdiscovery = CFeatureDiscovery::NewLC();
+
+ rc = fdiscovery->IsSupported(KInvalidFeatureId1);
+ TEST(!rc);
+ rc = fdiscovery->IsSupported(KLocationManagement.iUid);
+ TEST(rc);
+
+ rc = fdiscovery->IsSupported(KInvalidFeatureUid1);
+ TEST(!rc);
+ rc = fdiscovery->IsSupported(KLocationManagement);
+ TEST(rc);
+
+ CleanupStack::PopAndDestroy(fdiscovery);
+ }
+
+void DoFeatureDiscoveryTest2(TBool aStaticMethodsUsed)
+ {
+ CFeatureDiscovery* fdiscovery = NULL;
+ if(!aStaticMethodsUsed)
+ {
+ fdiscovery = CFeatureDiscovery::NewL();
+ }
+ //////////////////////////////////////////////////////////
+ //A test with a set: one valid and one invalid feature
+ TFeatureSet fset;
+ TInt err = fset.Append(KConnectivity);
+ TEST2(err, KErrNone);
+ err = fset.Append(KInvalidFeatureUid1);
+ TEST2(err, KErrNone);
+ TBool rc = fset.IsFeatureSupported(KConnectivity);
+ TEST(!rc);
+ rc = fset.IsFeatureSupported(KInvalidFeatureUid1);
+ TEST(!rc);
+ if(aStaticMethodsUsed)
+ {
+ TRAP(err, CFeatureDiscovery::FeaturesSupportedL(fset));
+ }
+ else
+ {
+ err = fdiscovery->FeaturesSupported(fset);
+ }
+ TEST2(err, KErrNone);
+ rc = fset.IsFeatureSupported(KConnectivity);
+ TEST(rc);
+ rc = fset.IsFeatureSupported(KInvalidFeatureUid1);
+ TEST(!rc);
+ rc = fset.AreAllFeaturesSupported();
+ TEST(!rc);
+ //////////////////////////////////////////////////////////
+ //A test with an empty set
+ TFeatureSet fset2;
+ rc = fset2.IsFeatureSupported(KConnectivity);
+ TEST(!rc);
+ rc = fset2.IsFeatureSupported(KInvalidFeatureUid1);
+ TEST(!rc);
+ if(aStaticMethodsUsed)
+ {
+ TRAP(err, CFeatureDiscovery::FeaturesSupportedL(fset2));
+ }
+ else
+ {
+ err = fdiscovery->FeaturesSupported(fset2);
+ }
+ TEST2(err, KErrArgument);
+ rc = fset2.IsFeatureSupported(KConnectivity);
+ TEST(!rc);
+ rc = fset2.IsFeatureSupported(KInvalidFeatureUid1);
+ TEST(!rc);
+ rc = fset2.AreAllFeaturesSupported();
+ TEST(rc);//because fset2 is empty
+ //////////////////////////////////////////////////////////
+ //A test with a set: two valid features
+ TFeatureSet fset3;
+ err = fset3.Append(KConnectivity);
+ TEST2(err, KErrNone);
+ err = fset3.Append(KSip);
+ TEST2(err, KErrNone);
+ if(aStaticMethodsUsed)
+ {
+ TRAP(err, CFeatureDiscovery::FeaturesSupportedL(fset3));
+ }
+ else
+ {
+ err = fdiscovery->FeaturesSupported(fset3);
+ }
+ TEST2(err, KErrNone);
+ rc = fset3.IsFeatureSupported(KConnectivity);
+ TEST(rc);
+ rc = fset3.IsFeatureSupported(KSip);
+ TEST(rc);
+ rc = fset3.AreAllFeaturesSupported();
+ TEST(rc);
+ //////////////////////////////////////////////////////////
+ delete fdiscovery;
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4064
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureDiscoveryTest2L()
+ {
+ DoFeatureDiscoveryTest2(ETrue);
+ DoFeatureDiscoveryTest2(EFalse);
+ }
+
+void DoTestsL()
+ {
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4059 FeatureManager::FeatureSupported() test"));
+ FeatureSupportedTestL();
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4060 RFeatureControl tests-1"));
+ FeatureControlTest1();
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4061 RFeatureControl tests-2"));
+ FeatureControlTest2();
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4062 RFeatureControl tests-3"));
+ FeatureControlTest3();
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4063 CFeatureDiscovery tests-1"));
+ FeatureDiscoveryTest1L();
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4064 CFeatureDiscovery & TFeatureSet tests"));
+ FeatureDiscoveryTest2L();
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrbackupresponse.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,182 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#include <e32test.h>
+#include <e32debug.h>
+#include <bautils.h>
+#include <featurecontrol.h>
+#include "t_fmgrbursim.h"
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+RTest TheTest(_L("t_fmgrbackupresponse"));
+
+const TUint threadTimeout = 2000000; // thread timeout = 2 seconds
+
+static RSemaphore MainThreadCrS;
+static TBool featMgrIsResponsive = EFalse;
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine, TBool aPrintThreadName = EFalse)
+ {
+ if(!aValue)
+ {
+ //DeleteTestFiles();
+ if(aPrintThreadName)
+ {
+ RThread th;
+ TName name = th.Name();
+ RDebug::Print(_L("*** Thread %S, Line %d\r\n"), &name, aLine);
+ }
+ else
+ {
+ RDebug::Print(_L("*** Line %d\r\n"), aLine);
+ }
+ TheTest(EFalse, aLine);
+ }
+ }
+
+void Check2(TInt aValue, TInt aExpected, TInt aLine, TBool aPrintThreadName = EFalse)
+ {
+ if(aValue != aExpected)
+ {
+ //DeleteTestFiles();
+ if(aPrintThreadName)
+ {
+ RThread th;
+ TName name = th.Name();
+ RDebug::Print(_L("*** Thread %S, Line %d Expected error: %d, got: %d\r\n"), &name, aLine, aExpected, aValue);
+ }
+ else
+ {
+ RDebug::Print(_L("*** Line %d, Expected error: %d, got: %d\r\n"), aLine, aExpected, aValue);
+ }
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+#define TTEST(arg) ::Check1((arg), __LINE__, ETrue)
+#define TTEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__, ETrue)
+
+// ------------------------- -------------------------
+// setup and cleanup functions
+
+TInt TestThreadL(void*)
+ {
+ __UHEAP_MARK;
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ RFeatureControl rfc;
+ TTEST2( rfc.Connect(), KErrNone );
+
+ // During backup, feature manager server should be responsive and return KErrServerBusy for write request
+ TInt err = rfc.EnableFeature( TUid::Uid(0x00000001) );
+ TTEST2(err, KErrServerBusy);
+
+ // During backup, feature manager server should be responsive and NOT return KErrServerBusy for read request
+ err = rfc.FeatureSupported( TUid::Uid(0x00000001) );
+ TTEST(err != KErrServerBusy);
+
+ rfc.Close();
+ featMgrIsResponsive = ETrue;
+ RDebug::Print(_L("+++:TestThread: Query and Modification completed\r\n"));
+ MainThreadCrS.Signal();
+ delete tc;
+
+ __UHEAP_MARKEND;
+
+ return KErrNone;
+ }
+/**
+@SYMTestCaseID PDS-EFM-CT-4057
+@SYMTestCaseDesc Querying and modifying a feature during backup operation.
+ Verify that a response is returned from the server during backup.
+@SYMTestPriority High
+@SYMTestActions Start simulating backup operation
+ Create a thread that will:
+ Modify a feature and verify that a response (KErrServerBusy) is received
+ Query a feature and verify that a response is received (doesn't matter what the result is)
+ The thread should finished in less than 2 seconds.
+ Otherwise the test fail.
+@SYMTestExpectedResults Test must not fail
+@SYMREQ
+*/
+void TestBackupResponseL()
+ {
+ _LIT(KThreadName, "BakTh");
+ featMgrIsResponsive = EFalse;
+
+ CFeatMgrBURSim* simulate = CFeatMgrBURSim::NewLC();
+ RThread testThread;
+ TRequestStatus testStatus;
+ CleanupClosePushL( testThread );
+
+ simulate->Simulate_CheckRegFileL();
+
+ // Simulate a backup
+ RDebug::Print(_L("Simulating Backup of FeatMgr\r\n"));
+ simulate->Simulate_StartBackupL();
+
+ TEST2( testThread.Create(KThreadName, &TestThreadL, 0x2000, 0x1000, 0x10000, NULL, EOwnerProcess), KErrNone );
+ testThread.Logon(testStatus);
+ TEST2( testStatus.Int(), KRequestPending );
+ testThread.Resume();
+ // Wait for 1.5 second for the query thread to finish.
+ RDebug::Print(_L("+++:MainThread: Wait for query and modification completion...\r\n"));
+ MainThreadCrS.Wait(threadTimeout);
+ // If query is responsive within the 1.5 second frame the following check should pass.
+ TEST (featMgrIsResponsive);
+ simulate->Simulate_EndBackupL();
+
+ CleanupStack::PopAndDestroy(&testThread);
+ CleanupStack::PopAndDestroy(simulate);
+ }
+
+////////////////////////////////////////////////////////////////////////////////////
+void DoTestsL()
+ {
+ MainThreadCrS.CreateLocal(0);
+
+ TheTest.Start(_L(" @SYMTestCaseID:PDS-EFM-CT-4057 Backup Query and Modification Response"));
+ TestBackupResponseL();
+
+ MainThreadCrS.Close();
+
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrbadclient.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,425 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <e32math.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include "featurepanics.h"
+#include <featurecontrol.h>
+#include <featurenotifier.h>
+#include "..\src\inc\featmgrconfiguration.h"
+#include "..\src\inc\featmgrclientserver.h"
+
+using namespace NFeature;
+
+static RTest TheTest(_L("t_fmgrbadclient"));
+
+const TInt KTestIterCount = 5000;
+
+enum TArgType
+ {
+ EIntArgType,
+ ETextArgType,
+ EBinArgType,
+ ELastArgType
+ };
+
+const TInt KMaxDesArgLen = 1000;
+
+//If the FeatMgr server crashes and the test receives KErrServerTerminated error, then the
+//next set will contain the last:
+// - iteration number;
+// - handle type;
+// - function code;
+// - handle;
+// - IPC arguments values;
+struct TThreadData
+ {
+ TInt iIteration;
+ TInt iFunction;
+ TArgType iArgType[KMaxMessageArguments];
+ TInt iIntArg[KMaxMessageArguments];
+ TBuf<KMaxDesArgLen> iTextArg[KMaxMessageArguments];
+ TBuf8<KMaxDesArgLen> iBinArg[KMaxMessageArguments];
+ TInt64 iSeed;
+ };
+
+_LIT(KPanicCategory, "SrvTerm");
+_LIT(KPanicCategory2, "InvArg");
+const TInt KPanicCode = 1111;
+const TInt KPanicCode2 = 2222;
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine, TBool aPrintThreadName = EFalse)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ if(aPrintThreadName)
+ {
+ RThread th;
+ TName name = th.Name();
+ RDebug::Print(_L("*** Expression evaluated to false. Thread %S, Line %d\r\n"), &name, aLine);
+ }
+ else
+ {
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ }
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine, TBool aPrintThreadName = EFalse)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ if(aPrintThreadName)
+ {
+ RThread th;
+ TName name = th.Name();
+ RDebug::Print(_L("*** Thread %S, Line %d Expected error: %d, got: %d\r\n"), &name, aLine, aExpected, aValue);
+ }
+ else
+ {
+ RDebug::Print(_L("*** Line %d, Expected error: %d, got: %d\r\n"), aLine, aExpected, aValue);
+ }
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+#define TTEST(arg) ::Check1((arg), __LINE__, ETrue)
+#define TTEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__, ETrue)
+
+//////////////////////////////////////////////////////////////////////////////////////////////////
+
+static TInt StartFeatMgrServer()
+ {
+ RProcess server;
+ const TUidType serverUid( KNullUid, KServerUid2, KNullUid );
+ TInt err = server.Create( KServerExeName, // FeatMgrServer.exe
+ KNullDesC, // A descriptor containing data passed as
+ // an argument to the thread function of
+ // the new process's main thread, when it
+ // is first scheduled.
+ serverUid, // FeatMgr server UID
+ EOwnerProcess ); // Ownership of this process handle
+
+ // Return error code if we couldn't create a process
+ if ( err == KErrNone )
+ {
+ // Rendezvous is used to detect server start
+ TRequestStatus stat;
+ server.Rendezvous( stat );
+
+ if ( stat != KRequestPending )
+ {
+ server.Kill( KErrNone ); // Abort startup
+ }
+ else
+ {
+ server.Resume(); // Logon OK - start the server
+ }
+
+ User::WaitForRequest( stat ); // Wait for start or death
+
+ // We can't use the 'exit reason' if the server paniced as this
+ // is the panic 'reason' and may be '0' which cannot be distinguished
+ // from KErrNone
+ err = (server.ExitType() == EExitPanic)? KErrGeneral : stat.Int();
+
+ // We can close the handle now
+ server.Close();
+ }
+
+ return err;
+ }
+
+//////////////////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////// RTestFeatMgrSession ////////////////////////////////
+//////////////////////////////////////////////////////////////////////////////////////////////////
+
+class RTestFeatMgrSession : public RSessionBase
+ {
+public:
+ TInt Connect();
+ void Close();
+ TInt SendReceive(TInt aFunction);
+ TInt SendReceive(TInt aFunction, const TIpcArgs& aArgs);
+
+private:
+ TInt DoCreateSession();
+ };
+
+TInt RTestFeatMgrSession::Connect()
+ {
+ TInt err = DoCreateSession();
+ if(err != KErrNone && err != KErrAlreadyExists)
+ {
+ Close();
+ }
+ return err;
+ }
+
+void RTestFeatMgrSession::Close()
+ {
+ RSessionBase::Close();
+ }
+
+TInt RTestFeatMgrSession::SendReceive(TInt aFunction)
+ {
+ return RSessionBase::SendReceive(aFunction);
+ }
+
+TInt RTestFeatMgrSession::SendReceive(TInt aFunction, const TIpcArgs& aArgs)
+ {
+ return RSessionBase::SendReceive(aFunction, aArgs);
+ }
+
+TInt RTestFeatMgrSession::DoCreateSession()
+ {
+ const TInt KRetry( 2 );
+ // Try this twice
+ TInt retry( KRetry );
+ TInt err( KErrNone );
+
+ while ( retry > 0 )
+ {
+ // Try to create a FeatMgr Server session
+ err = CreateSession(KServerProcessName,
+ TVersion(KServerVersionMajor, KServerVersionMinor, KServerVersionBuild),
+ KDefaultAsyncSlots);
+
+ if ( err != KErrNotFound && err != KErrServerTerminated )
+ {
+ // KErrNone or unrecoverable error
+ retry = 0;
+ }
+ else
+ {
+ // Return code was KErrNotFound or KErrServerTerminated.
+ // Try to start a new FeatMgr Server
+ err = StartFeatMgrServer();
+
+ if ( err != KErrNone && err != KErrAlreadyExists )
+ {
+ // Unrecoverable error
+ retry = 0;
+ }
+ }
+
+ retry--;
+ }
+
+ return err;
+ }
+
+void PrintIterationCount(TInt aIteration)
+ {
+ if((aIteration % 100) == 0)
+ {
+ TTime time;
+ time.HomeTime();
+ TDateTime dt = time.DateTime();
+ TBuf<16> tbuf;
+ tbuf.Format(_L("%02d:%02d:%02d.%06d"), dt.Hour(), dt.Minute(), dt.Second(), dt.MicroSecond());
+ RDebug::Print(_L("-----[%S] Test iterations: %d\r\n"), &tbuf, aIteration);
+ }
+ }
+
+//Worker thread function.
+//It behaves as a malicious client. Connects to the FeatMgr server. In each test iteration generates some random values
+//for the function number, handle, IPC arguments. Then sends a command to the server using these
+//randomly generated values. If the server crashes and the thread function receives KErrServerTerminated error,
+//then the thread kills itself and the main thread will get KPanicCategory and KPanicCode as a reason for the
+//worker thread's death. The last set of randomly generated values will be stored in the memory, pointed by aData argument.
+TInt ThreadFunc1(void* aData)
+ {
+ __UHEAP_MARK;
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TTEST(tc != NULL);
+
+ TThreadData* p = static_cast <TThreadData*> (aData);
+ TTEST(p != NULL);
+ TThreadData& data = *p;
+
+ RTestFeatMgrSession sess;
+ TInt err = sess.Connect();
+ TTEST2(err, KErrNone);
+
+ while(++data.iIteration <= KTestIterCount)
+ {
+ RDebug::Print(_L("++++ %d\r\n"), data.iIteration);
+
+ PrintIterationCount(data.iIteration);
+ TIpcArgs args;
+ data.iFunction = Math::Rand(data.iSeed) % (EFeatMgrSWIEnd + 1);//EFeatMgrSWIEnd - the last server message number (without resource checking IPCs))
+ for(TInt i=0;i<KMaxMessageArguments;++i)
+ {
+ //Initialize arguments
+ data.iArgType[i] = static_cast <TArgType> (Math::Rand(data.iSeed) % ELastArgType);
+ switch(data.iArgType[i])
+ {
+ case EIntArgType:
+ data.iIntArg[i] = Math::Rand(data.iSeed) % 9711;
+ args.Set(i, data.iIntArg[i]);
+ break;
+ case ETextArgType:
+ {
+ TInt len = Math::Rand(data.iSeed) % KMaxDesArgLen;
+ data.iTextArg[i].SetLength(len);
+ args.Set(i, &data.iTextArg[i]);
+ }
+ break;
+ case EBinArgType:
+ {
+ TInt len = Math::Rand(data.iSeed) % KMaxDesArgLen;
+ data.iBinArg[i].SetLength(len);
+ args.Set(i, &data.iBinArg[i]);
+ }
+ break;
+ default:
+ User::Panic(KPanicCategory2, KPanicCode2);
+ break;
+ }
+ }
+ //Send arguments
+ User::SetJustInTime(EFalse);
+ TInt err = KErrNone;
+ err = sess.SendReceive(data.iFunction, args);
+ if(err == KErrServerTerminated)
+ {
+ User::Panic(KPanicCategory, KPanicCode);
+ }
+ User::SetJustInTime(ETrue);
+ }
+
+ sess.Close();
+
+ delete tc;
+
+ __UHEAP_MARKEND;
+
+ return KErrNone;
+ }
+
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4065
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void BadClientTest()
+ {
+ TThreadData* p = new TThreadData;
+ TEST(p != NULL);
+ TThreadData& data = *p;
+ data.iFunction = 0;
+ TTime now;
+ now.UniversalTime();
+ data.iSeed = now.Int64();
+
+ _LIT(KThreadName, "WorkThrd");
+
+ for(data.iIteration=0;data.iIteration<KTestIterCount;++data.iIteration)
+ {
+ PrintIterationCount(data.iIteration);
+ //Run the malicious client (one worker theread which will try to crash the FeatMgr server)
+ RThread thread;
+ TEST2(thread.Create(KThreadName, &ThreadFunc1, 0x2000, 0x1000, 0x10000, &data, EOwnerProcess), KErrNone);
+ TRequestStatus status;
+ thread.Logon(status);
+ TEST2(status.Int(), KRequestPending);
+ thread.Resume();
+ User::WaitForRequest(status);
+ User::SetJustInTime(ETrue); // enable debugger panic handling
+ if(thread.ExitType() == EExitPanic)
+ {
+ if(thread.ExitReason() == KPanicCode)
+ {
+ TheTest.Printf(_L("##Server terminated!\r\n"));
+ TheTest.Printf(_L("##Iteration=%d, Function(hex)=%X, Handle=%d\r\n"), data.iIteration, data.iFunction);
+ for(TInt i=0;i<KMaxMessageArguments;++i)
+ {
+ switch(data.iArgType[i])
+ {
+ case EIntArgType:
+ TheTest.Printf(_L("##Arg %d, Integer, value=%d\r\n"), i, data.iIntArg[i]);
+ break;
+ case ETextArgType:
+ TheTest.Printf(_L("##Arg %d, Text, length=%d\r\n"), i, data.iTextArg[i].Length());
+ break;
+ case EBinArgType:
+ TheTest.Printf(_L("##Arg %d, Binary, length=%d\r\n"), i, data.iBinArg[i].Length());
+ break;
+ default:
+ TheTest.Printf(_L("##Arg %d, Invalid argument type: %d\r\n"), i, data.iArgType[i]);
+ break;
+ }
+ }
+ TEST(0);
+ }
+ }
+ thread.Close();
+ }
+ User::SetJustInTime(ETrue); // enable debugger panic handling
+ delete p;
+ }
+
+void DoTestsL()
+ {
+ //TODO: this test won't pass
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4065 Bad client test"));
+ BadClientTest();
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrnotify.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,293 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include <featurecontrol.h>
+#include <featurenotifier.h>
+
+using namespace NFeature;
+
+const TUid KNewFeatureUid = {0x7888ABCD};
+const TUid KNewFeatureUid2 = {0x7888ABCF};
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgrnotify"));
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+_LIT(KFeatureNoChange, "FeatureNoChange");
+_LIT(KFeatureStatusUpdated, "FeatureStatusUpdated");
+_LIT(KFeatureDataUpdated, "FeatureDataUpdated");
+_LIT(KFeatureStatusDataUpdated, "FeatureStatusDataUpdated");
+_LIT(KFeatureRediscover, "FeatureRediscover");
+_LIT(KFeatureCreated, "FeatureCreated");
+_LIT(KFeatureDeleted, "FeatureDeleted");
+
+const TPtrC KNotificationText[] = {KFeatureNoChange(), KFeatureStatusUpdated(), KFeatureDataUpdated(),
+ KFeatureStatusDataUpdated(), KFeatureRediscover(), KFeatureCreated(),
+ KFeatureDeleted()};
+
+class TTestFeatureObserver : public MFeatureObserver
+ {
+public:
+ TTestFeatureObserver() :
+ iType(static_cast <TFeatureChangeType> (-1)),
+ iFeatureUid(KNullUid)
+ {
+ }
+ void SetExpected(TFeatureChangeType aType, TUid aFeatureUid)
+ {
+ iType = aType;
+ iFeatureUid = aFeatureUid;
+ }
+ void Reset()
+ {
+ iType = static_cast <TFeatureChangeType> (-1);
+ iFeatureUid = KNullUid;
+ }
+ virtual void HandleNotifyChange(TFeatureChangeType aType, TFeatureEntry aFeature)
+ {
+ TheTest.Printf(_L("=== HandleNotifyChange() called with aType=\"%S\" and aFeature.FeatureUid()=0x%X\r\n"), &KNotificationText[aType], aFeature.FeatureUid());
+ CActiveScheduler::Stop();
+ TEST2(aType, iType);
+ TEST(aFeature.FeatureUid() == iFeatureUid);
+ }
+ virtual void HandleNotifyError(TInt aError)
+ {
+ TheTest.Printf(_L("=== HandleNotifyError() called with error=%d\r\n"), aError);
+ CActiveScheduler::Stop();
+ TEST2(aError, KErrNone);
+ }
+private:
+ TFeatureChangeType iType;
+ TUid iFeatureUid;
+ };
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+void AddFeature(RFeatureControl& aCtrl, TUid aFeatureUid)
+ {
+ TBitFlags32 flags;
+ flags.ClearAll();
+ flags.Set(EFeatureSupported);
+ flags.Set(EFeatureModifiable);
+ TFeatureEntry fentry(aFeatureUid, flags, 0x0);
+ TInt err = aCtrl.AddFeature(fentry);
+ TEST2(err, KErrNone);
+ }
+
+void DeleteFeature(RFeatureControl& aCtrl, TUid aFeatureUid)
+ {
+ TInt err = aCtrl.DeleteFeature(aFeatureUid);
+ TEST2(err, KErrNone);
+ }
+
+/**
+@SYMTestCaseID PDS-FEATMGR-CT-????
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void NotificationsTest1()
+ {
+ TTestFeatureObserver observer;
+ CFeatureNotifier* notifier = NULL;
+ TRAPD(err, notifier = CFeatureNotifier::NewL(observer));
+ TEST2(err, KErrNone);
+ //Request notification for feature with KNewFeatureUid uid.
+ err = notifier->NotifyRequest(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ err = notifier->NotifyRequest(KNewFeatureUid);
+ TEST2(err, KErrAlreadyExists);
+
+ RFeatureControl ctrl;
+ err = ctrl.Connect();
+ TEST2(err, KErrNone);
+ //Add a feature with KNewFeatureUid uid and check the notification
+ AddFeature(ctrl, KNewFeatureUid);
+ observer.SetExpected(EFeatureFeatureCreated, KNewFeatureUid);
+ CActiveScheduler::Start();
+ //Set the feature status and data and check the notification
+ err = ctrl.SetFeature(KNewFeatureUid, ETrue, 100);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureStatusDataUpdated, KNewFeatureUid);
+ CActiveScheduler::Start();
+ //Set the feature data and check the notification
+ err = ctrl.SetFeature(KNewFeatureUid, 200);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureDataUpdated, KNewFeatureUid);
+ CActiveScheduler::Start();
+ //Enable the feature (it is already enabled) and check the notification
+ err = ctrl.EnableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureNoChange, KNewFeatureUid);//the feature is enabled - no status change
+ CActiveScheduler::Start();
+ //Disable the feature and check the notification
+ err = ctrl.DisableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureStatusUpdated, KNewFeatureUid);
+ CActiveScheduler::Start();
+ //Cancel notifications
+ err = notifier->NotifyCancel(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ err = notifier->NotifyCancel(KNewFeatureUid);
+ TEST2(err, KErrNotFound);
+ //Request notifications again
+ err = notifier->NotifyRequest(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ //Delete the feature and check the notification
+ DeleteFeature(ctrl, KNewFeatureUid);
+ observer.SetExpected(EFeatureFeatureDeleted, KNewFeatureUid);
+ CActiveScheduler::Start();
+ //Cleanup
+ ctrl.Close();
+ delete notifier;
+ }
+
+/**
+@SYMTestCaseID PDS-FEATMGR-CT-????
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void NotificationsTest2()
+ {
+ TTestFeatureObserver observer;
+ CFeatureNotifier* notifier = NULL;
+ TRAPD(err, notifier = CFeatureNotifier::NewL(observer));
+ TEST2(err, KErrNone);
+
+ RFeatureControl ctrl;
+ err = ctrl.Connect();
+ TEST2(err, KErrNone);
+ //Add two features
+ AddFeature(ctrl, KNewFeatureUid);
+ AddFeature(ctrl, KNewFeatureUid2);
+ //Request notifications for the added features. One of them - duplicated in the array.
+ RFeatureUidArray farray;
+ err = farray.Append(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ err = farray.Append(KNewFeatureUid2);
+ TEST2(err, KErrNone);
+ err = farray.Append(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ //
+ err = notifier->NotifyRequest(farray);
+ TEST2(err, KErrNone);
+ //Enable one of the features (already enabled) and check the notification
+ err = ctrl.EnableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureNoChange, KNewFeatureUid);//the feature is enabled - no status change
+ CActiveScheduler::Start();
+ //Disable the second feature and check the notification
+ err = ctrl.DisableFeature(KNewFeatureUid2);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureStatusUpdated, KNewFeatureUid2);
+ CActiveScheduler::Start();
+ //Cancel notifications for the second feature
+ err = notifier->NotifyCancel(KNewFeatureUid2);
+ TEST2(err, KErrNone);
+ //Disable the first feature and check notification
+ err = ctrl.DisableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ observer.SetExpected(EFeatureStatusUpdated, KNewFeatureUid);
+ CActiveScheduler::Start();
+ //Cancel all notifications
+ err = notifier->NotifyCancelAll();
+ TEST2(err, KErrNone);
+ err = notifier->NotifyCancelAll();
+ TEST2(err, KErrNone);
+ //Cleanup
+ farray.Close();
+ ctrl.Close();
+ delete notifier;
+ }
+
+void DoTestsL()
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4066 Notifications test 1"));
+ NotificationsTest1();
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4067 Notifications test 2"));
+ NotificationsTest2();
+
+ delete scheduler;
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgroom.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,669 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <bautils.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include <featurecontrol.h>
+#include <featdiscovery.h>
+#include <featurenotifier.h>
+#include "../../../src/clientdll/featmgrresourcetester.h"
+
+using namespace NFeature;
+
+_LIT( KZOrgFeaturesFile, "Z:\\Private\\10205054\\features.dat" );
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+_LIT( KZFeaturesFile, "C:\\Private\\102836E5\\features.dat" );
+_LIT( KZFeaturesDir, "C:\\Private\\102836E5\\" );
+#else
+_LIT( KZFeaturesFile, "Z:\\Private\\10205054\\features.dat" );
+_LIT( KZFeaturesDir, "Z:\\Private\\10205054\\" );
+#endif // EXTENDED_FEATURE_MANAGER_TEST
+
+const TInt KInvalidFeatureId = 90901671;
+const TUid KInvalidFeatureUid = {KInvalidFeatureId};
+
+static TInt TheProcessHandleCount = 0;
+static TInt TheThreadHandleCount = 0;
+static TInt TheAllocatedCellsCount = 0;
+
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+static const TInt KBurstRate = 20;
+#endif
+
+enum TFeatMgrOomTestMode
+ {
+ EFeatMgrOomServerTestMode,
+ EFeatMgrOomClientTestMode,
+ };
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgroom"));
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static void MarkHandles()
+ {
+ RThread().HandleCount(TheProcessHandleCount, TheThreadHandleCount);
+ }
+
+static void MarkAllocatedCells()
+ {
+ TheAllocatedCellsCount = User::CountAllocCells();
+ }
+
+static void CheckAllocatedCells()
+ {
+ TInt allocatedCellsCount = User::CountAllocCells();
+ TEST2(allocatedCellsCount, TheAllocatedCellsCount);
+ }
+
+static void CheckHandles()
+ {
+ TInt endProcessHandleCount;
+ TInt endThreadHandleCount;
+
+ RThread().HandleCount(endProcessHandleCount, endThreadHandleCount);
+
+ TEST2(TheProcessHandleCount, endProcessHandleCount);
+ TEST2(TheThreadHandleCount, endThreadHandleCount);
+ }
+
+static void OomPreStep(TInt aFailingAllocationNo, TFeatMgrOomTestMode aMode = EFeatMgrOomClientTestMode)
+ {
+ if(aMode == EFeatMgrOomClientTestMode)
+ {
+ MarkHandles();
+ MarkAllocatedCells();
+ __UHEAP_MARK;
+ __UHEAP_SETBURSTFAIL(RAllocator::EBurstFailNext, aFailingAllocationNo, KBurstRate);
+ }
+ else
+ {
+ TFeatMgrResourceTester::Mark();
+ TFeatMgrResourceTester::SetHeapFailure(RHeap::EBurstFailNext, aFailingAllocationNo);
+ }
+ }
+
+static void OomPostStep(TFeatMgrOomTestMode aMode = EFeatMgrOomClientTestMode)
+ {
+ if(aMode == EFeatMgrOomClientTestMode)
+ {
+ __UHEAP_RESET;
+ __UHEAP_MARKEND;
+ CheckAllocatedCells();
+ CheckHandles();
+ }
+ else
+ {
+ TFeatMgrResourceTester::SetHeapFailure(RHeap::ENone, 0);
+ TFeatMgrResourceTester::Check();
+ }
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4068
+@SYMTestCaseDesc Include test case 4069 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void ControlOpenOomTest(TBool aUseConnect)
+ {
+ TInt err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ RFeatureControl ctrl;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo);
+ err = aUseConnect ? ctrl.Connect() : ctrl.Open();
+ ctrl.Close();
+ OomPostStep();
+ }
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ }
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4070
+@SYMTestCaseDesc Include test case 4071-4077 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void ControlFeatureSupportedOomTest(TBool aUseUid, TBool aInvalidFeature, TFeatMgrOomTestMode aMode)
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ const TUid KFeatureUid(aInvalidFeature ? KInvalidFeatureUid : KConnectivity);
+ TFeatureEntry fentry(KFeatureUid);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ err = aUseUid ? ctrl.FeatureSupported(KFeatureUid) : ctrl.FeatureSupported(fentry);
+ OomPostStep(aMode);
+ }
+ ctrl.Close();
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, aInvalidFeature ? KErrNotFound : KFeatureSupported);
+ }
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4078
+@SYMTestCaseDesc Include test case 4079 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void ControlListSupportedFeaturesOomTest(TFeatMgrOomTestMode aMode)
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ const TInt KGranularity = 1;
+ RFeatureUidArray farray(KGranularity);
+ err = ctrl.ListSupportedFeatures(farray);
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ TInt count = farray.Count();
+ TheTest.Printf(_L("===Features count: %d\r\n"), count);
+ TEST(count > 0);
+ }
+ farray.Close();
+ OomPostStep(aMode);
+ }
+ ctrl.Close();
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4080
+@SYMTestCaseDesc Include test case 4081 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void ControlFeaturesSupportedOomTest(TFeatMgrOomTestMode aMode)
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+ RFeatureUidArray farray;
+ err = ctrl.ListSupportedFeatures(farray);
+ TEST2(err, KErrNone);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ RFeatureArray farray2;
+ err = KErrNone;
+ for(TInt i=0;i<farray.Count() && err==KErrNone;++i)
+ {
+ err = farray2.Append(farray[i]);
+ }
+ if(err == KErrNone)
+ {
+ err = ctrl.FeaturesSupported(farray2);
+ }
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ TInt count = farray2.Count();
+ TheTest.Printf(_L("===Features count: %d\r\n"), count);
+ TEST(count > 0);
+ }
+ farray2.Close();
+ OomPostStep(aMode);
+ }
+ farray.Close();
+ ctrl.Close();
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4082
+@SYMTestCaseDesc Include test case 4083 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void ControlAddFeatureOomTest(TFeatMgrOomTestMode aMode)
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ const TUid KNewFeatureUid = {0x7888ABCE};
+ TBitFlags32 flags;
+ flags.Set(EFeatureSupported);
+ flags.Set(EFeatureModifiable);
+ TFeatureEntry fentry(KNewFeatureUid, flags, 0x0);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ err = ctrl.AddFeature(fentry);
+ OomPostStep(aMode);
+ if(err == KErrNoMemory)
+ {
+ err = ctrl.EnableFeature(fentry.FeatureUid());
+ TEST2(err, KErrNotFound);
+ }
+ }
+ TEST2(err, KErrNone);
+ err = ctrl.DeleteFeature(fentry.FeatureUid());
+ TEST2(err, KErrNone);
+
+ ctrl.Close();
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4084
+@SYMTestCaseDesc Include test case 4085 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void ControlDeleteFeatureOomTest(TFeatMgrOomTestMode aMode)
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ const TUid KNewFeatureUid = {0x7888ABCE};
+ TBitFlags32 flags;
+ flags.Set(EFeatureSupported);
+ flags.Set(EFeatureModifiable);
+ TFeatureEntry fentry(KNewFeatureUid, flags, 0x0);
+ err = ctrl.AddFeature(fentry);
+ TEST2(err, KErrNone);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ err = ctrl.DeleteFeature(fentry.FeatureUid());
+ OomPostStep(aMode);
+ if(err == KErrNoMemory)
+ {
+ err = ctrl.EnableFeature(fentry.FeatureUid());
+ TEST2(err, KErrNone);
+ }
+ }
+ TEST2(err, KErrNone);
+
+ ctrl.Close();
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
+/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+class TTestFeatureObserver : public MFeatureObserver
+ {
+ public:
+ virtual void HandleNotifyChange(TFeatureChangeType /*aType*/, TFeatureEntry /*aFeature*/)
+ {
+ }
+ virtual void HandleNotifyError(TInt /*aError*/)
+ {
+ }
+ };
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4086
+@SYMTestCaseDesc Include test case 4087 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void NotifierNewLOomTest(TFeatMgrOomTestMode aMode)
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ TTestFeatureObserver observer;
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ CFeatureNotifier* notifier = NULL;
+ TRAP(err, notifier = CFeatureNotifier::NewL(observer));
+ delete notifier;
+ OomPostStep(aMode);
+ }
+ TEST2(err, KErrNone);
+ ctrl.Close();
+ delete scheduler;
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4088
+@SYMTestCaseDesc Include test case 4089-4091 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void NotifierNotifyRequestOomTest(TBool aInvalidFeature, TFeatMgrOomTestMode aMode)
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ TTestFeatureObserver observer;
+ CFeatureNotifier* notifier = NULL;
+ TRAP(err, notifier = CFeatureNotifier::NewL(observer));
+ TEST2(err, KErrNone);
+
+ const TUid KFeatureUid(aInvalidFeature ? KInvalidFeatureUid : KConnectivity);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ err = notifier->NotifyRequest(KFeatureUid);
+ (void)notifier->NotifyCancelAll();
+ OomPostStep(aMode);
+ }
+ TEST2(err, KErrNone);
+ delete notifier;
+ ctrl.Close();
+ delete scheduler;
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4092
+@SYMTestCaseDesc Include test case 4093 too
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void NotifierNotifyRequestsOomTest(TFeatMgrOomTestMode aMode)
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ TTestFeatureObserver observer;
+ CFeatureNotifier* notifier = NULL;
+ TRAP(err, notifier = CFeatureNotifier::NewL(observer));
+ TEST2(err, KErrNone);
+
+ RFeatureUidArray features;
+ err = features.Append(KConnectivity);
+ TEST2(err, KErrNone);
+ err = features.Append(KFax);
+ TEST2(err, KErrNone);
+ err = features.Append(KConnectivity);
+ TEST2(err, KErrNone);
+ err = features.Append(KLocationManagement);
+ TEST2(err, KErrNone);
+
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo, aMode);
+ err = notifier->NotifyRequest(features);
+ (void)notifier->NotifyCancelAll();
+ OomPostStep(aMode);
+ }
+ TEST2(err, KErrNone);
+ features.Close();
+ delete notifier;
+ ctrl.Close();
+ delete scheduler;
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+void PreTest()
+ {
+ // Connect session
+ RFs fsSession;
+ User::LeaveIfError(fsSession.Connect());
+
+ TEntry entry;
+ TInt err = fsSession.Entry(KZFeaturesDir, entry);
+ if (err == KErrNotFound)
+ {
+ err = fsSession.MkDir(KZFeaturesDir);
+ }
+ TEST2 (err, KErrNone);
+ err = BaflUtils::CopyFile(fsSession, KZOrgFeaturesFile, KZFeaturesDir);
+ TEST2 (err, KErrNone);
+
+ // close file server session
+ fsSession.Close();
+
+ }
+
+void PostTest()
+ {
+ // Connect session
+ RFs fsSession;
+ User::LeaveIfError(fsSession.Connect());
+
+ TEntry entry;
+ TInt err = fsSession.Entry(KZFeaturesDir, entry);
+ if (err == KErrNone)
+ {
+ err = BaflUtils::DeleteFile(fsSession,KZFeaturesFile);
+ TEST2 (err, KErrNone);
+
+ }
+ TEST2 (err, KErrNone);
+
+ // close file server session
+ fsSession.Close();
+ }
+
+void DoTestsL()
+ {
+
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4068 RFeatureControl::Connect() OOM test"));
+ PreTest();
+ ControlOpenOomTest(ETrue);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4069 RFeatureControl::Open() OOM test"));
+ ControlOpenOomTest(EFalse);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4070 RFeatureControl::FeatureSupported(UID) + valid feature, client side OOM test"));
+ ControlFeatureSupportedOomTest(ETrue, EFalse, EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4071 RFeatureControl::FeatureSupported(UID) + valid feature, server side OOM test"));
+ ControlFeatureSupportedOomTest(ETrue, EFalse, EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4072 RFeatureControl::FeatureSupported() + valid feature, client side OOM test"));
+ ControlFeatureSupportedOomTest(EFalse, EFalse, EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4073 RFeatureControl::FeatureSupported() + valid feature, server side OOM test"));
+ ControlFeatureSupportedOomTest(EFalse, EFalse, EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4074 RFeatureControl::FeatureSupported(UID) + invalid feature, client side OOM test"));
+ ControlFeatureSupportedOomTest(ETrue, ETrue, EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4075 RFeatureControl::FeatureSupported(UID) + invalid feature, server side OOM test"));
+ ControlFeatureSupportedOomTest(ETrue, ETrue, EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4076 RFeatureControl::FeatureSupported() + invalid feature, client side OOM OOM test"));
+ ControlFeatureSupportedOomTest(EFalse, ETrue, EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4077 RFeatureControl::FeatureSupported() + invalid feature, server side OOM OOM test"));
+ ControlFeatureSupportedOomTest(EFalse, ETrue, EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4078 RFeatureControl::ListSupportedFeatures(), client side OOM test"));
+ ControlListSupportedFeaturesOomTest(EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4079 RFeatureControl::ListSupportedFeatures(), server side OOM test"));
+ ControlListSupportedFeaturesOomTest(EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4080 RFeatureControl::FeaturesSupported(), client side OOM test"));
+ ControlFeaturesSupportedOomTest(EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4081 RFeatureControl::FeaturesSupported(),server side OOM test"));
+ ControlFeaturesSupportedOomTest(EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4082 RFeatureControl::AddFeature(), client side OOM test"));
+ ControlAddFeatureOomTest(EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4083 RFeatureControl::AddFeature(), server side OOM test"));
+ ControlAddFeatureOomTest(EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4084 RFeatureControl::DeleteFeature(), client side OOM test"));
+ ControlDeleteFeatureOomTest(EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4085 RFeatureControl::DeleteFeature(), server side OOM test"));
+ ControlDeleteFeatureOomTest(EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4086 CFeatureNotifier::NewL(), client side OOM test"));
+ NotifierNewLOomTest(EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4087 CFeatureNotifier::NewL(), server side OOM test"));
+ NotifierNewLOomTest(EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4088 CFeatureNotifier::NotifyRequest(), valid feature, client side OOM test"));
+ NotifierNotifyRequestOomTest(ETrue, EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4089 CFeatureNotifier::NotifyRequest(), valid feature, server side OOM test"));
+ NotifierNotifyRequestOomTest(ETrue, EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4090 CFeatureNotifier::NotifyRequest(), invalid feature, client side OOM test"));
+ NotifierNotifyRequestOomTest(EFalse, EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4091 CFeatureNotifier::NotifyRequest(), invalid feature, server side OOM test"));
+ NotifierNotifyRequestOomTest(EFalse, EFeatMgrOomServerTestMode);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4092 CFeatureNotifier::NotifyRequest(<array>), valid feature, client side OOM test"));
+ NotifierNotifyRequestsOomTest(EFeatMgrOomClientTestMode);
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4093 CFeatureNotifier::NotifyRequest(<array>), valid feature, server side OOM test"));
+ NotifierNotifyRequestsOomTest(EFeatMgrOomServerTestMode);
+
+ PostTest();
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrpanic.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,337 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include "featurepanics.h"
+#include <featurecontrol.h>
+#include <featurenotifier.h>
+
+using namespace NFeature;
+
+static RTest TheTest(_L("t_fmgrpanic"));
+
+_LIT(KPanicCategory, "RFeatureControl");
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Panic thread function.
+//It will cast aData parameter to a TFunctor pointer and call it.
+//The expectation is that the called function will panic and kill the panic thread.
+TInt ThreadFunc(void* aData)
+ {
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TEST(tc != NULL);
+
+ User::SetJustInTime(EFalse); // disable debugger panic handling
+
+ TFunctor* obj = reinterpret_cast<TFunctor*> (aData);
+ TEST(obj != NULL);
+ (*obj)();//call the panic function
+
+ delete tc;
+
+ return KErrNone;
+ }
+
+//Panic test.
+//PanicTest function will create a new thread - panic thread, giving it a pointer to the function which has to
+//be executed and the expectation is that the function will panic and kill the panic thread.
+//PanicTest function will check the panic thread exit code, exit category and the panic code.
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4094
+@SYMTestCaseDesc Include test case 4105 too
+@SYMTestPriority High
+@SYMTestActions PanicTest function will create a new thread - panic
+ thread, giving it a pointer to the function which has to
+ be executed and the expectation is that the function
+ will panic and kill the panic thread.
+ PanicTest function will check the panic thread exit code,
+ exit category and the panic code.
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void PanicTest(TFunctor& aFunctor, TExitType aExpectedExitType, const TDesC& aExpectedCategory, TInt aExpectedPanicCode)
+ {
+ RThread thread;
+ _LIT(KThreadName,"FeatMgrPanicThread");
+ TEST2(thread.Create(KThreadName, &ThreadFunc, 0x2000, 0x1000, 0x10000, (void*)&aFunctor, EOwnerThread), KErrNone);
+
+ TRequestStatus status;
+ thread.Logon(status);
+ TEST2(status.Int(), KRequestPending);
+ thread.Resume();
+ User::WaitForRequest(status);
+ User::SetJustInTime(ETrue); // enable debugger panic handling
+
+ TEST2(thread.ExitType(), aExpectedExitType);
+ TEST(thread.ExitCategory() == aExpectedCategory);
+ TEST2(thread.ExitReason(), aExpectedPanicCode);
+
+ CLOSE_AND_WAIT(thread);
+ }
+
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+////////////////////////////// Panic test functions /////////////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+//1 Panic when calling RFeatureControl::FeatureSupported() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_FeatureSupported1 : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.FeatureSupported(KConnectivity);
+ }
+ };
+static TFeatureControl_NotCreated_FeatureSupported1 TheFeatureControl_NotCreated_FeatureSupported1;
+
+//2 Panic when calling RFeatureControl::FeatureSupported() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_FeatureSupported2 : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ TFeatureEntry fentry;
+ (void)ctrl.FeatureSupported(fentry);
+ }
+ };
+static TFeatureControl_NotCreated_FeatureSupported2 TheFeatureControl_NotCreated_FeatureSupported2;
+
+//Panic when calling RFeatureControl::FeaturesSupported() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_FeaturesSupported : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ RFeatureArray farray;
+ TFeatureEntry fentry;
+ TInt err = farray.Append(fentry);
+ TEST2(err, KErrNone);
+ (void)ctrl.FeaturesSupported(farray);
+ }
+ };
+static TFeatureControl_NotCreated_FeaturesSupported TheFeatureControl_NotCreated_FeaturesSupported;
+
+//Panic when calling RFeatureControl::EnableFeature() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_EnableFeature : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.EnableFeature(KConnectivity);
+ }
+ };
+static TFeatureControl_NotCreated_EnableFeature TheFeatureControl_NotCreated_EnableFeature;
+
+//Panic when calling RFeatureControl::DisableFeature() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_DisableFeature : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.DisableFeature(KConnectivity);
+ }
+ };
+static TFeatureControl_NotCreated_DisableFeature TheFeatureControl_NotCreated_DisableFeature;
+
+//1 Panic when calling RFeatureControl::SetFeature() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_SetFeature1 : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.SetFeature(KConnectivity, EFalse, 0);
+ }
+ };
+static TFeatureControl_NotCreated_SetFeature1 TheFeatureControl_NotCreated_SetFeature1;
+
+//2 Panic when calling RFeatureControl::SetFeature() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_SetFeature2 : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.SetFeature(KConnectivity, 0);
+ }
+ };
+static TFeatureControl_NotCreated_SetFeature2 TheFeatureControl_NotCreated_SetFeature2;
+
+//Panic when calling RFeatureControl::AddFeature() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_AddFeature : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ TFeatureEntry fentry;
+ (void)ctrl.AddFeature(fentry);
+ }
+ };
+static TFeatureControl_NotCreated_AddFeature TheFeatureControl_NotCreated_AddFeature;
+
+//Panic when calling RFeatureControl::DeleteFeature() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_DeleteFeature : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.DeleteFeature(KConnectivity);
+ }
+ };
+static TFeatureControl_NotCreated_DeleteFeature TheFeatureControl_NotCreated_DeleteFeature;
+
+//Panic when calling RFeatureControl::ListSupportedFeatures() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_ListSupportedFeatures : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ RFeatureUidArray farray;
+ (void)ctrl.ListSupportedFeatures(farray);
+ }
+ };
+static TFeatureControl_NotCreated_ListSupportedFeatures TheFeatureControl_NotCreated_ListSupportedFeatures;
+
+//Panic when calling RFeatureControl::SWIStart() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_SWIStart : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.SWIStart();
+ }
+ };
+static TFeatureControl_NotCreated_SWIStart TheFeatureControl_NotCreated_SWIStart;
+
+//Panic when calling RFeatureControl::SWIEnd() on an invalid RFeatureControl object.
+class TFeatureControl_NotCreated_SWIEnd : public TFunctor
+ {
+private:
+ virtual void operator()()
+ {
+ RFeatureControl ctrl;
+ (void)ctrl.SWIEnd();
+ }
+ };
+static TFeatureControl_NotCreated_SWIEnd TheFeatureControl_NotCreated_SWIEnd;
+
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+void DoTestsL()
+ {
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4094 RFeatureControl::FeatureSupported() panic test 1"));
+ PanicTest(TheFeatureControl_NotCreated_FeatureSupported1, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4095 RFeatureControl::FeatureSupported() panic test 2"));
+ PanicTest(TheFeatureControl_NotCreated_FeatureSupported2, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4096 RFeatureControl::FeaturesSupported() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_FeaturesSupported, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4097 RFeatureControl::EnableFeature() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_EnableFeature, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4098 RFeatureControl::DisableFeature() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_DisableFeature, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4099 RFeatureControl::SetFeature() panic test 1"));
+ PanicTest(TheFeatureControl_NotCreated_SetFeature1, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4100 RFeatureControl::SetFeature() panic test 2"));
+ PanicTest(TheFeatureControl_NotCreated_SetFeature2, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4101 RFeatureControl::AddFeature() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_AddFeature, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4102 RFeatureControl::DeleteFeature() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_DeleteFeature, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4103 RFeatureControl::ListSupportedFeatures() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_ListSupportedFeatures, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4104 RFeatureControl::SWIStart() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_SWIStart, EExitPanic, KPanicCategory, EPanicBadHandle);
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4105 RFeatureControl::SWIEnd() panic test"));
+ PanicTest(TheFeatureControl_NotCreated_SWIEnd, EExitPanic, KPanicCategory, EPanicBadHandle);
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrperformance.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,299 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <hal.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include <featurecontrol.h>
+#include <featdiscovery.h>
+
+using namespace NFeature;
+
+TInt TheFastCounterFreq = 0;
+
+const TInt KInvalidFeatureId1 = 90901671;
+const TUid KInvalidFeatureUid1 = {KInvalidFeatureId1};
+const TUid KNewFeatureUid = {0x7888ABC1};
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgrperformance"));
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+TInt TimeDiffUs(TUint32 aStartTicks, TUint32 aEndTicks)
+ {
+ if(TheFastCounterFreq == 0)
+ {
+ TEST2(HAL::Get(HAL::EFastCounterFrequency, TheFastCounterFreq), KErrNone);
+ TheTest.Printf(_L("===Fast counter frequency = %d Hz\r\n"), TheFastCounterFreq);
+ }
+ TInt64 diffTicks = (TInt64)aEndTicks - (TInt64)aStartTicks;
+ if(diffTicks < 0)
+ {
+ diffTicks = KMaxTUint32 + diffTicks + 1;
+ }
+ const TInt KMicroSecIn1Sec = 1000000;
+ TInt us = (diffTicks * KMicroSecIn1Sec) / TheFastCounterFreq;
+ return us;
+ }
+
+void PrintTime(const TDesC& aFmt, TUint32 aStartTicks, TUint32 aEndTicks)
+ {
+ TInt us = TimeDiffUs(aStartTicks, aEndTicks);
+ TheTest.Printf(aFmt, us);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4106
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureControlTest()
+ {
+ TFeatureEntry fentry;
+
+ TUint32 start = User::FastCounter();
+ RFeatureControl ctrl;
+
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+ TUint32 end = User::FastCounter();
+ PrintTime(_L("===1 RFeatureControl::Open(), time=%d us\r\n"), start, end);
+
+ //The second RFeatureControl::Open() call is "free", because only one connection per thread is kept in TLS
+ RFeatureControl ctrl2;
+ start = User::FastCounter();
+ err = ctrl2.Open();
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===2 RFeatureControl::Open(), time=%d us\r\n"), start, end);
+
+ //
+ start = User::FastCounter();
+ ctrl2.Close();
+ end = User::FastCounter();
+ PrintTime(_L("===2 RFeatureControl::Close(), time=%d us\r\n"), start, end);
+
+ //
+ TBitFlags32 flags;
+ flags.ClearAll();
+ flags.Set(EFeatureSupported);
+ flags.Set(EFeatureModifiable);
+
+ fentry = TFeatureEntry(KNewFeatureUid, flags, 0x0);
+ start = User::FastCounter();
+ err = ctrl.AddFeature(fentry);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::AddFeature(), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.FeatureSupported(KNewFeatureUid);
+ TEST2(err, 1);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::FeatureSupported(TUid), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.FeatureSupported(KInvalidFeatureUid1);
+ TEST2(err, KErrNotFound);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::FeatureSupported(invalid TUid), time=%d us\r\n"), start, end);
+ //
+ fentry = TFeatureEntry(KNewFeatureUid);
+ start = User::FastCounter();
+ err = ctrl.FeatureSupported(fentry);
+ TEST2(err, 1);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::FeatureSupported(TFeatureEntry), time=%d us\r\n"), start, end);
+ //
+ RFeatureArray farray;
+ err = farray.Append(TFeatureEntry(KNewFeatureUid));
+ TEST2(err, KErrNone);
+ err = farray.Append(TFeatureEntry(KInvalidFeatureUid1));
+ TEST2(err, KErrNone);
+ err = farray.Append(TFeatureEntry(KConnectivity));
+ TEST2(err, KErrNone);
+ err = farray.Append(TFeatureEntry(KUsb));
+ TEST2(err, KErrNone);
+ start = User::FastCounter();
+ err = ctrl.FeaturesSupported(farray);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::FeaturesSupported(), time=%d us\r\n"), start, end);
+ TEST2(farray.Count(), 3);//KInvalidFeatureUid1 should have been removed from the array
+ farray.Close();
+ //
+ start = User::FastCounter();
+ err = ctrl.DisableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===1 RFeatureControl::DisableFeature(), time=%d us\r\n"), start, end);
+ //Disable the same feature again
+ start = User::FastCounter();
+ err = ctrl.DisableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===2 RFeatureControl::DisableFeature(already disabled), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.DisableFeature(KFax);
+ TEST2(err, KErrAccessDenied);
+ end = User::FastCounter();
+ PrintTime(_L("===3 RFeatureControl::DisableFeature(access denied), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.EnableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===1 RFeatureControl::EnableFeature(), time=%d us\r\n"), start, end);
+ //Enable the same feature again
+ start = User::FastCounter();
+ err = ctrl.EnableFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===2 RFeatureControl::EnableFeature(already enabled), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.EnableFeature(KFax);
+ TEST2(err, KErrAccessDenied);
+ end = User::FastCounter();
+ PrintTime(_L("===3 RFeatureControl::EnableFeature(access denied), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.SetFeature(KNewFeatureUid, EFalse, 100);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===1 RFeatureControl::SetFeature(), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ err = ctrl.SetFeature(KNewFeatureUid, 200);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===2 RFeatureControl::SetFeature(), time=%d us\r\n"), start, end);
+ //
+ RFeatureUidArray farray2;
+ start = User::FastCounter();
+ err = ctrl.ListSupportedFeatures(farray2);
+ TEST2(err, KErrNone);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::ListSupportedFeatures(), time=%d us\r\n"), start, end);
+ TEST(farray2.Count() > 0);
+ farray2.Close();
+ //
+ start = User::FastCounter();
+ ctrl.DeleteFeature(KNewFeatureUid);
+ end = User::FastCounter();
+ PrintTime(_L("===RFeatureControl::DeleteFeature(), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ ctrl.Close();
+ end = User::FastCounter();
+ PrintTime(_L("===1 RFeatureControl::Close(), time=%d us\r\n"), start, end);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4107
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatureManagerTest()
+ {
+ TUint32 start = User::FastCounter();
+ FeatureManager::InitializeLibL();
+ TUint32 end = User::FastCounter();
+ PrintTime(_L("===FeatureManager::InitializeLibL(server already loaded by the previous test), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ TBool rc = FeatureManager::FeatureSupported(KConnectivity.iUid);
+ TEST(rc);
+ end = User::FastCounter();
+ PrintTime(_L("===FeatureManager::FeatureSupported(), time=%d us\r\n"), start, end);
+ //
+ start = User::FastCounter();
+ FeatureManager::UnInitializeLib();
+ end = User::FastCounter();
+ PrintTime(_L("===FeatureManager::UnInitializeLib(), time=%d us\r\n"), start, end);
+ }
+
+void DoTestsL()
+ {
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4106 RFeatureControl performance test"));
+ FeatureControlTest();
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4107 FeatureManager performance test"));
+ FeatureManagerTest();
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrrestoreresponse.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,182 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#include <e32test.h>
+#include <e32debug.h>
+#include <bautils.h>
+#include <featurecontrol.h>
+#include "t_fmgrbursim.h"
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+RTest TheTest(_L("t_fmgrrestoreresponse"));
+
+const TUint threadTimeout = 2000000; // thread timeout = 2 seconds
+
+static RSemaphore MainThreadCrS;
+static TBool featMgrIsResponsive = EFalse;
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine, TBool aPrintThreadName = EFalse)
+ {
+ if(!aValue)
+ {
+ //DeleteTestFiles();
+ if(aPrintThreadName)
+ {
+ RThread th;
+ TName name = th.Name();
+ RDebug::Print(_L("*** Thread %S, Line %d\r\n"), &name, aLine);
+ }
+ else
+ {
+ RDebug::Print(_L("*** Line %d\r\n"), aLine);
+ }
+ TheTest(EFalse, aLine);
+ }
+ }
+
+void Check2(TInt aValue, TInt aExpected, TInt aLine, TBool aPrintThreadName = EFalse)
+ {
+ if(aValue != aExpected)
+ {
+ //DeleteTestFiles();
+ if(aPrintThreadName)
+ {
+ RThread th;
+ TName name = th.Name();
+ RDebug::Print(_L("*** Thread %S, Line %d Expected error: %d, got: %d\r\n"), &name, aLine, aExpected, aValue);
+ }
+ else
+ {
+ RDebug::Print(_L("*** Line %d, Expected error: %d, got: %d\r\n"), aLine, aExpected, aValue);
+ }
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+#define TTEST(arg) ::Check1((arg), __LINE__, ETrue)
+#define TTEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__, ETrue)
+
+// ------------------------- -------------------------
+// setup and cleanup functions
+
+TInt TestThreadL(void*)
+ {
+ __UHEAP_MARK;
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ RFeatureControl rfc;
+ TTEST2( rfc.Connect(), KErrNone );
+
+ // During restore, feature manager server should be responsive and return KErrServerBusy for write request
+ TInt err = rfc.EnableFeature( TUid::Uid(0x00000001) );
+ TTEST2(err, KErrServerBusy);
+
+ // During restore, feature manager server should be responsive and NOT return KErrServerBusy for read request
+ err = rfc.FeatureSupported( TUid::Uid(0x00000001) );
+ TTEST(err != KErrServerBusy);
+
+ rfc.Close();
+ featMgrIsResponsive = ETrue;
+ RDebug::Print(_L("+++:TestThread: Query and Modification completed\r\n"));
+ MainThreadCrS.Signal();
+ delete tc;
+
+ __UHEAP_MARKEND;
+
+ return KErrNone;
+ }
+/**
+@SYMTestCaseID PDS-EFM-CT-4058
+@SYMTestCaseDesc Querying and modifying a feature during restore operation.
+ Verify that a response is returned from the server during restore.
+@SYMTestPriority High
+@SYMTestActions Start simulating restore operation
+ Create a thread that will:
+ Modify a feature and verify that a response (KErrServerBusy) is received
+ Query a feature and verify that a response is received (doesn't matter what the result is)
+ The thread should finished in less than 2 seconds.
+ Otherwise the test fail.
+@SYMTestExpectedResults Test must not fail
+@SYMREQ
+*/
+void TestRestoreResponseL()
+ {
+ _LIT(KThreadName, "RstTh");
+ featMgrIsResponsive = EFalse;
+
+ CFeatMgrBURSim* simulate = CFeatMgrBURSim::NewLC();
+ RThread testThread;
+ TRequestStatus testStatus;
+ CleanupClosePushL( testThread );
+
+ simulate->Simulate_CheckRegFileL();
+
+ // Simulate a restore
+ RDebug::Print(_L("Simulating Restore of FeatMgr\r\n"));
+ simulate->Simulate_StartRestoreL();
+
+ TEST2( testThread.Create(KThreadName, &TestThreadL, 0x2000, 0x1000, 0x10000, NULL, EOwnerProcess), KErrNone );
+ testThread.Logon(testStatus);
+ TEST2( testStatus.Int(), KRequestPending );
+ testThread.Resume();
+ // Wait for 1.5 second for the query thread to finish.
+ RDebug::Print(_L("+++:MainThread: Wait for query and modification completion...\r\n"));
+ MainThreadCrS.Wait(threadTimeout);
+ // If query is responsive within the 1.5 second frame the following check should pass.
+ TEST (featMgrIsResponsive);
+ simulate->Simulate_EndRestoreL();
+
+ CleanupStack::PopAndDestroy(&testThread);
+ CleanupStack::PopAndDestroy(simulate);
+ }
+
+////////////////////////////////////////////////////////////////////////////////////
+void DoTestsL()
+ {
+ MainThreadCrS.CreateLocal(0);
+
+ TheTest.Start(_L(" @SYMTestCaseID:PDS-EFM-CT-4058 Restore Query and Modification Response"));
+ TestRestoreResponseL();
+
+ MainThreadCrS.Close();
+
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrsecurity1.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,144 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include <featurecontrol.h>
+#include <featdiscovery.h>
+
+using namespace NFeature;
+
+const TInt KInvalidFeatureId1 = 90901671;
+const TUid KInvalidFeatureUid1 = {KInvalidFeatureId1};
+
+///////////////////////////////////////////////////////////////////////////////////////
+////// Note: This test has no platsec capabilities. It should not be possible to /////
+////// call platsec protected FeatMgr methods. /////
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgrsecurity1"));
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+/**
+@SYMTestCaseID PDS-FEATMGR-CT-????
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF ????
+*/
+void FeatureControlPlatSecTest()
+ {
+ RFeatureControl ctrl;
+ TInt err = ctrl.Open();
+ TEST2(err, KErrNone);
+
+ err = ctrl.EnableFeature(KConnectivity);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.EnableFeature(KInvalidFeatureUid1);
+ TEST2(err, KErrPermissionDenied);
+
+ err = ctrl.DisableFeature(KConnectivity);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.DisableFeature(KInvalidFeatureUid1);
+ TEST2(err, KErrPermissionDenied);
+
+ err = ctrl.SetFeature(KConnectivity, ETrue, 0);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.SetFeature(KInvalidFeatureUid1, ETrue, 0);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.SetFeature(KConnectivity, 0);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.SetFeature(KInvalidFeatureUid1, 0);
+ TEST2(err, KErrPermissionDenied);
+
+ TFeatureEntry fentry;
+ err = ctrl.AddFeature(fentry);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.DeleteFeature(KConnectivity);
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.DeleteFeature(KInvalidFeatureUid1);
+ TEST2(err, KErrPermissionDenied);
+
+ err = ctrl.SWIStart();
+ TEST2(err, KErrPermissionDenied);
+ err = ctrl.SWIEnd();
+ TEST2(err, KErrPermissionDenied);
+
+ ctrl.Close();
+ }
+
+void DoTestsL()
+ {
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4108 RFeatureControl platsec test"));
+ FeatureControlPlatSecTest();
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrstartup.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,269 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <bautils.h>
+#include "featmgrserver.h"
+#include "featmgrconfiguration.h"
+
+static TInt TheProcessHandleCount = 0;
+static TInt TheThreadHandleCount = 0;
+static TInt TheAllocatedCellsCount = 0;
+
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+static const TInt KBurstRate = 20;
+#endif
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgrstartup"));
+_LIT( KZOrgFeaturesFile, "Z:\\Private\\10205054\\features.dat" );
+#ifdef EXTENDED_FEATURE_MANAGER_TEST
+_LIT( KZFeaturesFile, "C:\\Private\\102836E5\\features.dat" );
+_LIT( KZFeaturesDir, "C:\\Private\\102836E5\\" );
+#else
+_LIT( KZFeaturesFile, "Z:\\Private\\10205054\\features.dat" );
+_LIT( KZFeaturesDir, "Z:\\Private\\10205054\\" );
+#endif // EXTENDED_FEATURE_MANAGER_TEST
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static void MarkHandles()
+ {
+ RThread().HandleCount(TheProcessHandleCount, TheThreadHandleCount);
+ }
+
+static void MarkAllocatedCells()
+ {
+ TheAllocatedCellsCount = User::CountAllocCells();
+ }
+
+static void CheckAllocatedCells()
+ {
+ TInt allocatedCellsCount = User::CountAllocCells();
+ TEST2(allocatedCellsCount, TheAllocatedCellsCount);
+ }
+
+static void CheckHandles()
+ {
+ TInt endProcessHandleCount;
+ TInt endThreadHandleCount;
+
+ RThread().HandleCount(endProcessHandleCount, endThreadHandleCount);
+
+ TEST2(TheProcessHandleCount, endProcessHandleCount);
+ TEST2(TheThreadHandleCount, endThreadHandleCount);
+ }
+
+static void OomPreStep(TInt aFailingAllocationNo)
+ {
+ aFailingAllocationNo = aFailingAllocationNo; //to silent the warning in urel build
+ MarkHandles();
+ MarkAllocatedCells();
+ __UHEAP_MARK;
+ __UHEAP_SETBURSTFAIL(RAllocator::EBurstFailNext, aFailingAllocationNo, KBurstRate);
+ }
+
+static void OomPostStep()
+ {
+ __UHEAP_RESET;
+ __UHEAP_MARKEND;
+ CheckAllocatedCells();
+ CheckHandles();
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static void CreateAndDestroyFeatMgrServerL()
+ {
+ CFeatMgrServer* server = CFeatMgrServer::NewLC(KServerCActivePriority);
+ CleanupStack::PopAndDestroy(server);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4109
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatMgrServerStartupOomTest()
+//TODO - panics in CFeatMgrServer::LoadPluginsL() because the error is KErrNoMemory
+ {
+ TInt err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo);
+ TRAP(err, CreateAndDestroyFeatMgrServerL());
+ OomPostStep();
+ }
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ }
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4110
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void FeatMgrServerStartupFileIoTest()
+ {
+ RFs fs;
+ TInt err = fs.Connect();
+ TEST2(err, KErrNone);
+ err = KErrNotFound;
+ TInt cnt=1;
+ for(;err<KErrNone;++cnt)
+ {
+ TheTest.Printf(_L("===Iteration %d. Simulated error:\r\n"), cnt);
+ for (TInt fsError=KErrNotFound;fsError>=KErrBadName;--fsError)
+ {
+ if(fsError == KErrNotFound || fsError == KErrCorrupt || fsError == KErrPathNotFound || fsError == KErrEof)
+ {
+ continue;//TODO: the server code panics
+ }
+ TheTest.Printf(_L("%d "), fsError);
+ (void)fs.SetErrorCondition(fsError, cnt);
+ TRAP(err, CreateAndDestroyFeatMgrServerL());
+ (void)fs.SetErrorCondition(KErrNone);
+ }
+ TheTest.Printf(_L("\r\n"));
+ }
+ fs.Close();
+ TheTest.Printf(_L("\r\n===File I/O error simulation test succeeded on iteration %d===\r\n"), cnt);
+ }
+
+void PreTest()
+ {
+ // Connect session
+ RFs fsSession;
+ User::LeaveIfError(fsSession.Connect());
+
+ TEntry entry;
+ TInt err = fsSession.Entry(KZFeaturesDir, entry);
+ if (err == KErrNotFound)
+ {
+ err = fsSession.MkDir(KZFeaturesDir);
+ }
+ TEST2 (err, KErrNone);
+ err = BaflUtils::CopyFile(fsSession, KZOrgFeaturesFile, KZFeaturesDir);
+ TEST2 (err, KErrNone);
+
+ // close file server session
+ fsSession.Close();
+
+ }
+
+void PostTest()
+ {
+ // Connect session
+ RFs fsSession;
+ User::LeaveIfError(fsSession.Connect());
+
+ TEntry entry;
+ TInt err = fsSession.Entry(KZFeaturesDir, entry);
+ if (err == KErrNone)
+ {
+ err = BaflUtils::DeleteFile(fsSession,KZFeaturesFile);
+ TEST2 (err, KErrNone);
+
+ }
+ TEST2 (err, KErrNone);
+
+ // close file server session
+ fsSession.Close();
+ }
+
+void DoTestsL()
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4109 CFeatMgrServer::NewLC() OOM test"));
+ PreTest();
+ FeatMgrServerStartupOomTest();
+
+ TheTest.Next(_L("@SYMTestCaseID:PDS-EFM-CT-4110 CFeatMgrServer::NewLC() file I/O error simulation test"));
+ FeatMgrServerStartupFileIoTest();
+ PostTest();
+
+ delete scheduler;
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrswi.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,195 @@
+// 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 "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:
+//
+
+#include <e32test.h>
+#include <f32file.h>
+#include <sacls.h>
+#include <e32property.h>
+#include <featmgr.h>
+#include <featureuids.h>
+#include <featurecontrol.h>
+#include <featdiscovery.h>
+#include "..\src\inc\featmgrconfiguration.h"
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+static RTest TheTest(_L("t_fmgrswi"));
+
+const TUid KNewFeatureUid = {0x7888ABC2};
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+//Deletes all created test files.
+void DestroyTestEnv()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expression evaluated to false. Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DestroyTestEnv();
+ RDebug::Print(_L("*** Expected: %d, got: %d. Line %d\r\n"), aExpected, aValue, aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+TInt KillProcess(const TDesC& aProcessName)
+ {
+ TFullName name;
+ //RDebug::Print(_L("Find and kill \"%S\" process.\n"), &aProcessName);
+ TBuf<64> pattern(aProcessName);
+ TInt length = pattern.Length();
+ pattern += _L("*");
+ TFindProcess procFinder(pattern);
+
+ while (procFinder.Next(name) == KErrNone)
+ {
+ if (name.Length() > length)
+ {//If found name is a string containing aProcessName string.
+ TChar c(name[length]);
+ if (c.IsAlphaDigit() ||
+ c == TChar('_') ||
+ c == TChar('-'))
+ {
+ // If the found name is other valid application name
+ // starting with aProcessName string.
+ //RDebug::Print(_L(":: Process name: \"%S\".\n"), &name);
+ continue;
+ }
+ }
+ RProcess proc;
+ if (proc.Open(name) == KErrNone)
+ {
+ proc.Kill(0);
+ //RDebug::Print(_L("\"%S\" process killed.\n"), &name);
+ }
+ proc.Close();
+ }
+ return KErrNone;
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-CT-4111
+@SYMTestCaseDesc
+@SYMTestPriority High
+@SYMTestActions
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void SWItest()
+ {
+ RFs fs;
+ TInt err = fs.Connect();
+ TEST2(err, KErrNone);
+ //
+ RFeatureControl ctrl;
+ err = ctrl.Open();
+ TEST2(err, KErrNone);
+ //Simulate SWI start
+ err = RProperty::Set(KUidSystemCategory, KSAUidSoftwareInstallKeyValue, ESASwisInstall);
+ TEST2(err, KErrNone);
+ //Notify FeatMgr server that SWI started
+ err = ctrl.SWIStart();
+ TEST2(err, KErrNone);
+ //Add a new persistent feature (using the same SWI connection)
+ TBitFlags32 flags;
+ flags.ClearAll();
+ flags.Set(EFeatureSupported);
+ flags.Set(EFeatureModifiable);
+ flags.Set(EFeaturePersisted);
+ TFeatureEntry fentry(KNewFeatureUid, flags, 9876);
+ err = ctrl.AddFeature(fentry);
+ TEST2(err, KErrNone);
+ //Simulate file I/O error
+ (void)fs.SetErrorCondition(KErrGeneral, 4);
+ //Complete the SWI simulation
+ err = RProperty::Set(KUidSystemCategory, KSAUidSoftwareInstallKeyValue, ESASwisInstall | ESASwisStatusSuccess);
+ TEST2(err, KErrNone);
+ //Notify FeatMgr server that SWI completed
+ err = ctrl.SWIEnd();
+ TEST2(err, KErrNone);
+ //Cleanup
+ ctrl.Close();
+ (void)fs.SetErrorCondition(KErrNone);
+ fs.Close();
+ //Kill FeatMgr server
+ err = KillProcess(KServerProcessName);
+ TEST2(err, KErrNone);
+ //Open new connection
+ err = ctrl.Open();
+ TEST2(err, KErrNone);
+ //The feature should be there
+ TFeatureEntry fentry2(KNewFeatureUid);
+ err = ctrl.FeatureSupported(fentry2);
+ TEST2(err, KFeatureSupported);
+ TEST2(fentry2.FeatureData(), fentry.FeatureData());
+ //Cleanup
+ err = ctrl.DeleteFeature(KNewFeatureUid);
+ TEST2(err, KErrNone);
+ ctrl.Close();
+ }
+
+void DoTestsL()
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ TheTest.Start(_L("@SYMTestCaseID:PDS-EFM-CT-4111 SWI test"));
+ SWItest();
+
+ delete scheduler;
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ DestroyTestEnv();
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/featuremgmt/featuremgr/test/rtest/src/t_fmgrunitrefcount.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,146 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#include <e32test.h>
+#include <e32debug.h>
+#include <bautils.h>
+#include <featmgr/featurecontrol.h>
+#include <featmgr/featmgr.h>
+#include <featdiscovery.h>
+#include "featmgrtlsdata.h"
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+RTest TheTest(_L("t_fmgrunitrefcount test"));
+
+const TUid KDummyFeatUid = {0x12345678};
+
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check1(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ //DeleteTestFiles();
+ RDebug::Print(_L("*** Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+
+void Check2(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ RDebug::Print(_L("*** Line %d, Expected error: %d, got: %d\r\n"), aLine, aExpected, aValue);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check1((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
+
+/**
+@SYMTestCaseID PDS-EFM-UT-4112
+@SYMTestCaseDesc Unit test for client reference counting.
+@SYMTestPriority High
+@SYMTestActions Initialise FeatureManager and check the client reference count
+ Connect using RFeatureControl and check the client reference count
+ Uninitialise FeatureManager and check the client reference count
+ Close RFeatureControl and check the client reference count
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void TestRefCountFeatureManagerL()
+ {
+ RFeatureControl featCtrl;
+
+ CleanupClosePushL(featCtrl);
+ FeatureManager::InitializeLibL();
+ TEST2 (GetClientCount(), 1); // Client count should be 1 at this point
+
+ featCtrl.Connect();
+ TEST2 (GetClientCount(), 2); // Client count should be 2 at this point
+
+ // Both should return same result
+ TEST2 (FeatureManager::FeatureSupported(KDummyFeatUid.iUid), featCtrl.FeatureSupported(KDummyFeatUid)==KFeatureSupported);
+
+ FeatureManager::UnInitializeLib();
+ TEST2 (GetClientCount(), 1); // Client count should be 1 at this point
+
+ CleanupStack::PopAndDestroy(&featCtrl);
+ TEST2 (GetClientCount(), 0); // Client count should be 0 at this point
+ }
+
+/**
+@SYMTestCaseID PDS-EFM-UT-4113
+@SYMTestCaseDesc Unit test for client reference counting.
+@SYMTestPriority High
+@SYMTestActions Create CFeatureDiscovery object and check the client reference count
+ Connect using RFeatureControl and check the client reference count
+ Delete the CFeatureDiscovery object and check the client reference count
+ Close RFeatureControl and check the client reference count
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144262
+*/
+void TestRefCountCFeatureDiscoveryL()
+ {
+ RFeatureControl featCtrl;
+ CleanupClosePushL(featCtrl);
+ CFeatureDiscovery* featDisc = CFeatureDiscovery::NewLC();
+ TEST2 (GetClientCount(), 1); // Client count should be 1 at this point
+ featCtrl.Connect();
+ TEST2 (GetClientCount(), 2); // Client count should be 2 at this point
+
+ // Both should return same result
+ TEST2 (featDisc->IsSupported(KDummyFeatUid), featCtrl.FeatureSupported(KDummyFeatUid)==KFeatureSupported);
+
+ CleanupStack::PopAndDestroy(featDisc);
+ TEST2 (GetClientCount(), 1); // Client count should be 1 at this point
+
+ CleanupStack::PopAndDestroy(&featCtrl);
+ TEST2 (GetClientCount(), 0); // Client count should be 0 at this point
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+void DoTestsL()
+ {
+ TheTest.Start(_L(" @SYMTestCaseID:PDS-EFM-UT-4112 Client Reference Count using FeatureManager"));
+ TestRefCountFeatureManagerL();
+ TheTest.Next(_L(" @SYMTestCaseID:PDS-EFM-UT-4113 Client Reference Count using CFeatureDiscovery"));
+ TestRefCountCFeatureDiscoveryL();
+
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+
+ __UHEAP_MARK;
+
+ TRAPD(err, DoTestsL());
+ TEST2(err, KErrNone);
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- a/featuremgmt/featuremgr/test/tef/tef_efm_bursuite/scripts/tef_efm_bursuite.script Sat Feb 20 00:33:55 2010 +0200
+++ b/featuremgmt/featuremgr/test/tef/tef_efm_bursuite/scripts/tef_efm_bursuite.script Fri Mar 12 15:51:02 2010 +0200
@@ -102,7 +102,7 @@
// -------------------------
-START_TESTCASE SYSLIB-EFM-CT-4047
+//START_TESTCASE SYSLIB-EFM-CT-4047
//! @SYMTestCaseID SYSLIB-EFM-CT-4047
//! @SYMTestCaseDesc Check that feature requests made during a BUR operation are queued and then
//! implemented after the BUR operation has completed. This is to test the queue
@@ -173,13 +173,13 @@
//! on all occasions.
//! @SYMDEF DEF107378
-RUN_TEST_STEP 100 tef_efm_bursuite QueueBackupStep
-RUN_TEST_STEP 100 tef_efm_bursuite QueueRestoreStep
-END_TESTCASE SYSLIB-EFM-CT-4047
+//RUN_TEST_STEP 100 tef_efm_bursuite QueueBackupStep
+//RUN_TEST_STEP 100 tef_efm_bursuite QueueRestoreStep
+//END_TESTCASE SYSLIB-EFM-CT-4047
// -------------------------
-START_TESTCASE SYSLIB-EFM-CT-4048
+//START_TESTCASE SYSLIB-EFM-CT-4048
//! @SYMTestCaseID SYSLIB-EFM-CT-4048
//! @SYMTestCaseDesc To test that a notification occurs when a feature is notified during a BUR operation.
//! This is to test the queue mechanism of the feature manager.
@@ -238,9 +238,9 @@
//! @SYMDEF DEF107378
-RUN_TEST_STEP 100 tef_efm_bursuite NotifyBackupStep
-RUN_TEST_STEP 100 tef_efm_bursuite NotifyRestoreStep
-END_TESTCASE SYSLIB-EFM-CT-4048
+//RUN_TEST_STEP 100 tef_efm_bursuite NotifyBackupStep
+//RUN_TEST_STEP 100 tef_efm_bursuite NotifyRestoreStep
+//END_TESTCASE SYSLIB-EFM-CT-4048
// -------------------------
--- a/persistentstorage/centralrepository/cenrepsrv/obsrvr_noc.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/centralrepository/cenrepsrv/obsrvr_noc.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -312,9 +312,8 @@
if (err==KErrNotFound)
{
//new entry
- TMultiRofsList newEntry(TUid::Uid(uidNum));
- newEntry.iMountFlagList.AppendL(newFlag);
- iMultiRofsUidList.InsertInOrderL(newEntry,reposSortOrder);
+ find.iMountFlagList.AppendL(newFlag);
+ iMultiRofsUidList.InsertInOrderL(find,reposSortOrder);
}
else
{
@@ -453,7 +452,6 @@
and not corrupted
*/
TSettingsAccessPolicy defaultTs=aOverrideRepository->GetDefaultAccessPolicy();
- //lets panic first on debug mode only
//here we panic immediately if there is any defined in the range meta/policy(we can check individually if
//they do override later on,we will assume any definiton of global policy is invalid here
if ( aOverrideRepository->Owner() != aCoreRepository->iSimRep->Owner()
@@ -505,7 +503,10 @@
}
-//Function on initialising a repository of multi ROFS files
+/**Function on initialising a repository of multi ROFS files
+aCoreInitialized indicate whether there is already existing keyspace file in the core layer
+otherwise the first one in the rofs layer will be the core repository
+*/
void CObservable::MergeMultiRofsL(TBool aCoreInitialized,CSharedRepository* aCoreRepository,const RArray<TRofsFlag>& aOverridingFileList)
{
//load all the files and construct an array of CHeapRepository to merge content into it
@@ -530,7 +531,8 @@
CIniFileIn* iniFile;
TInt err=CIniFileIn::NewLC(TServerResources::iFs,iniFile,repFileName);
User::LeaveIfError(err);
- aCoreRepository->ReloadContentL(*iniFile,ETrue);
+ err=aCoreRepository->ReloadContentL(*iniFile,ETrue);
+ User::LeaveIfError(err);
CleanupStack::PopAndDestroy(iniFile);//iniFile
}
else
--- a/persistentstorage/centralrepository/cenrepsrv/shrepos.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/centralrepository/cenrepsrv/shrepos.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -496,6 +496,8 @@
The current repository must be emptied (or must be empty already) before the call is made.
@param aIniFile A reference to CIniFileIn object, which will be used to load
the repository content.
+@param aFirstLoad is used to indicate whether the file is reloaded for first time, this is used to prevent
+notification if not needed. For example file loading for merging purpose will not result in notification
@return KErrCorrupt Corrupted repository file.
KErrNone The repository content was seccessfully loaded into memory.
KErrNotFound Setting not found in the file.
--- a/persistentstorage/centralrepository/cenrepsrv/srvrepos_noc.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/centralrepository/cenrepsrv/srvrepos_noc.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -80,11 +80,9 @@
/**
Attempt to reset a single key to it's value in the file in the given location. Routine
attempts to find a .cre file first. If ( and only if ) a cre file doesn't exist the
-routine attempts to find a txt file.
-Note that it would be possible to use LoadRepositoryLC here but for the txt file
-that would take longer. This is because in LoadRepositoryLC the txt file is
-completely processed. The Reset specific txt file opening code below is quicker because
-it is just attempting to find the reset key.
+routine attempts to find a txt file. In the presence of multi rofs, it needs to perform
+merging of all the rom keyspaces first before doing a reset, hence we are not able to perform
+the reading line by line for efficiency purpose.
*/
#ifdef SYMBIAN_CENTREP_SUPPORT_MULTIROFS
void CServerRepository::ResetFromIniFileL(TUint32 aId,
@@ -113,6 +111,15 @@
CleanupStack::PopAndDestroy(rep);
}
#else
+/**
+Attempt to reset a single key to it's value in the file in the given location. Routine
+attempts to find a .cre file first. If ( and only if ) a cre file doesn't exist the
+routine attempts to find a txt file.
+Note that it would be possible to use LoadRepositoryLC here but for the txt file
+that would take longer. This is because in LoadRepositoryLC the txt file is
+completely processed. The Reset specific txt file opening code below is quicker because
+it is just attempting to find the reset key.
+*/
void CServerRepository::ResetFromIniFileL(TUint32 aId,
TCentRepLocation aLocation,
TBool& aKeyFound)
@@ -448,7 +455,9 @@
TServerResources::iObserver->LoadRepositoryLC(uid, ETrue, defaultRepository, CIniFileIn::EInstallOnly);
}
else
- {
+ {
+ // The repository must exist in the ROM or install directory (or both).
+ ASSERT(romExists || installExists);
// Reset against empty repository if neither ROM or install file are found
defaultRepository = CSharedRepository::NewL(uid);
CleanupStack::PushL(defaultRepository);
--- a/persistentstorage/dbms/tdbms/t_dbood.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/dbms/tdbms/t_dbood.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -191,6 +191,10 @@
static void SetupTestDirectory()
{
TInt err = TheFs.MkDir(KTestDatabase);
+ if(err != KErrNone)
+ {
+ RDebug::Print(_L("*** SetupTestDirectory(), RFs::MkDir(), err=%d\r\n"), err);
+ }
TEST(err == KErrNone || err == KErrAlreadyExists);
}
--- a/persistentstorage/sql/GROUP/BLD.INF Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/GROUP/BLD.INF Fri Mar 12 15:51:02 2010 +0200
@@ -102,6 +102,11 @@
t_sqlauthorizer.mmp
t_sqlfilebuf64.mmp
t_sqldb64.mmp manual
+t_sqlstartup.mmp
+#ifndef WINS //hardware only
+t_sqlfilesrvcrash1.mmp manual
+t_sqlfilesrvcrash2.mmp manual
+#endif
t_sqlenvdestroy.mmp
--- a/persistentstorage/sql/GROUP/sqltests.bat Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/GROUP/sqltests.bat Fri Mar 12 15:51:02 2010 +0200
@@ -58,4 +58,5 @@
T_SQLBLOB.EXE
T_SQLFILEBUF64.EXE
T_SQLAUTHORIZER.EXE
+T_SQLSTARTUP.EXE
T_SQLENVDESTROY.EXE
--- a/persistentstorage/sql/GROUP/sqltests.iby Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/GROUP/sqltests.iby Fri Mar 12 15:51:02 2010 +0200
@@ -103,7 +103,10 @@
file=ABI_DIR\BUILD_DIR\T_SQLBLOB.EXE \TEST\T_SQLBLOB.EXE
file=ABI_DIR\BUILD_DIR\T_SQLAUTHORIZER.EXE \TEST\T_SQLAUTHORIZER.EXE
file=ABI_DIR\BUILD_DIR\T_SQLFILEBUF64.EXE \TEST\T_SQLFILEBUF64.EXE
-file=ABI_DIR\BUILD_DIR\T_SQLDB64.EXE \TEST\T_SQLDB64.EXE
+file=ABI_DIR\BUILD_DIR\T_SQLSTARTUP.EXE \TEST\T_SQLSTARTUP.EXE
+file=ABI_DIR\BUILD_DIR\T_SQLDB64.EXE \TEST\T_SQLDB64.EXE
+file=ABI_DIR\BUILD_DIR\T_SQLFILESRVCRASH1.EXE \TEST\T_SQLFILESRVCRASH1.EXE
+file=ABI_DIR\BUILD_DIR\T_SQLFILESRVCRASH2.EXE \TEST\T_SQLFILESRVCRASH2.EXE
file=ABI_DIR\BUILD_DIR\T_SQLENVDESTROY.EXE \TEST\T_SQLENVDESTROY.EXE
#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/persistentstorage/sql/GROUP/t_sqlfilesrvcrash1.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,32 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+TARGET t_sqlfilesrvcrash1.exe
+TARGETTYPE exe
+CAPABILITY All -TCB
+
+USERINCLUDE .
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../TEST
+SOURCE t_sqlfilesrvcrash1.cpp
+
+LIBRARY euser.lib
+LIBRARY sqldb.lib
+LIBRARY efsrv.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/persistentstorage/sql/GROUP/t_sqlfilesrvcrash2.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,33 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+#include "sqlite_macro.mmh"
+
+TARGET t_sqlfilesrvcrash2.exe
+TARGETTYPE exe
+CAPABILITY NONE
+
+USERINCLUDE .
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+
+SOURCEPATH ../TEST
+SOURCE t_sqlfilesrvcrash2.cpp
+
+LIBRARY euser.lib
+LIBRARY sqldb.lib
+LIBRARY efsrv.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
\ No newline at end of file
--- a/persistentstorage/sql/GROUP/t_sqlfserr.mmp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/GROUP/t_sqlfserr.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -44,6 +44,7 @@
LIBRARY hal.lib
STATICLIBRARY sqlite.lib
+UID 0 0x212A2C27
VENDORID 0x70000001
SMPSAFE
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/persistentstorage/sql/GROUP/t_sqlstartup.mmp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,81 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+TARGET t_sqlstartup.exe
+TARGETTYPE EXE
+CAPABILITY ProtServ AllFiles
+
+EPOCFIXEDPROCESS
+
+#ifdef WINSCW
+EPOCHEAPSIZE 0x00020000 0x00600000
+#else
+EPOCHEAPSIZE 0x00020000 0x02000000
+#endif
+
+EPOCSTACKSIZE 0x3000
+
+UID 0 0x10281E17
+
+MACRO SQLSRV_STARTUP_TEST
+
+USERINCLUDE .
+USERINCLUDE ../INC
+USERINCLUDE ../SRC/Common
+USERINCLUDE ../SRC/Common/IPC
+USERINCLUDE ../SRC/Common/Trace
+USERINCLUDE ../SRC/Server
+USERINCLUDE ../SRC/Server/Compact
+USERINCLUDE ../SRC/Server/IPC
+USERINCLUDE ../SRC/Security
+USERINCLUDE ../SQLite
+USERINCLUDE ../OsLayer
+OS_LAYER_SYSTEMINCLUDE_SYMBIAN
+OS_LAYER_ESTLIB_SYSTEMINCLUDE
+
+SOURCEPATH ../TEST
+SOURCE t_sqlstartup.cpp
+
+SOURCEPATH ../SRC/Common
+SOURCE SqlBufFlat.cpp
+SOURCE SqlUtil.cpp
+
+SOURCEPATH ../SRC/Server
+SOURCE SqlBur.cpp
+SOURCE SqlSrvConfig.cpp
+SOURCE SqlSrvMain.cpp
+SOURCE SqlSrvDriveSpace.cpp
+SOURCE SqlSrvStrings.cpp
+SOURCE SqlSrvStatementUtil.cpp
+SOURCE SqlSrvSecurityMap.cpp
+SOURCE SqlSrvUtil.cpp
+
+SOURCEPATH ../SRC/Server/Compact
+SOURCE SqlCompact.cpp
+SOURCE SqlCompactConn.cpp
+SOURCE SqlCompactEntry.cpp
+SOURCE SqlCompactTimer.cpp
+
+LIBRARY estlib.lib
+LIBRARY hal.lib
+LIBRARY euser.lib
+LIBRARY efsrv.lib
+LIBRARY estor.lib
+LIBRARY abclient.lib
+STATICLIBRARY sqlite.lib
+
+VENDORID 0x70000001
+
+SMPSAFE
--- a/persistentstorage/sql/INC/SqlDb.h Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/INC/SqlDb.h Fri Mar 12 15:51:02 2010 +0200
@@ -167,6 +167,10 @@
Note that in the cases where an 'overriding' security policy was not originally assigned,
then the security policy returned will simply be the default security policy.
+Note: The database security policies are used to control the access to the objects (tables, indexes, triggers, views)
+in the main database. The access to the temporary tables, indexes, etc. is not a subject of any restrictions, e.g.
+a client with "read" database security policy only can create and use temporary tables, views, indexes, triggers.
+
@see TSecurityPolicy
@see RSqlDatabase
@see RSqlSecurityPolicy::SetDbPolicy()
--- a/persistentstorage/sql/OsLayer/FileBuf64.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/OsLayer/FileBuf64.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -192,44 +192,6 @@
#endif//_DEBUG
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-/////////////////////////// MFileInitializer64 /////////////////////////////////////////////////////////////
-//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-
-/**
-MFileInitializer64 interface provides only one abstract method - Init() that is used during the initialization of
-the RFileBuf64 objects.
-Here is what is the problem MFileInitializer64 tries to solve.
-RFileBuf64 has 4 different "resource acquisition" methods - Create(), Open(), Temp() and AdoptFromClient().
-They perform different actions and have different input arguments.
-This is the variable part of the RFileBuf64 initialization.
-Apart from that, RFileBuf64 has a "fixed" initialization part that does not change whatever the variable part is.
-If MFileInitializer64 interface is not used then the following chunk of code has to be duplicated 4 times:
-@code
- TInt err = do_fixed_init();
- if(err == KErrNone)
- {
- err = do_variable_init();
- if(err != KErrNone)
- {
- revert_fixed_init();
- }
- }
- return err;
-@endcode
-In order to avoid the code duplication, the fixed part of the initialization is moved to RFileBuf64::DoInit(), which
-is given a reference to a MFileInitializer64 derived class that performas the variable part of the initialization.
-4 different MFileInitializer64 derived classes are provided for the 4 different "resource acquisition" methods.
-All they store the variable part of the RFileBuf64 initialization parameters and implement MFileInitializer64::Init().
-
-@see RFileBuf64::DoInit()
-@internalComponent
-*/
-struct MFileInitializer64
- {
- virtual TInt Init(RFile64& aFile) = 0;
- };
-
-//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////// RFileBuf64 /////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@@ -262,7 +224,6 @@
@see TFileMode
@see RFile64::Create()
-@see MFileInitializer64
@panic FBuf64 7 In _DEBUG mode - Invalid aFs object (null file session handle).
@panic FBuf64 10 In _DEBUG mode - Invalid file name length (zero file name length).
@@ -272,24 +233,12 @@
__FBUF64_ASSERT(aFs.Handle() != 0, EFBufPanicFsHandle);
__FBUF64_ASSERT(aFileName.Length() > 0, EFBufPanicFileNameLen);
- struct TFileCreateInitializer64 : public MFileInitializer64
- {
- inline TFileCreateInitializer64(RFs& aFs, const TDesC& aFileName, TUint aFileMode) :
- iFs(aFs),
- iFileName(aFileName),
- iFileMode(aFileMode)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.Create(iFs, iFileName, iFileMode);
- }
- RFs& iFs;
- const TDesC& iFileName;
- TUint iFileMode;
- } initializer(aFs, aFileName, aFileMode);
-
- return DoInit(initializer);
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.Create(aFs, aFileName, aFileMode);
+ }
+ return DoPostInit(err);
}
/**
@@ -306,7 +255,6 @@
@see TFileMode
@see RFile64::Open()
-@see MFileInitializer64
@panic FBuf64 7 In _DEBUG mode - Invalid aFs object (null file session handle).
@panic FBuf64 10 In _DEBUG mode - Invalid file name length (zero file name length).
@@ -316,24 +264,12 @@
__FBUF64_ASSERT(aFs.Handle() != 0, EFBufPanicFsHandle);
__FBUF64_ASSERT(aFileName.Length() > 0, EFBufPanicFileNameLen);
- struct TFileOpenInitializer64 : public MFileInitializer64
- {
- inline TFileOpenInitializer64(RFs& aFs, const TDesC& aFileName, TUint aFileMode) :
- iFs(aFs),
- iFileName(aFileName),
- iFileMode(aFileMode)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.Open(iFs, iFileName, iFileMode);
- }
- RFs& iFs;
- const TDesC& iFileName;
- TUint iFileMode;
- } initializer(aFs, aFileName, aFileMode);
-
- return DoInit(initializer);
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.Open(aFs, aFileName, aFileMode);
+ }
+ return DoPostInit(err);
}
/**
@@ -352,7 +288,6 @@
@see TFileMode
@see RFile64::Temp()
-@see MFileInitializer64
@panic FBuf64 7 In _DEBUG mode - Invalid aFs object (null file session handle).
*/
@@ -360,26 +295,12 @@
{
__FBUF64_ASSERT(aFs.Handle() != 0, EFBufPanicFsHandle);
- struct TFileTempInitializer64 : public MFileInitializer64
- {
- inline TFileTempInitializer64(RFs& aFs, const TDesC& aPath, TFileName& aFileName, TUint aFileMode) :
- iFs(aFs),
- iPath(aPath),
- iFileName(aFileName),
- iFileMode(aFileMode)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.Temp(iFs, iPath, iFileName, iFileMode);
- }
- RFs& iFs;
- const TDesC& iPath;
- TFileName& iFileName;
- TUint iFileMode;
- } initializer(aFs, aPath, aFileName, aFileMode);
-
- return DoInit(initializer);
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.Temp(aFs, aPath, aFileName, aFileMode);
+ }
+ return DoPostInit(err);
}
/**
@@ -398,7 +319,6 @@
@see TFileMode
@see RFile64::AdoptFromClient()
-@see MFileInitializer64
@see KMaxMessageArguments
@panic FBuf64 8 In _DEBUG mode - Invalid aMsg object (null message handle).
@@ -411,24 +331,12 @@
__FBUF64_ASSERT(aFsIndex >= 0 && aFsIndex < KMaxMessageArguments, EFBufPanicMsgIndex);
__FBUF64_ASSERT(aFileIndex >= 0 && aFileIndex < KMaxMessageArguments, EFBufPanicMsgIndex);
- struct TFileAdoptInitializer64 : public MFileInitializer64
- {
- inline TFileAdoptInitializer64(const RMessage2& aMsg, TInt aFsIndex, TInt aFileIndex) :
- iMsg(aMsg),
- iFsIndex(aFsIndex),
- iFileIndex(aFileIndex)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.AdoptFromClient(iMsg, iFsIndex, iFileIndex);
- }
- const RMessage2& iMsg;
- TInt iFsIndex;
- TInt iFileIndex;
- } initializer(aMsg, aFsIndex, aFileIndex);
-
- return DoInit(initializer);
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.AdoptFromClient(aMsg, aFsIndex, aFileIndex);
+ }
+ return DoPostInit(err);
}
/**
@@ -452,6 +360,16 @@
/**
Calculates and sets optimal read-ahead buffer size.
+aBlockSize and aReadRecBufSize values are retrieved by the caller from the file system.
+
+Initialization rules:
+Rule 1: If aReadRecBufSize is positive, bigger than the default read-ahead and
+ a power of two then the read-ahead value will be
+ initialized with aReadRecBufSize (if aReadRecBufSize is less than the buffer capacity otherwise
+ the buffer capacity will be used as a read-ahead value).
+Rule 2: If rule#1 is not applicable then the same checks, as in rule#1, are performed this time for aBlockSize.
+ If aBlockSize passes the checks then it will be used as a read-ahead value.
+
@param aBlockSize The size of a file block in bytes
@param aReadRecBufSize The recommended buffer size for optimised reading performance
@@ -516,7 +434,7 @@
TInt len = aDes.MaxLength();
if(len > iCapacity)
{
- if((aFilePos + len) > iFilePos && !(aFilePos >= (iFilePos + iLength)))
+ if((aFilePos + len) > iFilePos && aFilePos < (iFilePos + iLength))
{//Write the pending data if the iDirty flag is set, otherwise preserve the buffer content.
err = DoFileWrite1(aFilePos);
}
@@ -532,13 +450,13 @@
TUint8* outptr = const_cast <TUint8*> (aDes.Ptr());
while(len > 0 && err == KErrNone && aFilePos < iFileSize)
{
- //1. If part of all of the data is in the buffer - copy the data to the target location
+ //1. If part or all of the data is in the buffer - copy the data to the target location
if(aFilePos >= iFilePos && aFilePos < (iFilePos + iLength))
{
- TInt l = Min(len, (iFilePos + iLength - aFilePos));
- outptr = Mem::Copy(outptr, iBase + (aFilePos - iFilePos), l);
- len -= l;
- aFilePos += l;
+ TInt blocklen = Min(len, (iFilePos + iLength - aFilePos));
+ outptr = Mem::Copy(outptr, iBase + (aFilePos - iFilePos), blocklen);
+ len -= blocklen;
+ aFilePos += blocklen;
}
//2. Perform a read-ahead operation
else
@@ -550,7 +468,7 @@
break;
}
if(iNextReadFilePos != aFilePos)
- {//Direct "file read" operation
+ {//Guessed read ahead was wrong. Direct "file read" operation
iNextReadFilePosHits = 0;
TPtr8 ptr2(outptr, len);
err = iFile.Read(aFilePos, ptr2);
@@ -804,31 +722,38 @@
}
/**
-Performs the fixed part of the RFileBuf64 initialization and then calls MFileInitializer64::Init() to perform
-the variable part of the initialization.
+Initializes RFileBuf64 data members with their initial values.
+Allocates memory for the file buffer.
+
+@return KErrNone if successful,
+ KErrNoMemory out of memory;
+*/
+TInt RFileBuf64::DoPreInit()
+ {
+ DoDiscard();
+ iReadAheadSize = RFileBuf64::KDefaultReadAheadSize;
+ iBase = static_cast <TUint8*> (User::Alloc(iCapacity));
+ return iBase ? KErrNone : KErrNoMemory;
+ }
-@param aFileInitializer A reference to an initializer object that implements MFileInitializer64::Init()
+/**
+Performs post-initialization of the RFileBuf64 object.
+If aInitErr is not KErrNone, then the buffer memory will be released.
+The function returns the aInitErr value to the caller.
+@param aInitErr The result of the performed before the call RFileBuf64 initialization.
+
@return KErrNone if successful, otherwise one of the other system-wide error codes.
*/
-TInt RFileBuf64::DoInit(MFileInitializer64& aFileInitializer)
- {
- DoDiscard();
- iReadAheadSize = RFileBuf64::KDefaultReadAheadSize;
- TInt err = KErrNoMemory;
- iBase = static_cast <TUint8*> (User::Alloc(iCapacity));
- if(!iBase)
- {
- return KErrNoMemory;
- }
- err = aFileInitializer.Init(iFile);
- if(err != KErrNone)
- {
- User::Free(iBase);
- iBase = 0;
- }
- return err;
- }
+TInt RFileBuf64::DoPostInit(TInt aInitErr)
+ {
+ if(aInitErr != KErrNone)
+ {
+ User::Free(iBase);
+ iBase = 0;
+ }
+ return aInitErr;
+ }
/**
Discards the content of the RFileBuf64 object returning it to the state as if it has just been created.
--- a/persistentstorage/sql/OsLayer/FileBuf64.h Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/OsLayer/FileBuf64.h Fri Mar 12 15:51:02 2010 +0200
@@ -18,9 +18,6 @@
#include <f32file.h>
#include <f32file64.h>
-//Forward declaration
-struct MFileInitializer64;
-
/**
The RFileBuf64 class provides buffered file read/write operations on a single RFile64 object.
RFileBuf64::Read() and RFileBuf64::Write() methods may boost the performance of the read/write file operations up to 30%
@@ -47,37 +44,41 @@
In details, to create a file and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.Create(fs, <file name>, <file mode>);
+ err = fbuf.Create(fs, <file name>, <file mode>);
//check the error
To open an existing file and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.Open(fs, <file name>, <file mode>);
+ err = fbuf.Open(fs, <file name>, <file mode>);
//check the error
To create a temporary file and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.Temp(fs, <path>, <file name>, <file mode>);
+ err = fbuf.Temp(fs, <path>, <file name>, <file mode>);
//check the error
To open a file from handle and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.AdoptFromClient(<msg>, <fs handle index>, <file handle index>);
+ err = fbuf.AdoptFromClient(<msg>, <fs handle index>, <file handle index>);
//check the error
- if the RFileBuf64 object is initialised successfully, now the public RFileBuf64 methods can be called to perform
@@ -99,7 +100,7 @@
@endcode
Implementation notes: the current RFileBuf64 implementation is optimised for use by the SQLite OS porting layer.
- After a detailed investigation of the performed by SQLite file read/write operations it was found that buffering of
+ After investigation of SQLite file read/write operations it was found that buffering of
two or more logical file writes into a single physical file write has a positive impact (as expected) on the performance
of the database write operations. But the picture is quite different for the file read operations. The database data is
organised in pages with fixed size. After a database is created and set of insert/update/delete operations is performed
@@ -160,7 +161,8 @@
private:
void Invariant() const;
- TInt DoInit(MFileInitializer64& aFileInitializer);
+ TInt DoPreInit();
+ TInt DoPostInit(TInt aInitErr);
void DoDiscard();
TInt DoFileSize();
TInt DoSetFileSize(TInt64 aFileSize);
--- a/persistentstorage/sql/OsLayer/os_symbian.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/OsLayer/os_symbian.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -700,11 +700,7 @@
TFileName iSysPrivDir;//"<system drive>:\" + process's private data path. Initialized in sqlite3SymbianFsOpen().
//Used for storing sqlite temporary files.
TInt64 iSeed;
- RAllocator* iAllocator;
- enum {KZeroBufSize = SQLITE_DEFAULT_SECTOR_SIZE};
- TBuf8<KZeroBufSize> iZeroBuf;
-
private:
static COsLayerData* iOsLayerData;
TInt iStoredOsErrorCode; //Contains the last OS error code.
@@ -712,6 +708,17 @@
TBool iReadOnly; //Fh data
};
+/**
+This functon returns a reference to the current thread allocator object.
+The static RAllocator& variable will be initialized once at the moment when the function is called for
+first time.
+*/
+static RAllocator& Allocator()
+ {
+ static RAllocator& allocator = User::Allocator();
+ return allocator;
+ }
+
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////// TDbFile struct declaration /////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@@ -1042,7 +1049,6 @@
Initializes the COsLayerData data members with their default values.
*/
inline COsLayerData::COsLayerData() :
- iAllocator(0),
iStoredOsErrorCode(KErrNone),
iMessage(0),
iReadOnly(EFalse)
@@ -1050,7 +1056,6 @@
TTime now;
now.UniversalTime();
iSeed = now.Int64();
- iZeroBuf.FillZ(COsLayerData::KZeroBufSize);
}
/**
@@ -1084,7 +1089,6 @@
*/
TInt COsLayerData::DoCreate()
{
- iAllocator = &User::Allocator();
__FS_CALL(EFsOpFsConnect, 0);
TInt err = iFs.Connect();
if(err != KErrNone)
@@ -1447,8 +1451,7 @@
SQLite OS porting layer API.
Closes the file referred by aDbFile parameter.
-If aDbFile, which is actually a pointer to a TDbFile instance, the iFullName data member is not NULL,
-then the file will be deleted.
+If aDbFile.iFullName data member is not NULL, then the file will be deleted.
@param aDbFile A pointer to a TDbFile instance, than contains the file handle to be closed.
@@ -1465,7 +1468,8 @@
__FS_CALL(EFsOpFileClose, 0);
dbFile.iFileBuf.Close();
if(dbFile.iFullName)
- {
+ {//"iFullName" will not be NULL only when TVfs::Open() is called with SQLITE_OPEN_DELETEONCLOSE flag.
+ //That means - SQlite expects the file to be deleted after the file close operation.
__FS_CALL(EFsOpFileDelete, 0);
(void)COsLayerData::Instance().iFs.Delete(*dbFile.iFullName);
delete dbFile.iFullName;
@@ -2301,6 +2305,11 @@
dbFile.iFileBuf.Close();
delete dbFile.iFullName;
dbFile.iFullName = NULL;
+ if(!aFileName && fname.Length() > 0)
+ {//temporary file, the error is not KErrNone. Then delete the file (after a successfull
+ //temporary file creation there could be a failed memory allocation)
+ (void)osLayerData.iFs.Delete(fname);
+ }
}
else
{
@@ -2614,7 +2623,7 @@
extern "C" void* sqlite3SymbianMalloc(size_t aSize)
{
__MEM_CALL(EMemOpAlloc, aSize, 0);
- return COsLayerData::Instance().iAllocator->Alloc(aSize);
+ return Allocator().Alloc(aSize);
}
/**
@@ -2627,10 +2636,10 @@
extern "C" void* sqlite3SymbianRealloc(void* aPtr, size_t aSize)
{
#ifdef _SQLPROFILER
- TInt size = COsLayerData::Instance().iAllocator->AllocLen(aPtr);
+ TInt size = Allocator().AllocLen(aPtr);
__MEM_CALL(EMemOpRealloc, aSize, size);
#endif
- return COsLayerData::Instance().iAllocator->ReAlloc(aPtr, aSize);
+ return Allocator().ReAlloc(aPtr, aSize);
}
/**
@@ -2643,10 +2652,10 @@
extern "C" void sqlite3SymbianFree(void* aPtr)
{
#ifdef _SQLPROFILER
- TInt size = COsLayerData::Instance().iAllocator->AllocLen(aPtr);
+ TInt size = Allocator().AllocLen(aPtr);
__MEM_CALL(EMemOpFree, size, 0);
#endif
- COsLayerData::Instance().iAllocator->Free(aPtr);
+ Allocator().Free(aPtr);
}
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
--- a/persistentstorage/sql/SRC/Client/SqlDbSession.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Client/SqlDbSession.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -303,7 +303,11 @@
*/
TInt RSqlDbSession::Connect(TSqlSrvFunction aFunction, const TDesC& aDbFileName, const TDesC8& aSecurityPolicyData, const TDesC8* aConfig)
{
+#ifdef SYSLIBS_TEST
+ const TInt KDefaultMsgBufLen = 4;
+#else
const TInt KDefaultMsgBufLen = 128;
+#endif
iLastErrorMessage = HBufC::New(KDefaultMsgBufLen);
if(!iLastErrorMessage)
{
--- a/persistentstorage/sql/SRC/Client/SqlStatementImpl.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Client/SqlStatementImpl.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -652,10 +652,15 @@
}
TPtr8 ptr(reinterpret_cast <TUint8*> (const_cast <TUint16*> (aDest.Ptr())), aDest.MaxLength() * sizeof(TUint16));
err = iSqlStmtSession.ReadColumnValue(aColumnIndex, ptr);
- if(err == KErrNone || err == KErrOverflow)
- {
- aDest.SetLength(ptr.Length() / sizeof(TUint16));
- }
+ switch(err)
+ {
+ case KErrNone:
+ case KErrOverflow:
+ aDest.SetLength(ptr.Length() / sizeof(TUint16));
+ break;
+ default:
+ break;
+ }
}
else
{
--- a/persistentstorage/sql/SRC/Server/SqlBur.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlBur.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -17,26 +17,6 @@
#include "SqlAssert.h"
#include "SqlPanic.h"
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-////////////// Backup database file header format ///////////////////
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-
-////// No version (Version 0)
-// 8 chars 8 chars 8 chars up to 256 characters (512 bytes)
-// <32-bit checksum><32-bit filesize><32-bit filenamelen><filename - UTF16 encoded>
-
-////// Version 2
-// 8 chars 8 chars 4 chars 16 chars 8 chars up to 256 characters (512 bytes)
-// <32-bit checksum><FFFFAA55><Version N#><64-bit filesize><32-bit filenamelen><filename - UTF16 encoded>
-
-const TInt KBackupHeaderVersion = 2; //Current backup database file header version
-
-const TUint32 KMagicNum = 0xFFFFAA55; //Magic number. If the "old database file size" field in the header
- //has this value, then the header version is 2+
-const TInt KMaxHeaderSize = 256 + KMaxFileName; //The size of the buffer used for the operations on the header
-
-///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-
//Extracts and returns 32-bit integer from aNumBuf buffer.
static TUint32 GetNumUint32L(const TDesC& aNumBuf)
{
@@ -115,9 +95,6 @@
// make sure the file list is released
iFileList.Reset();
- // the header buffer
- delete iBuffer;
-
// the file list array
iFileList.Close();
@@ -125,10 +102,7 @@
iFile.Close();
// nuke the active backup client
- if(iActiveBackupClient)
- {
- delete iActiveBackupClient;
- }
+ delete iActiveBackupClient;
}
/** Standard two phase construction
@@ -142,9 +116,6 @@
// add us to the scheduler
CActiveScheduler::Add(this);
- // a place for the header info
- iBuffer=HBufC::NewL(KMaxHeaderSize);
-
// set active and request notification of changes to backup
// and restore publish/subscribe property
StartL();
@@ -173,11 +144,8 @@
*/
void CSqlBackupClient::StartL()
{
- if(!IsActive())
- {
- TestBurStatusL();
- NotifyChange();
- }
+ TestBurStatusL();
+ NotifyChange();
}
/** Resubscribe and wait for events
@@ -202,27 +170,16 @@
status&=KBURPartTypeMask;
switch(status)
{
- case EBURUnset:
- // same as EBURNormal
+ case EBURUnset: // same as EBURNormal
case EBURNormal:
- if(iActiveBackupClient)
- {
- delete iActiveBackupClient;
- iActiveBackupClient=NULL;
- }
+ delete iActiveBackupClient;
+ iActiveBackupClient=NULL;
break;
case EBURBackupFull:
case EBURBackupPartial:
- // we only do full backups
- if(!iActiveBackupClient)
- {
- iActiveBackupClient=CActiveBackupClient::NewL(this);
- }
- iActiveBackupClient->ConfirmReadyForBURL(KErrNone);
- break;
- case EBURRestoreFull:
- case EBURRestorePartial:
- // we only do full restores
+ case EBURRestoreFull:
+ case EBURRestorePartial:
+ // we only do full backups and full restores
if(!iActiveBackupClient)
{
iActiveBackupClient=CActiveBackupClient::NewL(this);
@@ -322,17 +279,14 @@
break;
}
- // build the header - this is an instance member because it
- // has to persist over multiple calls to this method
- TPtr hdrPtr=iBuffer->Des();
-
// get the checksum - only grab last 4 bytes - enough to be satisfied that
// the backup and restore worked ok
- TUint32 checksum = CheckSumL(iFile) & 0xFFFFFFFF;
+ TUint32 checksum = CheckSumL(iFile) & KMaxTUint32;
- // build the header
+ // build the header - this is an instance member because it
+ // has to persist over multiple calls to this method
const TDesC& fileName = iFileList[iFileIndex].FullName();
- hdrPtr.Format(_L("%8x%8x%4x%16lx%8x%S"),
+ iBuffer.Format(_L("%8x%8x%4x%16lx%8x%S"),
checksum, // %8x
KMagicNum, // %8x
KBackupHeaderVersion, // %4x
@@ -341,7 +295,7 @@
&fileName); // %S
// we need it to look like an 8bit buffer
- TPtr8 hdrPtr8((TUint8*)hdrPtr.Ptr(),hdrPtr.Size(),hdrPtr.Size());
+ TPtr8 hdrPtr8((TUint8*)iBuffer.Ptr(), iBuffer.Size(), iBuffer.Size());
TInt len = Min(hdrPtr8.Size(), bufFreeSpace);
@@ -368,14 +322,13 @@
case EBackupOpenPartHeaderSent: // need to send the rest of the header
{
// get back the header - this is already loaded with the necessary info
- // from the previous state we were in
- TPtr hdrPtr = iBuffer->Des();
+ // from the previous state we were in - EBackupOpenNothingSent
// we need it to look like an 8bit buffer
- TPtr8 hdrPtr8((TUint8*)hdrPtr.Ptr(),hdrPtr.Size(),hdrPtr.Size());
+ TPtr8 hdrPtr8((TUint8*)iBuffer.Ptr(), iBuffer.Size(), iBuffer.Size());
// how many bytes have we yet to send?
- TInt bytesRemaining = hdrPtr.Size() - iHeaderSent;
+ TInt bytesRemaining = hdrPtr8.Size() - iHeaderSent;
TInt len = Min(bytesRemaining, bufFreeSpace);
aBuffer.Append(hdrPtr8.Ptr() + iHeaderSent, len);
@@ -456,7 +409,7 @@
*/
void CSqlBackupClient::InitialiseRestoreProxyBaseDataL(TSecureId aSid, TDriveNumber /* aDrive */)
{
- iBuffer->Des().Zero();
+ iBuffer.Zero();
// this is the first state of the restore state machine
iState=ERestoreExpectChecksum;
iAnyData=EFalse; // to keep track in the state machine whether any data was actually sent
@@ -481,9 +434,6 @@
// fresh chunk of data
TInt inBufferPos = 0;
- // convert the buffer - this is KMaxHeaderSize=256+KMaxFileName
- TPtr outBufPtr = iBuffer->Des();
-
// to mark when the state machine is through
TBool done = EFalse;
@@ -527,22 +477,22 @@
case ERestoreExpectChecksum: // 16 bytes (the header is UTF16 encoded, 8 unicode characters for the checksum)
{
const TInt KCheckSumStrLen = 8;
- CopyBufData(aInBuffer, inBufferPos, outBufPtr, KCheckSumStrLen);
- if(outBufPtr.Length() == KCheckSumStrLen)
+ CopyBufData(aInBuffer, inBufferPos, iBuffer, KCheckSumStrLen);
+ if(iBuffer.Length() == KCheckSumStrLen)
{
- iChecksum = ::GetNumUint32L(outBufPtr);
+ iChecksum = ::GetNumUint32L(iBuffer);
iState = ERestoreExpectOldFileSize;
- outBufPtr.Zero();
+ iBuffer.Zero();
}
break;
}
case ERestoreExpectOldFileSize: // 16 bytes (the header is UTF16 encoded, 8 unicode characters for 32-bit old file size)
{
const TInt KOldFileSizeStrLen = 8;
- CopyBufData(aInBuffer, inBufferPos, outBufPtr, KOldFileSizeStrLen);
- if(outBufPtr.Length() == KOldFileSizeStrLen)
+ CopyBufData(aInBuffer, inBufferPos, iBuffer, KOldFileSizeStrLen);
+ if(iBuffer.Length() == KOldFileSizeStrLen)
{
- TUint32 oldFileSize = ::GetNumUint32L(outBufPtr);
+ TUint32 oldFileSize = ::GetNumUint32L(iBuffer);
if(oldFileSize == KMagicNum)
{
iState = ERestoreExpectVersion;
@@ -552,60 +502,60 @@
iFileSize = oldFileSize;
iState = ERestoreExpectFileNameSize;
}
- outBufPtr.Zero();
+ iBuffer.Zero();
}
break;
}
case ERestoreExpectVersion:
{
const TInt KVersionStrLen = 4;
- CopyBufData(aInBuffer, inBufferPos, outBufPtr, KVersionStrLen);
- if(outBufPtr.Length() == KVersionStrLen)
+ CopyBufData(aInBuffer, inBufferPos, iBuffer, KVersionStrLen);
+ if(iBuffer.Length() == KVersionStrLen)
{
- //Ignore the version: ::GetNumUint32L(outBufPtr);
+ //Ignore the version: ::GetNumUint32L(iBuffer);
//At this stage we know that the version is 2+
iState = ERestoreExpectFileSize;
- outBufPtr.Zero();
+ iBuffer.Zero();
}
break;
}
case ERestoreExpectFileSize:
{
const TInt KFileSizeStrLen = 16;
- CopyBufData(aInBuffer, inBufferPos, outBufPtr, KFileSizeStrLen);
- if(outBufPtr.Length() == KFileSizeStrLen)
+ CopyBufData(aInBuffer, inBufferPos, iBuffer, KFileSizeStrLen);
+ if(iBuffer.Length() == KFileSizeStrLen)
{
- iFileSize = GetNumInt64L(outBufPtr);
+ iFileSize = GetNumInt64L(iBuffer);
iState = ERestoreExpectFileNameSize;
- outBufPtr.Zero();
+ iBuffer.Zero();
}
break;
}
case ERestoreExpectFileNameSize: // the size of the file name to restore
{
const TInt KFileNameLenStrLen = 8;
- CopyBufData(aInBuffer, inBufferPos, outBufPtr, KFileNameLenStrLen);
- if(outBufPtr.Length() == KFileNameLenStrLen)
+ CopyBufData(aInBuffer, inBufferPos, iBuffer, KFileNameLenStrLen);
+ if(iBuffer.Length() == KFileNameLenStrLen)
{
- iFileNameSize = GetNumUint32L(outBufPtr);
+ iFileNameSize = GetNumUint32L(iBuffer);
iState = ERestoreExpectFileName;
- outBufPtr.Zero();
+ iBuffer.Zero();
}
break;
}
case ERestoreExpectFileName: // the name of the file to restore
{
- CopyBufData(aInBuffer, inBufferPos, outBufPtr, iFileNameSize);
- if(outBufPtr.Length() == iFileNameSize)
+ CopyBufData(aInBuffer, inBufferPos, iBuffer, iFileNameSize);
+ if(iBuffer.Length() == iFileNameSize)
{
iState = ERestoreExpectData;
- outBufPtr.Append(KRestoreSuffix);
+ iBuffer.Append(KRestoreSuffix);
// now we start writing the data to the target file
// write to a temp - double disk space potentially
// once all the temp files are created, then they are renamed to the
// real file names in one fell swoop
- __SQLLEAVE_IF_ERROR(iFile.Replace(iInterface->Fs(), outBufPtr, EFileWrite | EFileShareExclusive));
- outBufPtr.Zero();
+ __SQLLEAVE_IF_ERROR(iFile.Replace(iInterface->Fs(), iBuffer, EFileWrite | EFileShareExclusive));
+ iBuffer.Zero();
}
break;
}
@@ -624,18 +574,19 @@
case ERestoreComplete: // file completely restored
{
// calculate the checksum
- TUint32 cksum = CheckSumL(iFile) & 0xFFFFFFFF;
+ TUint32 cksum = CheckSumL(iFile) & KMaxTUint32;
- // validate that the checksum matches
- if(cksum!=iChecksum)
- {
- __SQLLEAVE(KErrCorrupt);
- }
-
// done with the file now - has to follow checksum cos it
- // expects ann open file
+ // expects an open file
+ __SQLLEAVE_IF_ERROR(iFile.Flush());
iFile.Close();
+ // validate that the checksum matches
+ if(cksum!=iChecksum)
+ {
+ __SQLLEAVE(KErrCorrupt);
+ }
+
// end of data - or another file to be restored?
if(aFinishedFlag)
{
@@ -647,12 +598,12 @@
for(TInt a=0;a<dir->Count();++a)
{
TEntry entry=(*dir)[a];
- TPtr rst=entry.iName.Des();
+ TPtrC rst=entry.iName.Des();
TInt len=rst.Length();
// format <filename>.db.bak.rst
// just a convenience!
- TBufC<KMaxFileName> bak(rst.LeftTPtr(len-4));
- TBufC<KMaxFileName> db(rst.LeftTPtr(len-8));
+ TPtrC bak(rst.Left(len - 4));//".rst" part excluded
+ TPtrC db(rst.Left(len - 8));//".bak.rst" part excluded
// first, rename the orig .db as .bak just in case
// ok if not found - might have been deleted.
@@ -685,7 +636,7 @@
for(TInt a1=0;a1<dir->Count();++a1)
{
TEntry entry=(*dir)[a1];
- TPtr bak=entry.iName.Des();
+ TPtrC bak=entry.iName.Des();
__SQLLEAVE_IF_ERROR(iInterface->Fs().Delete(bak));
}
@@ -728,23 +679,20 @@
for(TInt a=0;a<dir->Count();++a)
{
TEntry entry=(*dir)[a];
- TPtr bak=entry.iName.Des();
+ TPtrC bak=entry.iName.Des();
TInt len=bak.Length();
- TBufC<KMaxFileName> db(bak.LeftTPtr(len-4));
+ TPtrC db(bak.Left(len-4));//".bak" part excluded
rc=iInterface->Fs().Delete(db); // rename does not overwrite
- if(KErrNone!=rc)
+ if(KErrNone == rc)
{
- // nothing happened, still have bak file (and new db)
- delete dir;
- return;
+ rc = iInterface->Fs().Rename(bak,db);
}
- rc=iInterface->Fs().Rename(bak,db);
- if(KErrNone!=rc)
- {
- // still have bak file, but db is gone!
- delete dir;
- return;
- }
+ //The function cannot leave or return an error. The only thing which could be done here is to print out something
+ //and continue with the next file.
+ if(KErrNone != rc)
+ {
+ RDebug::Print(_L(" *** CSqlBackupClient::TerminateMultiStageOperation(), file \"%S\", err=%d\r\n"), &db, rc);
+ }
// backup restored ok
}
// cleanup dir
--- a/persistentstorage/sql/SRC/Server/SqlBur.h Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlBur.h Fri Mar 12 15:51:02 2010 +0200
@@ -25,6 +25,27 @@
using namespace conn;
+///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
+////////////// Backup database file header format ///////////////////
+///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+////// No version (Version 0)
+// 8 chars 8 chars 8 chars up to 256 characters (512 bytes)
+// <32-bit checksum><32-bit filesize><32-bit filenamelen><filename - UTF16 encoded>
+
+////// Version 2
+// 8 chars 8 chars 4 chars 16 chars 8 chars up to 256 characters (512 bytes)
+// <32-bit checksum><FFFFAA55><Version N#><64-bit filesize><32-bit filenamelen><filename - UTF16 encoded>
+
+const TInt KBackupHeaderVersion = 2; //Current backup database file header version
+
+const TUint32 KMagicNum = 0xFFFFAA55; //Magic number. If the "old database file size" field in the header
+ //has this value, then the header version is 2+
+const TInt KMaxHeaderSize = 256 + KMaxFileName; //The size of the buffer used for the operations on the header
+
+///////////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+
//-----------------------------------------
// CSqlBackupClient
//-----------------------------------------
@@ -127,7 +148,7 @@
RFile64 iFile;
TInt iFileIndex;
TUint iState;
- HBufC* iBuffer; // used for the header data
+ TBuf<KMaxHeaderSize> iBuffer; // used for the header data
TInt iHeaderSent; // how many header bytes sent so far
TUint32 iChecksum; // used by restore
TInt64 iFileSize; // used by restore
--- a/persistentstorage/sql/SRC/Server/SqlSrvAuthorizer.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlSrvAuthorizer.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -269,14 +269,6 @@
case SQLITE_DROP_TRIGGER:// Trigger Name Table Name
case SQLITE_DROP_VIEW:// View Name NULL
case SQLITE_ALTER_TABLE:// Database Name Table Name
- case SQLITE_CREATE_TEMP_INDEX:// Index Name Table Name
- case SQLITE_CREATE_TEMP_TABLE:// Table Name NULL
- case SQLITE_CREATE_TEMP_TRIGGER:// Trigger Name Table Name
- case SQLITE_CREATE_TEMP_VIEW:// View Name NULL
- case SQLITE_DROP_TEMP_INDEX:// Index Name Table Name
- case SQLITE_DROP_TEMP_TABLE:// Table Name NULL
- case SQLITE_DROP_TEMP_TRIGGER:// Trigger Name Table Name
- case SQLITE_DROP_TEMP_VIEW:// View Name NULL
case SQLITE_SELECT:// NULL NULL
case SQLITE_TRANSACTION:// NULL NULL
case SQLITE_DELETE:// Table Name NULL
@@ -294,6 +286,16 @@
case SQLITE_PRAGMA:// Pragma Name 1st arg or NULL
res = PragmaCheck(aDbObjName1, (aDbObjName2 != NULL), EFalse);
break;
+//All "temp" operations are handled earlier, in CSqlSrvDatabase::AuthorizeCallback(), where a check for "temp"
+//database name is performed.
+// case SQLITE_CREATE_TEMP_INDEX:// Index Name Table Name
+// case SQLITE_CREATE_TEMP_TABLE:// Table Name NULL
+// case SQLITE_CREATE_TEMP_TRIGGER:// Trigger Name Table Name
+// case SQLITE_CREATE_TEMP_VIEW:// View Name NULL
+// case SQLITE_DROP_TEMP_INDEX:// Index Name Table Name
+// case SQLITE_DROP_TEMP_TABLE:// Table Name NULL
+// case SQLITE_DROP_TEMP_TRIGGER:// Trigger Name Table Name
+// case SQLITE_DROP_TEMP_VIEW:// View Name NULL
default:
__SQLASSERT(EFalse, ESqlPanicInternalError);
break;
@@ -360,14 +362,6 @@
}
break;
//No policy check
- case SQLITE_CREATE_TEMP_INDEX:// Index Name Table Name
- case SQLITE_CREATE_TEMP_TABLE:// Table Name NULL
- case SQLITE_CREATE_TEMP_TRIGGER:// Trigger Name Table Name
- case SQLITE_CREATE_TEMP_VIEW:// View Name NULL
- case SQLITE_DROP_TEMP_INDEX:// Index Name Table Name
- case SQLITE_DROP_TEMP_TABLE:// Table Name NULL
- case SQLITE_DROP_TEMP_TRIGGER:// Trigger Name Table Name
- case SQLITE_DROP_TEMP_VIEW:// View Name NULL
case SQLITE_SELECT:// NULL NULL
case SQLITE_TRANSACTION:// NULL NULL
break;
@@ -423,6 +417,16 @@
//No policy check
case SQLITE_FUNCTION:
break;
+//All "temp" operations are handled earlier, in CSqlSrvDatabase::AuthorizeCallback(), where a check for "temp"
+//database name is performed.
+// case SQLITE_CREATE_TEMP_INDEX:// Index Name Table Name
+// case SQLITE_CREATE_TEMP_TABLE:// Table Name NULL
+// case SQLITE_CREATE_TEMP_TRIGGER:// Trigger Name Table Name
+// case SQLITE_CREATE_TEMP_VIEW:// View Name NULL
+// case SQLITE_DROP_TEMP_INDEX:// Index Name Table Name
+// case SQLITE_DROP_TEMP_TABLE:// Table Name NULL
+// case SQLITE_DROP_TEMP_TRIGGER:// Trigger Name Table Name
+// case SQLITE_DROP_TEMP_VIEW:// View Name NULL
default:
__SQLASSERT(EFalse, ESqlPanicInternalError);
break;
--- a/persistentstorage/sql/SRC/Server/SqlSrvMain.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlSrvMain.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -233,6 +233,9 @@
/**
Creates new CSqlSrvSession instance.
+If SQLSRV_STARTUP_TEST macro is defined, then the function returns NULL.
+The "real" implementation of the function is not used in this case because the used unit test will require
+a lot of cpp files to be included into the test build (t_sqlstartup).
@return A pointer to the created CSqlSrvSession instance.
@@ -241,15 +244,20 @@
@see CSqlSrvSession
*/
-CSession2* CSqlServer::NewSessionL(const TVersion &aVersion, const RMessage2&) const
- {
- if(!User::QueryVersionSupported(::SqlSrvVersion(), aVersion))
- {
- User::Leave(KErrNotSupported);
- }
- CSqlSrvSession* sess = CSqlSrvSession::NewL();
- return sess;
- }
+CSession2* CSqlServer::NewSessionL(const TVersion& aVersion, const RMessage2&) const
+ {
+#ifdef SQLSRV_STARTUP_TEST
+ aVersion.Name();//to prevent the compiler warning ("unused parameter").
+ return NULL;
+#else
+ if(!User::QueryVersionSupported(::SqlSrvVersion(), aVersion))
+ {
+ User::Leave(KErrNotSupported);
+ }
+ CSqlSrvSession* sess = CSqlSrvSession::NewL();
+ return sess;
+#endif //SQLSRV_STARTUP_TEST
+ }
/**
CSqlServer's active object priority.
@@ -283,7 +291,11 @@
*/
void CSqlServer::ConstructL()
{
+#ifndef SQLSRV_STARTUP_TEST
+ //Start the server only in "normal" builds, not in the case where t_sqlstartup unit test tests directly
+ //the SQL server startup code.
StartL(KSqlSrvName);
+#endif
#ifdef _SQLPROFILER
TheSqlSrvStartTime.UniversalTime();
SQLPROFILER_SERVER_START();
@@ -329,18 +341,24 @@
//Compactor
iCompactor = CSqlCompactor::NewL(&SqlCreateCompactConnL, KSqlCompactStepIntervalMs);
#ifdef _DEBUG
- /*
- The following statements exist to prevent the failure of the resource allocation
- checking for debug mode.
- They allocate some memory when the server object is constructed so avoid these memory
- allocations during debug mode.
- */
-const TInt KAnyNumber = 0xAA55;
-const TInt KGreatSize = 1024;
+ //The following statements exist to prevent the failure of the OOM testing in debug mode.
+ //The standard C library allocates some memory at the startup and stores a pointer to the allocated memory
+ //in the TLS. During normal API OOM testing the SQL server is not restarted, it never goes down.
+ //Then the TLS and the allocated memory are not released. In which case the OOM testing will fail
+ //(because the standard C library performs a lazy initialization and the allocation and TLS usage will be made
+ //at the point of first use of some C function. This is out of the control of the test code).
+ //In order to avoid that, during the SQL server startup here, before the OOM test goes and checks what
+ //is the allocated memory at the beginning, a fake sprintf() call is made in order to force the mentioned above
+ //allocation in the standard C library.
+ //All explanations above are true, except one case when the SQl server startup code is tested directly.
+ #ifndef SQLSRV_STARTUP_TEST
+ const TInt KAnyNumber = 0xAA55;
char tmp[32];
sprintf(tmp, "%04X", KAnyNumber);
+ const TInt KGreatSize = 1024;
__SQLLEAVE_IF_ERROR(ReAllocBuf(KGreatSize));
-#endif
+ #endif //SQLSRV_STARTUP_TEST
+#endif //_DEBUG
}
/**
@@ -436,6 +454,7 @@
*/
void CSqlServer::GetBackUpListL(TSecureId aUid, RArray<TParse>& aFileList)
{
+ aFileList.Reset();
TFindFile findFile(iFileData.Fs());
CDir* fileNameCol = NULL;
TUidName uidName = (static_cast <TUid> (aUid)).Name();
@@ -479,6 +498,9 @@
fileNameCol = NULL;
} while((err = findFile.FindWild(fileNameCol)) == KErrNone);//Get the next set of files
}//end of "if(err == KErrNone)"
+ //TODO: once DEF144134 gets fixed, the next 2 lines shall be removed
+ delete fileNameCol;
+ fileNameCol = NULL;
__SQLASSERT(!fileNameCol, ESqlPanicInternalError);
if(err != KErrNotFound && err != KErrNone)
{
@@ -490,6 +512,8 @@
//////////////////////////////////////// SQL server startup //////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////////////////////////////////
+#ifndef SQLSRV_STARTUP_TEST
+
//Run the SQL server
static void RunServerL()
{
@@ -526,3 +550,4 @@
return err;
}
+#endif //SQLSRV_STARTUP_TEST
--- a/persistentstorage/sql/SRC/Server/SqlSrvSession.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlSrvSession.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -519,17 +519,24 @@
__SQLPANIC_CLIENT(!iDatabase, aMessage, ESqlPanicObjExists);
const TInt KSecurityPolicyLen = (aMessage.Int2() & 0x7fff0000) >> 16;
const TInt KConfigStringLen = aMessage.Int2() & 0xffff;
- if(KSecurityPolicyLen < 0 || KConfigStringLen < 0 || KConfigStringLen > KSqlSrvMaxConfigStrLen)
+ if(KSecurityPolicyLen < 0 || (TUint)KConfigStringLen > KSqlSrvMaxConfigStrLen)
{
__SQLLEAVE(KErrArgument);
}
- TBuf8<KSqlSrvMaxConfigStrLen> configStr;
+ RBuf8 securityAndConfigBuf;
+ CleanupClosePushL(securityAndConfigBuf);
+ if((KSecurityPolicyLen + KConfigStringLen) > 0)
+ {
+ securityAndConfigBuf.CreateL(KSecurityPolicyLen + KConfigStringLen);
+ aMessage.ReadL(3, securityAndConfigBuf);
+ SQLPROFILER_REPORT_IPC(ESqlIpcRead, (KSecurityPolicyLen + KConfigStringLen));
+ }
+ TSqlSrvFileData& fileData = Server().FileData();
+ TPtrC8 configStr(KNullDesC8);
if(KConfigStringLen > 0)
- {
- aMessage.ReadL(3, configStr, KSecurityPolicyLen);
- SQLPROFILER_REPORT_IPC(ESqlIpcRead, KConfigStringLen);
- }
- TSqlSrvFileData& fileData = Server().FileData();
+ {
+ configStr.Set(securityAndConfigBuf.Mid(KSecurityPolicyLen));//the first part of the buffer is for the security policies
+ }
fileData.SetL(aMessage, aMessage.Int0(), 1, &configStr);
iDrive = fileData.Drive();
switch(aFunction)
@@ -543,7 +550,7 @@
break;
case ESqlSrvDbCreateSecure:
{
- if(!fileData.IsSecureFileNameFmt())
+ if(!fileData.IsSecureFileNameFmt() || KSecurityPolicyLen == 0)
{
__SQLLEAVE(KErrArgument);
}
@@ -552,7 +559,7 @@
{
__SQLLEAVE(KErrPermissionDenied);
}
- CSqlSecurityPolicy* policy = InternalizeSecurityPolicyL(aMessage);
+ CSqlSecurityPolicy* policy = CreateSecurityPolicyL(securityAndConfigBuf.Left(KSecurityPolicyLen));
iDatabase = CSqlSrvDatabase::CreateSecureL(fileData, policy);
}
break;
@@ -563,6 +570,7 @@
__SQLLEAVE(KErrArgument);
break;
}
+ CleanupStack::PopAndDestroy(&securityAndConfigBuf);
}
/**
@@ -596,14 +604,8 @@
const TBool KCreated = (aMessage.Int0() & 0x40000000) != 0;
const TInt KDbFileNameLen = aMessage.Int0() & 0x0000FFFF;
const TInt KConfigStringLen = (aMessage.Int0() & 0x3FFF0000) >> 16;
- if(KConfigStringLen < 0 || KConfigStringLen > KSqlSrvMaxConfigStrLen)
- {
- __SQLLEAVE(KErrArgument);
- }
- if(KDbFileNameLen < 1 || KDbFileNameLen > KMaxFileName)
- {
- __SQLLEAVE(KErrBadName);
- }
+ __SQLPANIC_CLIENT((TUint)KConfigStringLen <= KSqlSrvMaxConfigStrLen, aMessage, ESqlPanicBadArgument);
+ __SQLPANIC_CLIENT((TUint)KDbFileNameLen <= KMaxFileName, aMessage, ESqlPanicBadArgument);
TDes16& buffer = Server().GetBuf16L(KDbFileNameLen + KConfigStringLen);
aMessage.ReadL(1, buffer);
SQLPROFILER_REPORT_IPC(ESqlIpcRead, ((KDbFileNameLen + KConfigStringLen) * sizeof(TText)));
@@ -881,7 +883,7 @@
{
__SQLPANIC_CLIENT(iDatabase != NULL, aMessage, ESqlPanicInvalidObj);
const TInt KDbNameLen = aMessage.Int1();
- if(KDbNameLen < 0 || KDbNameLen > KMaxFileName)
+ if((TUint)KDbNameLen > KMaxFileName)
{
__SQLLEAVE(KErrBadName);
}
@@ -928,7 +930,7 @@
return 0;
}
const TInt KDbNameLen = aMessage.Int1();
- if(KDbNameLen < 0 || KDbNameLen > KMaxFileName)
+ if((TUint)KDbNameLen > KMaxFileName)
{
__SQLLEAVE(KErrBadName);
}
@@ -1140,8 +1142,8 @@
__SQLLEAVE(KErrBadName);
}
}
-
- if(len < 1 || len > KMaxFileName)
+ __SQLASSERT(len > 0, ESqlPanicInternalError);//The "if" above should have hanled the case with "len == 0"
+ if((TUint)len > KMaxFileName)
{
__SQLLEAVE(KErrBadName);
}
@@ -1617,47 +1619,21 @@
}
/**
-The method reads the message argument 1 data and constructs a CSqlSecurityPolicy object from the data.
+The method constructs a CSqlSecurityPolicy object from the passed as an argument descriptor.
-@param aMessage Client request encapsulated in RMessage2 object.
+@param aSecurityPolicyData A descriptor with the security policy data.
@return A pointer to the created CSqlSecurityPolicy instance.
-@leave KErrArgument, if aMessage argument 0 length is 0 or negative (no security data);
- KErrNoMemory, out of memory condition has occured.
-
-Usage of the IPC call arguments:
-Arg 2: [in] security policies buffer length in bytes if aFunction is ESqlSrvDbCreateSecure
-Arg 3: [in] security policies buffer if aFunction is ESqlSrvDbCreateSecure
+@leave KErrNoMemory, out of memory condition has occured.
*/
-CSqlSecurityPolicy* CSqlSrvSession::InternalizeSecurityPolicyL(const RMessage2& aMessage)
+CSqlSecurityPolicy* CSqlSrvSession::CreateSecurityPolicyL(const TDesC8& aSecurityPolicyData)
{
- // Leave if there is no security policy data
- // The format of arg[2] is an unsigned int
- // with the policy length shifted and concated to the config length
- // the policy data is the first part of arg[3]
- const TUint KConfigStrLenBitWidth = 16;
- TInt securityPolicyLen = aMessage.Int2() >> KConfigStrLenBitWidth;
- if(securityPolicyLen < 1)
- {
- __SQLLEAVE(KErrArgument);
- }
TSecurityPolicy defaultPolicy(TSecurityPolicy::EAlwaysFail);
CSqlSecurityPolicy* dbPolicy = CSqlSecurityPolicy::NewLC(defaultPolicy);
RSqlBufFlat& bufFlat = dbPolicy->BufFlat();
- if(securityPolicyLen > bufFlat.MaxSize())
- {
- __SQLLEAVE_IF_ERROR(bufFlat.ReAlloc(securityPolicyLen));
- }
- TPtr8& ptr = bufFlat.BufPtr();
- aMessage.ReadL(3, ptr);
- SQLPROFILER_REPORT_IPC(ESqlIpcRead, securityPolicyLen);
- // trim off config data if any
- TInt extraBytes = ptr.Length() - securityPolicyLen;
- if(extraBytes > 0)
- {
- ptr.Delete(securityPolicyLen, extraBytes);
- }
+ __SQLLEAVE_IF_ERROR(bufFlat.ReAlloc(aSecurityPolicyData.Length()));
+ bufFlat.BufPtr().Copy(aSecurityPolicyData);
CleanupStack::Pop(dbPolicy);
return dbPolicy;
}
--- a/persistentstorage/sql/SRC/Server/SqlSrvSession.h Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlSrvSession.h Fri Mar 12 15:51:02 2010 +0200
@@ -113,7 +113,7 @@
TDes8& ReadString8ZL(const RMessage2& aMessage, TInt aArgNum, TInt aByteLen);
TDes16& ReadString16ZL(const RMessage2& aMessage, TInt aArgNum, TInt aCharLen);
TDes16& ReadString16L(const RMessage2& aMessage, TInt aArgNum, TInt aCharLen);
- CSqlSecurityPolicy* InternalizeSecurityPolicyL(const RMessage2& aMessage);
+ CSqlSecurityPolicy* CreateSecurityPolicyL(const TDesC8& aSecurotyPolicyData);
virtual TInt CountResources();
void Extract(const RMessage2& aMessage, TSqlSrvFunction& aFunction, TInt& aHandle);
TInt GetColumnValueL(const RMessage2& aMessage, CSqlSrvStatement& aStmt, TSqlColumnType aColType);
--- a/persistentstorage/sql/SRC/Server/SqlSrvUtil.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/SRC/Server/SqlSrvUtil.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -156,7 +156,7 @@
des.Append(TChar(0));
TInt len = wcstombs((char*)aOut.Ptr(), (const wchar_t*)des.Ptr(), KMaxFileName);
//Check the file name length. If it is longer than KMaxFileName characters, then the file name is not valid.
- if(len >= 0 && len <= KMaxFileName)
+ if((TUint)len <= KMaxFileName)
{
aOut.SetLength(len);
return ETrue;
@@ -185,7 +185,7 @@
const wchar_t* src = reinterpret_cast <const wchar_t*> (aFileName.Ptr());
TInt len = wcstombs((char*)aFileNameDestBuf.Ptr(), src, KMaxFileName);
//Check the file name length. If it is longer than KMaxFileName characters, then the file name is not valid.
- if(len >= 0 && len <= KMaxFileName)
+ if((TUint)len <= KMaxFileName)
{
aFileNameDestBuf.SetLength(len + 1);
aFileNameDestBuf[len] = 0;
--- a/persistentstorage/sql/TEST/t_sqlapi.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlapi.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -1,4 +1,4 @@
-// Copyright (c) 2005-2009 Nokia Corporation and/or its subsidiary(-ies).
+// Copyright (c) 2005-2010 Nokia Corporation and/or its subsidiary(-ies).
// All rights reserved.
// This component and the accompanying materials are made available
// under the terms of "Eclipse Public License v1.0"
@@ -42,6 +42,7 @@
_LIT8(KServerConfigString2, " badconfigstring ");
_LIT8(KServerConfigString3, " aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa");
_LIT8(KServerConfigString4, "");
+_LIT8(KServerConfigString5, "dfgdfrgdkfjgjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj43w3wk4jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnn");
const TUid KSecureUid = {0x1111CCCC};//The same as the UID in the MMP file
@@ -244,7 +245,12 @@
db.Close();
rc2 = RSqlDatabase::Delete(KTestCfgDbName);
TEST2(rc2, KErrNone);
-
+
+ // create database with very long config specified
+ rc = db.Create(KTestCfgDbName, &KServerConfigString5);
+ TEST2(rc, KErrArgument);
+ db.Close();
+
//Secure shared database file on an existing drive (C:).
//Very long database file name (> 90 characters) but still a valid name.
rc = db.Create(KTestDbName4, securityPolicy);
@@ -1110,6 +1116,10 @@
//Read row 2 using ColumnText(TInt aColumnIndex, TDes& aDest).
rc = stmt.ColumnText(1, colData);
TEST2(rc, KErrNone);
+ //Too small target buffer
+ TBuf<3> buf1;
+ rc = stmt.ColumnText(1, buf1);
+ TEST2(rc, KErrOverflow);
//Check the column value
for(i=0;i<KTextLen;++i)
@@ -1224,6 +1234,10 @@
rc = db.Exec(sql);
TEST2(rc, 1);
+ //Insert row 3: the binary column length is just 2 bytes
+ rc = db.Exec(_L("INSERT INTO A VALUES(3, x'A5D3')"));
+ TEST2(rc, 1);
+
//Prepare SELECT SQL statement
_LIT8(KSqlStmt3, "SELECT * FROM A");
RSqlStatement stmt = PrepareSqlStmt<TDesC8, TBuf8<KSqlBufSize> >(db, KSqlStmt3, KErrNone);
@@ -1315,6 +1329,19 @@
TEST(val = KHexVal2);
}
+ //Move on row 3. The binary column value length is just 2 bytes.
+ rc = stmt.Next();
+ TEST2(rc, KSqlAtRow);
+ rc = stmt.Next();
+ TEST2(rc, KSqlAtRow);
+ TBuf8<2> buf1;
+ rc = stmt.ColumnBinary(1, buf1);
+ TEST2(rc, KErrNone);
+ TEST2(buf1.Length(), 2);
+ TBuf8<1> buf2;
+ rc = stmt.ColumnBinary(1, buf2);
+ TEST2(rc, KErrOverflow);
+
stmt.Close();
//Deallocate buf
@@ -1534,6 +1561,10 @@
RSqlParamWriteStream paramStream;
rc = paramStream.BindBinary(stmt, 0);
TEST2(rc, KErrNone);
+ paramStream.Close();
+ //Open the parameter stream with BindBinaryL()
+ TRAP(rc, paramStream.BindBinaryL(stmt, 0));
+ TEST2(rc, KErrNone);
//Prepare and set the parameter value (NULL parameter value)
TPtr8 prmVal = buf->Des();
@@ -2059,6 +2090,14 @@
TPtrC msg = db.LastErrorMessage();
TheTest.Printf(_L("Non-existing attached database, error message: %S\r\n"), &msg);
+ //An attempt to get the size when the attached database name contains "bad" unicode characters (cannot be converted to UTF8)
+ TBuf<2> dbName3;
+ dbName3.SetLength(2);
+ dbName3[0] = TChar(0xD800);
+ dbName3[1] = TChar(0xFC00);
+ err = db.Size(size1, dbName3);
+ TEST2(err, KErrGeneral);
+
err = db.Detach(KAttachDbName);
TEST2(err, KErrNone);
db.Close();
--- a/persistentstorage/sql/TEST/t_sqlapi2.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlapi2.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -460,6 +460,12 @@
err = TheStmt.ColumnName(0, colName);
TEST2(err, KErrNone);
TEST2(colName.Compare(_L("RES")), 0);
+ //Too big column index
+ err = TheStmt.ColumnName(1323, colName);
+ TEST2(err, KErrNotFound);
+ //Negative column index
+ err = TheStmt.ColumnName(-100, colName);
+ TEST2(err, KErrNotFound);
TheStmt.Close();
//Select constant
err = TheStmt.Prepare(TheDb, _L("SELECT (Id + Data) AS RES, 55.89 FROM t2"));
@@ -529,7 +535,20 @@
TEST2(err, KErrNone);
TEST2(paramName.Compare(expectedParamName), 0);
}
+ //Too big parameter index
+ err = TheStmt.ParamName(1323, paramName);
+ TEST2(err, KErrNotFound);
+ //Negative parameter index
+ err = TheStmt.ParamName(-100, paramName);
+ TEST2(err, KErrNotFound);
TheStmt.Close();
+
+ //SQL statement without parameters
+ err = TheStmt.Prepare(TheDb, _L("INSERT INTO T (A1, A2) VALUES (1, '1')"));
+ TEST2(err, KErrNone);
+ err = TheStmt.ParamName(0, paramName);
+ TEST2(err, KErrNotFound);
+ TheStmt.Close();
// Create insert statement, then check param names
err = TheStmt.Prepare(TheDb, _L("INSERT INTO T (A1, A2) VALUES (:prm1, ?)"));
--- a/persistentstorage/sql/TEST/t_sqlattach.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlattach.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -277,7 +277,19 @@
err = TheDb.Detach(KAttachDb4);
TEST(err != KErrNone);
-
+
+ //Detach() with zero-length logical database name
+ err = TheDb.Detach(_L(""));
+ TEST2(err, KErrBadName);
+
+ //Detach() with logical database name containing "bad" unicode characters (cannot be converted to UTF8)
+ TBuf<2> dbName3;
+ dbName3.SetLength(2);
+ dbName3[0] = TChar(0xD800);
+ dbName3[1] = TChar(0xFC00);
+ err = TheDb.Detach(dbName3);
+ TEST2(err, KSqlErrGeneral);
+
TheDb.Close();
}
--- a/persistentstorage/sql/TEST/t_sqldefect.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqldefect.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -36,7 +36,8 @@
_LIT(KTestDatabase4, "z:\\test\\t_inc095412.db"); //Created outside this test app
_LIT(KTestDatabase5, "c:\\test\\t_sqldefect_5.db");
_LIT(KTestDatabase6, "c:\\test\\t_def120237.db");
-
+_LIT(KTestDatabase7, "c:\\test\\t_def144027.db");
+_LIT(KTestDatabase7Journal, "c:\\test\\t_def144027.db-journal");
// This value has been found by performing the OOM test
// with an allocation limit of 2000 and then taking a value
@@ -49,6 +50,8 @@
void DeleteTestFiles()
{
TheDb.Close();
+ (void)TheFs.Delete(KTestDatabase7Journal);
+ (void)RSqlDatabase::Delete(KTestDatabase7);
(void)RSqlDatabase::Delete(KTestDatabase6);
(void)RSqlDatabase::Delete(KTestDatabase5);
(void)RSqlDatabase::Delete(KTestDatabase3);
@@ -1582,9 +1585,55 @@
TEST2(err, 1);
}
+/**
+@SYMTestCaseID PDS-SQL-CT-4166
+@SYMTestCaseDesc Tests for DEF144027: SQL Open returns error if the reported and actual file size are different
+@SYMTestPriority Medium
+@SYMTestActions 1) Create a simple database and close it (this will automatically delete the journal file
+ 2) Create a 15 bytes garbage journal file which is just less than the minimum file size allowed.
+ 3) Reopen the database and checks that the open operation does not fail even thou we've used a
+ garbage journal file which is too small
+@SYMTestExpectedResults The RSqlDatabase::Open operation should not fail
+@SYMDEF DEF144027
+ DEF144238
+*/
+void DEF144027()
+ {
+ (void) RSqlDatabase::Delete(KTestDatabase7);
+ (void) TheFs.Delete(KTestDatabase7Journal);
+
+ TInt err = TheDb.Create(KTestDatabase7);
+ TEST2(err, KErrNone);
+
+ err = TheDb.Exec(_L("CREATE TABLE t1(NUM INTEGER)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("INSERT INTO t1(NUM) VALUES (1)"));
+ TEST2(err, 1);
+
+ TheDb.Close();
+
+ //Created a garbage 15 bytes journal file
+ RFile file;
+ err = file.Create(TheFs, KTestDatabase7Journal, EFileWrite);
+ TEST2(err, KErrNone);
+
+ _LIT8(KJournalJunkData, "A123456789B1234");//15 bytes
+ err = file.Write(0, KJournalJunkData);
+ TEST2(err, KErrNone);
+
+ file.Flush();
+ file.Close();
+
+ //Here we check the open operation does not return an error,
+ //even though there is a journal file less than 16 bytes
+ err = TheDb.Open(KTestDatabase7);
+ TEST2(err, KErrNone);
+ TheDb.Close();
+ }
+
void DoTestsL()
{
-
TheTest.Start(_L(" @SYMTestCaseID:SYSLIB-SQL-CT-1763 \"SQL against a detached db\" test "));
SqlDetachedDbTest();
@@ -1665,6 +1714,9 @@
TheTest.Next(_L(" @SYMTestCaseID:PDS-SQL-CT-4157 PDEF143461 : CSqlSrvDatabase::LastErrorMessage() alignment problem"));
PDEF143461L();
+
+ TheTest.Next(_L(" @SYMTestCaseID:PDS-SQL-CT-4166 DEF144027: SQL Open returns error if the reported and actual file size are different"));
+ DEF144027();
}
TInt E32Main()
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/persistentstorage/sql/TEST/t_sqlfilesrvcrash1.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,255 @@
+// 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 "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:
+//
+
+/**
+Instructions:
+
+This is a manual test created to verify DEFXXXXX, 2 executables needs to be run to do this test
+1) t_sqlfilesrvcrash1.exe - Generate a corrupted journal file, this will cause the device to reset.
+2) t_sqlfilesrvcrash2.exe - After the reboot, tests if SQL can handle the courrpted journal file.
+
+This test requires a non-rugged drive to store the database file and therefore will only work in hardware mode
+*/
+
+#include <e32test.h>
+#include <f32file.h>
+#include <Sqldb.h>
+
+RTest TheTest(_L("t_sqlfilesrvcrash1 test"));
+
+#if !defined __WINS__ && !defined __WINSCW__
+
+RFs TheFs;
+RSqlDatabase TheDb;
+
+const TInt KControlIoRuggedOn=2;
+const TInt KControlIoRuggedOff=3;
+const TInt KControlIoIsRugged=4;
+
+const TChar KDrvLetter = ('E');
+_LIT(KTestDir, "E:\\test\\");
+_LIT(KDbName, "E:\\test\\t_sqlfilesrvcrash.db");
+_LIT8(KConfigStr, "page_size=32768");
+_LIT(KFileSrvName, "efile.exe");
+
+///////////////////////////////////////////////////////////////////////////////////////
+//Deletes all created test files.
+void DeleteTestFiles()
+ {
+ TheDb.Close();
+ (void)RSqlDatabase::Delete(KDbName);
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DeleteTestFiles();
+ RDebug::Print(_L("*** Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DeleteTestFiles();
+ RDebug::Print(_L("*** Expected error: %d, got: %d\r\n"), aExpected, aValue);
+ TheTest(EFalse, aLine);
+ }
+ }
+
+#define TEST(arg) ::Check((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check(aValue, aExpected, __LINE__)
+
+///////////////////////////////////////////////////////////////////////////////////////
+//Set the drive to Rugged or non-rugged depending on the input parameter
+void SetDrive(TBool aSetToRugged)
+ {
+ TUint8 isRugged;
+ TPtr8 pRugged(&isRugged,1,1);
+
+ TInt drvNum;
+ TInt err = TheFs.CharToDrive(KDrvLetter, drvNum);
+ TEST2(err, KErrNone);
+ err=TheFs.ControlIo(drvNum,KControlIoIsRugged,pRugged);
+ TEST2(err, KErrNone);
+
+ if(!aSetToRugged)
+ {
+ if(isRugged)
+ {
+ err=TheFs.ControlIo(drvNum,KControlIoRuggedOff);
+ TEST2(err, KErrNone);
+ }
+ }
+ else
+ {
+ if(!isRugged)
+ {
+ err=TheFs.ControlIo(drvNum,KControlIoRuggedOn);
+ TEST2(err, KErrNone);
+ }
+ }
+ }
+
+//Creates file session instance and the test directory
+void CreateTestEnv()
+ {
+ TInt err = TheFs.Connect();
+ TEST2(err, KErrNone);
+
+ //Set the drive to non-rugged
+ TBool setDriveToRugged = EFalse;
+ SetDrive(setDriveToRugged);
+
+ err = TheFs.MkDir(KTestDir);
+ TEST(err == KErrNone || err == KErrAlreadyExists);
+ }
+
+TInt KillProcess(const TDesC& aProcessName)
+ {
+ TFullName name;
+ //RDebug::Print(_L("Find and kill \"%S\" process.\n"), &aProcessName);
+ TBuf<64> pattern(aProcessName);
+ TInt length = pattern.Length();
+ pattern += _L("*");
+ TFindProcess procFinder(pattern);
+
+ while (procFinder.Next(name) == KErrNone)
+ {
+ if (name.Length() > length)
+ {//If found name is a string containing aProcessName string.
+ TChar c(name[length]);
+ if (c.IsAlphaDigit() ||
+ c == TChar('_') ||
+ c == TChar('-'))
+ {
+ //RDebug::Print(_L(":: Process name: \"%S\".\n"), &name);
+ continue;
+ }
+ }
+ RProcess proc;
+ if (proc.Open(name) == KErrNone)
+ {
+ RDebug::Print(_L("About to kill process \"%S\", This will force a reboot\n"), &name);
+ proc.Kill(0);
+
+ }
+ proc.Close();
+ }
+ return KErrNone;
+ }
+
+/**
+@SYMTestCaseID PDS-SQL-CT-4164
+@SYMTestCaseDesc Tests for DEF144027: SQL Open returns error if the reported and actual file size are different
+ This function creates a corrupted jorunal file on a non-rugged FAT, where the actual and
+ reported file size is different. This is done by killing the file server forcing the device to
+ reset. After the reset t_sqlfilesrvcrash2.exe is used to verify SQL can handle this corrupted
+ journal file properly.
+@SYMTestActions DEF144027: SQL Open returns error if the reported and actual file size are different
+@SYMTestExpectedResults Test must not fail
+@SYMTestPriority Medium
+@SYMDEF DEF144027
+ DEF144238
+*/
+void DEF144027()
+ {
+ TInt err = TheDb.Create(KDbName, &KConfigStr);
+ TEST2(err, KErrNone);
+
+ err = TheDb.Exec(_L("CREATE TABLE t1(NUM INTEGER)"));
+ TEST2(err, 1);
+ err = TheDb.Exec(_L("CREATE TABLE t2(NUM INTEGER)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("INSERT INTO t1(NUM) VALUES (1)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("INSERT INTO t2(NUM) VALUES (1)"));
+ TEST2(err, 1);
+
+ TheDb.Close();
+
+ err = TheDb.Open(KDbName);
+ TEST2(err, KErrNone);
+
+ err = TheDb.Exec(_L("BEGIN"));
+ TEST(err >= 0);
+
+ err = TheDb.Exec(_L("CREATE TABLE t3(NUM INTEGER)"));
+ TEST2(err, KErrNone);
+
+ err = TheDb.Exec(_L("INSERT INTO t1(NUM) VALUES (1)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("INSERT INTO t2(NUM) VALUES (1)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("INSERT INTO t3(NUM) VALUES (1)"));
+ TEST2(err, 1);
+
+
+ //Here the transaction is committed but the database is not close
+ //this makes sure that the journal is truncated but not deleted
+ err = TheDb.Exec(_L("COMMIT"));
+ TEST(err >= 0);
+
+ //Reset the drive to rugged
+ TBool setDriveToRugged = ETrue;
+ SetDrive(setDriveToRugged);
+
+ //When the file server is killed, the file size meta data will not be updated
+ KillProcess(KFileSrvName);
+ }
+
+void DoTests()
+ {
+ TheTest.Start(_L(" @SYMTestCaseID:PDS-SQL-CT-4164 DEF144027: SQL Open returns error if the reported and actual file size are different"));
+ DEF144027();
+ }
+#endif //#if !defined __WINS__ && !defined __WINSCW__
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+
+ __UHEAP_MARK;
+
+#if !defined __WINS__ && !defined __WINSCW__
+ CreateTestEnv();
+ DeleteTestFiles();
+ DoTests();
+ TheFs.Close();
+ TheTest.End();
+#else
+ TheTest.Start(_L("This test works only works on hardware!"));
+ TheTest.End();
+#endif
+
+ __UHEAP_MARKEND;
+
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/persistentstorage/sql/TEST/t_sqlfilesrvcrash2.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,152 @@
+// 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 "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:
+//
+
+/**
+Instructions:
+
+This is a manual test created to verify DEFXXXXX, 2 executables needs to be run to do this test
+1) t_sqlfilesrvcrash1.exe - Generate a corrupted journal file, this will cause the device to reset.
+2) t_sqlfilesrvcrash2.exe - After the reboot, tests if SQL can handle the courrpted journal file.
+
+This test requires a non-rugged drive to store the database file and therefore will only work in hardware mode
+*/
+
+#include <e32test.h>
+#include <f32file.h>
+#include <Sqldb.h>
+
+RTest TheTest(_L("t_sqlfilesrvcrash2 test"));
+
+#if !defined __WINS__ && !defined __WINSCW__
+
+RFs TheFs;
+RSqlDatabase TheDb;
+
+_LIT(KDbName, "E:\\test\\t_sqlfilesrvcrash.db");
+_LIT(KJournalName, "E:\\test\t_sqlfilesrvcrash.db-journal");
+///////////////////////////////////////////////////////////////////////////////////////
+//Deletes all created test files.
+void DeleteTestFiles()
+ {
+ TheDb.Close();
+ (void)RSqlDatabase::Delete(KDbName);
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ RDebug::Print(_L("*** Line %d\r\n"), aLine);
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ RDebug::Print(_L("*** Expected error: %d, got: %d\r\n"), aExpected, aValue);
+ TheTest(EFalse, aLine);
+ }
+ }
+
+#define TEST(arg) ::Check((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check(aValue, aExpected, __LINE__)
+///////////////////////////////////////////////////////////////////////////////////////
+//Creates file session instance and the test directory
+void CreateTestEnv()
+ {
+ TInt err = TheFs.Connect();
+ TEST2(err, KErrNone);
+
+ RFile file;
+ err = file.Open(TheFs, KJournalName, EFileRead);
+ TEST2(err, KErrNone);
+
+ TInt size;
+ err = file.Size(size);
+ TEST2(err, KErrNone);
+ TEST(size > SQLITE_DEFAULT_JOURNAL_SIZE_LIMIT);
+ file.Close();
+ }
+///////////////////////////////////////////////////////////////////////////////////////
+/**
+@SYMTestCaseID PDS-SQL-CT-4165
+@SYMTestCaseDesc Tests for DEF144027: SQL Open returns error if the reported and actual file size are different
+ Requires a corrupted journal file to be created using t_sqlfilesrvcrash1.exe before running
+ this test. If a corrupted journal file exists then check that the opening the database does not
+ return an error.
+@SYMTestActions DEF144027: SQL Open returns error if the reported and actual file size are different
+@SYMTestExpectedResults The RSqlDatabase::Open operation should not fail
+@SYMTestPriority Medium
+@SYMDEF DEF144027
+ DEF144238
+*/
+void DEF144027()
+ {
+ TInt err = TheDb.Open(KDbName);
+ TEST2(err, KErrNone);
+
+ //Lets perform a simple operation to make sure it works
+ err = TheDb.Exec(_L("BEGIN"));
+ TEST(err >= 0);
+
+ err = TheDb.Exec(_L("INSERT INTO t1(NUM) VALUES (55)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("INSERT INTO t2(NUM) VALUES (55)"));
+ TEST2(err, 1);
+
+ err = TheDb.Exec(_L("COMMIT"));
+ TEST(err >= 0);
+
+ TheDb.Close();
+ }
+
+void DoTests()
+ {
+ TheTest.Start(_L(" @SYMTestCaseID:PDS-SQL-CT-4165 DEF144027: SQL Open returns error if the reported and actual file size are different"));
+ DEF144027();
+ }
+#endif //#if !defined __WINS__ && !defined __WINSCW__
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+
+ __UHEAP_MARK;
+
+#if !defined __WINS__ && !defined __WINSCW__
+ DoTests();
+ DeleteTestFiles();
+ TheFs.Close();
+ TheTest.End();
+#else
+ TheTest.Start(_L("This test works only works on hardware!"));
+ TheTest.End();
+#endif
+
+ __UHEAP_MARKEND;
+
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- a/persistentstorage/sql/TEST/t_sqlfserr.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlfserr.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -27,6 +27,9 @@
RTest TheTest(_L("t_sqlfserr test"));
_LIT(KTestDir, "c:\\test\\");
_LIT(KTestDbName, "c:\\test\\t_fserr.db");
+_LIT(KPrivateTestDbName, "c:\\private\\212A2C27\\t_fserr2.db");
+_LIT(KSecureTestDbName, "c:[212A2C27]t_fserr3.db");
+
TFileName TheRmvMediaDbFileName;//The name of the file used for tests on a removable media
RFs TheFs;
RSqlDatabase TheDb;
@@ -55,6 +58,8 @@
void DestroyTestEnv()
{
TheDb.Close();
+ (void)RSqlDatabase::Delete(KSecureTestDbName);
+ (void)RSqlDatabase::Delete(KPrivateTestDbName);
(void)RSqlDatabase::Delete(KTestDbName);
(void)RSqlDatabase::Delete(TheRmvMediaDbFileName);
TheFs.Close();
@@ -117,11 +122,11 @@
sqlite3SymbianLibInit();
}
-TBool CheckRecord(TInt aId, const TDesC& aExpectedName, TBool aOpenDb = ETrue)
+TBool CheckRecord(const TDesC& aDbName, TInt aId, const TDesC& aExpectedName, TBool aOpenDb = ETrue)
{
if(aOpenDb)
{
- TEST2(TheDb.Open(KTestDbName), KErrNone);
+ TEST2(TheDb.Open(aDbName), KErrNone);
}
TBuf<64> sql;
sql.Copy(_L("SELECT Name FROM A WHERE Id="));
@@ -179,13 +184,13 @@
TheDb.Close();//close the database to recover from the last error
//check the database content - all bets are off in a case of an I/O error.
//The existing record might have been updated.
- TEST(CheckRecord(1, _L("Name")) || CheckRecord(1, _L("Name2")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name")) || CheckRecord(KTestDbName, 1, _L("Name2")));
}
else
{
TEST2(err, 1);
//check the database content has been modified by the operation.
- TEST(CheckRecord(1, _L("Name2"), EFalse));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name2"), EFalse));
TheDb.Close();
}
}
@@ -193,7 +198,7 @@
(void)TheFs.SetErrorCondition(KErrNone);
TEST2(err, 1);
//check the database content (transaction durability).
- TEST(CheckRecord(1, _L("Name2")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name2")));
err = RSqlDatabase::Delete(KTestDbName);
TEST2(err, KErrNone);
TheTest.Printf(_L("\r\n"));
@@ -245,13 +250,13 @@
TheDb.Close();//close the database to recover from the last error
//check the database content - all bets are off in a case of an I/O error.
//The existing record might have been updated.
- TEST(CheckRecord(1, _L("Name")) || CheckRecord(1, _L("Name2")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name")) || CheckRecord(KTestDbName, 1, _L("Name2")));
}
else
{
TEST2(err, 1);
//check the database content has been modified by the operation.
- TEST(CheckRecord(1, _L("Name2"), EFalse));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name2"), EFalse));
TheDb.Close();
}
}
@@ -259,12 +264,26 @@
(void)TheFs.SetErrorCondition(KErrNone);
TEST2(err, 1);
//check the database content has been modified by the operation.
- TEST(CheckRecord(1, _L("Name2")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name2")));
err = RSqlDatabase::Delete(KTestDbName);
TEST2(err, KErrNone);
TheTest.Printf(_L("\r\n"));
}
+void CreateTestSecurityPolicy(RSqlSecurityPolicy& aSecurityPolicy)
+ {
+ TSecurityPolicy alwaysPassPolicy(TSecurityPolicy::EAlwaysPass);
+ TInt err = aSecurityPolicy.Create(alwaysPassPolicy);
+ TEST2(err, KErrNone);
+
+ err = aSecurityPolicy.SetDbPolicy(RSqlSecurityPolicy::ESchemaPolicy, alwaysPassPolicy);
+ TEST2(err, KErrNone);
+ err = aSecurityPolicy.SetDbPolicy(RSqlSecurityPolicy::EWritePolicy, alwaysPassPolicy);
+ TEST2(err, KErrNone);
+ err = aSecurityPolicy.SetDbPolicy(RSqlSecurityPolicy::EReadPolicy, alwaysPassPolicy);
+ TEST2(err, KErrNone);
+ }
+
/**
@SYMTestCaseID SYSLIB-SQL-UT-3421
@SYMTestCaseDesc Test for DEF103859 "SQLITE panic, _DEBUG mode, persistent file I/O error simulation".
@@ -279,46 +298,63 @@
*/
void OpenDatabaseTest()
{
- (void)RSqlDatabase::Delete(KTestDbName);
- TInt err = TheDb.Create(KTestDbName);
- TEST2(err, KErrNone);
- err = TheDb.Exec(_L("CREATE TABLE A(Id INTEGER,Name TEXT)"));
- TEST(err >= 0);
- err = TheDb.Exec(_L("INSERT INTO A(Id,Name) VALUES(1,'Name')"));
- TEST2(err, 1);
- TheDb.Close();
-
- err = KErrNotFound;
- for(TInt cnt=1;err<KErrNone;++cnt)
- {
- TheTest.Printf(_L("%d \r"), cnt);
- for (TInt fsError=KErrNotFound;fsError>=KErrDied;--fsError)
- {
- (void)TheFs.SetErrorCondition(fsError, cnt);
- err = TheDb.Open(KTestDbName);
- (void)TheFs.SetErrorCondition(KErrNone);
- if(err != KErrNone)
- {
- TheDb.Close();//close the database to recover from the last error
- //check the database content is still the same as before the "open" call
- TEST(CheckRecord(1, _L("Name")));
- }
- else
- {
- TEST2(err, KErrNone);
- //check the database content is still the same as before the operation, without closing the database
- TEST(CheckRecord(1, _L("Name"), EFalse));
- TheDb.Close();
- }
- }
- }
- (void)TheFs.SetErrorCondition(KErrNone);
- TEST2(err, KErrNone);
- //check the database content is the same as before the operation, after reopening the database.
- TEST(CheckRecord(1, _L("Name")));
- err = RSqlDatabase::Delete(KTestDbName);
- TEST2(err, KErrNone);
- TheTest.Printf(_L("\r\n"));
+ TPtrC dbName[] = {KTestDbName(), KPrivateTestDbName(), KSecureTestDbName()};
+ const TInt KDbNameCnt = sizeof(dbName) / sizeof(dbName[0]);
+ for(TInt k=0;k<KDbNameCnt;++k)
+ {
+ TheTest.Printf(_L("Database: \"%S\"\r\n"), &dbName[k]);
+ (void)RSqlDatabase::Delete(dbName[k]);
+ TInt err = KErrGeneral;
+ if(k == (KDbNameCnt - 1))
+ {
+ RSqlSecurityPolicy policy;
+ CreateTestSecurityPolicy(policy);
+ err = TheDb.Create(dbName[k], policy);
+ policy.Close();
+ }
+ else
+ {
+ err = TheDb.Create(dbName[k]);
+ }
+ TEST2(err, KErrNone);
+ err = TheDb.Exec(_L("CREATE TABLE A(Id INTEGER,Name TEXT)"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("INSERT INTO A(Id,Name) VALUES(1,'Name')"));
+ TEST2(err, 1);
+ TheDb.Close();
+
+ err = KErrNotFound;
+ for(TInt cnt=1;err<KErrNone;++cnt)
+ {
+ TheTest.Printf(_L("%d \r"), cnt);
+ for (TInt fsError=KErrNotFound;fsError>=KErrDied;--fsError)
+ {
+ (void)TheFs.SetErrorCondition(fsError, cnt);
+ err = TheDb.Open(dbName[k]);
+ (void)TheFs.SetErrorCondition(KErrNone);
+ if(err != KErrNone)
+ {
+ TheDb.Close();//close the database to recover from the last error
+ //check the database content is still the same as before the "open" call
+ TEST(CheckRecord(dbName[k], 1, _L("Name")));
+ }
+ else
+ {
+ TEST2(err, KErrNone);
+ //check the database content is still the same as before the operation, without closing the database
+ TEST(CheckRecord(dbName[k], 1, _L("Name"), EFalse));
+ TheDb.Close();
+ }
+ }
+ }
+ (void)TheFs.SetErrorCondition(KErrNone);
+ TEST2(err, KErrNone);
+ //check the database content is the same as before the operation, after reopening the database.
+ TEST(CheckRecord(dbName[k], 1, _L("Name")));
+ err = RSqlDatabase::Delete(dbName[k]);
+ TEST2(err, KErrNone);
+ TheTest.Printf(_L("\r\n"));
+ }
}
/**
@@ -335,32 +371,45 @@
*/
void CreateDatabaseTest()
{
- TInt err = -1;
- for(TInt cnt=1;err<KErrNone;++cnt)
- {
- TheTest.Printf(_L("%d \r"), cnt);
- for (TInt fsError=KErrNotFound;fsError>=KErrDied;--fsError)
- {
- //Ideally, the database should be deleted by the SQL server, if RSqlDatabase::Create() fails.
- //But SetErrorCondition() makes the error persistent, so the SQL server will fail to delete the file.
- //This is the reason, RSqlDatabase::Delete()to be used, before simulating file I/O error.
- (void)RSqlDatabase::Delete(KTestDbName);
- (void)TheFs.SetErrorCondition(fsError, cnt);
- err = TheDb.Create(KTestDbName);
- (void)TheFs.SetErrorCondition(KErrNone);
- TheDb.Close();
- //If err != KErrNone, the database file should have been already deleted by the server and here is
- //the place to check that. But since the file I/O failure simulation makes the file I/O error
- //persistent, the file cannot be deleted by the server, because the "file delete" operation also fails.
- }
- }
- (void)TheFs.SetErrorCondition(KErrNone);
- TheDb.Close();
- TEST2(err, KErrNone);
- TEST(FileExists(KTestDbName));
- err = RSqlDatabase::Delete(KTestDbName);
- TEST2(err, KErrNone);
- TheTest.Printf(_L("\r\n"));
+ RSqlSecurityPolicy policy;
+ CreateTestSecurityPolicy(policy);
+
+ TPtrC dbName[] = {KTestDbName(), KPrivateTestDbName(), KSecureTestDbName()};
+ const TInt KDbNameCnt = sizeof(dbName) / sizeof(dbName[0]);
+ for(TInt k=0;k<KDbNameCnt;++k)
+ {
+ TheTest.Printf(_L("Database: \"%S\"\r\n"), &dbName[k]);
+ TInt err = -1;
+ for(TInt cnt=1;err<KErrNone;++cnt)
+ {
+ TheTest.Printf(_L("%d \r"), cnt);
+ for (TInt fsError=KErrNotFound;fsError>=KErrDied;--fsError)
+ {
+ //Ideally, the database should be deleted by the SQL server, if RSqlDatabase::Create() fails.
+ //But SetErrorCondition() makes the error persistent, so the SQL server will fail to delete the file.
+ //This is the reason, RSqlDatabase::Delete()to be used, before simulating file I/O error.
+ (void)RSqlDatabase::Delete(dbName[k]);
+ (void)TheFs.SetErrorCondition(fsError, cnt);
+ err = (k == (KDbNameCnt - 1)) ? TheDb.Create(dbName[k], policy) : TheDb.Create(dbName[k]);
+ (void)TheFs.SetErrorCondition(KErrNone);
+ TheDb.Close();
+ //If err != KErrNone, the database file should have been already deleted by the server and here is
+ //the place to check that. But since the file I/O failure simulation makes the file I/O error
+ //persistent, the file cannot be deleted by the server, because the "file delete" operation also fails.
+ }
+ }
+ (void)TheFs.SetErrorCondition(KErrNone);
+ TheDb.Close();
+ TEST2(err, KErrNone);
+ if( k != (KDbNameCnt - 1))
+ {
+ TEST(FileExists(dbName[k]));
+ }
+ err = RSqlDatabase::Delete(dbName[k]);
+ TEST2(err, KErrNone);
+ TheTest.Printf(_L("\r\n"));
+ }
+ policy.Close();
}
/**
@@ -415,13 +464,13 @@
stmt.Close();
TheDb.Close();
//check the database content is the same as before the operation
- TEST(CheckRecord(1, _L("Name")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name")));
}
(void)TheFs.SetErrorCondition(KErrNone);
TEST(err >= 0);
TheDb.Close();
//check the database content is the same as before the operation, after reopening the database.
- TEST(CheckRecord(1, _L("Name")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name")));
err = RSqlDatabase::Delete(KTestDbName);
TEST2(err, KErrNone);
TheTest.Printf(_L("\r\n"));
@@ -477,22 +526,22 @@
{
TheDb.Close();//close the database to recover from the last error
//check that the database contains the "name" record that has been inserted before the file I/O failure test.
- TEST(CheckRecord(1, _L("Name")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name")));
}
else
{
TEST2(err, 1);
//check the database content has been modified by the operation, without closing the database.
- TEST(CheckRecord(1, _L("Name"), EFalse));
- TEST(CheckRecord(2, _L("Name2"), EFalse));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name"), EFalse));
+ TEST(CheckRecord(KTestDbName, 2, _L("Name2"), EFalse));
TheDb.Close();
}
}
(void)TheFs.SetErrorCondition(KErrNone);
TEST2(err, 1);
//check the database content (transaction durability).
- TEST(CheckRecord(1, _L("Name")));
- TEST(CheckRecord(2, _L("Name2")));
+ TEST(CheckRecord(KTestDbName, 1, _L("Name")));
+ TEST(CheckRecord(KTestDbName, 2, _L("Name2")));
(void)RSqlDatabase::Delete(KTestDbName);
TheTest.Printf(_L("\r\n"));
}
--- a/persistentstorage/sql/TEST/t_sqlood.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlood.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -127,6 +127,10 @@
TEST2(err, KErrNone);
err = TheFs.MkDir(KTestDir);
+ if(err != KErrNone)
+ {
+ RDebug::Print(_L("*** CreateTestEnv(), RFs::MkDir(), err=%d\r\n"), err);
+ }
TEST(err == KErrNone || err == KErrAlreadyExists);
}
--- a/persistentstorage/sql/TEST/t_sqloslayer.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqloslayer.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -41,6 +41,8 @@
const char* KTestFile1Z = "c:\\test\\t_sqloslayer.bin";
const char* KTestFile2Z = "z:\\test\\TestDb1.db";
const char* KTestFile3Z = "c:\\test\\t_sqloslayer.db";
+_LIT(KPrivateDir, "c:\\private\\21F12127\\");
+const char* KTestFile4Z = "c:\\test\\t_sqloslayer2.db";
//In order to be able to compile the test, the following variables are defined (used inside the OS porting layer, when _SQLPROFILER macro is defined)
#ifdef _SQLPROFILER
@@ -91,6 +93,63 @@
///////////////////////////////////////////////////////////////////////////////////////
+static TInt TheProcessHandleCount = 0;
+static TInt TheThreadHandleCount = 0;
+static TInt TheAllocatedCellsCount = 0;
+
+#ifdef _DEBUG
+static const TInt KBurstRate = 20;
+#endif
+
+static void MarkHandles()
+ {
+ RThread().HandleCount(TheProcessHandleCount, TheThreadHandleCount);
+ }
+
+static void MarkAllocatedCells()
+ {
+ TheAllocatedCellsCount = User::CountAllocCells();
+ }
+
+static void CheckAllocatedCells()
+ {
+ TInt allocatedCellsCount = User::CountAllocCells();
+ TEST2(allocatedCellsCount, TheAllocatedCellsCount);
+ }
+
+static void CheckHandles()
+ {
+ TInt endProcessHandleCount;
+ TInt endThreadHandleCount;
+
+ RThread().HandleCount(endProcessHandleCount, endThreadHandleCount);
+
+ TEST2(TheProcessHandleCount, endProcessHandleCount);
+ TEST2(TheThreadHandleCount, endThreadHandleCount);
+ }
+
+static void OomPreStep(TInt
+#ifdef _DEBUG
+ aFailingAllocationNo
+#endif
+ )
+ {
+ MarkHandles();
+ MarkAllocatedCells();
+ __UHEAP_MARK;
+ __UHEAP_SETBURSTFAIL(RAllocator::EBurstFailNext, aFailingAllocationNo, KBurstRate);
+ }
+
+static void OomPostStep()
+ {
+ __UHEAP_RESET;
+ __UHEAP_MARKEND;
+ CheckAllocatedCells();
+ CheckHandles();
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+
void TestEnvInit()
{
TInt err = TheFs.Connect();
@@ -405,35 +464,14 @@
TInt err = KErrNoMemory;
while(err == KErrNoMemory)
{
- TInt processHandleCnt = 0;
- TInt threadHandleCnt = 0;
- RThread().HandleCount(processHandleCnt, threadHandleCnt);
- TInt allocCellsCnt = User::CountAllocCells();
-
- __UHEAP_MARK;
-
- __UHEAP_SETBURSTFAIL(RHeap::EDeterministic, ++failingAllocNum, 10);
-
+ OomPreStep(++failingAllocNum);
err = sqlite3SymbianLibInit();
-
- __UHEAP_SETBURSTFAIL(RHeap::ENone, 0, 0);
-
- if(err != KErrNoMemory)
- {
- TEST2(err, KErrNone);
- sqlite3SymbianLibFinalize();
- }
-
- __UHEAP_MARKEND;
-
- TInt processHandleCnt2 = 0;
- TInt threadHandleCnt2 = 0;
- RThread().HandleCount(processHandleCnt2, threadHandleCnt2);
- TEST2(processHandleCnt2, processHandleCnt);
- TEST2(threadHandleCnt2, threadHandleCnt);
-
- TInt allocCellsCnt2 = User::CountAllocCells();
- TEST2(allocCellsCnt2, allocCellsCnt);
+ sqlite3SymbianLibFinalize();
+ OomPostStep();
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ }
}
TEST2(err, KErrNone);
TheTest.Printf(_L("=== sqlite3SymbianLibInit() OOM test succeeded at allcoation %d\r\n"), failingAllocNum);
@@ -585,6 +623,94 @@
User::Free(osFile);
}
+void VfsOpenTempFileOomTest()
+ {
+ //Delete all temp files in this test private data cage.
+ CFileMan* fm = NULL;
+ TRAPD(err, fm = CFileMan::NewL(TheFs));
+ TEST2(err, KErrNone);
+ TBuf<50> path;
+ path.Copy(KPrivateDir);
+ path.Append(_L("*.$$$"));
+ err = fm->Delete(path);
+ TEST(err == KErrNone || err == KErrNotFound);
+
+ sqlite3_vfs* vfs = sqlite3_vfs_find(NULL);
+ TEST(vfs != NULL);
+
+ sqlite3_file* osFile = (sqlite3_file*)User::Alloc(vfs->szOsFile);
+ TEST(osFile != NULL);
+
+ TheTest.Printf(_L("Iteration: "));
+ TInt failingAllocNum = 0;
+ err = SQLITE_IOERR_NOMEM;
+ while(err == SQLITE_IOERR_NOMEM)
+ {
+ ++failingAllocNum;
+ TheTest.Printf(_L("%d "), failingAllocNum);
+ OomPreStep(failingAllocNum);
+ int outFlags = 0;
+ err = sqlite3OsOpen(vfs, NULL, osFile, SQLITE_OPEN_READWRITE, &outFlags);
+ if(err == SQLITE_OK)
+ {
+ err = sqlite3OsClose(osFile);
+ }
+ OomPostStep();
+ if(err != SQLITE_OK)
+ {
+ TEST2(err, SQLITE_IOERR_NOMEM);
+ }
+ //If the iteration has failed, then no temp file should exist in the test private data cage.
+ //If the iteration has succeeded, then sqlite3OsClose() should have deleted the temp file.
+ TInt err2 = fm->Delete(path);
+ TEST2(err2, KErrNotFound);
+ }
+ TEST2(err, SQLITE_OK);
+ TheTest.Printf(_L("\r\n=== TVfs::Open(<temp file>) OOM test succeeded at allcoation %d\r\n"), failingAllocNum);
+
+ User::Free(osFile);
+ delete fm;
+ }
+
+void VfsCreateDeleteOnCloseFileOomTest()
+ {
+ sqlite3_vfs* vfs = sqlite3_vfs_find(NULL);
+ TEST(vfs != NULL);
+
+ sqlite3_file* osFile = (sqlite3_file*)User::Alloc(vfs->szOsFile);
+ TEST(osFile != NULL);
+
+ TheTest.Printf(_L("Iteration: "));
+ TInt failingAllocNum = 0;
+ TInt err = SQLITE_IOERR_NOMEM;
+ while(err == SQLITE_IOERR_NOMEM)
+ {
+ ++failingAllocNum;
+ TheTest.Printf(_L("%d "), failingAllocNum);
+ OomPreStep(failingAllocNum);
+ int outFlags = 0;
+ err = sqlite3OsOpen(vfs, KTestFile4Z, osFile, SQLITE_OPEN_CREATE | SQLITE_OPEN_DELETEONCLOSE, &outFlags);
+ if(err == SQLITE_OK)
+ {
+ err = sqlite3OsClose(osFile);
+ }
+ OomPostStep();
+ if(err != SQLITE_OK)
+ {
+ TEST2(err, SQLITE_IOERR_NOMEM);
+ }
+ //Whether the iteration has failed or succeeded, the file should not exist.
+ TPtrC8 ptrname((const TUint8*)KTestFile4Z);
+ TBuf<50> fname;
+ fname.Copy(ptrname);
+ TInt err2 = TheFs.Delete(fname);
+ TEST2(err2, KErrNotFound);
+ }
+ TEST2(err, SQLITE_OK);
+ TheTest.Printf(_L("\r\n=== TVfs::Open(<delete on close file>) OOM test succeeded at allcoation %d\r\n"), failingAllocNum);
+ User::Free(osFile);
+ }
+
/**
@SYMTestCaseID SYSLIB-SQL-CT-1650
@SYMTestCaseDesc SQL, OS porting layer tests.
@@ -612,6 +738,10 @@
ProfilerDisabledTest();
TheTest.Printf(_L("OS porting layer test - negative tests\r\n"));
NegativeTest();
+ TheTest.Printf(_L("TVfs::Open(<temp file>) OOM test\r\n"));
+ VfsOpenTempFileOomTest();
+ TheTest.Printf(_L("TVfs::Open(<'delete on close' file>) OOM test\r\n"));
+ VfsCreateDeleteOnCloseFileOomTest();
}
TInt E32Main()
@@ -619,6 +749,7 @@
TheTest.Title();
CTrapCleanup* tc = CTrapCleanup::New();
+ TheTest(tc != NULL);
__UHEAP_MARK;
--- a/persistentstorage/sql/TEST/t_sqlprivcage.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlprivcage.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -239,6 +239,16 @@
//...create as a non-secure database
err = db.Create(_L("C:[21212122]BBDb2.db"));
TEST2(err, KErrArgument);//secure database name, no security policy
+ //Very long private database name
+ err = db.Create(_L("c:\\private\\21212124\\hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh.db"));
+ TEST2(err, KErrBadName);
+ //Zero length private database name
+ err = db.Create(_L(""));
+ TEST2(err, KErrBadName);
+ //Private database + very long config string
+ _LIT8(KVeryLongConfig, "jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj");
+ err = db.Create(KTestDb2, &KVeryLongConfig);
+ TEST2(err, KErrArgument);
//...create as a secure database
RSqlSecurityPolicy dbSecurity;
TSecurityPolicy policy(TSecurityPolicy::EAlwaysPass);
--- a/persistentstorage/sql/TEST/t_sqlsecurity2.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlsecurity2.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -96,6 +96,14 @@
//Attempt to modify the database schema
err = TheDb.Exec(_L("CREATE TABLE C(FFF TEXT)"));
TEST2(err, KErrPermissionDenied);
+ err = TheDb.Exec(_L("CREATE TEMP TABLE TBL100(COL1 INTEGER)"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("CREATE INDEX IDX100 ON TBL100(COL1)"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP INDEX IDX100"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP TABLE TBL100"));
+ TEST(err >= 0);
//Attempt to update the user data
err = TheDb.Exec(_L("UPDATE A SET F1 = 11 WHERE F1 = 1"));
TEST2(err, KErrPermissionDenied);
--- a/persistentstorage/sql/TEST/t_sqlsecurity3.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlsecurity3.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -104,6 +104,16 @@
//Attempt to modify the database schema
err = TheDb.Exec(_L("CREATE TABLE C(FFF TEXT)"));
TEST2(err, KErrPermissionDenied);
+ err = TheDb.Exec(_L("CREATE TRIGGER upd_a_b1 UPDATE OF B1 ON A BEGIN UPDATE B SET F3 = 'AAAA' WHERE F2 = A.F1; END;"));
+ TEST2(err, KErrPermissionDenied);
+ err = TheDb.Exec(_L("CREATE TEMP TRIGGER upd_a_b1 UPDATE OF B1 ON A BEGIN UPDATE B SET F3 = 'AAAA' WHERE F2 = A.F1; END;"));
+ TEST2(err, KErrPermissionDenied);//Temp trigger which attempts to update one of the tables.
+ err = TheDb.Exec(_L("CREATE VIEW V1 AS SELECT * FROM A"));
+ TEST2(err, KErrPermissionDenied);
+ err = TheDb.Exec(_L("CREATE TEMP VIEW V1 AS SELECT * FROM A"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP VIEW V1"));
+ TEST(err >= 0);
//Attempt to update the user data (but it includes a READ operation)
err = TheDb.Exec(_L("UPDATE A SET F1 = 11 WHERE F1 = 1"));
TEST2(err, KErrPermissionDenied);
--- a/persistentstorage/sql/TEST/t_sqlsecurity4.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlsecurity4.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -41,6 +41,7 @@
RTest TheTest(_L("t_sqlsecurity4 test"));
_LIT(KTestDbName, "c:[21212125]t_ab.db");
+_LIT(KTestDbName2, "c:\\test\\t_sqlsecurity4_2.db");
///////////////////////////////////////////////////////////////////////////////////////
//Restore original test database function
@@ -85,6 +86,65 @@
///////////////////////////////////////////////////////////////////////////////////////
+//This functnion is called while there is an open secure connection.
+//The function will create a new, non-secure connection and check that the non-secure database schema can be modified,
+//while there is another alive, secure database connection.
+void NonSecureDbTest()
+ {
+ (void)RSqlDatabase::Delete(KTestDbName2);
+ RSqlDatabase db;
+ TInt err = db.Create(KTestDbName2);
+ TEST2(err, KErrNone);
+
+ err = db.Exec(_L("CREATE TABLE A(I1 INTEGER, I2 INTEGER)"));
+ TEST(err >= 0);
+ err = db.Exec(_L("CREATE TEMP TABLE B(I1 INTEGER, I2 INTEGER)"));
+ TEST(err >= 0);
+
+ //"CREATE VIRTUAL TABLE" statement not supported
+ err = db.Exec(_L("CREATE VIRTUAL TABLE V1 USING FTS3(ColOne TEXT, ColTwo DATETIME)"));
+ TPtrC msg = db.LastErrorMessage();
+ TheTest.Printf(_L("*** \"CREATE VIRTUAL TABLE\" expected failure, msg=\"%S\", err=%d\r\n"), &msg, err);
+ TEST(err != KErrNone);
+
+ err = db.Exec(_L("CREATE TRIGGER T1 AFTER INSERT ON A BEGIN INSERT INTO B VALUES(new.I1, new.I2); END;"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP TRIGGER T1"));
+ TEST(err >= 0);
+ err = db.Exec(_L("CREATE TEMP TRIGGER T2 AFTER UPDATE OF I1 ON A BEGIN UPDATE B SET I1 = new.I1; END;"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP TRIGGER T2"));
+ TEST(err >= 0);
+
+ err = db.Exec(_L("CREATE VIEW V1 AS SELECT * FROM A"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP VIEW V1"));
+ TEST(err >= 0);
+ err = db.Exec(_L("CREATE TEMP VIEW V2 AS SELECT * FROM A"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP VIEW V2"));
+ TEST(err >= 0);
+
+ err = db.Exec(_L("CREATE INDEX Idx1 ON A(I1)"));
+ TEST(err >= 0);
+ err = db.Exec(_L("ANALYZE A"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP INDEX Idx1"));
+ TEST(err >= 0);
+ err = db.Exec(_L("CREATE INDEX Idx2 ON B(I1)"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP INDEX Idx2"));
+ TEST(err >= 0);
+
+ err = db.Exec(_L("DROP TABLE B"));
+ TEST(err >= 0);
+ err = db.Exec(_L("DROP TABLE A"));
+ TEST(err >= 0);
+
+ db.Close();
+ (void)RSqlDatabase::Delete(KTestDbName2);
+ }
+
/**
@SYMTestCaseID SYSLIB-SQL-CT-1646
@SYMTestCaseDesc Testing database operations on a secure database.
@@ -105,6 +165,26 @@
//Attempt to modify the database schema
err = TheDb.Exec(_L("CREATE TABLE C(FFF TEXT)"));
TEST2(err, KErrPermissionDenied);
+ err = TheDb.Exec(_L("CREATE TEMP TABLE TBL1(COL1 INTEGER, COL2 INTEGER)"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("CREATE TEMP TRIGGER del1 AFTER DELETE ON TBL1 BEGIN DELETE FROM A; END;"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP TRIGGER del1"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("CREATE TEMP VIEW V1 AS SELECT * FROM TBL1"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP VIEW V1"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("CREATE INDEX I1 ON TBL1(COL2)"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP INDEX I1"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP TABLE TBL1"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("ANALYZE A"));
+ TEST2(err, KErrPermissionDenied);
+ err = TheDb.Exec(_L("CREATE VIEW V2 AS SELECT * FROM A"));
+ TEST2(err, KErrPermissionDenied);
//Attempt to update the user data (but it includes a READ operation)
err = TheDb.Exec(_L("UPDATE A SET F1 = 11 WHERE F1 = 1"));
TEST(err >= 0);
@@ -156,6 +236,8 @@
RDebug::Print(_L("Value=%S\r\n"), &p);
stmt.Close();
+ NonSecureDbTest();
+
TheDb.Close();
}
--- a/persistentstorage/sql/TEST/t_sqlsecurity5.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sql/TEST/t_sqlsecurity5.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -115,6 +115,23 @@
//Attempt to modify the database schema
err = TheDb.Exec(_L("CREATE TABLE IF NOT EXISTS C(FFF TEXT)"));
TEST(err >= 0);
+ //Index operations
+ err = TheDb.Exec(_L("CREATE INDEX Cidx ON C(FFF)"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("ANALYZE C"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP INDEX Cidx"));
+ TEST(err >= 0);
+ //Trigger operations
+ err = TheDb.Exec(_L("CREATE TRIGGER T1 AFTER INSERT ON C BEGIN INSERT INTO B VALUES(1, 2); END;"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP TRIGGER T1"));
+ TEST(err >= 0);
+ //View operations
+ err = TheDb.Exec(_L("CREATE VIEW V1 AS SELECT * FROM C"));
+ TEST(err >= 0);
+ err = TheDb.Exec(_L("DROP VIEW V1"));
+ TEST(err >= 0);
//Attempt to update the user data (but it includes a READ operation)
err = TheDb.Exec(_L("UPDATE A SET F1 = 11 WHERE F1 = 1"));
TEST(err >= 0);
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/persistentstorage/sql/TEST/t_sqlstartup.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -0,0 +1,365 @@
+// Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
+// All rights reserved.
+// This component and the accompanying materials are made available
+// under the terms of "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:
+//
+
+#include <e32test.h>
+#include <bautils.h>
+#include "SqlSrvMain.h"
+#include "SqlSrvStartup.h"
+#include "SqlSrvUtil.h"
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+RTest TheTest(_L("t_sqlstartup test"));
+
+static TInt TheProcessHandleCount = 0;
+static TInt TheThreadHandleCount = 0;
+static TInt TheAllocatedCellsCount = 0;
+
+#ifdef _DEBUG
+static const TInt KBurstRate = 20;
+#endif
+
+///////////////////////////////////////////////////////////////////////////////////////
+
+void DeleteTestFiles()
+ {
+ }
+
+///////////////////////////////////////////////////////////////////////////////////////
+///////////////////////////////////////////////////////////////////////////////////////
+//Test macros and functions
+void Check(TInt aValue, TInt aLine)
+ {
+ if(!aValue)
+ {
+ DeleteTestFiles();
+ RDebug::Print(_L("*** Expresssion evaluated to false\r\n"));
+ TheTest(EFalse, aLine);
+ }
+ }
+void Check(TInt aValue, TInt aExpected, TInt aLine)
+ {
+ if(aValue != aExpected)
+ {
+ DeleteTestFiles();
+ RDebug::Print(_L("*** Expected error: %d, got: %d\r\n"), aExpected, aValue);
+ TheTest(EFalse, aLine);
+ }
+ }
+#define TEST(arg) ::Check((arg), __LINE__)
+#define TEST2(aValue, aExpected) ::Check(aValue, aExpected, __LINE__)
+
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+static void MarkHandles()
+ {
+ RThread().HandleCount(TheProcessHandleCount, TheThreadHandleCount);
+ }
+
+static void MarkAllocatedCells()
+ {
+ TheAllocatedCellsCount = User::CountAllocCells();
+ }
+
+static void CheckAllocatedCells()
+ {
+ TInt allocatedCellsCount = User::CountAllocCells();
+ TEST2(allocatedCellsCount, TheAllocatedCellsCount);
+ }
+
+static void CheckHandles()
+ {
+ TInt endProcessHandleCount;
+ TInt endThreadHandleCount;
+
+ RThread().HandleCount(endProcessHandleCount, endThreadHandleCount);
+
+ TEST2(TheProcessHandleCount, endProcessHandleCount);
+ TEST2(TheThreadHandleCount, endThreadHandleCount);
+ }
+
+static void OomPreStep(TInt
+#ifdef _DEBUG
+ aFailingAllocationNo
+#endif
+ )
+ {
+ MarkHandles();
+ MarkAllocatedCells();
+ __UHEAP_MARK;
+ __UHEAP_SETBURSTFAIL(RAllocator::EBurstFailNext, aFailingAllocationNo, KBurstRate);
+ }
+
+static void OomPostStep()
+ {
+ __UHEAP_RESET;
+ __UHEAP_MARKEND;
+ CheckAllocatedCells();
+ CheckHandles();
+ }
+
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////////////////////////////////////////
+
+static void CreateAndDestroySqlServerL()
+ {
+ CSqlServer* server = CSqlServer::NewLC();
+ CleanupStack::PopAndDestroy(server);
+ }
+
+static CSqlServer* CreateSqlServerL()
+ {
+ CSqlServer* server = CSqlServer::NewLC();
+ CleanupStack::Pop(server);
+ return server;
+ }
+
+/**
+@SYMTestCaseID PDS-SQL-UT-4159
+@SYMTestCaseDesc SQL server startup OOM test
+@SYMTestPriority High
+@SYMTestActions Runs the SQL server startup code in an OOM loop.
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144096
+*/
+void SqlServerStartupOomTest()
+ {
+ TInt err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo);
+ TRAP(err, CreateAndDestroySqlServerL());
+ OomPostStep();
+ }
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ }
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\n"), failingAllocationNo);
+ }
+
+/**
+@SYMTestCaseID PDS-SQL-UT-4160
+@SYMTestCaseDesc CSqlServer::GetBackUpListL() OOM test
+@SYMTestPriority High
+@SYMTestActions Calls CSqlServer::GetBackUpListL() in an OOM loop.
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144096
+*/
+void GetBackupListOomTest()
+ {
+ CSqlServer* server = NULL;
+ TRAPD(err, server = CreateSqlServerL());
+ TEST2(err, KErrNone);
+
+ TInt fileCnt = 0;
+ err = KErrNoMemory;
+ TInt failingAllocationNo = 0;
+ TheTest.Printf(_L("Iteration:\r\n"));
+ while(err == KErrNoMemory)
+ {
+ TheTest.Printf(_L(" %d"), ++failingAllocationNo);
+ OomPreStep(failingAllocationNo);
+ const TUid KDbUd = {0x98765432};
+ RArray<TParse> files;
+ TRAP(err, server->GetBackUpListL(KDbUd, files));
+ fileCnt = files.Count();
+ files.Close();
+ OomPostStep();
+ }
+
+ delete server;
+
+ if(err != KErrNoMemory)
+ {
+ TEST2(err, KErrNone);
+ }
+ TheTest.Printf(_L("\r\n===OOM test succeeded at heap failure rate of %d ===\r\nFile count: %d\r\n"), failingAllocationNo, fileCnt);
+ }
+
+/**
+@SYMTestCaseID PDS-SQL-UT-4161
+@SYMTestCaseDesc SQL server startup file I/O error simulation test
+@SYMTestPriority High
+@SYMTestActions Runs the SQL server startup code in a file I/O error simulation loop.
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144096
+*/
+void SqlServerStartupFileIoErrorTest()
+ {
+ RFs fs;
+ TInt err = fs.Connect();
+ TEST2(err, KErrNone);
+
+ for(TInt fsError=KErrNotFound;fsError>=KErrBadName;--fsError)
+ {
+ TheTest.Printf(_L("===Simulated error: %d\r\nIteration: "), fsError);
+ err = KErrNotFound;
+ TInt cnt=1;
+ while(err<KErrNone)
+ {
+ TheTest.Printf(_L("%d "), cnt);
+ (void)fs.SetErrorCondition(fsError, cnt);
+ TRAP(err, CreateAndDestroySqlServerL());
+ (void)fs.SetErrorCondition(KErrNone);
+ if(err != KErrNone)
+ {
+ ++cnt;
+ }
+ }
+ TEST2(err, KErrNone);
+ TheTest.Printf(_L("\r\n===File I/O error simulation test succeeded on iteration %d===\r\n"), cnt);
+ }
+
+ fs.Close();
+ }
+
+/**
+@SYMTestCaseID PDS-SQL-UT-4162
+@SYMTestCaseDesc CSqlServer::GetBackUpListL() file I/O error simulation test
+@SYMTestPriority High
+@SYMTestActions Calls CSqlServer::GetBackUpListL() in a file I/O error simulation loop.
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144096
+*/
+void GetBackupListFileIoErrorTest()
+ {
+ CSqlServer* server = NULL;
+ TRAPD(err, server = CreateSqlServerL());
+ TEST2(err, KErrNone);
+
+ for(TInt fsError=KErrNotFound;fsError>=KErrBadName;--fsError)
+ {
+ TheTest.Printf(_L("===Simulated error: %d\r\nIteration: "), fsError);
+ err = KErrNotFound;
+ TInt fileCnt = 0;
+ TInt cnt=1;
+ while(err<KErrNone)
+ {
+ TheTest.Printf(_L("%d "), cnt);
+ (void)server->Fs().SetErrorCondition(fsError, cnt);
+ const TUid KDbUd = {0x98765432};
+ RArray<TParse> files;
+ TRAP(err, server->GetBackUpListL(KDbUd, files));
+ fileCnt = files.Count();
+ files.Close();
+ (void)server->Fs().SetErrorCondition(KErrNone);
+ if(err != KErrNone)
+ {
+ ++cnt;
+ }
+ }
+ TEST2(err, KErrNone);
+ TheTest.Printf(_L("\r\n===File I/O error simulation test succeeded on iteration %d===\r\nFile count: %d\r\n"), cnt, fileCnt);
+ }
+
+ delete server;
+ }
+
+/**
+@SYMTestCaseID PDS-SQL-UT-4163
+@SYMTestCaseDesc Test for DEF144196: SQL, server code coverage can be improved
+@SYMTestPriority High
+@SYMTestActions Tests the UTF conversion functions implemented in SqlSrvUtil.cpp.
+@SYMTestExpectedResults Test must not fail
+@SYMDEF DEF144196
+*/
+void UtfConversionTest()
+ {
+ ///////// UTF16ToUTF8() ///////////////////////
+ _LIT(KStr16, "abcd");
+ _LIT8(KStr8, "abcd");
+ TBuf8<KMaxFileName + 1> bufout;
+ TBool rc = UTF16ToUTF8(KStr16, bufout);
+ TEST(rc);
+ TEST(bufout == KStr8);
+ //Test where the input buffer contains non-convertible characters
+ TBuf<2> name2;
+ name2.SetLength(2);
+ name2[0] = TChar(0xD800);
+ name2[1] = TChar(0xFC00);
+ rc = UTF16ToUTF8(name2, bufout);
+ TEST(!rc);
+ ///////// UTF16ToUTF8Z() ///////////////////////
+ _LIT8(KStr8Z, "abcd\x0");
+ rc = UTF16ToUTF8Z(KStr16, bufout);
+ TEST(rc);
+ TEST(bufout == KStr8Z);
+ //Test where the input buffer contains non-convertible characters
+ rc = UTF16ToUTF8Z(name2, bufout);
+ TEST(!rc);
+ ///////// UTF16ZToUTF8Z() ///////////////////////
+ _LIT(KStr16Z, "abcd\x0");
+ rc = UTF16ZToUTF8Z(KStr16Z, bufout);
+ TEST(rc);
+ TEST(bufout == KStr8Z);
+ //Test where the input buffer contains non-convertible characters
+ TBuf<3> name3;
+ name3.SetLength(3);
+ name3[0] = TChar(0xD800);
+ name3[1] = TChar(0xFC00);
+ name3[2] = TChar(0x0000);
+ rc = UTF16ZToUTF8Z(name3, bufout);
+ TEST(!rc);
+ }
+
+void DoTests()
+ {
+ CActiveScheduler* scheduler = new CActiveScheduler;
+ TEST(scheduler != NULL);
+ CActiveScheduler::Install(scheduler);
+
+ TheTest.Start(_L(" @SYMTestCaseID:PDS-SQL-UT-4159 SQL server startup OOM test"));
+ SqlServerStartupOomTest();
+
+ TheTest.Next (_L(" @SYMTestCaseID:PDS-SQL-UT-4160 CSqlServer::GetBackUpListL() OOM test"));
+ GetBackupListOomTest();
+
+ TheTest.Next (_L(" @SYMTestCaseID:PDS-SQL-UT-4161 SQL server startup file I/O error simulation test"));
+ SqlServerStartupFileIoErrorTest();
+
+ TheTest.Next (_L(" @SYMTestCaseID:PDS-SQL-UT-4162 CSqlServer::GetBackUpListL() file I/O error simulation test"));
+ GetBackupListFileIoErrorTest();
+
+ TheTest.Next (_L(" @SYMTestCaseID:PDS-SQL-UT-4163 SQL server, UTF conversion test"));
+ UtfConversionTest();
+
+ delete scheduler;
+ }
+
+TInt E32Main()
+ {
+ TheTest.Title();
+
+ CTrapCleanup* tc = CTrapCleanup::New();
+
+ __UHEAP_MARK;
+
+ DoTests();
+ DeleteTestFiles();
+
+ __UHEAP_MARKEND;
+
+ TheTest.End();
+ TheTest.Close();
+
+ delete tc;
+
+ User::Heap().Check();
+ return KErrNone;
+ }
--- a/persistentstorage/sqlite3api/OsLayer/FileBuf64.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sqlite3api/OsLayer/FileBuf64.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -186,44 +186,6 @@
#endif//_DEBUG
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-/////////////////////////// MFileInitializer64 /////////////////////////////////////////////////////////////
-//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
-
-/**
-MFileInitializer64 interface provides only one abstract method - Init() that is used during the initialization of
-the RFileBuf64 objects.
-Here is what is the problem MFileInitializer64 tries to solve.
-RFileBuf64 has 4 different "resource acquisition" methods - Create(), Open() and Temp().
-They perform different actions and have different input arguments.
-This is the variable part of the RFileBuf64 initialization.
-Apart from that, RFileBuf64 has a "fixed" initialization part that does not change whatever the variable part is.
-If MFileInitializer64 interface is not used then the following chunk of code has to be duplicated 4 times:
-@code
- TInt err = do_fixed_init();
- if(err == KErrNone)
- {
- err = do_variable_init();
- if(err != KErrNone)
- {
- revert_fixed_init();
- }
- }
- return err;
-@endcode
-In order to avoid the code duplication, the fixed part of the initialization is moved to RFileBuf64::DoInit(), which
-is given a reference to a MFileInitializer64 derived class that performas the variable part of the initialization.
-4 different MFileInitializer64 derived classes are provided for the 4 different "resource acquisition" methods.
-All they store the variable part of the RFileBuf64 initialization parameters and implement MFileInitializer64::Init().
-
-@see RFileBuf64::DoInit()
-@internalComponent
-*/
-struct MFileInitializer64
- {
- virtual TInt Init(RFile64& aFile) = 0;
- };
-
-//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////// RFileBuf64 /////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@@ -256,7 +218,6 @@
@see TFileMode
@see RFile64::Create()
-@see MFileInitializer64
@panic FBuf64 7 In _DEBUG mode - Invalid aFs object (null file session handle).
@panic FBuf64 10 In _DEBUG mode - Invalid file name length (zero file name length).
@@ -266,24 +227,12 @@
__FBUF64_ASSERT(aFs.Handle() != 0, EFBufPanicFsHandle);
__FBUF64_ASSERT(aFileName.Length() > 0, EFBufPanicFileNameLen);
- struct TFileCreateInitializer64 : public MFileInitializer64
- {
- inline TFileCreateInitializer64(RFs& aFs, const TDesC& aFileName, TUint aFileMode) :
- iFs(aFs),
- iFileName(aFileName),
- iFileMode(aFileMode)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.Create(iFs, iFileName, iFileMode);
- }
- RFs& iFs;
- const TDesC& iFileName;
- TUint iFileMode;
- } initializer(aFs, aFileName, aFileMode);
-
- return DoInit(initializer);
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.Create(aFs, aFileName, aFileMode);
+ }
+ return DoPostInit(err);
}
/**
@@ -300,7 +249,6 @@
@see TFileMode
@see RFile64::Open()
-@see MFileInitializer64
@panic FBuf64 7 In _DEBUG mode - Invalid aFs object (null file session handle).
@panic FBuf64 10 In _DEBUG mode - Invalid file name length (zero file name length).
@@ -309,25 +257,13 @@
{
__FBUF64_ASSERT(aFs.Handle() != 0, EFBufPanicFsHandle);
__FBUF64_ASSERT(aFileName.Length() > 0, EFBufPanicFileNameLen);
-
- struct TFileOpenInitializer64 : public MFileInitializer64
- {
- inline TFileOpenInitializer64(RFs& aFs, const TDesC& aFileName, TUint aFileMode) :
- iFs(aFs),
- iFileName(aFileName),
- iFileMode(aFileMode)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.Open(iFs, iFileName, iFileMode);
- }
- RFs& iFs;
- const TDesC& iFileName;
- TUint iFileMode;
- } initializer(aFs, aFileName, aFileMode);
-
- return DoInit(initializer);
+
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.Open(aFs, aFileName, aFileMode);
+ }
+ return DoPostInit(err);
}
/**
@@ -346,34 +282,19 @@
@see TFileMode
@see RFile64::Temp()
-@see MFileInitializer64
@panic FBuf64 7 In _DEBUG mode - Invalid aFs object (null file session handle).
*/
TInt RFileBuf64::Temp(RFs& aFs, const TDesC& aPath, TFileName& aFileName, TUint aFileMode)
{
__FBUF64_ASSERT(aFs.Handle() != 0, EFBufPanicFsHandle);
-
- struct TFileTempInitializer64 : public MFileInitializer64
- {
- inline TFileTempInitializer64(RFs& aFs, const TDesC& aPath, TFileName& aFileName, TUint aFileMode) :
- iFs(aFs),
- iPath(aPath),
- iFileName(aFileName),
- iFileMode(aFileMode)
- {
- }
- virtual TInt Init(RFile64& aFile)
- {
- return aFile.Temp(iFs, iPath, iFileName, iFileMode);
- }
- RFs& iFs;
- const TDesC& iPath;
- TFileName& iFileName;
- TUint iFileMode;
- } initializer(aFs, aPath, aFileName, aFileMode);
-
- return DoInit(initializer);
+
+ TInt err = DoPreInit();
+ if(err == KErrNone)
+ {
+ err = iFile.Temp(aFs, aPath, aFileName, aFileMode);
+ }
+ return DoPostInit(err);
}
/**
@@ -397,6 +318,15 @@
/**
Calculates and sets optimal read-ahead buffer size.
+aBlockSize and aReadRecBufSize values are retrieved by the caller from the file system.
+
+Initialization rules:
+Rule 1: If aReadRecBufSize is positive, bigger than the default read-ahead and
+ a power of two then the read-ahead value will be
+ initialized with aReadRecBufSize (if aReadRecBufSize is less than the buffer capacity otherwise
+ the buffer capacity will be used as a read-ahead value).
+Rule 2: If rule#1 is not applicable then the same checks, as in rule#1, are performed this time for aBlockSize.
+ If aBlockSize passes the checks then it will be used as a read-ahead value.
@param aBlockSize The size of a file block in bytes
@param aReadRecBufSize The recommended buffer size for optimised reading performance
@@ -477,13 +407,13 @@
TUint8* outptr = const_cast <TUint8*> (aDes.Ptr());
while(len > 0 && err == KErrNone && aFilePos < iFileSize)
{
- //1. If part of all of the data is in the buffer - copy the data to the target location
+ //1. If part or all of the data is in the buffer - copy the data to the target location
if(aFilePos >= iFilePos && aFilePos < (iFilePos + iLength))
{
- TInt l = Min(len, (iFilePos + iLength - aFilePos));
- outptr = Mem::Copy(outptr, iBase + (aFilePos - iFilePos), l);
- len -= l;
- aFilePos += l;
+ TInt blocklen = Min(len, (iFilePos + iLength - aFilePos));
+ outptr = Mem::Copy(outptr, iBase + (aFilePos - iFilePos), blocklen);
+ len -= blocklen;
+ aFilePos += blocklen;
}
//2. Perform a read-ahead operation
else
@@ -495,7 +425,7 @@
break;
}
if(iNextReadFilePos != aFilePos)
- {//Direct "file read" operation
+ {//Guessed read ahead was wrong. Direct "file read" operation
iNextReadFilePosHits = 0;
TPtr8 ptr2(outptr, len);
err = iFile.Read(aFilePos, ptr2);
@@ -790,31 +720,38 @@
}
/**
-Performs the fixed part of the RFileBuf64 initialization and then calls MFileInitializer64::Init() to perform
-the variable part of the initialization.
+Initializes RFileBuf64 data members with their initial values.
+Allocates memory for the file buffer.
+
+@return KErrNone if successful,
+ KErrNoMemory out of memory;
+*/
+TInt RFileBuf64::DoPreInit()
+ {
+ DoDiscard();
+ iReadAheadSize = RFileBuf64::KDefaultReadAheadSize;
+ iBase = static_cast <TUint8*> (User::Alloc(iCapacity));
+ return iBase ? KErrNone : KErrNoMemory;
+ }
-@param aFileInitializer A reference to an initializer object that implements MFileInitializer64::Init()
+/**
+Performs post-initialization of the RFileBuf64 object.
+If aInitErr is not KErrNone, then the buffer memory will be released.
+The function returns the aInitErr value to the caller.
+@param aInitErr The result of the performed before the call RFileBuf64 initialization.
+
@return KErrNone if successful, otherwise one of the other system-wide error codes.
*/
-TInt RFileBuf64::DoInit(MFileInitializer64& aFileInitializer)
- {
- DoDiscard();
- iReadAheadSize = RFileBuf64::KDefaultReadAheadSize;
- TInt err = KErrNoMemory;
- iBase = static_cast <TUint8*> (User::Alloc(iCapacity));
- if(!iBase)
- {
- return KErrNoMemory;
- }
- err = aFileInitializer.Init(iFile);
- if(err != KErrNone)
- {
- User::Free(iBase);
- iBase = 0;
- }
- return err;
- }
+TInt RFileBuf64::DoPostInit(TInt aInitErr)
+ {
+ if(aInitErr != KErrNone)
+ {
+ User::Free(iBase);
+ iBase = 0;
+ }
+ return aInitErr;
+ }
/**
Discards the content of the RFileBuf64 object returning it to the state as if it has just been created.
--- a/persistentstorage/sqlite3api/OsLayer/FileBuf64.h Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sqlite3api/OsLayer/FileBuf64.h Fri Mar 12 15:51:02 2010 +0200
@@ -18,9 +18,6 @@
#include <f32file.h>
#include <f32file64.h>
-//Forward declaration
-struct MFileInitializer64;
-
/**
The RFileBuf64 class provides buffered file read/write operations on a single RFile64 object.
RFileBuf64::Read() and RFileBuf64::Write() methods may boost the performance of the read/write file operations up to 30%
@@ -47,28 +44,31 @@
In details, to create a file and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.Create(fs, <file name>, <file mode>);
+ err = fbuf.Create(fs, <file name>, <file mode>);
//check the error
To open an existing file and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.Open(fs, <file name>, <file mode>);
+ err = fbuf.Open(fs, <file name>, <file mode>);
//check the error
To create a temporary file and access it through a RFileBuf64 object:
RFs fs;
- //initialize the file session
+ TInt err = fs.Connect();
+ //check the error
...
RFileBuf64 fbuf(<N>); //<N> is the buffer capacity in bytes
- TInt err = fbuf.Temp(fs, <path>, <file name>, <file mode>);
+ err = fbuf.Temp(fs, <path>, <file name>, <file mode>);
//check the error
- if the RFileBuf64 object is initialised successfully, now the public RFileBuf64 methods can be called to perform
@@ -90,7 +90,7 @@
@endcode
Implementation notes: the current RFileBuf64 implementation is optimised for use by the SQLite OS porting layer.
- After a detailed investigation of the performed by SQLite file read/write operations it was found that buffering of
+ After investigation of SQLite file read/write operations it was found that buffering of
two or more logical file writes into a single physical file write has a positive impact (as expected) on the performance
of the database write operations. But the picture is quite different for the file read operations. The database data is
organised in pages with fixed size. After a database is created and set of insert/update/delete operations is performed
@@ -150,7 +150,8 @@
private:
void Invariant() const;
- TInt DoInit(MFileInitializer64& aFileInitializer);
+ TInt DoPreInit();
+ TInt DoPostInit(TInt aInitErr);
void DoDiscard();
TInt DoFileSize();
TInt DoSetFileSize(TInt64 aFileSize);
--- a/persistentstorage/sqlite3api/OsLayer/os_symbian_mt.cpp Sat Feb 20 00:33:55 2010 +0200
+++ b/persistentstorage/sqlite3api/OsLayer/os_symbian_mt.cpp Fri Mar 12 15:51:02 2010 +0200
@@ -547,8 +547,7 @@
SQLite OS porting layer API.
Closes the file referred by aDbFile parameter.
-If aDbFile, which is actually a pointer to a TDbFile instance, the iFullName data member is not NULL,
-then the file will be deleted.
+If aDbFile.iFullName data member is not NULL, then the file will be deleted.
@param aDbFile A pointer to a TDbFile instance, than contains the file handle to be closed.
@@ -562,7 +561,8 @@
TDbFile& dbFile = ::DbFile(aDbFile);
dbFile.iFileBuf.Close();
if(dbFile.iFullName)
- {
+ {//"iFullName" will not be NULL only when TVfs::Open() is called with SQLITE_OPEN_DELETEONCLOSE flag.
+ //That means - SQlite expects the file to be deleted after the file close operation.
(void)TStaticFs::Fs().Delete(*dbFile.iFullName);
delete dbFile.iFullName;
dbFile.iFullName = NULL;