--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/mmtestenv/mmtestfw/Source/TestFrameworkClient/Log.cpp Tue Feb 02 01:56:55 2010 +0200
@@ -0,0 +1,1097 @@
+// Copyright (c) 2002-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:
+// Client / server logging for Test Framework
+// NOTE : does NOT include secure API changes in EKA2
+//
+//
+
+
+// Test system includes
+#include <testframework.h>
+
+// do not export if Unit Testing
+#if defined (__TSU_TESTFRAMEWORK__)
+#undef EXPORT_C
+#define EXPORT_C
+#endif
+
+/**
+ *
+ * HTML font formatting strings
+ *
+ * @xxxx
+ *
+ */
+_LIT(KResultPass, "<font size=4 color=00AF00>");
+_LIT(KResultFail, "<font size=4 color=FF0000>");
+_LIT(KResultInconclusive, "<font size=4 color=0000FF>");
+_LIT(KResultUndefined, "<font size=4 color=FF00FF>");
+_LIT(KResultEnd, "</font>");
+_LIT(KResultNonHtml, "");
+
+_LIT(KResultKnownFailure, "<font size=4 color=008080>"); //A new TVerdict for a known failed test
+
+// logging macro used only for verdicts - not for external use
+#define VER_PRINTF(r1, r2, r3) LogExtra(__FILE8__, __LINE__, ESevrVer, _L("%S%S%S\n"), (r1), (r2), (r3))
+
+/**
+ *
+ * Global : start a server
+ * NOTE. Function is global static as only one server will ever run at any time
+ * (there may be multiple client sessions)
+ *
+ * @return "TInt"
+ * Error code (KErrNone if successful)
+ *
+ * @xxxx
+ *
+ */
+GLDEF_C TInt StartServer()
+// Start the server process/thread which lives in an (EPOC)EXE object
+ {
+ const TUidType serverUid(KNullUid, KNullUid, KTestFrameworkServerUid3);
+
+
+// EPOC is easy, we just create a new server process. Simultaneous launching
+// of two such processes should be detected when the second one attempts to
+// create the server object, failing with KErrAlreadyExists.
+
+ RProcess server;
+ TInt r = server.Create(KTestFrameworkServerImg, KNullDesC, serverUid);
+
+ if (r != KErrNone)
+ return r;
+
+
+ TRequestStatus rendezvous;
+ server.Rendezvous(rendezvous);
+
+ if (rendezvous!=KRequestPending)
+ {
+ server.Kill(0);
+ }
+ else
+ {
+ server.Resume();
+ }
+
+
+ User::WaitForRequest(rendezvous); // wait for start or death
+
+ // we can't use the 'exit reason' if the server panicked as this
+ // is the panic 'reason' and may be '0' which cannot be distinguished
+ // from KErrNone
+ if (rendezvous!=KErrNone)
+ {
+ server.Close();
+ }
+
+ // server started (at last). Cancel and consume the death-notification
+ // before reporting success
+ return rendezvous.Int();
+ }
+
+/**
+ *
+ * Constructor for RTestFrameworkClientSession
+ *
+ * @xxxx
+ *
+ */
+RTestFrameworkClientSession::RTestFrameworkClientSession()
+ {
+ }
+
+/**
+ *
+ * Client session : connect to server.
+ * Will start a new server session if no server exists
+ *
+ * @return "TInt"
+ * Error code (KErrNone if connect successful)
+ *
+ * @xxxx
+ *
+ */
+TInt RTestFrameworkClientSession::Connect()
+ {
+ // NOTE : this loop is ugly and can probably be rewritten to be more graceful
+ const TInt KNumRetries = 2;
+
+ TInt retry = KNumRetries;
+ for (;;)
+ {
+ TInt r = CreateSession(KTestFrameworkServerName, TVersion(KTestFrameworkServerMajorVersionNumber,
+ KTestFrameworkServerMinorVersionNumber,
+ KTestFrameworkServerBuildVersionNumber));
+ if (r == KErrNone)
+ {
+#ifdef __IPC_V2_PRESENT__
+ r = ShareAuto();
+#else
+ r = Share(RSessionBase::EAutoAttach);
+#endif
+ if (r!=KErrNone)
+ Close();
+ return r;
+ }
+ if (r != KErrNotFound && r != KErrServerTerminated)
+ {
+ return r;
+ }
+ if (--retry == 0)
+ return r;
+ r = StartServer();
+ if (r != KErrNone && r != KErrAlreadyExists)
+ return r;
+ }
+ }
+
+/**
+ *
+ * Request creation of an input window.
+ * NOTE. For initialisation of input console only - unlikely to
+ * be required by user
+ *
+ * @param "TRectBuf& aAllocatedWindow"
+ * Window dimensions
+ *
+ * @param "TRequestStatus& aReqStat"
+ * Request status
+ *
+ * @xxxx
+ *
+ */
+void RTestFrameworkClientSession::CreateInputWindow(TRectBuf& aAllocatedWindow, TRequestStatus& aReqStat)
+ {
+ SendReceiveResult(ECreateInputWindow, aAllocatedWindow, aReqStat);
+ }
+
+/**
+ *
+ * Request window change notifications
+ * NOTE. For initialisation of input console only - unlikely to
+ * be required by user
+ *
+ * @param "TRectBuf& aNewWindow"
+ * New window dimensions
+ *
+ * @param "TRequestStatus& aReqStat"
+ * Request status
+ *
+ * @xxxx
+ *
+ */
+void RTestFrameworkClientSession::NotifyIfWindowChange(TRectBuf& aNewWindow, TRequestStatus& aReqStat)
+ {
+ SendReceiveResult(ENotifyIfWindowChange, aNewWindow, aReqStat);
+ }
+
+/**
+ *
+ * Cancel window change notifications
+ * NOTE. For initialisation of input console only - unlikely to
+ * be required by user
+ *
+ * @return "TInt"
+ * SendReceive error code
+ *
+ * @xxxx
+ *
+ */
+TInt RTestFrameworkClientSession::CancelNotifyIfWindowChange()
+ {
+ return SendReceive(ECancelNotifyIfWindowChange);
+ }
+
+
+/**
+ *
+ * Open a log server session
+ *
+ * @param "const TDesC& aLogName"
+ * The log name
+ *
+ * @param "TInt aLogMode"
+ * The log mode (a bitmask of TTestFrameworkLogMode)
+ *
+ * @xxxx
+ *
+ */
+void RTestFrameworkClientSession::OpenLog(const TDesC& aLogName, TInt aLogMode)
+ {
+ (void) SendReceive(EOpenLog, aLogName, aLogMode);
+ }
+
+/**
+ *
+ * Write message string to log server session
+ *
+ * @param "const TDesC& aMsg"
+ * The message string
+ *
+ * @param "TInt aLogMode"
+ * The log mode (a bitmask of TTestFrameworkLogMode)
+ *
+ * @xxxx
+ *
+ */
+void RTestFrameworkClientSession::WriteLog(const TDesC& aMsg, TInt aLogMode)
+ {
+ (void) SendReceive(EWriteLog, aMsg, aLogMode);
+ }
+
+/**
+ *
+ * Send close log message to server
+ *
+ * @xxxx
+ *
+ */
+void RTestFrameworkClientSession::CloseLog()
+ {
+ SendReceive(ECloseLog);
+ }
+
+/**
+ *
+ * Retrieve log status from server
+ *
+ * @return "TInt"
+ * The log status (a bitmask of TTestFrameworkLogMode)
+ *
+ * @xxxx
+ *
+ */
+TInt RTestFrameworkClientSession::LogStatus()
+ {
+ TInt res = 0;
+ TPckgBuf<TInt> pckg;
+ TInt r = SendReceiveResult(ELogStatus, pckg);
+ if (r != KErrNone)
+ {
+ // RTestFrameworkClientSession does not log -
+ // we can however return 0 to indicate an error (no outputs)
+ res = 0;
+ }
+ else
+ res = pckg();
+ return res;
+ }
+
+/**
+ *
+ * Static constructor for CLog.
+ *
+ *
+ * @return "CLog*"
+ * The constructed CLog
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C CLog* CLog::NewL()
+ {
+ CLog* self = new(ELeave) CLog;
+ self->Construct();
+ return self;
+ }
+
+/**
+ *
+ * Static NewLC constructor for CLog.
+ *
+ *
+ * @return "CLog*"
+ * The constructed CLog
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C CLog* CLog::NewLC()
+ {
+ CLog* self = new(ELeave) CLog;
+ CleanupStack::PushL(self);
+ self->Construct();
+ return self;
+ }
+
+/**
+ *
+ * Second-phase constructor for CLog.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::Construct()
+ {
+ iLogStatus = 0; // no outputs enabled yet
+ iSeverity = ESevrAll;
+ //Do we need to put information about source file & #line?
+ //Default is yes.
+ iLogFlags = ELogPutSrcInfo | ELogHtmlMode;
+ }
+
+/**
+ *
+ * Destructor for CLog.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C CLog::~CLog()
+ {
+ // tell server to close logs here
+ iClientSession.Close();
+ }
+
+/**
+ *
+ * Open a new test log.
+ *
+ * @param "const TDesC& aLogName"
+ * Log file or console name
+ *
+ * @param "TInt aLogMode"
+ * Log modes (a bitmask of TTestFrameworkLogMode).
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::OpenLogFileL(const TDesC& aLogName, TInt aLogMode)
+ {
+ User::LeaveIfError(iClientSession.Connect());
+
+ iClientSession.OpenLog(aLogName, aLogMode);
+ // get and store the log status - this will determine whether we
+ // e.g. do any formatting for file output
+ iLogStatus = iClientSession.LogStatus();
+ }
+
+/**
+ *
+ * Open an existing test log.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::OpenLogFileL()
+ {
+ User::LeaveIfError(iClientSession.Connect());
+ iLogStatus = iClientSession.LogStatus();
+ }
+
+/**
+ *
+ * Set put source info (i.e. traceable logging).
+ *
+ * @param "TBool aPutSrcInfo"
+ * Put source info on or off.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::SetPutSrcInfo(TBool aPutSrcInfo)
+ {
+ if(aPutSrcInfo)
+ iLogFlags |= ELogPutSrcInfo;
+ else
+ iLogFlags &= ~ELogPutSrcInfo;
+ }
+
+/**
+ *
+ * Set HTML logging mode.
+ *
+ * @param "TBool aArg"
+ * HTML mode on or off.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::SetHtmlLogMode(TBool aArg)
+ {
+ if(aArg)
+ iLogFlags |= ELogHtmlMode;
+ else
+ iLogFlags &= ~ELogHtmlMode;
+ }
+
+/**
+ *
+ * Get HTML logging mode.
+ *
+ * @return "TBool"
+ * HTML mode on or off.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TBool CLog::HtmlLogMode() const
+ {
+ return ((iLogFlags & ELogHtmlMode) != 0);
+ }
+
+
+/**
+ *
+ * General logging function.
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "..."
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::Log(TRefByValue<const TDesC16> aFmt, ...)
+ {
+ VA_LIST aList;
+ VA_START(aList, aFmt);
+
+ TIntegrationTestLog16Overflow overflow16;
+
+ // decode formatted data for display on console
+ TBuf<KMaxLogLineLength> lineBuf;
+ lineBuf = KNullDesC;
+ lineBuf.AppendFormatList(aFmt, aList, &overflow16);
+
+ // write to the console
+ if(iLogStatus & ELogConsoleFull)
+ iClientSession.WriteLog(lineBuf, ELogToConsole);
+
+ // write to log file
+ WriteFormat(_L("%S\n"), &lineBuf);
+
+ VA_END(aList);
+ }
+
+/**
+ *
+ * General logging function with severity.
+ *
+ * @param "TInt aSeverity"
+ * Severity level required to log
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "..."
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::Log(TInt aSeverity, TRefByValue<const TDesC16> aFmt, ...)
+ {
+ VA_LIST aList;
+ VA_START(aList, aFmt);
+
+ if(LogSeverity::IsActive(aSeverity, Severity()))
+ {
+ Log(aFmt, aList);
+ }
+
+ VA_END(aList);
+ }
+
+/**
+ *
+ * General logging function.
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "VA_LIST aList"
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::Log(TRefByValue<const TDesC16> aFmt, VA_LIST aList)
+ {
+ // decode formatted data for display on console
+ TBuf<KMaxLogLineLength> lineBuf;
+ TIntegrationTestLog16Overflow overflow16;
+
+ lineBuf = KNullDesC;
+ lineBuf.AppendFormatList(aFmt, aList, &overflow16);
+
+ // write to log file
+ WriteFormat(_L("%S\n"),&lineBuf);
+
+ // write to the console
+ if(iLogStatus & ELogConsoleFull)
+ iClientSession.WriteLog(lineBuf, ELogToConsole);
+
+ }
+
+/**
+ *
+ * Traceable logging function
+ *
+ * Should be used for macros only
+ *
+ * @param "const TText8* aFile"
+ * Source code file name
+ *
+ * @param "TInt aLine"
+ * Source code line
+ *
+ * @param "TInt aSeverity"
+ * Severity level required to log
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "VA_LIST aList"
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+#ifdef EXCLUDE_FOR_UNITTEST
+EXPORT_C void CLog::LogExtra(const TText8* /*aFile*/, TInt /*aLine*/, TInt /*aSeverity*/,
+ TRefByValue<const TDesC16> /*aFmt*/, VA_LIST /*aList*/)
+ {
+ }
+#else
+EXPORT_C void CLog::LogExtra(const TText8* aFile, TInt aLine, TInt aSeverity,
+ TRefByValue<const TDesC16> aFmt, VA_LIST aList)
+ {
+ if(LogSeverity::IsActive(aSeverity, Severity()))
+ {
+
+ TIntegrationTestLog16Overflow overflow16;
+
+ // decode formatted data for display on console
+ TBuf<KMaxLogLineLength> lineBuf;
+
+ lineBuf = KNullDesC;
+ lineBuf.AppendFormatList(aFmt, aList, &overflow16);
+
+ // write to the console
+ if(iLogStatus & ELogConsoleFull)
+ WriteLogConsole(lineBuf);
+
+ // log severity
+ TBuf<1> charSevr;
+ switch(aSeverity)
+ {
+ case ESevrVer:
+ charSevr = _L("V");
+ break;
+ case ESevrErr:
+ charSevr = _L("E");
+ break;
+ case ESevrWarn:
+ charSevr = _L("W");
+ break;
+ case ESevrInfo:
+ default:
+ charSevr = _L("I");
+ break;
+ }
+
+ // Do we need to put information about source file & #line?
+ if(iLogFlags & ELogPutSrcInfo)
+ { // Braces used to scope lifetime of TBuf objects
+ TPtrC8 fileName8(aFile);
+ TBuf<256> fileName;
+ TParse printFileName;
+ fileName.Copy(fileName8); // TText8->TBuf16
+ // We don't need full file name.
+ printFileName.Set(fileName, NULL, NULL) ;
+ fileName.Copy(printFileName.NameAndExt()) ;
+ // write to log file
+ WriteFormat(_L("%S\t%S\t%d\t%S\n"), &charSevr, &fileName, aLine, &lineBuf);
+ }
+ else
+ {
+ // write to log file
+ WriteFormat(_L("%S\t%S\n"), &charSevr, &lineBuf);
+ }
+ }
+ }
+#endif // EXCLUDE_FOR_UNITTEST
+
+/**
+ *
+ * Traceable logging function with variable param list.
+ *
+ * Should be used for macros only
+ *
+ * @param "const TText8* aFile"
+ * Source code file name
+ *
+ * @param "TInt aLine"
+ * Source code line
+ *
+ * @param "TInt aSeverity"
+ * Severity level required to log
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "..."
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::LogExtra(const TText8* aFile, TInt aLine, TInt aSeverity,
+ TRefByValue<const TDesC16> aFmt,...)
+ {
+ VA_LIST aList;
+ VA_START(aList, aFmt);
+ LogExtra(aFile, aLine, aSeverity, aFmt, aList);
+ VA_END(aList);
+ }
+
+
+/**
+ *
+ * Write a test result highlighted to the log.
+ *
+ * @param "TVerdict aVerdict"
+ * The test verdict.
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "..."
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::LogResult(TVerdict aVerdict, TRefByValue<const TDesC16> aFmt, ...)
+ {
+ VA_LIST aList;
+ VA_START(aList, aFmt);
+
+ TIntegrationTestLog16Overflow iOverflow16;
+
+ // decode formatted data for display on console
+ TBuf <KMaxLogLineLength> lineBuf;
+ lineBuf.AppendFormatList(aFmt, aList, &iOverflow16);
+
+ // write to the console
+ iClientSession.WriteLog(lineBuf, ELogToConsole);
+
+ // write to log file
+ if(iLogFlags & ELogHtmlMode)
+ {
+ switch(aVerdict)
+ {
+ case EPass:
+ VER_PRINTF(&KResultPass(), &lineBuf, &KResultEnd());
+ break;
+ case EFail:
+ VER_PRINTF(&KResultFail(), &lineBuf, &KResultEnd());
+ break;
+ case EInconclusive:
+ case ETestSuiteError:
+ case EAbort:
+ VER_PRINTF(&KResultInconclusive(), &lineBuf, &KResultEnd());
+ break;
+ case EKnownFailure: //A new TVerdict for a known failed test
+ VER_PRINTF(&KResultKnownFailure(), &lineBuf, &KResultEnd());
+ break;
+
+ default: // undefined
+ VER_PRINTF(&KResultUndefined(), &lineBuf, &KResultEnd());
+ break;
+ }
+ }
+ else
+ {
+ VER_PRINTF(&KResultNonHtml(), &lineBuf, &KResultNonHtml());
+ }
+ VA_END(aList);
+ }
+
+/**
+ *
+ * Make a readable string out of an EPOC error code.
+ *
+ * @param "TInt aError"
+ * The error code
+ *
+ * @return "TPtrC"
+ * The error code as a readable string
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TPtrC CLog::EpocErrorToText(TInt aError)
+ {
+ switch (aError)
+ {
+ case KErrNone:
+ return _L("KErrNone");
+ case KErrNotFound:
+ return _L("KErrNotFound");
+ case KErrGeneral:
+ return _L("KErrGeneral");
+ case KErrCancel:
+ return _L("KErrCancel");
+ case KErrNoMemory:
+ return _L("KErrNoMemory");
+ case KErrNotSupported:
+ return _L("KErrNotSupported");
+ case KErrArgument:
+ return _L("KErrArgument");
+ case KErrTotalLossOfPrecision:
+ return _L("KErrTotalLossOfPrecision");
+ case KErrBadHandle:
+ return _L("KErrBadHandle");
+ case KErrOverflow:
+ return _L("KErrOverflow");
+ case KErrUnderflow:
+ return _L("KErrUnderflow");
+ case KErrAlreadyExists:
+ return _L("KErrAlreadyExists");
+ case KErrPathNotFound:
+ return _L("KErrPathNotFound");
+ case KErrDied:
+ return _L("KErrDied");
+ case KErrInUse:
+ return _L("KErrInUse");
+ case KErrServerTerminated:
+ return _L("KErrServerTerminated");
+ case KErrServerBusy:
+ return _L("KErrServerBusy");
+ case KErrCompletion:
+ return _L("KErrCompletion");
+ case KErrNotReady:
+ return _L("KErrNotReady");
+ case KErrUnknown:
+ return _L("KErrUnknown");
+ case KErrCorrupt:
+ return _L("KErrCorrupt");
+ case KErrAccessDenied:
+ return _L("KErrAccessDenied");
+ case KErrLocked:
+ return _L("KErrLocked");
+ case KErrWrite:
+ return _L("KErrWrite");
+ case KErrDisMounted:
+ return _L("KErrDisMounted");
+ case KErrEof:
+ return _L("KErrEof");
+ case KErrDiskFull:
+ return _L("KErrDiskFull");
+ case KErrBadDriver:
+ return _L("KErrBadDriver");
+ case KErrBadName:
+ return _L("KErrBadName");
+ case KErrCommsLineFail:
+ return _L("KErrCommsLineFail");
+ case KErrCommsFrame:
+ return _L("KErrCommsFrame");
+ case KErrCommsOverrun:
+ return _L("KErrCommsOverrun");
+ case KErrCommsParity:
+ return _L("KErrCommsParity");
+ case KErrTimedOut:
+ return _L("KErrTimedOut");
+ case KErrCouldNotConnect:
+ return _L("KErrCouldNotConnect");
+ case KErrCouldNotDisconnect:
+ return _L("KErrCouldNotDisconnect");
+ case KErrDisconnected:
+ return _L("KErrDisconnected");
+ case KErrBadLibraryEntryPoint:
+ return _L("KErrBadLibraryEntryPoint");
+ case KErrBadDescriptor:
+ return _L("KErrBadDescriptor");
+ case KErrAbort:
+ return _L("KErrAbort");
+ case KErrTooBig:
+ return _L("KErrTooBig");
+ default:
+ return _L("Unknown");
+ } // end switch
+ }
+
+
+/**
+ *
+ * Make a readable string out of a test verdict.
+ *
+ * @param "TVerdict aTestVerdict"
+ * The test verdict
+ *
+ * @return "TPtrC"
+ * The test verdict as a readable string
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TPtrC CLog::TestResultText(TVerdict aTestVerdict)
+ {
+ switch (aTestVerdict)
+ {
+ case EPass:
+ return _L("PASS");
+ case EFail:
+ return _L("FAIL");
+ case EInconclusive:
+ return _L("INCONCLUSIVE");
+ case ETestSuiteError:
+ return _L("TEST_SUITE_ERROR");
+ case EAbort:
+ return _L("ABORT");
+ case EKnownFailure: //A new TVerdict for a known failed test
+ return _L("KNOWN_Failure"); //using lower case in 'Failure' can remove the confusion on 'savres2html.bat' making test summary
+ default:
+ return _L("undefined");
+
+ }
+ }
+
+/**
+ *
+ * Write blank lines to the log.
+ *
+ * @param "TInt number"
+ * Number of lines to write
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::LogBlankLine(TInt aNumber)
+ {
+ for (TInt i = 0; i < aNumber; i++)
+ Log(_L(" "));
+ }
+
+/**
+ *
+ * Close the log.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::CloseLogFile()
+ {
+ // add the htm end
+ WriteFormat(_L("</end>"));
+
+ iClientSession.CloseLog();
+ }
+
+/**
+ *
+ * Set log severity.
+ *
+ * @param "TInt aSeverity"
+ * The required severity
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::SetSeverity(TInt aSeverity)
+{
+ iSeverity = aSeverity;
+}
+
+/**
+ *
+ * Get log severity.
+ *
+ * @return "TInt"
+ * The current severity
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TInt CLog::Severity() const
+{
+ return iSeverity;
+}
+
+/**
+ *
+ * Get log status from this logger's client session.
+ *
+ * @return "TInt"
+ * The current log status (a bitmask of TTestFrameworkLogMode)
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TInt CLog::LogStatus()
+ {
+ return iClientSession.LogStatus();
+ }
+
+
+/**
+ *
+ * Write formatted output to the log.
+ *
+ * @param "TRefByValue<const TDesC16> aFmt"
+ * Printf-style format.
+ *
+ * @param "..."
+ * Variable print parameters
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::WriteFormat(TRefByValue<const TDesC16> aFmt, ...)
+ {
+
+ // file / port logging not enabled
+ if (!(iLogStatus & ELogToFile))
+ if (!(iLogStatus & ELogToPort))
+ return;
+
+ VA_LIST aList;
+ VA_START(aList, aFmt);
+
+ TIntegrationTestLog16Overflow overflow16;
+
+ TUint16* dataBufPtr = (TUint16*)(iDataBuf.Ptr());
+ TPtr16 lineBuf(dataBufPtr, 0, KMaxLogLineLength);
+ lineBuf.Fill('\0', KMaxLogLineLength);
+
+ // get the current time and date
+ TTime now;
+ now.HomeTime();
+ TDateTime dateTime = now.DateTime() ;
+
+ // add the current time and date
+ lineBuf.Format(_L("%02d/%02d/%04d\t%02d:%02d:%02d:%03d\t"),
+ dateTime.Day()+1,
+ dateTime.Month()+1,
+ dateTime.Year(),
+ dateTime.Hour(),
+ dateTime.Minute(),
+ dateTime.Second(),
+ (dateTime.MicroSecond() / 1000));
+
+ // followed by the formatted data
+ lineBuf.AppendFormatList(aFmt, aList, &overflow16);
+ VA_END(aList);
+
+ // send one message - the server will write to both if enabled
+ TInt theStatus = 0;
+ if (iLogStatus & ELogToFile)
+ theStatus |= ELogToFile;
+ if (iLogStatus & ELogToPort)
+ theStatus |= ELogToPort;
+
+ iClientSession.WriteLog(lineBuf, theStatus);
+ }
+
+/**
+ *
+ * Write output to the console with date/time stamp
+ *
+ * @param "const TDesC& aBuf"
+ * The output.
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C void CLog::WriteLogConsole(const TDesC& aBuf)
+ {
+
+ // console logging not enabled
+ if (!(iLogStatus & ELogConsoleFull))
+ return;
+
+ // decode formatted data for display on console
+ TUint16* dataBufPtr = (TUint16*)(iDataBuf.Ptr());
+ TPtr16 lineBuf(dataBufPtr, 0, KMaxLogLineLength);
+ lineBuf.Fill('\0', KMaxLogLineLength);
+
+ // get the current time and date
+ TTime now;
+ now.HomeTime();
+ TDateTime dateTime = now.DateTime() ;
+
+ // add the current time and date
+ lineBuf.Format(_L("%02d/%02d/%04d\t%02d:%02d:%02d:%03d\t%S"),
+ dateTime.Day()+1,
+ dateTime.Month()+1,
+ dateTime.Year(),
+ dateTime.Hour(),
+ dateTime.Minute(),
+ dateTime.Second(),
+ (dateTime.MicroSecond() / 1000),
+ &aBuf);
+
+ iClientSession.WriteLog(lineBuf, ELogToConsole);
+ }
+
+/**
+ *
+ * This function is used to avoid a panic if format text overflows
+ * the internal buffer.
+ *
+ * @param "TDes16&"
+ * the overflowing string
+ *
+ * @xxxx
+ *
+ */
+void TIntegrationTestLog16Overflow::Overflow(TDes16& aDes)
+ {
+ aDes = _L("*** ERROR : line too long, cannot log ***");
+ }
+
+/**
+ *
+ * Check a severity value is valid.
+ *
+ * @param "TInt aSev"
+ * The value to check.
+ *
+ * @return "TBool"
+ * Valid (ETrue) or not (EFalse).
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TBool LogSeverity::IsValid(TInt aSev)
+ {
+ return ((aSev & ~(ESevrAll)) == 0);
+ }
+
+/**
+ *
+ * Check a severity value is active
+ *
+ * @param "TInt aThisSev"
+ * The value to check.
+ *
+ * @param "TInt aGlobalSev"
+ * The value to check against (e.g. global severity value of a log).
+ *
+ * @return "TBool"
+ * Active (ETrue) or not (EFalse).
+ *
+ * @xxxx
+ *
+ */
+EXPORT_C TBool LogSeverity::IsActive(TInt aThisSev, TInt aGlobalSev)
+ {
+ return ((aThisSev & aGlobalSev) != 0);
+ }