applayerprotocols/httptransportfw/Test/T_HttpIntegration/TEngine.cpp
changeset 0 b16258d2340f
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/applayerprotocols/httptransportfw/Test/T_HttpIntegration/TEngine.cpp	Tue Feb 02 01:09:52 2010 +0200
@@ -0,0 +1,1876 @@
+// 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:
+// $Header$
+// The CTEngine is the class that manages the test infrastructure
+// It knows how to process scripts and where to find command knowledge
+// The plan is:
+// Process console command line or command line supplied script
+// read in each line (or command) and process that (if appropriate)
+// Include Files  
+// 
+//
+
+#include <e32std.h>
+#include <s32file.h>
+#include <f32file.h>
+#include <e32hal.h>
+#include <fbs.h>
+
+//-----------------------------------------------------------------------------
+
+const TInt KMaxLogEntrySize = 512;
+const TInt KMaxUserEntrySize = 128;
+
+//-----------------------------------------------------------------------------
+
+//	result define names
+_LIT(KLastResultCode, "$LastResult$");
+_LIT(KLastErrorCode, "$LastError$");
+
+//-----------------------------------------------------------------------------
+
+#include "TEngine.h"
+
+//-----------------------------------------------------------------------------
+// This is used by the CallCmdFile, CloseCmdFile and CloseCmdFiles member
+// functions to alter the command file context. This function defines the
+// call argument tags %0%, %1%, ... %k% to those of the present cmd file.
+// If there is no command file, then the argument tags (all) are removed.
+
+#if !defined(TEMPLATED_CATALOGUE)
+
+LOCAL_C void SetContextL(CCatalogue *aCatalog, CCmdFile* aCmdFile )
+
+#else
+
+template <class T>
+LOCAL_C void SetContextL(CCatalogue<T> *aCatalog, CCmdFile* aCmdFile )
+
+#endif
+
+{
+if ( aCmdFile == NULL )
+	{
+	// No command file = console context: parameter markers are not
+	// recognised at all i.e. remove them all.
+	TBuf<6> buf;
+	TInt i;
+	for ( i = 0; i <= TFR_MAX_CALL_ARGUMENTS; ++i )
+		{
+		buf.Format( _L("%%%d%%"), i );
+		aCatalog->Delete(buf);
+		}
+	}
+else
+	{
+	// Command file context: parameters markers will be mapped to the
+	// file name, to the call arguments and to "".
+	TBuf<6> buf;
+	TPtrC   arg;
+	TInt    i;
+	TInt		iArgs = aCmdFile->Argc();
+
+	for ( i = 0; ( (i < TFR_MAX_CALL_ARGUMENTS) && (i < iArgs) ); ++i )
+		{
+		buf.Format(_L("%%%d%%"), i);
+		arg.Set(aCmdFile->Argv(i));
+		aCatalog->Delete(buf);
+		aCatalog->AddL(buf,arg);
+		}
+
+	for ( ; i < 10; ++i )
+		{
+		buf.Format(_L("%%%d%%"), i);
+		aCatalog->Delete(buf);
+		aCatalog->AddL(buf, _L(""));
+		}
+	}
+
+}
+
+//-----------------------------------------------------------------------------
+//    Overflow handler.
+
+void TTestMachineOverflow::Overflow( TDes16& aDes)
+{
+_LIT(KErrOverflowMsg, "...");
+if( aDes.MaxLength() >= KErrOverflowMsg().Length() + aDes.Length() )
+	aDes.Append(KErrOverflowMsg);
+}
+
+//-----------------------------------------------------------------------------
+//	NewL for Console interface
+
+CTEngine* CTEngine::NewL( CConsoleBase* aConsole )
+{
+CTEngine* self = NewLC(aConsole);
+CleanupStack::Pop(self);
+return self; 
+}
+
+//-----------------------------------------------------------------------------
+//	NewLC for Console Interface
+
+CTEngine* CTEngine::NewLC( CConsoleBase* aConsole )
+{
+CTEngine* self = new (ELeave) CTEngine(aConsole);
+CleanupStack::PushL(self);
+self->ConstructL();
+return self;
+}
+
+//-----------------------------------------------------------------------------
+//	Destructor
+
+CTEngine::~CTEngine()
+{
+Cancel();
+
+	iTimer.Close();
+	iFileServer.Close();
+	delete iCmdFile;
+	delete iLogFile;
+
+	delete iConsoleReader;
+	delete iDomain;
+	delete iDefines;
+	delete iIFPile;
+	delete iLogPile;
+ 	delete iCmdPile;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::ConstructL()
+{
+
+iConsoleEnabled = ( iConsole != NULL );    
+
+iCmdPile = CPile<CCmdFile>::NewL();
+iLogPile = CPile<CLogFile>::NewL();
+iIFPile = CPile<CIFControl>::NewL();
+
+
+#if !defined(TEMPLATED_CATALOGUE)
+iDefines = CCatalogue::NewL();
+#else
+iDefines = CCatalogue<CLabeledText>::NewL();
+#endif
+
+
+//	domain specific catalogue of items. This provides
+//	a mechanism by which we can disassociate the framework
+//	from the domain specific commands/data requirements
+iDomain = CObjCatalogue::NewL();
+
+iConsoleReader = CConsoleReader::NewL(*iConsole);
+TInt r = iTimer.CreateLocal();
+
+if (r!=KErrNone)
+	User::Leave(r);
+
+//	Provide access to the fileserver
+User::LeaveIfError(iFileServer.Connect());
+
+//	This is normally true (to enable replication of printed
+//	output to log (if enabled)
+iLogActivity = ETrue;
+
+//	show the unprocessed command lines on screen and log
+SetShowCmdLine(ETrue);
+}
+
+//-----------------------------------------------------------------------------
+
+CTEngine::CTEngine(CConsoleBase* aConsole)
+	: 
+	CActive(EPriorityStandard), 
+	iStopped(ETrue), 
+	iEchoMode(ETrue),
+	iConsole(aConsole)
+{
+iConsoleEnabled = ( iConsole != NULL );    
+
+iCmdPath.Zero();
+iLogPath.Zero();
+iCmdline.Zero();
+iCommand.Zero();
+iPrompt.Copy(THA_CommandPrompt);
+
+CActiveScheduler::Add(this);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::SetCmdFamily(CCmdFamily* aCmdFamily)
+{
+iCmdFamily = aCmdFamily;
+if (aCmdFamily != NULL) 
+	aCmdFamily->SetMachine( this );
+}
+
+//-----------------------------------------------------------------------------
+
+TBool CTEngine::ConsoleEnabled( )
+{
+return ( iConsoleEnabled );
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::DisableConsole()
+{
+iConsoleEnabled = EFalse;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::EnableConsole()
+{
+iConsoleEnabled = (iConsole != NULL);
+}
+
+//-----------------------------------------------------------------------------
+
+CConsoleBase* CTEngine::Console() const
+{
+return (iConsole);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Write(const TDesC& aText)
+{    
+if (ConsoleEnabled()) 
+	iConsole->Write(aText);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Writeln( const TDesC& aText )
+{
+if (ConsoleEnabled())
+	{
+	iConsole->Write(aText);
+	iConsole->Write(TFR_KTxtNewLine);
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Writeln()
+{    
+if (ConsoleEnabled()) 
+	iConsole->Write(TFR_KTxtNewLine);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Printf( TRefByValue<const TDesC> aFmt, ... )
+{    
+VA_LIST list;
+VA_START( list, aFmt );
+Printf( aFmt, list ); 
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Printf( TRefByValue<const TDesC> aFmt, VA_LIST& aList )
+{
+if ( ConsoleEnabled() )
+	{
+	iPrintBuf.Zero();
+	TRAPD(error,iPrintBuf.AppendFormatList( aFmt, aList, &iOverflow));
+	if ( error == KErrNone )
+		{
+		iConsole->Write( iPrintBuf );
+		}
+	else
+		{
+		iConsole->Write( TFR_KTxtErrPrintOflo );
+		iConsole->Write( TFR_KTxtNewLine );
+		}
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Printfln( TRefByValue<const TDesC> aFmt, ... )
+{    
+VA_LIST list;
+VA_START( list, aFmt );
+Printfln( aFmt, list );
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Printfln( TRefByValue<const TDesC> aFmt, VA_LIST& aList )
+{
+if ( ConsoleEnabled( ) )
+	{
+	iPrintBuf.Zero();
+	TInt error = KErrNone;
+	TRAP(error,iPrintBuf.AppendFormatList( aFmt, aList, &iOverflow));
+	if ( error != KErrNone ) 
+		return;
+	TRAP(error,iPrintBuf.AppendFormat( _L("%S"), &iOverflow, &TFR_KTxtNewLine ));
+	if (error == KErrNone )
+		{
+		iConsole->Write( iPrintBuf );
+		}
+	else
+		{
+		iConsole->Write( TFR_KTxtErrPrintOflo );
+		iConsole->Write( TFR_KTxtNewLine );
+		}
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Pause(const TDesC& aPrompt)
+{
+if (ConsoleEnabled())
+	{
+	iCmdline.Zero();
+	iConsole->Write(aPrompt);
+	if (!IsActive())
+		SetActive();
+	iConsoleReader->ReadChar(iCmdline, iStatus);
+	}
+else
+	CompleteRequest();
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::Hold(TTimeIntervalMicroSeconds32 aInterval)
+{
+iTimer.After(iStatus, aInterval);
+SetActive();
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::SetCmdPath( const TDesC& aPath )
+{
+if (aPath.Length() == 0)
+	{
+	Printf(_L("Path is set to: %S\r\n"), &iCmdPath);
+	return KErrNone;
+	}
+
+if (iParse.SetNoWild( aPath, NULL, NULL ) != KErrNone)
+	return KErrArgument;
+
+if (!iParse.PathPresent() || iParse.NameOrExtPresent())
+	return KErrArgument;
+
+//	set it
+iCmdPath.Copy(aPath);
+
+//	echo it
+Printf(_L("Path is set to: %S\r\n"), &iCmdPath);
+
+return KErrNone;
+}
+
+//-----------------------------------------------------------------------------
+
+TPtrC CTEngine::CmdPath() const
+{
+TPtrC path(iCmdPath);
+return path;
+}
+
+//-----------------------------------------------------------------------------
+
+TPtrC CTEngine::FileName() const
+{
+TPtrC fileName(iFileName);
+return fileName;
+}
+
+//-----------------------------------------------------------------------------
+//	parameterless version
+
+TInt CTEngine::CallCmdFile(const TDesC& aFile)
+{
+return CallCmdFile(aFile, _L(""));
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::CallCmdFile(const TDesC &aFile, const TDesC &aArgs)
+{
+// Make CCmdFile object.
+CCmdFile *file = NULL;
+TRAPD(error, file = CCmdFile::NewL());
+if ( error != KErrNone ) 
+	return error;
+
+error = file->Open(iCmdPath, aFile);
+if ( error != KErrNone )
+	{
+	delete file;
+
+	//	print file x not found echo it
+	Printf(_L("Error: file [%S] not found\r\n"), &aFile);
+	Printf(_L("       Check file path <%S>\r\n"), &iCmdPath);
+	return error;
+	}
+
+// Save file name and arguments.
+TRAP(error, file->AddArgsL(aFile));
+if (error == KErrNone) 
+	TRAP(error, file->AddArgsL(aArgs));
+
+if ( error != KErrNone )
+	{
+	delete file;
+	return error;
+	}
+
+// Check that not too many call arguments.
+if ( file->Argc() > (TFR_MAX_CALL_ARGUMENTS + 1))
+	{
+	delete file;
+	return error = KErrArgument;
+	}
+
+// Push present command file to cmdfile pile.
+TRAP(error, iCmdPile->PushL( iCmdFile ));
+if ( error != KErrNone )
+	{
+	delete file;
+	return error;
+	}
+
+// Switch context to the called command file.
+iCmdFile = file;
+file = NULL;
+TRAP(error, SetContextL(iDefines, iCmdFile));
+return error;
+}
+
+//-----------------------------------------------------------------------------
+
+CCmdFile* CTEngine::CmdFile()
+{
+return iCmdFile;
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::CloseCmdFile()
+{
+// Get rid of the present command file (NULL iCmdFile is Ok).
+delete iCmdFile;
+iCmdFile = NULL;
+
+// Pop the previous one from the pile (returns NULL if none).
+iCmdFile = iCmdPile->Pop();
+
+// Switch context to that file (NULL iCmdFile does no harm).
+TRAPD(error,SetContextL(iDefines,iCmdFile));
+return error;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::CloseCmdFiles()
+{
+// Pop and delete all previous command files from the file pile.
+iCmdPile->Empty();
+
+// Get rid of the present file as well (NULL iCmdFile is Ok).
+delete iCmdFile;
+iCmdFile = NULL;
+
+// Switch context to "no command file" (since iCmdFile = NULL).
+TRAP_IGNORE(SetContextL(iDefines,iCmdFile)); // doesn't LEAVE, see yourself
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::SetLogPath( const TDesC& aPath )
+{
+if (aPath.Length() == 0)
+	{
+	iLogPath.Zero();
+	return KErrNone;
+	}
+
+if (iParse.SetNoWild( aPath, NULL, NULL ) != KErrNone)
+	return KErrArgument;
+
+if (!iParse.PathPresent() || iParse.NameOrExtPresent())
+	return KErrArgument;
+
+TInt error;
+RFs fs;
+if (error = fs.Connect(), error == KErrNone)
+	{
+	error = fs.MkDirAll( iParse.DriveAndPath());
+	if (error == KErrAlreadyExists) 
+		error = KErrNone;
+
+	fs.Close();
+	if (error == KErrNone) 
+		iLogPath.Copy(aPath);
+	}
+return error;
+}
+
+//-----------------------------------------------------------------------------
+
+TPtrC CTEngine::LogPath() const
+{
+TPtrC logpath(iLogPath);
+return logpath;
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::OpenLogFile(const TDesC& aFile)
+{
+// Construct a full log file.
+TInt error = iParse.Set(aFile, NULL, &iLogPath);
+if (error != KErrNone) 
+	return error;
+
+// Construct and open the new log file.
+CLogFile* file = NULL;
+TRAP(error, file = CLogFile::NewL());
+if ( error != KErrNone ) 
+	return error;
+
+error = file->Open( iParse.FullName() );
+if ( error == KErrNone && iLogFile != NULL )
+	{
+	// Close and save the present log file.
+	iLogFile->Close();
+	TRAP(error, iLogPile->PushL(iLogFile));
+	if ( error == KErrNone ) 
+		iLogFile = NULL;
+	}
+
+if (error == KErrNone)
+	{
+	// Switch the log file.
+	file->PrintHeading();
+	iLogFile = file;
+	file = NULL;
+	}
+
+delete file; // is NULL if no errors!
+return error;
+}
+
+//-----------------------------------------------------------------------------
+
+CLogFile *CTEngine::LogFile()
+{
+return iLogFile;
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::CloseLogFile( )
+{
+delete iLogFile;
+iLogFile = NULL;
+iLogFile = iLogPile->Pop();
+TInt error = KErrNone;
+if ( iLogFile != NULL )
+	error = iLogFile->Open();
+return error;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::CloseLogFiles()
+{
+TInt count = iLogPile->Count();
+while (count > 0 )
+	{
+	CLogFile* file = iLogPile->Pop();
+	delete file; // NULL does no harm!
+	}
+
+delete iLogFile;
+iLogFile = NULL;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogWrite( const TDesC& aText )
+{
+if ( iLogFile != NULL ) 
+	iLogFile->Write( aText );
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogWriteln( const TDesC& aText )
+{
+if ( iLogFile != NULL ) 
+	iLogFile->Writeln( aText );
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogWriteln()
+{
+if ( iLogFile != NULL ) 
+	iLogFile->Writeln();
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogPrintf( TRefByValue<const TDesC> aFmt, ... )
+{
+VA_LIST list;
+VA_START(list, aFmt);
+LogPrintf(aFmt, list);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogPrintf( TRefByValue<const TDesC> aFmt, VA_LIST& aList )
+{
+if (iLogFile != NULL) 
+	iLogFile->Printf(aFmt, aList);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogPrintfln( TRefByValue<const TDesC> aFmt, ... )
+{
+VA_LIST list;
+VA_START(list, aFmt);
+LogPrintfln(aFmt, list);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::LogPrintfln( TRefByValue<const TDesC> aFmt, VA_LIST& aList )
+{
+if (iLogFile != NULL)
+	{
+	iLogFile->Printf(aFmt, aList);
+	iLogFile->Writeln();
+	}
+}
+
+//-----------------------------------------------------------------------------
+//    Standard message output:
+//    - CTEngine::MsgWrite
+//    - CTEngine::MsgWriteln
+//    - CTEngine::MsgWriteln
+//    - CTEngine::MsgPrintf
+//    - CTEngine::MsgPrintf
+//    - CTEngine::MsgPrintfln
+//    - CTEngine::MsgPrintfln
+//
+//	A message goes to the log if there is one open. The message is printed
+//	to the display as well, except when having echo mode off and running a
+//	command file.
+//
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgWrite(const TDesC& aText)
+{
+LogWrite(aText);
+if (EchoMode() || (iCmdFile == NULL)) 
+	Write(aText);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgWriteln(const TDesC& aText)
+{
+LogWriteln(aText);
+if (EchoMode() || (iCmdFile == NULL)) 
+	Writeln(aText);
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgWriteln()
+{
+LogWriteln();
+if (EchoMode() || (iCmdFile == NULL)) 
+	Writeln();
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgPrintf( TRefByValue<const TDesC> aFmt, ... )
+{
+VA_LIST list;
+VA_START( list, aFmt  );
+MsgPrintf( aFmt, list );
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgPrintf( TRefByValue<const TDesC> aFmt, VA_LIST& aList )
+{
+if ( EchoMode() || (iCmdFile == NULL) ) 
+	{
+	VA_LIST clone;
+	Mem::Move( &clone, &aList, sizeof(VA_LIST) );
+	LogPrintf( aFmt, aList );
+	Printf( aFmt, clone );
+	}
+else
+	{
+	LogPrintf( aFmt, aList );
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgPrintfln( TRefByValue<const TDesC> aFmt, ... )
+{
+VA_LIST list;
+VA_START( list, aFmt );
+MsgPrintfln( aFmt, list );
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::MsgPrintfln( TRefByValue<const TDesC> aFmt, VA_LIST& aList )
+{
+if ( EchoMode() || (iCmdFile == NULL) ) 
+	{
+	VA_LIST clone;
+	Mem::Move( &clone, &aList, sizeof(VA_LIST) );
+	LogPrintfln( aFmt, aList );
+	Printfln( aFmt, clone );
+	}
+else
+	LogPrintfln(aFmt, aList);
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::SetPrompt(const TDesC& aPrompt)
+{
+// Return error in case a too long prompt was proposed.
+if (aPrompt.Length() > iPrompt.MaxLength()) 
+	return KErrTooBig;
+
+// Otherwise alter trhe prompt and return Ok.
+iPrompt.Copy(aPrompt);
+return KErrNone;
+}
+
+//-----------------------------------------------------------------------------
+
+TPtrC CTEngine::Prompt() const
+{
+TPtrC prompt(iPrompt);
+return prompt;
+}
+
+//-----------------------------------------------------------------------------
+//	Run
+//	Start things off! We have a variety of options: 
+//	1.	interactive. (no params) => Call Run()
+//	2.	semi-interactive. (some params, no script) => Call Run(Args)
+//	3.  automatic. (some params & script) => Run(Script, Args)
+
+void CTEngine::Run()
+{
+if (!IsActive())
+	{
+	// Start the engine and set the state to get the next cmd
+	iStopped   = EFalse;
+	iState = EGetNextCmd;
+
+	// Complete request
+	CompleteRequest();
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::Run(const TDesC& aFile)
+{
+return Run(aFile, _L(""));
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::Run(const TDesC& aFile, const TDesC& aArgs)
+{
+iStopped = EFalse;
+
+// Open (call) the command file. Stop test engine if fails.
+TInt error = CallCmdFile(aFile, aArgs);
+if (error != KErrNone) 
+	StopEngine();
+
+// Keep going until stopped or reading the commands fails.
+while ((!iStopped) && (error == KErrNone))
+	{
+	error = ReadCmdline(EFalse);
+	if (error == KErrNone)
+		{
+		if (MakeCommand() == KErrNone)
+			{
+			TRAP(error,(void) ObeyCommandL()); 
+			}
+		}
+	}
+
+// Make sure that command files and log files get closed and return.
+CloseCmdFiles();
+CloseLogFiles();
+return error;
+}
+
+//-----------------------------------------------------------------------------
+//	CTEngine::Terminate
+//
+//	Terminate processing of command files. If not inside a command file,
+//	then does not do anything - doesn't even close the opened log files.
+
+void  CTEngine::Terminate()
+{
+// Inside command file?
+if (iCmdFile != NULL)
+	{
+
+	// Close all command files.
+	CloseCmdFiles();
+
+	// Close all log files. Write the "run aborted" message to the end
+	// of every log file.
+	while (iLogPile->Count() > 0)
+		{
+		// There is yet at least one log file in pile: write the abort
+		// message and close => previous file in pile will be opened.
+		LogWriteln( TFR_KTxtMsgRunAborted );
+		(void)CloseLogFile();
+		}
+
+	// Close the very last log file too. Having iLogFile = NULL is not
+	// checkd in here because that doesn't do any harm.
+	LogWriteln( TFR_KTxtMsgRunAborted );
+	delete iLogFile;
+	iLogFile = NULL;
+
+	// Print abort message to console too.
+	Writeln( TFR_KTxtMsgRunAborted );
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::StopEngine( )
+{
+iStopped = ETrue;
+CloseCmdFiles();
+
+// Print message to console
+Writeln(TFR_KTxtMsgRunStopped);
+}
+
+//-----------------------------------------------------------------------------
+
+TBool CTEngine::Stopped()
+{
+return iStopped;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::SetEchoMode(const TBool &aBoolean)
+{
+iEchoMode = aBoolean;
+}
+
+//-----------------------------------------------------------------------------
+
+TBool CTEngine::EchoMode()
+{
+return iEchoMode;
+}
+
+//-----------------------------------------------------------------------------
+
+#if !defined(TEMPLATED_CATALOGUE)
+CCatalogue *CTEngine::Defines()
+#else
+CCatalogue<CLabeledText> *CTEngine::Defines()
+#endif
+{
+return iDefines;
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::ReadCmdline(TBool aConsole)
+{
+
+// Reset cmd.
+iCmdline.Zero();
+
+TInt error = KErrNone;
+if (iCmdFile != NULL)
+	error = ReadCmdFile();
+
+else
+	// Set error to imply that the end of the cmd file has been reached
+	error = KErrEof;
+
+if ((error == KErrEof) && aConsole )
+	// Get the next cmd line from the console
+	error = ReadConsole();
+
+return error;
+}
+
+//-----------------------------------------------------------------------------
+//	Read command line (iCmdline) from command files.
+
+TInt CTEngine::ReadCmdFile()
+{
+
+// Reset cmd and read from the command files. Close files if at end.
+iCmdline.Zero();
+TInt error = KErrEof;
+while ((iCmdFile != NULL) && (error == KErrEof))
+	{
+	error = iCmdFile->Read(iCmdline);
+	if (error == KErrEof)
+		{
+		error = CloseCmdFile();
+		if (error == KErrNone) 
+			error = KErrEof;
+		}
+	else
+		CompleteRequest();
+
+	}
+
+return error;
+}
+
+//-----------------------------------------------------------------------------
+//	Read command line (iCmdline) from console.
+
+TInt CTEngine::ReadConsole()
+{
+// Get cmd from console - first write prompt.
+iConsole->Write(iPrompt);
+iConsoleReader->ReadLine(iCmdline, iStatus);
+SetActive();
+
+return KErrNone;
+}
+
+//-----------------------------------------------------------------------------
+
+TPtrC CTEngine::GetDefine(const TDesC &aTag) const
+{
+TPtrC iVal;
+TInt len = aTag.Length();
+
+for (TInt i = 0; i < iDefines->Count(); ++i)
+	{
+	CLabeledText *tag = iDefines->At(i);
+	TInt pos = tag->Label().Find(aTag);
+	//make sure that 'xyz' does not match with '$xyz_abcd$' 
+	if ( (pos == 1) && (tag->Label().Length() == len+2) )
+		{
+		iVal.Set(tag->Value());
+		break;
+		}
+	}
+
+return iVal;
+}
+
+//-----------------------------------------------------------------------------
+//	Make the command (iCommand) to obey. Copies the command line (iCmdline)
+//	to the iCommand buffer and expands the tags to their defined values. If
+//	fails, prints out the original command line and an error message.
+
+TInt CTEngine::MakeCommand()
+{
+TInt error = KErrNone;
+
+// Copy command line from iCmdline buffer to iCommand buffer.
+iCommand.Copy(iCmdline);
+
+// Expand tags = replace tag markers with their defined values.
+TInt  counter = 0;
+TBool proceed = ETrue;
+while (proceed && (error == KErrNone))
+	{
+	// One round = replace all tag labels with their values and
+	// alter the proceed to ETrue in replaced one or more tags.
+	proceed = EFalse;
+	for (TInt i = 0; i < iDefines->Count(); ++i)
+		{
+		CLabeledText *tag = iDefines->At(i);
+		TInt pos = iCommand.Find(tag->Label());
+		if (pos >= 0)
+			{
+
+			// More than a hundred replacements as the whole is
+			// propably due to an infinite loop ( recursive tag
+			// definitions ): 
+			if (counter > 99)
+				{
+				// Propably recursive tag definitions.
+				MsgWriteln(TfrLex::Trim(iCmdline));
+				MsgWriteln(TFR_KTxtErrRecursiveTags);
+				error = KErrOverflow;
+				break;
+				}
+
+			// Check that this very tag replacement won't cause
+			// overflow in command buffer.
+			TInt newlength = iCommand.Length() - tag->Label().Length();
+			newlength += tag->Value().Length();
+			if (newlength > iCommand.MaxLength())
+				{
+				// Command has grown too big in size.
+				MsgWriteln(TfrLex::Trim( iCmdline));
+				MsgWriteln(TFR_KTxtErrTooLongCmd);
+				error = KErrOverflow;
+				break;
+				}
+
+			// Fine, replace the tag with its defined value and
+			// mark that there shall be at least one more round.
+			proceed = ETrue;
+			iCommand.Replace(pos, tag->Label().Length(), tag->Value());
+			++counter; // keep up total count of replacements.
+			}
+		} // end-for
+	} // end-while
+
+// Return if everything went fine.
+if ( error == KErrNone ) 
+	return error;
+
+// Otherwise terminate command files, unless when in check mode.
+if ( (iCmdFamily == NULL) || !iCmdFamily->Switch(CCmdFamily::EParseOnly) )
+	Terminate();
+
+return error;
+}
+
+//-----------------------------------------------------------------------------
+
+TInt CTEngine::ObeyCommandL()
+{
+TInt error = KErrNone;
+
+// The command is handled without the leading/trailing spaces.
+TPtrC cmd = TfrLex::Trim(iCommand);
+
+// The command shall be echoed if echo mode is On and command
+// was read from a command file. 
+TBool doEcho = (iEchoMode && (iCmdFile != NULL));
+
+// Check if command begins with @ character and remove if yes.
+// That kind of commands aren't echoed afterall.
+if (cmd.Match(_L("@*")) == 0)
+	{
+	// Command is not echoed afterall.
+	doEcho = EFalse;
+
+	// Remove @ and them trim once more.
+	cmd.Set(cmd.Ptr()+1, cmd.Length()-1);
+	cmd.Set(TfrLex::TrimLeft(cmd));
+	}
+
+//	Look up from Command Family if there's a registered command to
+//	handle this very command string. If there is no Command Family
+//	then there is no handler either.
+//	bear in mind that we have to possibly skip a valid command if
+//	our if mode directs us... 
+CCmdBase *handler = NULL; 
+if (iCmdFamily != NULL) 
+	handler = iCmdFamily->Recognize(cmd);
+
+if (handler != NULL)
+	{
+	TBool stepover = DetermineStepover(handler);
+
+	if (!stepover)
+		{
+		// This one shall be processed.
+		// ----------------------------
+		// Echo the original input command to the display.
+
+		//	log command and display the command on the screen if appropriate
+		if (iShowCmdLine)
+			MsgWriteln(iCmdline);	
+		else if (doEcho) 
+			Writeln(TfrLex::TrimRight(iCommand));
+
+		//	Write into the log unless that has been prevented.
+		//	and then process the command.
+		error = handler->ProcessL(cmd);
+		}
+	else
+		// This one shall not be processed.
+		// --------------------------------
+		// Command it is not written to log nor echoed either.
+		{
+		error = handler->ProcessStepOverL();
+		}
+
+	}
+else
+	{
+	// There was no handler for this command i.e. it's an unknown
+	// command and we don't known what to do with it. However, if
+	// the processing is in step over mode odds commands are here
+	// silently ignored (not echoed either).
+
+	if (iCmdFamily->StepOver())
+		// Step over mode: ignore odd command silently.
+		error = KErrNone;
+
+	else
+		{
+		// Otherwise, echo the original input command to display
+		// and log an error message.
+		if (doEcho) 
+			Writeln(TfrLex::TrimRight(iCommand));
+		LogWriteln(cmd);
+		MsgWriteln(TFR_KTxtErrUnknownCmd);
+		error = KErrNotFound;
+		}
+	}
+
+//	if the last command was a 'domain' command store the result (deano requirement)
+//	unless the last command was IF!
+if (handler == NULL || (handler->CommandId() < THA_KCmdMaxStandard))
+	;//	do nothing
+else
+	SetErrorDefine(error);
+
+//	As we are recording the value of the return, it is no longer necessary 
+//	to abort here - let the 'script' worry about subsequent action if required
+
+// Return if successful.
+//if (error == KErrNone) 
+//	return error;
+// Error/failure: terminate command files, unless when check mode.
+//if ((iCmdFamily == NULL) || !iCmdFamily->Switch(CCmdFamily::EParseOnly))
+  //Terminate();
+
+return error;
+}
+
+
+//-----------------------------------------------------------------------------
+//	Assign the passed value to the last result define
+
+TBool CTEngine::DetermineStepover(CCmdBase *aHandler)
+{
+//	Handler was found: check if the command is to be processed
+//	and if the command is among those to write into the log.
+//	dont forget to check the if, else, endif situation
+//	first - incase the if mode needs changing
+TBool iSOver = aHandler->StepOver();
+
+//	we must be aware of the problem of nested loops
+//	we must 'count' and 'match' the intervening if/else/endif's
+//	until we get back to our current level
+//
+//	to do this, we need to know what command is being executed
+//	and use that and the current state to work out where we are.
+//	At this point we have not set the ifstate so we can predetermine
+//	the next move.
+//
+//	NOTE: If we encounter if's we must process them (if they are part
+//				of the correct branch!
+
+CIFControl::TIFMode eIFMode = GetIfMode();
+CIFControl::TIFProcessing eIFState = GetIfState();
+
+//	iBranch merely tells us if the current clause return true/false
+//	not which branch is being executed (thats from eIFState)
+TBool iBranch = (iIFPile->Peek()) ? (iIFPile->Peek())->GetIFResult() : EFalse;
+TInt iCmd = aHandler->CommandId();
+TBool iInSubClause = EFalse;
+switch (iCmd)
+	{
+	case THA_KCmdIf : 
+		
+		//	we've encountered an IF statement, which should be processed ONLY
+		//	if we're in the correct branch of a current IF
+		//	if the if is FALSE we still need to count the internal IFs/ELSE/ENDIFs as normal
+		switch (eIFState)
+			{
+			//	we are in the middle of an if,else,endif block note: the logic here is tortuous!
+			//	iIfState is true if the IF was true
+			case CIFControl::EInIF : 
+				
+				//	process the IF if we're in the correct (true) clause this will start 
+				//	another IF object (unless it's false)
+				iSOver = (eIFMode == CIFControl::EELSETrue);
+				if (iSOver)
+					//	we now have to count the else's and endifs as we're not processing the IF!
+					{
+					if (iIFPile->Peek())
+						(iIFPile->Peek())->If();
+					}
+				break;
+
+			case CIFControl::EInELSE : 
+
+				iSOver = (eIFMode == CIFControl::EIFTrue); 
+				if (iSOver)
+					{
+					if (iIFPile->Peek())
+						(iIFPile->Peek())->Else();
+					}
+				break;
+			
+			//	must be a 'virgin' IF so ensure we call it!
+			default : iSOver = EFalse; break;
+			}			
+		break;	
+
+	case THA_KCmdElse :
+
+		//	we're already in an IF or ELSE so merely continue as 'normal'
+		switch (eIFState)
+			{
+			//	We should execute the ELSE as this sets up the state var but not the subsequent
+			//	commands as necessary. We are in the middle of an if,else,endif block 
+			//	note: the logic here is tortuous! iIfState is true if the IF was true (i.e.
+			case CIFControl::EInIF : 
+				if (iIFPile->Peek())
+					//	we need to ensure we're accounting for outer IF's etc
+					//	we need to ensure we process it correctly
+					iInSubClause = ((iIFPile->Peek())->GetIfCount() > 0) ? ETrue : EFalse;
+
+				if (iInSubClause)
+					iSOver = iInSubClause;
+				else
+					//	if the subclause is subject to fail then we should ignore this completely
+					//iSOver = (eIFMode == CIFControl::EELSETrue) ? ETrue : EFalse;
+					//	if the subclause is subject to fail then we should ignore this completely
+					//	unless we are supposed to execute it...
+					if (iBranch)
+						iSOver = (eIFMode == CIFControl::EELSETrue) ? ETrue : EFalse;
+					else	
+						iSOver = (eIFMode == CIFControl::EELSETrue) ? EFalse : ETrue;
+
+				if (iSOver)
+					{
+					if (iIFPile->Peek())
+						(iIFPile->Peek())->Else();
+					}
+				break;
+
+			case CIFControl::EInELSE : 
+				if (iIFPile->Peek())
+					//	we need to ensure we're accounting for outer IF's etc
+					//	we need to ensure we process it correctly
+					iInSubClause = ((iIFPile->Peek())->GetIfCount() > 0) ? ETrue : EFalse;
+
+				if (iInSubClause)
+					iSOver = iInSubClause;
+				else
+					//	if the subclause is subject to fail then we should ignore this completely
+					//	unless we are supposed to execute it...
+					if (iBranch)
+						iSOver = (eIFMode == CIFControl::EELSETrue) ? ETrue : EFalse;
+					else	
+						iSOver = (eIFMode == CIFControl::EELSETrue) ? EFalse : ETrue;
+
+				if (iSOver)
+					{
+					if (iIFPile->Peek())
+						(iIFPile->Peek())->Else();
+					}
+				break;
+
+			default : 
+				//	accept current iSOver state but if we're in the non-executing
+				//	branch of current clause, increment the else count and ensure we 
+				//	skip the command
+				if (!iBranch)
+					{
+					if (iIFPile->Peek())
+						(iIFPile->Peek())->Else();
+					iSOver = true;
+					}
+				break;
+			}
+		break;
+
+	//	ok, here's where the real 'meat' of the situation
+	case THA_KCmdEndIf : 
+		{
+		
+		//	we MUST be in an IF sequence, but we also need to be aware
+		//	of the state of any outer IF clause 
+		if (iIFPile->Peek())
+			{
+			//	before we decrement our counters, we need to see the state of play
+			//	if we're in an IF which is part of an untrue IF clause *see if test9/10*
+			//	we need to ensure we process it correctly
+			TInt iIfs = (iIFPile->Peek())->GetIfCount();
+			//TInt iElses = (iIFPile->Peek())->GetElseCount();
+			iInSubClause = (iIfs == 0) ? EFalse : ETrue;
+			//iInSubClause = ( (iIfs == 0) && (iElses == 0) ) ? EFalse : ETrue;
+
+			//	decrement our counters. If we are NOT in a SubClause then these will
+			//	be zero. If so we SHOULD execute the ENDIF
+			(iIFPile->Peek())->EndIf();
+			}
+
+		switch (eIFState)
+			{
+			//	we are in the middle of an if,else,endif block
+			//	note: the logic here is tortuous!
+			//	iIfState is true if the IF was true (i.e.
+			//iSOver = iIfState; break;
+			case CIFControl::EInIF : 
+				iSOver = (iSOver || (eIFMode == CIFControl::EELSETrue)) && iInSubClause; 
+				break;
+			case CIFControl::EInELSE : 
+				iSOver = (iSOver || (eIFMode == CIFControl::EIFTrue)) && iInSubClause; 
+				break;
+			default : 
+				if (iInSubClause)
+					iSOver = ETrue;
+				break;
+			}
+		break;
+		}
+				
+	//	other commands must be checked against our if state!
+	default : 
+		switch (eIFState)
+			{
+			case CIFControl::EInIF :
+				switch (eIFMode)
+					{
+					case CIFControl::EIFTrue : iSOver = EFalse; break;
+					case CIFControl::EELSETrue : iSOver = ETrue; break;
+					default : iSOver = ETrue; break;	//	?????
+					}
+				break;
+
+			case CIFControl::EInELSE :
+				switch (eIFMode)
+					{
+					case CIFControl::EIFTrue : iSOver = ETrue; break;
+					case CIFControl::EELSETrue : iSOver = EFalse; break;
+					default : iSOver = ETrue; break;	//	?????
+					//case CIFControl::EENDIF : iSOver = !iBranch; break;
+					}
+				break;
+
+			default : 
+				switch (eIFMode)
+					{
+					case CIFControl::EIFTrue : iSOver = ETrue; break;
+					case CIFControl::EELSETrue : iSOver = EFalse; break;
+					default : iSOver = EFalse; break;	//	?????
+					//case CIFControl::EENDIF : iSOver = ETrue; break;
+					}
+			break;
+			}
+		break;
+	}
+
+return iSOver;
+}
+
+//-----------------------------------------------------------------------------
+//	Assign the passed value to the last result define
+
+void CTEngine::SetResultDefine(TInt aValue)
+	{
+	TInt error;
+
+	//	so that we can process it if required - code stolen from CmdDefine...
+	TBuf<16+2> taglabel;
+	taglabel.Format(KLastResultCode);
+
+	// Set tag value to be the last error code received
+	TBuf<12> tagvalue;
+	tagvalue.Format(_L("%d"), aValue);
+	CLabeledText *tag = Defines()->Text(taglabel);
+	if (tag != NULL)
+		{
+		//	alter tag
+		TRAP(error, tag->SetL(tagvalue));
+		}
+	else
+		{
+		//	Add a tag.
+		TRAP(error, Defines()->AddL(taglabel, tagvalue));
+		}
+	}
+
+void CTEngine::SetResultDefine (const TDesC& aDefineTxt, TInt aValue)
+	{
+	TInt error;
+
+	TBuf<32+2> taglabel;
+
+	taglabel.Format(_L("$%SHttpStatus$"), &aDefineTxt);
+
+	// Set tag value to be the last error code received
+	TBuf<16> tagvalue;
+	tagvalue.Format(_L("%d"), aValue);
+	CLabeledText *tag = Defines()->Text(taglabel);
+
+	if (tag != NULL)
+		{
+		TRAP(error, tag->SetL(tagvalue));
+		}
+	else
+		{
+		//	Add a tag.
+		TRAP(error, Defines()->AddL(taglabel, tagvalue));
+		}
+	}
+
+void CTEngine::DeleteResultDefine (const TDesC& aDefineTxt)
+	{
+	TBuf<32+2> taglabel;
+
+	taglabel.Format(_L("$%SHttpStatus$"), &aDefineTxt);
+
+	Defines()->Delete(taglabel);
+	}
+
+//-----------------------------------------------------------------------------
+//	Assign the passed value to the last result define
+
+void CTEngine::SetErrorDefine(TInt aValue)
+	{
+	TInt error;
+
+	//	so that we can process it if required - code stolen from CmdDefine...
+	TBuf<16+2> taglabel;
+	taglabel.Format(KLastErrorCode);
+
+	// Set tag value to be the last error code received
+	TBuf<12> tagvalue;
+	tagvalue.Format(_L("%d"), aValue);
+	CLabeledText *tag = Defines()->Text(taglabel);
+	if (tag != NULL)
+		{
+		//	alter tag
+		TRAP(error, tag->SetL(tagvalue));
+		}
+	else
+		{
+		//	Add a tag.
+		TRAP(error, Defines()->AddL(taglabel, tagvalue));
+		}
+	}
+
+void CTEngine::SetErrorDefine (const TDesC& aDefineTxt, TInt aValue)
+	{
+	TInt error;
+
+	TBuf<32+2> taglabel;
+
+	taglabel.Format(_L("$%SLastEvent$"), &aDefineTxt);
+
+	// Set tag value to be the last error code received
+	TBuf<16> tagvalue;
+	tagvalue.Format(_L("%d"), aValue);
+	CLabeledText *tag = Defines()->Text(taglabel);
+
+	if (tag != NULL)
+		{
+		TRAP(error, tag->SetL(tagvalue));
+		}
+	else
+		{
+		//	Add a tag.
+		TRAP(error, Defines()->AddL(taglabel, tagvalue));
+		}
+	}
+
+void CTEngine::DeleteErrorDefine (const TDesC& aDefineTxt)
+	{
+	TBuf<32+2> taglabel;
+
+	taglabel.Format(_L("$%SLastEvent$"), &aDefineTxt);
+
+	Defines()->Delete(taglabel);
+	}
+
+//-----------------------------------------------------------------------------
+//	Called by the scheduler evert time request completed.
+
+void CTEngine::RunL()
+{
+switch (iState)
+	{
+	case EIdle:
+		if (iStopped)
+			// We've finished - close resources...
+			{
+			CloseCmdFiles();
+			CloseLogFiles();
+
+			// Cancel...
+			Cancel();
+
+			//	Stop the active scheduler only if we're driven via commandline script.
+			//	if via interactive then has no meaning!
+			//if (Console != NULL)
+			CActiveScheduler::Stop();
+			}
+		break;
+
+	case EStopping:
+		{
+		// Close any open sessions and their transactions
+		if ( iCmdFamily != NULL )
+			{
+			//	Perform any operational close/shutdown operations here
+			//CCmdBase *handler = NULL;
+			//handler = iCmdFamily->Command(EDoClose);
+			//STATIC_CAST(CCmdDoClose*, handler)->CloseAll();
+			}
+		iState = EIdle;
+		} 
+		CompleteRequest();
+		break;
+
+	case EGetNextCmd:
+		// Get the next cmd
+		if (ReadCmdline(iConsoleEnabled) != KErrNone)
+			{
+			// Something went wrong, so stop
+			iStopped = ETrue;
+			iState = EIdle;
+
+			// Complete self
+			CompleteRequest();
+			}
+		else
+			// Parse the next cmd once we get it
+			iState = EParseCurrentCmd;
+		break;
+
+	case EParseCurrentCmd:
+		// Run the parsed cmd or Could not parse the cmd line so get the next cmd
+		iState = (MakeCommand() == KErrNone) ? ERunCurrentCmd : EGetNextCmd;
+
+		// Complete self and set active
+		CompleteRequest();
+		break;
+
+	case ERunCurrentCmd:
+		{
+		TInt iErr = ObeyCommandL();
+
+		// Run the cmd - the cmd will complete the request 
+		if (iErr != KErrNone) 
+			{
+			//	if major problem then complete the request
+			if (!IsActive())
+				CompleteRequest();
+			else	//	command requested produced subsequent operational error (i.e. what we're looking for!)
+				{
+				//	assign the response to an accessible 'variable'
+				}
+			}
+
+		// Set state...
+		iState = (!iStopped) ? EGetNextCmd : EStopping;
+		}
+		
+		break;
+	
+	default : break;
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::DoCancel()
+{
+iTimer.Cancel();
+iConsoleReader->ReadCancel();
+}
+
+//-----------------------------------------------------------------------------
+//	Standard Issue...
+
+void CTEngine::CompleteRequest()
+{
+if (IsActive())
+	return ;
+
+TRequestStatus* pStat = &iStatus;
+
+User::RequestComplete(pStat, KErrNone);
+SetActive();
+}
+
+//-----------------------------------------------------------------------------
+//	was 'GetAnEntry' but that is slightly inaccurate!
+
+void CTEngine::GetUserInput(const TDesC& ourPrompt, TDes& currentstring)
+{
+TBuf16<KMaxUserEntrySize> ourLine;
+TBuf<KMaxUserEntrySize> tempstring;	//tempstring is a unicode descriptor
+
+//	create a temporary buffer where the unicode strings are stored in order to 
+//	be displayed
+ourLine.Zero();
+tempstring.Copy(currentstring);		//Copy current string to Unicode buffer
+TKeyCode key = EKeyNull;						//current string buffer is 8 bits wide.
+
+//	Unicode string bufffer (tempstring) is 16 bits wide.
+FOREVER
+	{
+	if (ourLine.Length () == 0)
+		{
+
+		iConsole->SetPos (0, iConsole->WhereY ());
+		iConsole->Printf (_L ("%S"), &ourPrompt);
+		if (tempstring.Length () != 0)						//get tempstring's number of items
+			iConsole->Printf (_L (" = %S"), &tempstring);	//if not zero print them to iTest.Console()
+		iConsole->Printf (_L (" : "));
+		iConsole->ClearToEndOfLine ();
+		}
+
+	key = iConsole->Getch();
+
+	if (key == EKeyBackspace)
+		{
+		if (ourLine.Length() !=0)
+			{
+			ourLine.SetLength(ourLine.Length()-1);
+			iConsole->Printf(_L ("%c"), key);
+			iConsole->SetPos(iConsole->WhereX(), iConsole->WhereY());
+			iConsole->ClearToEndOfLine();
+			}	// end if (ourLine.Length() !=0)
+		}	// end if (key == KeyBackSpace)
+
+
+	if (key == EKeyDelete) 			
+		{
+		ourLine.Zero();
+		iConsole->SetPos(0, iConsole->WhereY());
+		iConsole->ClearToEndOfLine();
+		tempstring.Copy(ourLine);
+		break;
+		}
+
+	if (key == EKeyEnter)
+		break;
+
+	if (key < ' ') // ascii code thats not a printable character
+		continue;
+
+	ourLine.Append(key);
+	iConsole->Printf(_L ("%c"), key);
+	iConsole->SetPos(iConsole->WhereX(), iConsole->WhereY());
+	iConsole->ClearToEndOfLine();
+	if (ourLine.Length () == ourLine.MaxLength ())
+		break;
+	}	// end of for statement
+
+if ((key == EKeyEnter) && (ourLine.Length () == 0))
+	tempstring.Copy (currentstring);				//copy contents of 8 bit "ourLine" descriptor
+
+iConsole->SetPos(0, iConsole->WhereY());		
+iConsole->ClearToEndOfLine();
+
+if ((key == EKeyEnter) && (ourLine.Length() !=0))
+	tempstring.Copy(ourLine);
+
+if (tempstring.Length () != 0)						//if temstring length is not zero
+	{
+	iConsole->Printf(_L(" Entered = %S\n"), &tempstring);	//print the contents to iTest.Console()
+	LogPrintf(_L("%S = %S\n"), &ourPrompt, &tempstring);
+	}
+
+iConsole->Printf (_L("\n"));
+currentstring.Copy(tempstring);						//copy 16 bit tempstring descriptor back 
+} 
+
+//-----------------------------------------------------------------------------
+//	File Management and Support
+//	note: this takes the current 'path' as defined by PATH as the root file path 
+//	      if defined.
+
+TInt CTEngine::SetFileName(const TDesC &aName, 	RFile &aReqFile)
+	{
+	TBuf<256> ourFile(iCmdPath);
+	ourFile.Append(aName);
+
+	TParse ParsedFileName;
+	TInt iError = ParsedFileName.Set(ourFile, NULL, NULL); 
+
+	if (iError == KErrNone)
+		{//	check is a valid file and open a handle
+
+		//	assign the filename to our reference
+		TFileName fileName;
+		fileName.Copy(ParsedFileName.FullName());
+
+		if (iFileServer.IsValidName(fileName))
+			{
+			iError = aReqFile.Open(iFileServer, ParsedFileName.FullName(), EFileRead);
+			}
+		}
+		
+	return iError;
+	}
+
+//-----------------------------------------------------------------------------
+
+//-----------------------------------------------------------------------------
+//	Do a formatted dump of binary data, optionally logging it
+//	Iterate the supplied block of data in blocks of 16 bytes
+
+void CTEngine::DumpData(const TDesC8& aData, const TBool &logIt)
+{
+TInt pos = 0;
+TBuf<KMaxLogEntrySize> logLine;
+TBuf<KMaxLogEntrySize> anEntry;
+
+while (pos < aData.Length())
+	{
+	anEntry.Format(TRefByValue<const TDesC>_L("%04x : "), pos);
+	logLine.Append(anEntry);
+
+	// Hex output
+	TInt offset;
+	for (offset = 0; offset < 16; ++offset)
+		{
+		if (pos + offset < 10)//aData.Length())
+			{
+			TInt nextByte = aData[pos + offset];
+			anEntry.Format(TRefByValue<const TDesC>_L("%02x "), nextByte);
+			logLine.Append(anEntry);
+			}
+		else
+			{
+			anEntry.Format(TRefByValue<const TDesC>_L("   "));
+			logLine.Append(anEntry);
+			}
+		}
+	
+	anEntry.Format(TRefByValue<const TDesC>_L(": "));
+	logLine.Append(anEntry);
+
+	// Char output
+	for (offset = 0; offset < 16; ++offset)
+		{
+		if (pos + offset < 10)//aData.Length())
+			{
+			TInt nextByte = aData[pos + offset];
+			if ((nextByte >= 32) && (nextByte <= 127))
+				{
+				anEntry.Format(TRefByValue<const TDesC>_L("%c"), nextByte);
+				logLine.Append(anEntry);
+				}
+			else
+				{
+				anEntry.Format(TRefByValue<const TDesC>_L("."));
+				logLine.Append(anEntry);
+				}
+			}
+		else
+			{
+			anEntry.Format(TRefByValue<const TDesC>_L(" "));
+			logLine.Append(anEntry);
+			}
+		}
+
+	if (logIt)
+		LogPrintf(TRefByValue<const TDesC>_L("%S"), &logLine);
+	
+	// Advance to next 16 byte segment
+	pos += 16;
+	}
+}
+
+//-----------------------------------------------------------------------------
+
+CIFControl::TIFMode CTEngine::GetIfMode() 
+{
+return (iIFPile->Peek()) ? (iIFPile->Peek())->GetIFMode() : CIFControl::ENotIf;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::SetIfMode(const CIFControl::TIFMode &eMode) 
+{ 
+if (iIFPile->Peek())
+  (iIFPile->Peek())->SetIFMode(eMode); 
+}
+
+//-----------------------------------------------------------------------------
+
+CIFControl::TIFProcessing CTEngine::GetIfState() 
+{
+return (iIFPile->Peek()) ? (iIFPile->Peek())->GetIFState() : CIFControl::EIgnoreIF;
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::SetIfState(const CIFControl::TIFProcessing &eProc) 
+{
+if (iIFPile->Peek())
+  (iIFPile->Peek())->SetIFState(eProc); 
+}
+
+//-----------------------------------------------------------------------------
+//	Create new IF object to manage the current processing
+//	Use the EndIf to Pop the current object when ENDIF is processed
+
+void CTEngine::IfL(const CIFControl::TIFMode &eProc, 
+									const TBool &aResult, 
+									const CIFControl::TIFProcessing &aProcess) 
+{
+CIFControl *cif = CIFControl::NewLC(eProc, aResult, aProcess);
+
+iIFPile->PushL(cif);
+// CleanupStack::PopAndDestroy();
+CleanupStack::Pop();
+}
+
+//-----------------------------------------------------------------------------
+
+void CTEngine::EndIf() 
+{
+if (iIFPile->Peek())
+	iIFPile->Skim();
+}
+
+//-----------------------------------------------------------------------------
+//	End of File
+//-----------------------------------------------------------------------------