symport/e32/euser/us_test.cpp
changeset 1 0a7b44b10206
child 2 806186ab5e14
equal deleted inserted replaced
0:c55016431358 1:0a7b44b10206
       
     1 // Copyright (c) 1994-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 the License "Symbian Foundation License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.symbianfoundation.org/legal/sfl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 // e32\euser\us_test.cpp
       
    15 // 
       
    16 //
       
    17 
       
    18 #include "us_std.h"
       
    19 #include <e32test.h>
       
    20 
       
    21 #if defined(test)
       
    22 #undef test
       
    23 #endif
       
    24 
       
    25 #include <e32svr.h> 
       
    26 
       
    27 void RTest::CheckConsoleCreated()
       
    28 	{
       
    29 	// Check that the console has been created.
       
    30 	if (iConsole == NULL)
       
    31 		{
       
    32 		TRAPD(r, iConsole = Console::NewL(iTitle, TSize(KConsFullScreen, KConsFullScreen)))
       
    33 		__ASSERT_ALWAYS(r == KErrNone, ::Panic(ERTestCreateConsole));
       
    34 		}
       
    35 	}
       
    36 
       
    37 void RTest::DisplayLevel()
       
    38 	{
       
    39 	// Display the current level string.
       
    40 	TBuf<0x100> aBuf(_L("RTEST: Level "));
       
    41 	for (TInt ii = 1; ii < iLevel; ii++)
       
    42 		{
       
    43 		if (ii > 1)
       
    44 			{
       
    45 			aBuf.AppendFormat(_L(".%02d"), iStack[ii]);
       
    46 			}
       
    47 		else
       
    48 			{
       
    49 			aBuf.AppendFormat(_L(" %03d"), iStack[ii]);
       
    50 			}
       
    51 		}
       
    52 	if (iLevel > 1)
       
    53 		{
       
    54 		aBuf.AppendFormat(_L(".%02d "), iTest);
       
    55 		}
       
    56 	else
       
    57 		{
       
    58 		aBuf.AppendFormat(_L(" %03d "), iTest);
       
    59 		}
       
    60 
       
    61 	Printf(aBuf);
       
    62 	}
       
    63 
       
    64 
       
    65 
       
    66 
       
    67 /**
       
    68 Constructor.
       
    69 
       
    70 @param aTitle           A title describing this use of RTest.
       
    71                         This is also referred to as the console title.
       
    72 @param aThrowaway       Not used.
       
    73 @param anOtherThrowaway Not used.
       
    74 */
       
    75 EXPORT_C RTest::RTest(const TDesC &aTitle,TInt /* aThrowaway */,const TText* /* anOtherThrowaway */)
       
    76 	: iTest(0), iLevel(0), iLogging(ETrue), iConsole(NULL), iTitle(aTitle)
       
    77 	// Constructor
       
    78 	// There is a #define test(x) test(x, __LINE__) in e32test.h to pass on line info of failing tests,
       
    79 	// This depends upon the user naming their RTest object test, but if they do this then an extra
       
    80 	// parameter aThrowaway must be added to the constructor
       
    81 	{}
       
    82 
       
    83 
       
    84 
       
    85 /**
       
    86 Constructor.
       
    87 
       
    88 @param aTitle     A title describing this use of RTest.
       
    89                   This is also referred to as the console title.
       
    90 @param aThrowaway Not used.
       
    91 */
       
    92 EXPORT_C RTest::RTest(const TDesC &aTitle, TInt /* athrowaway */)
       
    93 	: iTest(0), iLevel(0), iLogging(ETrue), iConsole(NULL), iTitle(aTitle)
       
    94 	// Constructor
       
    95 	// There is a #define test(x) test(x, __LINE__) in e32test.h to pass on line info of failing tests,
       
    96 	// This depends upon the user naming their RTest object test, but if they do this then an extra
       
    97 	// parameter aThrowaway must be added to the constructor
       
    98 	{}
       
    99 
       
   100 
       
   101 
       
   102 
       
   103 /**
       
   104 Constructor.
       
   105 
       
   106 @param aTitle A title describing this use of RTest.
       
   107               This is also referred to as the console title.
       
   108 */
       
   109 EXPORT_C RTest::RTest(const TDesC &aTitle)
       
   110 	: iTest(0), iLevel(0), iLogging(ETrue), iConsole(NULL), iTitle(aTitle)
       
   111 	// Constructor
       
   112 	{}
       
   113 
       
   114 
       
   115 
       
   116 
       
   117 /**
       
   118 Closes the console and frees any resources acquired.
       
   119 */
       
   120 EXPORT_C void RTest::Close()
       
   121 	{
       
   122 	// Close the console.
       
   123 	delete iConsole;
       
   124 	iConsole=NULL;
       
   125 	}
       
   126 
       
   127 
       
   128 
       
   129 
       
   130 /**
       
   131 Prints out the console title and version number.
       
   132 
       
   133 The format of the text is:
       
   134 
       
   135 @code
       
   136 RTEST TITLE: XXX YYY
       
   137 Epoc/32 YYY
       
   138 @endcode
       
   139 
       
   140 where XXX is the console title, and YYY is the version number,
       
   141 formatted as described by TVersion::Name().
       
   142 
       
   143 @see TVersion::Name()
       
   144 @see RTest::Printf() 
       
   145 */
       
   146 EXPORT_C void RTest::Title()
       
   147 	{
       
   148 	// Print out the program title and version number.
       
   149 	TVersion v(KE32MajorVersionNumber, KE32MinorVersionNumber, KE32BuildVersionNumber);
       
   150 	TBuf<16> vName=v.Name();
       
   151 	Printf(_L("RTEST TITLE: %S %S\n"), &iTitle, &vName);
       
   152 	vName=User::Version().Name();
       
   153 	Printf(_L("Epoc/32 %S\n"), &vName);
       
   154 	}
       
   155 
       
   156 
       
   157 
       
   158 
       
   159 /**
       
   160 Marks the start of a set of tests.
       
   161 
       
   162 Note that sets of tests can be nested.
       
   163 
       
   164 A call to this function must be matched by a call to RTest::End() to mark
       
   165 the end of this set of tests.
       
   166 
       
   167 @param aHeading A heading describing the set of tests; this is
       
   168                 printed at the console.
       
   169                 
       
   170 @see RTest::End()                
       
   171 */
       
   172 EXPORT_C void RTest::Start(const TDesC &aHeading)
       
   173 	{
       
   174 	// Print out the heading and nest the level.
       
   175 	Push();
       
   176 	Next(aHeading);
       
   177 	}
       
   178 
       
   179 
       
   180 
       
   181 
       
   182 /**
       
   183 Marks the start of the next test.
       
   184 
       
   185 @param aHeading A heading describing the test; this
       
   186                 is printed at the console. This function is also
       
   187                 called by Start(), which passes the text that describes
       
   188                 the set of tests.
       
   189                 
       
   190 @see RTest::Start()                
       
   191 */
       
   192 EXPORT_C void RTest::Next(const TDesC &aHeading)
       
   193 	{
       
   194 	// Print out the heading and nest the level.
       
   195 	iTest++;
       
   196 	iCheck = 0;
       
   197 	DisplayLevel();
       
   198 	Printf(_L("Next test - %S\n"), &aHeading);
       
   199 	}
       
   200 
       
   201 
       
   202 
       
   203 
       
   204 /**
       
   205 Checks the result of a condition and, if this is false, prints
       
   206 a failure message at the console and raises a panic.
       
   207 
       
   208 Before checking the condition passed in, the operator increments
       
   209 a check number. This is a value that is set to zero at the start of a test
       
   210 and is incremented by this operator (and by all variants of it). It identifies
       
   211 the check being made within the current test.
       
   212 This value is printed on a failure message.
       
   213 
       
   214 Typically, the operator is called, passing a test condition, for example:
       
   215 
       
   216 @code
       
   217 RTest test(... heading text...,line number... file name)
       
   218 TInt r;
       
   219 ...some operation to be tested that returns a value in r...
       
   220 test(r==KErrNone);
       
   221 @endcode
       
   222 
       
   223 The failure message has the format:
       
   224 
       
   225 @code
       
   226 : FAIL : XXX failed check N in FFF at line Number: M
       
   227 RTEST: Checkpoint-fail
       
   228 @endcode
       
   229 
       
   230 where XXX is the console title, N is the check number, FFF is the filename,
       
   231 and M is the line number passed in.
       
   232 
       
   233 @param aResult   The condition being tested.
       
   234                  This is interpreted as a true or false value.
       
   235 @param aLineNum  A line number that is printed in the failure message if
       
   236                  the condition being tested is false.
       
   237 @param aFileName A file name that is printed in the failure message if
       
   238                  the condition being tested is false.
       
   239                  
       
   240 @panic USER 84 if the condition being tested is false.
       
   241 
       
   242 @see RTest::Next()
       
   243 @see RTest::Start()
       
   244 */
       
   245 EXPORT_C void RTest::operator()(TInt aResult, TInt aLineNum, const TText* aFileName)
       
   246 	{
       
   247 	// Test a condition.
       
   248 	iCheck++;
       
   249 	if (!aResult)
       
   250 		{
       
   251 		RDebug::Printf(": FAILING : failed check at line number %d", aLineNum);
       
   252 		DisplayLevel();
       
   253 		Printf(_L(": FAIL : %S failed check %d in %s at line number %d\n"),
       
   254 			   &iTitle, iCheck, aFileName, aLineNum);
       
   255 		Panic(_L("Checkpoint-fail\n"));
       
   256 		if (!iLogging)
       
   257 			Getch();
       
   258 		}
       
   259 	}
       
   260 
       
   261 
       
   262 
       
   263 
       
   264 /**
       
   265 Checks the result of a condition and, if this is false, prints
       
   266 a failure message at the console and raises a panic.
       
   267 
       
   268 Before checking the condition passed in, the operator increments
       
   269 a check number. This is a value that is set to zero at the start of a test
       
   270 and is incremented by this operator (and by all variants of it). It identifies
       
   271 the check being made within the current test.
       
   272 This value is printed on the failure message.
       
   273 
       
   274 Typically, the operator is called, passing a test condition, for example:
       
   275 
       
   276 @code
       
   277 RTest test(... heading text...,line number)
       
   278 TInt r;
       
   279 ...some operation to be tested that returns a value in r...
       
   280 test(r==KErrNone);
       
   281 @endcode
       
   282 
       
   283 The failure message has the format:
       
   284 
       
   285 @code
       
   286 : FAIL : XXX failed check N at line Number: M
       
   287 RTEST: Checkpoint-fail
       
   288 @endcode
       
   289 
       
   290 where XXX is the console title, N is the check number, and M is
       
   291 the line number passed in.
       
   292 
       
   293 @param aResult  The condition being tested.
       
   294                 This is interpreted as a true or false value.
       
   295 @param aLineNum A line number that is printed in the failure message if
       
   296                 the condition being tested is false.               
       
   297 
       
   298 @panic USER 84 if the condition being tested is false.
       
   299 
       
   300 @see RTest::Next()
       
   301 @see RTest::Start()
       
   302 */
       
   303 EXPORT_C void RTest::operator()(TInt aResult,TInt aLineNum)
       
   304 	{
       
   305 	// Test a condition.
       
   306 	iCheck++;
       
   307 	if (!aResult)
       
   308 		{
       
   309 		RDebug::Printf(": FAILING : failed check at line Number: %d", aLineNum);
       
   310 		DisplayLevel();
       
   311 		Printf(_L(": FAIL : %S failed check %d at line Number: %d\n"), &iTitle, iCheck, aLineNum);
       
   312 		Panic(_L("Checkpoint-fail\n"));
       
   313 		if (!iLogging)
       
   314 			Getch();
       
   315 		}
       
   316 	}  
       
   317 
       
   318 
       
   319 
       
   320 
       
   321 /**
       
   322 Checks the result of a condition and, if this is false, prints
       
   323 a failure message at the console and raises a panic.
       
   324 
       
   325 Before checking the condition passed in, the operator increments
       
   326 a check number. This is a value that is set to zero at the start of a test
       
   327 and is incremented by this operator (and by all variants of it). It identifies
       
   328 the check being made within the current test.
       
   329 This value is printed on the failure message.
       
   330 
       
   331 Typically, the operator is called, passing a test condition, for example:
       
   332 
       
   333 @code
       
   334 RTest test(... heading text...)
       
   335 TInt r;
       
   336 ...some operation to be tested that returns a value in r...
       
   337 test(r==KErrNone);
       
   338 @endcode
       
   339 
       
   340 The failure message has the format:
       
   341 
       
   342 @code
       
   343 : FAIL : XXX failed check N
       
   344 RTEST: Checkpoint-fail
       
   345 @endcode
       
   346 
       
   347 where XXX is the console title, and N is the check number.
       
   348 
       
   349 @param aResult The condition being tested.
       
   350                This is interpreted as a true or false value.
       
   351 
       
   352 @panic USER 84 if the condition being tested is false.
       
   353 
       
   354 @see RTest::Next()
       
   355 @see RTest::Start()
       
   356 */
       
   357 EXPORT_C void RTest::operator()(TInt aResult)
       
   358 	{
       
   359 	// Test a condition.
       
   360 	iCheck++;
       
   361 	if (!aResult)
       
   362 		{
       
   363 		RDebug::Printf(": FAILING : failed check\n");
       
   364 		DisplayLevel();
       
   365 		Printf(_L(": FAIL : %S failed check %d\n"), &iTitle, iCheck);
       
   366 		Panic(_L("Checkpoint-fail\n"));
       
   367 		if (!iLogging)
       
   368 			Getch();
       
   369 		}
       
   370 	}
       
   371 
       
   372 
       
   373 
       
   374 
       
   375 /**
       
   376 Ends the current set of tests.
       
   377 
       
   378 If this set of tests is not nested within another set,
       
   379 then a message reporting success is written to
       
   380 the console.
       
   381 
       
   382 @panic USER 84 if there was no matching call to RTest::Start(),
       
   383                i.e. more calls to End() have been made than calls to Start().
       
   384 
       
   385 @see RTest::Start()
       
   386 */
       
   387 EXPORT_C void RTest::End()
       
   388 	{
       
   389 	// End the current level of tests.
       
   390 	if (TInt(iLevel-1) < 0)
       
   391 		{
       
   392 		Panic(_L("End() without matching Start()\n"));
       
   393 		}
       
   394 
       
   395 	Pop();
       
   396 
       
   397 	if (iLevel == 0)
       
   398 		{
       
   399 		Printf(_L("RTEST: SUCCESS : %S test completed O.K.\n"), &iTitle);
       
   400 		if (!iLogging)
       
   401 			Getch();
       
   402 		}
       
   403 	}
       
   404 
       
   405 
       
   406 
       
   407 
       
   408 /**
       
   409 Prints an error message and an error code,
       
   410 and raises a USER 84 panic.
       
   411 
       
   412 @param anError The error code.
       
   413 @param aFmt    A format list.
       
   414 @param ...     A variable number of parameters.
       
   415 */
       
   416 EXPORT_C void RTest::Panic(TInt anError,TRefByValue<const TDesC> aFmt,...)
       
   417 	{
       
   418 	// Print an error message, an error and then panic.
       
   419 	TestOverflowTruncate overflow;
       
   420 	VA_LIST list;
       
   421 	VA_START(list, aFmt);
       
   422 	TBuf<0x100> aBuf;
       
   423 	aBuf.AppendFormat(_L("RTEST: "));
       
   424 	aBuf.AppendFormatList(aFmt, list, &overflow);
       
   425 	aBuf.AppendFormat(_L(" Failed with error %d\n"), anError);
       
   426 	Printf(aBuf);
       
   427 	if (!iLogging)
       
   428 		Getch();
       
   429 	::Panic(ERTestFailed);
       
   430 	}
       
   431 
       
   432 
       
   433 
       
   434 
       
   435 /**
       
   436 Prints an error message, and raises a USER 84 panic.
       
   437 
       
   438 @param aFmt    A format list.
       
   439 @param ...     A variable number of parameters.
       
   440 */
       
   441 EXPORT_C void RTest::Panic(TRefByValue<const TDesC> aFmt,...)
       
   442 	{
       
   443 	// Print an error message and then panic.
       
   444 	TestOverflowTruncate overflow;
       
   445 	VA_LIST list;
       
   446 	VA_START(list, aFmt);
       
   447 	TBuf<0x100> aBuf;
       
   448 	aBuf.AppendFormat(_L("RTEST: "));
       
   449 	aBuf.AppendFormatList(aFmt, list, &overflow);
       
   450 	Printf(aBuf);
       
   451 	if (!iLogging)
       
   452 		Getch();
       
   453 	::Panic(ERTestFailed);
       
   454 	}
       
   455 
       
   456 
       
   457 
       
   458 _LIT(KLitNL, "\n");
       
   459 _LIT(KLitCRNL, "\r\n");
       
   460 /**
       
   461 Prints text to the console.
       
   462 
       
   463 If the logging flag is set, the string
       
   464 is also written to the debug output as represented by an RDebug object.
       
   465 
       
   466 @param aFmt    A format list.
       
   467 @param ...     A variable number of parameters.
       
   468 
       
   469 @see RTest::SetLogged()
       
   470 @see Rtest::Logged()
       
   471 @see RDebug
       
   472 */
       
   473 EXPORT_C void RTest::Printf(TRefByValue<const TDesC> aFmt,...)
       
   474 	{
       
   475 	// Print to a console screen.
       
   476 	TestOverflowTruncate overflow;
       
   477 	VA_LIST list;
       
   478 	VA_START(list, aFmt);
       
   479 	TBuf<0x100> buf;
       
   480 	buf.AppendFormatList(aFmt, list, &overflow);
       
   481 	CheckConsoleCreated();
       
   482 	iConsole->Write(buf);
       
   483 	
       
   484 	if (iLogging)
       
   485 		{
       
   486 		TPtrC ptr(buf);
       
   487 		TInt newline;
       
   488 		while ((newline = ptr.Locate('\n')) != KErrNotFound)
       
   489 			{
       
   490 			RDebug::RawPrint(ptr.Left(newline));
       
   491 			if (newline==0 || ptr[newline-1]!='\r')
       
   492 				RDebug::RawPrint(KLitCRNL); // bare nl, replace with crnl
       
   493 			else
       
   494 				RDebug::RawPrint(KLitNL); // crnl, already printed cr
       
   495 			if (newline+1<ptr.Length())
       
   496 				ptr.Set(ptr.Mid(newline+1));
       
   497 			else
       
   498 				return; // newline was end of string
       
   499 			}
       
   500 		RDebug::RawPrint(ptr);
       
   501 		}
       
   502 	}
       
   503 
       
   504 
       
   505 
       
   506 
       
   507 /**
       
   508 Gets an input key stroke.
       
   509 
       
   510 @return The input key code.
       
   511 */
       
   512 EXPORT_C TKeyCode RTest::Getch()
       
   513 	{
       
   514 	// Get a key from the console.
       
   515 	CheckConsoleCreated();
       
   516 	return(iConsole->Getch());
       
   517 	}
       
   518 
       
   519 
       
   520 
       
   521 EXPORT_C TInt RTest::CloseHandleAndWaitForDestruction(RHandleBase& aH)
       
   522 	{
       
   523 #ifndef __TOOLS2__
       
   524 	TRequestStatus s;
       
   525 	aH.NotifyDestruction(s);
       
   526 	aH.Close();
       
   527 	TUint32 initial = User::NTickCount();
       
   528 	TInt r = KErrNone;
       
   529 	if (s == KErrNoMemory)
       
   530 		r = KErrNoMemory;
       
   531 	while (s == KRequestPending)
       
   532 		{
       
   533 		TUint32 now = User::NTickCount();
       
   534 		if ((now - initial) > 5000)
       
   535 			{
       
   536 			User::CancelMiscNotifier(s);
       
   537 			r = KErrTimedOut;
       
   538 			break;
       
   539 			}
       
   540 		User::AfterHighRes(1000);
       
   541 		}
       
   542 	User::WaitForRequest(s);
       
   543 	return r;
       
   544 #else
       
   545 	return KErrNone;
       
   546 #endif // __TOOLS2__
       
   547 	}
       
   548 
       
   549