mirror of
https://github.com/alliedmodders/hl2sdk.git
synced 2025-12-07 18:48:22 +00:00
Port KeyValues class from Source SDK 2013.
This commit is contained in:
parent
02af635a89
commit
1c13e12266
Binary file not shown.
@ -1,4 +1,4 @@
|
|||||||
//========= Copyright © 1996-2005, Valve Corporation, All rights reserved. ============//
|
//========= Copyright Valve Corporation, All rights reserved. ============//
|
||||||
//
|
//
|
||||||
// Purpose: This header should never be used directly from leaf code!!!
|
// Purpose: This header should never be used directly from leaf code!!!
|
||||||
// Instead, just add the file memoverride.cpp into your project and all this
|
// Instead, just add the file memoverride.cpp into your project and all this
|
||||||
@ -14,25 +14,31 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if !defined(NO_MALLOC_OVERRIDE) && defined(POSIX)
|
// These memory debugging switches aren't relevant under Linux builds since memoverride.cpp
|
||||||
#define NO_MALLOC_OVERRIDE
|
// isn't built into Linux projects
|
||||||
#endif
|
#ifndef POSIX
|
||||||
|
|
||||||
// Define this in release to get memory tracking even in release builds
|
// Define this in release to get memory tracking even in release builds
|
||||||
//#define USE_MEM_DEBUG 1
|
//#define USE_MEM_DEBUG 1
|
||||||
|
#endif
|
||||||
|
|
||||||
#if defined( _MEMTEST )
|
#if defined( _MEMTEST )
|
||||||
|
#ifdef _WIN32
|
||||||
#define USE_MEM_DEBUG 1
|
#define USE_MEM_DEBUG 1
|
||||||
#endif
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
// Undefine this if using a compiler lacking threadsafe RTTI (like vc6)
|
// Undefine this if using a compiler lacking threadsafe RTTI (like vc6)
|
||||||
#define MEM_DEBUG_CLASSNAME 1
|
#define MEM_DEBUG_CLASSNAME 1
|
||||||
|
|
||||||
#if !defined(STEAM) && !defined(NO_MALLOC_OVERRIDE)
|
|
||||||
|
|
||||||
#include <stddef.h>
|
#include <stddef.h>
|
||||||
|
#if defined( OSX )
|
||||||
|
#include <malloc/malloc.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include "tier0/mem.h"
|
#include "tier0/mem.h"
|
||||||
|
|
||||||
|
#if !defined(STEAM) && !defined(NO_MALLOC_OVERRIDE)
|
||||||
|
|
||||||
struct _CrtMemState;
|
struct _CrtMemState;
|
||||||
|
|
||||||
#define MEMALLOC_VERSION 1
|
#define MEMALLOC_VERSION 1
|
||||||
@ -107,7 +113,17 @@ public:
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
// Returns 0 if no failure, otherwise the size_t of the last requested chunk
|
// Returns 0 if no failure, otherwise the size_t of the last requested chunk
|
||||||
|
// "I'm sure this is completely thread safe!" Brian Deen 7/19/2012.
|
||||||
virtual size_t MemoryAllocFailed() = 0;
|
virtual size_t MemoryAllocFailed() = 0;
|
||||||
|
|
||||||
|
// handles storing allocation info for coroutines
|
||||||
|
virtual uint32 GetDebugInfoSize() = 0;
|
||||||
|
virtual void SaveDebugInfo( void *pvDebugInfo ) = 0;
|
||||||
|
virtual void RestoreDebugInfo( const void *pvDebugInfo ) = 0;
|
||||||
|
virtual void InitDebugInfo( void *pvDebugInfo, const char *pchRootFileName, int nLine ) = 0;
|
||||||
|
|
||||||
|
// Replacement for ::GlobalMemoryStatus which accounts for unused memory in our system
|
||||||
|
virtual void GlobalMemoryStatus( size_t *pUsedMemory, size_t *pFreeMemory ) = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
@ -117,11 +133,52 @@ MEM_INTERFACE IMemAlloc *g_pMemAlloc;
|
|||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#ifdef MEMALLOC_REGIONS
|
||||||
|
#ifndef MEMALLOC_REGION
|
||||||
|
#define MEMALLOC_REGION 0
|
||||||
|
#endif
|
||||||
|
inline void *MemAlloc_Alloc( size_t nSize )
|
||||||
|
{
|
||||||
|
return g_pMemAlloc->RegionAlloc( MEMALLOC_REGION, nSize );
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void *MemAlloc_Alloc( size_t nSize, const char *pFileName, int nLine )
|
||||||
|
{
|
||||||
|
return g_pMemAlloc->RegionAlloc( MEMALLOC_REGION, nSize, pFileName, nLine );
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
#undef MEMALLOC_REGION
|
||||||
|
inline void *MemAlloc_Alloc( size_t nSize )
|
||||||
|
{
|
||||||
|
return g_pMemAlloc->Alloc( nSize );
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void *MemAlloc_Alloc( size_t nSize, const char *pFileName, int nLine )
|
||||||
|
{
|
||||||
|
return g_pMemAlloc->Alloc( nSize, pFileName, nLine );
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
inline void MemAlloc_Free( void *ptr )
|
||||||
|
{
|
||||||
|
g_pMemAlloc->Free( ptr );
|
||||||
|
}
|
||||||
|
inline void MemAlloc_Free( void *ptr, const char *pFileName, int nLine )
|
||||||
|
{
|
||||||
|
g_pMemAlloc->Free( ptr, pFileName, nLine );
|
||||||
|
}
|
||||||
|
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
inline bool ValueIsPowerOfTwo( size_t value ) // don't clash with mathlib definition
|
||||||
|
{
|
||||||
|
return (value & ( value - 1 )) == 0;
|
||||||
|
}
|
||||||
|
|
||||||
inline void *MemAlloc_AllocAligned( size_t size, size_t align )
|
inline void *MemAlloc_AllocAligned( size_t size, size_t align )
|
||||||
{
|
{
|
||||||
unsigned char *pAlloc, *pResult;
|
unsigned char *pAlloc, *pResult;
|
||||||
|
|
||||||
if (!IsPowerOfTwo(uint(align)))
|
if (!IsPowerOfTwo(align))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
align = (align > sizeof(void *) ? align : sizeof(void *)) - 1;
|
align = (align > sizeof(void *) ? align : sizeof(void *)) - 1;
|
||||||
@ -139,7 +196,7 @@ inline void *MemAlloc_AllocAligned( size_t size, size_t align, const char *pszFi
|
|||||||
{
|
{
|
||||||
unsigned char *pAlloc, *pResult;
|
unsigned char *pAlloc, *pResult;
|
||||||
|
|
||||||
if (!IsPowerOfTwo(uint(align)))
|
if (!IsPowerOfTwo(align))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
align = (align > sizeof(void *) ? align : sizeof(void *)) - 1;
|
align = (align > sizeof(void *) ? align : sizeof(void *)) - 1;
|
||||||
@ -153,9 +210,45 @@ inline void *MemAlloc_AllocAligned( size_t size, size_t align, const char *pszFi
|
|||||||
return (void *)pResult;
|
return (void *)pResult;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void *MemAlloc_AllocAlignedUnattributed( size_t size, size_t align )
|
||||||
|
{
|
||||||
|
unsigned char *pAlloc, *pResult;
|
||||||
|
|
||||||
|
if (!ValueIsPowerOfTwo(align))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
align = (align > sizeof(void *) ? align : sizeof(void *)) - 1;
|
||||||
|
|
||||||
|
if ( (pAlloc = (unsigned char*)MemAlloc_Alloc( sizeof(void *) + align + size ) ) == (unsigned char*)NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
pResult = (unsigned char*)( (size_t)(pAlloc + sizeof(void *) + align ) & ~align );
|
||||||
|
((unsigned char**)(pResult))[-1] = pAlloc;
|
||||||
|
|
||||||
|
return (void *)pResult;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline void *MemAlloc_AllocAlignedFileLine( size_t size, size_t align, const char *pszFile, int nLine )
|
||||||
|
{
|
||||||
|
unsigned char *pAlloc, *pResult;
|
||||||
|
|
||||||
|
if (!ValueIsPowerOfTwo(align))
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
align = (align > sizeof(void *) ? align : sizeof(void *)) - 1;
|
||||||
|
|
||||||
|
if ( (pAlloc = (unsigned char*)MemAlloc_Alloc( sizeof(void *) + align + size, pszFile, nLine ) ) == (unsigned char*)NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
pResult = (unsigned char*)( (size_t)(pAlloc + sizeof(void *) + align ) & ~align );
|
||||||
|
((unsigned char**)(pResult))[-1] = pAlloc;
|
||||||
|
|
||||||
|
return (void *)pResult;
|
||||||
|
}
|
||||||
|
|
||||||
inline void *MemAlloc_ReallocAligned( void *ptr, size_t size, size_t align )
|
inline void *MemAlloc_ReallocAligned( void *ptr, size_t size, size_t align )
|
||||||
{
|
{
|
||||||
if ( !IsPowerOfTwo( uint(align) ) )
|
if ( !IsPowerOfTwo( align ) )
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
// Don't change alignment between allocation + reallocation.
|
// Don't change alignment between allocation + reallocation.
|
||||||
@ -201,6 +294,23 @@ inline void MemAlloc_FreeAligned( void *pMemBlock )
|
|||||||
g_pMemAlloc->Free( pAlloc );
|
g_pMemAlloc->Free( pAlloc );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void MemAlloc_FreeAligned( void *pMemBlock, const char *pFileName, int nLine )
|
||||||
|
{
|
||||||
|
void *pAlloc;
|
||||||
|
|
||||||
|
if ( pMemBlock == NULL )
|
||||||
|
return;
|
||||||
|
|
||||||
|
pAlloc = pMemBlock;
|
||||||
|
|
||||||
|
// pAlloc points to the pointer to starting of the memory block
|
||||||
|
pAlloc = (void *)(((size_t)pAlloc & ~( sizeof(void *) - 1 ) ) - sizeof(void *));
|
||||||
|
|
||||||
|
// pAlloc is the pointer to the start of memory block
|
||||||
|
pAlloc = *( (void **)pAlloc );
|
||||||
|
g_pMemAlloc->Free( pAlloc, pFileName, nLine );
|
||||||
|
}
|
||||||
|
|
||||||
inline size_t MemAlloc_GetSizeAligned( void *pMemBlock )
|
inline size_t MemAlloc_GetSizeAligned( void *pMemBlock )
|
||||||
{
|
{
|
||||||
void *pAlloc;
|
void *pAlloc;
|
||||||
@ -234,6 +344,20 @@ inline size_t MemAlloc_GetSizeAligned( void *pMemBlock )
|
|||||||
#define MemAlloc_RegisterDeallocation( pFileName, nLine, nLogicalSize, nActualSize, nTime ) ((void)0)
|
#define MemAlloc_RegisterDeallocation( pFileName, nLine, nLogicalSize, nActualSize, nTime ) ((void)0)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#define MemAlloc_DumpStats() g_pMemAlloc->DumpStats()
|
||||||
|
#define MemAlloc_CompactHeap() g_pMemAlloc->CompactHeap()
|
||||||
|
#define MemAlloc_OutOfMemory() g_pMemAlloc->OutOfMemory()
|
||||||
|
#define MemAlloc_CompactIncremental() g_pMemAlloc->CompactIncremental()
|
||||||
|
#define MemAlloc_DumpStatsFileBase( _filename ) g_pMemAlloc->DumpStatsFileBase( _filename )
|
||||||
|
#define MemAlloc_CrtCheckMemory() g_pMemAlloc->CrtCheckMemory()
|
||||||
|
#define MemAlloc_GlobalMemoryStatus( _usedMemory, _freeMemory ) g_pMemAlloc->GlobalMemoryStatus( _usedMemory, _freeMemory )
|
||||||
|
#define MemAlloc_MemoryAllocFailed() g_pMemAlloc->MemoryAllocFailed()
|
||||||
|
|
||||||
|
#define MemAlloc_GetDebugInfoSize() g_pMemAlloc->GetDebugInfoSize()
|
||||||
|
#define MemAlloc_SaveDebugInfo( pvDebugInfo ) g_pMemAlloc->SaveDebugInfo( pvDebugInfo )
|
||||||
|
#define MemAlloc_RestoreDebugInfo( pvDebugInfo ) g_pMemAlloc->RestoreDebugInfo( pvDebugInfo )
|
||||||
|
#define MemAlloc_InitDebugInfo( pvDebugInfo, pchRootFileName, nLine ) g_pMemAlloc->InitDebugInfo( pvDebugInfo, pchRootFileName, nLine )
|
||||||
|
#define MemAlloc_GetSize( x ) g_pMemAlloc->GetSize( x );
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
class CMemAllocAttributeAlloction
|
class CMemAllocAttributeAlloction
|
||||||
@ -339,6 +463,51 @@ struct MemAllocFileLine_t
|
|||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#elif defined( POSIX )
|
||||||
|
|
||||||
|
#if defined( OSX )
|
||||||
|
// Mac always aligns allocs, don't need to call posix_memalign which doesn't exist in 10.5.8 which TF2 still needs to run on
|
||||||
|
//inline void *memalign(size_t alignment, size_t size) {void *pTmp=NULL; posix_memalign(&pTmp, alignment, size); return pTmp;}
|
||||||
|
inline void *memalign(size_t alignment, size_t size) {void *pTmp=NULL; pTmp = malloc(size); return pTmp;}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
inline void *_aligned_malloc( size_t nSize, size_t align ) { return memalign( align, nSize ); }
|
||||||
|
inline void _aligned_free( void *ptr ) { free( ptr ); }
|
||||||
|
|
||||||
|
inline void *MemAlloc_Alloc( size_t nSize, const char *pFileName = NULL, int nLine = 0 ) { return malloc( nSize ); }
|
||||||
|
inline void MemAlloc_Free( void *ptr, const char *pFileName = NULL, int nLine = 0 ) { free( ptr ); }
|
||||||
|
|
||||||
|
inline void *MemAlloc_AllocAligned( size_t size, size_t align, const char *pszFile = NULL, int nLine = 0 ) { return memalign( align, size ); }
|
||||||
|
inline void *MemAlloc_AllocAlignedFileLine( size_t size, size_t align, const char *pszFile = NULL, int nLine = 0 ) { return memalign( align, size ); }
|
||||||
|
inline void MemAlloc_FreeAligned( void *pMemBlock, const char *pszFile = NULL, int nLine = 0 ) { free( pMemBlock ); }
|
||||||
|
|
||||||
|
#if defined( OSX )
|
||||||
|
inline size_t _msize( void *ptr ) { return malloc_size( ptr ); }
|
||||||
|
#else
|
||||||
|
inline size_t _msize( void *ptr ) { return malloc_usable_size( ptr ); }
|
||||||
|
#endif
|
||||||
|
|
||||||
|
inline void *MemAlloc_ReallocAligned( void *ptr, size_t size, size_t align )
|
||||||
|
{
|
||||||
|
void *ptr_new_aligned = memalign( align, size );
|
||||||
|
|
||||||
|
if( ptr_new_aligned )
|
||||||
|
{
|
||||||
|
size_t old_size = _msize( ptr );
|
||||||
|
size_t copy_size = ( size < old_size ) ? size : old_size;
|
||||||
|
|
||||||
|
memcpy( ptr_new_aligned, ptr, copy_size );
|
||||||
|
free( ptr );
|
||||||
|
}
|
||||||
|
|
||||||
|
return ptr_new_aligned;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
#define MemAlloc_GetDebugInfoSize() g_pMemAlloc->GetDebugInfoSize()
|
||||||
|
#define MemAlloc_SaveDebugInfo( pvDebugInfo ) g_pMemAlloc->SaveDebugInfo( pvDebugInfo )
|
||||||
|
#define MemAlloc_RestoreDebugInfo( pvDebugInfo ) g_pMemAlloc->RestoreDebugInfo( pvDebugInfo )
|
||||||
|
#define MemAlloc_InitDebugInfo( pvDebugInfo, pchRootFileName, nLine ) g_pMemAlloc->InitDebugInfo( pvDebugInfo, pchRootFileName, nLine )
|
||||||
|
|
||||||
#endif // !STEAM && !NO_MALLOC_OVERRIDE
|
#endif // !STEAM && !NO_MALLOC_OVERRIDE
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
@ -347,12 +516,139 @@ struct MemAllocFileLine_t
|
|||||||
|
|
||||||
#define MEM_ALLOC_CREDIT_(tag) ((void)0)
|
#define MEM_ALLOC_CREDIT_(tag) ((void)0)
|
||||||
#define MEM_ALLOC_CREDIT() MEM_ALLOC_CREDIT_(__FILE__)
|
#define MEM_ALLOC_CREDIT() MEM_ALLOC_CREDIT_(__FILE__)
|
||||||
|
#define MEM_ALLOC_CREDIT_FUNCTION()
|
||||||
#define MEM_ALLOC_CREDIT_CLASS()
|
#define MEM_ALLOC_CREDIT_CLASS()
|
||||||
#define MEM_ALLOC_CLASSNAME(type) NULL
|
#define MEM_ALLOC_CLASSNAME(type) NULL
|
||||||
#define MEM_ALLOC_CREDIT_FUNCTION()
|
|
||||||
|
#define MemAlloc_PushAllocDbgInfo( pszFile, line )
|
||||||
|
#define MemAlloc_PopAllocDbgInfo()
|
||||||
|
#define MemAlloc_RegisterAllocation( pFileName, nLine, nLogicalSize, nActualSize, nTime ) ((void)0)
|
||||||
|
#define MemAlloc_RegisterDeallocation( pFileName, nLine, nLogicalSize, nActualSize, nTime ) ((void)0)
|
||||||
|
#define MemAlloc_DumpStats() ((void)0)
|
||||||
|
#define MemAlloc_CompactHeap() ((void)0)
|
||||||
|
#define MemAlloc_OutOfMemory() ((void)0)
|
||||||
|
#define MemAlloc_CompactIncremental() ((void)0)
|
||||||
|
#define MemAlloc_DumpStatsFileBase( _filename ) ((void)0)
|
||||||
|
inline bool MemAlloc_CrtCheckMemory() { return true; }
|
||||||
|
inline void MemAlloc_GlobalMemoryStatus( size_t *pusedMemory, size_t *pfreeMemory )
|
||||||
|
{
|
||||||
|
*pusedMemory = 0;
|
||||||
|
*pfreeMemory = 0;
|
||||||
|
}
|
||||||
|
#define MemAlloc_MemoryAllocFailed() 0
|
||||||
|
|
||||||
|
#define MemAlloc_GetDebugInfoSize() 0
|
||||||
|
#define MemAlloc_SaveDebugInfo( pvDebugInfo ) ((void)0)
|
||||||
|
#define MemAlloc_RestoreDebugInfo( pvDebugInfo ) ((void)0)
|
||||||
|
#define MemAlloc_InitDebugInfo( pvDebugInfo, pchRootFileName, nLine ) ((void)0)
|
||||||
|
|
||||||
|
|
||||||
|
#define MEMALLOC_DEFINE_EXTERNAL_TRACKING( tag )
|
||||||
|
#define MemAlloc_RegisterExternalAllocation( tag, p, size ) ((void)0)
|
||||||
|
#define MemAlloc_RegisterExternalDeallocation( tag, p, size ) ((void)0)
|
||||||
|
|
||||||
#endif // !STEAM && NO_MALLOC_OVERRIDE
|
#endif // !STEAM && NO_MALLOC_OVERRIDE
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// linux memory tracking via hooks.
|
||||||
|
#if defined( POSIX ) && !defined( NO_HOOK_MALLOC )
|
||||||
|
PLATFORM_INTERFACE void MemoryLogMessage( char const *s ); // throw a message into the memory log
|
||||||
|
PLATFORM_INTERFACE void EnableMemoryLogging( bool bOnOff );
|
||||||
|
PLATFORM_INTERFACE void DumpMemoryLog( int nThresh );
|
||||||
|
PLATFORM_INTERFACE void DumpMemorySummary( void );
|
||||||
|
PLATFORM_INTERFACE void SetMemoryMark( void );
|
||||||
|
PLATFORM_INTERFACE void DumpChangedMemory( int nThresh );
|
||||||
|
|
||||||
|
#else
|
||||||
|
FORCEINLINE void MemoryLogMessage( char const *s )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
FORCEINLINE void EnableMemoryLogging( bool bOnOff )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
FORCEINLINE void DumpMemoryLog( int nThresh )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
FORCEINLINE void DumpMemorySummary( void )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
FORCEINLINE void SetMemoryMark( void )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
FORCEINLINE void DumpChangedMemory( int nThresh )
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef POSIX
|
||||||
|
// ApproximateProcessMemoryUsage returns the approximate memory footprint of this process.
|
||||||
|
PLATFORM_INTERFACE size_t ApproximateProcessMemoryUsage( void );
|
||||||
|
#else
|
||||||
|
FORCEINLINE size_t ApproximateProcessMemoryUsage( void )
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct aligned_tmp_t
|
||||||
|
{
|
||||||
|
// empty base class
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
This class used to be required if you wanted an object to be allocated with a specific
|
||||||
|
alignment. ALIGN16 and ALIGN16_POST are not actually sufficient for this because they
|
||||||
|
guarantee that the globals, statics, locals, and function parameters are appropriately
|
||||||
|
aligned they do not affect memory allocation alignment.
|
||||||
|
However this class is usually not needed because as of 2012 our policy is that our
|
||||||
|
allocator should take care of this automatically. Any object whose size is a multiple
|
||||||
|
of 16 will be 16-byte aligned. Existing uses of this class were not changed because
|
||||||
|
the cost/benefit did not justify it.
|
||||||
|
*/
|
||||||
|
// template here to allow adding alignment at levels of hierarchy that aren't the base
|
||||||
|
template< int bytesAlignment = 16, class T = aligned_tmp_t >
|
||||||
|
class CAlignedNewDelete : public T
|
||||||
|
{
|
||||||
|
|
||||||
|
public:
|
||||||
|
/*
|
||||||
|
Note that this class does not overload operator new[] and delete[] which means that
|
||||||
|
classes that depend on this for alignment may end up misaligned if an array is
|
||||||
|
allocated. This problem is now mostly theoretical because this class is mostly
|
||||||
|
obsolete.
|
||||||
|
*/
|
||||||
|
void *operator new( size_t nSize )
|
||||||
|
{
|
||||||
|
return MemAlloc_AllocAligned( nSize, bytesAlignment );
|
||||||
|
}
|
||||||
|
|
||||||
|
void* operator new( size_t nSize, int nBlockUse, const char *pFileName, int nLine )
|
||||||
|
{
|
||||||
|
return MemAlloc_AllocAlignedFileLine( nSize, bytesAlignment, pFileName, nLine );
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator delete(void *pData)
|
||||||
|
{
|
||||||
|
if ( pData )
|
||||||
|
{
|
||||||
|
MemAlloc_FreeAligned( pData );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator delete( void* pData, int nBlockUse, const char *pFileName, int nLine )
|
||||||
|
{
|
||||||
|
if ( pData )
|
||||||
|
{
|
||||||
|
MemAlloc_FreeAligned( pData, pFileName, nLine );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
#endif /* TIER0_MEMALLOC_H */
|
#endif /* TIER0_MEMALLOC_H */
|
||||||
|
|||||||
@ -75,27 +75,58 @@
|
|||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
#define IsLinux() false
|
#define IsLinux() false
|
||||||
|
#define IsOSX() false
|
||||||
|
#define IsPosix() false
|
||||||
|
#ifndef PLATFORM_WINDOWS
|
||||||
|
#define PLATFORM_WINDOWS 1 // Windows PC or Xbox 360
|
||||||
|
#endif
|
||||||
#ifndef _X360
|
#ifndef _X360
|
||||||
|
#define IsWindows() true
|
||||||
#define IsPC() true
|
#define IsPC() true
|
||||||
#define IsConsole() false
|
#define IsConsole() false
|
||||||
#define IsX360() false
|
#define IsX360() false
|
||||||
#define IsPS3() false
|
#define IsPS3() false
|
||||||
#define IS_WINDOWS_PC
|
#define IS_WINDOWS_PC
|
||||||
|
#define PLATFORM_WINDOWS_PC 1 // Windows PC
|
||||||
|
#ifdef _WIN64
|
||||||
|
#define IsPlatformWindowsPC64() true
|
||||||
|
#define IsPlatformWindowsPC32() false
|
||||||
|
#define PLATFORM_WINDOWS_PC64 1
|
||||||
#else
|
#else
|
||||||
|
#define IsPlatformWindowsPC64() false
|
||||||
|
#define IsPlatformWindowsPC32() true
|
||||||
|
#define PLATFORM_WINDOWS_PC32 1
|
||||||
|
#endif
|
||||||
|
#else
|
||||||
|
#define PLATFORM_X360 1
|
||||||
#ifndef _CONSOLE
|
#ifndef _CONSOLE
|
||||||
#define _CONSOLE
|
#define _CONSOLE
|
||||||
#endif
|
#endif
|
||||||
|
#define IsWindows() false
|
||||||
#define IsPC() false
|
#define IsPC() false
|
||||||
#define IsConsole() true
|
#define IsConsole() true
|
||||||
#define IsX360() true
|
#define IsX360() true
|
||||||
#define IsPS3() false
|
#define IsPS3() false
|
||||||
#endif
|
#endif
|
||||||
#elif defined(_LINUX) || defined(__APPLE__)
|
#elif defined(POSIX)
|
||||||
#define IsPC() true
|
#define IsPC() true
|
||||||
|
#define IsWindows() false
|
||||||
#define IsConsole() false
|
#define IsConsole() false
|
||||||
#define IsX360() false
|
#define IsX360() false
|
||||||
#define IsPS3() false
|
#define IsPS3() false
|
||||||
|
#if defined( LINUX )
|
||||||
#define IsLinux() true
|
#define IsLinux() true
|
||||||
|
#else
|
||||||
|
#define IsLinux() false
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if defined( OSX )
|
||||||
|
#define IsOSX() true
|
||||||
|
#else
|
||||||
|
#define IsOSX() false
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define IsPosix() true
|
||||||
#else
|
#else
|
||||||
#error
|
#error
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@ -1,4 +1,4 @@
|
|||||||
//========= Copyright © 1996-2005, Valve Corporation, All rights reserved. ============//
|
//========= Copyright Valve Corporation, All rights reserved. ============//
|
||||||
//
|
//
|
||||||
// Purpose:
|
// Purpose:
|
||||||
//
|
//
|
||||||
@ -25,10 +25,20 @@
|
|||||||
#include "utlvector.h"
|
#include "utlvector.h"
|
||||||
#include "Color.h"
|
#include "Color.h"
|
||||||
|
|
||||||
|
#define FOR_EACH_SUBKEY( kvRoot, kvSubKey ) \
|
||||||
|
for ( KeyValues * kvSubKey = kvRoot->GetFirstSubKey(); kvSubKey != NULL; kvSubKey = kvSubKey->GetNextKey() )
|
||||||
|
|
||||||
|
#define FOR_EACH_TRUE_SUBKEY( kvRoot, kvSubKey ) \
|
||||||
|
for ( KeyValues * kvSubKey = kvRoot->GetFirstTrueSubKey(); kvSubKey != NULL; kvSubKey = kvSubKey->GetNextTrueSubKey() )
|
||||||
|
|
||||||
|
#define FOR_EACH_VALUE( kvRoot, kvValue ) \
|
||||||
|
for ( KeyValues * kvValue = kvRoot->GetFirstValue(); kvValue != NULL; kvValue = kvValue->GetNextValue() )
|
||||||
|
|
||||||
class IBaseFileSystem;
|
class IBaseFileSystem;
|
||||||
class CUtlBuffer;
|
class CUtlBuffer;
|
||||||
class Color;
|
class Color;
|
||||||
typedef void * FileHandle_t;
|
typedef void * FileHandle_t;
|
||||||
|
class CKeyValuesGrowableStringTable;
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Purpose: Simple recursive data access class
|
// Purpose: Simple recursive data access class
|
||||||
@ -39,7 +49,7 @@ typedef void * FileHandle_t;
|
|||||||
// About KeyValues Text File Format:
|
// About KeyValues Text File Format:
|
||||||
|
|
||||||
// It has 3 control characters '{', '}' and '"'. Names and values may be quoted or
|
// It has 3 control characters '{', '}' and '"'. Names and values may be quoted or
|
||||||
// not. The quote '"' charater must not be used within name or values, only for
|
// not. The quote '"' character must not be used within name or values, only for
|
||||||
// quoting whole tokens. You may use escape sequences wile parsing and add within a
|
// quoting whole tokens. You may use escape sequences wile parsing and add within a
|
||||||
// quoted token a \" to add quotes within your name or token. When using Escape
|
// quoted token a \" to add quotes within your name or token. When using Escape
|
||||||
// Sequence the parser must now that by setting KeyValues::UsesEscapeSequences( true ),
|
// Sequence the parser must now that by setting KeyValues::UsesEscapeSequences( true ),
|
||||||
@ -49,11 +59,25 @@ typedef void * FileHandle_t;
|
|||||||
// with a closing bracket '}'. Subkeys use the same definitions recursively.
|
// with a closing bracket '}'. Subkeys use the same definitions recursively.
|
||||||
// Whitespaces are space, return, newline and tabulator. Allowed Escape sequences
|
// Whitespaces are space, return, newline and tabulator. Allowed Escape sequences
|
||||||
// are \n, \t, \\, \n and \". The number character '#' is used for macro purposes
|
// are \n, \t, \\, \n and \". The number character '#' is used for macro purposes
|
||||||
// (eg #include), don't use it as first charater in key names.
|
// (eg #include), don't use it as first character in key names.
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
class KeyValues
|
class KeyValues
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
// By default, the KeyValues class uses a string table for the key names that is
|
||||||
|
// limited to 4MB. The game will exit in error if this space is exhausted. In
|
||||||
|
// general this is preferable for game code for performance and memory fragmentation
|
||||||
|
// reasons.
|
||||||
|
//
|
||||||
|
// If this is not acceptable, you can use this call to switch to a table that can grow
|
||||||
|
// arbitrarily. This call must be made before any KeyValues objects are allocated or it
|
||||||
|
// will result in undefined behavior. If you use the growable string table, you cannot
|
||||||
|
// share KeyValues pointers directly with any other module. You can serialize them across
|
||||||
|
// module boundaries. These limitations are acceptable in the Steam backend code
|
||||||
|
// this option was written for, but may not be in other situations. Make sure to
|
||||||
|
// understand the implications before using this.
|
||||||
|
static void SetUseGrowableStringTable( bool bUseGrowableTable );
|
||||||
|
|
||||||
KeyValues( const char *setName );
|
KeyValues( const char *setName );
|
||||||
|
|
||||||
//
|
//
|
||||||
@ -68,8 +92,11 @@ public:
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
explicit inline AutoDelete( KeyValues *pKeyValues ) : m_pKeyValues( pKeyValues ) {}
|
explicit inline AutoDelete( KeyValues *pKeyValues ) : m_pKeyValues( pKeyValues ) {}
|
||||||
|
explicit inline AutoDelete( const char *pchKVName ) : m_pKeyValues( new KeyValues( pchKVName ) ) {}
|
||||||
inline ~AutoDelete( void ) { if( m_pKeyValues ) m_pKeyValues->deleteThis(); }
|
inline ~AutoDelete( void ) { if( m_pKeyValues ) m_pKeyValues->deleteThis(); }
|
||||||
inline void Assign( KeyValues *pKeyValues ) { m_pKeyValues = pKeyValues; }
|
inline void Assign( KeyValues *pKeyValues ) { m_pKeyValues = pKeyValues; }
|
||||||
|
KeyValues *operator->() { return m_pKeyValues; }
|
||||||
|
operator KeyValues *() { return m_pKeyValues; }
|
||||||
private:
|
private:
|
||||||
AutoDelete( AutoDelete const &x ); // forbid
|
AutoDelete( AutoDelete const &x ); // forbid
|
||||||
AutoDelete & operator= ( AutoDelete const &x ); // forbid
|
AutoDelete & operator= ( AutoDelete const &x ); // forbid
|
||||||
@ -88,12 +115,13 @@ public:
|
|||||||
void SetName( const char *setName);
|
void SetName( const char *setName);
|
||||||
|
|
||||||
// gets the name as a unique int
|
// gets the name as a unique int
|
||||||
int GetNameSymbol() const;
|
int GetNameSymbol() const { return m_iKeyName; }
|
||||||
|
|
||||||
// File access. Set UsesEscapeSequences true, if resource file/buffer uses Escape Sequences (eg \n, \t)
|
// File access. Set UsesEscapeSequences true, if resource file/buffer uses Escape Sequences (eg \n, \t)
|
||||||
void UsesEscapeSequences(bool state); // default false
|
void UsesEscapeSequences(bool state); // default false
|
||||||
|
void UsesConditionals(bool state); // default true
|
||||||
bool LoadFromFile( IBaseFileSystem *filesystem, const char *resourceName, const char *pathID = NULL );
|
bool LoadFromFile( IBaseFileSystem *filesystem, const char *resourceName, const char *pathID = NULL );
|
||||||
bool SaveToFile( IBaseFileSystem *filesystem, const char *resourceName, const char *pathID = NULL);
|
bool SaveToFile( IBaseFileSystem *filesystem, const char *resourceName, const char *pathID = NULL, bool sortKeys = false, bool bAllowEmptyString = false );
|
||||||
|
|
||||||
// Read from a buffer... Note that the buffer must be null terminated
|
// Read from a buffer... Note that the buffer must be null terminated
|
||||||
bool LoadFromBuffer( char const *resourceName, const char *pBuffer, IBaseFileSystem* pFileSystem = NULL, const char *pPathID = NULL );
|
bool LoadFromBuffer( char const *resourceName, const char *pBuffer, IBaseFileSystem* pFileSystem = NULL, const char *pPathID = NULL );
|
||||||
@ -114,9 +142,10 @@ public:
|
|||||||
// NOTE: GetFirstSubKey/GetNextKey will iterate keys AND values. Use the functions
|
// NOTE: GetFirstSubKey/GetNextKey will iterate keys AND values. Use the functions
|
||||||
// below if you want to iterate over just the keys or just the values.
|
// below if you want to iterate over just the keys or just the values.
|
||||||
//
|
//
|
||||||
KeyValues *GetFirstSubKey(); // returns the first subkey in the list
|
KeyValues *GetFirstSubKey() { return m_pSub; } // returns the first subkey in the list
|
||||||
KeyValues *GetNextKey(); // returns the next subkey
|
KeyValues *GetNextKey() { return m_pPeer; } // returns the next subkey
|
||||||
void SetNextKey( KeyValues * pDat);
|
void SetNextKey( KeyValues * pDat);
|
||||||
|
KeyValues *FindLastSubKey(); // returns the LAST subkey in the list. This requires a linked list iteration to find the key. Returns NULL if we don't have any children
|
||||||
|
|
||||||
//
|
//
|
||||||
// These functions can be used to treat it like a true key/values tree instead of
|
// These functions can be used to treat it like a true key/values tree instead of
|
||||||
@ -145,6 +174,7 @@ public:
|
|||||||
const char *GetString( const char *keyName = NULL, const char *defaultValue = "" );
|
const char *GetString( const char *keyName = NULL, const char *defaultValue = "" );
|
||||||
const wchar_t *GetWString( const char *keyName = NULL, const wchar_t *defaultValue = L"" );
|
const wchar_t *GetWString( const char *keyName = NULL, const wchar_t *defaultValue = L"" );
|
||||||
void *GetPtr( const char *keyName = NULL, void *defaultValue = (void*)0 );
|
void *GetPtr( const char *keyName = NULL, void *defaultValue = (void*)0 );
|
||||||
|
bool GetBool( const char *keyName = NULL, bool defaultValue = false, bool* optGotDefault = NULL );
|
||||||
Color GetColor( const char *keyName = NULL /* default value is all black */);
|
Color GetColor( const char *keyName = NULL /* default value is all black */);
|
||||||
bool IsEmpty(const char *keyName = NULL);
|
bool IsEmpty(const char *keyName = NULL);
|
||||||
|
|
||||||
@ -165,6 +195,7 @@ public:
|
|||||||
void SetFloat( const char *keyName, float value );
|
void SetFloat( const char *keyName, float value );
|
||||||
void SetPtr( const char *keyName, void *value );
|
void SetPtr( const char *keyName, void *value );
|
||||||
void SetColor( const char *keyName, Color value);
|
void SetColor( const char *keyName, Color value);
|
||||||
|
void SetBool( const char *keyName, bool value ) { SetInt( keyName, value ? 1 : 0 ); }
|
||||||
|
|
||||||
// Memory allocation (optimized)
|
// Memory allocation (optimized)
|
||||||
void *operator new( size_t iAllocSize );
|
void *operator new( size_t iAllocSize );
|
||||||
@ -178,10 +209,10 @@ public:
|
|||||||
// in the one we're chained to.
|
// in the one we're chained to.
|
||||||
void ChainKeyValue( KeyValues* pChain );
|
void ChainKeyValue( KeyValues* pChain );
|
||||||
|
|
||||||
void RecursiveSaveToFile( CUtlBuffer& buf, int indentLevel );
|
void RecursiveSaveToFile( CUtlBuffer& buf, int indentLevel, bool sortKeys = false, bool bAllowEmptyString = false );
|
||||||
|
|
||||||
bool WriteAsBinary( CUtlBuffer &buffer );
|
bool WriteAsBinary( CUtlBuffer &buffer );
|
||||||
bool ReadAsBinary( CUtlBuffer &buffer );
|
bool ReadAsBinary( CUtlBuffer &buffer, int nStackDepth = 0 );
|
||||||
|
|
||||||
// Allocate & create a new copy of the keys
|
// Allocate & create a new copy of the keys
|
||||||
KeyValues *MakeCopy( void ) const;
|
KeyValues *MakeCopy( void ) const;
|
||||||
@ -213,11 +244,17 @@ public:
|
|||||||
void SetStringValue( char const *strValue );
|
void SetStringValue( char const *strValue );
|
||||||
|
|
||||||
// unpack a key values list into a structure
|
// unpack a key values list into a structure
|
||||||
void UnpackIntoStructure( struct KeyValuesUnpackStructure const *pUnpackTable, void *pDest );
|
void UnpackIntoStructure( struct KeyValuesUnpackStructure const *pUnpackTable, void *pDest, size_t DestSizeInBytes );
|
||||||
|
|
||||||
// Process conditional keys for widescreen support.
|
// Process conditional keys for widescreen support.
|
||||||
bool ProcessResolutionKeys( const char *pResString );
|
bool ProcessResolutionKeys( const char *pResString );
|
||||||
|
|
||||||
|
// Dump keyvalues recursively into a dump context
|
||||||
|
bool Dump( class IKeyValuesDumpContext *pDump, int nIndentLevel = 0 );
|
||||||
|
|
||||||
|
// Merge in another KeyValues, keeping "our" settings
|
||||||
|
void RecursiveMergeKeyValues( KeyValues *baseKV );
|
||||||
|
|
||||||
private:
|
private:
|
||||||
KeyValues( KeyValues& ); // prevent copy constructor being used
|
KeyValues( KeyValues& ); // prevent copy constructor being used
|
||||||
|
|
||||||
@ -226,6 +263,13 @@ private:
|
|||||||
|
|
||||||
KeyValues* CreateKey( const char *keyName );
|
KeyValues* CreateKey( const char *keyName );
|
||||||
|
|
||||||
|
/// Create a child key, given that we know which child is currently the last child.
|
||||||
|
/// This avoids the O(N^2) behaviour when adding children in sequence to KV,
|
||||||
|
/// when CreateKey() wil have to re-locate the end of the list each time. This happens,
|
||||||
|
/// for example, every time we load any KV file whatsoever.
|
||||||
|
KeyValues* CreateKeyUsingKnownLastChild( const char *keyName, KeyValues *pLastChild );
|
||||||
|
void AddSubkeyUsingKnownLastChild( KeyValues *pSubKey, KeyValues *pLastChild );
|
||||||
|
|
||||||
void RecursiveCopyKeyValues( KeyValues& src );
|
void RecursiveCopyKeyValues( KeyValues& src );
|
||||||
void RemoveEverything();
|
void RemoveEverything();
|
||||||
// void RecursiveSaveToFile( IBaseFileSystem *filesystem, CUtlBuffer &buffer, int indentLevel );
|
// void RecursiveSaveToFile( IBaseFileSystem *filesystem, CUtlBuffer &buffer, int indentLevel );
|
||||||
@ -233,7 +277,8 @@ private:
|
|||||||
|
|
||||||
// NOTE: If both filesystem and pBuf are non-null, it'll save to both of them.
|
// NOTE: If both filesystem and pBuf are non-null, it'll save to both of them.
|
||||||
// If filesystem is null, it'll ignore f.
|
// If filesystem is null, it'll ignore f.
|
||||||
void RecursiveSaveToFile( IBaseFileSystem *filesystem, FileHandle_t f, CUtlBuffer *pBuf, int indentLevel );
|
void RecursiveSaveToFile( IBaseFileSystem *filesystem, FileHandle_t f, CUtlBuffer *pBuf, int indentLevel, bool sortKeys, bool bAllowEmptyString );
|
||||||
|
void SaveKeyToFile( KeyValues *dat, IBaseFileSystem *filesystem, FileHandle_t f, CUtlBuffer *pBuf, int indentLevel, bool sortKeys, bool bAllowEmptyString );
|
||||||
void WriteConvertedString( IBaseFileSystem *filesystem, FileHandle_t f, CUtlBuffer *pBuf, const char *pszString );
|
void WriteConvertedString( IBaseFileSystem *filesystem, FileHandle_t f, CUtlBuffer *pBuf, const char *pszString );
|
||||||
|
|
||||||
void RecursiveLoadFromBuffer( char const *resourceName, CUtlBuffer &buf );
|
void RecursiveLoadFromBuffer( char const *resourceName, CUtlBuffer &buf );
|
||||||
@ -245,7 +290,6 @@ private:
|
|||||||
|
|
||||||
// For handling #base "filename"
|
// For handling #base "filename"
|
||||||
void MergeBaseKeys( CUtlVector< KeyValues * >& baseKeys );
|
void MergeBaseKeys( CUtlVector< KeyValues * >& baseKeys );
|
||||||
void RecursiveMergeKeyValues( KeyValues *baseKV );
|
|
||||||
|
|
||||||
// NOTE: If both filesystem and pBuf are non-null, it'll save to both of them.
|
// NOTE: If both filesystem and pBuf are non-null, it'll save to both of them.
|
||||||
// If filesystem is null, it'll ignore f.
|
// If filesystem is null, it'll ignore f.
|
||||||
@ -275,13 +319,36 @@ private:
|
|||||||
|
|
||||||
char m_iDataType;
|
char m_iDataType;
|
||||||
char m_bHasEscapeSequences; // true, if while parsing this KeyValue, Escape Sequences are used (default false)
|
char m_bHasEscapeSequences; // true, if while parsing this KeyValue, Escape Sequences are used (default false)
|
||||||
char unused[2];
|
char m_bEvaluateConditionals; // true, if while parsing this KeyValue, conditionals blocks are evaluated (default true)
|
||||||
|
char unused[1];
|
||||||
|
|
||||||
KeyValues *m_pPeer; // pointer to next key in list
|
KeyValues *m_pPeer; // pointer to next key in list
|
||||||
KeyValues *m_pSub; // pointer to Start of a new sub key list
|
KeyValues *m_pSub; // pointer to Start of a new sub key list
|
||||||
KeyValues *m_pChain;// Search here if it's not in our list
|
KeyValues *m_pChain;// Search here if it's not in our list
|
||||||
|
|
||||||
|
private:
|
||||||
|
// Statics to implement the optional growable string table
|
||||||
|
// Function pointers that will determine which mode we are in
|
||||||
|
static int (*s_pfGetSymbolForString)( const char *name, bool bCreate );
|
||||||
|
static const char *(*s_pfGetStringForSymbol)( int symbol );
|
||||||
|
static CKeyValuesGrowableStringTable *s_pGrowableStringTable;
|
||||||
|
|
||||||
|
public:
|
||||||
|
// Functions that invoke the default behavior
|
||||||
|
static int GetSymbolForStringClassic( const char *name, bool bCreate = true );
|
||||||
|
static const char *GetStringForSymbolClassic( int symbol );
|
||||||
|
|
||||||
|
// Functions that use the growable string table
|
||||||
|
static int GetSymbolForStringGrowable( const char *name, bool bCreate = true );
|
||||||
|
static const char *GetStringForSymbolGrowable( int symbol );
|
||||||
|
|
||||||
|
// Functions to get external access to whichever of the above functions we're going to call.
|
||||||
|
static int CallGetSymbolForString( const char *name, bool bCreate = true ) { return s_pfGetSymbolForString( name, bCreate ); }
|
||||||
|
static const char *CallGetStringForSymbol( int symbol ) { return s_pfGetStringForSymbol( symbol ); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef KeyValues::AutoDelete KeyValuesAD;
|
||||||
|
|
||||||
enum KeyValuesUnpackDestinationTypes_t
|
enum KeyValuesUnpackDestinationTypes_t
|
||||||
{
|
{
|
||||||
UNPACK_TYPE_FLOAT, // dest is a float
|
UNPACK_TYPE_FLOAT, // dest is a float
|
||||||
@ -354,4 +421,57 @@ inline bool KeyValues::IsEmpty( int keySymbol )
|
|||||||
|
|
||||||
bool EvaluateConditional( const char *str );
|
bool EvaluateConditional( const char *str );
|
||||||
|
|
||||||
|
class CUtlSortVectorKeyValuesByName
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
bool Less( const KeyValues* lhs, const KeyValues* rhs, void * )
|
||||||
|
{
|
||||||
|
return Q_stricmp( lhs->GetName(), rhs->GetName() ) < 0;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
//
|
||||||
|
// KeyValuesDumpContext and generic implementations
|
||||||
|
//
|
||||||
|
|
||||||
|
class IKeyValuesDumpContext
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual bool KvBeginKey( KeyValues *pKey, int nIndentLevel ) = 0;
|
||||||
|
virtual bool KvWriteValue( KeyValues *pValue, int nIndentLevel ) = 0;
|
||||||
|
virtual bool KvEndKey( KeyValues *pKey, int nIndentLevel ) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
class IKeyValuesDumpContextAsText : public IKeyValuesDumpContext
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
virtual bool KvBeginKey( KeyValues *pKey, int nIndentLevel );
|
||||||
|
virtual bool KvWriteValue( KeyValues *pValue, int nIndentLevel );
|
||||||
|
virtual bool KvEndKey( KeyValues *pKey, int nIndentLevel );
|
||||||
|
|
||||||
|
public:
|
||||||
|
virtual bool KvWriteIndent( int nIndentLevel );
|
||||||
|
virtual bool KvWriteText( char const *szText ) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
class CKeyValuesDumpContextAsDevMsg : public IKeyValuesDumpContextAsText
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
// Overrides developer level to dump in DevMsg, zero to dump as Msg
|
||||||
|
CKeyValuesDumpContextAsDevMsg( int nDeveloperLevel = 1 ) : m_nDeveloperLevel( nDeveloperLevel ) {}
|
||||||
|
|
||||||
|
public:
|
||||||
|
virtual bool KvBeginKey( KeyValues *pKey, int nIndentLevel );
|
||||||
|
virtual bool KvWriteText( char const *szText );
|
||||||
|
|
||||||
|
protected:
|
||||||
|
int m_nDeveloperLevel;
|
||||||
|
};
|
||||||
|
|
||||||
|
inline bool KeyValuesDumpAsDevMsg( KeyValues *pKeyValues, int nIndentLevel = 0, int nDeveloperLevel = 1 )
|
||||||
|
{
|
||||||
|
CKeyValuesDumpContextAsDevMsg ctx( nDeveloperLevel );
|
||||||
|
return pKeyValues->Dump( &ctx, nIndentLevel );
|
||||||
|
}
|
||||||
|
|
||||||
#endif // KEYVALUES_H
|
#endif // KEYVALUES_H
|
||||||
|
|||||||
@ -110,6 +110,8 @@ int V_strcasecmp (const char *s1, const char *s2);
|
|||||||
int V_strncasecmp (const char *s1, const char *s2, int n);
|
int V_strncasecmp (const char *s1, const char *s2, int n);
|
||||||
int V_strnicmp (const char *s1, const char *s2, int n);
|
int V_strnicmp (const char *s1, const char *s2, int n);
|
||||||
int V_atoi (const char *str);
|
int V_atoi (const char *str);
|
||||||
|
int64 V_atoi64(const char *str);
|
||||||
|
uint64 V_atoui64(const char *str);
|
||||||
float V_atof (const char *str);
|
float V_atof (const char *str);
|
||||||
char* V_stristr( char* pStr, const char* pSearch );
|
char* V_stristr( char* pStr, const char* pSearch );
|
||||||
const char* V_stristr( const char* pStr, const char* pSearch );
|
const char* V_stristr( const char* pStr, const char* pSearch );
|
||||||
@ -409,6 +411,8 @@ bool V_GenerateUniqueName( char *name, int memsize, const char *prefix, const Na
|
|||||||
#define Q_strncasecmp V_strncasecmp
|
#define Q_strncasecmp V_strncasecmp
|
||||||
#define Q_strnicmp V_strnicmp
|
#define Q_strnicmp V_strnicmp
|
||||||
#define Q_atoi V_atoi
|
#define Q_atoi V_atoi
|
||||||
|
#define Q_atoi64 V_atoi64
|
||||||
|
#define Q_atoui64 V_atoui64
|
||||||
#define Q_atof V_atof
|
#define Q_atof V_atof
|
||||||
#define Q_stristr V_stristr
|
#define Q_stristr V_stristr
|
||||||
#define Q_strnistr V_strnistr
|
#define Q_strnistr V_strnistr
|
||||||
|
|||||||
@ -176,6 +176,7 @@ public:
|
|||||||
short GetShort( );
|
short GetShort( );
|
||||||
unsigned short GetUnsignedShort( );
|
unsigned short GetUnsignedShort( );
|
||||||
int GetInt( );
|
int GetInt( );
|
||||||
|
int64 GetInt64( );
|
||||||
int GetIntHex( );
|
int GetIntHex( );
|
||||||
unsigned int GetUnsignedInt( );
|
unsigned int GetUnsignedInt( );
|
||||||
float GetFloat( );
|
float GetFloat( );
|
||||||
@ -249,6 +250,7 @@ public:
|
|||||||
void PutShort( short s );
|
void PutShort( short s );
|
||||||
void PutUnsignedShort( unsigned short us );
|
void PutUnsignedShort( unsigned short us );
|
||||||
void PutInt( int i );
|
void PutInt( int i );
|
||||||
|
void PutInt64( int64 i );
|
||||||
void PutUnsignedInt( unsigned int u );
|
void PutUnsignedInt( unsigned int u );
|
||||||
void PutFloat( float f );
|
void PutFloat( float f );
|
||||||
void PutDouble( double d );
|
void PutDouble( double d );
|
||||||
@ -700,6 +702,13 @@ inline int CUtlBuffer::GetInt( )
|
|||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline int64 CUtlBuffer::GetInt64( )
|
||||||
|
{
|
||||||
|
int64 i;
|
||||||
|
GetType( i, "%lld" );
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
|
||||||
inline int CUtlBuffer::GetIntHex( )
|
inline int CUtlBuffer::GetIntHex( )
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
@ -920,6 +929,11 @@ inline void CUtlBuffer::PutInt( int i )
|
|||||||
PutType( i, "%d" );
|
PutType( i, "%d" );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void CUtlBuffer::PutInt64( int64 i )
|
||||||
|
{
|
||||||
|
PutType( i, "%llu" );
|
||||||
|
}
|
||||||
|
|
||||||
inline void CUtlBuffer::PutUnsignedInt( unsigned int u )
|
inline void CUtlBuffer::PutUnsignedInt( unsigned int u )
|
||||||
{
|
{
|
||||||
PutType( u, "%u" );
|
PutType( u, "%u" );
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@ -316,13 +316,13 @@ const char *StringAfterPrefixCaseSensitive( const char *str, const char *prefix
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int V_atoi (const char *str)
|
int64 V_atoi64( const char *str )
|
||||||
{
|
{
|
||||||
AssertValidStringPtr( str );
|
AssertValidStringPtr( str );
|
||||||
|
|
||||||
int val;
|
int64 val;
|
||||||
int sign;
|
int64 sign;
|
||||||
int c;
|
int64 c;
|
||||||
|
|
||||||
Assert( str );
|
Assert( str );
|
||||||
if (*str == '-')
|
if (*str == '-')
|
||||||
@ -377,6 +377,63 @@ int V_atoi (const char *str)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint64 V_atoui64( const char *str )
|
||||||
|
{
|
||||||
|
AssertValidStringPtr( str );
|
||||||
|
|
||||||
|
uint64 val;
|
||||||
|
uint64 c;
|
||||||
|
|
||||||
|
Assert( str );
|
||||||
|
|
||||||
|
val = 0;
|
||||||
|
|
||||||
|
//
|
||||||
|
// check for hex
|
||||||
|
//
|
||||||
|
if (str[0] == '0' && (str[1] == 'x' || str[1] == 'X') )
|
||||||
|
{
|
||||||
|
str += 2;
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
c = *str++;
|
||||||
|
if (c >= '0' && c <= '9')
|
||||||
|
val = (val<<4) + c - '0';
|
||||||
|
else if (c >= 'a' && c <= 'f')
|
||||||
|
val = (val<<4) + c - 'a' + 10;
|
||||||
|
else if (c >= 'A' && c <= 'F')
|
||||||
|
val = (val<<4) + c - 'A' + 10;
|
||||||
|
else
|
||||||
|
return val;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// check for character
|
||||||
|
//
|
||||||
|
if (str[0] == '\'')
|
||||||
|
{
|
||||||
|
return str[1];
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// assume decimal
|
||||||
|
//
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
c = *str++;
|
||||||
|
if (c <'0' || c > '9')
|
||||||
|
return val;
|
||||||
|
val = val*10 + c - '0';
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int V_atoi( const char *str )
|
||||||
|
{
|
||||||
|
return (int)V_atoi64( str );
|
||||||
|
}
|
||||||
|
|
||||||
float V_atof (const char *str)
|
float V_atof (const char *str)
|
||||||
{
|
{
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user