os/persistentdata/traceservices/commsdebugutility/SCLI/comsdbgcli.cpp
author sl@SLION-WIN7.fritz.box
Fri, 15 Jun 2012 03:10:57 +0200
changeset 0 bde4ae8d615e
permissions -rw-r--r--
First public contribution.
     1 // Copyright (c) 1997-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 // Implements the Flogger client side
    15 // 
    16 //
    17 
    18 /**
    19  @file
    20  @internalTechnology
    21 */
    22 
    23 #include <f32file.h>
    24 #include <comms-infras/commsdebugutility.h>
    25 #include "comsdbgstd.h"
    26 #include <e32def.h>
    27 
    28 #include <utf.h>
    29 
    30 #define BLANK	_S("")
    31 
    32 const TInt KHexDumpWidth=16;			///< Number of bytes written per line when formatting as hex.
    33 const TInt KNumberMessageSlots=1;       ///< Number of message slots on flogger client.no asynchronous IPC so never need more than 1 slot
    34 const TInt KLowestPrintableCharacter = 32; ///< In Hex output, replace chars below space with a dot.
    35 const TInt KHighestPrintableCharacter = 126; ///< In Hex output, replace chars above 7-bits with a dot.
    36 
    37 _LIT(KFirstFormatString,"%s%04x : ");   ///< Format string used in Hexdump to format first part: header and byte numbers.
    38 _LIT(KSecondFormatString,"%02x ");      ///< Format string used in Hexdump to format mid part: each of the 16 bytes as hex
    39 _LIT(KThirdFormatString,"%c");          ///< Format string used in Hexdump to format the last part: each of the 16 bytes as characters
    40 _LIT(KThreeSpaces,"   ");               ///< Format string used in Hexdump to define padding between first and mid parts
    41 _LIT(KTwoSpaces," ");                   ///< Format string used in Hexdump to define padding between hex and char bytes.
    42 
    43 _LIT8(KFirstFormatString8,"%04x : ");   ///< Format string used in Hexdump to format first part: header and byte numbers.
    44 _LIT8(KSecondFormatString8,"%02x ");      ///< Format string used in Hexdump to format mid part: each of the 16 bytes as hex
    45 _LIT8(KThirdFormatString8,"%c");          ///< Format string used in Hexdump to format the last part: each of the 16 bytes as characters
    46 _LIT8(KThreeSpaces8,"   ");               ///< Format string used in Hexdump to define padding between first and mid parts
    47 _LIT8(KTwoSpaces8," ");                   ///< Format string used in Hexdump to define padding between hex and char bytes.
    48 
    49 
    50 
    51 //
    52 // RFileLogger class definition
    53 //
    54 
    55 EXPORT_C RFileLogger::RFileLogger() : iLoggerBody(NULL)
    56 /**
    57  * Create a new flogger client interface object with an empty body.
    58  * @internalTechnology 
    59  */
    60 	{}
    61 
    62 EXPORT_C RFileLogger::~RFileLogger()
    63 /**
    64  * Destructor
    65  * @internalTechnology 
    66  */
    67 	{}
    68 
    69 EXPORT_C TVersion RFileLogger::Version() const
    70 /**
    71  * Return the client side version number
    72  * @internalTechnology 
    73  * @return TVersion 3-part version number: major, minor, build.
    74  */
    75 	{
    76 
    77 	return(TVersion(KFLogSrvMajorVersionNumber,KFLogSrvMinorVersionNumber,KFLogSrvBuildVersionNumber));
    78 	}
    79 
    80 EXPORT_C TInt RFileLogger::Connect()
    81 /**
    82  Connect to the flogger server - default number of message slots = 1
    83  @internalTechnology 
    84  @return TInt indicating success code (KErrNone), KErrNoMemory if failed to allocate log body
    85          or an error from RSessionBase::CreateSession.
    86          KErrAlreadyExists if Connect has already been called.
    87  */
    88 	{
    89 	if (iLoggerBody)
    90 		{
    91 		return KErrAlreadyExists;
    92 		}
    93 	iLoggerBody = new RFileLoggerBody;
    94 	if (iLoggerBody)
    95 		{
    96 		TInt ret=DoConnect();
    97 		if (ret==KErrNotFound)
    98 			{
    99 			ret=FLogger::Start();
   100 			if (ret==KErrNone || ret==KErrAlreadyExists)
   101 				ret=DoConnect();
   102 			}
   103 		if (ret != KErrNone)
   104 			{
   105 			// we had a problem (perhaps no memory) so kill loggerbody again
   106 			delete iLoggerBody;
   107 			iLoggerBody = NULL;
   108 			}
   109 			
   110 		return ret;
   111 		} 
   112 	else
   113 		{
   114 		//OOM, so return KErrNoMemory so that OOM tests know this
   115 		return KErrNoMemory;
   116 		}
   117 	}
   118 
   119 EXPORT_C void RFileLogger::Close()
   120 /**
   121  * Close a client side session with the flogger server.
   122  * @internalTechnology 
   123  * @post The client session is closed and the body of the class is deleted.
   124  *       Further calls to the Write functions will fail silently until a new session is opened.
   125  */
   126 	{
   127 	if (iLoggerBody)
   128 		{
   129 		iLoggerBody->Close();
   130 		delete iLoggerBody;
   131 		}
   132 	iLoggerBody = NULL;
   133 	}
   134 
   135 EXPORT_C void RFileLogger::SetDateAndTime(TBool /*aUseDate*/,TBool /*aUseTime*/)
   136 /**
   137  * Does nothing.
   138  * @internalTechnology 
   139  * @removed    This function no longer needed since now logging to one file and
   140  *             date/time comes from system.
   141  */
   142 	{}
   143 
   144 EXPORT_C TInt RFileLogger::SetLogTags(const TDesC8& aSubsystem, const TDesC8& aComponent)
   145 /**
   146  * Set the two tag strings that all further writes by this client will use to
   147  * idenitfy it in the log file.
   148  * @internalTechnology 
   149  * @param aSubsystem	Specifies the tag1 name that goes into the log file
   150  * @param aComponent	specifies the tag2 name that goes into the log file
   151  * @post  The client session is updated so that all future calls use this tag set.
   152  *        Tags are truncated to KMaxTagLength.
   153  * @return TInt indicating success code (KErrNone) or an error code.
   154  * @note If an error occurs, the client connection will be silently closed to protect
   155  *       the client.
   156  */
   157 	{
   158 	TPtrC8 validSubsystem;
   159 	TPtrC8 validComponent;
   160 		
   161 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   162 	validComponent.Set(aComponent.Left(KMaxTagLength));
   163 	return DoSetLogTags(validSubsystem, validComponent);
   164 	}
   165 
   166 EXPORT_C void RFileLogger::CreateLog(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode /*aMode*/)
   167 /**
   168  * Sets the log tags.
   169  * @internalTechnology 
   170  * @removed             Not fully supported since flogger only uses one log file. Use SetLogTags instead.
   171  * @param aSubsystem	Specifies the tag1 name that goes into the log file
   172  * @param aComponent	specifies the tag2 name that goes into the log file
   173  * @param aMode         not used
   174  * @note	            This function is partially supported and is equivalent to calling SetLogTags.
   175  * @see SetLogTags
   176  */
   177 	{
   178 
   179 	TNameTag narrowComponent;
   180 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   181 	TNameTag narrowSubsystem;
   182 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   183 	
   184 	(void)DoSetLogTags(narrowSubsystem,narrowComponent);
   185 	}
   186 
   187 EXPORT_C void RFileLogger::CloseLog()
   188 /**
   189  * Close a client side session with the flogger server.
   190  * @internalTechnology 
   191  * @deprecated   With the advent of a single log file for all clients, closing the log file is no longer necessary. Use Close to close the session.
   192  * @see          Close
   193  */
   194 	{
   195 	Close();
   196 	}
   197 
   198 EXPORT_C TBool RFileLogger::LogValid() const
   199 /**
   200  * Always returns ETrue.
   201  * @internalTechnology 
   202  * @removed  With the advent of a single log file for all clients, checking for log validity is no longer necessary.
   203  * @return   ETrue always.
   204  */
   205 	{
   206 	return ETrue;
   207 	}
   208 
   209 EXPORT_C TInt RFileLogger::LastError() const
   210 /**
   211  * Always returns KErrNone
   212  * @internalTechnology 
   213  * @removed  Flogger no longer retains internal errors.
   214  * @return   KErrNone always.
   215  */
   216 	{
   217 	return KErrNone;
   218 	}
   219 
   220 EXPORT_C TInt RFileLogger::ClearLog()
   221 /**
   222  * Request that the server empty the log file.
   223  * @internalTechnology 
   224  * @pre  The client requesting the log be cleared must be listed in the flogger "ini" file
   225  *       as an enabled logging client. This prevents unwanted clients clearing the log.
   226  *       The session with the server must be active, otherwise this will fail silently.
   227  * @post A message is added to the server write queue that indicates to clear the log.
   228  *       Once the message reaches the head of the queue flogger will empty the log file
   229  *       and begin filling it again.
   230  * @return TInt indicating success code (KErrNone) or an error code.
   231  */
   232 	{
   233 	if (IsLogging())
   234 		{
   235 		__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
   236 		return iLoggerBody->DoSendReceive(EClearLog, TIpcArgs());
   237 		}
   238 	else
   239 		{
   240 		return KErrNone;
   241 		}
   242 	}
   243 
   244 //
   245 // 16-bit non-static writes
   246 //
   247 
   248 EXPORT_C void RFileLogger::Write(const TDesC16& aText)
   249 /**
   250  * Write 16-bit aText to the log file.
   251  * @internalTechnology 
   252  * @pre  The client requesting to log must be listed in the flogger "ini" file
   253  *       as an enabled logging client, otherwise no logging will occur.
   254  *       The session with the server must be active, otherwise this will fail silently.
   255  * @param aText Text to write
   256  * @post The 16-bit text is converted to 8-bit text before writing, and is truncated to KLogBufferSize
   257  *       if necessary.
   258  *       The text is preceded in the log file by the two client tags and the client thread ID.
   259  @note There is no need to supply CR, LF. If these are supplied it may cause the log output to be incorrect.
   260  */
   261 	{
   262 	if (!IsLogging())
   263 		{
   264 		return;
   265 		}
   266 
   267 	TPtrC16 textValid;
   268 	textValid.Set(aText.Left(KLogBufferSize));
   269 	TBuf8<KLogBufferSize> buf;
   270 	CnvUtfConverter::ConvertFromUnicodeToUtf8(buf,textValid);
   271 	DoWrite(buf);
   272 	}
   273 	
   274 EXPORT_C void RFileLogger::WriteFormat(TRefByValue<const TDesC16> aFmt,...)
   275 /**
   276  * Write the formatted 16-bit string aFmt to the log file
   277  * @internalTechnology 
   278  * @pre  The client requesting to log must be listed in the flogger "ini" file
   279  *       as an enabled logging client, otherwise no logging will occur.
   280  *       The session with the server must be active, otherwise this will fail silently.
   281  * @param aFmt c-style format descriptor, followed by any variables required by the format.
   282  * @post The 16-bit text is converted to 8-bit text before writing, and is truncated to KLogBufferSize
   283  *       if necessary.
   284  *       The text is preceded in the log file by the two client tags and the client thread ID.
   285  */
   286 	{
   287 	if (!IsLogging())
   288 		{
   289 		return;
   290 		}
   291   //coverity[var_decl]
   292 	VA_LIST list;
   293 	VA_START(list,aFmt);
   294 	//coverity[uninit_use_in_call]
   295 	DoWriteFormat(aFmt,list);
   296 	
   297 	}
   298 
   299 EXPORT_C void RFileLogger::WriteFormat(TRefByValue<const TDesC16> aFmt, VA_LIST& aList)
   300 /**
   301  * Write the formatted 16-bit string aFmt to the log file.
   302  * @internalTechnology 
   303  * @pre  The client requesting to log must be listed in the flogger "ini" file
   304  *       as an enabled logging client, otherwise no logging will occur.
   305  *       The session with the server must be active, otherwise this will fail silently.
   306  * @param aFmt c-style format descriptor
   307  * @param aList any variables required by the format.
   308  * @post The 16-bit text is converted to 8-bit text before writing, and is truncated to KLogBufferSize
   309  *       if necessary.
   310  *       The text is preceded in the log file by the two client tags and the client thread ID.
   311  */
   312 	{
   313 	if (IsLogging())
   314 		{
   315 		DoWriteFormat(aFmt,aList);
   316 		}
   317 	}
   318 
   319 //
   320 // 8-bit non-static writes
   321 //
   322 
   323 EXPORT_C void RFileLogger::Write(const TDesC8& aText)
   324 /**
   325  * Write 8-bit aText to the log file.
   326  * @internalTechnology 
   327  * @pre  The client requesting to log must be listed in the flogger "ini" file
   328  *       as an enabled logging client, otherwise no logging will occur.
   329  *       The session with the server must be active, otherwise this will fail silently.
   330  * @param aText  Text to log.
   331  * @post The text is truncated to KLogBufferSize if necessary.
   332  *       The text is preceded in the log file by the two client tags and the client thread ID.
   333  */
   334 	{
   335 	TPtrC8 textValid;
   336 	textValid.Set(aText.Left(KLogBufferSize));
   337 	if (IsLogging())
   338 		{
   339 		DoWrite(textValid);
   340 		}
   341 	}
   342 	
   343 EXPORT_C void RFileLogger::WriteFormat(TRefByValue<const TDesC8> aFmt,...)
   344 /**
   345  * Write the formatted 8-bit string aFmt to the log file.
   346  * @internalTechnology 
   347  * @pre  The client requesting to log must be listed in the flogger "ini" file
   348  *       as an enabled logging client, otherwise no logging will occur.
   349  *       The session with the server must be active, otherwise this will fail silently.
   350  * @param aFmt c-style format descriptor, followed by any variables required by the format.
   351  * @post The text is truncated to KLogBufferSize if necessary.
   352  *       The text is preceded in the log file by the two client tags and the client thread ID.
   353  */
   354 	{
   355 	if (!IsLogging())
   356 		{
   357 		return;
   358 		}
   359   //coverity[var_decl]		
   360 	VA_LIST list;
   361 	VA_START(list,aFmt);
   362 	//coverity[uninit_use_in_call]  
   363 	DoWriteFormat(aFmt,list);
   364 	}
   365 
   366 EXPORT_C void RFileLogger::WriteFormat(TRefByValue<const TDesC8> aFmt, VA_LIST& aList)
   367 /**
   368  * Write the formatted 8-bit string aFmt to the log file if it is a valid file.
   369  * @internalTechnology 
   370  * @pre  The client requesting to log must be listed in the flogger "ini" file
   371  *       as an enabled logging client, otherwise no logging will occur.
   372  *       The session with the server must be active, otherwise this will fail silently.
   373  * @param aFmt c-style format descriptor
   374  * @param aList any variables required by the format.
   375  * @post The text is truncated to KLogBufferSize if necessary.
   376  *       The text is preceded in the log file by the two client tags and the client thread ID.
   377  */
   378 	{
   379 	if (IsLogging())
   380 		{
   381 		DoWriteFormat(aFmt,aList);
   382 		}
   383 	}
   384 
   385 EXPORT_C void RFileLogger::WriteBinary(const TDesC8& aData)
   386 /**
   387  * Dump arbitrary data to the log file in a binary format.
   388  * @internalTechnology 
   389  * @pre  The client requesting to log must be listed in the flogger "ini" file
   390  *       as an enabled logging client, otherwise no logging will occur.
   391  *       The session with the server must be active, otherwise this will fail silently.
   392  * @param aData Descriptor of the data to be dumped
   393  * @post The 8-bit binary dump is preceded in the log file by the two client tags
   394  *
   395  * @note Unlike all other write API's, no thread ID is written with this API.
   396  */
   397 	{
   398 	if (IsLogging())
   399 		{
   400 		__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
   401 		(void)iLoggerBody->DoSendReceive(EWriteBinary, TIpcArgs(&aData, aData.Length()));
   402 		}
   403 	}
   404 
   405 
   406 //
   407 // 16-bit static writes
   408 //
   409 
   410 EXPORT_C void RFileLogger::Write(const TDesC8& aSubsystem, const TDesC8& aComponent, const TDesC16& aText)
   411 /**
   412  * Static write. Write 16-bit aText to the log file if it is a valid file.
   413  * @internalTechnology 
   414    @pre The client requesting to log must be listed in the flogger "ini" file
   415          as an enabled logging client, otherwise no logging will occur.
   416  * @param aSubsystem Specifies the tag1 name that goes into the log file
   417  * @param aComponent specifies the tag2 name that goes into the log file
   418  * @param aMode not used
   419  * @param aText Text to write
   420  * @post The text is converted to 8-bit text before writing, and truncated to KLogBufferSize if necessary.
   421  *       The text is preceded in the log file by the two client tags and the client thread ID.
   422  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   423  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   424  */
   425 	{
   426 	// truncate tags
   427 	TPtrC8 validSubsystem;
   428 	TPtrC8 validComponent;
   429 			
   430 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   431 	validComponent.Set(aComponent.Left(KMaxTagLength));
   432 
   433 	TBuf8<KLogBufferSize> buf;
   434 	CnvUtfConverter::ConvertFromUnicodeToUtf8(buf,aText);
   435 
   436 	DoStaticWrite(validSubsystem, validComponent, buf);
   437 	}
   438 
   439 EXPORT_C void RFileLogger::WriteFormat(const TDesC8& aSubsystem, const TDesC8& aComponent, const TRefByValue<const TDesC16> aFmt,...)
   440 /**
   441  * Static write. Write the formatted 16-bit string aFmt to the log file.
   442  * @internalTechnology 
   443    @pre The client requesting to log must be listed in the flogger "ini" file
   444         as an enabled logging client, otherwise no logging will occur.
   445  * @param aSubsystem Specifies the tag1 name that goes into the log file
   446  * @param aComponent specifies the tag2 name that goes into the log file
   447  * @param aFmt c-style format descriptor, followed by any variables required by the format.
   448  * @post The text is converted to 8-bit text before writing, and truncated to KLogBufferSize if necessary.
   449  *       The text is preceded in the log file by the two client tags and the client thread ID.
   450  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   451  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   452  */
   453 	{
   454 	//coverity[var_decl]
   455 	VA_LIST list;
   456 	VA_START(list,aFmt);
   457 	
   458 	// truncate tags
   459 	TPtrC8 validSubsystem;
   460 	TPtrC8 validComponent;
   461 		
   462 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   463 	validComponent.Set(aComponent.Left(KMaxTagLength));
   464 	//coverity[uninit_use_in_call]
   465 	DoStaticWriteFormat(validSubsystem,validComponent,aFmt,list);
   466 	}
   467 
   468 EXPORT_C void RFileLogger::WriteFormat(const TDesC8& aSubsystem, const TDesC8& aComponent, const TRefByValue<const TDesC16> aFmt, VA_LIST& aList)
   469 /**
   470  * Static write. Write the formatted 16-bit string aFmt to the log file.
   471  * @internalTechnology 
   472    @pre The client requesting to log must be listed in the flogger "ini" file
   473         as an enabled logging client, otherwise no logging will occur.
   474  * @param aSubsystem Specifies the tag1 name that goes into the log file
   475  * @param aComponent specifies the tag2 name that goes into the log file
   476  * @param aFmt c-style format descriptor
   477  * @param aList any variables required by the format.
   478  * @post The text is converted to 8-bit text before writing, and truncated to KLogBufferSize if necessary.
   479  *       The text is preceded in the log file by the two client tags and the client thread ID.
   480  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   481  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   482  */
   483 	{
   484 	// truncate tags
   485 	TPtrC8 validSubsystem;
   486 	TPtrC8 validComponent;
   487 		
   488 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   489 	validComponent.Set(aComponent.Left(KMaxTagLength));
   490 	
   491 	DoStaticWriteFormat(validSubsystem,validComponent,aFmt,aList);
   492 	}
   493 
   494 //
   495 // 8-bit static writes
   496 //
   497 
   498 EXPORT_C void RFileLogger::Write(const TDesC8& aSubsystem, const TDesC8& aComponent, const TDesC8& aText)
   499 /**
   500  * Static write. Write 8-bit aText to the log file.
   501  * @internalTechnology 
   502    @pre The client requesting to log must be listed in the flogger "ini" file
   503         as an enabled logging client, otherwise no logging will occur.
   504  * @param aSubsystem Specifies the tag1 name that goes into the log file
   505  * @param aComponent specifies the tag2 name that goes into the log file
   506  * @param aText  Text to log.
   507  * @post The text is truncated to KLogBufferSize if necessary.
   508  *       The text is preceded in the log file by the two client tags and the client thread ID.
   509  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   510  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   511  */
   512 	{
   513 	// truncate tags
   514 	TPtrC8 validSubsystem;
   515 	TPtrC8 validComponent;
   516 			
   517 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   518 	validComponent.Set(aComponent.Left(KMaxTagLength));
   519 	DoStaticWrite(validSubsystem,validComponent, aText);
   520 	}
   521 
   522 EXPORT_C void RFileLogger::WriteFormat(const TDesC8& aSubsystem, const TDesC8& aComponent, const TRefByValue<const TDesC8> aFmt,...)
   523 /**
   524  * Static write. Write the formatted 8-bit string aFmt to the log file.
   525  * @internalTechnology 
   526    @pre The client requesting to log must be listed in the flogger "ini" file
   527         as an enabled logging client, otherwise no logging will occur.
   528  * @param aSubsystem Specifies the tag1 name that goes into the log file
   529  * @param aComponent specifies the tag2 name that goes into the log file
   530  * @param aFmt c-style format descriptor, followed by any variables required by the format.
   531  * @post The text is truncated to KLogBufferSize if necessary.
   532  *       The text is preceded in the log file by the two client tags and the client thread ID.
   533  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   534  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   535  */
   536 
   537 	{
   538 	//coverity[var_decl]
   539 	VA_LIST list;
   540 	VA_START(list,aFmt);
   541 	
   542 	// truncate tags
   543 	TPtrC8 validSubsystem;
   544 	TPtrC8 validComponent;
   545 		
   546 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   547 	validComponent.Set(aComponent.Left(KMaxTagLength));
   548 	//coverity[uninit_use_in_call]
   549 	DoStaticWriteFormat(validSubsystem,validComponent,aFmt,list);
   550 	}
   551 
   552 EXPORT_C void RFileLogger::WriteFormat(const TDesC8& aSubsystem, const TDesC8& aComponent, const TRefByValue<const TDesC8> aFmt, VA_LIST& aList)
   553 /**
   554  * Static write. Write the formatted 16-bit string aFmt to the log file.
   555  * @internalTechnology 
   556    @pre The client requesting to log must be listed in the flogger "ini" file
   557         as an enabled logging client, otherwise no logging will occur.
   558  * @param aSubsystem Specifies the tag1 name that goes into the log file
   559  * @param aComponent specifies the tag2 name that goes into the log file
   560  * @param aFmt c-style format descriptor
   561  * @param aList any variables required by the format.
   562  * @post The text is truncated to KLogBufferSize if necessary.
   563  *       The text is preceded in the log file by the two client tags and the client thread ID.
   564  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   565  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   566  */
   567 	{
   568 	//truncate tags
   569 	TPtrC8 validSubsystem;
   570 	TPtrC8 validComponent;
   571 		
   572 	validSubsystem.Set(aSubsystem.Left(KMaxTagLength));
   573 	validComponent.Set(aComponent.Left(KMaxTagLength));
   574 		
   575 	DoStaticWriteFormat(validSubsystem,validComponent,aFmt,aList);
   576 	}
   577 
   578 
   579 
   580 
   581 
   582 
   583 //
   584 // Removed 16-bit static writes
   585 //
   586 
   587 EXPORT_C void RFileLogger::Write(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode /*aMode*/, const TDesC16& aText)
   588 /**
   589  * Static write. Write 16-bit aText to the log file if it is a valid file.
   590  * @internalTechnology 
   591  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   592    @pre The client requesting to log must be listed in the flogger "ini" file
   593         as an enabled logging client, otherwise no logging will occur.
   594  * @param aSubsystem Specifies the tag1 name that goes into the log file
   595  * @param aComponent specifies the tag2 name that goes into the log file
   596  * @param aMode not used
   597  * @param aText Text to write
   598  * @post The text is converted to 8-bit text before writing, and truncated to KLogBufferSize if necessary.
   599  *       The text is preceded in the log file by the two client tags and the client thread ID.
   600  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   601  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   602  */
   603 	{
   604 	// the convert also truncates if necessary	
   605 	TNameTag narrowComponent;
   606 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   607 	TNameTag narrowSubsystem;
   608 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   609 
   610 	Write(narrowSubsystem, narrowComponent, aText);
   611 	}
   612 
   613 EXPORT_C void RFileLogger::WriteFormat(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode aMode, TRefByValue<const TDesC16> aFmt,...)
   614 /**
   615  * Static write. Write the formatted 16-bit string aFmt to the log file.
   616  * @internalTechnology 
   617  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   618    @pre The client requesting to log must be listed in the flogger "ini" file
   619         as an enabled logging client, otherwise no logging will occur.
   620  * @param aSubsystem Specifies the tag1 name that goes into the log file
   621  * @param aComponent specifies the tag2 name that goes into the log file
   622  * @param aMode not used
   623  * @param aFmt c-style format descriptor, followed by any variables required by the format.
   624  * @post The text is converted to 8-bit text before writing, and truncated to KLogBufferSize if necessary.
   625  *       The text is preceded in the log file by the two client tags and the client thread ID.
   626  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   627  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   628  */
   629 	{
   630 	// Just to remove the warning otherwise this does nothing 
   631 	if (aMode == EFileLoggingModeUnknown) { }
   632 	//coverity[var_decl]
   633 	VA_LIST list;
   634 	VA_START(list,aFmt);
   635 	
   636 	// the convert also truncates if necessary	
   637 	TNameTag narrowComponent;
   638 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   639 	TNameTag narrowSubsystem;
   640 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   641 	//coverity[uninit_use_in_call]
   642 	DoStaticWriteFormat(narrowSubsystem, narrowComponent,aFmt,list);
   643 	}
   644 
   645 EXPORT_C void RFileLogger::WriteFormat(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode /*aMode*/, TRefByValue<const TDesC16> aFmt, VA_LIST& aList)
   646 /**
   647  * Static write. Write the formatted 16-bit string aFmt to the log file.
   648  * @internalTechnology 
   649  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   650    @pre The client requesting to log must be listed in the flogger "ini" file
   651         as an enabled logging client, otherwise no logging will occur.
   652  * @param aSubsystem Specifies the tag1 name that goes into the log file
   653  * @param aComponent specifies the tag2 name that goes into the log file
   654  * @param aMode not used
   655  * @param aFmt c-style format descriptor
   656  * @param aList any variables required by the format.
   657  * @post The text is converted to 8-bit text before writing, and truncated to KLogBufferSize if necessary.
   658  *       The text is preceded in the log file by the two client tags and the client thread ID.
   659  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   660  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   661  */
   662 	{
   663 	// the convert also truncates if necessary	
   664 	TNameTag narrowComponent;
   665 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   666 	TNameTag narrowSubsystem;
   667 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   668 	
   669 	DoStaticWriteFormat(narrowSubsystem, narrowComponent,aFmt,aList);
   670 	}
   671 
   672 //
   673 // Removed 8-bit static writes
   674 //
   675 
   676 EXPORT_C void RFileLogger::Write(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode /*aMode*/, const TDesC8& aText)
   677 /**
   678  * Static write. Write 8-bit aText to the log file.
   679  * @internalTechnology 
   680  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   681    @pre The client requesting to log must be listed in the flogger "ini" file
   682         as an enabled logging client, otherwise no logging will occur.
   683  * @param aSubsystem Specifies the tag1 name that goes into the log file
   684  * @param aComponent specifies the tag2 name that goes into the log file
   685  * @param aMode not used
   686  * @param aText  Text to log.
   687  * @post The text is truncated to KLogBufferSize if necessary.
   688  *       The text is preceded in the log file by the two client tags and the client thread ID.
   689  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   690  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   691  */
   692 	{
   693 	// the convert also truncates if necessary
   694 	TNameTag narrowComponent;
   695 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   696 	TNameTag narrowSubsystem;
   697 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   698 	
   699 	Write(narrowSubsystem, narrowComponent, aText);
   700 	}
   701 
   702 EXPORT_C void RFileLogger::WriteFormat(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode aMode, TRefByValue<const TDesC8> aFmt,...)
   703 /**
   704  * Static write. Write the formatted 8-bit string aFmt to the log file.
   705  * @internalTechnology 
   706  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   707    @pre The client requesting to log must be listed in the flogger "ini" file
   708         as an enabled logging client, otherwise no logging will occur.
   709  * @param aSubsystem Specifies the tag1 name that goes into the log file
   710  * @param aComponent specifies the tag2 name that goes into the log file
   711  * @param aMode not used
   712  * @param aFmt c-style format descriptor, followed by any variables required by the format.
   713  * @post The text is truncated to KLogBufferSize if necessary.
   714  *       The text is preceded in the log file by the two client tags and the client thread ID.
   715  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   716  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   717  */
   718 
   719 	{
   720 	// Just to remove the warning otherwise this does nothing 
   721 	if (aMode == EFileLoggingModeUnknown) { }
   722 	//coverity[var_decl]
   723 	VA_LIST list;
   724 	VA_START(list,aFmt);
   725 	
   726 	// the convert also truncates if necessary	
   727 	TNameTag narrowComponent;
   728 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   729 	TNameTag narrowSubsystem;
   730 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   731 	//coverity[uninit_use_in_call]
   732 	DoStaticWriteFormat(narrowSubsystem, narrowComponent, aFmt, list);
   733 	}
   734 
   735 EXPORT_C void RFileLogger::WriteFormat(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode /*aMode*/, TRefByValue<const TDesC8> aFmt, VA_LIST& aList)
   736 /**
   737  * Static write. Write the formatted 16-bit string aFmt to the log file.
   738  * @internalTechnology 
   739  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   740    @pre The client requesting to log must be listed in the flogger "ini" file
   741         as an enabled logging client, otherwise no logging will occur.
   742  * @param aSubsystem Specifies the tag1 name that goes into the log file
   743  * @param aComponent specifies the tag2 name that goes into the log file
   744  * @param aMode not used
   745  * @param aFmt c-style format descriptor
   746  * @param aList any variables required by the format.
   747  * @post The text is truncated to KLogBufferSize if necessary.
   748  *       The text is preceded in the log file by the two client tags and the client thread ID.
   749  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   750  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   751  */
   752 	{
   753 	// the convert also truncates if necessary	
   754 	TNameTag narrowComponent;
   755 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   756 	TNameTag narrowSubsystem;
   757 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   758 	
   759 	DoStaticWriteFormat(narrowSubsystem, narrowComponent,aFmt,aList);
   760 	}
   761 
   762 //
   763 // Hex Dumps
   764 //
   765 
   766 EXPORT_C void RFileLogger::HexDump(const TText* aHeader, const TText* aMargin, const TUint8* aPtr, TInt aLen)
   767 /**
   768  * Dump arbitrary data to the log file as a standard hex dump.
   769  * @internalTechnology 
   770  * @pre   The session with the server must be active, otherwise this no action is taken.
   771          The client requesting to log must be listed in the flogger "ini" file
   772         as an enabled logging client, otherwise no logging will occur.
   773  * @param aHeader Specify a zero-terminated string to be printed before the first hex line. Leave as null or an empty string for no header.
   774  * @param aMargin Specify a zero-terminated string to be printed before each subsequent line. Leave as null or an empty string for no Margin.
   775  * @param aPtr pointer to the data being dumped.
   776  * @param aLen the number of bytes to dump
   777  * @post Each line is preceded in the log file by the two client tags and the client thread ID.
   778  * @note Example of aHeader/aMargin. If "aHeader" is set to "Fn Output:" and "aMargin" is set to "         ", then output would look
   779  *       like (for a print of the alphabet):
   780  *       TLOG	Example	20	FnOutput:0000 : 61 62 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70  abcdefghijklmnop
   781  *       TLOG	Example	20	         0010 : 71 72 73 74 75 76 77 78 79 7a                    qrstuvwxyz
   782  *   
   783  */
   784 	{
   785 	if (IsLogging())
   786 		{
   787 		DoHexDump(aHeader,aMargin,aPtr,aLen);
   788 		}
   789 
   790 
   791 	}
   792 
   793 
   794 
   795 EXPORT_C void RFileLogger::HexDump(const TDesC8& aData, const TDesC8& aHeader)
   796 /**
   797  * Dump arbitrary data to the log file as a standard hex dump.
   798  * @internalTechnology 
   799  * @pre   The session with the server must be active, otherwise this no action is taken.
   800           The client requesting to log must be listed in the flogger "ini" file
   801         as an enabled logging client, otherwise no logging will occur.
   802  * @param aData the data being dumped.
   803  * @param aHeader Specify a string to be printed before the first hex line. If not supplied, no header or margin is written.
   804  *        If supplied, then subsequent lines are indented to the length of aHeader.
   805  * @post Each line is preceded in the log file by the two client tags and the client thread ID.
   806  * @note Example of aHeader. If "aHeader" is set to "Fn Output:" then output would look
   807  *       like (for a print of the alphabet):
   808  *       TLOG	Example	20	FnOutput:0000 : 61 62 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70  abcdefghijklmnop
   809  *       TLOG	Example	20	         0010 : 71 72 73 74 75 76 77 78 79 7a                    qrstuvwxyz
   810  *   
   811  */
   812 	{
   813 	if (IsLogging())
   814 		{
   815 		DoHexDump(aData,aHeader,TPtrC8(NULL,0));
   816 		}
   817 
   818 
   819 	}
   820 
   821 
   822 
   823 
   824 
   825 
   826 EXPORT_C void RFileLogger::HexDump(const TDesC8& aSubsystem, const TDesC8& aComponent, const TDesC8& aData, const TDesC8& aHeader)
   827 /**
   828  * Static Write. Dump arbitrary data to the log file as a standard hex dump.
   829  * @internalTechnology 
   830    @pre The client requesting to log must be listed in the flogger "ini" file
   831         as an enabled logging client, otherwise no logging will occur.
   832  * @param aSubsystem Specifies the tag1 name that goes into the log file
   833  * @param aComponent specifies the tag2 name that goes into the log file
   834  * @param aData the data being dumped.
   835  * @param aHeader Specify a string to be printed before the first hex line. If not supplied, no header or Margin is written.
   836  * @param aMargin Specify a string to be printed before each subsequent line. If not supplied, a string of spaces equal to the length of aHeader is used.
   837  * @post Each line is preceded in the log file by the two client tags and the client thread ID.
   838  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   839  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   840  *       Example of aHeader/aMargin. If "aHeader" is set to "Fn Output:" and "aMargin" is set to "         ", then output would look
   841  *       like (for a print of the alphabet):
   842  *       TLOG	Example	20	FnOutput:0000 : 61 62 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70  abcdefghijklmnop
   843  *       TLOG	Example	20	         0010 : 71 72 73 74 75 76 77 78 79 7a                    qrstuvwxyz
   844  *   
   845  */
   846 	{
   847 	RFileLogger logger;
   848 	TInt ret=logger.Connect();
   849 	if (ret==KErrNone)
   850 		{
   851 		ret = logger.SetLogTags(aSubsystem,aComponent);
   852 		if (((ret == KErrNone) && logger.iLoggerBody) && logger.iLoggerBody->iLoggingOnPckg())
   853 			{
   854 			logger.DoHexDump(aData,aHeader,TPtrC8(NULL,0));
   855 			}
   856 		logger.Close();
   857 		}
   858 	}
   859 
   860 
   861 
   862 
   863 
   864 EXPORT_C void RFileLogger::HexDump(const TDesC& aSubsystem, const TDesC& aComponent, TFileLoggingMode /*aMode*/, const TText* aHeader, const TText* aMargin, const TUint8* aPtr, TInt aLen)
   865 /**
   866  * Static Write. Dump arbitrary data to the log file as a standard hex dump.
   867  * @internalTechnology 
   868  * @removed With the advent of a single log file for all clients, this function has been replaced by an equivalent without the aMode parameter.
   869    @pre The client requesting to log must be listed in the flogger "ini" file
   870         as an enabled logging client, otherwise no logging will occur.
   871  * @param aSubsystem Specifies the tag1 name that goes into the log file
   872  * @param aComponent specifies the tag2 name that goes into the log file
   873  * @param aMode not used
   874  * @param aHeader Specify a zero-terminated string to be printed before the first hex line. Leave as null or an empty string for no header.
   875  * @param aMargin Specify a zero-terminated string to be printed before each subsequent line. Leave as null or an empty string for no Margin.
   876  * @param aPtr pointer to the data being dumped.
   877  * @param aLen the number of bytes to dump
   878  * @post Each line is preceded in the log file by the two client tags and the client thread ID.
   879  *       "aSubsystem" and "aComponent" are each truncated to KMaxTagLength.
   880  * @note This function has poor performance since it performs a full connection and disconnection to the flogger server.
   881  *       Example of aHeader/aMargin. If "aHeader" is set to "Fn Output:" and "aMargin" is set to "         ", then output would look
   882  *       like (for a print of the alphabet):
   883  *       TLOG	Example	20	FnOutput:0000 : 61 62 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70  abcdefghijklmnop
   884  *       TLOG	Example	20	         0010 : 71 72 73 74 75 76 77 78 79 7a                    qrstuvwxyz
   885  *   
   886  */
   887 	{
   888 	// the convert also truncates if necessary
   889 	TNameTag narrowComponent;
   890 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowComponent,aComponent);
   891 	TNameTag narrowSubsystem;
   892 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowSubsystem,aSubsystem);
   893 	
   894 	RFileLogger logger;
   895 	TInt ret=logger.Connect();
   896 	if (ret==KErrNone)
   897 		{
   898 		ret = logger.SetLogTags(narrowSubsystem,narrowComponent);
   899 		if (((ret == KErrNone) && logger.iLoggerBody) && logger.iLoggerBody->iLoggingOnPckg())
   900 			{
   901 			logger.DoHexDump(aHeader,aMargin,aPtr,aLen);
   902 			}
   903 		logger.Close();
   904 		}
   905 
   906 	}
   907 
   908 
   909 EXPORT_C TInt RFileLogger::Handle() const
   910 // Returns handle of session, or Null if no session.
   911 	{
   912 	if (iLoggerBody)
   913 		{
   914 		return iLoggerBody->Handle();
   915 		}
   916 	else
   917 		{
   918 		return 0;
   919 		}
   920 	}
   921 
   922 EXPORT_C TInt RFileLogger::Share() 
   923 	{
   924 	if (iLoggerBody)
   925 		{
   926   		return iLoggerBody->ShareAuto();
   927 		}
   928 	return KErrSessionClosed;
   929 	}
   930 
   931 
   932 //
   933 // Debug tools to check for memory leaks
   934 //
   935 
   936 EXPORT_C void RFileLogger::__DbgShutDownServer()
   937 /**
   938  * Debugging Tool. Ask the flogger server to shutdown. Only valid in DEBUG builds.
   939  * @internalTechnology 
   940  */
   941 	{
   942 #ifdef _DEBUG
   943 	if (iLoggerBody)
   944 		(void)iLoggerBody->DoSendReceive(EShutDownServer);
   945 #endif
   946 	}
   947 
   948 EXPORT_C void RFileLogger::__DbgSetHeapFailure(TInt aFailAfter)
   949 /**
   950  * Debugging Tool. Ask the flogger server to set its heap failure. Only valid in DEBUG builds.
   951  * @internalTechnology 
   952  * @param aFailAfter The number of successful memory allocations which will occur before
   953  *        a memory allocation is failed by the memory manager.
   954  */
   955 	{
   956 #ifdef _DEBUG
   957 	if (iLoggerBody)
   958 		{
   959 		(void)iLoggerBody->DoSendReceive(ESetHeapFailure, TIpcArgs(aFailAfter));
   960 		}
   961 #else
   962 	(void)aFailAfter;
   963 #endif
   964 	}
   965 
   966 //
   967 // Private functions
   968 //
   969 
   970 TInt RFileLogger::DoConnect()
   971 /**
   972  * Connect to the flogger server
   973  * @return TInt indicating success code (KErrNone) or an error code.
   974  * @note: creates 1 slot: no asynchronous IPC so never need more than 1 reserved message slot.
   975  @internalComponent
   976  */
   977 	{
   978 	__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
   979 	return iLoggerBody->DoCreateSession(KFLoggerServerName,Version(),KNumberMessageSlots);
   980 	}
   981 
   982 TInt RFileLogger::DoSetLogTags(const TDesC8& aSubsystem, const TDesC8& aComponent)
   983 /**
   984  * Set the two tag strings that all further writes by this client will use to
   985  * identify it in the log file.
   986  * @param aSubsystem	Specifies the tag1 name that goes into the log file
   987  * @param aComponent	specifies the tag2 name that goes into the log file
   988  * @return TInt indicating success code (KErrNone), or (KErrNotFound) if
   989   the connection is not valid, or an error code from SendReceive.
   990  * @note If an error occurs, the client connection will be silently closed to protect
   991  *       the client.
   992  */
   993 	{
   994 	TInt err(KErrNone);
   995 	if (iLoggerBody)	//check that the connection was set up correctly
   996 		{
   997 		err = iLoggerBody->DoSendReceive(ESetLogTag, TIpcArgs(&aSubsystem, &aComponent, &(iLoggerBody->iLoggingOnPckg)));
   998 		if (err !=KErrNone )
   999 			{	//Something went wrong. We need to protect the client because error can be ignored.
  1000 			Close();
  1001 			}
  1002 		}
  1003 	else
  1004 		{
  1005 		err = KErrNotFound;
  1006 		}
  1007 	return err;
  1008 	}
  1009 
  1010 void RFileLogger::DoWrite(const TDesC8& aBuf)
  1011 /**
  1012  * Send to the flogger server the pre-formatted write string.
  1013  * @internalTechnology 
  1014  * @pre session is already open.
  1015  * @param aBuf 8-bit text to be written. It must not exceed KLogBufferSize.
  1016  */
  1017 	{
  1018 	__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
  1019 	(void)iLoggerBody->DoSendReceive(EWriteToLog,TIpcArgs(&aBuf, aBuf.Length()));	
  1020 	}
  1021 
  1022 void RFileLogger::DoWriteFormat(TRefByValue<const TDesC16> aFmt, VA_LIST& aList)
  1023 /**
  1024  * Trim and convert format string before sending to the flogger server.
  1025  * @pre session is already open.
  1026  * @param aFmt c-style formatted text to be written.
  1027  * @param aList any variables required by the format.
  1028  * @post The final string is truncated to KLogBufferSize and converted to 8-bit.
  1029  */
  1030 	{
  1031 	TBuf16<KLogBufferSize> wideBuf;
  1032 	__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
  1033 	wideBuf.AppendFormatList(aFmt, aList, &(iLoggerBody->iFlogOverflow16));
  1034 	TBuf8<KLogBufferSize> narrowBuf;
  1035 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowBuf,wideBuf);
  1036 	DoWrite(narrowBuf);
  1037 	}
  1038 
  1039 void RFileLogger::DoWriteFormat(TRefByValue<const TDesC8> aFmt, VA_LIST& aList)
  1040 /**
  1041  * Trim format string before sending to the flogger server.
  1042  * @pre session is already open.
  1043  * @param aFmt c-style formatted text to be written.
  1044  * @param aList any variables required by the format.
  1045  * @post The final string is truncated to KLogBufferSize.
  1046  */
  1047 	{
  1048 	TBuf8<KLogBufferSize> buf;
  1049 	__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
  1050 	buf.AppendFormatList(aFmt,aList, &(iLoggerBody->iFlogOverflow8));
  1051 	DoWrite(buf);
  1052 	}
  1053 	
  1054 void RFileLogger::DoSendStaticWrite(const TDesC8& aSubsystem, const TDesC8& aComponent, const TDesC8& aText)
  1055 /**
  1056  * Send to the flogger server the pre-formatted write string.
  1057  * @pre session is already open.
  1058  *      aText is not longer than KLogBufferSize
  1059  * @param aSubsystem Specifies the tag1 name that goes into the log file
  1060  * @param aComponent specifies the tag2 name that goes into the log file
  1061  * @param aText text to write
  1062  * @post The text is only written if the tag1+tag2 combination is listed as an enabled client
  1063  *       in the flogger "ini" file, otherwise no action is taken.
  1064  *       The text is preceded in the log file by the two client tags and the client thread ID.
  1065  */
  1066 	{
  1067 	__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
  1068 	(void)iLoggerBody->DoSendReceive(EStaticWriteToLog,TIpcArgs(&aSubsystem, &aComponent, &aText, aText.Length()));		// ignore error
  1069 	}	
  1070 
  1071 void RFileLogger::DoStaticWrite(const TDesC8& aSubsystem, const TDesC8& aComponent, const TDesC8& aText)
  1072 /**
  1073  * Send to the flogger server the pre-formatted write string.
  1074  * @pre session is already open.
  1075  *      aText is not longer than KLogBufferSize
  1076  * @param aSubsystem Specifies the tag1 name that goes into the log file
  1077  * @param aComponent specifies the tag2 name that goes into the log file
  1078  * @param aText text to write
  1079  * @post The text is only written if the tag1+tag2 combination is listed as an enabled client
  1080  *       in the flogger "ini" file, otherwise no action is taken.
  1081  *       The text is preceded in the log file by the two client tags and the client thread ID.
  1082  */
  1083 	{
  1084 	RFileLogger logger;
  1085 	TInt ret=logger.Connect();
  1086 	if (ret==KErrNone)
  1087 		{
  1088 		TPtrC8 textValid;
  1089 		textValid.Set(aText.Left(KLogBufferSize));
  1090 
  1091 		logger.DoSendStaticWrite(aSubsystem, aComponent, textValid);
  1092 		}
  1093 
  1094 	logger.Close();
  1095 	}	
  1096 
  1097 
  1098 
  1099 void RFileLogger::DoStaticWriteFormat(const TDesC8& aSubsystem, const TDesC8& aComponent, TRefByValue<const TDesC> aFmt, VA_LIST& aList)
  1100 /**
  1101  * Send to the flogger server a format write string.
  1102  * @param aSubsystem Specifies the tag1 name that goes into the log file
  1103  * @param aComponent specifies the tag2 name that goes into the log file
  1104  * @param aFmt c-style formatted text to be written.
  1105  * @param aList any variables required by the format.
  1106  * @post The text is only written if the tag1+tag2 combination is listed as an enabled client
  1107  *       in the flogger "ini" file, otherwise no action is taken.
  1108  *       If necessary, the final string is truncated to KLogBufferSize.
  1109  *       The final string is converted to an 8-bit string.
  1110  *       The text is preceded in the log file by the two client tags and the client thread ID.
  1111  */
  1112 	{
  1113 	TFlogOverflow16 objFlogBody16;
  1114 	TBuf<KLogBufferSize> wideBuf;
  1115 	TBuf8<KLogBufferSize> narrowBuf;
  1116 
  1117     wideBuf.AppendFormatList(aFmt, aList, &objFlogBody16);
  1118 	CnvUtfConverter::ConvertFromUnicodeToUtf8(narrowBuf,wideBuf);
  1119 		
  1120     DoStaticWrite(aSubsystem, aComponent, narrowBuf);
  1121 	}
  1122 
  1123 void RFileLogger::DoStaticWriteFormat(const TDesC8& aSubsystem, const TDesC8& aComponent, TRefByValue<const TDesC8> aFmt, VA_LIST& aList)
  1124 /**
  1125  * Send to the flogger server a format write string.
  1126  * @param aSubsystem Specifies the tag1 name that goes into the log file
  1127  * @param aComponent specifies the tag2 name that goes into the log file
  1128  * @param aFmt c-style formatted text to be written.
  1129  * @param aList any variables required by the format.
  1130  * @post The text is only written if the tag1+tag2 combination is listed as an enabled client
  1131  *       in the flogger "ini" file, otherwise no action is taken.
  1132  *       If necessary, the final string is truncated to KLogBufferSize.
  1133  *       The text is preceded in the log file by the two client tags and the client thread ID.
  1134  */	{
  1135 	TFlogOverflow8 objFlogBody8;
  1136 	TBuf8<KLogBufferSize> buf;
  1137 	buf.AppendFormatList(aFmt, aList, &objFlogBody8);
  1138 	
  1139     DoStaticWrite(aSubsystem, aComponent, buf);
  1140 	}
  1141 
  1142 void RFileLogger::DoHexDump(const TText* aHeader, const TText* aMargin, const TUint8* aPtr, TInt aLen)
  1143 /**
  1144  * Static Write. Dump arbitrary data to the log file as a standard hex dump.
  1145  * @pre session is already open.
  1146  * @param aHeader Specify a zero-terminated string to be printed before the first hex line. Leave as null or an empty string for no header.
  1147  * @param aMargin Specify a zero-terminated string to be printed before each subsequent line. Leave as null or an empty string for no Margin.
  1148  * @param aPtr pointer to the data being dumped.
  1149  * @param aLen the number of bytes to dump
  1150  * @post The text is only written if the tag1+tag2 combination is listed as an enabled client
  1151  *       in the flogger "ini" file, otherwise no action is taken.
  1152  *       Each line is preceded in the log file by the two client tags and the client thread ID.
  1153  *       The data is written in lines of 16 characters.
  1154  * @note Example of aHeader/aMargin. If "aHeader" is set to "Fn Output:" and "aMargin" is set to "         ", then output would look
  1155  *       like (for a print of the alphabet):
  1156  *       TLOG	Example	20	FnOutput:0000 : 61 62 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70  abcdefghijklmnop
  1157  *       TLOG	Example	20	         0010 : 71 72 73 74 75 76 77 78 79 7a                    qrstuvwxyz
  1158  *   
  1159  */
  1160 	{
  1161 	// this delightful art-deco code lifted straight from old flogger
  1162 	if (aPtr==NULL)		// nothing to do
  1163 		{
  1164 		return;
  1165 		}
  1166 
  1167 	TBuf<KMaxHexDumpWidth> buf;
  1168 	TBuf8<KMaxHexDumpWidth> temp;
  1169 
  1170 
  1171 	TInt i=0;
  1172 	const TText* p=aHeader;
  1173 	while (aLen>0)
  1174 		{
  1175 		if (p==NULL)
  1176 			{
  1177 			p=BLANK;	// if NULL set p to a blank string
  1178 			}
  1179 		TInt n=(aLen>KHexDumpWidth ? KHexDumpWidth : aLen);
  1180 		__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
  1181 		buf.AppendFormat(KFirstFormatString,&(iLoggerBody->iFlogOverflow16),p,i);
  1182 		TInt j;
  1183 		for (j=0; j<n; j++)
  1184 			{
  1185 			buf.AppendFormat(KSecondFormatString,aPtr[i+j]);
  1186 			}
  1187 		while (j++<KHexDumpWidth)
  1188 			{
  1189 			buf.Append(KThreeSpaces);
  1190 			}
  1191 		buf.Append(KTwoSpaces);
  1192 		for (j=0; j<n; j++)
  1193 			{
  1194 			buf.AppendFormat(KThirdFormatString,(aPtr[i+j]<KLowestPrintableCharacter || aPtr[i+j]>KHighestPrintableCharacter) ? KFullStopChar : aPtr[i+j]);
  1195 			}
  1196 		
  1197 		CnvUtfConverter::ConvertFromUnicodeToUtf8(temp,buf);
  1198 		DoWrite(temp);
  1199 		
  1200 		buf.SetLength(0);
  1201 		temp.SetLength(0);
  1202 		aLen-=n;
  1203 		i+=n;
  1204 		p=aMargin;
  1205 		}
  1206 	}
  1207 
  1208 
  1209 
  1210 void RFileLogger::DoHexDump(const TDesC8& aData, const TDesC8& aHeader, const TDesC8& aMargin)
  1211 /**
  1212  * Static Write. Dump arbitrary data to the log file as a standard hex dump.
  1213  * @see RFileLogger::HexDump(const TDesC8& aData, const TDesC8& aHeader = 0)
  1214  * @param aMargin - supply a margin - if left null, then a margin of spaces of equal length to "aHeader"
  1215  *                  is used.
  1216  * @pre session is already open.
  1217  */
  1218 	{
  1219 	HBufC8* marginStr = NULL;
  1220 	TBuf8<KMaxHexDumpWidth> buf;
  1221 	TInt aRemainingLen = aData.Length();
  1222 	TInt aHeaderLen = aHeader.Length();
  1223 	
  1224 	__ASSERT_ALWAYS(iLoggerBody,User::Panic(KFloggerPanic, EInternalConsistencyFault));
  1225 	
  1226 	if (aData.Length()==0)		// nothing to do
  1227 		{
  1228 		return;
  1229 		}
  1230 
  1231 
  1232 	if (aHeaderLen > 0)
  1233 		{
  1234 		
  1235 		if (aMargin.Length() == 0)
  1236 			{
  1237 			marginStr = HBufC8::New(aHeader.Length());
  1238 			if (marginStr == NULL)
  1239 				{
  1240 				return;		// abort if No memory
  1241 				}
  1242 			TPtr8 marginStrPtr(marginStr->Des());
  1243 			marginStrPtr.AppendFill(' ',aHeader.Length());
  1244 			}
  1245 		else
  1246 			{
  1247 			marginStr = aMargin.Alloc();
  1248 			}
  1249 		}
  1250 		
  1251 		
  1252 	
  1253 	TUint blockStartPos = 0;
  1254 	while (aRemainingLen>0)
  1255 		{
  1256 		TInt blockLength = (aRemainingLen>KHexDumpWidth ? KHexDumpWidth : aRemainingLen);
  1257 		
  1258 		// write the header/margin and print in hex which bytes we are about to write
  1259 		if (blockStartPos == 0)
  1260 			{
  1261 			if (aHeaderLen > 0)
  1262 				{
  1263 				buf.Append(aHeader);
  1264 				}
  1265 			buf.AppendFormat(KFirstFormatString8,&(iLoggerBody->iFlogOverflow8), blockStartPos);
  1266 			}
  1267 		else
  1268 			{
  1269 			if (marginStr)
  1270 				{
  1271 				buf.Append(*marginStr);
  1272 				}
  1273 			buf.AppendFormat(KFirstFormatString8,&(iLoggerBody->iFlogOverflow8),blockStartPos);
  1274 			}
  1275 		
  1276 		TInt bytePos;
  1277 		// write the bytes as hex
  1278 		for (bytePos = 0; bytePos < blockLength; bytePos++)
  1279 			{
  1280 			buf.AppendFormat(KSecondFormatString8,aData[blockStartPos + bytePos]);
  1281 			}
  1282 		while (bytePos++ < KHexDumpWidth)
  1283 			{
  1284 			buf.Append(KThreeSpaces8);
  1285 			}
  1286 		buf.Append(KTwoSpaces8);
  1287 		// print the bytes as characters, or full stops if outside printable range
  1288 		for (bytePos = 0; bytePos < blockLength; bytePos++)
  1289 			{
  1290 			buf.AppendFormat(KThirdFormatString8,(aData[blockStartPos + bytePos] < KLowestPrintableCharacter || aData[blockStartPos + bytePos] > KHighestPrintableCharacter) ? KFullStopChar8 : aData[blockStartPos + bytePos]);
  1291 			}
  1292 		
  1293 		DoWrite(buf);
  1294 		
  1295 		buf.SetLength(0);
  1296 		aRemainingLen -= blockLength;
  1297 		blockStartPos += blockLength;
  1298 		}
  1299 	delete marginStr;
  1300 	}
  1301 
  1302 
  1303 
  1304 EXPORT_C void ClientRunStubOrdinal1()
  1305 /**
  1306  * @removed This function has been removed because the flogsvrl dll contains the equivalent function
  1307 @internalComponent
  1308  */
  1309 	{User::Panic(KFloggerPanic, KErrNotSupported);}
  1310