#ifndef UTLBUFFER_H #define UTLBUFFER_H #ifdef _WIN32 #pragma once #endif #include "utlmemory.h" #include "byteswap.h" #include struct characterset_t; class CUtlCharConversion { public: struct ConversionArray_t { char m_nActualChar; char* m_pReplacementString; }; CUtlCharConversion(char nEscapeChar, const char* pDelimiter, int nCount, ConversionArray_t* pArray); char GetEscapeChar() const; const char* GetDelimiter() const; int GetDelimiterLength() const; const char* GetConversionString(char c) const; int GetConversionLength(char c) const; int MaxConversionLength() const; virtual char FindConversion(const char* pString, int* pLength); protected: struct ConversionInfo_t { int m_nLength; char* m_pReplacementString; }; char m_nEscapeChar; const char* m_pDelimiter; int m_nDelimiterLength; int m_nCount; int m_nMaxConversionLength; char m_pList[256]; ConversionInfo_t m_pReplacements[256]; }; #define BEGIN_CHAR_CONVERSION( _name, _delimiter, _escapeChar ) \ static CUtlCharConversion::ConversionArray_t s_pConversionArray ## _name[] = { #define END_CHAR_CONVERSION( _name, _delimiter, _escapeChar ) \ }; \ CUtlCharConversion _name( _escapeChar, _delimiter, sizeof( s_pConversionArray ## _name ) / sizeof( CUtlCharConversion::ConversionArray_t ), s_pConversionArray ## _name ); #define BEGIN_CUSTOM_CHAR_CONVERSION( _className, _name, _delimiter, _escapeChar ) \ static CUtlCharConversion::ConversionArray_t s_pConversionArray ## _name[] = { #define END_CUSTOM_CHAR_CONVERSION( _className, _name, _delimiter, _escapeChar ) \ }; \ _className _name( _escapeChar, _delimiter, sizeof( s_pConversionArray ## _name ) / sizeof( CUtlCharConversion::ConversionArray_t ), s_pConversionArray ## _name ); CUtlCharConversion* GetCStringCharConversion(); CUtlCharConversion* GetNoEscCharConversion(); #define SetUtlBufferOverflowFuncs( _get, _put ) \ SetOverflowFuncs( static_cast ( _get ), static_cast ( _put ) ) typedef unsigned short ushort; template < class A > static const char* GetFmtStr(int nRadix = 10, bool bPrint = true) { Assert(0); return ""; } #if defined( LINUX ) || defined( __clang__ ) || ( defined( _MSC_VER ) && _MSC_VER >= 1900 ) template <> const char* GetFmtStr< short >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%hd"; } template <> const char* GetFmtStr< ushort >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%hu"; } template <> const char* GetFmtStr< int >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%d"; } template <> const char* GetFmtStr< uint >(int nRadix, bool bPrint) { Assert(nRadix == 10 || nRadix == 16); return nRadix == 16 ? "%x" : "%u"; } template <> const char* GetFmtStr< int64 >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%lld"; } template <> const char* GetFmtStr< float >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%f"; } template <> const char* GetFmtStr< double >(int nRadix, bool bPrint) { Assert(nRadix == 10); return bPrint ? "%.15lf" : "%lf"; } #else template <> static const char* GetFmtStr< short >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%hd"; } template <> static const char* GetFmtStr< ushort >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%hu"; } template <> static const char* GetFmtStr< int >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%d"; } template <> static const char* GetFmtStr< uint >(int nRadix, bool bPrint) { Assert(nRadix == 10 || nRadix == 16); return nRadix == 16 ? "%x" : "%u"; } template <> static const char* GetFmtStr< int64 >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%lld"; } template <> static const char* GetFmtStr< float >(int nRadix, bool bPrint) { Assert(nRadix == 10); return "%f"; } template <> static const char* GetFmtStr< double >(int nRadix, bool bPrint) { Assert(nRadix == 10); return bPrint ? "%.15lf" : "%lf"; } #endif class CUtlBuffer { public: enum SeekType_t { SEEK_HEAD = 0, SEEK_CURRENT, SEEK_TAIL }; enum BufferFlags_t { TEXT_BUFFER = 0x1, EXTERNAL_GROWABLE = 0x2, CONTAINS_CRLF = 0x4, READ_ONLY = 0x8, AUTO_TABS_DISABLED = 0x10, }; typedef bool (CUtlBuffer::* UtlBufferOverflowFunc_t)(int nSize); CUtlBuffer(int growSize = 0, int initSize = 0, int nFlags = 0); CUtlBuffer(const void* pBuffer, int size, int nFlags = 0); CUtlBuffer(const void* pBuffer, int size, bool crap) = delete; CUtlBuffer(const CUtlBuffer&); CUtlBuffer& operator= (const CUtlBuffer&); #if VALVE_CPP11 CUtlBuffer(CUtlBuffer&& moveFrom); CUtlBuffer& operator= (CUtlBuffer&& moveFrom); #endif unsigned char GetFlags() const; void SetBufferType(bool bIsText, bool bContainsCRLF); void EnsureCapacity(int num); void* AccessForDirectRead(int nBytes); void SetExternalBuffer(void* pMemory, int nSize, int nInitialPut, int nFlags = 0); bool IsExternallyAllocated() const; void AssumeMemory(void* pMemory, int nSize, int nInitialPut, int nFlags = 0); void* Detach(); void* DetachMemory(); void CopyBuffer(const CUtlBuffer& buffer); void CopyBuffer(const void* pubData, int cubData); void Swap(CUtlBuffer& buf); void Swap(CUtlMemory& mem); FORCEINLINE void ActivateByteSwappingIfBigEndian(void) { if ((IsX360() || IsPS3())) ActivateByteSwapping(true); } void ActivateByteSwapping(bool bActivate); void SetBigEndian(bool bigEndian); bool IsBigEndian(void); void Clear(); void Purge(); void Spew(); char GetChar(); unsigned char GetUnsignedChar(); short GetShort(); unsigned short GetUnsignedShort(); int GetInt(); int64 GetInt64(); unsigned int GetIntHex(); unsigned int GetUnsignedInt(); uint64 GetUnsignedInt64(); float GetFloat(); double GetDouble(); void* GetPtr(); void GetString(char* pString, int nMaxChars); void Get(void* pMem, int size); void GetLine(char* pLine, int nMaxChars); template void GetObjects(T* dest, int count = 1); int GetUpTo(void* pMem, int nSize); void GetDelimitedString(CUtlCharConversion* pConv, char* pString, int nMaxChars = 0); char GetDelimitedChar(CUtlCharConversion* pConv); int PeekStringLength(); int PeekDelimitedStringLength(CUtlCharConversion* pConv, bool bActualSize = true); int Scanf(SCANF_FORMAT_STRING const char* pFmt, ...); int VaScanf(const char* pFmt, va_list list); void EatWhiteSpace(); bool EatCPPComment(); bool ParseToken(const char* pStartingDelim, const char* pEndingDelim, char* pString, int nMaxLen); bool GetToken(const char* pToken); int ParseToken(characterset_t* pBreaks, char* pTokenBuf, int nMaxLen, bool bParseComments = true); void PutChar(char c); void PutUnsignedChar(unsigned char uc); void PutShort(short s); void PutUnsignedShort(unsigned short us); void PutInt(int i); void PutInt64(int64 i); void PutUnsignedInt(unsigned int u); void PutUnsignedInt64(uint64 u); void PutFloat(float f); void PutDouble(double d); void PutPtr(void*); void PutString(const char* pString); void Put(const void* pMem, int size); template void PutObjects(T* src, int count = 1); void PutDelimitedString(CUtlCharConversion* pConv, const char* pString); void PutDelimitedChar(CUtlCharConversion* pConv, char c); void Printf(PRINTF_FORMAT_STRING const char* pFmt, ...) FMTFUNCTION(2, 3); void VaPrintf(const char* pFmt, va_list list); void* PeekPut(int offset = 0); const void* PeekGet(int offset = 0) const; const void* PeekGet(int nMaxSize, int nOffset); int TellPut() const; int TellGet() const; int TellMaxPut() const; int GetBytesRemaining() const; void SeekPut(SeekType_t type, int offset); void SeekGet(SeekType_t type, int offset); const void* Base() const; void* Base(); int Size() const; bool IsText() const; bool IsGrowable() const; bool IsValid() const; bool ContainsCRLF() const; bool IsReadOnly() const; bool ConvertCRLF(CUtlBuffer& outBuf); void PushTab(); void PopTab(); void EnableTabs(bool bEnable); #if !defined( _GAMECONSOLE ) void SwapCopy(CUtlBuffer& other); #endif protected: enum { PUT_OVERFLOW = 0x1, GET_OVERFLOW = 0x2, MAX_ERROR_FLAG = GET_OVERFLOW, }; void SetOverflowFuncs(UtlBufferOverflowFunc_t getFunc, UtlBufferOverflowFunc_t putFunc); bool OnPutOverflow(int nSize); bool OnGetOverflow(int nSize); protected: bool CheckPut(int size); bool CheckGet(int size); void AddNullTermination(int nPut); bool WasLastCharacterCR(); void PutTabs(); char GetDelimitedCharInternal(CUtlCharConversion* pConv); void PutDelimitedCharInternal(CUtlCharConversion* pConv, char c); bool PutOverflow(int nSize); bool GetOverflow(int nSize); bool PeekStringMatch(int nOffset, const char* pString, int nLen); int PeekLineLength(); int PeekWhiteSpace(int nOffset); bool CheckPeekGet(int nOffset, int nSize); bool CheckArbitraryPeekGet(int nOffset, int& nIncrement); template void GetType(T& dest); template void GetTypeBin(T& dest); template bool GetTypeText(T& value, int nRadix = 10); template void GetObject(T* src); template void PutType(T src); template void PutTypeBin(T src); template void PutObject(T* src); CUtlMemory m_Memory; int m_Get; int m_Put; unsigned char m_Error; unsigned char m_Flags; unsigned char m_Reserved; #if defined( _GAMECONSOLE ) unsigned char pad; #endif int m_nTab; int m_nMaxPut; int m_nOffset; UtlBufferOverflowFunc_t m_GetOverflowFunc; UtlBufferOverflowFunc_t m_PutOverflowFunc; CByteswap m_Byteswap; }; inline CUtlBuffer& operator<<(CUtlBuffer& b, char v) { b.PutChar(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, unsigned char v) { b.PutUnsignedChar(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, short v) { b.PutShort(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, unsigned short v) { b.PutUnsignedShort(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, int v) { b.PutInt(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, unsigned int v) { b.PutUnsignedInt(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, float v) { b.PutFloat(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, double v) { b.PutDouble(v); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, const char* pv) { b.PutString(pv); return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, const Vector& v) { b << v.x << " " << v.y << " " << v.z; return b; } inline CUtlBuffer& operator<<(CUtlBuffer& b, const Vector2D& v) { b << v.x << " " << v.y; return b; } class CUtlInplaceBuffer : public CUtlBuffer { public: CUtlInplaceBuffer(int growSize = 0, int initSize = 0, int nFlags = 0); public: bool InplaceGetLinePtr( char** ppszInBufferPtr, int* pnLineLength); char* InplaceGetLinePtr(void); }; inline int CUtlBuffer::TellGet() const { return m_Get; } inline int CUtlBuffer::GetBytesRemaining() const { return m_nMaxPut - TellGet(); } inline const void* CUtlBuffer::PeekGet(int offset) const { return &m_Memory[m_Get + offset - m_nOffset]; } template inline void CUtlBuffer::GetObject(T* dest) { if (CheckGet(sizeof(T))) { if (!m_Byteswap.IsSwappingBytes() || (sizeof(T) == 1)) { *dest = *(T*)PeekGet(); } else { m_Byteswap.SwapFieldsToTargetEndian(dest, (T*)PeekGet()); } m_Get += sizeof(T); } else { Q_memset(&dest, 0, sizeof(T)); } } template inline void CUtlBuffer::GetObjects(T* dest, int count) { for (int i = 0; i < count; ++i, ++dest) { GetObject(dest); } } template inline void CUtlBuffer::GetTypeBin(T& dest) { if (CheckGet(sizeof(T))) { if (!m_Byteswap.IsSwappingBytes() || (sizeof(T) == 1)) { dest = *(T*)PeekGet(); } else { m_Byteswap.SwapBufferToTargetEndian(&dest, (T*)PeekGet()); } m_Get += sizeof(T); } else { dest = 0; } } template <> inline void CUtlBuffer::GetTypeBin< float >(float& dest) { if (CheckGet(sizeof(float))) { uintp pData = (uintp)PeekGet(); if ((IsX360() || IsPS3()) && (pData & 0x03)) { ((unsigned char*)&dest)[0] = ((unsigned char*)pData)[0]; ((unsigned char*)&dest)[1] = ((unsigned char*)pData)[1]; ((unsigned char*)&dest)[2] = ((unsigned char*)pData)[2]; ((unsigned char*)&dest)[3] = ((unsigned char*)pData)[3]; } else { dest = *(float*)pData; } if (m_Byteswap.IsSwappingBytes()) { m_Byteswap.SwapBufferToTargetEndian< float >(&dest, &dest); } m_Get += sizeof(float); } else { dest = 0; } } template <> inline void CUtlBuffer::GetTypeBin< double >(double& dest) { if (CheckGet(sizeof(double))) { uintp pData = (uintp)PeekGet(); if ((IsX360() || IsPS3()) && (pData & 0x07)) { ((unsigned char*)&dest)[0] = ((unsigned char*)pData)[0]; ((unsigned char*)&dest)[1] = ((unsigned char*)pData)[1]; ((unsigned char*)&dest)[2] = ((unsigned char*)pData)[2]; ((unsigned char*)&dest)[3] = ((unsigned char*)pData)[3]; ((unsigned char*)&dest)[4] = ((unsigned char*)pData)[4]; ((unsigned char*)&dest)[5] = ((unsigned char*)pData)[5]; ((unsigned char*)&dest)[6] = ((unsigned char*)pData)[6]; ((unsigned char*)&dest)[7] = ((unsigned char*)pData)[7]; } else { dest = *(double*)pData; } if (m_Byteswap.IsSwappingBytes()) { m_Byteswap.SwapBufferToTargetEndian< double >(&dest, &dest); } m_Get += sizeof(double); } else { dest = 0; } } template < class T > inline T StringToNumber(char* pString, char** ppEnd, int nRadix) { Assert(0); *ppEnd = pString; return 0; } template <> inline int8 StringToNumber(char* pString, char** ppEnd, int nRadix) { return (int8)strtol(pString, ppEnd, nRadix); } template <> inline uint8 StringToNumber(char* pString, char** ppEnd, int nRadix) { return (uint8)strtoul(pString, ppEnd, nRadix); } template <> inline int16 StringToNumber(char* pString, char** ppEnd, int nRadix) { return (int16)strtol(pString, ppEnd, nRadix); } template <> inline uint16 StringToNumber(char* pString, char** ppEnd, int nRadix) { return (uint16)strtoul(pString, ppEnd, nRadix); } template <> inline int32 StringToNumber(char* pString, char** ppEnd, int nRadix) { return (int32)strtol(pString, ppEnd, nRadix); } template <> inline uint32 StringToNumber(char* pString, char** ppEnd, int nRadix) { return (uint32)strtoul(pString, ppEnd, nRadix); } template <> inline int64 StringToNumber(char* pString, char** ppEnd, int nRadix) { #if defined(_PS3) || defined(POSIX) return (int64)strtoll(pString, ppEnd, nRadix); #else return (int64)_strtoi64(pString, ppEnd, nRadix); #endif } template <> inline float StringToNumber(char* pString, char** ppEnd, int nRadix) { NOTE_UNUSED(nRadix); return (float)strtod(pString, ppEnd); } template <> inline double StringToNumber(char* pString, char** ppEnd, int nRadix) { NOTE_UNUSED(nRadix); return (double)strtod(pString, ppEnd); } template inline bool CUtlBuffer::GetTypeText(T& value, int nRadix ) { int nLength = 128; if (!CheckArbitraryPeekGet(0, nLength)) { value = 0; return false; } char* pStart = (char*)PeekGet(); char* pEnd = pStart; value = StringToNumber< T >(pStart, &pEnd, nRadix); int nBytesRead = (int)(pEnd - pStart); if (nBytesRead == 0) return false; m_Get += nBytesRead; return true; } template inline void CUtlBuffer::GetType(T& dest) { if (!IsText()) { GetTypeBin(dest); } else { GetTypeText(dest); } } inline char CUtlBuffer::GetChar() { char c; GetTypeBin(c); return c; } inline unsigned char CUtlBuffer::GetUnsignedChar() { unsigned char c; if (!IsText()) { GetTypeBin(c); } else { c = (unsigned char)GetUnsignedShort(); } return c; } inline short CUtlBuffer::GetShort() { short s; GetType(s); return s; } inline unsigned short CUtlBuffer::GetUnsignedShort() { unsigned short s; GetType(s); return s; } inline int CUtlBuffer::GetInt() { int i; GetType(i); return i; } inline int64 CUtlBuffer::GetInt64() { int64 i; GetType(i); return i; } inline unsigned int CUtlBuffer::GetIntHex() { uint i; if (!IsText()) { GetTypeBin(i); } else { GetTypeText(i, 16); } return i; } inline unsigned int CUtlBuffer::GetUnsignedInt() { unsigned int i; GetType(i); return i; } inline uint64 CUtlBuffer::GetUnsignedInt64() { uint64 i; GetType(i); return i; } inline float CUtlBuffer::GetFloat() { float f; GetType(f); return f; } inline double CUtlBuffer::GetDouble() { double d; GetType(d); return d; } inline void* CUtlBuffer::GetPtr() { void* p; #if !defined(X64BITS) && !defined(PLATFORM_64BITS) p = (void*)GetUnsignedInt(); #else p = (void*)GetInt64(); #endif return p; } inline unsigned char CUtlBuffer::GetFlags() const { return m_Flags; } inline bool CUtlBuffer::IsExternallyAllocated() const { return m_Memory.IsExternallyAllocated(); } inline int CUtlBuffer::TellPut() const { return m_Put; } inline int CUtlBuffer::TellMaxPut() const { return m_nMaxPut; } inline void* CUtlBuffer::PeekPut(int offset) { return &m_Memory[m_Put + offset - m_nOffset]; } template inline void CUtlBuffer::PutObject(T* src) { if (CheckPut(sizeof(T))) { if (!m_Byteswap.IsSwappingBytes() || (sizeof(T) == 1)) { *(T*)PeekPut() = *src; } else { m_Byteswap.SwapFieldsToTargetEndian((T*)PeekPut(), src); } m_Put += sizeof(T); AddNullTermination(m_Put); } } template inline void CUtlBuffer::PutObjects(T* src, int count) { for (int i = 0; i < count; ++i, ++src) { PutObject(src); } } template inline void CUtlBuffer::PutTypeBin(T src) { if (CheckPut(sizeof(T))) { if (!m_Byteswap.IsSwappingBytes() || (sizeof(T) == 1)) { *(T*)PeekPut() = src; } else { m_Byteswap.SwapBufferToTargetEndian((T*)PeekPut(), &src); } m_Put += sizeof(T); AddNullTermination(m_Put); } } #if defined( _GAMECONSOLE ) template <> inline void CUtlBuffer::PutTypeBin< float >(float src) { if (CheckPut(sizeof(src))) { if (m_Byteswap.IsSwappingBytes()) { m_Byteswap.SwapBufferToTargetEndian(&src, &src); } unsigned pData = (unsigned)PeekPut(); if (pData & 0x03) { byte* dst = (byte*)pData; byte* srcPtr = (byte*)&src; dst[0] = srcPtr[0]; dst[1] = srcPtr[1]; dst[2] = srcPtr[2]; dst[3] = srcPtr[3]; } else { *(float*)pData = src; } m_Put += sizeof(float); AddNullTermination(m_Put); } } template <> inline void CUtlBuffer::PutTypeBin< double >(double src) { if (CheckPut(sizeof(src))) { if (m_Byteswap.IsSwappingBytes()) { m_Byteswap.SwapBufferToTargetEndian(&src, &src); } unsigned pData = (unsigned)PeekPut(); if (pData & 0x07) { byte* dst = (byte*)pData; byte* srcPtr = (byte*)&src; dst[0] = srcPtr[0]; dst[1] = srcPtr[1]; dst[2] = srcPtr[2]; dst[3] = srcPtr[3]; dst[4] = srcPtr[4]; dst[5] = srcPtr[5]; dst[6] = srcPtr[6]; dst[7] = srcPtr[7]; } else { *(double*)pData = src; } m_Put += sizeof(double); AddNullTermination(m_Put); } } #endif template inline void CUtlBuffer::PutType(T src) { if (!IsText()) { PutTypeBin(src); } else { Printf(GetFmtStr< T >(), src); } } inline bool CUtlBuffer::WasLastCharacterCR() { if (!IsText() || (TellPut() == 0)) return false; return (*(const char*)PeekPut(-1) == '\n'); } inline void CUtlBuffer::PutTabs() { int nTabCount = (m_Flags & AUTO_TABS_DISABLED) ? 0 : m_nTab; for (int i = nTabCount; --i >= 0; ) { PutTypeBin('\t'); } } inline void CUtlBuffer::PushTab() { ++m_nTab; } inline void CUtlBuffer::PopTab() { if (--m_nTab < 0) { m_nTab = 0; } } inline void CUtlBuffer::EnableTabs(bool bEnable) { if (bEnable) { m_Flags &= ~AUTO_TABS_DISABLED; } else { m_Flags |= AUTO_TABS_DISABLED; } } inline void CUtlBuffer::PutChar(char c) { if (WasLastCharacterCR()) { PutTabs(); } PutTypeBin(c); } inline void CUtlBuffer::PutUnsignedChar(unsigned char c) { if (!IsText()) { PutTypeBin(c); } else { PutUnsignedShort(c); } } inline void CUtlBuffer::PutShort(short s) { PutType(s); } inline void CUtlBuffer::PutUnsignedShort(unsigned short s) { PutType(s); } inline void CUtlBuffer::PutInt(int i) { PutType(i); } inline void CUtlBuffer::PutInt64(int64 i) { PutType(i); } inline void CUtlBuffer::PutUnsignedInt(unsigned int u) { PutType(u); } inline void CUtlBuffer::PutUnsignedInt64(uint64 i) { PutType(i); } inline void CUtlBuffer::PutFloat(float f) { PutType(f); } inline void CUtlBuffer::PutDouble(double d) { PutType(d); } inline void CUtlBuffer::PutPtr(void* p) { if (!IsText()) { PutTypeBin(p); } else { Printf("0x%p", p); } } inline bool CUtlBuffer::IsText() const { return (m_Flags & TEXT_BUFFER) != 0; } inline bool CUtlBuffer::IsGrowable() const { return (m_Flags & EXTERNAL_GROWABLE) != 0; } inline bool CUtlBuffer::IsValid() const { return m_Error == 0; } inline bool CUtlBuffer::ContainsCRLF() const { return IsText() && ((m_Flags & CONTAINS_CRLF) != 0); } inline bool CUtlBuffer::IsReadOnly() const { return (m_Flags & READ_ONLY) != 0; } inline const void* CUtlBuffer::Base() const { return m_Memory.Base(); } inline void* CUtlBuffer::Base() { return m_Memory.Base(); } inline int CUtlBuffer::Size() const { return m_Memory.NumAllocated(); } inline void CUtlBuffer::Clear() { m_Get = 0; m_Put = 0; m_Error = 0; m_nOffset = 0; m_nMaxPut = -1; AddNullTermination(m_Put); } inline void CUtlBuffer::Purge() { m_Get = 0; m_Put = 0; m_nOffset = 0; m_nMaxPut = 0; m_Error = 0; m_Memory.Purge(); } inline void* CUtlBuffer::AccessForDirectRead(int nBytes) { Assert(m_Get == 0 && m_Put == 0 && m_nMaxPut == 0); EnsureCapacity(nBytes); m_nMaxPut = nBytes; return Base(); } inline void* CUtlBuffer::Detach() { void* p = m_Memory.Detach(); Clear(); return p; } inline void CUtlBuffer::Spew() { SeekGet(CUtlBuffer::SEEK_HEAD, 0); char pTmpLine[1024]; while (IsValid() && GetBytesRemaining()) { V_memset(pTmpLine, 0, sizeof(pTmpLine)); Get(pTmpLine, MIN((size_t)GetBytesRemaining(), sizeof(pTmpLine) - 1)); Msg(_T("%s"), pTmpLine); } } #if !defined(_GAMECONSOLE) inline void CUtlBuffer::SwapCopy(CUtlBuffer& other) { m_Get = other.m_Get; m_Put = other.m_Put; m_Error = other.m_Error; m_Flags = other.m_Flags; m_Reserved = other.m_Reserved; m_nTab = other.m_nTab; m_nMaxPut = other.m_nMaxPut; m_nOffset = other.m_nOffset; m_GetOverflowFunc = other.m_GetOverflowFunc; m_PutOverflowFunc = other.m_PutOverflowFunc; m_Byteswap = other.m_Byteswap; m_Memory.Swap(other.m_Memory); } #endif inline void CUtlBuffer::CopyBuffer(const CUtlBuffer& buffer) { CopyBuffer(buffer.Base(), buffer.TellPut()); } inline void CUtlBuffer::CopyBuffer(const void* pubData, int cubData) { Clear(); if (cubData) { Put(pubData, cubData); } } #endif