persistentstorage/sql/TEST/t_sqlload.cpp
changeset 0 08ec8eefde2f
child 12 6b6fd149daa2
equal deleted inserted replaced
-1:000000000000 0:08ec8eefde2f
       
     1 // Copyright (c) 2006-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 //
       
    15 
       
    16 #include <e32test.h>
       
    17 #include <e32math.h>
       
    18 #include <bautils.h>
       
    19 #include <sqldb.h>
       
    20 #include "SqlResourceTester.h"
       
    21 
       
    22 ///////////////////////////////////////////////////////////////////////////////////////
       
    23 
       
    24 #define UNUSED_VAR(a) (a) = (a)
       
    25 
       
    26 RTest TheTest(_L("t_sqlload test"));
       
    27 
       
    28 _LIT(KTestDir, "c:\\test\\");
       
    29 _LIT(KTestDbName1, "c:\\test\\t_sqlload_1.db");
       
    30 _LIT(KTestDbName2, "c:\\test\\t_sqlload_2.db");
       
    31 _LIT(KTestDbName3, "c:\\test\\t_sqlload_3.db");
       
    32 
       
    33 //Test thread count
       
    34 const TInt KTestThreadCnt = 4;
       
    35 
       
    36 //Test database names
       
    37 const TPtrC KTestDbNames[] =
       
    38 	{
       
    39 	KTestDbName1(),
       
    40 	KTestDbName2(),
       
    41 	KTestDbName3()
       
    42 	};
       
    43 
       
    44 //Test database count
       
    45 const TInt KTestDbCnt = sizeof(KTestDbNames) / sizeof(KTestDbNames[0]);
       
    46 
       
    47 //Test duration
       
    48 const TInt KTestDuration = 120;//seconds
       
    49 
       
    50 //Test record count
       
    51 const TInt KRecordCnt = 100;
       
    52 //Record count which will be used in the test SQL queries
       
    53 const TInt KQueriedRecordCnt = 40;
       
    54 //Every SQL query will be processed (stepped) in KTestStepCnt steps.
       
    55 const TInt KTestStepCnt = 4;
       
    56 //RSqlStatement object count which will be used in the tests
       
    57 const TInt KStatementCnt = 10;
       
    58 //Max allowed alive RSqlStatement objects per thread
       
    59 const TInt KMaxStatementPerThread = 30;
       
    60 //Binary data length
       
    61 const TInt KBinDataLen = 2003;
       
    62 
       
    63 ///////////////////////////////////////////////////////////////////////////////////////
       
    64 
       
    65 void DeleteTestFiles()
       
    66 	{
       
    67 	RSqlDatabase::Delete(KTestDbName3);
       
    68 	RSqlDatabase::Delete(KTestDbName2);
       
    69 	RSqlDatabase::Delete(KTestDbName1);
       
    70 	}
       
    71 
       
    72 ///////////////////////////////////////////////////////////////////////////////////////
       
    73 ///////////////////////////////////////////////////////////////////////////////////////
       
    74 //Test macros and functions
       
    75 void Check1(TInt aValue, TInt aLine, TBool aPrintThreadName = EFalse)
       
    76 	{
       
    77 	if(!aValue)
       
    78 		{
       
    79 		DeleteTestFiles();
       
    80 		if(aPrintThreadName)
       
    81 			{
       
    82 			RThread th;
       
    83 			TName name = th.Name();
       
    84 			RDebug::Print(_L("*** Thread %S, Line %d\r\n"), &name, aLine);
       
    85 			}
       
    86 		else
       
    87 			{
       
    88 			RDebug::Print(_L("*** Line %d\r\n"), aLine);
       
    89 			}
       
    90 		TheTest(EFalse, aLine);
       
    91 		}
       
    92 	}
       
    93 void Check2(TInt aValue, TInt aExpected, TInt aLine, TBool aPrintThreadName = EFalse)
       
    94 	{
       
    95 	if(aValue != aExpected)
       
    96 		{
       
    97 		DeleteTestFiles();
       
    98 		if(aPrintThreadName)
       
    99 			{
       
   100 			RThread th;
       
   101 			TName name = th.Name();
       
   102 			RDebug::Print(_L("*** Thread %S, Line %d Expected error: %d, got: %d\r\n"), &name, aLine, aExpected, aValue);
       
   103 			}
       
   104 		else
       
   105 			{
       
   106 			RDebug::Print(_L("*** Line %d, Expected error: %d, got: %d\r\n"), aLine, aExpected, aValue);
       
   107 			}
       
   108 		TheTest(EFalse, aLine);
       
   109 		}
       
   110 	}
       
   111 #define TEST(arg) ::Check1((arg), __LINE__)
       
   112 #define TEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__)
       
   113 #define TTEST(arg) ::Check1((arg), __LINE__, ETrue)
       
   114 #define TTEST2(aValue, aExpected) ::Check2(aValue, aExpected, __LINE__, ETrue)
       
   115 
       
   116 ///////////////////////////////////////////////////////////////////////////////////////
       
   117 
       
   118 void CreateTestDir()
       
   119     {
       
   120     RFs fs;
       
   121 	TInt err = fs.Connect();
       
   122 	TEST2(err, KErrNone);
       
   123 
       
   124 	err = fs.MkDir(KTestDir);
       
   125 	TEST(err == KErrNone || err == KErrAlreadyExists);
       
   126 
       
   127 	fs.Close();
       
   128 	}
       
   129 
       
   130 ///////////////////////////////////////////////////////////////////////////////////////
       
   131 
       
   132 void CreateTestDatabases()
       
   133 	{
       
   134 	HBufC8* recData = HBufC8::New(KBinDataLen * 2 + 50);//"* 2" - hex values for the INSERT SQL statement
       
   135 	TEST(recData != NULL);
       
   136 	TPtr8 sql = recData->Des();
       
   137 
       
   138 	for(TInt dbIdx=0;dbIdx<KTestDbCnt;++dbIdx)
       
   139 		{
       
   140 		//Create test database
       
   141 		RSqlDatabase db;
       
   142 		TInt err = db.Create(KTestDbNames[dbIdx]);
       
   143 		TEST2(err, KErrNone);
       
   144 
       
   145 		//Create test table
       
   146 		_LIT8(KCreateSql, "CREATE TABLE A(F1 INTEGER, F2 BLOB)");
       
   147 		err = db.Exec(KCreateSql);
       
   148 		TEST(err >= 0);
       
   149 
       
   150 		//Insert records in the test table
       
   151 		for(TInt recIdx=1;recIdx<=KRecordCnt;++recIdx)
       
   152 			{
       
   153 			_LIT8(KInsertSql, "INSERT INTO A(F1, F2) VALUES(");
       
   154 			sql.Copy(KInsertSql);
       
   155 			sql.AppendNum((TInt64)recIdx);
       
   156 			sql.Append(_L(", X'"));
       
   157 			for(TInt k=0;k<KBinDataLen;++k)
       
   158 				{
       
   159 				sql.AppendFormat(_L8("%02X"), recIdx);
       
   160 				}
       
   161 			sql.Append(_L("')"));
       
   162 			err = db.Exec(sql);
       
   163 			TEST2(err, 1);
       
   164 			}
       
   165 
       
   166 		db.Close();
       
   167 		}
       
   168 
       
   169 	delete recData;
       
   170 	}
       
   171 
       
   172 //Structure used by the test thread function for orginizing its set of test data.
       
   173 struct TSqlStatement
       
   174 	{
       
   175 	RSqlStatement	iObj;
       
   176 	TBool 			iAlive;			//Non-zero if iObj is alive
       
   177 	TInt			iCurIndex;		//The number of the current record in the set controlled by iObj statement
       
   178 	TInt			iEndIndex;		//The last record number in the set controlled by iObj statement
       
   179 	TInt			iCount;			//Records count in the set controlled by iObj statement
       
   180 	};
       
   181 	
       
   182 typedef RArray<TSqlStatement> RSqlStatementArray;	
       
   183 
       
   184 //Inits the random numbers generator.
       
   185 //Opens one of the test databases.
       
   186 void PreTest(RSqlDatabase& aDb, TInt64& aSeed, TName& aThreadName)
       
   187 	{
       
   188 	RThread currThread;
       
   189 	
       
   190 	//Init the random numbers generator
       
   191 	TTime now;
       
   192 	now.UniversalTime();
       
   193 	aSeed = now.Int64() + currThread.Id();
       
   194 
       
   195 	//Open one of the test databases
       
   196 	const TInt KDbIndex = Math::Rand(aSeed) % KTestDbCnt;
       
   197 
       
   198 	aThreadName = currThread.Name();
       
   199 	RDebug::Print(_L("=== Thread %S, database %S\r\n"), &aThreadName, &KTestDbNames[KDbIndex]);
       
   200 
       
   201 	TInt err = aDb.Open(KTestDbNames[KDbIndex]);
       
   202 	TTEST2(err, KErrNone);
       
   203 	}
       
   204 
       
   205 //Creates N statements, where 0 < N < KStatementCnt
       
   206 TInt CreateStatements(RSqlDatabase& aDb, TInt64& aSeed, RSqlStatementArray& aStmtArray)
       
   207 	{
       
   208 	TInt stmtCount = Math::Rand(aSeed) % KStatementCnt;
       
   209 	if(stmtCount == 0)
       
   210 		{
       
   211 		stmtCount = 1;
       
   212 		}
       
   213 	for(TInt i=0;i<stmtCount;++i)
       
   214 		{
       
   215 		TSqlStatement stmt;
       
   216 		stmt.iAlive = EFalse;
       
   217 		stmt.iCount = KQueriedRecordCnt;
       
   218 		stmt.iCurIndex = Math::Rand(aSeed) % KRecordCnt;
       
   219 		if(stmt.iCurIndex == 0)
       
   220 			{
       
   221 			stmt.iCurIndex = 1;
       
   222 			}
       
   223 		if(stmt.iCurIndex > (KRecordCnt - KQueriedRecordCnt))
       
   224 			{
       
   225 			stmt.iCurIndex = KRecordCnt - KQueriedRecordCnt;
       
   226 			}
       
   227 		stmt.iEndIndex = stmt.iCurIndex + KQueriedRecordCnt;
       
   228 		TBuf8<100> sql;
       
   229 		sql.Copy(_L8("SELECT * FROM A WHERE F1 >= "));
       
   230 		sql.AppendNum(stmt.iCurIndex);
       
   231 		sql.Append(_L8(" AND F1 < "));
       
   232 		sql.AppendNum(stmt.iEndIndex);
       
   233 		TInt err = stmt.iObj.Prepare(aDb, sql);
       
   234 		TTEST2(err, KErrNone);
       
   235 		stmt.iAlive = ETrue;
       
   236 		err = aStmtArray.Append(stmt);
       
   237 		TTEST2(err, KErrNone);
       
   238 		}
       
   239 	return stmtCount;		
       
   240 	}
       
   241 	
       
   242 //For each alive statement object - do (TSqlStatement::iCount / KTestStepCnt)
       
   243 //RSqlStatement::Next() calls. If the Next() call reaches the end - close the statement object.
       
   244 TInt ProcessStatements(RSqlStatementArray& aStmtArray)
       
   245 	{
       
   246 	const TInt KTotalStmtCount = aStmtArray.Count();
       
   247 	TInt alive = 0;
       
   248 	TInt completed = 0;
       
   249 	for(TInt k=0;k<KTotalStmtCount;++k)
       
   250 		{
       
   251 		TSqlStatement& stmt = aStmtArray[k];
       
   252 		if(stmt.iAlive)
       
   253 			{
       
   254 			++alive;
       
   255 			TInt endIndex = stmt.iCurIndex + stmt.iCount / KTestStepCnt;
       
   256 			if(endIndex <= stmt.iEndIndex)
       
   257 				{
       
   258 				while(stmt.iCurIndex < endIndex)
       
   259 					{
       
   260 					TInt err = stmt.iObj.Next();
       
   261 					TTEST2(err, KSqlAtRow);
       
   262 					//test column values
       
   263 					TInt val1 = stmt.iObj.ColumnInt(0);
       
   264 					TTEST(val1 == stmt.iCurIndex);
       
   265 					RSqlColumnReadStream strm;
       
   266 					err = strm.ColumnBinary(stmt.iObj, 1);
       
   267 					TTEST2(err, KErrNone);
       
   268 					for(TInt ii=0;ii<KBinDataLen;++ii)
       
   269 						{
       
   270 						TUint8 byte = 0;
       
   271 						TRAP(err, byte = strm.ReadUint8L());
       
   272 						TTEST2(err, KErrNone);
       
   273 						TTEST(byte == (TUint8)val1);
       
   274 						}
       
   275 					strm.Close();
       
   276 					++stmt.iCurIndex;
       
   277 					}
       
   278 				}
       
   279 			if(stmt.iCurIndex >= stmt.iEndIndex)
       
   280 				{
       
   281 				stmt.iObj.Close();
       
   282 				stmt.iAlive = EFalse;
       
   283 				++completed;
       
   284 				}
       
   285 			}
       
   286 		}
       
   287 	return completed;
       
   288 	}
       
   289 
       
   290 //Close up to N statements, where 0 < N < KStatementCnt
       
   291 TInt CloseStatements(RSqlStatementArray& aStmtArray, TInt64& aSeed)
       
   292 	{
       
   293 	TInt stmtCount = Math::Rand(aSeed) % KStatementCnt;
       
   294 	if(stmtCount == 0)
       
   295 		{
       
   296 		stmtCount = 1;
       
   297 		}
       
   298 	const TInt KTotalStmtCount = aStmtArray.Count();
       
   299 	TInt closed = 0;
       
   300 	for(TInt j=0;j<stmtCount;++j)
       
   301 		{
       
   302 		const TInt KIdx = Math::Rand(aSeed) % KTotalStmtCount;
       
   303 		TInt idx = KIdx;
       
   304 		while((idx = (++idx % KTotalStmtCount)) != KIdx)
       
   305 			{
       
   306 			if(aStmtArray[idx].iAlive)
       
   307 				{
       
   308 				aStmtArray[idx].iObj.Close();
       
   309 				aStmtArray[idx].iAlive = EFalse;
       
   310 				++closed;
       
   311 				break;
       
   312 				}
       
   313 			}
       
   314 		}
       
   315 	return closed;
       
   316 	}
       
   317 
       
   318 //Counts the alive statements
       
   319 TInt AliveStatementsCount(RSqlStatementArray& aStmtArray)
       
   320 	{
       
   321 	TInt aliveCnt = 0;
       
   322 	const TInt KTotalStmtCount = aStmtArray.Count();
       
   323 	for(TInt l=0;l<KTotalStmtCount;++l)
       
   324 		{
       
   325 		if(aStmtArray[l].iAlive)
       
   326 			{
       
   327 			++aliveCnt;
       
   328 			}
       
   329 		}
       
   330 	return aliveCnt;
       
   331 	}
       
   332 	
       
   333 //Close all alive statements
       
   334 void CloseAllStatements(RSqlStatementArray& aStmtArray)
       
   335 	{
       
   336 	const TInt KTotalStmtCount = aStmtArray.Count();
       
   337 	for(TInt i=0;i<KTotalStmtCount;++i)
       
   338 		{
       
   339 		if(aStmtArray[i].iAlive)
       
   340 			{
       
   341 			aStmtArray[i].iObj.Close();
       
   342 			}
       
   343 		}
       
   344 	TTEST2(TSqlResourceTester::Count(), 0);
       
   345 	}
       
   346 
       
   347 //Removes the already closed statements and compresses the array
       
   348 void RemoveDeadStatements(RSqlStatementArray& aStmtArray)
       
   349 	{
       
   350 	for(TInt i=aStmtArray.Count()-1;i>=0;--i)
       
   351 		{
       
   352 		if(!aStmtArray[i].iAlive)
       
   353 			{
       
   354 			aStmtArray.Remove(i);
       
   355 			}
       
   356 		}
       
   357 	aStmtArray.Compress();		
       
   358 	}
       
   359 
       
   360 //Close statement objects, statements array and the database object
       
   361 TInt PostTest(RSqlDatabase& aDb, RSqlStatementArray& aStmtArray)
       
   362 	{
       
   363 	TInt statementsAlive = AliveStatementsCount(aStmtArray);
       
   364 	CloseAllStatements(aStmtArray);
       
   365 	aStmtArray.Close();
       
   366 	aDb.Close();
       
   367 	return statementsAlive;
       
   368 	}
       
   369 
       
   370 //Test thread function
       
   371 //The thread function works with a set of TSqlStatement objects
       
   372 //The test consists of 4 steps:
       
   373 //Step 1: the test thread creates m TSqlStatement objects, 0 < m < KStatementCnt.
       
   374 //		  With each of the created TSqlStatement objects the test thread prepares SELECT SQL query
       
   375 //        "SELECT * FROM A WHERE F1 >= K1 AND F1 < K2", where K1 is random generated number, such that:
       
   376 //        0 < K1 < (KRecordCnt - KQueriedRecordCnt)
       
   377 //        K2 = K1 + KQueriedRecordCnt
       
   378 //		  All just created TSqlStatement objects are marked as alive.
       
   379 //Step 2: For each alive TSqlStatement object the test thread calls iObj.Next() method KTestStepCnt times,
       
   380 //        KTestStepCnt < KQueriedRecordCnt.
       
   381 //        The column values are retrieved and checked.
       
   382 //Step 3: the test thread closes n TSqlStatement objects, 0 < n < KStatementCnt.
       
   383 //Step 4: the test thread counts how many alive TSqlStatement objects are there.
       
   384 //        If this count > KMaxStatementPerThread then the test thread closes all alive TSqlStatement objects
       
   385 //		  to avoid OOM errors during the test.
       
   386 //
       
   387 //		  Each test thread does steps 1..4 for a period of KTestDuration seconds.
       
   388 //		  At the end all TSqlStatement objects are closed.
       
   389 //
       
   390 //		  The idea of the test is to load the SQL server creating several amount of statement and stream objects
       
   391 //		  and see that it is working stable and without problems.
       
   392 TInt ThreadFunc(void*)
       
   393 	{
       
   394 	__UHEAP_MARK;
       
   395 
       
   396 	CTrapCleanup* tc = CTrapCleanup::New();
       
   397 	TTEST(tc != NULL);
       
   398 
       
   399 	TInt64 seed = 0;
       
   400 	RSqlDatabase db;
       
   401 	TName threadName;
       
   402 	RSqlStatementArray statements;
       
   403 	
       
   404 	//Init the random numbers generator, opens the database
       
   405 	PreTest(db, seed, threadName);
       
   406 
       
   407 	//Main test loop
       
   408 	TInt iteration = 0;
       
   409 	TTime currTime;
       
   410 	currTime.UniversalTime();
       
   411 	TTime endTime = currTime + TTimeIntervalSeconds(KTestDuration);
       
   412 	while(currTime < endTime)
       
   413 		{
       
   414 		++iteration;
       
   415 		///////////////////////////////////////////////////////////////////////
       
   416 		TInt statementsAliveBegin = statements.Count();
       
   417 		//Step 1: Create N statements, where 0 < N < KStatementCnt
       
   418 		TInt statementsCreated = CreateStatements(db, seed, statements);
       
   419 		///////////////////////////////////////////////////////////////////////
       
   420 		//Step 2: For each alive statement object - do (TSqlStatement::iCount / KTestStepCnt)
       
   421 		//        RSqlStatement::Next() calls. If the Next() call reaches the end - close the statement object.
       
   422 		TInt statementsCompleted = ProcessStatements(statements);
       
   423 		///////////////////////////////////////////////////////////////////////
       
   424 		//Step 3: Close up to N statements, where 0 < N < KStatementCnt
       
   425 		TInt statementsClosed = CloseStatements(statements, seed);
       
   426 		///////////////////////////////////////////////////////////////////////
       
   427 		//Step 4: If the alive statement count is more than KMaxStatementPerThread, then close them all
       
   428 		TInt statementsAliveEnd = AliveStatementsCount(statements);
       
   429 		if(statementsAliveEnd > KMaxStatementPerThread)
       
   430 			{
       
   431 			RDebug::Print(_L("!!! Thread %S, iteration %d, alive %d, close all\r\n"), &threadName, iteration, statementsAliveEnd);
       
   432 			CloseAllStatements(statements);
       
   433 			statementsAliveEnd = 0;
       
   434 			}
       
   435 		///////////////////////////////////////////////////////////////////////
       
   436 		RemoveDeadStatements(statements);
       
   437 		RDebug::Print(_L("=== Thread %S, iteration % 4d, begin: % 3d, created % 2d, closed % 2d, completed % 2d, end % 3d, \r\n"),
       
   438 							&threadName, iteration, statementsAliveBegin, 
       
   439 													statementsCreated, statementsClosed, statementsCompleted, 
       
   440 													statementsAliveEnd);
       
   441 		currTime.UniversalTime();
       
   442 		}
       
   443 
       
   444 	//Close statement objects and the database object
       
   445 	TInt statementsAlive = PostTest(db, statements);
       
   446 
       
   447 	delete tc;
       
   448 
       
   449 	__UHEAP_MARKEND;
       
   450 
       
   451 	RDebug::Print(_L("=== Thread %S exit, still alive %d\r\n"), &threadName, statementsAlive);
       
   452 
       
   453 	return KErrNone;
       
   454 	}
       
   455 
       
   456 void CreateTestThreads(RThread aThreads[], TRequestStatus aStatuses[], TInt aMaxCount)
       
   457 	{
       
   458 	_LIT(KThreadName, "TstThr");
       
   459 	for(TInt i=0;i<aMaxCount;++i)
       
   460 		{
       
   461 		TBuf<20> threadName(KThreadName);
       
   462 		threadName.AppendNum((TInt64)(i + 1));
       
   463 		TEST2(aThreads[i].Create(threadName, &ThreadFunc, 0x2000, 0x1000, 0x10000, NULL, EOwnerProcess), KErrNone);
       
   464 		aThreads[i].Logon(aStatuses[i]);
       
   465 		TEST2(aStatuses[i].Int(), KRequestPending);
       
   466 		}
       
   467 	}
       
   468 
       
   469 void ResumeTestThreads(RThread aThreads[], TInt aMaxCount)
       
   470 	{
       
   471 	for(TInt i=0;i<aMaxCount;++i)
       
   472 		{
       
   473 		aThreads[i].Resume();
       
   474 		}
       
   475 	}
       
   476 
       
   477 
       
   478 void CloseTestThreads(RThread aThreads[], TRequestStatus aStatuses[], TInt aMaxCount)
       
   479 	{
       
   480 	for(TInt i=0;i<aMaxCount;++i)
       
   481 		{
       
   482 		User::WaitForRequest(aStatuses[i]);
       
   483 		TEST(aThreads[i].ExitType() != EExitPanic);
       
   484 		aThreads[i].Close();
       
   485 		}
       
   486 	}
       
   487 
       
   488 /**
       
   489 @SYMTestCaseID			SYSLIB-SQL-CT-1627-0001
       
   490 @SYMTestCaseDesc		SQL server load test. The test creates KTestThreadCnt threads, KTestDbCnt test databases and
       
   491 						inserts in each of them KRecordCnt test records.
       
   492 						Pre-test step: each test thread randomly chooses and opens one of the test databases.
       
   493 						Then, each of the test threads is doing the following 4 test steps:
       
   494 						Step 1: the test thread creates m TSqlStatement objects, 0 < m < KStatementCnt.
       
   495 						With each of the created TSqlStatement objects the test thread prepares SELECT SQL query
       
   496 						"SELECT * FROM A WHERE F1 >= K1 AND F1 < K2", where K1 is random generated number, such that:
       
   497 						0 < K1 < (KRecordCnt - KQueriedRecordCnt)
       
   498 						K2 = K1 + KQueriedRecordCnt
       
   499 						All just created TSqlStatement objects are marked as alive.
       
   500 						Step 2: For each alive TSqlStatement object the test thread calls iObj.Next() method KTestStepCnt times,
       
   501 						KTestStepCnt < KQueriedRecordCnt.
       
   502 						The column values are retrieved and checked.
       
   503 						Step 3: the test thread closes n TSqlStatement objects, 0 < n < KStatementCnt.
       
   504 						Step 4: the test thread counts how many alive TSqlStatement objects are there.
       
   505 						If this count > KMaxStatementPerThread then the test thread closes all alive TSqlStatement objects
       
   506 						to avoid OOM errors during the test.
       
   507 
       
   508 						Each test thread does steps 1..4 for a period of KTestDuration seconds.
       
   509 						At the end all TSqlStatement objects are closed.
       
   510 
       
   511 						The idea of the test is to load the SQL server creating several amount of statement and stream objects
       
   512 						and see that it is working stable and without problems.
       
   513 @SYMTestPriority		High
       
   514 @SYMTestActions			SQL server load test
       
   515 @SYMTestExpectedResults Test must not fail
       
   516 @SYMREQ					REQ5792
       
   517                         REQ5793
       
   518 */
       
   519 void SqlLoadTest()
       
   520 	{
       
   521 	CreateTestDatabases();
       
   522 
       
   523 	RThread threads[KTestThreadCnt];
       
   524 	TRequestStatus statuses[KTestThreadCnt];
       
   525 
       
   526 	CreateTestThreads(threads, statuses, KTestThreadCnt);
       
   527 
       
   528 	ResumeTestThreads(threads, KTestThreadCnt);
       
   529 
       
   530 	User::After(2000000);
       
   531 
       
   532 	CloseTestThreads(threads, statuses, KTestThreadCnt);
       
   533 	}
       
   534 
       
   535 void DoTests()
       
   536 	{
       
   537 	TheTest.Start(_L(" @SYMTestCaseID:SYSLIB-SQL-CT-1627-0001 SQL server load test "));
       
   538 	SqlLoadTest();
       
   539 	}
       
   540 
       
   541 TInt E32Main()
       
   542 	{
       
   543 	TheTest.Title();
       
   544 
       
   545 	CTrapCleanup* tc = CTrapCleanup::New();
       
   546 
       
   547 	__UHEAP_MARK;
       
   548 
       
   549 	CreateTestDir();
       
   550 	DeleteTestFiles();
       
   551 	DoTests();
       
   552 	DeleteTestFiles();
       
   553 
       
   554 	__UHEAP_MARKEND;
       
   555 
       
   556 	TheTest.End();
       
   557 	TheTest.Close();
       
   558 
       
   559 	delete tc;
       
   560 
       
   561 	User::Heap().Check();
       
   562 	return KErrNone;
       
   563 	}