From cb40d114abe8a41ed5193e9cc99b06727f497452 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Wed, 26 Feb 2014 22:17:28 +0100 Subject: Fixed a gcc warning in FastNBT.h. --- src/WorldStorage/FastNBT.h | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) (limited to 'src/WorldStorage/FastNBT.h') diff --git a/src/WorldStorage/FastNBT.h b/src/WorldStorage/FastNBT.h index b84eda1a1..a78b610cb 100644 --- a/src/WorldStorage/FastNBT.h +++ b/src/WorldStorage/FastNBT.h @@ -172,8 +172,17 @@ public: inline float GetFloat(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_Float); - Int32 tmp = GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); - return *((float *)&tmp); + + // Cause a compile-time error if sizeof(int) != sizeof(float) + char Check1[sizeof(int) - sizeof(float) + 1]; // sizeof(int) >= sizeof(float) + char Check2[sizeof(float) - sizeof(int) + 1]; // sizeof(float) >= sizeof(int) + UNUSED(Check1); + UNUSED(Check2); + + int i = GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); + float f; + memcpy(&f, &i, sizeof(f)); + return f; } inline double GetDouble(int a_Tag) const -- cgit v1.2.3 From baf2d8892127cd6da9d2f6f2f8d991d617c87800 Mon Sep 17 00:00:00 2001 From: Tiger Wang Date: Wed, 26 Feb 2014 23:29:14 +0000 Subject: Implemented ballistic missiles (fireworks) + Added fireworks --- src/WorldStorage/FastNBT.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/WorldStorage/FastNBT.h') diff --git a/src/WorldStorage/FastNBT.h b/src/WorldStorage/FastNBT.h index a78b610cb..e7e56282f 100644 --- a/src/WorldStorage/FastNBT.h +++ b/src/WorldStorage/FastNBT.h @@ -266,7 +266,7 @@ protected: eTagType m_ItemType; // for TAG_List, the element type } ; - static const int MAX_STACK = 50; // Highliy doubtful that an NBT would be constructed this many levels deep + static const int MAX_STACK = 50; // Highly doubtful that an NBT would be constructed this many levels deep // These two fields emulate a stack. A raw array is used due to speed issues - no reallocations are allowed. sParent m_Stack[MAX_STACK]; -- cgit v1.2.3 From 0aac17874c25a2c1be36a8b5d691331852cec49f Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Fri, 28 Feb 2014 08:31:35 +0100 Subject: Better fix for the 32-bit float reading. --- src/WorldStorage/FastNBT.h | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) (limited to 'src/WorldStorage/FastNBT.h') diff --git a/src/WorldStorage/FastNBT.h b/src/WorldStorage/FastNBT.h index a78b610cb..49f97c458 100644 --- a/src/WorldStorage/FastNBT.h +++ b/src/WorldStorage/FastNBT.h @@ -173,13 +173,14 @@ public: { ASSERT(m_Tags[a_Tag].m_Type == TAG_Float); - // Cause a compile-time error if sizeof(int) != sizeof(float) - char Check1[sizeof(int) - sizeof(float) + 1]; // sizeof(int) >= sizeof(float) - char Check2[sizeof(float) - sizeof(int) + 1]; // sizeof(float) >= sizeof(int) + // Cause a compile-time error if sizeof(float) != 4 + // If your platform produces a compiler error here, you'll need to add code that manually decodes 32-bit floats + char Check1[5 - sizeof(float)]; // sizeof(float) <= 4 + char Check2[sizeof(float) - 3]; // sizeof(float) >= 4 UNUSED(Check1); UNUSED(Check2); - int i = GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); + Int32 i = GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); float f; memcpy(&f, &i, sizeof(f)); return f; -- cgit v1.2.3 From 3991c04d478b0e929faff4ce95fdb53eae67b888 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sat, 1 Mar 2014 02:43:35 +0100 Subject: Improved comments in float size check. --- src/WorldStorage/FastNBT.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/WorldStorage/FastNBT.h') diff --git a/src/WorldStorage/FastNBT.h b/src/WorldStorage/FastNBT.h index 49f97c458..d68ebd54c 100644 --- a/src/WorldStorage/FastNBT.h +++ b/src/WorldStorage/FastNBT.h @@ -175,8 +175,8 @@ public: // Cause a compile-time error if sizeof(float) != 4 // If your platform produces a compiler error here, you'll need to add code that manually decodes 32-bit floats - char Check1[5 - sizeof(float)]; // sizeof(float) <= 4 - char Check2[sizeof(float) - 3]; // sizeof(float) >= 4 + char Check1[5 - sizeof(float)]; // Fails if sizeof(float) > 4 + char Check2[sizeof(float) - 3]; // Fails if sizeof(float) < 4 UNUSED(Check1); UNUSED(Check2); -- cgit v1.2.3 From 2998228e85bb535ea49f3ef0d7314274a72dd9b9 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 2 Mar 2014 08:22:27 +0100 Subject: Added more documentation for FastNBT parser. --- src/WorldStorage/FastNBT.h | 48 +++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 45 insertions(+), 3 deletions(-) (limited to 'src/WorldStorage/FastNBT.h') diff --git a/src/WorldStorage/FastNBT.h b/src/WorldStorage/FastNBT.h index d68ebd54c..01a9ad274 100644 --- a/src/WorldStorage/FastNBT.h +++ b/src/WorldStorage/FastNBT.h @@ -106,6 +106,10 @@ public: /** Parses and contains the parsed data Also implements data accessor functions for tree traversal and value getters The data pointer passed in the constructor is assumed to be valid throughout the object's life. Care must be taken not to initialize from a temporary. +The parser decomposes the input data into a tree of tags that is stored as an array of cFastNBTTag items, +and accessing the tree is done by using the array indices for tags. Each tag stores the indices for its parent, +first child, last child, prev sibling and next sibling, a value of -1 indicates that the indice is not valid. +Each primitive tag also stores the length of the contained data, in bytes. */ class cParsedNBT { @@ -114,13 +118,32 @@ public: bool IsValid(void) const {return m_IsValid; } + /** Returns the root tag of the hierarchy. */ int GetRoot(void) const {return 0; } + + /** Returns the first child of the specified tag, or -1 if none / not applicable. */ int GetFirstChild (int a_Tag) const { return m_Tags[a_Tag].m_FirstChild; } + + /** Returns the last child of the specified tag, or -1 if none / not applicable. */ int GetLastChild (int a_Tag) const { return m_Tags[a_Tag].m_LastChild; } + + /** Returns the next sibling of the specified tag, or -1 if none. */ int GetNextSibling(int a_Tag) const { return m_Tags[a_Tag].m_NextSibling; } + + /** Returns the previous sibling of the specified tag, or -1 if none. */ int GetPrevSibling(int a_Tag) const { return m_Tags[a_Tag].m_PrevSibling; } - int GetDataLength (int a_Tag) const { return m_Tags[a_Tag].m_DataLength; } + + /** Returns the length of the tag's data, in bytes. + Not valid for Compound or List tags! */ + int GetDataLength (int a_Tag) const + { + ASSERT(m_Tags[a_Tag].m_Type != TAG_List); + ASSERT(m_Tags[a_Tag].m_Type != TAG_Compound); + return m_Tags[a_Tag].m_DataLength; + } + /** Returns the data stored in this tag. + Not valid for Compound or List tags! */ const char * GetData(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type != TAG_List); @@ -128,47 +151,56 @@ public: return m_Data + m_Tags[a_Tag].m_DataStart; } + /** Returns the direct child tag of the specified name, or -1 if no such tag. */ int FindChildByName(int a_Tag, const AString & a_Name) const { return FindChildByName(a_Tag, a_Name.c_str(), a_Name.length()); } + /** Returns the direct child tag of the specified name, or -1 if no such tag. */ int FindChildByName(int a_Tag, const char * a_Name, size_t a_NameLength = 0) const; - int FindTagByPath (int a_Tag, const AString & a_Path) const; + + /** Returns the child tag of the specified path (Name1\Name2\Name3...), or -1 if no such tag. */ + int FindTagByPath(int a_Tag, const AString & a_Path) const; eTagType GetType(int a_Tag) const { return m_Tags[a_Tag].m_Type; } - /// Returns the children type for a list tag; undefined on other tags. If list empty, returns TAG_End + /** Returns the children type for a List tag; undefined on other tags. If list empty, returns TAG_End. */ eTagType GetChildrenType(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_List); return (m_Tags[a_Tag].m_FirstChild < 0) ? TAG_End : m_Tags[m_Tags[a_Tag].m_FirstChild].m_Type; } + /** Returns the value stored in a Byte tag. Not valid for any other tag type. */ inline unsigned char GetByte(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_Byte); return (unsigned char)(m_Data[m_Tags[a_Tag].m_DataStart]); } + /** Returns the value stored in a Short tag. Not valid for any other tag type. */ inline Int16 GetShort(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_Short); return GetBEShort(m_Data + m_Tags[a_Tag].m_DataStart); } + /** Returns the value stored in an Int tag. Not valid for any other tag type. */ inline Int32 GetInt(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_Int); return GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); } + /** Returns the value stored in a Long tag. Not valid for any other tag type. */ inline Int64 GetLong(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_Long); return NetworkToHostLong8(m_Data + m_Tags[a_Tag].m_DataStart); } + /** Returns the value stored in a Float tag. Not valid for any other tag type. */ inline float GetFloat(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_Float); @@ -186,12 +218,21 @@ public: return f; } + /** Returns the value stored in a Double tag. Not valid for any other tag type. */ inline double GetDouble(int a_Tag) const { + // Cause a compile-time error if sizeof(double) != 8 + // If your platform produces a compiler error here, you'll need to add code that manually decodes 64-bit doubles + char Check1[9 - sizeof(double)]; // Fails if sizeof(double) > 8 + char Check2[sizeof(double) - 7]; // Fails if sizeof(double) < 8 + UNUSED(Check1); + UNUSED(Check2); + ASSERT(m_Tags[a_Tag].m_Type == TAG_Double); return NetworkToHostDouble8(m_Data + m_Tags[a_Tag].m_DataStart); } + /** Returns the value stored in a String tag. Not valid for any other tag type. */ inline AString GetString(int a_Tag) const { ASSERT(m_Tags[a_Tag].m_Type == TAG_String); @@ -200,6 +241,7 @@ public: return res; } + /** Returns the tag's name. For tags that are not named, returns an empty string. */ inline AString GetName(int a_Tag) const { AString res; -- cgit v1.2.3 From 396abb5db6e46f214e27e4dba1099490bf03bb0a Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Fri, 4 Apr 2014 10:19:21 +0200 Subject: Fixed silly Clang's warnings in FastNBT. --- src/WorldStorage/FastNBT.h | 56 +++++++++++++++++++++++----------------------- 1 file changed, 28 insertions(+), 28 deletions(-) (limited to 'src/WorldStorage/FastNBT.h') diff --git a/src/WorldStorage/FastNBT.h b/src/WorldStorage/FastNBT.h index 1b8b09c21..5e5af3ca3 100644 --- a/src/WorldStorage/FastNBT.h +++ b/src/WorldStorage/FastNBT.h @@ -122,33 +122,33 @@ public: int GetRoot(void) const {return 0; } /** Returns the first child of the specified tag, or -1 if none / not applicable. */ - int GetFirstChild (int a_Tag) const { return m_Tags[a_Tag].m_FirstChild; } + int GetFirstChild (int a_Tag) const { return m_Tags[(size_t)a_Tag].m_FirstChild; } /** Returns the last child of the specified tag, or -1 if none / not applicable. */ - int GetLastChild (int a_Tag) const { return m_Tags[a_Tag].m_LastChild; } + int GetLastChild (int a_Tag) const { return m_Tags[(size_t)a_Tag].m_LastChild; } /** Returns the next sibling of the specified tag, or -1 if none. */ - int GetNextSibling(int a_Tag) const { return m_Tags[a_Tag].m_NextSibling; } + int GetNextSibling(int a_Tag) const { return m_Tags[(size_t)a_Tag].m_NextSibling; } /** Returns the previous sibling of the specified tag, or -1 if none. */ - int GetPrevSibling(int a_Tag) const { return m_Tags[a_Tag].m_PrevSibling; } + int GetPrevSibling(int a_Tag) const { return m_Tags[(size_t)a_Tag].m_PrevSibling; } /** Returns the length of the tag's data, in bytes. Not valid for Compound or List tags! */ int GetDataLength (int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type != TAG_List); - ASSERT(m_Tags[a_Tag].m_Type != TAG_Compound); - return m_Tags[a_Tag].m_DataLength; + ASSERT(m_Tags[(size_t)a_Tag].m_Type != TAG_List); + ASSERT(m_Tags[(size_t)a_Tag].m_Type != TAG_Compound); + return m_Tags[(size_t)a_Tag].m_DataLength; } /** Returns the data stored in this tag. Not valid for Compound or List tags! */ const char * GetData(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type != TAG_List); - ASSERT(m_Tags[a_Tag].m_Type != TAG_Compound); - return m_Data + m_Tags[a_Tag].m_DataStart; + ASSERT(m_Tags[(size_t)a_Tag].m_Type != TAG_List); + ASSERT(m_Tags[(size_t)a_Tag].m_Type != TAG_Compound); + return m_Data + m_Tags[(size_t)a_Tag].m_DataStart; } /** Returns the direct child tag of the specified name, or -1 if no such tag. */ @@ -163,47 +163,47 @@ public: /** Returns the child tag of the specified path (Name1\Name2\Name3...), or -1 if no such tag. */ int FindTagByPath(int a_Tag, const AString & a_Path) const; - eTagType GetType(int a_Tag) const { return m_Tags[a_Tag].m_Type; } + eTagType GetType(int a_Tag) const { return m_Tags[(size_t)a_Tag].m_Type; } /** Returns the children type for a List tag; undefined on other tags. If list empty, returns TAG_End. */ eTagType GetChildrenType(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_List); - return (m_Tags[a_Tag].m_FirstChild < 0) ? TAG_End : m_Tags[m_Tags[a_Tag].m_FirstChild].m_Type; + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_List); + return (m_Tags[(size_t)a_Tag].m_FirstChild < 0) ? TAG_End : m_Tags[(size_t)m_Tags[(size_t)a_Tag].m_FirstChild].m_Type; } /** Returns the value stored in a Byte tag. Not valid for any other tag type. */ inline unsigned char GetByte(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_Byte); - return (unsigned char)(m_Data[m_Tags[a_Tag].m_DataStart]); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_Byte); + return (unsigned char)(m_Data[(size_t)m_Tags[(size_t)a_Tag].m_DataStart]); } /** Returns the value stored in a Short tag. Not valid for any other tag type. */ inline Int16 GetShort(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_Short); - return GetBEShort(m_Data + m_Tags[a_Tag].m_DataStart); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_Short); + return GetBEShort(m_Data + m_Tags[(size_t)a_Tag].m_DataStart); } /** Returns the value stored in an Int tag. Not valid for any other tag type. */ inline Int32 GetInt(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_Int); - return GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_Int); + return GetBEInt(m_Data + m_Tags[(size_t)a_Tag].m_DataStart); } /** Returns the value stored in a Long tag. Not valid for any other tag type. */ inline Int64 GetLong(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_Long); - return NetworkToHostLong8(m_Data + m_Tags[a_Tag].m_DataStart); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_Long); + return NetworkToHostLong8(m_Data + m_Tags[(size_t)a_Tag].m_DataStart); } /** Returns the value stored in a Float tag. Not valid for any other tag type. */ inline float GetFloat(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_Float); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_Float); // Cause a compile-time error if sizeof(float) != 4 // If your platform produces a compiler error here, you'll need to add code that manually decodes 32-bit floats @@ -212,7 +212,7 @@ public: UNUSED(Check1); UNUSED(Check2); - Int32 i = GetBEInt(m_Data + m_Tags[a_Tag].m_DataStart); + Int32 i = GetBEInt(m_Data + m_Tags[(size_t)a_Tag].m_DataStart); float f; memcpy(&f, &i, sizeof(f)); return f; @@ -228,16 +228,16 @@ public: UNUSED(Check1); UNUSED(Check2); - ASSERT(m_Tags[a_Tag].m_Type == TAG_Double); - return NetworkToHostDouble8(m_Data + m_Tags[a_Tag].m_DataStart); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_Double); + return NetworkToHostDouble8(m_Data + m_Tags[(size_t)a_Tag].m_DataStart); } /** Returns the value stored in a String tag. Not valid for any other tag type. */ inline AString GetString(int a_Tag) const { - ASSERT(m_Tags[a_Tag].m_Type == TAG_String); + ASSERT(m_Tags[(size_t)a_Tag].m_Type == TAG_String); AString res; - res.assign(m_Data + m_Tags[a_Tag].m_DataStart, m_Tags[a_Tag].m_DataLength); + res.assign(m_Data + m_Tags[(size_t)a_Tag].m_DataStart, m_Tags[(size_t)a_Tag].m_DataLength); return res; } @@ -245,7 +245,7 @@ public: inline AString GetName(int a_Tag) const { AString res; - res.assign(m_Data + m_Tags[a_Tag].m_NameStart, m_Tags[a_Tag].m_NameLength); + res.assign(m_Data + m_Tags[(size_t)a_Tag].m_NameStart, m_Tags[(size_t)a_Tag].m_NameLength); return res; } -- cgit v1.2.3