windows-nt/Source/XPSP1/NT/inetsrv/query/qutil/h/string.hxx
2020-09-26 16:20:57 +08:00

144 lines
3.5 KiB
C++

//+---------------------------------------------------------------------------
//
// Copyright (C) 1996-1998, Microsoft Corporation.
//
// File: string.hxx
//
// Contents: Yet another string class
//
// History: 96/Jan/3 DwightKr Created
//
//----------------------------------------------------------------------------
#pragma once
#include <ci64.hxx>
//+---------------------------------------------------------------------------
//
// Class: CVirtualString
//
// Purpose: Maintains a WCHAR string buffer as a virtual allocation
// and grows & commits it as necessary. This class should
// be used whenever you need a string buffer which will be
// slowly grow by appending new strings to it ... such as with
// the construction of query results in a HTML page.
//
// History: 96/Jan/23 DwightKr Created
//
//----------------------------------------------------------------------------
class CVirtualString
{
public:
CVirtualString( unsigned cwcBuffer = 2048 );
~CVirtualString();
WCHAR const * Get() const
{
Win4Assert( _wcsEnd <= _pwcLastCommitted );
*_wcsEnd = 0;
return _wcsString;
}
WCHAR * GetPointer() const
{
Win4Assert( _wcsEnd <= _pwcLastCommitted );
*_wcsEnd = 0;
return _wcsString;
}
void StrCat( WCHAR const * wcsString )
{
StrCat( wcsString, wcslen( wcsString ) );
}
void StrCat( WCHAR const * wcsString, ULONG cwcValue )
{
Win4Assert( ( 0 != wcsString ) || ( 0 == cwcValue ) );
if ( ( _wcsEnd + cwcValue ) >= _pwcLastCommitted )
GrowBuffer( cwcValue + 1 );
RtlCopyMemory( _wcsEnd, wcsString, cwcValue * sizeof WCHAR );
_wcsEnd += cwcValue;
Win4Assert( (_wcsEnd - _wcsString) < (int) _cwcBuffer );
}
void CharCat( WCHAR wcChar )
{
Win4Assert( 0 != wcChar );
Win4Assert( _wcsEnd <= _pwcLastCommitted );
if ( _wcsEnd != _pwcLastCommitted )
{
// duplicate the assignment to avoid a branch
*_wcsEnd++ = wcChar;
Win4Assert( (_wcsEnd - _wcsString) < (int) _cwcBuffer );
return;
}
GrowBuffer( 1 );
*_wcsEnd++ = wcChar;
Win4Assert( (_wcsEnd - _wcsString) < (int) _cwcBuffer );
}
WCHAR * StrDup() const
{
WCHAR * wcsString = new WCHAR[ StrLen() + 1 ];
RtlCopyMemory( wcsString,
_wcsString,
StrLen() * sizeof(WCHAR) );
wcsString[ StrLen() ] = 0;
return wcsString;
}
unsigned StrLen() const
{
return CiPtrToUint( _wcsEnd - _wcsString );
}
void Empty()
{
Win4Assert( 0 != _wcsString );
Win4Assert( _wcsEnd <= _pwcLastCommitted );
_wcsEnd = _wcsString;
*_wcsEnd = 0;
}
private:
void GrowBuffer( ULONG cwcToGrow );
WCHAR * _wcsString; // Start of the string
WCHAR * _wcsEnd; // Next place to strcat new data
WCHAR * _pwcLastCommitted; // Pointer to last committed WCHAR
unsigned _cwcBuffer; // Total size of virtual alloc'ed memory
};
void URLEscapeW( WCHAR const * wcsString,
CVirtualString & StrResult,
ULONG ulCodepage,
BOOL fConvertSpaceToPlus = FALSE );
void URLEscapeMToW( BYTE const * psz,
unsigned cc,
CVirtualString & StrResult,
BOOL fConvertSpaceToPlus = FALSE );