Files
mars-flaim/xflaim/util/flmunittest.cpp
ahodgkinson 12a621dc04 Changed license to LGPL.
git-svn-id: https://svn.code.sf.net/p/flaim/code/trunk@1010 0109f412-320b-0410-ab79-c3e0c5ffbbe6
2007-01-23 11:22:22 +00:00

2108 lines
43 KiB
C++

//------------------------------------------------------------------------------
// Desc: Unit test driver
// Tabs: 3
//
// Copyright (c) 2003-2007 Novell, Inc. All Rights Reserved.
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
// License as published by the Free Software Foundation; version 2.1
// of the License.
//
// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
// Library Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, contact Novell, Inc.
//
// To contact Novell about this file by physical or electronic mail,
// you may find current contact information at www.novell.com.
//
// $Id$
//------------------------------------------------------------------------------
#include "flmunittest.h"
#if defined( FLM_WIN)
#if defined( FLM_64BIT)
#define PLATPROC_STR "w64ia64"
#else
#define PLATPROC_STR "w32x86"
#endif
#elif defined( FLM_NLM)
#define PLATPROC_STR "nwx86"
#elif defined( FLM_LINUX)
#define PLATPROC_STR "lxx86"
#elif defined( FLM_OSX)
#define PLATPROC_STR "osx"
#elif defined( FLM_SOLARIS)
#define PLATPROC_STR "solaris"
#endif
FLMBOOL gv_bShutdown = FALSE;
extern RCODE getTest( IFlmTest ** ppTest);
#ifdef FLM_RING_ZERO_NLM
#define main nlm_main
#endif
struct TEST_INFO
{
bool bLog;
char pszLogfile[ 256];
bool bDisplay;
bool bVerboseDisplay;
char pszEnvironment[ 32];
char pszBuild[ 32];
char pszUser[ 32];
char pszConfig[ 256];
TEST_INFO * pNext;
TEST_INFO()
{
bLog = FALSE;
bDisplay = FALSE;
bVerboseDisplay = FALSE;
pNext = NULL;
pszLogfile[0] = '\0';
f_strcpy( pszEnvironment, PLATPROC_STR);
f_strcpy( pszBuild, __DATE__);
f_strcpy( pszUser, "defaultUser");
pszConfig [0] = 0;
}
};
/****************************************************************************
Desc:
****************************************************************************/
RCODE ITestReporter::init(
const char * configFile,
const char * buildNum,
const char * environment,
const char * userName)
{
RCODE rc = NE_XFLM_OK;
if( (rc = createUnitTest( configFile, buildNum, environment, userName,
&(this->m_uTD))) != 0)
{
goto Exit;
}
m_bInitialized = true;
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
ITestReporter::~ITestReporter()
{
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE ITestReporter::recordUnitTestResults(
const char * testName,
const char * testDescr,
const char * steps,
const char * status,
const char * resultDetails,
const char * elapsedTime)
{
return ::recordUnitTestResults( &(this->m_uTD), testName, testDescr,
steps, status, resultDetails, elapsedTime);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE IFlmTestLogger::init(
const char * pszFilename)
{
f_strcpy( m_szFilename, pszFilename);
m_bInitialized = TRUE;
return (NE_XFLM_OK);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE IFlmTestLogger::appendString(
const char * pszString)
{
RCODE rc = NE_XFLM_OK;
char * pszTemp = NULL;
if ( RC_BAD( rc = f_alloc( f_strlen( pszString) + 3, &pszTemp)))
{
goto Exit;
}
f_sprintf( pszTemp, "%s\n", pszString);
if ( RC_BAD( rc = f_filecat( m_szFilename, pszString)))
{
goto Exit;
}
Exit:
if ( pszTemp)
{
f_free( &pszTemp);
}
return rc;
}
/****************************************************************************
Desc:
****************************************************************************/
IFlmTestDisplayer::IFlmTestDisplayer()
{
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE IFlmTestDisplayer::init( void)
{
return( NE_XFLM_OK);
}
/****************************************************************************
Desc:
****************************************************************************/
void IFlmTestDisplayer::appendString(
const char * pszString)
{
f_printf( pszString);
}
/****************************************************************************
Desc:
****************************************************************************/
void printHelp()
{
f_printf( "\nCommand-line usage:");
f_printf( "\n\n[-l<log file>] [-d]");
f_printf( "[-c<config>] [-b<build>] [-u<user>]");
f_printf( "\n-l - Specifies a log file to print to");
f_printf( "\n-d - Display output");
f_printf( "\n-t - Specifies configuration file for reporting");
f_printf( "\n-b - Specifies the build number");
f_printf( "\n-u - Specifies the user running the unit test");
f_printf( "\n-h - Shows this screen");
}
/****************************************************************************
Desc:
****************************************************************************/
extern "C" int main(
int argc,
char ** argv)
{
RCODE rc = NE_XFLM_OK;
IFlmTest * pTest = NULL;
unsigned int i = 1;
ArgList args;
TEST_INFO testInfo;
//parse the command line
//format:
//[-l<log file>] [-d] [-c<config>] [-b<build>] [-u<user>]
/*
if ( argc < 2)
{
f_printf("You must specify at least one test to run");
printHelp();
goto Exit;
}
*/
if ( argc > 1)
{
if ( ( f_strcmp( argv[1], "--help") == 0)||
( f_strcmp( argv[1], "-h") == 0))
{
printHelp();
goto Exit;
}
}
args.expandArgs( argv, argc);
while( i < args.getNumEntries())
{
if ( args[i][0] != '-')
{
goto Exit;
}
if ( ( args[i][1] == 'l') || ( args[i][1] == 'L'))
{
testInfo.bLog = true;
f_strcpy( testInfo.pszLogfile, &args[i][2]);
}
else if ( ( args[i][1] == 'd') || ( args[i][1] == 'D'))
{
testInfo.bDisplay = true;
}
else if ( ( args[i][1] == 'c') || ( args[i][1] == 'C'))
{
//config file
f_strcpy( testInfo.pszConfig, &args[i][2]);
}
else if ( ( args[i][1] == 'b') || ( args[i][1] == 'B'))
{
//build
f_strcpy( testInfo.pszBuild, &args[i][2]);
}
else if ( ( args[i][1] == 'u') || ( args[i][1] == 'U'))
{
//user
f_strcpy( testInfo.pszUser, &args[i][2]);
}
else if ( ( args[i][1] == 'v') || ( args[i][1] == 'V'))
{
//verbose
testInfo.bVerboseDisplay = TRUE;
}
else
{
f_printf( "\nInvalid parameter");
printHelp();
goto Exit;
}
i++;
}
f_printf("Running %s\n", argv[0]);
if ( RC_BAD( rc = getTest( &pTest)))
{
f_printf( "ERROR: Unable to create test instance\n");
goto Exit;
}
if ( pTest->init(
testInfo.bLog,
testInfo.pszLogfile,
testInfo.bDisplay,
testInfo.bVerboseDisplay,
testInfo.pszConfig,
testInfo.pszEnvironment,
testInfo.pszBuild,
testInfo.pszUser) != 0)
{
f_printf( "\nTest initialization failed");
goto Exit;
}
if ( RC_BAD( rc = pTest->execute()))
{
// f_printf("\nTest Failed.");
goto Exit;
}
Exit:
if ( pTest)
{
pTest->Release();
}
return( (int)rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE KeyIterator::next()
{
RCODE rc = NE_XFLM_OK;
IF_DataVector * pTemp = NULL;
if ( m_bFirstCall)
{
if ( RC_BAD( rc = m_pDb->keyRetrieve(
m_uiIndex,
NULL,
XFLM_FIRST,
m_pFoundKey)))
{
goto Exit;
}
m_bFirstCall = FALSE;
}
else
{
pTemp = m_pSearchKey;
m_pSearchKey = m_pFoundKey;
m_pFoundKey = pTemp;
if ( RC_BAD( rc = m_pDb->keyRetrieve(
m_uiIndex,
m_pSearchKey,
XFLM_EXCL,
m_pFoundKey)))
{
goto Exit;
}
}
Exit:
return rc;
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE KeyIterator::getCurrentKeyVal(
FLMUINT uiComponent,
FLMBYTE * pszKey,
FLMUINT uiBufSize,
FLMUINT * puiKeyLen,
FLMUINT64 * pui64Id)
{
RCODE rc = NE_XFLM_OK;
if ( RC_BAD( rc = m_pFoundKey->getUTF8( uiComponent, pszKey, &uiBufSize)))
{
goto Exit;
}
if ( puiKeyLen)
{
*puiKeyLen = uiBufSize;
}
if ( pui64Id)
{
*pui64Id = m_pFoundKey->getID( uiComponent);
}
Exit:
return rc;
}
/****************************************************************************
Desc:
****************************************************************************/
KeyIterator::~KeyIterator()
{
if ( m_pFoundKey)
{
m_pFoundKey->Release();
}
if ( m_pSearchKey)
{
m_pSearchKey->Release();
}
}
/****************************************************************************
Desc:
****************************************************************************/
FLMBOOL FlagSet::removeElem( FLMBYTE * pElem)
{
FLMBOOL bElemExisted = FALSE;
for ( FLMUINT uiLoop = 0; uiLoop < m_uiNumElems; uiLoop++)
{
if ( f_strcmp( (char *)pElem, (char *)m_ppucElemArray[ uiLoop]) == 0)
{
bElemExisted = TRUE;
if ( uiLoop < m_uiNumElems - 1)
{
f_free( &m_ppucElemArray[ uiLoop]);
f_memmove( &m_ppucElemArray[ uiLoop],
&m_ppucElemArray[ uiLoop + 1],
(m_uiNumElems - ( uiLoop + 1)) * sizeof( FLMBYTE *));
f_memmove( &m_pbFlagArray[ uiLoop],
&m_pbFlagArray[ uiLoop + 1],
(m_uiNumElems - ( uiLoop + 1)) * sizeof( FLMBOOL));
}
// Otherwise, we're at the end and decrementing to counter will suffice
m_uiNumElems--;
}
}
return bElemExisted;
}
/****************************************************************************
Desc:
****************************************************************************/
FLMBOOL FlagSet::removeElemContaining( FLMBYTE * pszSubString)
{
FLMBOOL bElemExisted = FALSE;
for ( FLMUINT uiLoop = 0; uiLoop < m_uiNumElems; )
{
if ( containsSubstring( m_ppucElemArray[ uiLoop], pszSubString))
{
bElemExisted = TRUE;
if ( uiLoop < m_uiNumElems - 1)
{
f_memmove( &m_ppucElemArray[ uiLoop],
&m_ppucElemArray[ uiLoop + 1],
( m_uiNumElems - ( uiLoop + 1)) * sizeof( FLMBYTE *));
f_memmove( &m_pbFlagArray[ uiLoop],
&m_pbFlagArray[ uiLoop + 1],
( m_uiNumElems - ( uiLoop + 1)) * sizeof( FLMBYTE *));
}
// Otherwise, we're at the end and decrementing to counter will suffice
m_uiNumElems--;
}
else
{
uiLoop++;
}
}
return bElemExisted;
}
/****************************************************************************
Desc:
****************************************************************************/
FLMBOOL FlagSet::setElemFlag( FLMBYTE * pElem)
{
FLMBOOL bIsInSet = FALSE;
for ( FLMUINT uiLoop = 0; uiLoop < m_uiNumElems; uiLoop++)
{
if ( f_strcmp( (char *)pElem, (char *)m_ppucElemArray[ uiLoop]) == 0 &&
!m_pbFlagArray [uiLoop])
{
m_pbFlagArray[ uiLoop] = TRUE;
bIsInSet = TRUE;
break;
}
}
return bIsInSet;
}
/****************************************************************************
Desc:
****************************************************************************/
FlagSet FlagSet::crossProduct( FlagSet& fs2)
{
FlagSet fsCross;
FLMUINT uiLoop1;
FLMUINT uiCrossProductElems = this->getNumElements() * fs2.getNumElements();
FLMBYTE ** ppszCross = NULL;
if( RC_BAD( f_alloc( sizeof( FLMBYTE *) * uiCrossProductElems, &ppszCross)))
{
f_assert( 0);
}
for ( uiLoop1 = 0; uiLoop1 < this->getNumElements(); uiLoop1++)
{
for ( FLMUINT uiLoop2 = 0; uiLoop2 < fs2.getNumElements(); uiLoop2++)
{
FLMUINT uiIndex = (uiLoop1 * fs2.getNumElements()) + uiLoop2;
if( RC_BAD( f_alloc(
f_strlen( (char *)this->m_ppucElemArray[ uiLoop1]) +
f_strlen( (char *)fs2.m_ppucElemArray[ uiLoop2]) + 1,
&ppszCross[ uiIndex])))
{
f_assert( 0);
}
f_strcpy( (char *)ppszCross[ uiIndex], (char *)this->m_ppucElemArray[ uiLoop1]);
f_strcat( (char *)ppszCross[ uiIndex], (char *)fs2.m_ppucElemArray[ uiLoop2]);
}
}
fsCross.init( ppszCross, uiCrossProductElems);
for( uiLoop1 = 0; uiLoop1 < uiCrossProductElems; uiLoop1++)
{
f_free( &ppszCross[ uiLoop1]);
}
f_free( &ppszCross);
return( fsCross);
}
/****************************************************************************
Desc:
****************************************************************************/
FlagSet& FlagSet::operator=( const FlagSet& fs)
{
if ( this != &fs)
{
if ( m_ppucElemArray || m_pbFlagArray)
{
this->reset();
}
this->init( fs.m_ppucElemArray, fs.m_uiNumElems);
}
return *this;
}
/****************************************************************************
Desc:
****************************************************************************/
FlagSet::FlagSet( const FlagSet& fs)
{
m_ppucElemArray = NULL;
m_pbFlagArray = NULL;
f_alloc( sizeof( FLMBYTE *) * fs.m_uiNumElems, &m_ppucElemArray);
f_alloc( sizeof( FLMBOOL) * fs.m_uiNumElems, &m_pbFlagArray);
f_memset( m_pbFlagArray, 0, sizeof( FLMBOOL) * fs.m_uiNumElems);
for ( FLMUINT uiLoop = 0; uiLoop < fs.m_uiNumElems; uiLoop++)
{
f_alloc( f_strlen( (char *)fs.m_ppucElemArray[uiLoop]) + 1,
&m_ppucElemArray[ uiLoop]);
f_strcpy( (char *)m_ppucElemArray[uiLoop], (char *)fs.m_ppucElemArray[uiLoop]);
}
m_uiNumElems = fs.m_uiNumElems;
}
/****************************************************************************
Desc:
****************************************************************************/
void FlagSet::reset()
{
for( FLMUINT uiLoop = 0; uiLoop < m_uiNumElems; uiLoop++)
{
f_free( &m_ppucElemArray[ uiLoop]);
}
f_free( &m_ppucElemArray);
f_free( &m_pbFlagArray);
m_uiNumElems = 0;
m_ppucElemArray = NULL;
m_pbFlagArray = NULL;
}
/****************************************************************************
Desc:
****************************************************************************/
void FlagSet::init( FLMBYTE ** ppucElemArray, FLMUINT uiNumElems)
{
reset();
f_alloc( sizeof( FLMBYTE *) * uiNumElems, &m_ppucElemArray);
f_alloc( sizeof( FLMBOOL) * uiNumElems, &m_pbFlagArray);
f_memset( m_pbFlagArray, 0, sizeof( FLMBOOL) * uiNumElems);
for ( FLMUINT uiLoop = 0; uiLoop < uiNumElems; uiLoop++)
{
f_alloc( f_strlen( (char *)ppucElemArray[uiLoop]) + 1,
&m_ppucElemArray[ uiLoop]);
f_strcpy( (char *)m_ppucElemArray[uiLoop], (char *)ppucElemArray[uiLoop]);
}
m_uiNumElems = uiNumElems;
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE createUnitTest(
const char * configPath,
const char * buildNum,
const char * environment,
const char * user,
unitTestData * uTD)
{
RCODE rc = NE_XFLM_OK;
IF_FileSystem * pFileSystem = NULL;
IF_FileHdl * pConfigFileHdl = NULL;
IF_FileHdl * pCSVFileHdl = NULL;
char buffer[ MAX_BUFFER_SIZE] = "";
FLMUINT size = MAX_BUFFER_SIZE;
FLMUINT64 ui64Tmp;
char * strPos1 = NULL;
char * strPos2 = NULL;
if( !configPath || !buildNum || !environment || !uTD || !user)
{
flmAssert(0);
}
if( f_strlen(user) > MAX_SMALL_BUFFER_SIZE)
{
rc = RC_SET( NE_XFLM_BUFFER_OVERFLOW);
goto Exit;
}
else
{
f_strcpy(uTD->userName, user);
}
if( f_strlen(environment) > MAX_SMALL_BUFFER_SIZE)
{
rc = RC_SET( NE_XFLM_BUFFER_OVERFLOW);
goto Exit;
}
else
{
f_strcpy(uTD->environment, environment);
}
if( f_strlen(buildNum) > MAX_SMALL_BUFFER_SIZE)
{
rc = RC_SET( NE_XFLM_BUFFER_OVERFLOW);
goto Exit;
}
else
{
f_strcpy(uTD->buildNumber, buildNum);
}
if( RC_BAD( rc = FlmGetFileSystem( &pFileSystem)))
{
goto Exit;
}
if( configPath [0])
{
if( RC_BAD( rc = pFileSystem->openFile( configPath,
FLM_IO_RDONLY | FLM_IO_SH_DENYNONE, &pConfigFileHdl)))
{
goto Exit;
}
if ( RC_BAD( rc = pConfigFileHdl->size( &ui64Tmp)))
{
goto Exit;
}
size = (FLMUINT)ui64Tmp;
if ( RC_BAD( rc = pConfigFileHdl->read(
0, size, buffer, &size)))
{
goto Exit;
}
#ifdef FLM_WIN
{
char * temp;
f_alloc( size, &temp);
char * tempbegin = temp;
size_t newsize = size;
for( unsigned int i = 0; i < size; i++)
{
if ( ( ( i + 1) < size)
&& ( buffer[i] == 0x0D && buffer[i + 1] == 0x0A))
{
*temp++ = 0x0A;
i++;
newsize--;
}
else
{
*temp++ = buffer[i];
}
}
f_memcpy( buffer, tempbegin, (FLMSIZET)newsize);
size = newsize;
}
#endif
// Get the FOLDER
strPos1 = f_strchr(buffer, ':');
strPos2 = f_strchr(strPos1, '\n');
if(!strPos1 || !strPos2)
{
rc = RC_SET( NE_XFLM_FAILURE);
goto Exit;
}
for( strPos1++; *strPos1 == ' ' || *strPos1 == '\t'; strPos1++);
if(strPos2-strPos1 > MAX_SMALL_BUFFER_SIZE)
{
rc = RC_SET( NE_XFLM_BUFFER_OVERFLOW);
goto Exit;
}
f_strncpy(uTD->folder, strPos1, strPos2-strPos1);
uTD->folder[strPos2-strPos1] = '\0';
// Get the ATTRIBUTES
strPos1 = f_strchr(strPos1, ':');
strPos2 = f_strchr(strPos1, '\n');
if(!strPos1 || !strPos2)
{
rc = RC_SET( NE_XFLM_FAILURE);
goto Exit;
}
for(strPos1++;*strPos1 == ' ' || *strPos1 == '\t';strPos1++);
if( strPos2-strPos1 > MAX_SMALL_BUFFER_SIZE)
{
rc = RC_SET( NE_XFLM_FAILURE);
goto Exit;
}
f_strncpy(uTD->attrs, strPos1, strPos2-strPos1);
uTD->attrs[strPos2-strPos1] = '\0';
// Get the CSVFILE
strPos1 = f_strchr(strPos1, ':');
strPos2 = f_strchr(strPos1, '\n');
// Allow for possible \r
if( *( --strPos2) != '\r')
{
strPos2++;
}
if( !strPos1 || !strPos2)
{
rc = RC_SET( NE_XFLM_FAILURE);
goto Exit;
}
for( strPos1++;*strPos1 == ' ' || *strPos1 == '\t';strPos1++);
if( strPos2-strPos1 > MAX_SMALL_BUFFER_SIZE)
{
rc = RC_SET( NE_XFLM_FAILURE);
goto Exit;
}
f_strncpy(uTD->csvFilename, strPos1, strPos2-strPos1);
uTD->csvFilename[strPos2-strPos1] = '\0';
rc = pFileSystem->openFile(
uTD->csvFilename, FLM_IO_RDWR | FLM_IO_SH_DENYNONE, &pCSVFileHdl);
if( RC_BAD( rc))
{
if ( rc == NE_FLM_IO_PATH_NOT_FOUND)
{
// Create the file and write the header
if (RC_BAD( rc = f_filecat( uTD->csvFilename, DATA_ORDER)))
{
goto Exit;
}
}
}
else
{
goto Exit;
}
}
Exit:
if( pConfigFileHdl)
{
pConfigFileHdl->Release();
}
if( pCSVFileHdl)
{
pCSVFileHdl->Release();
}
if( pFileSystem)
{
pFileSystem->Release();
}
return( rc);
}
/****************************************************************************
Desc: After each unit test call this to record the unit test status
to a CSV file.
uTD - contains the configuration information
testName - a Unique for this module unite test name.
testDescr - A description of the unit test.
steps - The steps the unit test performs.
status - Maybe be PASS or FAIL
resultDetails - details that explain the result status.
****************************************************************************/
RCODE recordUnitTestResults(
unitTestData * uTD,
const char * testName,
const char * testDescr,
const char * steps,
const char * status,
const char * resultDetails,
const char * elapsedTime)
{
RCODE rc = NE_XFLM_OK;
char buffer[MAX_BUFFER_SIZE];
if( !testName || !testDescr || !steps || !status || !resultDetails || !uTD )
{
flmAssert(0);
}
//VISIT - re-enable the elapsed time reporting when the TCB can support it
(void)elapsedTime;
f_sprintf( buffer, "%s,%s,%s,%s,%s,%s,%s,%s,"/*%s,*/"%s,%s\n",
testName, uTD->userName, testDescr, steps, uTD->buildNumber, status,
uTD->environment, resultDetails, /*elapsedTime ? elapsedTime : "",*/
uTD->attrs, uTD->folder);
if( RC_BAD( rc = f_filecat( uTD->csvFilename, buffer)))
{
goto Exit;
}
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::init(
FLMBOOL bLog,
const char * pszLogfile,
FLMBOOL bDisplay,
FLMBOOL bVerboseDisplay,
const char * pszConfigFile,
const char * pszEnvironment,
const char * pszBuild,
const char * pszUser)
{
RCODE rc = NE_XFLM_MEM;
if( RC_BAD( rc = FlmAllocDbSystem( &m_pDbSystem)))
{
goto Exit;
}
m_bLog = bLog;
m_bDisplay = bDisplay;
// Set up logger and displayer if true
if( m_bLog)
{
if( ( m_pLogger = f_new IFlmTestLogger) == NULL)
{
rc = RC_SET( NE_XFLM_MEM);
goto Exit;
}
if( RC_BAD( rc = m_pLogger->init( pszLogfile)))
{
goto Exit;
}
}
if( m_bDisplay)
{
if( (m_pDisplayer = f_new IFlmTestDisplayer) == NULL)
{
rc = RC_SET( NE_XFLM_MEM);
goto Exit;
}
if( RC_BAD( rc = m_pDisplayer->init()))
{
goto Exit;
}
}
if( (m_pReporter = f_new ITestReporter) == NULL)
{
rc = RC_SET( NE_XFLM_MEM);
goto Exit;
}
if( RC_BAD( rc = m_pReporter->init( pszConfigFile, pszBuild,
pszEnvironment, pszUser)))
{
goto Exit;
}
m_bDisplayVerbose = bVerboseDisplay;
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::beginTest(
const char * pszTestName,
const char * pszTestDesc,
const char * pszTestSteps,
const char * pszDetails)
{
char szTemp[ 256];
m_pszTestName = pszTestName;
m_pszTestDesc = pszTestDesc;
m_pszSteps = pszTestSteps;
if( m_bDisplayVerbose)
{
displayLine(
"========================================"
"=======================================");
f_sprintf( szTemp, "Test Name: %s", m_pszTestName);
displayLine( szTemp);
f_sprintf( szTemp, "Test Description: %s", m_pszTestDesc);
displayLine( szTemp);
f_sprintf( szTemp, "Steps: %s", m_pszSteps);
displayLine( szTemp);
}
else
{
f_sprintf( szTemp, "Test Name: %s ... ", m_pszTestName);
display( szTemp);
}
f_strcpy( m_szDetails, pszDetails);
m_ui64StartMs = FLM_TIMER_UNITS_TO_SECS( FLM_GET_TIMER());
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::endTest(
const char * pszTestResult)
{
m_ui64EndMs = FLM_TIMER_UNITS_TO_SECS( FLM_GET_TIMER());
outputAll( pszTestResult, m_ui64EndMs - m_ui64StartMs);
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::log(
const char * pszString)
{
if( m_bLog)
{
m_pLogger->appendString( pszString);
}
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::display(
const char * pszString)
{
if( m_bDisplay)
{
m_pDisplayer->appendString( pszString);
}
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::displayLine(
const char * pszString)
{
if( m_bDisplay)
{
m_pDisplayer->appendString( pszString);
m_pDisplayer->appendString( "\n");
}
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::displayTime(
FLMUINT64 ui64Milli,
const char * pszIntro)
{
const char * pszDefault = "Elapsed Time: ";
char szTimeBuf[ 64];
char * pszTempBuf = NULL;
if( pszIntro)
{
f_alloc( f_strlen( pszIntro) + sizeof( szTimeBuf), &pszTempBuf);
f_strcpy( pszTempBuf, pszIntro);
}
else
{
f_alloc( f_strlen( pszDefault) + sizeof( szTimeBuf), &pszTempBuf);
f_strcpy( pszTempBuf, pszDefault);
}
normalizeTime( ui64Milli, szTimeBuf);
f_strcat( pszTempBuf, szTimeBuf);
displayLine( pszTempBuf);
}
/****************************************************************************
Desc:
****************************************************************************/
void TestBase::normalizeTime(
FLMUINT64 ui64Milli,
char * pszString)
{
FLMUINT64 ui64Ms;
FLMUINT64 ui64S;
FLMUINT64 ui64M;
FLMUINT64 ui64H;
ui64Ms = ui64Milli % 1000;
ui64S = ui64Milli / 1000;
ui64M = ui64S / 60;
ui64S %= 60;
ui64H = ui64M / 60;
ui64M %= 60;
f_sprintf( pszString, "%02I64u:%02I64u:%02I64u.%03I64u",
ui64H, ui64M, ui64S, ui64Ms);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::initCleanTestState(
const char * pszDibName)
{
RCODE rc = NE_XFLM_OK;
XFLM_CREATE_OPTS createOpts;
// Create the database
f_memset( &createOpts, 0, sizeof( XFLM_CREATE_OPTS));
if ( RC_BAD( rc = m_pDbSystem->dbCreate( pszDibName, NULL, NULL, NULL,
NULL, &createOpts, &m_pDb)))
{
if( rc == NE_XFLM_FILE_EXISTS)
{
if( RC_BAD( rc = m_pDbSystem->dbRemove( pszDibName, NULL, NULL, TRUE)))
{
goto Exit;
}
}
if( RC_BAD( rc = m_pDbSystem->dbCreate( pszDibName, NULL, NULL, NULL,
NULL, &createOpts, &m_pDb)))
{
goto Exit;
}
}
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::openTestState(
const char * pszDibName)
{
XFLM_CREATE_OPTS createOpts;
IF_FileSystem * pFileSys = NULL;
RCODE rc = NE_XFLM_OK;
if( RC_BAD( rc = FlmGetFileSystem( &pFileSys)))
{
goto Exit;
}
if ( RC_BAD( rc = pFileSys->doesFileExist( pszDibName)))
{
// Create the database
f_memset( &createOpts, 0, sizeof( XFLM_CREATE_OPTS));
if ( RC_BAD( rc = m_pDbSystem->dbCreate( pszDibName, NULL, NULL, NULL,
NULL, &createOpts, &m_pDb)))
{
goto Exit;
}
}
else
{
// Open the existing database
if( RC_BAD( rc = m_pDbSystem->dbOpen( pszDibName, NULL, NULL,
NULL, FALSE, &m_pDb)))
{
goto Exit;
}
}
Exit:
if( pFileSys)
{
pFileSys->Release();
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::shutdownTestState(
const char * pszDibName,
FLMBOOL bRemoveDib)
{
RCODE rc = NE_XFLM_OK;
FLMUINT uiRefCount;
if( bRemoveDib)
{
if( m_pDb)
{
uiRefCount = m_pDb->Release();
flmAssert( uiRefCount == 0);
m_pDb = NULL;
}
if( RC_BAD( rc = m_pDbSystem->dbRemove(
pszDibName, NULL, NULL, TRUE)))
{
goto Exit;
}
}
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::checkQueryResults(
const char ** ppszResults,
FLMUINT uiNumResultsExpected,
IF_Query * pQuery,
char * pszDetails)
{
RCODE rc = NE_XFLM_OK;
FlagSet flagSet;
IF_DOMNode * pReturn = NULL;
FLMUINT uiLoop;
char szBuffer[ 500];
flagSet.init( (FLMBYTE **)ppszResults, uiNumResultsExpected);
for( uiLoop = 0; ; uiLoop++)
{
if( !uiLoop)
{
if( RC_BAD( rc = pQuery->getFirst( m_pDb, &pReturn)))
{
MAKE_FLM_ERROR_STRING( "getFirst failed.", pszDetails, rc);
goto Exit;
}
}
else
{
if( RC_BAD( rc = pQuery->getNext( m_pDb, &pReturn)))
{
if( uiLoop < uiNumResultsExpected - 1)
{
MAKE_FLM_ERROR_STRING( "getNext failed.", pszDetails, rc);
goto Exit;
}
else
{
rc = NE_XFLM_OK;
break;
}
}
}
if( RC_BAD( rc = pReturn->getUTF8( m_pDb, (FLMBYTE *)szBuffer,
sizeof(szBuffer), 0, sizeof( szBuffer) - 1)))
{
MAKE_FLM_ERROR_STRING( "getUTF8 failed.", pszDetails, rc);
goto Exit;
}
if ( !flagSet.setElemFlag( (FLMBYTE *)szBuffer))
{
rc = NE_XFLM_FAILURE;
MAKE_FLM_ERROR_STRING( "Unexpected result received.", pszDetails, rc);
goto Exit;
}
}
if( !flagSet.allElemFlagsSet())
{
rc = NE_XFLM_FAILURE;
MAKE_FLM_ERROR_STRING( "Expected results not received.",
pszDetails, rc);
goto Exit;
}
Exit:
if( pReturn)
{
pReturn->Release();
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::doQueryTest(
const char * pszQueryString,
const char ** ppszExpectedResults,
FLMUINT uiNumResultsExpected,
IF_Query * pQuery,
char * pszDetails,
FLMUINT uiRequestedIndex,
FLMUINT * puiIndexUsed)
{
RCODE rc = NE_XFLM_OK;
FLMBOOL bHaveMult;
if( pszQueryString)
{
if( RC_BAD( rc = pQuery->setupQueryExpr( m_pDb, pszQueryString)))
{
MAKE_FLM_ERROR_STRING( "setupQueryExpr failed.", pszDetails, rc);
goto Exit;
}
}
if( uiRequestedIndex)
{
if( RC_BAD( rc = pQuery->setIndex( uiRequestedIndex)))
{
MAKE_FLM_ERROR_STRING( "setIndex failed.", pszDetails, rc);
goto Exit;
}
}
if( RC_BAD( rc = checkQueryResults( ppszExpectedResults,
uiNumResultsExpected, pQuery, pszDetails)))
{
goto Exit;
}
if( puiIndexUsed)
{
if( RC_BAD( rc = pQuery->getIndex( m_pDb, puiIndexUsed, &bHaveMult)))
{
goto Exit;
}
}
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::logTestResults(
const char * pszTestResult,
FLMUINT64 ui64ElapsedTime)
{
RCODE rc = NE_XFLM_OK;
char * pszTemp = NULL;
char szTime[ 64];
if( RC_BAD( rc = f_alloc( DETAILS_BUF_SIZ + 64, &pszTemp)))
{
goto Exit;
}
if( ui64ElapsedTime != ~((FLMUINT64)0))
{
normalizeTime( ui64ElapsedTime, szTime);
}
else
{
f_strcpy( szTime, "Not Recorded");
}
log(
"========================================"
"=======================================");
f_sprintf( pszTemp, "Test Name: %s", m_pszTestName);
log( pszTemp);
f_sprintf( pszTemp, "Test Description: %s", m_pszTestDesc);
log( pszTemp);
f_sprintf( pszTemp, "Steps: %s", m_pszSteps);
log( pszTemp);
f_sprintf( pszTemp, "Test Result: %s", pszTestResult);
log( pszTemp);
f_sprintf( pszTemp, "Details: %s", m_szDetails);
log( pszTemp);
f_sprintf( pszTemp, "Elapsed Time: %s", szTime);
log( pszTemp);
log(
"========================================"
"=======================================");
Exit:
if( pszTemp)
{
f_free( &pszTemp);
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::displayTestResults(
const char * pszTestResult,
FLMUINT64 ui64ElapsedTime)
{
RCODE rc = NE_XFLM_OK;
char * pszTemp = NULL;
char szTime[ 64];
if( RC_BAD( rc = f_alloc( DETAILS_BUF_SIZ + 64, &pszTemp)))
{
goto Exit;
}
if( ui64ElapsedTime != ~((FLMUINT64)0))
{
normalizeTime( ui64ElapsedTime, szTime);
}
else
{
f_strcpy( szTime, "Not Recorded");
}
if( m_bDisplayVerbose)
{
f_sprintf( pszTemp, "Test Result: %s", pszTestResult);
displayLine( pszTemp);
f_sprintf( pszTemp, "Details: %s", m_szDetails);
displayLine( pszTemp);
f_sprintf( pszTemp, "Elapsed Time: %s", szTime);
displayLine( pszTemp);
displayLine(
"========================================"
"=======================================");
}
else
{
f_sprintf( pszTemp, "Result: %s", pszTestResult);
displayLine( pszTestResult);
}
Exit:
if( pszTemp)
{
f_free( &pszTemp);
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::outputAll(
const char * pszTestResult,
FLMUINT64 ui64ElapsedTime)
{
RCODE rc = NE_XFLM_OK;
char * pszTime = NULL;
if( ui64ElapsedTime != ~((FLMUINT64)0))
{
if( RC_BAD( rc = f_alloc( 64, &pszTime)))
{
goto Exit;
}
normalizeTime( ui64ElapsedTime, pszTime);
}
if( RC_BAD( rc = displayTestResults( pszTestResult, ui64ElapsedTime)))
{
goto Exit;
}
if( RC_BAD( rc = logTestResults( pszTestResult, ui64ElapsedTime)))
{
goto Exit;
}
if( RC_BAD( rc = m_pReporter->recordUnitTestResults(
m_pszTestName, m_pszTestDesc, m_pszSteps, pszTestResult, m_szDetails,
pszTime)))
{
goto Exit;
}
Exit:
if( pszTime)
{
f_free( &pszTime);
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::importBuffer(
const char * pszBuffer,
FLMUINT uiCollection)
{
RCODE rc = NE_XFLM_OK;
if( RC_BAD( rc = m_pDbSystem->openBufferIStream( pszBuffer,
f_strlen( pszBuffer), &m_pInputStream)))
{
MAKE_FLM_ERROR_STRING( "openBufferIStream failed.", m_szDetails, rc);
goto Exit;
}
if( RC_BAD( rc = m_pDb->import( m_pInputStream, uiCollection)))
{
goto Exit;
}
Exit:
if( m_pInputStream)
{
m_pInputStream->Release();
m_pInputStream = NULL;
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::importDocument(
const char * pszBuffer,
FLMUINT uiCollection)
{
RCODE rc = NE_XFLM_OK;
if( RC_BAD( rc = m_pDbSystem->openBufferIStream( pszBuffer,
f_strlen( pszBuffer), &m_pInputStream)))
{
MAKE_FLM_ERROR_STRING( "openBufferIStream failed.", m_szDetails, rc);
goto Exit;
}
if( RC_BAD( rc = m_pDb->importDocument( m_pInputStream, uiCollection)))
{
goto Exit;
}
Exit:
if( m_pInputStream)
{
m_pInputStream->Release();
m_pInputStream = NULL;
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::importFile(
const char * pszFilename,
FLMUINT uiCollection)
{
RCODE rc = NE_XFLM_OK;
if( RC_BAD( rc = m_pDbSystem->openFileIStream( pszFilename,
&m_pInputStream)))
{
MAKE_FLM_ERROR_STRING( "openFileIStream failed.", m_szDetails, rc);
goto Exit;
}
if( RC_BAD( rc = m_pDb->import( m_pInputStream, uiCollection)))
{
MAKE_FLM_ERROR_STRING( "file import failed.", m_szDetails, rc);
goto Exit;
}
Exit:
if( m_pInputStream)
{
m_pInputStream->Release();
m_pInputStream = NULL;
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
TestBase::~TestBase()
{
if( m_pLogger)
{
m_pLogger->Release();
}
if( m_pDisplayer)
{
m_pDisplayer->Release();
}
if( m_pReporter)
{
m_pReporter->Release();
}
if( m_pInputStream)
{
m_pInputStream->Release();
}
if( m_pDb)
{
m_pDb->Release();
}
if( m_pDbSystem)
{
m_pDbSystem->Release();
}
}
/****************************************************************************
Desc:
****************************************************************************/
FLMINT TestBase::unicmp(
FLMUNICODE * puzStr1,
FLMUNICODE * puzStr2)
{
while( *puzStr1 == *puzStr2 && *puzStr1)
{
puzStr1++;
puzStr2++;
}
return( (FLMINT)*puzStr1 - (FLMINT)*puzStr2);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE TestBase::createCompoundDoc(
ELEMENT_NODE_INFO * pElementNodes,
FLMUINT uiNumElementNodes,
FLMUINT64 * pui64DocId)
{
IF_DOMNode * pDocRoot = NULL;
IF_DOMNode * pNode = NULL;
FLMUINT uiLoop;
RCODE rc = NE_XFLM_OK;
if( pui64DocId)
{
*pui64DocId = 0;
}
if( RC_BAD( rc = m_pDb->createRootElement(
XFLM_DATA_COLLECTION, ELM_ANY_TAG, &pDocRoot)))
{
MAKE_FLM_ERROR_STRING( "createRootElement failed.", m_szDetails, rc);
goto Exit;
}
for( uiLoop = 0; uiLoop < uiNumElementNodes; uiLoop++)
{
if( isPlaceHolder(pElementNodes[uiLoop]))
{
continue;
}
if( RC_BAD( rc = pDocRoot->createNode(
m_pDb, ELEMENT_NODE, pElementNodes[uiLoop].uiDictNum,
XFLM_LAST_CHILD, &pNode)))
{
MAKE_FLM_ERROR_STRING( "createNode failed.", m_szDetails, rc);
goto Exit;
}
switch( pElementNodes[uiLoop].uiDataType)
{
case XFLM_TEXT_TYPE:
{
if( RC_BAD( rc = pNode->setUTF8(
m_pDb, (FLMBYTE *)pElementNodes[uiLoop].pvData)))
{
goto Exit;
}
break;
}
case XFLM_NUMBER_TYPE:
{
if ( RC_BAD( rc = pNode->setUINT(
m_pDb, (FLMUINT)pElementNodes[uiLoop].pvData)))
{
goto Exit;
}
break;
}
case XFLM_BINARY_TYPE:
{
if ( RC_BAD( rc = pNode->setBinary(
m_pDb, (FLMBYTE*)pElementNodes[uiLoop].pvData,
pElementNodes[uiLoop].uiDataSize)))
{
goto Exit;
}
break;
}
default:
{
flmAssert( 0);
}
}
}
if( RC_BAD ( rc = m_pDb->documentDone( pDocRoot)))
{
MAKE_FLM_ERROR_STRING( "documentDone failed.", m_szDetails, rc);
goto Exit;
}
if( pui64DocId)
{
if( RC_BAD( rc = pDocRoot->getNodeId( m_pDb, pui64DocId)))
{
goto Exit;
}
}
Exit:
if( pNode)
{
pNode->Release();
}
if( pDocRoot)
{
pDocRoot->Release();
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
ArgList::ArgList()
{
m_uiCapacity = INIT_SIZE;
m_uiNumEntries = 0;
f_alloc( m_uiCapacity * sizeof( char *), &m_ppszArgs);
}
/****************************************************************************
Desc:
****************************************************************************/
ArgList::~ArgList()
{
FLMUINT uiLoop;
if( m_ppszArgs)
{
for( uiLoop = 0; uiLoop < m_uiNumEntries; uiLoop++)
{
f_free( &( m_ppszArgs[uiLoop]));
}
f_free( &m_ppszArgs);
}
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE ArgList::resize( void)
{
RCODE rc = NE_XFLM_OK;
FLMUINT uiLoop;
char ** ppszTemp = NULL;
if( RC_BAD( rc = f_alloc( m_uiCapacity * GROW_FACTOR * sizeof(char*),
&ppszTemp)))
{
goto Exit;
}
m_uiCapacity *= GROW_FACTOR;
for( uiLoop = 0; uiLoop < m_uiNumEntries; uiLoop++)
{
if( RC_BAD( rc = f_alloc( f_strlen( m_ppszArgs[uiLoop]) + 1,
&ppszTemp[uiLoop])))
{
f_free( &ppszTemp);
goto Exit;
}
f_strcpy( ppszTemp[uiLoop], m_ppszArgs[uiLoop]);
}
f_free( &m_ppszArgs);
m_ppszArgs = ppszTemp;
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
FLMUINT ArgList::getNumEntries( void)
{
return( m_uiNumEntries);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE ArgList::addArg(
const char * pszArg)
{
RCODE rc = NE_XFLM_OK;
if( m_uiNumEntries >= m_uiCapacity)
{
if( RC_BAD( rc = resize()))
{
goto Exit;
}
}
if( RC_BAD( rc = f_alloc( f_strlen( pszArg) + 1,
&m_ppszArgs[m_uiNumEntries])))
{
goto Exit;
}
f_strcpy( m_ppszArgs[ m_uiNumEntries++], pszArg);
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
const char * ArgList::getArg(
FLMUINT uiIndex)
{
return( m_ppszArgs[ uiIndex]);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE ArgList::expandFileArgs(
const char * pszFilename)
{
RCODE rc = NE_XFLM_OK;
char token[64];
IF_FileSystem * pFileSystem = NULL;
IF_FileHdl * pFileHdl = NULL;
if( RC_BAD( rc = FlmGetFileSystem( &pFileSystem)))
{
goto Exit;
}
if( RC_BAD( rc = pFileSystem->openFile( pszFilename, FLM_IO_RDWR,
&pFileHdl)))
{
goto Exit;
}
while( RC_OK( rc = getTokenFromFile(token, pFileHdl)))
{
if( token[0] == '@')
{
if( RC_BAD( rc = expandFileArgs( &token[1])))
{
goto Exit;
}
}
else
{
flmAssert(*token);
if( RC_BAD( rc = addArg( token)))
{
goto Exit;
}
}
}
if( rc == NE_FLM_IO_END_OF_FILE)
{
rc = NE_XFLM_OK;
}
Exit:
if( pFileHdl)
{
pFileHdl->Release();
}
if( pFileSystem)
{
pFileSystem->Release();
}
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE ArgList::expandArgs(
char ** ppszArgs,
FLMUINT uiNumArgs)
{
RCODE rc = NE_XFLM_OK;
FLMUINT uiLoop;
for( uiLoop = 0; uiLoop < uiNumArgs; uiLoop++)
{
if( ppszArgs[uiLoop][0] == '@')
{
if( RC_BAD( rc = expandFileArgs( &ppszArgs[uiLoop][ 1])))
{
goto Exit;
}
}
else
{
if( RC_BAD( rc = addArg( ppszArgs[ uiLoop])))
{
goto Exit;
}
}
}
Exit:
return( rc);
}
/****************************************************************************
Desc:
****************************************************************************/
const char * ArgList::operator []( FLMUINT uiIndex)
{
return( m_ppszArgs[ uiIndex]);
}
/****************************************************************************
Desc:
****************************************************************************/
RCODE ArgList::getTokenFromFile(
char * pszToken,
IF_FileHdl * pFileHdl)
{
RCODE rc = NE_XFLM_OK;
FLMUINT uiSize = 1;
FLMUINT64 ui64Offset = 0;
FLMUINT64 ui64TrueOffset = 0;
char c;
for(;;)
{
Skip_WS_And_Comments:
if ( RC_BAD( rc = pFileHdl->read( 0, 1, &c, &uiSize)))
{
goto Exit;
}
// Skip whitespace
while( isWhitespace(c))
{
if( RC_BAD( rc = pFileHdl->read( 0, 1, &c, &uiSize)))
{
goto Exit;
}
}
if( c == '#')
{
// Skip comment
for (;;)
{
if( RC_BAD( rc = pFileHdl->read( 0, 1, &c, &uiSize)))
{
goto Exit;
}
#ifdef FLM_UNIX
// On unix platforms, an EOL is indicated by an LF
if( c == 0x0A)
{
break;
}
#else
// On Windows and NetWare we need to look for CR/LF
if( c == 0x0D)
{
if( RC_BAD( rc = pFileHdl->read( 0, 1, &c, &uiSize)))
{
goto Exit;
}
// Newline found
if( c == 0x0A)
{
break;
}
else
{
// Rewind
ui64Offset = 0;
ui64TrueOffset = 0;
if( RC_BAD( rc = pFileHdl->tell( &ui64Offset)))
{
goto Exit;
}
ui64Offset--;
if( RC_BAD( rc = pFileHdl->seek( ui64Offset,
FLM_IO_SEEK_SET, &ui64TrueOffset)))
{
goto Exit;
}
}
}
#endif
}
goto Skip_WS_And_Comments;
}
while( !isWhitespace( c))
{
if( c == '#')
{
break;
}
*pszToken++ = c;
if( RC_BAD( rc = pFileHdl->read( 0, 1, &c, &uiSize)))
{
goto Exit;
}
}
// Put the char back
if( RC_BAD( rc = pFileHdl->tell( &ui64Offset)))
{
goto Exit;
}
ui64Offset--;
if( RC_BAD( rc = pFileHdl->seek( ui64Offset,
FLM_IO_SEEK_SET, &ui64TrueOffset)))
{
goto Exit;
}
break;
}
Exit:
*pszToken = '\0';
return( rc);
}