Counter Strike : Global Offensive Source Code
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

201 lines
6.5 KiB

  1. #ifndef SCHEMA_H_
  2. #define SCHEMA_H_
  3. #include "basetypes.h" // for 'schema' define
  4. #include "resourcefile/resourcestream.h"
  5. #include "resourcefile/resourcefile.h"
  6. #include "resourcefile/resourcetype.h"
  7. class CResourceStructIntrospection;
  8. #ifdef COMPILING_SCHEMA
  9. #define INTERNAL_SCHEMA_CLASS_MARKER_DATA `__schema_class_marker_data__`
  10. #define INTERNAL_SCHEMA_CLASS_MARKER_VIRTUAL `__schema_class_marker_virtual__`
  11. #define INTERNAL_SCHEMA_CLASS_MARKER_ABSTRACT `__schema_class_marker_abstract__`
  12. #define INTERNAL_SCHEMA_CLASS_MARKER_SIMPLE `__schema_class_marker_simple__`
  13. #else
  14. #define INTERNAL_SCHEMA_CLASS_MARKER_DATA
  15. #define INTERNAL_SCHEMA_CLASS_MARKER_VIRTUAL
  16. #define INTERNAL_SCHEMA_CLASS_MARKER_ABSTRACT
  17. #define INTERNAL_SCHEMA_CLASS_MARKER_SIMPLE
  18. #endif
  19. //////////////////////////////////////////////////////////////////////////
  20. //////////////////////////////////////////////////////////////////////////
  21. //////////////////////////////////////////////////////////////////////////
  22. // Pay no attention to the code behind the curtain
  23. #define DECLARE_SCHEMA_CLASS_HELPER( _className, _bindingType ) \
  24. friend class _bindingType < _className >; \
  25. friend class CSchemaVerificationFor##_className; \
  26. public: \
  27. static _bindingType < _className > s_##_className##SchemaBinding; \
  28. static const CResourceStructIntrospection *Schema_StaticBinding( ) { return (s_##_className##SchemaBinding).GetIntrospection(); }
  29. #define DECLARE_SCHEMA_VIRTUAL_CLASS_HELPER( _className, _bindingType ) \
  30. DECLARE_SCHEMA_CLASS_HELPER( _className, _bindingType ); \
  31. public: \
  32. virtual const CSchemaClassBindingBase *Schema_GetBinding( ) const { return &s_##_className##SchemaBinding; } \
  33. const CResourceStructIntrospection *Schema_GetIntrospection( ) const { return Schema_GetBinding()->GetIntrospection(); }
  34. #define DECLARE_SCHEMA_PLAIN_CLASS_HELPER( _className, _bindingType ) \
  35. DECLARE_SCHEMA_CLASS_HELPER( _className, _bindingType ); \
  36. public: \
  37. const CSchemaClassBindingBase *Schema_GetBinding( ) const { return &s_##_className##SchemaBinding; } \
  38. const CResourceStructIntrospection *Schema_GetIntrospection( ) const { return Schema_GetBinding()->GetIntrospection(); }
  39. #define DEFINE_SCHEMA_CLASS_HELPER( _className, _bindingType ) \
  40. _bindingType < _className > _className :: s_##_className##SchemaBinding( #_className );
  41. //////////////////////////////////////////////////////////////////////////
  42. //////////////////////////////////////////////////////////////////////////
  43. //////////////////////////////////////////////////////////////////////////
  44. // Data Classes (no vtable)
  45. #define DECLARE_SCHEMA_DATA_CLASS( _className ) \
  46. INTERNAL_SCHEMA_CLASS_MARKER_DATA \
  47. DECLARE_SCHEMA_PLAIN_CLASS_HELPER( _className, CSchemaClassBinding )
  48. #define DEFINE_SCHEMA_DATA_CLASS( _className ) DEFINE_SCHEMA_CLASS_HELPER( _className, CSchemaClassBinding )
  49. ///////////////////////////////////////
  50. // Virtual Classes
  51. #define DECLARE_SCHEMA_VIRTUAL_CLASS( _className ) \
  52. INTERNAL_SCHEMA_CLASS_MARKER_VIRTUAL \
  53. DECLARE_SCHEMA_VIRTUAL_CLASS_HELPER( _className, CSchemaClassBinding )
  54. #define DEFINE_SCHEMA_VIRTUAL_CLASS( _className ) DEFINE_SCHEMA_CLASS_HELPER( _className, CSchemaClassBinding )
  55. ///////////////////////////////////////
  56. // Abstract Classes
  57. #define DECLARE_SCHEMA_ABSTRACT_CLASS( _className ) \
  58. INTERNAL_SCHEMA_CLASS_MARKER_ABSTRACT \
  59. DECLARE_SCHEMA_VIRTUAL_CLASS_HELPER( _className, CSchemaAbstractClassBinding )
  60. #define DEFINE_SCHEMA_ABSTRACT_CLASS( _className ) DEFINE_SCHEMA_CLASS_HELPER( _className, CSchemaAbstractClassBinding )
  61. ///////////////////////////////////////
  62. // Simple Classes
  63. // For classes where you don't want to use a DEFINE_ macro
  64. // - Only works for classes with no vtable.
  65. // - If unserialized, it will be memzeroed rather than constructed
  66. #define DECLARE_SCHEMA_SIMPLE_CLASS( _name ) \
  67. INTERNAL_SCHEMA_CLASS_MARKER_SIMPLE \
  68. const CResourceStructIntrospection *Schema_GetIntrospection( ) const { return g_pResourceSystem->FindStructIntrospection( #_name ); }
  69. //////////////////////////////////////////////////////////////////////////
  70. //////////////////////////////////////////////////////////////////////////
  71. //////////////////////////////////////////////////////////////////////////
  72. /*
  73. template<class T> void Serialize( const T* pObj )
  74. {
  75. const CResourceStructIntrospection *pIntrospection = pObj ? pObj->Schema_GetIntrospection() : NULL;
  76. SerializeGeneric( (const void*)pObj, pIntrospection );
  77. }
  78. template<class T> void Print( const T* pObj )
  79. {
  80. const CResourceStructIntrospection *pIntrospection = pObj ? pObj->Schema_GetIntrospection() : NULL;
  81. PrintGeneric( (const void*)pObj, pIntrospection );
  82. }
  83. void SerializeGeneric( const void *pData, const CResourceStructIntrospection *pIntrospection );
  84. void PrintGeneric( const void *pData, const CResourceStructIntrospection *pIntrospection );
  85. */
  86. //////////////////////////////////////////////////////////////////////////
  87. class CSchemaClassBindingBase
  88. {
  89. public:
  90. CSchemaClassBindingBase( const char* pClassName ):
  91. m_pClassName(pClassName),
  92. m_pIntrospection(NULL)
  93. {
  94. // Hook into the local class binding list
  95. m_pNextBinding = sm_pClassBindingList;
  96. sm_pClassBindingList = this;
  97. }
  98. inline const char* GetName() const
  99. {
  100. return m_pClassName;
  101. }
  102. virtual void ConstructInPlace( void* pMemory ) const = 0;
  103. virtual void DestructInPlace( void* pMemory ) const = 0;
  104. virtual int GetSize() const = 0;
  105. const CResourceStructIntrospection *GetIntrospection() const;
  106. static void Install();
  107. protected:
  108. const char *m_pClassName;
  109. mutable const CResourceStructIntrospection *m_pIntrospection;
  110. CSchemaClassBindingBase *m_pNextBinding;
  111. static CSchemaClassBindingBase *sm_pClassBindingList;
  112. };
  113. template<class TSchemaClass> class CSchemaClassBinding: public CSchemaClassBindingBase
  114. {
  115. public:
  116. CSchemaClassBinding( const char* pClassName ):
  117. CSchemaClassBindingBase( pClassName )
  118. {
  119. // nop
  120. }
  121. virtual void ConstructInPlace( void* pMemory ) const
  122. {
  123. new(pMemory) TSchemaClass;
  124. }
  125. virtual void DestructInPlace( void* pMemory ) const
  126. {
  127. ((TSchemaClass*)(pMemory))->~TSchemaClass();
  128. }
  129. virtual int GetSize() const
  130. {
  131. return sizeof(TSchemaClass);
  132. }
  133. };
  134. template<class TSchemaClass> class CSchemaAbstractClassBinding: public CSchemaClassBindingBase
  135. {
  136. public:
  137. CSchemaAbstractClassBinding( const char* pClassName ):
  138. CSchemaClassBindingBase(pClassName)
  139. {
  140. // nop
  141. }
  142. virtual void ConstructInPlace( void* pMemory ) const
  143. {
  144. Error( "Cannot construct abstract class %s\n", m_pClassName );
  145. }
  146. virtual void DestructInPlace( void* pMemory ) const
  147. {
  148. Error( "Cannot destruct abstract class %s\n", m_pClassName );
  149. }
  150. virtual int GetSize() const
  151. {
  152. return sizeof(TSchemaClass);
  153. }
  154. };
  155. #endif