Browse Source

Restoring authorship annotation for <qkrorlqr@yandex-team.ru>. Commit 2 of 2.

qkrorlqr 3 years ago
parent
commit
eec632e483

+ 6 - 6
build/rules/kikimr.policy

@@ -71,19 +71,19 @@ ALLOW .* -> kikimr/public/lib/ydb_cli
 
 ALLOW .* -> kikimr/yndx/api
 
-ALLOW cloud/blockstore -> kikimr/blockstore 
-ALLOW cloud/blockstore -> kikimr/core 
+ALLOW cloud/blockstore -> kikimr/blockstore
+ALLOW cloud/blockstore -> kikimr/core
 ALLOW cloud/blockstore -> kikimr/driver_lib/run
 ALLOW cloud/blockstore -> kikimr/public/lib/deprecated/kicli
-ALLOW cloud/blockstore -> kikimr/yndx 
+ALLOW cloud/blockstore -> kikimr/yndx
 
 ALLOW cloud/filestore -> kikimr/core
 ALLOW cloud/filestore -> kikimr/driver_lib/run
 ALLOW cloud/filestore -> kikimr/public/lib/deprecated/kicli
-ALLOW cloud/filestore -> kikimr/yndx 
+ALLOW cloud/filestore -> kikimr/yndx
+
+ALLOW cloud/storage -> kikimr/core
 
-ALLOW cloud/storage -> kikimr/core 
- 
 ALLOW cloud/kms/benchcrypto/cpp -> kikimr/core/blobstorage/crypto
 
 ALLOW rtmapreduce -> kikimr/yf

+ 1 - 1
contrib/libs/protobuf/src/google/protobuf/io/coded_stream.cc

@@ -813,7 +813,7 @@ uint8* EpsCopyOutputStream::Next() {
       buffer_end_ = ptr;
       end_ = buffer_ + size;
       return buffer_;
-    } 
+    }
   } else {
     std::memcpy(buffer_, end_, kSlopBytes);
     buffer_end_ = end_;

+ 158 - 158
contrib/libs/rapidjson/CHANGELOG.md

@@ -1,158 +1,158 @@
-# Change Log 
-All notable changes to this project will be documented in this file. 
-This project adheres to [Semantic Versioning](http://semver.org/). 
- 
-## [Unreleased] 
- 
-## 1.1.0 - 2016-08-25 
- 
-### Added 
-* Add GenericDocument ctor overload to specify JSON type (#369) 
-* Add FAQ (#372, #373, #374, #376) 
-* Add forward declaration header `fwd.h` 
-* Add @PlatformIO Library Registry manifest file (#400) 
-* Implement assignment operator for BigInteger (#404) 
-* Add comments support (#443) 
-* Adding coapp definition (#460) 
-* documenttest.cpp: EXPECT_THROW when checking empty allocator (470) 
-* GenericDocument: add implicit conversion to ParseResult (#480) 
-* Use <wchar.h> with C++ linkage on Windows ARM (#485) 
-* Detect little endian for Microsoft ARM targets  
-* Check Nan/Inf when writing a double (#510) 
-* Add JSON Schema Implementation (#522) 
-* Add iostream wrapper (#530) 
-* Add Jsonx example for converting JSON into JSONx (a XML format) (#531) 
-* Add optional unresolvedTokenIndex parameter to Pointer::Get() (#532) 
-* Add encoding validation option for Writer/PrettyWriter (#534) 
-* Add Writer::SetMaxDecimalPlaces() (#536) 
-* Support {0, } and {0, m} in Regex (#539) 
-* Add Value::Get/SetFloat(), Value::IsLossLessFloat/Double() (#540) 
-* Add stream position check to reader unit tests (#541) 
-* Add Templated accessors and range-based for (#542) 
-* Add (Pretty)Writer::RawValue() (#543) 
-* Add Document::Parse(std::string), Document::Parse(const char*, size_t length) and related APIs. (#553) 
-* Add move constructor for GenericSchemaDocument (#554) 
-* Add VS2010 and VS2015 to AppVeyor CI (#555) 
-* Add parse-by-parts example (#556, #562) 
-* Support parse number as string (#564, #589) 
-* Add kFormatSingleLineArray for PrettyWriter (#577) 
-* Added optional support for trailing commas (#584) 
-* Added filterkey and filterkeydom examples (#615) 
-* Added npm docs (#639) 
-* Allow options for writing and parsing NaN/Infinity (#641) 
-* Add std::string overload to PrettyWriter::Key() when RAPIDJSON_HAS_STDSTRING is defined (#698) 
- 
-### Fixed 
-* Fix gcc/clang/vc warnings (#350, #394, #397, #444, #447, #473, #515, #582, #589, #595, #667) 
-* Fix documentation (#482, #511, #550, #557, #614, #635, #660) 
-* Fix emscripten alignment issue (#535) 
-* Fix missing allocator to uses of AddMember in document (#365) 
-* CMake will no longer complain that the minimum CMake version is not specified (#501) 
-* Make it usable with old VC8 (VS2005) (#383) 
-* Prohibit C++11 move from Document to Value (#391) 
-* Try to fix incorrect 64-bit alignment (#419) 
-* Check return of fwrite to avoid warn_unused_result build failures (#421) 
-* Fix UB in GenericDocument::ParseStream (#426) 
-* Keep Document value unchanged on parse error (#439) 
-* Add missing return statement (#450) 
-* Fix Document::Parse(const Ch*) for transcoding (#478) 
-* encodings.h: fix typo in preprocessor condition (#495) 
-* Custom Microsoft headers are necessary only for Visual Studio 2012 and lower (#559) 
-* Fix memory leak for invalid regex (26e69ffde95ba4773ab06db6457b78f308716f4b) 
-* Fix a bug in schema minimum/maximum keywords for 64-bit integer (e7149d665941068ccf8c565e77495521331cf390) 
-* Fix a crash bug in regex (#605) 
-* Fix schema "required" keyword cannot handle duplicated keys (#609) 
-* Fix cmake CMP0054 warning (#612) 
-* Added missing include guards in istreamwrapper.h and ostreamwrapper.h (#634) 
-* Fix undefined behaviour (#646) 
-* Fix buffer overrun using PutN (#673) 
-* Fix rapidjson::value::Get<std::string>() may returns wrong data (#681) 
-* Add Flush() for all value types (#689) 
-* Handle malloc() fail in PoolAllocator (#691) 
-* Fix builds on x32 platform. #703 
- 
-### Changed 
-* Clarify problematic JSON license (#392) 
-* Move Travis to container based infrastructure (#504, #558) 
-* Make whitespace array more compact (#513) 
-* Optimize Writer::WriteString() with SIMD (#544) 
-* x86-64 48-bit pointer optimization for GenericValue (#546) 
-* Define RAPIDJSON_HAS_CXX11_RVALUE_REFS directly in clang (#617) 
-* Make GenericSchemaDocument constructor explicit (#674) 
-* Optimize FindMember when use std::string (#690) 
- 
-## [1.0.2] - 2015-05-14 
- 
-### Added 
-* Add Value::XXXMember(...) overloads for std::string (#335) 
- 
-### Fixed 
-* Include rapidjson.h for all internal/error headers. 
-* Parsing some numbers incorrectly in full-precision mode (`kFullPrecisionParseFlag`) (#342) 
-* Fix some numbers parsed incorrectly (#336) 
-* Fix alignment of 64bit platforms (#328) 
-* Fix MemoryPoolAllocator::Clear() to clear user-buffer (0691502573f1afd3341073dd24b12c3db20fbde4) 
- 
-### Changed 
-* CMakeLists for include as a thirdparty in projects (#334, #337) 
-* Change Document::ParseStream() to use stack allocator for Reader (ffbe38614732af8e0b3abdc8b50071f386a4a685)  
- 
-## [1.0.1] - 2015-04-25 
- 
-### Added 
-* Changelog following [Keep a CHANGELOG](https://github.com/olivierlacan/keep-a-changelog) suggestions. 
- 
-### Fixed 
-* Parsing of some numbers (e.g. "1e-00011111111111") causing assertion (#314). 
-* Visual C++ 32-bit compilation error in `diyfp.h` (#317). 
- 
-## [1.0.0] - 2015-04-22 
- 
-### Added 
-* 100% [Coverall](https://coveralls.io/r/miloyip/rapidjson?branch=master) coverage. 
-* Version macros (#311) 
- 
-### Fixed 
-* A bug in trimming long number sequence (4824f12efbf01af72b8cb6fc96fae7b097b73015). 
-* Double quote in unicode escape (#288). 
-* Negative zero roundtrip (double only) (#289). 
-* Standardize behavior of `memcpy()` and `malloc()` (0c5c1538dcfc7f160e5a4aa208ddf092c787be5a, #305, 0e8bbe5e3ef375e7f052f556878be0bd79e9062d). 
- 
-### Removed 
-* Remove an invalid `Document::ParseInsitu()` API (e7f1c6dd08b522cfcf9aed58a333bd9a0c0ccbeb). 
- 
-## 1.0-beta - 2015-04-8 
- 
-### Added 
-* RFC 7159 (#101) 
-* Optional Iterative Parser (#76) 
-* Deep-copy values (#20) 
-* Error code and message (#27) 
-* ASCII Encoding (#70) 
-* `kParseStopWhenDoneFlag` (#83) 
-* `kParseFullPrecisionFlag` (881c91d696f06b7f302af6d04ec14dd08db66ceb) 
-* Add `Key()` to handler concept (#134) 
-* C++11 compatibility and support (#128) 
-* Optimized number-to-string and vice versa conversions (#137, #80) 
-* Short-String Optimization (#131) 
-* Local stream optimization by traits (#32) 
-* Travis & Appveyor Continuous Integration, with Valgrind verification (#24, #242) 
-* Redo all documentation (English, Simplified Chinese) 
- 
-### Changed 
-* Copyright ownership transfered to THL A29 Limited (a Tencent company). 
-* Migrating from Premake to CMAKE (#192) 
-* Resolve all warning reports 
- 
-### Removed 
-* Remove other JSON libraries for performance comparison (#180) 
- 
-## 0.11 - 2012-11-16 
- 
-## 0.1 - 2011-11-18 
- 
-[Unreleased]: https://github.com/miloyip/rapidjson/compare/v1.1.0...HEAD 
-[1.1.0]: https://github.com/miloyip/rapidjson/compare/v1.0.2...v1.1.0 
-[1.0.2]: https://github.com/miloyip/rapidjson/compare/v1.0.1...v1.0.2 
-[1.0.1]: https://github.com/miloyip/rapidjson/compare/v1.0.0...v1.0.1 
-[1.0.0]: https://github.com/miloyip/rapidjson/compare/v1.0-beta...v1.0.0 
+# Change Log
+All notable changes to this project will be documented in this file.
+This project adheres to [Semantic Versioning](http://semver.org/).
+
+## [Unreleased]
+
+## 1.1.0 - 2016-08-25
+
+### Added
+* Add GenericDocument ctor overload to specify JSON type (#369)
+* Add FAQ (#372, #373, #374, #376)
+* Add forward declaration header `fwd.h`
+* Add @PlatformIO Library Registry manifest file (#400)
+* Implement assignment operator for BigInteger (#404)
+* Add comments support (#443)
+* Adding coapp definition (#460)
+* documenttest.cpp: EXPECT_THROW when checking empty allocator (470)
+* GenericDocument: add implicit conversion to ParseResult (#480)
+* Use <wchar.h> with C++ linkage on Windows ARM (#485)
+* Detect little endian for Microsoft ARM targets 
+* Check Nan/Inf when writing a double (#510)
+* Add JSON Schema Implementation (#522)
+* Add iostream wrapper (#530)
+* Add Jsonx example for converting JSON into JSONx (a XML format) (#531)
+* Add optional unresolvedTokenIndex parameter to Pointer::Get() (#532)
+* Add encoding validation option for Writer/PrettyWriter (#534)
+* Add Writer::SetMaxDecimalPlaces() (#536)
+* Support {0, } and {0, m} in Regex (#539)
+* Add Value::Get/SetFloat(), Value::IsLossLessFloat/Double() (#540)
+* Add stream position check to reader unit tests (#541)
+* Add Templated accessors and range-based for (#542)
+* Add (Pretty)Writer::RawValue() (#543)
+* Add Document::Parse(std::string), Document::Parse(const char*, size_t length) and related APIs. (#553)
+* Add move constructor for GenericSchemaDocument (#554)
+* Add VS2010 and VS2015 to AppVeyor CI (#555)
+* Add parse-by-parts example (#556, #562)
+* Support parse number as string (#564, #589)
+* Add kFormatSingleLineArray for PrettyWriter (#577)
+* Added optional support for trailing commas (#584)
+* Added filterkey and filterkeydom examples (#615)
+* Added npm docs (#639)
+* Allow options for writing and parsing NaN/Infinity (#641)
+* Add std::string overload to PrettyWriter::Key() when RAPIDJSON_HAS_STDSTRING is defined (#698)
+
+### Fixed
+* Fix gcc/clang/vc warnings (#350, #394, #397, #444, #447, #473, #515, #582, #589, #595, #667)
+* Fix documentation (#482, #511, #550, #557, #614, #635, #660)
+* Fix emscripten alignment issue (#535)
+* Fix missing allocator to uses of AddMember in document (#365)
+* CMake will no longer complain that the minimum CMake version is not specified (#501)
+* Make it usable with old VC8 (VS2005) (#383)
+* Prohibit C++11 move from Document to Value (#391)
+* Try to fix incorrect 64-bit alignment (#419)
+* Check return of fwrite to avoid warn_unused_result build failures (#421)
+* Fix UB in GenericDocument::ParseStream (#426)
+* Keep Document value unchanged on parse error (#439)
+* Add missing return statement (#450)
+* Fix Document::Parse(const Ch*) for transcoding (#478)
+* encodings.h: fix typo in preprocessor condition (#495)
+* Custom Microsoft headers are necessary only for Visual Studio 2012 and lower (#559)
+* Fix memory leak for invalid regex (26e69ffde95ba4773ab06db6457b78f308716f4b)
+* Fix a bug in schema minimum/maximum keywords for 64-bit integer (e7149d665941068ccf8c565e77495521331cf390)
+* Fix a crash bug in regex (#605)
+* Fix schema "required" keyword cannot handle duplicated keys (#609)
+* Fix cmake CMP0054 warning (#612)
+* Added missing include guards in istreamwrapper.h and ostreamwrapper.h (#634)
+* Fix undefined behaviour (#646)
+* Fix buffer overrun using PutN (#673)
+* Fix rapidjson::value::Get<std::string>() may returns wrong data (#681)
+* Add Flush() for all value types (#689)
+* Handle malloc() fail in PoolAllocator (#691)
+* Fix builds on x32 platform. #703
+
+### Changed
+* Clarify problematic JSON license (#392)
+* Move Travis to container based infrastructure (#504, #558)
+* Make whitespace array more compact (#513)
+* Optimize Writer::WriteString() with SIMD (#544)
+* x86-64 48-bit pointer optimization for GenericValue (#546)
+* Define RAPIDJSON_HAS_CXX11_RVALUE_REFS directly in clang (#617)
+* Make GenericSchemaDocument constructor explicit (#674)
+* Optimize FindMember when use std::string (#690)
+
+## [1.0.2] - 2015-05-14
+
+### Added
+* Add Value::XXXMember(...) overloads for std::string (#335)
+
+### Fixed
+* Include rapidjson.h for all internal/error headers.
+* Parsing some numbers incorrectly in full-precision mode (`kFullPrecisionParseFlag`) (#342)
+* Fix some numbers parsed incorrectly (#336)
+* Fix alignment of 64bit platforms (#328)
+* Fix MemoryPoolAllocator::Clear() to clear user-buffer (0691502573f1afd3341073dd24b12c3db20fbde4)
+
+### Changed
+* CMakeLists for include as a thirdparty in projects (#334, #337)
+* Change Document::ParseStream() to use stack allocator for Reader (ffbe38614732af8e0b3abdc8b50071f386a4a685) 
+
+## [1.0.1] - 2015-04-25
+
+### Added
+* Changelog following [Keep a CHANGELOG](https://github.com/olivierlacan/keep-a-changelog) suggestions.
+
+### Fixed
+* Parsing of some numbers (e.g. "1e-00011111111111") causing assertion (#314).
+* Visual C++ 32-bit compilation error in `diyfp.h` (#317).
+
+## [1.0.0] - 2015-04-22
+
+### Added
+* 100% [Coverall](https://coveralls.io/r/miloyip/rapidjson?branch=master) coverage.
+* Version macros (#311)
+
+### Fixed
+* A bug in trimming long number sequence (4824f12efbf01af72b8cb6fc96fae7b097b73015).
+* Double quote in unicode escape (#288).
+* Negative zero roundtrip (double only) (#289).
+* Standardize behavior of `memcpy()` and `malloc()` (0c5c1538dcfc7f160e5a4aa208ddf092c787be5a, #305, 0e8bbe5e3ef375e7f052f556878be0bd79e9062d).
+
+### Removed
+* Remove an invalid `Document::ParseInsitu()` API (e7f1c6dd08b522cfcf9aed58a333bd9a0c0ccbeb).
+
+## 1.0-beta - 2015-04-8
+
+### Added
+* RFC 7159 (#101)
+* Optional Iterative Parser (#76)
+* Deep-copy values (#20)
+* Error code and message (#27)
+* ASCII Encoding (#70)
+* `kParseStopWhenDoneFlag` (#83)
+* `kParseFullPrecisionFlag` (881c91d696f06b7f302af6d04ec14dd08db66ceb)
+* Add `Key()` to handler concept (#134)
+* C++11 compatibility and support (#128)
+* Optimized number-to-string and vice versa conversions (#137, #80)
+* Short-String Optimization (#131)
+* Local stream optimization by traits (#32)
+* Travis & Appveyor Continuous Integration, with Valgrind verification (#24, #242)
+* Redo all documentation (English, Simplified Chinese)
+
+### Changed
+* Copyright ownership transfered to THL A29 Limited (a Tencent company).
+* Migrating from Premake to CMAKE (#192)
+* Resolve all warning reports
+
+### Removed
+* Remove other JSON libraries for performance comparison (#180)
+
+## 0.11 - 2012-11-16
+
+## 0.1 - 2011-11-18
+
+[Unreleased]: https://github.com/miloyip/rapidjson/compare/v1.1.0...HEAD
+[1.1.0]: https://github.com/miloyip/rapidjson/compare/v1.0.2...v1.1.0
+[1.0.2]: https://github.com/miloyip/rapidjson/compare/v1.0.1...v1.0.2
+[1.0.1]: https://github.com/miloyip/rapidjson/compare/v1.0.0...v1.0.1
+[1.0.0]: https://github.com/miloyip/rapidjson/compare/v1.0-beta...v1.0.0

+ 269 - 269
contrib/libs/rapidjson/include/rapidjson/allocators.h

@@ -1,271 +1,271 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_ALLOCATORS_H_ 
-#define RAPIDJSON_ALLOCATORS_H_ 
- 
-#include "rapidjson.h" 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// Allocator 
- 
-/*! \class rapidjson::Allocator 
-    \brief Concept for allocating, resizing and freeing memory block. 
-     
-    Note that Malloc() and Realloc() are non-static but Free() is static. 
-     
-    So if an allocator need to support Free(), it needs to put its pointer in  
-    the header of memory block. 
- 
-\code 
-concept Allocator { 
-    static const bool kNeedFree;    //!< Whether this allocator needs to call Free(). 
- 
-    // Allocate a memory block. 
-    // \param size of the memory block in bytes. 
-    // \returns pointer to the memory block. 
-    void* Malloc(size_t size); 
- 
-    // Resize a memory block. 
-    // \param originalPtr The pointer to current memory block. Null pointer is permitted. 
-    // \param originalSize The current size in bytes. (Design issue: since some allocator may not book-keep this, explicitly pass to it can save memory.) 
-    // \param newSize the new size in bytes. 
-    void* Realloc(void* originalPtr, size_t originalSize, size_t newSize); 
- 
-    // Free a memory block. 
-    // \param pointer to the memory block. Null pointer is permitted. 
-    static void Free(void *ptr); 
-}; 
-\endcode 
-*/ 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// CrtAllocator 
- 
-//! C-runtime library allocator. 
-/*! This class is just wrapper for standard C library memory routines. 
-    \note implements Allocator concept 
-*/ 
-class CrtAllocator { 
-public: 
-    static const bool kNeedFree = true; 
-    void* Malloc(size_t size) {  
-        if (size) //  behavior of malloc(0) is implementation defined. 
-            return std::malloc(size); 
-        else 
-            return NULL; // standardize to returning NULL. 
-    } 
-    void* Realloc(void* originalPtr, size_t originalSize, size_t newSize) { 
-        (void)originalSize; 
-        if (newSize == 0) { 
-            std::free(originalPtr); 
-            return NULL; 
-        } 
-        return std::realloc(originalPtr, newSize); 
-    } 
-    static void Free(void *ptr) { std::free(ptr); } 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// MemoryPoolAllocator 
- 
-//! Default memory allocator used by the parser and DOM. 
-/*! This allocator allocate memory blocks from pre-allocated memory chunks.  
- 
-    It does not free memory blocks. And Realloc() only allocate new memory. 
- 
-    The memory chunks are allocated by BaseAllocator, which is CrtAllocator by default. 
- 
-    User may also supply a buffer as the first chunk. 
- 
-    If the user-buffer is full then additional chunks are allocated by BaseAllocator. 
- 
-    The user-buffer is not deallocated by this allocator. 
- 
-    \tparam BaseAllocator the allocator type for allocating memory chunks. Default is CrtAllocator. 
-    \note implements Allocator concept 
-*/ 
-template <typename BaseAllocator = CrtAllocator> 
-class MemoryPoolAllocator { 
-public: 
-    static const bool kNeedFree = false;    //!< Tell users that no need to call Free() with this allocator. (concept Allocator) 
- 
-    //! Constructor with chunkSize. 
-    /*! \param chunkSize The size of memory chunk. The default is kDefaultChunkSize. 
-        \param baseAllocator The allocator for allocating memory chunks. 
-    */ 
-    MemoryPoolAllocator(size_t chunkSize = kDefaultChunkCapacity, BaseAllocator* baseAllocator = 0) :  
-        chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(0), baseAllocator_(baseAllocator), ownBaseAllocator_(0) 
-    { 
-    } 
- 
-    //! Constructor with user-supplied buffer. 
-    /*! The user buffer will be used firstly. When it is full, memory pool allocates new chunk with chunk size. 
- 
-        The user buffer will not be deallocated when this allocator is destructed. 
- 
-        \param buffer User supplied buffer. 
-        \param size Size of the buffer in bytes. It must at least larger than sizeof(ChunkHeader). 
-        \param chunkSize The size of memory chunk. The default is kDefaultChunkSize. 
-        \param baseAllocator The allocator for allocating memory chunks. 
-    */ 
-    MemoryPoolAllocator(void *buffer, size_t size, size_t chunkSize = kDefaultChunkCapacity, BaseAllocator* baseAllocator = 0) : 
-        chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(buffer), baseAllocator_(baseAllocator), ownBaseAllocator_(0) 
-    { 
-        RAPIDJSON_ASSERT(buffer != 0); 
-        RAPIDJSON_ASSERT(size > sizeof(ChunkHeader)); 
-        chunkHead_ = reinterpret_cast<ChunkHeader*>(buffer); 
-        chunkHead_->capacity = size - sizeof(ChunkHeader); 
-        chunkHead_->size = 0; 
-        chunkHead_->next = 0; 
-    } 
- 
-    //! Destructor. 
-    /*! This deallocates all memory chunks, excluding the user-supplied buffer. 
-    */ 
-    ~MemoryPoolAllocator() { 
-        Clear(); 
-        RAPIDJSON_DELETE(ownBaseAllocator_); 
-    } 
- 
-    //! Deallocates all memory chunks, excluding the user-supplied buffer. 
-    void Clear() { 
-        while (chunkHead_ && chunkHead_ != userBuffer_) { 
-            ChunkHeader* next = chunkHead_->next; 
-            baseAllocator_->Free(chunkHead_); 
-            chunkHead_ = next; 
-        } 
-        if (chunkHead_ && chunkHead_ == userBuffer_) 
-            chunkHead_->size = 0; // Clear user buffer 
-    } 
- 
-    //! Computes the total capacity of allocated memory chunks. 
-    /*! \return total capacity in bytes. 
-    */ 
-    size_t Capacity() const { 
-        size_t capacity = 0; 
-        for (ChunkHeader* c = chunkHead_; c != 0; c = c->next) 
-            capacity += c->capacity; 
-        return capacity; 
-    } 
- 
-    //! Computes the memory blocks allocated. 
-    /*! \return total used bytes. 
-    */ 
-    size_t Size() const { 
-        size_t size = 0; 
-        for (ChunkHeader* c = chunkHead_; c != 0; c = c->next) 
-            size += c->size; 
-        return size; 
-    } 
- 
-    //! Allocates a memory block. (concept Allocator) 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_ALLOCATORS_H_
+#define RAPIDJSON_ALLOCATORS_H_
+
+#include "rapidjson.h"
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+///////////////////////////////////////////////////////////////////////////////
+// Allocator
+
+/*! \class rapidjson::Allocator
+    \brief Concept for allocating, resizing and freeing memory block.
+    
+    Note that Malloc() and Realloc() are non-static but Free() is static.
+    
+    So if an allocator need to support Free(), it needs to put its pointer in 
+    the header of memory block.
+
+\code
+concept Allocator {
+    static const bool kNeedFree;    //!< Whether this allocator needs to call Free().
+
+    // Allocate a memory block.
+    // \param size of the memory block in bytes.
+    // \returns pointer to the memory block.
+    void* Malloc(size_t size);
+
+    // Resize a memory block.
+    // \param originalPtr The pointer to current memory block. Null pointer is permitted.
+    // \param originalSize The current size in bytes. (Design issue: since some allocator may not book-keep this, explicitly pass to it can save memory.)
+    // \param newSize the new size in bytes.
+    void* Realloc(void* originalPtr, size_t originalSize, size_t newSize);
+
+    // Free a memory block.
+    // \param pointer to the memory block. Null pointer is permitted.
+    static void Free(void *ptr);
+};
+\endcode
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// CrtAllocator
+
+//! C-runtime library allocator.
+/*! This class is just wrapper for standard C library memory routines.
+    \note implements Allocator concept
+*/
+class CrtAllocator {
+public:
+    static const bool kNeedFree = true;
     void* Malloc(size_t size) { 
-        if (!size) 
-            return NULL; 
- 
-        size = RAPIDJSON_ALIGN(size); 
-        if (chunkHead_ == 0 || chunkHead_->size + size > chunkHead_->capacity) 
-            if (!AddChunk(chunk_capacity_ > size ? chunk_capacity_ : size)) 
-                return NULL; 
- 
-        void *buffer = reinterpret_cast<char *>(chunkHead_) + RAPIDJSON_ALIGN(sizeof(ChunkHeader)) + chunkHead_->size; 
-        chunkHead_->size += size; 
-        return buffer; 
-    } 
- 
-    //! Resizes a memory block (concept Allocator) 
-    void* Realloc(void* originalPtr, size_t originalSize, size_t newSize) { 
-        if (originalPtr == 0) 
-            return Malloc(newSize); 
- 
-        if (newSize == 0) 
-            return NULL; 
- 
-        originalSize = RAPIDJSON_ALIGN(originalSize); 
-        newSize = RAPIDJSON_ALIGN(newSize); 
- 
-        // Do not shrink if new size is smaller than original 
-        if (originalSize >= newSize) 
-            return originalPtr; 
- 
-        // Simply expand it if it is the last allocation and there is sufficient space 
-        if (originalPtr == reinterpret_cast<char *>(chunkHead_) + RAPIDJSON_ALIGN(sizeof(ChunkHeader)) + chunkHead_->size - originalSize) { 
-            size_t increment = static_cast<size_t>(newSize - originalSize); 
-            if (chunkHead_->size + increment <= chunkHead_->capacity) { 
-                chunkHead_->size += increment; 
-                return originalPtr; 
-            } 
-        } 
- 
-        // Realloc process: allocate and copy memory, do not free original buffer. 
-        if (void* newBuffer = Malloc(newSize)) { 
-            if (originalSize) 
-                std::memcpy(newBuffer, originalPtr, originalSize); 
-            return newBuffer; 
-        } 
-        else 
-            return NULL; 
-    } 
- 
-    //! Frees a memory block (concept Allocator) 
-    static void Free(void *ptr) { (void)ptr; } // Do nothing 
- 
-private: 
-    //! Copy constructor is not permitted. 
-    MemoryPoolAllocator(const MemoryPoolAllocator& rhs) /* = delete */; 
-    //! Copy assignment operator is not permitted. 
-    MemoryPoolAllocator& operator=(const MemoryPoolAllocator& rhs) /* = delete */; 
- 
-    //! Creates a new chunk. 
-    /*! \param capacity Capacity of the chunk in bytes. 
-        \return true if success. 
-    */ 
-    bool AddChunk(size_t capacity) { 
-        if (!baseAllocator_) 
-            ownBaseAllocator_ = baseAllocator_ = RAPIDJSON_NEW(BaseAllocator)(); 
-        if (ChunkHeader* chunk = reinterpret_cast<ChunkHeader*>(baseAllocator_->Malloc(RAPIDJSON_ALIGN(sizeof(ChunkHeader)) + capacity))) { 
-            chunk->capacity = capacity; 
-            chunk->size = 0; 
-            chunk->next = chunkHead_; 
-            chunkHead_ =  chunk; 
-            return true; 
-        } 
-        else 
-            return false; 
-    } 
- 
-    static const int kDefaultChunkCapacity = 64 * 1024; //!< Default chunk capacity. 
- 
-    //! Chunk header for perpending to each chunk. 
-    /*! Chunks are stored as a singly linked list. 
-    */ 
-    struct ChunkHeader { 
-        size_t capacity;    //!< Capacity of the chunk in bytes (excluding the header itself). 
-        size_t size;        //!< Current size of allocated memory in bytes. 
-        ChunkHeader *next;  //!< Next chunk in the linked list. 
-    }; 
- 
-    ChunkHeader *chunkHead_;    //!< Head of the chunk linked-list. Only the head chunk serves allocation. 
-    size_t chunk_capacity_;     //!< The minimum capacity of chunk when they are allocated. 
-    void *userBuffer_;          //!< User supplied buffer. 
-    BaseAllocator* baseAllocator_;  //!< base allocator for allocating memory chunks. 
-    BaseAllocator* ownBaseAllocator_;   //!< base allocator created by this object. 
-}; 
- 
-RAPIDJSON_NAMESPACE_END 
- 
-#endif // RAPIDJSON_ENCODINGS_H_ 
+        if (size) //  behavior of malloc(0) is implementation defined.
+            return std::malloc(size);
+        else
+            return NULL; // standardize to returning NULL.
+    }
+    void* Realloc(void* originalPtr, size_t originalSize, size_t newSize) {
+        (void)originalSize;
+        if (newSize == 0) {
+            std::free(originalPtr);
+            return NULL;
+        }
+        return std::realloc(originalPtr, newSize);
+    }
+    static void Free(void *ptr) { std::free(ptr); }
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// MemoryPoolAllocator
+
+//! Default memory allocator used by the parser and DOM.
+/*! This allocator allocate memory blocks from pre-allocated memory chunks. 
+
+    It does not free memory blocks. And Realloc() only allocate new memory.
+
+    The memory chunks are allocated by BaseAllocator, which is CrtAllocator by default.
+
+    User may also supply a buffer as the first chunk.
+
+    If the user-buffer is full then additional chunks are allocated by BaseAllocator.
+
+    The user-buffer is not deallocated by this allocator.
+
+    \tparam BaseAllocator the allocator type for allocating memory chunks. Default is CrtAllocator.
+    \note implements Allocator concept
+*/
+template <typename BaseAllocator = CrtAllocator>
+class MemoryPoolAllocator {
+public:
+    static const bool kNeedFree = false;    //!< Tell users that no need to call Free() with this allocator. (concept Allocator)
+
+    //! Constructor with chunkSize.
+    /*! \param chunkSize The size of memory chunk. The default is kDefaultChunkSize.
+        \param baseAllocator The allocator for allocating memory chunks.
+    */
+    MemoryPoolAllocator(size_t chunkSize = kDefaultChunkCapacity, BaseAllocator* baseAllocator = 0) : 
+        chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(0), baseAllocator_(baseAllocator), ownBaseAllocator_(0)
+    {
+    }
+
+    //! Constructor with user-supplied buffer.
+    /*! The user buffer will be used firstly. When it is full, memory pool allocates new chunk with chunk size.
+
+        The user buffer will not be deallocated when this allocator is destructed.
+
+        \param buffer User supplied buffer.
+        \param size Size of the buffer in bytes. It must at least larger than sizeof(ChunkHeader).
+        \param chunkSize The size of memory chunk. The default is kDefaultChunkSize.
+        \param baseAllocator The allocator for allocating memory chunks.
+    */
+    MemoryPoolAllocator(void *buffer, size_t size, size_t chunkSize = kDefaultChunkCapacity, BaseAllocator* baseAllocator = 0) :
+        chunkHead_(0), chunk_capacity_(chunkSize), userBuffer_(buffer), baseAllocator_(baseAllocator), ownBaseAllocator_(0)
+    {
+        RAPIDJSON_ASSERT(buffer != 0);
+        RAPIDJSON_ASSERT(size > sizeof(ChunkHeader));
+        chunkHead_ = reinterpret_cast<ChunkHeader*>(buffer);
+        chunkHead_->capacity = size - sizeof(ChunkHeader);
+        chunkHead_->size = 0;
+        chunkHead_->next = 0;
+    }
+
+    //! Destructor.
+    /*! This deallocates all memory chunks, excluding the user-supplied buffer.
+    */
+    ~MemoryPoolAllocator() {
+        Clear();
+        RAPIDJSON_DELETE(ownBaseAllocator_);
+    }
+
+    //! Deallocates all memory chunks, excluding the user-supplied buffer.
+    void Clear() {
+        while (chunkHead_ && chunkHead_ != userBuffer_) {
+            ChunkHeader* next = chunkHead_->next;
+            baseAllocator_->Free(chunkHead_);
+            chunkHead_ = next;
+        }
+        if (chunkHead_ && chunkHead_ == userBuffer_)
+            chunkHead_->size = 0; // Clear user buffer
+    }
+
+    //! Computes the total capacity of allocated memory chunks.
+    /*! \return total capacity in bytes.
+    */
+    size_t Capacity() const {
+        size_t capacity = 0;
+        for (ChunkHeader* c = chunkHead_; c != 0; c = c->next)
+            capacity += c->capacity;
+        return capacity;
+    }
+
+    //! Computes the memory blocks allocated.
+    /*! \return total used bytes.
+    */
+    size_t Size() const {
+        size_t size = 0;
+        for (ChunkHeader* c = chunkHead_; c != 0; c = c->next)
+            size += c->size;
+        return size;
+    }
+
+    //! Allocates a memory block. (concept Allocator)
+    void* Malloc(size_t size) {
+        if (!size)
+            return NULL;
+
+        size = RAPIDJSON_ALIGN(size);
+        if (chunkHead_ == 0 || chunkHead_->size + size > chunkHead_->capacity)
+            if (!AddChunk(chunk_capacity_ > size ? chunk_capacity_ : size))
+                return NULL;
+
+        void *buffer = reinterpret_cast<char *>(chunkHead_) + RAPIDJSON_ALIGN(sizeof(ChunkHeader)) + chunkHead_->size;
+        chunkHead_->size += size;
+        return buffer;
+    }
+
+    //! Resizes a memory block (concept Allocator)
+    void* Realloc(void* originalPtr, size_t originalSize, size_t newSize) {
+        if (originalPtr == 0)
+            return Malloc(newSize);
+
+        if (newSize == 0)
+            return NULL;
+
+        originalSize = RAPIDJSON_ALIGN(originalSize);
+        newSize = RAPIDJSON_ALIGN(newSize);
+
+        // Do not shrink if new size is smaller than original
+        if (originalSize >= newSize)
+            return originalPtr;
+
+        // Simply expand it if it is the last allocation and there is sufficient space
+        if (originalPtr == reinterpret_cast<char *>(chunkHead_) + RAPIDJSON_ALIGN(sizeof(ChunkHeader)) + chunkHead_->size - originalSize) {
+            size_t increment = static_cast<size_t>(newSize - originalSize);
+            if (chunkHead_->size + increment <= chunkHead_->capacity) {
+                chunkHead_->size += increment;
+                return originalPtr;
+            }
+        }
+
+        // Realloc process: allocate and copy memory, do not free original buffer.
+        if (void* newBuffer = Malloc(newSize)) {
+            if (originalSize)
+                std::memcpy(newBuffer, originalPtr, originalSize);
+            return newBuffer;
+        }
+        else
+            return NULL;
+    }
+
+    //! Frees a memory block (concept Allocator)
+    static void Free(void *ptr) { (void)ptr; } // Do nothing
+
+private:
+    //! Copy constructor is not permitted.
+    MemoryPoolAllocator(const MemoryPoolAllocator& rhs) /* = delete */;
+    //! Copy assignment operator is not permitted.
+    MemoryPoolAllocator& operator=(const MemoryPoolAllocator& rhs) /* = delete */;
+
+    //! Creates a new chunk.
+    /*! \param capacity Capacity of the chunk in bytes.
+        \return true if success.
+    */
+    bool AddChunk(size_t capacity) {
+        if (!baseAllocator_)
+            ownBaseAllocator_ = baseAllocator_ = RAPIDJSON_NEW(BaseAllocator)();
+        if (ChunkHeader* chunk = reinterpret_cast<ChunkHeader*>(baseAllocator_->Malloc(RAPIDJSON_ALIGN(sizeof(ChunkHeader)) + capacity))) {
+            chunk->capacity = capacity;
+            chunk->size = 0;
+            chunk->next = chunkHead_;
+            chunkHead_ =  chunk;
+            return true;
+        }
+        else
+            return false;
+    }
+
+    static const int kDefaultChunkCapacity = 64 * 1024; //!< Default chunk capacity.
+
+    //! Chunk header for perpending to each chunk.
+    /*! Chunks are stored as a singly linked list.
+    */
+    struct ChunkHeader {
+        size_t capacity;    //!< Capacity of the chunk in bytes (excluding the header itself).
+        size_t size;        //!< Current size of allocated memory in bytes.
+        ChunkHeader *next;  //!< Next chunk in the linked list.
+    };
+
+    ChunkHeader *chunkHead_;    //!< Head of the chunk linked-list. Only the head chunk serves allocation.
+    size_t chunk_capacity_;     //!< The minimum capacity of chunk when they are allocated.
+    void *userBuffer_;          //!< User supplied buffer.
+    BaseAllocator* baseAllocator_;  //!< base allocator for allocating memory chunks.
+    BaseAllocator* ownBaseAllocator_;   //!< base allocator created by this object.
+};
+
+RAPIDJSON_NAMESPACE_END
+
+#endif // RAPIDJSON_ENCODINGS_H_

+ 2597 - 2597
contrib/libs/rapidjson/include/rapidjson/document.h

@@ -1,2602 +1,2602 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_DOCUMENT_H_ 
-#define RAPIDJSON_DOCUMENT_H_ 
- 
-/*! \file document.h */ 
- 
-#include "reader.h" 
-#include "internal/meta.h" 
-#include "internal/strfunc.h" 
-#include "memorystream.h" 
-#include "encodedstream.h" 
-#include <new>      // placement new 
-#include <limits> 
- 
-RAPIDJSON_DIAG_PUSH 
-#ifdef _MSC_VER 
-RAPIDJSON_DIAG_OFF(4127) // conditional expression is constant 
-RAPIDJSON_DIAG_OFF(4244) // conversion from kXxxFlags to 'uint16_t', possible loss of data 
-#ifdef _MINWINDEF_       // see: http://stackoverflow.com/questions/22744262/cant-call-stdmax-because-minwindef-h-defines-max 
-#ifndef NOMINMAX 
-#pragma push_macro("min") 
-#pragma push_macro("max") 
-#undef min 
-#undef max 
-#endif 
-#endif 
-#endif 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_OFF(padded) 
-RAPIDJSON_DIAG_OFF(switch-enum) 
-RAPIDJSON_DIAG_OFF(c++98-compat) 
-#endif 
- 
-#ifdef __GNUC__ 
-RAPIDJSON_DIAG_OFF(effc++) 
-#if __GNUC__ >= 6 
-RAPIDJSON_DIAG_OFF(terminate) // ignore throwing RAPIDJSON_ASSERT in RAPIDJSON_NOEXCEPT functions 
-#endif 
-#endif // __GNUC__ 
- 
-#ifndef RAPIDJSON_NOMEMBERITERATORCLASS 
-#include <iterator> // std::iterator, std::random_access_iterator_tag 
-#endif 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-#include <utility> // std::move 
-#endif 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-// Forward declaration. 
-template <typename Encoding, typename Allocator> 
-class GenericValue; 
- 
-template <typename Encoding, typename Allocator, typename StackAllocator> 
-class GenericDocument; 
- 
-//! Name-value pair in a JSON object value. 
-/*! 
-    This class was internal to GenericValue. It used to be a inner struct. 
-    But a compiler (IBM XL C/C++ for AIX) have reported to have problem with that so it moved as a namespace scope struct. 
-    https://code.google.com/p/rapidjson/issues/detail?id=64 
-*/ 
-template <typename Encoding, typename Allocator>  
-struct GenericMember {  
-    GenericValue<Encoding, Allocator> name;     //!< name of member (must be a string) 
-    GenericValue<Encoding, Allocator> value;    //!< value of member. 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// GenericMemberIterator 
- 
-#ifndef RAPIDJSON_NOMEMBERITERATORCLASS 
- 
-//! (Constant) member iterator for a JSON object value 
-/*! 
-    \tparam Const Is this a constant iterator? 
-    \tparam Encoding    Encoding of the value. (Even non-string values need to have the same encoding in a document) 
-    \tparam Allocator   Allocator type for allocating memory of object, array and string. 
- 
-    This class implements a Random Access Iterator for GenericMember elements 
-    of a GenericValue, see ISO/IEC 14882:2003(E) C++ standard, 24.1 [lib.iterator.requirements]. 
- 
-    \note This iterator implementation is mainly intended to avoid implicit 
-        conversions from iterator values to \c NULL, 
-        e.g. from GenericValue::FindMember. 
- 
-    \note Define \c RAPIDJSON_NOMEMBERITERATORCLASS to fall back to a 
-        pointer-based implementation, if your platform doesn't provide 
-        the C++ <iterator> header. 
- 
-    \see GenericMember, GenericValue::MemberIterator, GenericValue::ConstMemberIterator 
- */ 
-template <bool Const, typename Encoding, typename Allocator> 
-class GenericMemberIterator 
-    : public std::iterator<std::random_access_iterator_tag 
-        , typename internal::MaybeAddConst<Const,GenericMember<Encoding,Allocator> >::Type> { 
- 
-    friend class GenericValue<Encoding,Allocator>; 
-    template <bool, typename, typename> friend class GenericMemberIterator; 
- 
-    typedef GenericMember<Encoding,Allocator> PlainType; 
-    typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType; 
-    typedef std::iterator<std::random_access_iterator_tag,ValueType> BaseType; 
- 
-public: 
-    //! Iterator type itself 
-    typedef GenericMemberIterator Iterator; 
-    //! Constant iterator type 
-    typedef GenericMemberIterator<true,Encoding,Allocator>  ConstIterator; 
-    //! Non-constant iterator type 
-    typedef GenericMemberIterator<false,Encoding,Allocator> NonConstIterator; 
- 
-    //! Pointer to (const) GenericMember 
-    typedef typename BaseType::pointer         Pointer; 
-    //! Reference to (const) GenericMember 
-    typedef typename BaseType::reference       Reference; 
-    //! Signed integer type (e.g. \c ptrdiff_t) 
-    typedef typename BaseType::difference_type DifferenceType; 
- 
-    //! Default constructor (singular value) 
-    /*! Creates an iterator pointing to no element. 
-        \note All operations, except for comparisons, are undefined on such values. 
-     */ 
-    GenericMemberIterator() : ptr_() {} 
- 
-    //! Iterator conversions to more const 
-    /*! 
-        \param it (Non-const) iterator to copy from 
- 
-        Allows the creation of an iterator from another GenericMemberIterator 
-        that is "less const".  Especially, creating a non-constant iterator 
-        from a constant iterator are disabled: 
-        \li const -> non-const (not ok) 
-        \li const -> const (ok) 
-        \li non-const -> const (ok) 
-        \li non-const -> non-const (ok) 
- 
-        \note If the \c Const template parameter is already \c false, this 
-            constructor effectively defines a regular copy-constructor. 
-            Otherwise, the copy constructor is implicitly defined. 
-    */ 
-    GenericMemberIterator(const NonConstIterator & it) : ptr_(it.ptr_) {} 
-    Iterator& operator=(const NonConstIterator & it) { ptr_ = it.ptr_; return *this; } 
- 
-    //! @name stepping 
-    //@{ 
-    Iterator& operator++(){ ++ptr_; return *this; } 
-    Iterator& operator--(){ --ptr_; return *this; } 
-    Iterator  operator++(int){ Iterator old(*this); ++ptr_; return old; } 
-    Iterator  operator--(int){ Iterator old(*this); --ptr_; return old; } 
-    //@} 
- 
-    //! @name increment/decrement 
-    //@{ 
-    Iterator operator+(DifferenceType n) const { return Iterator(ptr_+n); } 
-    Iterator operator-(DifferenceType n) const { return Iterator(ptr_-n); } 
- 
-    Iterator& operator+=(DifferenceType n) { ptr_+=n; return *this; } 
-    Iterator& operator-=(DifferenceType n) { ptr_-=n; return *this; } 
-    //@} 
- 
-    //! @name relations 
-    //@{ 
-    bool operator==(ConstIterator that) const { return ptr_ == that.ptr_; } 
-    bool operator!=(ConstIterator that) const { return ptr_ != that.ptr_; } 
-    bool operator<=(ConstIterator that) const { return ptr_ <= that.ptr_; } 
-    bool operator>=(ConstIterator that) const { return ptr_ >= that.ptr_; } 
-    bool operator< (ConstIterator that) const { return ptr_ < that.ptr_; } 
-    bool operator> (ConstIterator that) const { return ptr_ > that.ptr_; } 
-    //@} 
- 
-    //! @name dereference 
-    //@{ 
-    Reference operator*() const { return *ptr_; } 
-    Pointer   operator->() const { return ptr_; } 
-    Reference operator[](DifferenceType n) const { return ptr_[n]; } 
-    //@} 
- 
-    //! Distance 
-    DifferenceType operator-(ConstIterator that) const { return ptr_-that.ptr_; } 
- 
-private: 
-    //! Internal constructor from plain pointer 
-    explicit GenericMemberIterator(Pointer p) : ptr_(p) {} 
- 
-    Pointer ptr_; //!< raw pointer 
-}; 
- 
-#else // RAPIDJSON_NOMEMBERITERATORCLASS 
- 
-// class-based member iterator implementation disabled, use plain pointers 
- 
-template <bool Const, typename Encoding, typename Allocator> 
-struct GenericMemberIterator; 
- 
-//! non-const GenericMemberIterator 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_DOCUMENT_H_
+#define RAPIDJSON_DOCUMENT_H_
+
+/*! \file document.h */
+
+#include "reader.h"
+#include "internal/meta.h"
+#include "internal/strfunc.h"
+#include "memorystream.h"
+#include "encodedstream.h"
+#include <new>      // placement new
+#include <limits>
+
+RAPIDJSON_DIAG_PUSH
+#ifdef _MSC_VER
+RAPIDJSON_DIAG_OFF(4127) // conditional expression is constant
+RAPIDJSON_DIAG_OFF(4244) // conversion from kXxxFlags to 'uint16_t', possible loss of data
+#ifdef _MINWINDEF_       // see: http://stackoverflow.com/questions/22744262/cant-call-stdmax-because-minwindef-h-defines-max
+#ifndef NOMINMAX
+#pragma push_macro("min")
+#pragma push_macro("max")
+#undef min
+#undef max
+#endif
+#endif
+#endif
+
+#ifdef __clang__
+RAPIDJSON_DIAG_OFF(padded)
+RAPIDJSON_DIAG_OFF(switch-enum)
+RAPIDJSON_DIAG_OFF(c++98-compat)
+#endif
+
+#ifdef __GNUC__
+RAPIDJSON_DIAG_OFF(effc++)
+#if __GNUC__ >= 6
+RAPIDJSON_DIAG_OFF(terminate) // ignore throwing RAPIDJSON_ASSERT in RAPIDJSON_NOEXCEPT functions
+#endif
+#endif // __GNUC__
+
+#ifndef RAPIDJSON_NOMEMBERITERATORCLASS
+#include <iterator> // std::iterator, std::random_access_iterator_tag
+#endif
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+#include <utility> // std::move
+#endif
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+// Forward declaration.
+template <typename Encoding, typename Allocator>
+class GenericValue;
+
+template <typename Encoding, typename Allocator, typename StackAllocator>
+class GenericDocument;
+
+//! Name-value pair in a JSON object value.
+/*!
+    This class was internal to GenericValue. It used to be a inner struct.
+    But a compiler (IBM XL C/C++ for AIX) have reported to have problem with that so it moved as a namespace scope struct.
+    https://code.google.com/p/rapidjson/issues/detail?id=64
+*/
 template <typename Encoding, typename Allocator> 
-struct GenericMemberIterator<false,Encoding,Allocator> { 
-    //! use plain pointer as iterator type 
-    typedef GenericMember<Encoding,Allocator>* Iterator; 
-}; 
-//! const GenericMemberIterator 
-template <typename Encoding, typename Allocator> 
-struct GenericMemberIterator<true,Encoding,Allocator> { 
-    //! use plain const pointer as iterator type 
-    typedef const GenericMember<Encoding,Allocator>* Iterator; 
-}; 
- 
-#endif // RAPIDJSON_NOMEMBERITERATORCLASS 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// GenericStringRef 
- 
-//! Reference to a constant string (not taking a copy) 
-/*! 
-    \tparam CharType character type of the string 
- 
-    This helper class is used to automatically infer constant string 
-    references for string literals, especially from \c const \b (!) 
-    character arrays. 
- 
-    The main use is for creating JSON string values without copying the 
-    source string via an \ref Allocator.  This requires that the referenced 
-    string pointers have a sufficient lifetime, which exceeds the lifetime 
-    of the associated GenericValue. 
- 
-    \b Example 
-    \code 
-    Value v("foo");   // ok, no need to copy & calculate length 
-    const char foo[] = "foo"; 
-    v.SetString(foo); // ok 
- 
-    const char* bar = foo; 
-    // Value x(bar); // not ok, can't rely on bar's lifetime 
-    Value x(StringRef(bar)); // lifetime explicitly guaranteed by user 
-    Value y(StringRef(bar, 3));  // ok, explicitly pass length 
-    \endcode 
- 
-    \see StringRef, GenericValue::SetString 
-*/ 
-template<typename CharType> 
-struct GenericStringRef { 
-    typedef CharType Ch; //!< character type of the string 
- 
-    //! Create string reference from \c const character array 
-#ifndef __clang__ // -Wdocumentation 
-    /*! 
-        This constructor implicitly creates a constant string reference from 
-        a \c const character array.  It has better performance than 
-        \ref StringRef(const CharType*) by inferring the string \ref length 
-        from the array length, and also supports strings containing null 
-        characters. 
- 
-        \tparam N length of the string, automatically inferred 
- 
-        \param str Constant character array, lifetime assumed to be longer 
-            than the use of the string in e.g. a GenericValue 
- 
-        \post \ref s == str 
- 
-        \note Constant complexity. 
-        \note There is a hidden, private overload to disallow references to 
-            non-const character arrays to be created via this constructor. 
-            By this, e.g. function-scope arrays used to be filled via 
-            \c snprintf are excluded from consideration. 
-            In such cases, the referenced string should be \b copied to the 
-            GenericValue instead. 
-     */ 
-#endif 
-    template<SizeType N> 
-    GenericStringRef(const CharType (&str)[N]) RAPIDJSON_NOEXCEPT 
-        : s(str), length(N-1) {} 
- 
-    //! Explicitly create string reference from \c const character pointer 
-#ifndef __clang__ // -Wdocumentation 
-    /*! 
-        This constructor can be used to \b explicitly  create a reference to 
-        a constant string pointer. 
- 
-        \see StringRef(const CharType*) 
- 
-        \param str Constant character pointer, lifetime assumed to be longer 
-            than the use of the string in e.g. a GenericValue 
- 
-        \post \ref s == str 
- 
-        \note There is a hidden, private overload to disallow references to 
-            non-const character arrays to be created via this constructor. 
-            By this, e.g. function-scope arrays used to be filled via 
-            \c snprintf are excluded from consideration. 
-            In such cases, the referenced string should be \b copied to the 
-            GenericValue instead. 
-     */ 
-#endif 
-    explicit GenericStringRef(const CharType* str) 
-        : s(str), length(internal::StrLen(str)){ RAPIDJSON_ASSERT(s != 0); } 
- 
-    //! Create constant string reference from pointer and length 
-#ifndef __clang__ // -Wdocumentation 
-    /*! \param str constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue 
-        \param len length of the string, excluding the trailing NULL terminator 
- 
-        \post \ref s == str && \ref length == len 
-        \note Constant complexity. 
-     */ 
-#endif 
-    GenericStringRef(const CharType* str, SizeType len) 
-        : s(str), length(len) { RAPIDJSON_ASSERT(s != 0); } 
- 
-    GenericStringRef(const GenericStringRef& rhs) : s(rhs.s), length(rhs.length) {} 
- 
-    //! implicit conversion to plain CharType pointer 
-    operator const Ch *() const { return s; } 
- 
-    const Ch* const s; //!< plain CharType pointer 
-    const SizeType length; //!< length of the string (excluding the trailing NULL terminator) 
- 
-private: 
-    //! Disallow construction from non-const array 
-    template<SizeType N> 
-    GenericStringRef(CharType (&str)[N]) /* = delete */; 
-    //! Copy assignment operator not permitted - immutable type 
-    GenericStringRef& operator=(const GenericStringRef& rhs) /* = delete */; 
-}; 
- 
-//! Mark a character pointer as constant string 
-/*! Mark a plain character pointer as a "string literal".  This function 
-    can be used to avoid copying a character string to be referenced as a 
-    value in a JSON GenericValue object, if the string's lifetime is known 
-    to be valid long enough. 
-    \tparam CharType Character type of the string 
-    \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue 
-    \return GenericStringRef string reference object 
-    \relatesalso GenericStringRef 
- 
-    \see GenericValue::GenericValue(StringRefType), GenericValue::operator=(StringRefType), GenericValue::SetString(StringRefType), GenericValue::PushBack(StringRefType, Allocator&), GenericValue::AddMember 
-*/ 
-template<typename CharType> 
-inline GenericStringRef<CharType> StringRef(const CharType* str) { 
-    return GenericStringRef<CharType>(str, internal::StrLen(str)); 
-} 
- 
-//! Mark a character pointer as constant string 
-/*! Mark a plain character pointer as a "string literal".  This function 
-    can be used to avoid copying a character string to be referenced as a 
-    value in a JSON GenericValue object, if the string's lifetime is known 
-    to be valid long enough. 
- 
-    This version has better performance with supplied length, and also 
-    supports string containing null characters. 
- 
-    \tparam CharType character type of the string 
-    \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue 
-    \param length The length of source string. 
-    \return GenericStringRef string reference object 
-    \relatesalso GenericStringRef 
-*/ 
-template<typename CharType> 
-inline GenericStringRef<CharType> StringRef(const CharType* str, size_t length) { 
-    return GenericStringRef<CharType>(str, SizeType(length)); 
-} 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-//! Mark a string object as constant string 
-/*! Mark a string object (e.g. \c std::string) as a "string literal". 
-    This function can be used to avoid copying a string to be referenced as a 
-    value in a JSON GenericValue object, if the string's lifetime is known 
-    to be valid long enough. 
- 
-    \tparam CharType character type of the string 
-    \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue 
-    \return GenericStringRef string reference object 
-    \relatesalso GenericStringRef 
-    \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING. 
-*/ 
-template<typename CharType> 
-inline GenericStringRef<CharType> StringRef(const std::basic_string<CharType>& str) { 
-    return GenericStringRef<CharType>(str.data(), SizeType(str.size())); 
-} 
-#endif 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// GenericValue type traits 
-namespace internal { 
- 
-template <typename T, typename Encoding = void, typename Allocator = void> 
-struct IsGenericValueImpl : FalseType {}; 
- 
-// select candidates according to nested encoding and allocator types 
-template <typename T> struct IsGenericValueImpl<T, typename Void<typename T::EncodingType>::Type, typename Void<typename T::AllocatorType>::Type> 
-    : IsBaseOf<GenericValue<typename T::EncodingType, typename T::AllocatorType>, T>::Type {}; 
- 
-// helper to match arbitrary GenericValue instantiations, including derived classes 
-template <typename T> struct IsGenericValue : IsGenericValueImpl<T>::Type {}; 
- 
-} // namespace internal 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// TypeHelper 
- 
-namespace internal { 
- 
-template <typename ValueType, typename T> 
-struct TypeHelper {}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, bool> { 
-    static bool Is(const ValueType& v) { return v.IsBool(); } 
-    static bool Get(const ValueType& v) { return v.GetBool(); } 
-    static ValueType& Set(ValueType& v, bool data) { return v.SetBool(data); } 
-    static ValueType& Set(ValueType& v, bool data, typename ValueType::AllocatorType&) { return v.SetBool(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, int> { 
-    static bool Is(const ValueType& v) { return v.IsInt(); } 
-    static int Get(const ValueType& v) { return v.GetInt(); } 
-    static ValueType& Set(ValueType& v, int data) { return v.SetInt(data); } 
-    static ValueType& Set(ValueType& v, int data, typename ValueType::AllocatorType&) { return v.SetInt(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, unsigned> { 
-    static bool Is(const ValueType& v) { return v.IsUint(); } 
-    static unsigned Get(const ValueType& v) { return v.GetUint(); } 
-    static ValueType& Set(ValueType& v, unsigned data) { return v.SetUint(data); } 
-    static ValueType& Set(ValueType& v, unsigned data, typename ValueType::AllocatorType&) { return v.SetUint(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, int64_t> { 
-    static bool Is(const ValueType& v) { return v.IsInt64(); } 
-    static int64_t Get(const ValueType& v) { return v.GetInt64(); } 
-    static ValueType& Set(ValueType& v, int64_t data) { return v.SetInt64(data); } 
-    static ValueType& Set(ValueType& v, int64_t data, typename ValueType::AllocatorType&) { return v.SetInt64(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, uint64_t> { 
-    static bool Is(const ValueType& v) { return v.IsUint64(); } 
-    static uint64_t Get(const ValueType& v) { return v.GetUint64(); } 
-    static ValueType& Set(ValueType& v, uint64_t data) { return v.SetUint64(data); } 
-    static ValueType& Set(ValueType& v, uint64_t data, typename ValueType::AllocatorType&) { return v.SetUint64(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, double> { 
-    static bool Is(const ValueType& v) { return v.IsDouble(); } 
-    static double Get(const ValueType& v) { return v.GetDouble(); } 
-    static ValueType& Set(ValueType& v, double data) { return v.SetDouble(data); } 
-    static ValueType& Set(ValueType& v, double data, typename ValueType::AllocatorType&) { return v.SetDouble(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, float> { 
-    static bool Is(const ValueType& v) { return v.IsFloat(); } 
-    static float Get(const ValueType& v) { return v.GetFloat(); } 
-    static ValueType& Set(ValueType& v, float data) { return v.SetFloat(data); } 
-    static ValueType& Set(ValueType& v, float data, typename ValueType::AllocatorType&) { return v.SetFloat(data); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, const typename ValueType::Ch*> { 
-    typedef const typename ValueType::Ch* StringType; 
-    static bool Is(const ValueType& v) { return v.IsString(); } 
-    static StringType Get(const ValueType& v) { return v.GetString(); } 
-    static ValueType& Set(ValueType& v, const StringType data) { return v.SetString(typename ValueType::StringRefType(data)); } 
-    static ValueType& Set(ValueType& v, const StringType data, typename ValueType::AllocatorType& a) { return v.SetString(data, a); } 
-}; 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-template<typename ValueType>  
-struct TypeHelper<ValueType, std::basic_string<typename ValueType::Ch> > { 
-    typedef std::basic_string<typename ValueType::Ch> StringType; 
-    static bool Is(const ValueType& v) { return v.IsString(); } 
-    static StringType Get(const ValueType& v) { return StringType(v.GetString(), v.GetStringLength()); } 
-    static ValueType& Set(ValueType& v, const StringType& data, typename ValueType::AllocatorType& a) { return v.SetString(data, a); } 
-}; 
-#endif 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, typename ValueType::Array> { 
-    typedef typename ValueType::Array ArrayType; 
-    static bool Is(const ValueType& v) { return v.IsArray(); } 
-    static ArrayType Get(ValueType& v) { return v.GetArray(); } 
-    static ValueType& Set(ValueType& v, ArrayType data) { return v = data; } 
-    static ValueType& Set(ValueType& v, ArrayType data, typename ValueType::AllocatorType&) { return v = data; } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, typename ValueType::ConstArray> { 
-    typedef typename ValueType::ConstArray ArrayType; 
-    static bool Is(const ValueType& v) { return v.IsArray(); } 
-    static ArrayType Get(const ValueType& v) { return v.GetArray(); } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, typename ValueType::Object> { 
-    typedef typename ValueType::Object ObjectType; 
-    static bool Is(const ValueType& v) { return v.IsObject(); } 
-    static ObjectType Get(ValueType& v) { return v.GetObject(); } 
-    static ValueType& Set(ValueType& v, ObjectType data) { return v = data; } 
-    static ValueType& Set(ValueType& v, ObjectType data, typename ValueType::AllocatorType&) { v = data; } 
-}; 
- 
-template<typename ValueType>  
-struct TypeHelper<ValueType, typename ValueType::ConstObject> { 
-    typedef typename ValueType::ConstObject ObjectType; 
-    static bool Is(const ValueType& v) { return v.IsObject(); } 
-    static ObjectType Get(const ValueType& v) { return v.GetObject(); } 
-}; 
- 
-} // namespace internal 
- 
-// Forward declarations 
-template <bool, typename> class GenericArray; 
-template <bool, typename> class GenericObject; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// GenericValue 
- 
-//! Represents a JSON value. Use Value for UTF8 encoding and default allocator. 
-/*! 
-    A JSON value can be one of 7 types. This class is a variant type supporting 
-    these types. 
- 
-    Use the Value if UTF8 and default allocator 
- 
-    \tparam Encoding    Encoding of the value. (Even non-string values need to have the same encoding in a document) 
-    \tparam Allocator   Allocator type for allocating memory of object, array and string. 
-*/ 
-template <typename Encoding, typename Allocator = MemoryPoolAllocator<> >  
-class GenericValue { 
-public: 
-    //! Name-value pair in an object. 
-    typedef GenericMember<Encoding, Allocator> Member; 
-    typedef Encoding EncodingType;                  //!< Encoding type from template parameter. 
-    typedef Allocator AllocatorType;                //!< Allocator type from template parameter. 
-    typedef typename Encoding::Ch Ch;               //!< Character type derived from Encoding. 
-    typedef GenericStringRef<Ch> StringRefType;     //!< Reference to a constant string 
-    typedef typename GenericMemberIterator<false,Encoding,Allocator>::Iterator MemberIterator;  //!< Member iterator for iterating in object. 
-    typedef typename GenericMemberIterator<true,Encoding,Allocator>::Iterator ConstMemberIterator;  //!< Constant member iterator for iterating in object. 
-    typedef GenericValue* ValueIterator;            //!< Value iterator for iterating in array. 
-    typedef const GenericValue* ConstValueIterator; //!< Constant value iterator for iterating in array. 
-    typedef GenericValue<Encoding, Allocator> ValueType;    //!< Value type of itself. 
-    typedef GenericArray<false, ValueType> Array; 
-    typedef GenericArray<true, ValueType> ConstArray; 
-    typedef GenericObject<false, ValueType> Object; 
-    typedef GenericObject<true, ValueType> ConstObject; 
- 
-    //!@name Constructors and destructor. 
-    //@{ 
- 
-    //! Default constructor creates a null value. 
-    GenericValue() RAPIDJSON_NOEXCEPT : data_() { data_.f.flags = kNullFlag; } 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    //! Move constructor in C++11 
-    GenericValue(GenericValue&& rhs) RAPIDJSON_NOEXCEPT : data_(rhs.data_) { 
-        rhs.data_.f.flags = kNullFlag; // give up contents 
-    } 
-#endif 
- 
-private: 
-    //! Copy constructor is not permitted. 
-    GenericValue(const GenericValue& rhs); 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    //! Moving from a GenericDocument is not permitted. 
-    template <typename StackAllocator> 
-    GenericValue(GenericDocument<Encoding,Allocator,StackAllocator>&& rhs); 
- 
-    //! Move assignment from a GenericDocument is not permitted. 
-    template <typename StackAllocator> 
-    GenericValue& operator=(GenericDocument<Encoding,Allocator,StackAllocator>&& rhs); 
-#endif 
- 
-public: 
- 
-    //! Constructor with JSON value type. 
-    /*! This creates a Value of specified type with default content. 
-        \param type Type of the value. 
-        \note Default content for number is zero. 
-    */ 
-    explicit GenericValue(Type type) RAPIDJSON_NOEXCEPT : data_() { 
-        static const uint16_t defaultFlags[7] = { 
-            kNullFlag, kFalseFlag, kTrueFlag, kObjectFlag, kArrayFlag, kShortStringFlag, 
-            kNumberAnyFlag 
-        }; 
-        RAPIDJSON_ASSERT(type <= kNumberType); 
-        data_.f.flags = defaultFlags[type]; 
- 
-        // Use ShortString to store empty string. 
-        if (type == kStringType) 
-            data_.ss.SetLength(0); 
-    } 
- 
-    //! Explicit copy constructor (with allocator) 
-    /*! Creates a copy of a Value by using the given Allocator 
-        \tparam SourceAllocator allocator of \c rhs 
-        \param rhs Value to copy from (read-only) 
-        \param allocator Allocator for allocating copied elements and buffers. Commonly use GenericDocument::GetAllocator(). 
-        \see CopyFrom() 
-    */ 
-    template <typename SourceAllocator> 
-    GenericValue(const GenericValue<Encoding,SourceAllocator>& rhs, Allocator& allocator) { 
-        switch (rhs.GetType()) { 
-        case kObjectType: { 
-                SizeType count = rhs.data_.o.size; 
-                Member* lm = reinterpret_cast<Member*>(allocator.Malloc(count * sizeof(Member))); 
-                const typename GenericValue<Encoding,SourceAllocator>::Member* rm = rhs.GetMembersPointer(); 
-                for (SizeType i = 0; i < count; i++) { 
-                    new (&lm[i].name) GenericValue(rm[i].name, allocator); 
-                    new (&lm[i].value) GenericValue(rm[i].value, allocator); 
-                } 
-                data_.f.flags = kObjectFlag; 
-                data_.o.size = data_.o.capacity = count; 
-                SetMembersPointer(lm); 
-            } 
-            break; 
-        case kArrayType: { 
-                SizeType count = rhs.data_.a.size; 
-                GenericValue* le = reinterpret_cast<GenericValue*>(allocator.Malloc(count * sizeof(GenericValue))); 
-                const GenericValue<Encoding,SourceAllocator>* re = rhs.GetElementsPointer(); 
-                for (SizeType i = 0; i < count; i++) 
-                    new (&le[i]) GenericValue(re[i], allocator); 
-                data_.f.flags = kArrayFlag; 
-                data_.a.size = data_.a.capacity = count; 
-                SetElementsPointer(le); 
-            } 
-            break; 
-        case kStringType: 
-            if (rhs.data_.f.flags == kConstStringFlag) { 
-                data_.f.flags = rhs.data_.f.flags; 
-                data_  = *reinterpret_cast<const Data*>(&rhs.data_); 
-            } 
-            else 
-                SetStringRaw(StringRef(rhs.GetString(), rhs.GetStringLength()), allocator); 
-            break; 
-        default: 
-            data_.f.flags = rhs.data_.f.flags; 
-            data_  = *reinterpret_cast<const Data*>(&rhs.data_); 
-            break; 
-        } 
-    } 
- 
-    //! Constructor for boolean value. 
-    /*! \param b Boolean value 
-        \note This constructor is limited to \em real boolean values and rejects 
-            implicitly converted types like arbitrary pointers.  Use an explicit cast 
-            to \c bool, if you want to construct a boolean JSON value in such cases. 
-     */ 
-#ifndef RAPIDJSON_DOXYGEN_RUNNING // hide SFINAE from Doxygen 
-    template <typename T> 
-    explicit GenericValue(T b, RAPIDJSON_ENABLEIF((internal::IsSame<bool, T>))) RAPIDJSON_NOEXCEPT  // See #472 
-#else 
-    explicit GenericValue(bool b) RAPIDJSON_NOEXCEPT 
-#endif 
-        : data_() { 
-            // safe-guard against failing SFINAE 
-            RAPIDJSON_STATIC_ASSERT((internal::IsSame<bool,T>::Value)); 
-            data_.f.flags = b ? kTrueFlag : kFalseFlag; 
-    } 
- 
-    //! Constructor for int value. 
-    explicit GenericValue(int i) RAPIDJSON_NOEXCEPT : data_() { 
-        data_.n.i64 = i; 
-        data_.f.flags = (i >= 0) ? (kNumberIntFlag | kUintFlag | kUint64Flag) : kNumberIntFlag; 
-    } 
- 
-    //! Constructor for unsigned value. 
-    explicit GenericValue(unsigned u) RAPIDJSON_NOEXCEPT : data_() { 
-        data_.n.u64 = u;  
-        data_.f.flags = (u & 0x80000000) ? kNumberUintFlag : (kNumberUintFlag | kIntFlag | kInt64Flag); 
-    } 
- 
-    //! Constructor for int64_t value. 
-    explicit GenericValue(int64_t i64) RAPIDJSON_NOEXCEPT : data_() { 
-        data_.n.i64 = i64; 
-        data_.f.flags = kNumberInt64Flag; 
-        if (i64 >= 0) { 
-            data_.f.flags |= kNumberUint64Flag; 
-            if (!(static_cast<uint64_t>(i64) & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x00000000))) 
-                data_.f.flags |= kUintFlag; 
-            if (!(static_cast<uint64_t>(i64) & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000))) 
-                data_.f.flags |= kIntFlag; 
-        } 
-        else if (i64 >= static_cast<int64_t>(RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000))) 
-            data_.f.flags |= kIntFlag; 
-    } 
- 
-    //! Constructor for uint64_t value. 
-    explicit GenericValue(uint64_t u64) RAPIDJSON_NOEXCEPT : data_() { 
-        data_.n.u64 = u64; 
-        data_.f.flags = kNumberUint64Flag; 
-        if (!(u64 & RAPIDJSON_UINT64_C2(0x80000000, 0x00000000))) 
-            data_.f.flags |= kInt64Flag; 
-        if (!(u64 & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x00000000))) 
-            data_.f.flags |= kUintFlag; 
-        if (!(u64 & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000))) 
-            data_.f.flags |= kIntFlag; 
-    } 
- 
-    //! Constructor for double value. 
-    explicit GenericValue(double d) RAPIDJSON_NOEXCEPT : data_() { data_.n.d = d; data_.f.flags = kNumberDoubleFlag; } 
- 
-    //! Constructor for float value. 
-    explicit GenericValue(float f) RAPIDJSON_NOEXCEPT : data_() { data_.n.d = static_cast<double>(f); data_.f.flags = kNumberDoubleFlag; } 
- 
-    //! Constructor for constant string (i.e. do not make a copy of string) 
-    GenericValue(const Ch* s, SizeType length) RAPIDJSON_NOEXCEPT : data_() { SetStringRaw(StringRef(s, length)); } 
- 
-    //! Constructor for constant string (i.e. do not make a copy of string) 
-    explicit GenericValue(StringRefType s) RAPIDJSON_NOEXCEPT : data_() { SetStringRaw(s); } 
- 
-    //! Constructor for copy-string (i.e. do make a copy of string) 
-    GenericValue(const Ch* s, SizeType length, Allocator& allocator) : data_() { SetStringRaw(StringRef(s, length), allocator); } 
- 
-    //! Constructor for copy-string (i.e. do make a copy of string) 
-    GenericValue(const Ch*s, Allocator& allocator) : data_() { SetStringRaw(StringRef(s), allocator); } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Constructor for copy-string from a string object (i.e. do make a copy of string) 
-    /*! \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING. 
-     */ 
-    GenericValue(const std::basic_string<Ch>& s, Allocator& allocator) : data_() { SetStringRaw(StringRef(s), allocator); } 
-#endif 
- 
-    //! Constructor for Array. 
-    /*! 
-        \param a An array obtained by \c GetArray(). 
-        \note \c Array is always pass-by-value. 
-        \note the source array is moved into this value and the sourec array becomes empty. 
-    */ 
-    GenericValue(Array a) RAPIDJSON_NOEXCEPT : data_(a.value_.data_) { 
-        a.value_.data_ = Data(); 
-        a.value_.data_.f.flags = kArrayFlag; 
-    } 
- 
-    //! Constructor for Object. 
-    /*! 
-        \param o An object obtained by \c GetObject(). 
-        \note \c Object is always pass-by-value. 
-        \note the source object is moved into this value and the sourec object becomes empty. 
-    */ 
-    GenericValue(Object o) RAPIDJSON_NOEXCEPT : data_(o.value_.data_) { 
-        o.value_.data_ = Data(); 
-        o.value_.data_.f.flags = kObjectFlag; 
-    } 
- 
-    //! Destructor. 
-    /*! Need to destruct elements of array, members of object, or copy-string. 
-    */ 
-    ~GenericValue() { 
-        if (Allocator::kNeedFree) { // Shortcut by Allocator's trait 
-            switch(data_.f.flags) { 
-            case kArrayFlag: 
-                { 
-                    GenericValue* e = GetElementsPointer(); 
-                    for (GenericValue* v = e; v != e + data_.a.size; ++v) 
-                        v->~GenericValue(); 
-                    Allocator::Free(e); 
-                } 
-                break; 
- 
-            case kObjectFlag: 
-                for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m) 
-                    m->~Member(); 
-                Allocator::Free(GetMembersPointer()); 
-                break; 
- 
-            case kCopyStringFlag: 
-                Allocator::Free(const_cast<Ch*>(GetStringPointer())); 
-                break; 
- 
-            default: 
-                break;  // Do nothing for other types. 
-            } 
-        } 
-    } 
- 
-    //@} 
- 
-    //!@name Assignment operators 
-    //@{ 
- 
-    //! Assignment with move semantics. 
-    /*! \param rhs Source of the assignment. It will become a null value after assignment. 
-    */ 
-    GenericValue& operator=(GenericValue& rhs) RAPIDJSON_NOEXCEPT { 
-        RAPIDJSON_ASSERT(this != &rhs); 
-        this->~GenericValue(); 
-        RawAssign(rhs); 
-        return *this; 
-    } 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    //! Move assignment in C++11 
-    GenericValue& operator=(GenericValue&& rhs) RAPIDJSON_NOEXCEPT { 
-        return *this = rhs.Move(); 
-    } 
-#endif 
- 
-    //! Assignment of constant string reference (no copy) 
-    /*! \param str Constant string reference to be assigned 
-        \note This overload is needed to avoid clashes with the generic primitive type assignment overload below. 
-        \see GenericStringRef, operator=(T) 
-    */ 
-    GenericValue& operator=(StringRefType str) RAPIDJSON_NOEXCEPT { 
-        GenericValue s(str); 
-        return *this = s; 
-    } 
- 
-    //! Assignment with primitive types. 
-    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t 
-        \param value The value to be assigned. 
- 
-        \note The source type \c T explicitly disallows all pointer types, 
-            especially (\c const) \ref Ch*.  This helps avoiding implicitly 
-            referencing character strings with insufficient lifetime, use 
-            \ref SetString(const Ch*, Allocator&) (for copying) or 
-            \ref StringRef() (to explicitly mark the pointer as constant) instead. 
-            All other pointer types would implicitly convert to \c bool, 
-            use \ref SetBool() instead. 
-    */ 
-    template <typename T> 
-    RAPIDJSON_DISABLEIF_RETURN((internal::IsPointer<T>), (GenericValue&)) 
-    operator=(T value) { 
-        GenericValue v(value); 
-        return *this = v; 
-    } 
- 
-    //! Deep-copy assignment from Value 
-    /*! Assigns a \b copy of the Value to the current Value object 
-        \tparam SourceAllocator Allocator type of \c rhs 
-        \param rhs Value to copy from (read-only) 
-        \param allocator Allocator to use for copying 
-     */ 
-    template <typename SourceAllocator> 
-    GenericValue& CopyFrom(const GenericValue<Encoding, SourceAllocator>& rhs, Allocator& allocator) { 
-        RAPIDJSON_ASSERT(static_cast<void*>(this) != static_cast<void const*>(&rhs)); 
-        this->~GenericValue(); 
-        new (this) GenericValue(rhs, allocator); 
-        return *this; 
-    } 
- 
-    //! Exchange the contents of this value with those of other. 
-    /*! 
-        \param other Another value. 
-        \note Constant complexity. 
-    */ 
-    GenericValue& Swap(GenericValue& other) RAPIDJSON_NOEXCEPT { 
-        GenericValue temp; 
-        temp.RawAssign(*this); 
-        RawAssign(other); 
-        other.RawAssign(temp); 
-        return *this; 
-    } 
- 
-    //! free-standing swap function helper 
-    /*! 
-        Helper function to enable support for common swap implementation pattern based on \c std::swap: 
-        \code 
-        void swap(MyClass& a, MyClass& b) { 
-            using std::swap; 
-            swap(a.value, b.value); 
-            // ... 
-        } 
-        \endcode 
-        \see Swap() 
-     */ 
-    friend inline void swap(GenericValue& a, GenericValue& b) RAPIDJSON_NOEXCEPT { a.Swap(b); } 
- 
-    //! Prepare Value for move semantics 
-    /*! \return *this */ 
-    GenericValue& Move() RAPIDJSON_NOEXCEPT { return *this; } 
-    //@} 
- 
-    //!@name Equal-to and not-equal-to operators 
-    //@{ 
-    //! Equal-to operator 
-    /*! 
-        \note If an object contains duplicated named member, comparing equality with any object is always \c false. 
-        \note Linear time complexity (number of all values in the subtree and total lengths of all strings). 
-    */ 
-    template <typename SourceAllocator> 
-    bool operator==(const GenericValue<Encoding, SourceAllocator>& rhs) const { 
-        typedef GenericValue<Encoding, SourceAllocator> RhsType; 
-        if (GetType() != rhs.GetType()) 
-            return false; 
- 
-        switch (GetType()) { 
-        case kObjectType: // Warning: O(n^2) inner-loop 
-            if (data_.o.size != rhs.data_.o.size) 
-                return false;            
-            for (ConstMemberIterator lhsMemberItr = MemberBegin(); lhsMemberItr != MemberEnd(); ++lhsMemberItr) { 
-                typename RhsType::ConstMemberIterator rhsMemberItr = rhs.FindMember(lhsMemberItr->name); 
-                if (rhsMemberItr == rhs.MemberEnd() || lhsMemberItr->value != rhsMemberItr->value) 
-                    return false; 
-            } 
-            return true; 
-             
-        case kArrayType: 
-            if (data_.a.size != rhs.data_.a.size) 
-                return false; 
-            for (SizeType i = 0; i < data_.a.size; i++) 
-                if ((*this)[i] != rhs[i]) 
-                    return false; 
-            return true; 
- 
-        case kStringType: 
-            return StringEqual(rhs); 
- 
-        case kNumberType: 
-            if (IsDouble() || rhs.IsDouble()) { 
-                double a = GetDouble();     // May convert from integer to double. 
-                double b = rhs.GetDouble(); // Ditto 
-                return a >= b && a <= b;    // Prevent -Wfloat-equal 
-            } 
-            else 
-                return data_.n.u64 == rhs.data_.n.u64; 
- 
-        default: 
-            return true; 
-        } 
-    } 
- 
-    //! Equal-to operator with const C-string pointer 
-    bool operator==(const Ch* rhs) const { return *this == GenericValue(StringRef(rhs)); } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Equal-to operator with string object 
-    /*! \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING. 
-     */ 
-    bool operator==(const std::basic_string<Ch>& rhs) const { return *this == GenericValue(StringRef(rhs)); } 
-#endif 
- 
-    //! Equal-to operator with primitive types 
-    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t, \c double, \c true, \c false 
-    */ 
-    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>,internal::IsGenericValue<T> >), (bool)) operator==(const T& rhs) const { return *this == GenericValue(rhs); } 
- 
-    //! Not-equal-to operator 
-    /*! \return !(*this == rhs) 
-     */ 
-    template <typename SourceAllocator> 
-    bool operator!=(const GenericValue<Encoding, SourceAllocator>& rhs) const { return !(*this == rhs); } 
- 
-    //! Not-equal-to operator with const C-string pointer 
-    bool operator!=(const Ch* rhs) const { return !(*this == rhs); } 
- 
-    //! Not-equal-to operator with arbitrary types 
-    /*! \return !(*this == rhs) 
-     */ 
-    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator!=(const T& rhs) const { return !(*this == rhs); } 
- 
-    //! Equal-to operator with arbitrary types (symmetric version) 
-    /*! \return (rhs == lhs) 
-     */ 
-    template <typename T> friend RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator==(const T& lhs, const GenericValue& rhs) { return rhs == lhs; } 
- 
-    //! Not-Equal-to operator with arbitrary types (symmetric version) 
-    /*! \return !(rhs == lhs) 
-     */ 
-    template <typename T> friend RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator!=(const T& lhs, const GenericValue& rhs) { return !(rhs == lhs); } 
-    //@} 
- 
-    //!@name Type 
-    //@{ 
- 
-    Type GetType()  const { return static_cast<Type>(data_.f.flags & kTypeMask); } 
-    bool IsNull()   const { return data_.f.flags == kNullFlag; } 
-    bool IsFalse()  const { return data_.f.flags == kFalseFlag; } 
-    bool IsTrue()   const { return data_.f.flags == kTrueFlag; } 
-    bool IsBool()   const { return (data_.f.flags & kBoolFlag) != 0; } 
-    bool IsObject() const { return data_.f.flags == kObjectFlag; } 
-    bool IsArray()  const { return data_.f.flags == kArrayFlag; } 
-    bool IsNumber() const { return (data_.f.flags & kNumberFlag) != 0; } 
-    bool IsInt()    const { return (data_.f.flags & kIntFlag) != 0; } 
-    bool IsUint()   const { return (data_.f.flags & kUintFlag) != 0; } 
-    bool IsInt64()  const { return (data_.f.flags & kInt64Flag) != 0; } 
-    bool IsUint64() const { return (data_.f.flags & kUint64Flag) != 0; } 
-    bool IsDouble() const { return (data_.f.flags & kDoubleFlag) != 0; } 
-    bool IsString() const { return (data_.f.flags & kStringFlag) != 0; } 
- 
-    // Checks whether a number can be losslessly converted to a double. 
-    bool IsLosslessDouble() const { 
-        if (!IsNumber()) return false; 
-        if (IsUint64()) { 
-            uint64_t u = GetUint64(); 
-            volatile double d = static_cast<double>(u); 
-            return (d >= 0.0) 
-                && (d < static_cast<double>(std::numeric_limits<uint64_t>::max())) 
-                && (u == static_cast<uint64_t>(d)); 
-        } 
-        if (IsInt64()) { 
-            int64_t i = GetInt64(); 
-            volatile double d = static_cast<double>(i); 
-            return (d >= static_cast<double>(std::numeric_limits<int64_t>::min())) 
-                && (d < static_cast<double>(std::numeric_limits<int64_t>::max())) 
-                && (i == static_cast<int64_t>(d)); 
-        } 
-        return true; // double, int, uint are always lossless 
-    } 
- 
-    // Checks whether a number is a float (possible lossy). 
-    bool IsFloat() const  { 
-        if ((data_.f.flags & kDoubleFlag) == 0) 
-            return false; 
-        double d = GetDouble(); 
-        return d >= -3.4028234e38 && d <= 3.4028234e38; 
-    } 
-    // Checks whether a number can be losslessly converted to a float. 
-    bool IsLosslessFloat() const { 
-        if (!IsNumber()) return false; 
-        double a = GetDouble(); 
-        if (a < static_cast<double>(-std::numeric_limits<float>::max()) 
-                || a > static_cast<double>(std::numeric_limits<float>::max())) 
-            return false; 
-        double b = static_cast<double>(static_cast<float>(a)); 
-        return a >= b && a <= b;    // Prevent -Wfloat-equal 
-    } 
- 
-    //@} 
- 
-    //!@name Null 
-    //@{ 
- 
-    GenericValue& SetNull() { this->~GenericValue(); new (this) GenericValue(); return *this; } 
- 
-    //@} 
- 
-    //!@name Bool 
-    //@{ 
- 
-    bool GetBool() const { RAPIDJSON_ASSERT(IsBool()); return data_.f.flags == kTrueFlag; } 
-    //!< Set boolean value 
-    /*! \post IsBool() == true */ 
-    GenericValue& SetBool(bool b) { this->~GenericValue(); new (this) GenericValue(b); return *this; } 
- 
-    //@} 
- 
-    //!@name Object 
-    //@{ 
- 
-    //! Set this value as an empty object. 
-    /*! \post IsObject() == true */ 
-    GenericValue& SetObject() { this->~GenericValue(); new (this) GenericValue(kObjectType); return *this; } 
- 
-    //! Get the number of members in the object. 
-    SizeType MemberCount() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.size; } 
- 
-    //! Check whether the object is empty. 
-    bool ObjectEmpty() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.size == 0; } 
- 
-    //! Get a value from an object associated with the name. 
-    /*! \pre IsObject() == true 
-        \tparam T Either \c Ch or \c const \c Ch (template used for disambiguation with \ref operator[](SizeType)) 
-        \note In version 0.1x, if the member is not found, this function returns a null value. This makes issue 7. 
-        Since 0.2, if the name is not correct, it will assert. 
-        If user is unsure whether a member exists, user should use HasMember() first. 
-        A better approach is to use FindMember(). 
-        \note Linear time complexity. 
-    */ 
-    template <typename T> 
-    RAPIDJSON_DISABLEIF_RETURN((internal::NotExpr<internal::IsSame<typename internal::RemoveConst<T>::Type, Ch> >),(GenericValue&)) operator[](T* name) { 
-        GenericValue n(StringRef(name)); 
-        return (*this)[n]; 
-    } 
-    template <typename T> 
-    RAPIDJSON_DISABLEIF_RETURN((internal::NotExpr<internal::IsSame<typename internal::RemoveConst<T>::Type, Ch> >),(const GenericValue&)) operator[](T* name) const { return const_cast<GenericValue&>(*this)[name]; } 
- 
-    //! Get a value from an object associated with the name. 
-    /*! \pre IsObject() == true 
-        \tparam SourceAllocator Allocator of the \c name value 
- 
-        \note Compared to \ref operator[](T*), this version is faster because it does not need a StrLen(). 
-        And it can also handle strings with embedded null characters. 
- 
-        \note Linear time complexity. 
-    */ 
-    template <typename SourceAllocator> 
-    GenericValue& operator[](const GenericValue<Encoding, SourceAllocator>& name) { 
-        MemberIterator member = FindMember(name); 
-        if (member != MemberEnd()) 
-            return member->value; 
-        else { 
-            RAPIDJSON_ASSERT(false);    // see above note 
- 
-            // This will generate -Wexit-time-destructors in clang 
-            // static GenericValue NullValue; 
-            // return NullValue; 
- 
-            // Use static buffer and placement-new to prevent destruction 
-            static char buffer[sizeof(GenericValue)]; 
-            return *new (buffer) GenericValue(); 
-        } 
-    } 
-    template <typename SourceAllocator> 
-    const GenericValue& operator[](const GenericValue<Encoding, SourceAllocator>& name) const { return const_cast<GenericValue&>(*this)[name]; } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Get a value from an object associated with name (string object). 
-    GenericValue& operator[](const std::basic_string<Ch>& name) { return (*this)[GenericValue(StringRef(name))]; } 
-    const GenericValue& operator[](const std::basic_string<Ch>& name) const { return (*this)[GenericValue(StringRef(name))]; } 
-#endif 
- 
-    //! Const member iterator 
-    /*! \pre IsObject() == true */ 
-    ConstMemberIterator MemberBegin() const { RAPIDJSON_ASSERT(IsObject()); return ConstMemberIterator(GetMembersPointer()); } 
-    //! Const \em past-the-end member iterator 
-    /*! \pre IsObject() == true */ 
-    ConstMemberIterator MemberEnd() const   { RAPIDJSON_ASSERT(IsObject()); return ConstMemberIterator(GetMembersPointer() + data_.o.size); } 
-    //! Member iterator 
-    /*! \pre IsObject() == true */ 
-    MemberIterator MemberBegin()            { RAPIDJSON_ASSERT(IsObject()); return MemberIterator(GetMembersPointer()); } 
-    //! \em Past-the-end member iterator 
-    /*! \pre IsObject() == true */ 
-    MemberIterator MemberEnd()              { RAPIDJSON_ASSERT(IsObject()); return MemberIterator(GetMembersPointer() + data_.o.size); } 
- 
-    //! Check whether a member exists in the object. 
-    /*! 
-        \param name Member name to be searched. 
-        \pre IsObject() == true 
-        \return Whether a member with that name exists. 
-        \note It is better to use FindMember() directly if you need the obtain the value as well. 
-        \note Linear time complexity. 
-    */ 
-    bool HasMember(const Ch* name) const { return FindMember(name) != MemberEnd(); } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Check whether a member exists in the object with string object. 
-    /*! 
-        \param name Member name to be searched. 
-        \pre IsObject() == true 
-        \return Whether a member with that name exists. 
-        \note It is better to use FindMember() directly if you need the obtain the value as well. 
-        \note Linear time complexity. 
-    */ 
-    bool HasMember(const std::basic_string<Ch>& name) const { return FindMember(name) != MemberEnd(); } 
-#endif 
- 
-    //! Check whether a member exists in the object with GenericValue name. 
-    /*! 
-        This version is faster because it does not need a StrLen(). It can also handle string with null character. 
-        \param name Member name to be searched. 
-        \pre IsObject() == true 
-        \return Whether a member with that name exists. 
-        \note It is better to use FindMember() directly if you need the obtain the value as well. 
-        \note Linear time complexity. 
-    */ 
-    template <typename SourceAllocator> 
-    bool HasMember(const GenericValue<Encoding, SourceAllocator>& name) const { return FindMember(name) != MemberEnd(); } 
- 
-    //! Find member by name. 
-    /*! 
-        \param name Member name to be searched. 
-        \pre IsObject() == true 
-        \return Iterator to member, if it exists. 
-            Otherwise returns \ref MemberEnd(). 
- 
-        \note Earlier versions of Rapidjson returned a \c NULL pointer, in case 
-            the requested member doesn't exist. For consistency with e.g. 
-            \c std::map, this has been changed to MemberEnd() now. 
-        \note Linear time complexity. 
-    */ 
-    MemberIterator FindMember(const Ch* name) { 
-        GenericValue n(StringRef(name)); 
-        return FindMember(n); 
-    } 
- 
-    ConstMemberIterator FindMember(const Ch* name) const { return const_cast<GenericValue&>(*this).FindMember(name); } 
- 
-    //! Find member by name. 
-    /*! 
-        This version is faster because it does not need a StrLen(). It can also handle string with null character. 
-        \param name Member name to be searched. 
-        \pre IsObject() == true 
-        \return Iterator to member, if it exists. 
-            Otherwise returns \ref MemberEnd(). 
- 
-        \note Earlier versions of Rapidjson returned a \c NULL pointer, in case 
-            the requested member doesn't exist. For consistency with e.g. 
-            \c std::map, this has been changed to MemberEnd() now. 
-        \note Linear time complexity. 
-    */ 
-    template <typename SourceAllocator> 
-    MemberIterator FindMember(const GenericValue<Encoding, SourceAllocator>& name) { 
-        RAPIDJSON_ASSERT(IsObject()); 
-        RAPIDJSON_ASSERT(name.IsString()); 
-        MemberIterator member = MemberBegin(); 
-        for ( ; member != MemberEnd(); ++member) 
-            if (name.StringEqual(member->name)) 
-                break; 
-        return member; 
-    } 
-    template <typename SourceAllocator> ConstMemberIterator FindMember(const GenericValue<Encoding, SourceAllocator>& name) const { return const_cast<GenericValue&>(*this).FindMember(name); } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Find member by string object name. 
-    /*! 
-        \param name Member name to be searched. 
-        \pre IsObject() == true 
-        \return Iterator to member, if it exists. 
-            Otherwise returns \ref MemberEnd(). 
-    */ 
-    MemberIterator FindMember(const std::basic_string<Ch>& name) { return FindMember(GenericValue(StringRef(name))); } 
-    ConstMemberIterator FindMember(const std::basic_string<Ch>& name) const { return FindMember(GenericValue(StringRef(name))); } 
-#endif 
- 
-    //! Add a member (name-value pair) to the object. 
-    /*! \param name A string value as name of member. 
-        \param value Value of any type. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \note The ownership of \c name and \c value will be transferred to this object on success. 
-        \pre  IsObject() && name.IsString() 
-        \post name.IsNull() && value.IsNull() 
-        \note Amortized Constant time complexity. 
-    */ 
-    GenericValue& AddMember(GenericValue& name, GenericValue& value, Allocator& allocator) { 
-        RAPIDJSON_ASSERT(IsObject()); 
-        RAPIDJSON_ASSERT(name.IsString()); 
- 
-        ObjectData& o = data_.o; 
-        if (o.size >= o.capacity) { 
-            if (o.capacity == 0) { 
-                o.capacity = kDefaultObjectCapacity; 
-                SetMembersPointer(reinterpret_cast<Member*>(allocator.Malloc(o.capacity * sizeof(Member)))); 
-            } 
-            else { 
-                SizeType oldCapacity = o.capacity; 
-                o.capacity += (oldCapacity + 1) / 2; // grow by factor 1.5 
-                SetMembersPointer(reinterpret_cast<Member*>(allocator.Realloc(GetMembersPointer(), oldCapacity * sizeof(Member), o.capacity * sizeof(Member)))); 
-            } 
-        } 
-        Member* members = GetMembersPointer(); 
-        members[o.size].name.RawAssign(name); 
-        members[o.size].value.RawAssign(value); 
-        o.size++; 
-        return *this; 
-    } 
- 
-    //! Add a constant string value as member (name-value pair) to the object. 
-    /*! \param name A string value as name of member. 
-        \param value constant string reference as value of member. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \pre  IsObject() 
-        \note This overload is needed to avoid clashes with the generic primitive type AddMember(GenericValue&,T,Allocator&) overload below. 
-        \note Amortized Constant time complexity. 
-    */ 
-    GenericValue& AddMember(GenericValue& name, StringRefType value, Allocator& allocator) { 
-        GenericValue v(value); 
-        return AddMember(name, v, allocator); 
-    } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Add a string object as member (name-value pair) to the object. 
-    /*! \param name A string value as name of member. 
-        \param value constant string reference as value of member. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \pre  IsObject() 
-        \note This overload is needed to avoid clashes with the generic primitive type AddMember(GenericValue&,T,Allocator&) overload below. 
-        \note Amortized Constant time complexity. 
-    */ 
-    GenericValue& AddMember(GenericValue& name, std::basic_string<Ch>& value, Allocator& allocator) { 
-        GenericValue v(value, allocator); 
-        return AddMember(name, v, allocator); 
-    } 
-#endif 
- 
-    //! Add any primitive value as member (name-value pair) to the object. 
-    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t 
-        \param name A string value as name of member. 
-        \param value Value of primitive type \c T as value of member 
-        \param allocator Allocator for reallocating memory. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \pre  IsObject() 
- 
-        \note The source type \c T explicitly disallows all pointer types, 
-            especially (\c const) \ref Ch*.  This helps avoiding implicitly 
-            referencing character strings with insufficient lifetime, use 
-            \ref AddMember(StringRefType, GenericValue&, Allocator&) or \ref 
-            AddMember(StringRefType, StringRefType, Allocator&). 
-            All other pointer types would implicitly convert to \c bool, 
-            use an explicit cast instead, if needed. 
-        \note Amortized Constant time complexity. 
-    */ 
-    template <typename T> 
-    RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&)) 
-    AddMember(GenericValue& name, T value, Allocator& allocator) { 
-        GenericValue v(value); 
-        return AddMember(name, v, allocator); 
-    } 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    GenericValue& AddMember(GenericValue&& name, GenericValue&& value, Allocator& allocator) { 
-        return AddMember(name, value, allocator); 
-    } 
-    GenericValue& AddMember(GenericValue&& name, GenericValue& value, Allocator& allocator) { 
-        return AddMember(name, value, allocator); 
-    } 
-    GenericValue& AddMember(GenericValue& name, GenericValue&& value, Allocator& allocator) { 
-        return AddMember(name, value, allocator); 
-    } 
-    GenericValue& AddMember(StringRefType name, GenericValue&& value, Allocator& allocator) { 
-        GenericValue n(name); 
-        return AddMember(n, value, allocator); 
-    } 
-#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS 
- 
- 
-    //! Add a member (name-value pair) to the object. 
-    /*! \param name A constant string reference as name of member. 
-        \param value Value of any type. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \note The ownership of \c value will be transferred to this object on success. 
-        \pre  IsObject() 
-        \post value.IsNull() 
-        \note Amortized Constant time complexity. 
-    */ 
-    GenericValue& AddMember(StringRefType name, GenericValue& value, Allocator& allocator) { 
-        GenericValue n(name); 
-        return AddMember(n, value, allocator); 
-    } 
- 
-    //! Add a constant string value as member (name-value pair) to the object. 
-    /*! \param name A constant string reference as name of member. 
-        \param value constant string reference as value of member. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \pre  IsObject() 
-        \note This overload is needed to avoid clashes with the generic primitive type AddMember(StringRefType,T,Allocator&) overload below. 
-        \note Amortized Constant time complexity. 
-    */ 
-    GenericValue& AddMember(StringRefType name, StringRefType value, Allocator& allocator) { 
-        GenericValue v(value); 
-        return AddMember(name, v, allocator); 
-    } 
- 
-    //! Add any primitive value as member (name-value pair) to the object. 
-    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t 
-        \param name A constant string reference as name of member. 
-        \param value Value of primitive type \c T as value of member 
-        \param allocator Allocator for reallocating memory. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \pre  IsObject() 
- 
-        \note The source type \c T explicitly disallows all pointer types, 
-            especially (\c const) \ref Ch*.  This helps avoiding implicitly 
-            referencing character strings with insufficient lifetime, use 
-            \ref AddMember(StringRefType, GenericValue&, Allocator&) or \ref 
-            AddMember(StringRefType, StringRefType, Allocator&). 
-            All other pointer types would implicitly convert to \c bool, 
-            use an explicit cast instead, if needed. 
-        \note Amortized Constant time complexity. 
-    */ 
-    template <typename T> 
-    RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&)) 
-    AddMember(StringRefType name, T value, Allocator& allocator) { 
-        GenericValue n(name); 
-        return AddMember(n, value, allocator); 
-    } 
- 
-    //! Remove all members in the object. 
-    /*! This function do not deallocate memory in the object, i.e. the capacity is unchanged. 
-        \note Linear time complexity. 
-    */ 
-    void RemoveAllMembers() { 
-        RAPIDJSON_ASSERT(IsObject());  
-        for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m) 
-            m->~Member(); 
-        data_.o.size = 0; 
-    } 
- 
-    //! Remove a member in object by its name. 
-    /*! \param name Name of member to be removed. 
-        \return Whether the member existed. 
-        \note This function may reorder the object members. Use \ref 
-            EraseMember(ConstMemberIterator) if you need to preserve the 
-            relative order of the remaining members. 
-        \note Linear time complexity. 
-    */ 
-    bool RemoveMember(const Ch* name) { 
-        GenericValue n(StringRef(name)); 
-        return RemoveMember(n); 
-    } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    bool RemoveMember(const std::basic_string<Ch>& name) { return RemoveMember(GenericValue(StringRef(name))); } 
-#endif 
- 
-    template <typename SourceAllocator> 
-    bool RemoveMember(const GenericValue<Encoding, SourceAllocator>& name) { 
-        MemberIterator m = FindMember(name); 
-        if (m != MemberEnd()) { 
-            RemoveMember(m); 
-            return true; 
-        } 
-        else 
-            return false; 
-    } 
- 
-    //! Remove a member in object by iterator. 
-    /*! \param m member iterator (obtained by FindMember() or MemberBegin()). 
-        \return the new iterator after removal. 
-        \note This function may reorder the object members. Use \ref 
-            EraseMember(ConstMemberIterator) if you need to preserve the 
-            relative order of the remaining members. 
-        \note Constant time complexity. 
-    */ 
-    MemberIterator RemoveMember(MemberIterator m) { 
+struct GenericMember { 
+    GenericValue<Encoding, Allocator> name;     //!< name of member (must be a string)
+    GenericValue<Encoding, Allocator> value;    //!< value of member.
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// GenericMemberIterator
+
+#ifndef RAPIDJSON_NOMEMBERITERATORCLASS
+
+//! (Constant) member iterator for a JSON object value
+/*!
+    \tparam Const Is this a constant iterator?
+    \tparam Encoding    Encoding of the value. (Even non-string values need to have the same encoding in a document)
+    \tparam Allocator   Allocator type for allocating memory of object, array and string.
+
+    This class implements a Random Access Iterator for GenericMember elements
+    of a GenericValue, see ISO/IEC 14882:2003(E) C++ standard, 24.1 [lib.iterator.requirements].
+
+    \note This iterator implementation is mainly intended to avoid implicit
+        conversions from iterator values to \c NULL,
+        e.g. from GenericValue::FindMember.
+
+    \note Define \c RAPIDJSON_NOMEMBERITERATORCLASS to fall back to a
+        pointer-based implementation, if your platform doesn't provide
+        the C++ <iterator> header.
+
+    \see GenericMember, GenericValue::MemberIterator, GenericValue::ConstMemberIterator
+ */
+template <bool Const, typename Encoding, typename Allocator>
+class GenericMemberIterator
+    : public std::iterator<std::random_access_iterator_tag
+        , typename internal::MaybeAddConst<Const,GenericMember<Encoding,Allocator> >::Type> {
+
+    friend class GenericValue<Encoding,Allocator>;
+    template <bool, typename, typename> friend class GenericMemberIterator;
+
+    typedef GenericMember<Encoding,Allocator> PlainType;
+    typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType;
+    typedef std::iterator<std::random_access_iterator_tag,ValueType> BaseType;
+
+public:
+    //! Iterator type itself
+    typedef GenericMemberIterator Iterator;
+    //! Constant iterator type
+    typedef GenericMemberIterator<true,Encoding,Allocator>  ConstIterator;
+    //! Non-constant iterator type
+    typedef GenericMemberIterator<false,Encoding,Allocator> NonConstIterator;
+
+    //! Pointer to (const) GenericMember
+    typedef typename BaseType::pointer         Pointer;
+    //! Reference to (const) GenericMember
+    typedef typename BaseType::reference       Reference;
+    //! Signed integer type (e.g. \c ptrdiff_t)
+    typedef typename BaseType::difference_type DifferenceType;
+
+    //! Default constructor (singular value)
+    /*! Creates an iterator pointing to no element.
+        \note All operations, except for comparisons, are undefined on such values.
+     */
+    GenericMemberIterator() : ptr_() {}
+
+    //! Iterator conversions to more const
+    /*!
+        \param it (Non-const) iterator to copy from
+
+        Allows the creation of an iterator from another GenericMemberIterator
+        that is "less const".  Especially, creating a non-constant iterator
+        from a constant iterator are disabled:
+        \li const -> non-const (not ok)
+        \li const -> const (ok)
+        \li non-const -> const (ok)
+        \li non-const -> non-const (ok)
+
+        \note If the \c Const template parameter is already \c false, this
+            constructor effectively defines a regular copy-constructor.
+            Otherwise, the copy constructor is implicitly defined.
+    */
+    GenericMemberIterator(const NonConstIterator & it) : ptr_(it.ptr_) {}
+    Iterator& operator=(const NonConstIterator & it) { ptr_ = it.ptr_; return *this; }
+
+    //! @name stepping
+    //@{
+    Iterator& operator++(){ ++ptr_; return *this; }
+    Iterator& operator--(){ --ptr_; return *this; }
+    Iterator  operator++(int){ Iterator old(*this); ++ptr_; return old; }
+    Iterator  operator--(int){ Iterator old(*this); --ptr_; return old; }
+    //@}
+
+    //! @name increment/decrement
+    //@{
+    Iterator operator+(DifferenceType n) const { return Iterator(ptr_+n); }
+    Iterator operator-(DifferenceType n) const { return Iterator(ptr_-n); }
+
+    Iterator& operator+=(DifferenceType n) { ptr_+=n; return *this; }
+    Iterator& operator-=(DifferenceType n) { ptr_-=n; return *this; }
+    //@}
+
+    //! @name relations
+    //@{
+    bool operator==(ConstIterator that) const { return ptr_ == that.ptr_; }
+    bool operator!=(ConstIterator that) const { return ptr_ != that.ptr_; }
+    bool operator<=(ConstIterator that) const { return ptr_ <= that.ptr_; }
+    bool operator>=(ConstIterator that) const { return ptr_ >= that.ptr_; }
+    bool operator< (ConstIterator that) const { return ptr_ < that.ptr_; }
+    bool operator> (ConstIterator that) const { return ptr_ > that.ptr_; }
+    //@}
+
+    //! @name dereference
+    //@{
+    Reference operator*() const { return *ptr_; }
+    Pointer   operator->() const { return ptr_; }
+    Reference operator[](DifferenceType n) const { return ptr_[n]; }
+    //@}
+
+    //! Distance
+    DifferenceType operator-(ConstIterator that) const { return ptr_-that.ptr_; }
+
+private:
+    //! Internal constructor from plain pointer
+    explicit GenericMemberIterator(Pointer p) : ptr_(p) {}
+
+    Pointer ptr_; //!< raw pointer
+};
+
+#else // RAPIDJSON_NOMEMBERITERATORCLASS
+
+// class-based member iterator implementation disabled, use plain pointers
+
+template <bool Const, typename Encoding, typename Allocator>
+struct GenericMemberIterator;
+
+//! non-const GenericMemberIterator
+template <typename Encoding, typename Allocator>
+struct GenericMemberIterator<false,Encoding,Allocator> {
+    //! use plain pointer as iterator type
+    typedef GenericMember<Encoding,Allocator>* Iterator;
+};
+//! const GenericMemberIterator
+template <typename Encoding, typename Allocator>
+struct GenericMemberIterator<true,Encoding,Allocator> {
+    //! use plain const pointer as iterator type
+    typedef const GenericMember<Encoding,Allocator>* Iterator;
+};
+
+#endif // RAPIDJSON_NOMEMBERITERATORCLASS
+
+///////////////////////////////////////////////////////////////////////////////
+// GenericStringRef
+
+//! Reference to a constant string (not taking a copy)
+/*!
+    \tparam CharType character type of the string
+
+    This helper class is used to automatically infer constant string
+    references for string literals, especially from \c const \b (!)
+    character arrays.
+
+    The main use is for creating JSON string values without copying the
+    source string via an \ref Allocator.  This requires that the referenced
+    string pointers have a sufficient lifetime, which exceeds the lifetime
+    of the associated GenericValue.
+
+    \b Example
+    \code
+    Value v("foo");   // ok, no need to copy & calculate length
+    const char foo[] = "foo";
+    v.SetString(foo); // ok
+
+    const char* bar = foo;
+    // Value x(bar); // not ok, can't rely on bar's lifetime
+    Value x(StringRef(bar)); // lifetime explicitly guaranteed by user
+    Value y(StringRef(bar, 3));  // ok, explicitly pass length
+    \endcode
+
+    \see StringRef, GenericValue::SetString
+*/
+template<typename CharType>
+struct GenericStringRef {
+    typedef CharType Ch; //!< character type of the string
+
+    //! Create string reference from \c const character array
+#ifndef __clang__ // -Wdocumentation
+    /*!
+        This constructor implicitly creates a constant string reference from
+        a \c const character array.  It has better performance than
+        \ref StringRef(const CharType*) by inferring the string \ref length
+        from the array length, and also supports strings containing null
+        characters.
+
+        \tparam N length of the string, automatically inferred
+
+        \param str Constant character array, lifetime assumed to be longer
+            than the use of the string in e.g. a GenericValue
+
+        \post \ref s == str
+
+        \note Constant complexity.
+        \note There is a hidden, private overload to disallow references to
+            non-const character arrays to be created via this constructor.
+            By this, e.g. function-scope arrays used to be filled via
+            \c snprintf are excluded from consideration.
+            In such cases, the referenced string should be \b copied to the
+            GenericValue instead.
+     */
+#endif
+    template<SizeType N>
+    GenericStringRef(const CharType (&str)[N]) RAPIDJSON_NOEXCEPT
+        : s(str), length(N-1) {}
+
+    //! Explicitly create string reference from \c const character pointer
+#ifndef __clang__ // -Wdocumentation
+    /*!
+        This constructor can be used to \b explicitly  create a reference to
+        a constant string pointer.
+
+        \see StringRef(const CharType*)
+
+        \param str Constant character pointer, lifetime assumed to be longer
+            than the use of the string in e.g. a GenericValue
+
+        \post \ref s == str
+
+        \note There is a hidden, private overload to disallow references to
+            non-const character arrays to be created via this constructor.
+            By this, e.g. function-scope arrays used to be filled via
+            \c snprintf are excluded from consideration.
+            In such cases, the referenced string should be \b copied to the
+            GenericValue instead.
+     */
+#endif
+    explicit GenericStringRef(const CharType* str)
+        : s(str), length(internal::StrLen(str)){ RAPIDJSON_ASSERT(s != 0); }
+
+    //! Create constant string reference from pointer and length
+#ifndef __clang__ // -Wdocumentation
+    /*! \param str constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
+        \param len length of the string, excluding the trailing NULL terminator
+
+        \post \ref s == str && \ref length == len
+        \note Constant complexity.
+     */
+#endif
+    GenericStringRef(const CharType* str, SizeType len)
+        : s(str), length(len) { RAPIDJSON_ASSERT(s != 0); }
+
+    GenericStringRef(const GenericStringRef& rhs) : s(rhs.s), length(rhs.length) {}
+
+    //! implicit conversion to plain CharType pointer
+    operator const Ch *() const { return s; }
+
+    const Ch* const s; //!< plain CharType pointer
+    const SizeType length; //!< length of the string (excluding the trailing NULL terminator)
+
+private:
+    //! Disallow construction from non-const array
+    template<SizeType N>
+    GenericStringRef(CharType (&str)[N]) /* = delete */;
+    //! Copy assignment operator not permitted - immutable type
+    GenericStringRef& operator=(const GenericStringRef& rhs) /* = delete */;
+};
+
+//! Mark a character pointer as constant string
+/*! Mark a plain character pointer as a "string literal".  This function
+    can be used to avoid copying a character string to be referenced as a
+    value in a JSON GenericValue object, if the string's lifetime is known
+    to be valid long enough.
+    \tparam CharType Character type of the string
+    \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
+    \return GenericStringRef string reference object
+    \relatesalso GenericStringRef
+
+    \see GenericValue::GenericValue(StringRefType), GenericValue::operator=(StringRefType), GenericValue::SetString(StringRefType), GenericValue::PushBack(StringRefType, Allocator&), GenericValue::AddMember
+*/
+template<typename CharType>
+inline GenericStringRef<CharType> StringRef(const CharType* str) {
+    return GenericStringRef<CharType>(str, internal::StrLen(str));
+}
+
+//! Mark a character pointer as constant string
+/*! Mark a plain character pointer as a "string literal".  This function
+    can be used to avoid copying a character string to be referenced as a
+    value in a JSON GenericValue object, if the string's lifetime is known
+    to be valid long enough.
+
+    This version has better performance with supplied length, and also
+    supports string containing null characters.
+
+    \tparam CharType character type of the string
+    \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
+    \param length The length of source string.
+    \return GenericStringRef string reference object
+    \relatesalso GenericStringRef
+*/
+template<typename CharType>
+inline GenericStringRef<CharType> StringRef(const CharType* str, size_t length) {
+    return GenericStringRef<CharType>(str, SizeType(length));
+}
+
+#if RAPIDJSON_HAS_STDSTRING
+//! Mark a string object as constant string
+/*! Mark a string object (e.g. \c std::string) as a "string literal".
+    This function can be used to avoid copying a string to be referenced as a
+    value in a JSON GenericValue object, if the string's lifetime is known
+    to be valid long enough.
+
+    \tparam CharType character type of the string
+    \param str Constant string, lifetime assumed to be longer than the use of the string in e.g. a GenericValue
+    \return GenericStringRef string reference object
+    \relatesalso GenericStringRef
+    \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
+*/
+template<typename CharType>
+inline GenericStringRef<CharType> StringRef(const std::basic_string<CharType>& str) {
+    return GenericStringRef<CharType>(str.data(), SizeType(str.size()));
+}
+#endif
+
+///////////////////////////////////////////////////////////////////////////////
+// GenericValue type traits
+namespace internal {
+
+template <typename T, typename Encoding = void, typename Allocator = void>
+struct IsGenericValueImpl : FalseType {};
+
+// select candidates according to nested encoding and allocator types
+template <typename T> struct IsGenericValueImpl<T, typename Void<typename T::EncodingType>::Type, typename Void<typename T::AllocatorType>::Type>
+    : IsBaseOf<GenericValue<typename T::EncodingType, typename T::AllocatorType>, T>::Type {};
+
+// helper to match arbitrary GenericValue instantiations, including derived classes
+template <typename T> struct IsGenericValue : IsGenericValueImpl<T>::Type {};
+
+} // namespace internal
+
+///////////////////////////////////////////////////////////////////////////////
+// TypeHelper
+
+namespace internal {
+
+template <typename ValueType, typename T>
+struct TypeHelper {};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, bool> {
+    static bool Is(const ValueType& v) { return v.IsBool(); }
+    static bool Get(const ValueType& v) { return v.GetBool(); }
+    static ValueType& Set(ValueType& v, bool data) { return v.SetBool(data); }
+    static ValueType& Set(ValueType& v, bool data, typename ValueType::AllocatorType&) { return v.SetBool(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, int> {
+    static bool Is(const ValueType& v) { return v.IsInt(); }
+    static int Get(const ValueType& v) { return v.GetInt(); }
+    static ValueType& Set(ValueType& v, int data) { return v.SetInt(data); }
+    static ValueType& Set(ValueType& v, int data, typename ValueType::AllocatorType&) { return v.SetInt(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, unsigned> {
+    static bool Is(const ValueType& v) { return v.IsUint(); }
+    static unsigned Get(const ValueType& v) { return v.GetUint(); }
+    static ValueType& Set(ValueType& v, unsigned data) { return v.SetUint(data); }
+    static ValueType& Set(ValueType& v, unsigned data, typename ValueType::AllocatorType&) { return v.SetUint(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, int64_t> {
+    static bool Is(const ValueType& v) { return v.IsInt64(); }
+    static int64_t Get(const ValueType& v) { return v.GetInt64(); }
+    static ValueType& Set(ValueType& v, int64_t data) { return v.SetInt64(data); }
+    static ValueType& Set(ValueType& v, int64_t data, typename ValueType::AllocatorType&) { return v.SetInt64(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, uint64_t> {
+    static bool Is(const ValueType& v) { return v.IsUint64(); }
+    static uint64_t Get(const ValueType& v) { return v.GetUint64(); }
+    static ValueType& Set(ValueType& v, uint64_t data) { return v.SetUint64(data); }
+    static ValueType& Set(ValueType& v, uint64_t data, typename ValueType::AllocatorType&) { return v.SetUint64(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, double> {
+    static bool Is(const ValueType& v) { return v.IsDouble(); }
+    static double Get(const ValueType& v) { return v.GetDouble(); }
+    static ValueType& Set(ValueType& v, double data) { return v.SetDouble(data); }
+    static ValueType& Set(ValueType& v, double data, typename ValueType::AllocatorType&) { return v.SetDouble(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, float> {
+    static bool Is(const ValueType& v) { return v.IsFloat(); }
+    static float Get(const ValueType& v) { return v.GetFloat(); }
+    static ValueType& Set(ValueType& v, float data) { return v.SetFloat(data); }
+    static ValueType& Set(ValueType& v, float data, typename ValueType::AllocatorType&) { return v.SetFloat(data); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, const typename ValueType::Ch*> {
+    typedef const typename ValueType::Ch* StringType;
+    static bool Is(const ValueType& v) { return v.IsString(); }
+    static StringType Get(const ValueType& v) { return v.GetString(); }
+    static ValueType& Set(ValueType& v, const StringType data) { return v.SetString(typename ValueType::StringRefType(data)); }
+    static ValueType& Set(ValueType& v, const StringType data, typename ValueType::AllocatorType& a) { return v.SetString(data, a); }
+};
+
+#if RAPIDJSON_HAS_STDSTRING
+template<typename ValueType> 
+struct TypeHelper<ValueType, std::basic_string<typename ValueType::Ch> > {
+    typedef std::basic_string<typename ValueType::Ch> StringType;
+    static bool Is(const ValueType& v) { return v.IsString(); }
+    static StringType Get(const ValueType& v) { return StringType(v.GetString(), v.GetStringLength()); }
+    static ValueType& Set(ValueType& v, const StringType& data, typename ValueType::AllocatorType& a) { return v.SetString(data, a); }
+};
+#endif
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, typename ValueType::Array> {
+    typedef typename ValueType::Array ArrayType;
+    static bool Is(const ValueType& v) { return v.IsArray(); }
+    static ArrayType Get(ValueType& v) { return v.GetArray(); }
+    static ValueType& Set(ValueType& v, ArrayType data) { return v = data; }
+    static ValueType& Set(ValueType& v, ArrayType data, typename ValueType::AllocatorType&) { return v = data; }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, typename ValueType::ConstArray> {
+    typedef typename ValueType::ConstArray ArrayType;
+    static bool Is(const ValueType& v) { return v.IsArray(); }
+    static ArrayType Get(const ValueType& v) { return v.GetArray(); }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, typename ValueType::Object> {
+    typedef typename ValueType::Object ObjectType;
+    static bool Is(const ValueType& v) { return v.IsObject(); }
+    static ObjectType Get(ValueType& v) { return v.GetObject(); }
+    static ValueType& Set(ValueType& v, ObjectType data) { return v = data; }
+    static ValueType& Set(ValueType& v, ObjectType data, typename ValueType::AllocatorType&) { v = data; }
+};
+
+template<typename ValueType> 
+struct TypeHelper<ValueType, typename ValueType::ConstObject> {
+    typedef typename ValueType::ConstObject ObjectType;
+    static bool Is(const ValueType& v) { return v.IsObject(); }
+    static ObjectType Get(const ValueType& v) { return v.GetObject(); }
+};
+
+} // namespace internal
+
+// Forward declarations
+template <bool, typename> class GenericArray;
+template <bool, typename> class GenericObject;
+
+///////////////////////////////////////////////////////////////////////////////
+// GenericValue
+
+//! Represents a JSON value. Use Value for UTF8 encoding and default allocator.
+/*!
+    A JSON value can be one of 7 types. This class is a variant type supporting
+    these types.
+
+    Use the Value if UTF8 and default allocator
+
+    \tparam Encoding    Encoding of the value. (Even non-string values need to have the same encoding in a document)
+    \tparam Allocator   Allocator type for allocating memory of object, array and string.
+*/
+template <typename Encoding, typename Allocator = MemoryPoolAllocator<> > 
+class GenericValue {
+public:
+    //! Name-value pair in an object.
+    typedef GenericMember<Encoding, Allocator> Member;
+    typedef Encoding EncodingType;                  //!< Encoding type from template parameter.
+    typedef Allocator AllocatorType;                //!< Allocator type from template parameter.
+    typedef typename Encoding::Ch Ch;               //!< Character type derived from Encoding.
+    typedef GenericStringRef<Ch> StringRefType;     //!< Reference to a constant string
+    typedef typename GenericMemberIterator<false,Encoding,Allocator>::Iterator MemberIterator;  //!< Member iterator for iterating in object.
+    typedef typename GenericMemberIterator<true,Encoding,Allocator>::Iterator ConstMemberIterator;  //!< Constant member iterator for iterating in object.
+    typedef GenericValue* ValueIterator;            //!< Value iterator for iterating in array.
+    typedef const GenericValue* ConstValueIterator; //!< Constant value iterator for iterating in array.
+    typedef GenericValue<Encoding, Allocator> ValueType;    //!< Value type of itself.
+    typedef GenericArray<false, ValueType> Array;
+    typedef GenericArray<true, ValueType> ConstArray;
+    typedef GenericObject<false, ValueType> Object;
+    typedef GenericObject<true, ValueType> ConstObject;
+
+    //!@name Constructors and destructor.
+    //@{
+
+    //! Default constructor creates a null value.
+    GenericValue() RAPIDJSON_NOEXCEPT : data_() { data_.f.flags = kNullFlag; }
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    //! Move constructor in C++11
+    GenericValue(GenericValue&& rhs) RAPIDJSON_NOEXCEPT : data_(rhs.data_) {
+        rhs.data_.f.flags = kNullFlag; // give up contents
+    }
+#endif
+
+private:
+    //! Copy constructor is not permitted.
+    GenericValue(const GenericValue& rhs);
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    //! Moving from a GenericDocument is not permitted.
+    template <typename StackAllocator>
+    GenericValue(GenericDocument<Encoding,Allocator,StackAllocator>&& rhs);
+
+    //! Move assignment from a GenericDocument is not permitted.
+    template <typename StackAllocator>
+    GenericValue& operator=(GenericDocument<Encoding,Allocator,StackAllocator>&& rhs);
+#endif
+
+public:
+
+    //! Constructor with JSON value type.
+    /*! This creates a Value of specified type with default content.
+        \param type Type of the value.
+        \note Default content for number is zero.
+    */
+    explicit GenericValue(Type type) RAPIDJSON_NOEXCEPT : data_() {
+        static const uint16_t defaultFlags[7] = {
+            kNullFlag, kFalseFlag, kTrueFlag, kObjectFlag, kArrayFlag, kShortStringFlag,
+            kNumberAnyFlag
+        };
+        RAPIDJSON_ASSERT(type <= kNumberType);
+        data_.f.flags = defaultFlags[type];
+
+        // Use ShortString to store empty string.
+        if (type == kStringType)
+            data_.ss.SetLength(0);
+    }
+
+    //! Explicit copy constructor (with allocator)
+    /*! Creates a copy of a Value by using the given Allocator
+        \tparam SourceAllocator allocator of \c rhs
+        \param rhs Value to copy from (read-only)
+        \param allocator Allocator for allocating copied elements and buffers. Commonly use GenericDocument::GetAllocator().
+        \see CopyFrom()
+    */
+    template <typename SourceAllocator>
+    GenericValue(const GenericValue<Encoding,SourceAllocator>& rhs, Allocator& allocator) {
+        switch (rhs.GetType()) {
+        case kObjectType: {
+                SizeType count = rhs.data_.o.size;
+                Member* lm = reinterpret_cast<Member*>(allocator.Malloc(count * sizeof(Member)));
+                const typename GenericValue<Encoding,SourceAllocator>::Member* rm = rhs.GetMembersPointer();
+                for (SizeType i = 0; i < count; i++) {
+                    new (&lm[i].name) GenericValue(rm[i].name, allocator);
+                    new (&lm[i].value) GenericValue(rm[i].value, allocator);
+                }
+                data_.f.flags = kObjectFlag;
+                data_.o.size = data_.o.capacity = count;
+                SetMembersPointer(lm);
+            }
+            break;
+        case kArrayType: {
+                SizeType count = rhs.data_.a.size;
+                GenericValue* le = reinterpret_cast<GenericValue*>(allocator.Malloc(count * sizeof(GenericValue)));
+                const GenericValue<Encoding,SourceAllocator>* re = rhs.GetElementsPointer();
+                for (SizeType i = 0; i < count; i++)
+                    new (&le[i]) GenericValue(re[i], allocator);
+                data_.f.flags = kArrayFlag;
+                data_.a.size = data_.a.capacity = count;
+                SetElementsPointer(le);
+            }
+            break;
+        case kStringType:
+            if (rhs.data_.f.flags == kConstStringFlag) {
+                data_.f.flags = rhs.data_.f.flags;
+                data_  = *reinterpret_cast<const Data*>(&rhs.data_);
+            }
+            else
+                SetStringRaw(StringRef(rhs.GetString(), rhs.GetStringLength()), allocator);
+            break;
+        default:
+            data_.f.flags = rhs.data_.f.flags;
+            data_  = *reinterpret_cast<const Data*>(&rhs.data_);
+            break;
+        }
+    }
+
+    //! Constructor for boolean value.
+    /*! \param b Boolean value
+        \note This constructor is limited to \em real boolean values and rejects
+            implicitly converted types like arbitrary pointers.  Use an explicit cast
+            to \c bool, if you want to construct a boolean JSON value in such cases.
+     */
+#ifndef RAPIDJSON_DOXYGEN_RUNNING // hide SFINAE from Doxygen
+    template <typename T>
+    explicit GenericValue(T b, RAPIDJSON_ENABLEIF((internal::IsSame<bool, T>))) RAPIDJSON_NOEXCEPT  // See #472
+#else
+    explicit GenericValue(bool b) RAPIDJSON_NOEXCEPT
+#endif
+        : data_() {
+            // safe-guard against failing SFINAE
+            RAPIDJSON_STATIC_ASSERT((internal::IsSame<bool,T>::Value));
+            data_.f.flags = b ? kTrueFlag : kFalseFlag;
+    }
+
+    //! Constructor for int value.
+    explicit GenericValue(int i) RAPIDJSON_NOEXCEPT : data_() {
+        data_.n.i64 = i;
+        data_.f.flags = (i >= 0) ? (kNumberIntFlag | kUintFlag | kUint64Flag) : kNumberIntFlag;
+    }
+
+    //! Constructor for unsigned value.
+    explicit GenericValue(unsigned u) RAPIDJSON_NOEXCEPT : data_() {
+        data_.n.u64 = u; 
+        data_.f.flags = (u & 0x80000000) ? kNumberUintFlag : (kNumberUintFlag | kIntFlag | kInt64Flag);
+    }
+
+    //! Constructor for int64_t value.
+    explicit GenericValue(int64_t i64) RAPIDJSON_NOEXCEPT : data_() {
+        data_.n.i64 = i64;
+        data_.f.flags = kNumberInt64Flag;
+        if (i64 >= 0) {
+            data_.f.flags |= kNumberUint64Flag;
+            if (!(static_cast<uint64_t>(i64) & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x00000000)))
+                data_.f.flags |= kUintFlag;
+            if (!(static_cast<uint64_t>(i64) & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000)))
+                data_.f.flags |= kIntFlag;
+        }
+        else if (i64 >= static_cast<int64_t>(RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000)))
+            data_.f.flags |= kIntFlag;
+    }
+
+    //! Constructor for uint64_t value.
+    explicit GenericValue(uint64_t u64) RAPIDJSON_NOEXCEPT : data_() {
+        data_.n.u64 = u64;
+        data_.f.flags = kNumberUint64Flag;
+        if (!(u64 & RAPIDJSON_UINT64_C2(0x80000000, 0x00000000)))
+            data_.f.flags |= kInt64Flag;
+        if (!(u64 & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x00000000)))
+            data_.f.flags |= kUintFlag;
+        if (!(u64 & RAPIDJSON_UINT64_C2(0xFFFFFFFF, 0x80000000)))
+            data_.f.flags |= kIntFlag;
+    }
+
+    //! Constructor for double value.
+    explicit GenericValue(double d) RAPIDJSON_NOEXCEPT : data_() { data_.n.d = d; data_.f.flags = kNumberDoubleFlag; }
+
+    //! Constructor for float value.
+    explicit GenericValue(float f) RAPIDJSON_NOEXCEPT : data_() { data_.n.d = static_cast<double>(f); data_.f.flags = kNumberDoubleFlag; }
+
+    //! Constructor for constant string (i.e. do not make a copy of string)
+    GenericValue(const Ch* s, SizeType length) RAPIDJSON_NOEXCEPT : data_() { SetStringRaw(StringRef(s, length)); }
+
+    //! Constructor for constant string (i.e. do not make a copy of string)
+    explicit GenericValue(StringRefType s) RAPIDJSON_NOEXCEPT : data_() { SetStringRaw(s); }
+
+    //! Constructor for copy-string (i.e. do make a copy of string)
+    GenericValue(const Ch* s, SizeType length, Allocator& allocator) : data_() { SetStringRaw(StringRef(s, length), allocator); }
+
+    //! Constructor for copy-string (i.e. do make a copy of string)
+    GenericValue(const Ch*s, Allocator& allocator) : data_() { SetStringRaw(StringRef(s), allocator); }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Constructor for copy-string from a string object (i.e. do make a copy of string)
+    /*! \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
+     */
+    GenericValue(const std::basic_string<Ch>& s, Allocator& allocator) : data_() { SetStringRaw(StringRef(s), allocator); }
+#endif
+
+    //! Constructor for Array.
+    /*!
+        \param a An array obtained by \c GetArray().
+        \note \c Array is always pass-by-value.
+        \note the source array is moved into this value and the sourec array becomes empty.
+    */
+    GenericValue(Array a) RAPIDJSON_NOEXCEPT : data_(a.value_.data_) {
+        a.value_.data_ = Data();
+        a.value_.data_.f.flags = kArrayFlag;
+    }
+
+    //! Constructor for Object.
+    /*!
+        \param o An object obtained by \c GetObject().
+        \note \c Object is always pass-by-value.
+        \note the source object is moved into this value and the sourec object becomes empty.
+    */
+    GenericValue(Object o) RAPIDJSON_NOEXCEPT : data_(o.value_.data_) {
+        o.value_.data_ = Data();
+        o.value_.data_.f.flags = kObjectFlag;
+    }
+
+    //! Destructor.
+    /*! Need to destruct elements of array, members of object, or copy-string.
+    */
+    ~GenericValue() {
+        if (Allocator::kNeedFree) { // Shortcut by Allocator's trait
+            switch(data_.f.flags) {
+            case kArrayFlag:
+                {
+                    GenericValue* e = GetElementsPointer();
+                    for (GenericValue* v = e; v != e + data_.a.size; ++v)
+                        v->~GenericValue();
+                    Allocator::Free(e);
+                }
+                break;
+
+            case kObjectFlag:
+                for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m)
+                    m->~Member();
+                Allocator::Free(GetMembersPointer());
+                break;
+
+            case kCopyStringFlag:
+                Allocator::Free(const_cast<Ch*>(GetStringPointer()));
+                break;
+
+            default:
+                break;  // Do nothing for other types.
+            }
+        }
+    }
+
+    //@}
+
+    //!@name Assignment operators
+    //@{
+
+    //! Assignment with move semantics.
+    /*! \param rhs Source of the assignment. It will become a null value after assignment.
+    */
+    GenericValue& operator=(GenericValue& rhs) RAPIDJSON_NOEXCEPT {
+        RAPIDJSON_ASSERT(this != &rhs);
+        this->~GenericValue();
+        RawAssign(rhs);
+        return *this;
+    }
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    //! Move assignment in C++11
+    GenericValue& operator=(GenericValue&& rhs) RAPIDJSON_NOEXCEPT {
+        return *this = rhs.Move();
+    }
+#endif
+
+    //! Assignment of constant string reference (no copy)
+    /*! \param str Constant string reference to be assigned
+        \note This overload is needed to avoid clashes with the generic primitive type assignment overload below.
+        \see GenericStringRef, operator=(T)
+    */
+    GenericValue& operator=(StringRefType str) RAPIDJSON_NOEXCEPT {
+        GenericValue s(str);
+        return *this = s;
+    }
+
+    //! Assignment with primitive types.
+    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
+        \param value The value to be assigned.
+
+        \note The source type \c T explicitly disallows all pointer types,
+            especially (\c const) \ref Ch*.  This helps avoiding implicitly
+            referencing character strings with insufficient lifetime, use
+            \ref SetString(const Ch*, Allocator&) (for copying) or
+            \ref StringRef() (to explicitly mark the pointer as constant) instead.
+            All other pointer types would implicitly convert to \c bool,
+            use \ref SetBool() instead.
+    */
+    template <typename T>
+    RAPIDJSON_DISABLEIF_RETURN((internal::IsPointer<T>), (GenericValue&))
+    operator=(T value) {
+        GenericValue v(value);
+        return *this = v;
+    }
+
+    //! Deep-copy assignment from Value
+    /*! Assigns a \b copy of the Value to the current Value object
+        \tparam SourceAllocator Allocator type of \c rhs
+        \param rhs Value to copy from (read-only)
+        \param allocator Allocator to use for copying
+     */
+    template <typename SourceAllocator>
+    GenericValue& CopyFrom(const GenericValue<Encoding, SourceAllocator>& rhs, Allocator& allocator) {
+        RAPIDJSON_ASSERT(static_cast<void*>(this) != static_cast<void const*>(&rhs));
+        this->~GenericValue();
+        new (this) GenericValue(rhs, allocator);
+        return *this;
+    }
+
+    //! Exchange the contents of this value with those of other.
+    /*!
+        \param other Another value.
+        \note Constant complexity.
+    */
+    GenericValue& Swap(GenericValue& other) RAPIDJSON_NOEXCEPT {
+        GenericValue temp;
+        temp.RawAssign(*this);
+        RawAssign(other);
+        other.RawAssign(temp);
+        return *this;
+    }
+
+    //! free-standing swap function helper
+    /*!
+        Helper function to enable support for common swap implementation pattern based on \c std::swap:
+        \code
+        void swap(MyClass& a, MyClass& b) {
+            using std::swap;
+            swap(a.value, b.value);
+            // ...
+        }
+        \endcode
+        \see Swap()
+     */
+    friend inline void swap(GenericValue& a, GenericValue& b) RAPIDJSON_NOEXCEPT { a.Swap(b); }
+
+    //! Prepare Value for move semantics
+    /*! \return *this */
+    GenericValue& Move() RAPIDJSON_NOEXCEPT { return *this; }
+    //@}
+
+    //!@name Equal-to and not-equal-to operators
+    //@{
+    //! Equal-to operator
+    /*!
+        \note If an object contains duplicated named member, comparing equality with any object is always \c false.
+        \note Linear time complexity (number of all values in the subtree and total lengths of all strings).
+    */
+    template <typename SourceAllocator>
+    bool operator==(const GenericValue<Encoding, SourceAllocator>& rhs) const {
+        typedef GenericValue<Encoding, SourceAllocator> RhsType;
+        if (GetType() != rhs.GetType())
+            return false;
+
+        switch (GetType()) {
+        case kObjectType: // Warning: O(n^2) inner-loop
+            if (data_.o.size != rhs.data_.o.size)
+                return false;           
+            for (ConstMemberIterator lhsMemberItr = MemberBegin(); lhsMemberItr != MemberEnd(); ++lhsMemberItr) {
+                typename RhsType::ConstMemberIterator rhsMemberItr = rhs.FindMember(lhsMemberItr->name);
+                if (rhsMemberItr == rhs.MemberEnd() || lhsMemberItr->value != rhsMemberItr->value)
+                    return false;
+            }
+            return true;
+            
+        case kArrayType:
+            if (data_.a.size != rhs.data_.a.size)
+                return false;
+            for (SizeType i = 0; i < data_.a.size; i++)
+                if ((*this)[i] != rhs[i])
+                    return false;
+            return true;
+
+        case kStringType:
+            return StringEqual(rhs);
+
+        case kNumberType:
+            if (IsDouble() || rhs.IsDouble()) {
+                double a = GetDouble();     // May convert from integer to double.
+                double b = rhs.GetDouble(); // Ditto
+                return a >= b && a <= b;    // Prevent -Wfloat-equal
+            }
+            else
+                return data_.n.u64 == rhs.data_.n.u64;
+
+        default:
+            return true;
+        }
+    }
+
+    //! Equal-to operator with const C-string pointer
+    bool operator==(const Ch* rhs) const { return *this == GenericValue(StringRef(rhs)); }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Equal-to operator with string object
+    /*! \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
+     */
+    bool operator==(const std::basic_string<Ch>& rhs) const { return *this == GenericValue(StringRef(rhs)); }
+#endif
+
+    //! Equal-to operator with primitive types
+    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t, \c double, \c true, \c false
+    */
+    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>,internal::IsGenericValue<T> >), (bool)) operator==(const T& rhs) const { return *this == GenericValue(rhs); }
+
+    //! Not-equal-to operator
+    /*! \return !(*this == rhs)
+     */
+    template <typename SourceAllocator>
+    bool operator!=(const GenericValue<Encoding, SourceAllocator>& rhs) const { return !(*this == rhs); }
+
+    //! Not-equal-to operator with const C-string pointer
+    bool operator!=(const Ch* rhs) const { return !(*this == rhs); }
+
+    //! Not-equal-to operator with arbitrary types
+    /*! \return !(*this == rhs)
+     */
+    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator!=(const T& rhs) const { return !(*this == rhs); }
+
+    //! Equal-to operator with arbitrary types (symmetric version)
+    /*! \return (rhs == lhs)
+     */
+    template <typename T> friend RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator==(const T& lhs, const GenericValue& rhs) { return rhs == lhs; }
+
+    //! Not-Equal-to operator with arbitrary types (symmetric version)
+    /*! \return !(rhs == lhs)
+     */
+    template <typename T> friend RAPIDJSON_DISABLEIF_RETURN((internal::IsGenericValue<T>), (bool)) operator!=(const T& lhs, const GenericValue& rhs) { return !(rhs == lhs); }
+    //@}
+
+    //!@name Type
+    //@{
+
+    Type GetType()  const { return static_cast<Type>(data_.f.flags & kTypeMask); }
+    bool IsNull()   const { return data_.f.flags == kNullFlag; }
+    bool IsFalse()  const { return data_.f.flags == kFalseFlag; }
+    bool IsTrue()   const { return data_.f.flags == kTrueFlag; }
+    bool IsBool()   const { return (data_.f.flags & kBoolFlag) != 0; }
+    bool IsObject() const { return data_.f.flags == kObjectFlag; }
+    bool IsArray()  const { return data_.f.flags == kArrayFlag; }
+    bool IsNumber() const { return (data_.f.flags & kNumberFlag) != 0; }
+    bool IsInt()    const { return (data_.f.flags & kIntFlag) != 0; }
+    bool IsUint()   const { return (data_.f.flags & kUintFlag) != 0; }
+    bool IsInt64()  const { return (data_.f.flags & kInt64Flag) != 0; }
+    bool IsUint64() const { return (data_.f.flags & kUint64Flag) != 0; }
+    bool IsDouble() const { return (data_.f.flags & kDoubleFlag) != 0; }
+    bool IsString() const { return (data_.f.flags & kStringFlag) != 0; }
+
+    // Checks whether a number can be losslessly converted to a double.
+    bool IsLosslessDouble() const {
+        if (!IsNumber()) return false;
+        if (IsUint64()) {
+            uint64_t u = GetUint64();
+            volatile double d = static_cast<double>(u);
+            return (d >= 0.0)
+                && (d < static_cast<double>(std::numeric_limits<uint64_t>::max()))
+                && (u == static_cast<uint64_t>(d));
+        }
+        if (IsInt64()) {
+            int64_t i = GetInt64();
+            volatile double d = static_cast<double>(i);
+            return (d >= static_cast<double>(std::numeric_limits<int64_t>::min()))
+                && (d < static_cast<double>(std::numeric_limits<int64_t>::max()))
+                && (i == static_cast<int64_t>(d));
+        }
+        return true; // double, int, uint are always lossless
+    }
+
+    // Checks whether a number is a float (possible lossy).
+    bool IsFloat() const  {
+        if ((data_.f.flags & kDoubleFlag) == 0)
+            return false;
+        double d = GetDouble();
+        return d >= -3.4028234e38 && d <= 3.4028234e38;
+    }
+    // Checks whether a number can be losslessly converted to a float.
+    bool IsLosslessFloat() const {
+        if (!IsNumber()) return false;
+        double a = GetDouble();
+        if (a < static_cast<double>(-std::numeric_limits<float>::max())
+                || a > static_cast<double>(std::numeric_limits<float>::max()))
+            return false;
+        double b = static_cast<double>(static_cast<float>(a));
+        return a >= b && a <= b;    // Prevent -Wfloat-equal
+    }
+
+    //@}
+
+    //!@name Null
+    //@{
+
+    GenericValue& SetNull() { this->~GenericValue(); new (this) GenericValue(); return *this; }
+
+    //@}
+
+    //!@name Bool
+    //@{
+
+    bool GetBool() const { RAPIDJSON_ASSERT(IsBool()); return data_.f.flags == kTrueFlag; }
+    //!< Set boolean value
+    /*! \post IsBool() == true */
+    GenericValue& SetBool(bool b) { this->~GenericValue(); new (this) GenericValue(b); return *this; }
+
+    //@}
+
+    //!@name Object
+    //@{
+
+    //! Set this value as an empty object.
+    /*! \post IsObject() == true */
+    GenericValue& SetObject() { this->~GenericValue(); new (this) GenericValue(kObjectType); return *this; }
+
+    //! Get the number of members in the object.
+    SizeType MemberCount() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.size; }
+
+    //! Check whether the object is empty.
+    bool ObjectEmpty() const { RAPIDJSON_ASSERT(IsObject()); return data_.o.size == 0; }
+
+    //! Get a value from an object associated with the name.
+    /*! \pre IsObject() == true
+        \tparam T Either \c Ch or \c const \c Ch (template used for disambiguation with \ref operator[](SizeType))
+        \note In version 0.1x, if the member is not found, this function returns a null value. This makes issue 7.
+        Since 0.2, if the name is not correct, it will assert.
+        If user is unsure whether a member exists, user should use HasMember() first.
+        A better approach is to use FindMember().
+        \note Linear time complexity.
+    */
+    template <typename T>
+    RAPIDJSON_DISABLEIF_RETURN((internal::NotExpr<internal::IsSame<typename internal::RemoveConst<T>::Type, Ch> >),(GenericValue&)) operator[](T* name) {
+        GenericValue n(StringRef(name));
+        return (*this)[n];
+    }
+    template <typename T>
+    RAPIDJSON_DISABLEIF_RETURN((internal::NotExpr<internal::IsSame<typename internal::RemoveConst<T>::Type, Ch> >),(const GenericValue&)) operator[](T* name) const { return const_cast<GenericValue&>(*this)[name]; }
+
+    //! Get a value from an object associated with the name.
+    /*! \pre IsObject() == true
+        \tparam SourceAllocator Allocator of the \c name value
+
+        \note Compared to \ref operator[](T*), this version is faster because it does not need a StrLen().
+        And it can also handle strings with embedded null characters.
+
+        \note Linear time complexity.
+    */
+    template <typename SourceAllocator>
+    GenericValue& operator[](const GenericValue<Encoding, SourceAllocator>& name) {
+        MemberIterator member = FindMember(name);
+        if (member != MemberEnd())
+            return member->value;
+        else {
+            RAPIDJSON_ASSERT(false);    // see above note
+
+            // This will generate -Wexit-time-destructors in clang
+            // static GenericValue NullValue;
+            // return NullValue;
+
+            // Use static buffer and placement-new to prevent destruction
+            static char buffer[sizeof(GenericValue)];
+            return *new (buffer) GenericValue();
+        }
+    }
+    template <typename SourceAllocator>
+    const GenericValue& operator[](const GenericValue<Encoding, SourceAllocator>& name) const { return const_cast<GenericValue&>(*this)[name]; }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Get a value from an object associated with name (string object).
+    GenericValue& operator[](const std::basic_string<Ch>& name) { return (*this)[GenericValue(StringRef(name))]; }
+    const GenericValue& operator[](const std::basic_string<Ch>& name) const { return (*this)[GenericValue(StringRef(name))]; }
+#endif
+
+    //! Const member iterator
+    /*! \pre IsObject() == true */
+    ConstMemberIterator MemberBegin() const { RAPIDJSON_ASSERT(IsObject()); return ConstMemberIterator(GetMembersPointer()); }
+    //! Const \em past-the-end member iterator
+    /*! \pre IsObject() == true */
+    ConstMemberIterator MemberEnd() const   { RAPIDJSON_ASSERT(IsObject()); return ConstMemberIterator(GetMembersPointer() + data_.o.size); }
+    //! Member iterator
+    /*! \pre IsObject() == true */
+    MemberIterator MemberBegin()            { RAPIDJSON_ASSERT(IsObject()); return MemberIterator(GetMembersPointer()); }
+    //! \em Past-the-end member iterator
+    /*! \pre IsObject() == true */
+    MemberIterator MemberEnd()              { RAPIDJSON_ASSERT(IsObject()); return MemberIterator(GetMembersPointer() + data_.o.size); }
+
+    //! Check whether a member exists in the object.
+    /*!
+        \param name Member name to be searched.
+        \pre IsObject() == true
+        \return Whether a member with that name exists.
+        \note It is better to use FindMember() directly if you need the obtain the value as well.
+        \note Linear time complexity.
+    */
+    bool HasMember(const Ch* name) const { return FindMember(name) != MemberEnd(); }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Check whether a member exists in the object with string object.
+    /*!
+        \param name Member name to be searched.
+        \pre IsObject() == true
+        \return Whether a member with that name exists.
+        \note It is better to use FindMember() directly if you need the obtain the value as well.
+        \note Linear time complexity.
+    */
+    bool HasMember(const std::basic_string<Ch>& name) const { return FindMember(name) != MemberEnd(); }
+#endif
+
+    //! Check whether a member exists in the object with GenericValue name.
+    /*!
+        This version is faster because it does not need a StrLen(). It can also handle string with null character.
+        \param name Member name to be searched.
+        \pre IsObject() == true
+        \return Whether a member with that name exists.
+        \note It is better to use FindMember() directly if you need the obtain the value as well.
+        \note Linear time complexity.
+    */
+    template <typename SourceAllocator>
+    bool HasMember(const GenericValue<Encoding, SourceAllocator>& name) const { return FindMember(name) != MemberEnd(); }
+
+    //! Find member by name.
+    /*!
+        \param name Member name to be searched.
+        \pre IsObject() == true
+        \return Iterator to member, if it exists.
+            Otherwise returns \ref MemberEnd().
+
+        \note Earlier versions of Rapidjson returned a \c NULL pointer, in case
+            the requested member doesn't exist. For consistency with e.g.
+            \c std::map, this has been changed to MemberEnd() now.
+        \note Linear time complexity.
+    */
+    MemberIterator FindMember(const Ch* name) {
+        GenericValue n(StringRef(name));
+        return FindMember(n);
+    }
+
+    ConstMemberIterator FindMember(const Ch* name) const { return const_cast<GenericValue&>(*this).FindMember(name); }
+
+    //! Find member by name.
+    /*!
+        This version is faster because it does not need a StrLen(). It can also handle string with null character.
+        \param name Member name to be searched.
+        \pre IsObject() == true
+        \return Iterator to member, if it exists.
+            Otherwise returns \ref MemberEnd().
+
+        \note Earlier versions of Rapidjson returned a \c NULL pointer, in case
+            the requested member doesn't exist. For consistency with e.g.
+            \c std::map, this has been changed to MemberEnd() now.
+        \note Linear time complexity.
+    */
+    template <typename SourceAllocator>
+    MemberIterator FindMember(const GenericValue<Encoding, SourceAllocator>& name) {
+        RAPIDJSON_ASSERT(IsObject());
+        RAPIDJSON_ASSERT(name.IsString());
+        MemberIterator member = MemberBegin();
+        for ( ; member != MemberEnd(); ++member)
+            if (name.StringEqual(member->name))
+                break;
+        return member;
+    }
+    template <typename SourceAllocator> ConstMemberIterator FindMember(const GenericValue<Encoding, SourceAllocator>& name) const { return const_cast<GenericValue&>(*this).FindMember(name); }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Find member by string object name.
+    /*!
+        \param name Member name to be searched.
+        \pre IsObject() == true
+        \return Iterator to member, if it exists.
+            Otherwise returns \ref MemberEnd().
+    */
+    MemberIterator FindMember(const std::basic_string<Ch>& name) { return FindMember(GenericValue(StringRef(name))); }
+    ConstMemberIterator FindMember(const std::basic_string<Ch>& name) const { return FindMember(GenericValue(StringRef(name))); }
+#endif
+
+    //! Add a member (name-value pair) to the object.
+    /*! \param name A string value as name of member.
+        \param value Value of any type.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \note The ownership of \c name and \c value will be transferred to this object on success.
+        \pre  IsObject() && name.IsString()
+        \post name.IsNull() && value.IsNull()
+        \note Amortized Constant time complexity.
+    */
+    GenericValue& AddMember(GenericValue& name, GenericValue& value, Allocator& allocator) {
+        RAPIDJSON_ASSERT(IsObject());
+        RAPIDJSON_ASSERT(name.IsString());
+
+        ObjectData& o = data_.o;
+        if (o.size >= o.capacity) {
+            if (o.capacity == 0) {
+                o.capacity = kDefaultObjectCapacity;
+                SetMembersPointer(reinterpret_cast<Member*>(allocator.Malloc(o.capacity * sizeof(Member))));
+            }
+            else {
+                SizeType oldCapacity = o.capacity;
+                o.capacity += (oldCapacity + 1) / 2; // grow by factor 1.5
+                SetMembersPointer(reinterpret_cast<Member*>(allocator.Realloc(GetMembersPointer(), oldCapacity * sizeof(Member), o.capacity * sizeof(Member))));
+            }
+        }
+        Member* members = GetMembersPointer();
+        members[o.size].name.RawAssign(name);
+        members[o.size].value.RawAssign(value);
+        o.size++;
+        return *this;
+    }
+
+    //! Add a constant string value as member (name-value pair) to the object.
+    /*! \param name A string value as name of member.
+        \param value constant string reference as value of member.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \pre  IsObject()
+        \note This overload is needed to avoid clashes with the generic primitive type AddMember(GenericValue&,T,Allocator&) overload below.
+        \note Amortized Constant time complexity.
+    */
+    GenericValue& AddMember(GenericValue& name, StringRefType value, Allocator& allocator) {
+        GenericValue v(value);
+        return AddMember(name, v, allocator);
+    }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Add a string object as member (name-value pair) to the object.
+    /*! \param name A string value as name of member.
+        \param value constant string reference as value of member.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \pre  IsObject()
+        \note This overload is needed to avoid clashes with the generic primitive type AddMember(GenericValue&,T,Allocator&) overload below.
+        \note Amortized Constant time complexity.
+    */
+    GenericValue& AddMember(GenericValue& name, std::basic_string<Ch>& value, Allocator& allocator) {
+        GenericValue v(value, allocator);
+        return AddMember(name, v, allocator);
+    }
+#endif
+
+    //! Add any primitive value as member (name-value pair) to the object.
+    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
+        \param name A string value as name of member.
+        \param value Value of primitive type \c T as value of member
+        \param allocator Allocator for reallocating memory. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \pre  IsObject()
+
+        \note The source type \c T explicitly disallows all pointer types,
+            especially (\c const) \ref Ch*.  This helps avoiding implicitly
+            referencing character strings with insufficient lifetime, use
+            \ref AddMember(StringRefType, GenericValue&, Allocator&) or \ref
+            AddMember(StringRefType, StringRefType, Allocator&).
+            All other pointer types would implicitly convert to \c bool,
+            use an explicit cast instead, if needed.
+        \note Amortized Constant time complexity.
+    */
+    template <typename T>
+    RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&))
+    AddMember(GenericValue& name, T value, Allocator& allocator) {
+        GenericValue v(value);
+        return AddMember(name, v, allocator);
+    }
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    GenericValue& AddMember(GenericValue&& name, GenericValue&& value, Allocator& allocator) {
+        return AddMember(name, value, allocator);
+    }
+    GenericValue& AddMember(GenericValue&& name, GenericValue& value, Allocator& allocator) {
+        return AddMember(name, value, allocator);
+    }
+    GenericValue& AddMember(GenericValue& name, GenericValue&& value, Allocator& allocator) {
+        return AddMember(name, value, allocator);
+    }
+    GenericValue& AddMember(StringRefType name, GenericValue&& value, Allocator& allocator) {
+        GenericValue n(name);
+        return AddMember(n, value, allocator);
+    }
+#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
+
+
+    //! Add a member (name-value pair) to the object.
+    /*! \param name A constant string reference as name of member.
+        \param value Value of any type.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \note The ownership of \c value will be transferred to this object on success.
+        \pre  IsObject()
+        \post value.IsNull()
+        \note Amortized Constant time complexity.
+    */
+    GenericValue& AddMember(StringRefType name, GenericValue& value, Allocator& allocator) {
+        GenericValue n(name);
+        return AddMember(n, value, allocator);
+    }
+
+    //! Add a constant string value as member (name-value pair) to the object.
+    /*! \param name A constant string reference as name of member.
+        \param value constant string reference as value of member.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \pre  IsObject()
+        \note This overload is needed to avoid clashes with the generic primitive type AddMember(StringRefType,T,Allocator&) overload below.
+        \note Amortized Constant time complexity.
+    */
+    GenericValue& AddMember(StringRefType name, StringRefType value, Allocator& allocator) {
+        GenericValue v(value);
+        return AddMember(name, v, allocator);
+    }
+
+    //! Add any primitive value as member (name-value pair) to the object.
+    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
+        \param name A constant string reference as name of member.
+        \param value Value of primitive type \c T as value of member
+        \param allocator Allocator for reallocating memory. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \pre  IsObject()
+
+        \note The source type \c T explicitly disallows all pointer types,
+            especially (\c const) \ref Ch*.  This helps avoiding implicitly
+            referencing character strings with insufficient lifetime, use
+            \ref AddMember(StringRefType, GenericValue&, Allocator&) or \ref
+            AddMember(StringRefType, StringRefType, Allocator&).
+            All other pointer types would implicitly convert to \c bool,
+            use an explicit cast instead, if needed.
+        \note Amortized Constant time complexity.
+    */
+    template <typename T>
+    RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&))
+    AddMember(StringRefType name, T value, Allocator& allocator) {
+        GenericValue n(name);
+        return AddMember(n, value, allocator);
+    }
+
+    //! Remove all members in the object.
+    /*! This function do not deallocate memory in the object, i.e. the capacity is unchanged.
+        \note Linear time complexity.
+    */
+    void RemoveAllMembers() {
         RAPIDJSON_ASSERT(IsObject()); 
-        RAPIDJSON_ASSERT(data_.o.size > 0); 
-        RAPIDJSON_ASSERT(GetMembersPointer() != 0); 
-        RAPIDJSON_ASSERT(m >= MemberBegin() && m < MemberEnd()); 
- 
-        MemberIterator last(GetMembersPointer() + (data_.o.size - 1)); 
-        if (data_.o.size > 1 && m != last) 
-            *m = *last; // Move the last one to this place 
-        else 
-            m->~Member(); // Only one left, just destroy 
-        --data_.o.size; 
-        return m; 
-    } 
- 
-    //! Remove a member from an object by iterator. 
-    /*! \param pos iterator to the member to remove 
-        \pre IsObject() == true && \ref MemberBegin() <= \c pos < \ref MemberEnd() 
-        \return Iterator following the removed element. 
-            If the iterator \c pos refers to the last element, the \ref MemberEnd() iterator is returned. 
-        \note This function preserves the relative order of the remaining object 
-            members. If you do not need this, use the more efficient \ref RemoveMember(MemberIterator). 
-        \note Linear time complexity. 
-    */ 
-    MemberIterator EraseMember(ConstMemberIterator pos) { 
-        return EraseMember(pos, pos +1); 
-    } 
- 
-    //! Remove members in the range [first, last) from an object. 
-    /*! \param first iterator to the first member to remove 
-        \param last  iterator following the last member to remove 
-        \pre IsObject() == true && \ref MemberBegin() <= \c first <= \c last <= \ref MemberEnd() 
-        \return Iterator following the last removed element. 
-        \note This function preserves the relative order of the remaining object 
-            members. 
-        \note Linear time complexity. 
-    */ 
-    MemberIterator EraseMember(ConstMemberIterator first, ConstMemberIterator last) { 
-        RAPIDJSON_ASSERT(IsObject()); 
-        RAPIDJSON_ASSERT(data_.o.size > 0); 
-        RAPIDJSON_ASSERT(GetMembersPointer() != 0); 
-        RAPIDJSON_ASSERT(first >= MemberBegin()); 
-        RAPIDJSON_ASSERT(first <= last); 
-        RAPIDJSON_ASSERT(last <= MemberEnd()); 
- 
-        MemberIterator pos = MemberBegin() + (first - MemberBegin()); 
-        for (MemberIterator itr = pos; itr != last; ++itr) 
-            itr->~Member(); 
-        std::memmove(&*pos, &*last, static_cast<size_t>(MemberEnd() - last) * sizeof(Member)); 
-        data_.o.size -= static_cast<SizeType>(last - first); 
-        return pos; 
-    } 
- 
-    //! Erase a member in object by its name. 
-    /*! \param name Name of member to be removed. 
-        \return Whether the member existed. 
-        \note Linear time complexity. 
-    */ 
-    bool EraseMember(const Ch* name) { 
-        GenericValue n(StringRef(name)); 
-        return EraseMember(n); 
-    } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    bool EraseMember(const std::basic_string<Ch>& name) { return EraseMember(GenericValue(StringRef(name))); } 
-#endif 
- 
-    template <typename SourceAllocator> 
-    bool EraseMember(const GenericValue<Encoding, SourceAllocator>& name) { 
-        MemberIterator m = FindMember(name); 
-        if (m != MemberEnd()) { 
-            EraseMember(m); 
-            return true; 
-        } 
-        else 
-            return false; 
-    } 
- 
-    Object GetObject() { RAPIDJSON_ASSERT(IsObject()); return Object(*this); } 
-    ConstObject GetObject() const { RAPIDJSON_ASSERT(IsObject()); return ConstObject(*this); } 
- 
-    //@} 
- 
-    //!@name Array 
-    //@{ 
- 
-    //! Set this value as an empty array. 
-    /*! \post IsArray == true */ 
-    GenericValue& SetArray() { this->~GenericValue(); new (this) GenericValue(kArrayType); return *this; } 
- 
-    //! Get the number of elements in array. 
-    SizeType Size() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.size; } 
- 
-    //! Get the capacity of array. 
-    SizeType Capacity() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.capacity; } 
- 
-    //! Check whether the array is empty. 
-    bool Empty() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.size == 0; } 
- 
-    //! Remove all elements in the array. 
-    /*! This function do not deallocate memory in the array, i.e. the capacity is unchanged. 
-        \note Linear time complexity. 
-    */ 
-    void Clear() { 
-        RAPIDJSON_ASSERT(IsArray());  
-        GenericValue* e = GetElementsPointer(); 
-        for (GenericValue* v = e; v != e + data_.a.size; ++v) 
-            v->~GenericValue(); 
-        data_.a.size = 0; 
-    } 
- 
-    //! Get an element from array by index. 
-    /*! \pre IsArray() == true 
-        \param index Zero-based index of element. 
-        \see operator[](T*) 
-    */ 
-    GenericValue& operator[](SizeType index) { 
-        RAPIDJSON_ASSERT(IsArray()); 
-        RAPIDJSON_ASSERT(index < data_.a.size); 
-        return GetElementsPointer()[index]; 
-    } 
-    const GenericValue& operator[](SizeType index) const { return const_cast<GenericValue&>(*this)[index]; } 
- 
-    //! Element iterator 
-    /*! \pre IsArray() == true */ 
-    ValueIterator Begin() { RAPIDJSON_ASSERT(IsArray()); return GetElementsPointer(); } 
-    //! \em Past-the-end element iterator 
-    /*! \pre IsArray() == true */ 
-    ValueIterator End() { RAPIDJSON_ASSERT(IsArray()); return GetElementsPointer() + data_.a.size; } 
-    //! Constant element iterator 
-    /*! \pre IsArray() == true */ 
-    ConstValueIterator Begin() const { return const_cast<GenericValue&>(*this).Begin(); } 
-    //! Constant \em past-the-end element iterator 
-    /*! \pre IsArray() == true */ 
-    ConstValueIterator End() const { return const_cast<GenericValue&>(*this).End(); } 
- 
-    //! Request the array to have enough capacity to store elements. 
-    /*! \param newCapacity  The capacity that the array at least need to have. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \note Linear time complexity. 
-    */ 
-    GenericValue& Reserve(SizeType newCapacity, Allocator &allocator) { 
-        RAPIDJSON_ASSERT(IsArray()); 
-        if (newCapacity > data_.a.capacity) { 
-            SetElementsPointer(reinterpret_cast<GenericValue*>(allocator.Realloc(GetElementsPointer(), data_.a.capacity * sizeof(GenericValue), newCapacity * sizeof(GenericValue)))); 
-            data_.a.capacity = newCapacity; 
-        } 
-        return *this; 
-    } 
- 
-    //! Append a GenericValue at the end of the array. 
-    /*! \param value        Value to be appended. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \pre IsArray() == true 
-        \post value.IsNull() == true 
-        \return The value itself for fluent API. 
-        \note The ownership of \c value will be transferred to this array on success. 
-        \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient. 
-        \note Amortized constant time complexity. 
-    */ 
-    GenericValue& PushBack(GenericValue& value, Allocator& allocator) { 
-        RAPIDJSON_ASSERT(IsArray()); 
-        if (data_.a.size >= data_.a.capacity) 
-            Reserve(data_.a.capacity == 0 ? kDefaultArrayCapacity : (data_.a.capacity + (data_.a.capacity + 1) / 2), allocator); 
-        GetElementsPointer()[data_.a.size++].RawAssign(value); 
-        return *this; 
-    } 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    GenericValue& PushBack(GenericValue&& value, Allocator& allocator) { 
-        return PushBack(value, allocator); 
-    } 
-#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS 
- 
-    //! Append a constant string reference at the end of the array. 
-    /*! \param value        Constant string reference to be appended. 
-        \param allocator    Allocator for reallocating memory. It must be the same one used previously. Commonly use GenericDocument::GetAllocator(). 
-        \pre IsArray() == true 
-        \return The value itself for fluent API. 
-        \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient. 
-        \note Amortized constant time complexity. 
-        \see GenericStringRef 
-    */ 
-    GenericValue& PushBack(StringRefType value, Allocator& allocator) { 
-        return (*this).template PushBack<StringRefType>(value, allocator); 
-    } 
- 
-    //! Append a primitive value at the end of the array. 
-    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t 
-        \param value Value of primitive type T to be appended. 
-        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator(). 
-        \pre IsArray() == true 
-        \return The value itself for fluent API. 
-        \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient. 
- 
-        \note The source type \c T explicitly disallows all pointer types, 
-            especially (\c const) \ref Ch*.  This helps avoiding implicitly 
-            referencing character strings with insufficient lifetime, use 
-            \ref PushBack(GenericValue&, Allocator&) or \ref 
-            PushBack(StringRefType, Allocator&). 
-            All other pointer types would implicitly convert to \c bool, 
-            use an explicit cast instead, if needed. 
-        \note Amortized constant time complexity. 
-    */ 
-    template <typename T> 
-    RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&)) 
-    PushBack(T value, Allocator& allocator) { 
-        GenericValue v(value); 
-        return PushBack(v, allocator); 
-    } 
- 
-    //! Remove the last element in the array. 
-    /*! 
-        \note Constant time complexity. 
-    */ 
-    GenericValue& PopBack() { 
-        RAPIDJSON_ASSERT(IsArray()); 
-        RAPIDJSON_ASSERT(!Empty()); 
-        GetElementsPointer()[--data_.a.size].~GenericValue(); 
-        return *this; 
-    } 
- 
-    //! Remove an element of array by iterator. 
-    /*! 
-        \param pos iterator to the element to remove 
-        \pre IsArray() == true && \ref Begin() <= \c pos < \ref End() 
-        \return Iterator following the removed element. If the iterator pos refers to the last element, the End() iterator is returned. 
-        \note Linear time complexity. 
-    */ 
-    ValueIterator Erase(ConstValueIterator pos) { 
-        return Erase(pos, pos + 1); 
-    } 
- 
-    //! Remove elements in the range [first, last) of the array. 
-    /*! 
-        \param first iterator to the first element to remove 
-        \param last  iterator following the last element to remove 
-        \pre IsArray() == true && \ref Begin() <= \c first <= \c last <= \ref End() 
-        \return Iterator following the last removed element. 
-        \note Linear time complexity. 
-    */ 
-    ValueIterator Erase(ConstValueIterator first, ConstValueIterator last) { 
+        for (MemberIterator m = MemberBegin(); m != MemberEnd(); ++m)
+            m->~Member();
+        data_.o.size = 0;
+    }
+
+    //! Remove a member in object by its name.
+    /*! \param name Name of member to be removed.
+        \return Whether the member existed.
+        \note This function may reorder the object members. Use \ref
+            EraseMember(ConstMemberIterator) if you need to preserve the
+            relative order of the remaining members.
+        \note Linear time complexity.
+    */
+    bool RemoveMember(const Ch* name) {
+        GenericValue n(StringRef(name));
+        return RemoveMember(n);
+    }
+
+#if RAPIDJSON_HAS_STDSTRING
+    bool RemoveMember(const std::basic_string<Ch>& name) { return RemoveMember(GenericValue(StringRef(name))); }
+#endif
+
+    template <typename SourceAllocator>
+    bool RemoveMember(const GenericValue<Encoding, SourceAllocator>& name) {
+        MemberIterator m = FindMember(name);
+        if (m != MemberEnd()) {
+            RemoveMember(m);
+            return true;
+        }
+        else
+            return false;
+    }
+
+    //! Remove a member in object by iterator.
+    /*! \param m member iterator (obtained by FindMember() or MemberBegin()).
+        \return the new iterator after removal.
+        \note This function may reorder the object members. Use \ref
+            EraseMember(ConstMemberIterator) if you need to preserve the
+            relative order of the remaining members.
+        \note Constant time complexity.
+    */
+    MemberIterator RemoveMember(MemberIterator m) {
+        RAPIDJSON_ASSERT(IsObject());
+        RAPIDJSON_ASSERT(data_.o.size > 0);
+        RAPIDJSON_ASSERT(GetMembersPointer() != 0);
+        RAPIDJSON_ASSERT(m >= MemberBegin() && m < MemberEnd());
+
+        MemberIterator last(GetMembersPointer() + (data_.o.size - 1));
+        if (data_.o.size > 1 && m != last)
+            *m = *last; // Move the last one to this place
+        else
+            m->~Member(); // Only one left, just destroy
+        --data_.o.size;
+        return m;
+    }
+
+    //! Remove a member from an object by iterator.
+    /*! \param pos iterator to the member to remove
+        \pre IsObject() == true && \ref MemberBegin() <= \c pos < \ref MemberEnd()
+        \return Iterator following the removed element.
+            If the iterator \c pos refers to the last element, the \ref MemberEnd() iterator is returned.
+        \note This function preserves the relative order of the remaining object
+            members. If you do not need this, use the more efficient \ref RemoveMember(MemberIterator).
+        \note Linear time complexity.
+    */
+    MemberIterator EraseMember(ConstMemberIterator pos) {
+        return EraseMember(pos, pos +1);
+    }
+
+    //! Remove members in the range [first, last) from an object.
+    /*! \param first iterator to the first member to remove
+        \param last  iterator following the last member to remove
+        \pre IsObject() == true && \ref MemberBegin() <= \c first <= \c last <= \ref MemberEnd()
+        \return Iterator following the last removed element.
+        \note This function preserves the relative order of the remaining object
+            members.
+        \note Linear time complexity.
+    */
+    MemberIterator EraseMember(ConstMemberIterator first, ConstMemberIterator last) {
+        RAPIDJSON_ASSERT(IsObject());
+        RAPIDJSON_ASSERT(data_.o.size > 0);
+        RAPIDJSON_ASSERT(GetMembersPointer() != 0);
+        RAPIDJSON_ASSERT(first >= MemberBegin());
+        RAPIDJSON_ASSERT(first <= last);
+        RAPIDJSON_ASSERT(last <= MemberEnd());
+
+        MemberIterator pos = MemberBegin() + (first - MemberBegin());
+        for (MemberIterator itr = pos; itr != last; ++itr)
+            itr->~Member();
+        std::memmove(&*pos, &*last, static_cast<size_t>(MemberEnd() - last) * sizeof(Member));
+        data_.o.size -= static_cast<SizeType>(last - first);
+        return pos;
+    }
+
+    //! Erase a member in object by its name.
+    /*! \param name Name of member to be removed.
+        \return Whether the member existed.
+        \note Linear time complexity.
+    */
+    bool EraseMember(const Ch* name) {
+        GenericValue n(StringRef(name));
+        return EraseMember(n);
+    }
+
+#if RAPIDJSON_HAS_STDSTRING
+    bool EraseMember(const std::basic_string<Ch>& name) { return EraseMember(GenericValue(StringRef(name))); }
+#endif
+
+    template <typename SourceAllocator>
+    bool EraseMember(const GenericValue<Encoding, SourceAllocator>& name) {
+        MemberIterator m = FindMember(name);
+        if (m != MemberEnd()) {
+            EraseMember(m);
+            return true;
+        }
+        else
+            return false;
+    }
+
+    Object GetObject() { RAPIDJSON_ASSERT(IsObject()); return Object(*this); }
+    ConstObject GetObject() const { RAPIDJSON_ASSERT(IsObject()); return ConstObject(*this); }
+
+    //@}
+
+    //!@name Array
+    //@{
+
+    //! Set this value as an empty array.
+    /*! \post IsArray == true */
+    GenericValue& SetArray() { this->~GenericValue(); new (this) GenericValue(kArrayType); return *this; }
+
+    //! Get the number of elements in array.
+    SizeType Size() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.size; }
+
+    //! Get the capacity of array.
+    SizeType Capacity() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.capacity; }
+
+    //! Check whether the array is empty.
+    bool Empty() const { RAPIDJSON_ASSERT(IsArray()); return data_.a.size == 0; }
+
+    //! Remove all elements in the array.
+    /*! This function do not deallocate memory in the array, i.e. the capacity is unchanged.
+        \note Linear time complexity.
+    */
+    void Clear() {
         RAPIDJSON_ASSERT(IsArray()); 
-        RAPIDJSON_ASSERT(data_.a.size > 0); 
-        RAPIDJSON_ASSERT(GetElementsPointer() != 0); 
-        RAPIDJSON_ASSERT(first >= Begin()); 
-        RAPIDJSON_ASSERT(first <= last); 
-        RAPIDJSON_ASSERT(last <= End()); 
-        ValueIterator pos = Begin() + (first - Begin()); 
-        for (ValueIterator itr = pos; itr != last; ++itr) 
-            itr->~GenericValue();        
-        std::memmove(pos, last, static_cast<size_t>(End() - last) * sizeof(GenericValue)); 
-        data_.a.size -= static_cast<SizeType>(last - first); 
-        return pos; 
-    } 
- 
-    Array GetArray() { RAPIDJSON_ASSERT(IsArray()); return Array(*this); } 
-    ConstArray GetArray() const { RAPIDJSON_ASSERT(IsArray()); return ConstArray(*this); } 
- 
-    //@} 
- 
-    //!@name Number 
-    //@{ 
- 
-    int GetInt() const          { RAPIDJSON_ASSERT(data_.f.flags & kIntFlag);   return data_.n.i.i;   } 
-    unsigned GetUint() const    { RAPIDJSON_ASSERT(data_.f.flags & kUintFlag);  return data_.n.u.u;   } 
-    int64_t GetInt64() const    { RAPIDJSON_ASSERT(data_.f.flags & kInt64Flag); return data_.n.i64; } 
-    uint64_t GetUint64() const  { RAPIDJSON_ASSERT(data_.f.flags & kUint64Flag); return data_.n.u64; } 
- 
-    //! Get the value as double type. 
-    /*! \note If the value is 64-bit integer type, it may lose precision. Use \c IsLosslessDouble() to check whether the converison is lossless. 
-    */ 
-    double GetDouble() const { 
-        RAPIDJSON_ASSERT(IsNumber()); 
-        if ((data_.f.flags & kDoubleFlag) != 0)                return data_.n.d;   // exact type, no conversion. 
-        if ((data_.f.flags & kIntFlag) != 0)                   return data_.n.i.i; // int -> double 
-        if ((data_.f.flags & kUintFlag) != 0)                  return data_.n.u.u; // unsigned -> double 
-        if ((data_.f.flags & kInt64Flag) != 0)                 return static_cast<double>(data_.n.i64); // int64_t -> double (may lose precision) 
-        RAPIDJSON_ASSERT((data_.f.flags & kUint64Flag) != 0);  return static_cast<double>(data_.n.u64); // uint64_t -> double (may lose precision) 
-    } 
- 
-    //! Get the value as float type. 
-    /*! \note If the value is 64-bit integer type, it may lose precision. Use \c IsLosslessFloat() to check whether the converison is lossless. 
-    */ 
-    float GetFloat() const { 
-        return static_cast<float>(GetDouble()); 
-    } 
- 
-    GenericValue& SetInt(int i)             { this->~GenericValue(); new (this) GenericValue(i);    return *this; } 
-    GenericValue& SetUint(unsigned u)       { this->~GenericValue(); new (this) GenericValue(u);    return *this; } 
-    GenericValue& SetInt64(int64_t i64)     { this->~GenericValue(); new (this) GenericValue(i64);  return *this; } 
-    GenericValue& SetUint64(uint64_t u64)   { this->~GenericValue(); new (this) GenericValue(u64);  return *this; } 
-    GenericValue& SetDouble(double d)       { this->~GenericValue(); new (this) GenericValue(d);    return *this; } 
-    GenericValue& SetFloat(float f)         { this->~GenericValue(); new (this) GenericValue(static_cast<double>(f)); return *this; } 
- 
-    //@} 
- 
-    //!@name String 
-    //@{ 
- 
-    const Ch* GetString() const { RAPIDJSON_ASSERT(IsString()); return (data_.f.flags & kInlineStrFlag) ? data_.ss.str : GetStringPointer(); } 
- 
-    //! Get the length of string. 
-    /*! Since rapidjson permits "\\u0000" in the json string, strlen(v.GetString()) may not equal to v.GetStringLength(). 
-    */ 
-    SizeType GetStringLength() const { RAPIDJSON_ASSERT(IsString()); return ((data_.f.flags & kInlineStrFlag) ? (data_.ss.GetLength()) : data_.s.length); } 
- 
-    //! Set this value as a string without copying source string. 
-    /*! This version has better performance with supplied length, and also support string containing null character. 
-        \param s source string pointer.  
-        \param length The length of source string, excluding the trailing null terminator. 
-        \return The value itself for fluent API. 
-        \post IsString() == true && GetString() == s && GetStringLength() == length 
-        \see SetString(StringRefType) 
-    */ 
-    GenericValue& SetString(const Ch* s, SizeType length) { return SetString(StringRef(s, length)); } 
- 
-    //! Set this value as a string without copying source string. 
-    /*! \param s source string reference 
-        \return The value itself for fluent API. 
-        \post IsString() == true && GetString() == s && GetStringLength() == s.length 
-    */ 
-    GenericValue& SetString(StringRefType s) { this->~GenericValue(); SetStringRaw(s); return *this; } 
- 
-    //! Set this value as a string by copying from source string. 
-    /*! This version has better performance with supplied length, and also support string containing null character. 
-        \param s source string.  
-        \param length The length of source string, excluding the trailing null terminator. 
-        \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \post IsString() == true && GetString() != s && strcmp(GetString(),s) == 0 && GetStringLength() == length 
-    */ 
-    GenericValue& SetString(const Ch* s, SizeType length, Allocator& allocator) { this->~GenericValue(); SetStringRaw(StringRef(s, length), allocator); return *this; } 
- 
-    //! Set this value as a string by copying from source string. 
-    /*! \param s source string.  
-        \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \post IsString() == true && GetString() != s && strcmp(GetString(),s) == 0 && GetStringLength() == length 
-    */ 
-    GenericValue& SetString(const Ch* s, Allocator& allocator) { return SetString(s, internal::StrLen(s), allocator); } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    //! Set this value as a string by copying from source string. 
+        GenericValue* e = GetElementsPointer();
+        for (GenericValue* v = e; v != e + data_.a.size; ++v)
+            v->~GenericValue();
+        data_.a.size = 0;
+    }
+
+    //! Get an element from array by index.
+    /*! \pre IsArray() == true
+        \param index Zero-based index of element.
+        \see operator[](T*)
+    */
+    GenericValue& operator[](SizeType index) {
+        RAPIDJSON_ASSERT(IsArray());
+        RAPIDJSON_ASSERT(index < data_.a.size);
+        return GetElementsPointer()[index];
+    }
+    const GenericValue& operator[](SizeType index) const { return const_cast<GenericValue&>(*this)[index]; }
+
+    //! Element iterator
+    /*! \pre IsArray() == true */
+    ValueIterator Begin() { RAPIDJSON_ASSERT(IsArray()); return GetElementsPointer(); }
+    //! \em Past-the-end element iterator
+    /*! \pre IsArray() == true */
+    ValueIterator End() { RAPIDJSON_ASSERT(IsArray()); return GetElementsPointer() + data_.a.size; }
+    //! Constant element iterator
+    /*! \pre IsArray() == true */
+    ConstValueIterator Begin() const { return const_cast<GenericValue&>(*this).Begin(); }
+    //! Constant \em past-the-end element iterator
+    /*! \pre IsArray() == true */
+    ConstValueIterator End() const { return const_cast<GenericValue&>(*this).End(); }
+
+    //! Request the array to have enough capacity to store elements.
+    /*! \param newCapacity  The capacity that the array at least need to have.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \note Linear time complexity.
+    */
+    GenericValue& Reserve(SizeType newCapacity, Allocator &allocator) {
+        RAPIDJSON_ASSERT(IsArray());
+        if (newCapacity > data_.a.capacity) {
+            SetElementsPointer(reinterpret_cast<GenericValue*>(allocator.Realloc(GetElementsPointer(), data_.a.capacity * sizeof(GenericValue), newCapacity * sizeof(GenericValue))));
+            data_.a.capacity = newCapacity;
+        }
+        return *this;
+    }
+
+    //! Append a GenericValue at the end of the array.
+    /*! \param value        Value to be appended.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \pre IsArray() == true
+        \post value.IsNull() == true
+        \return The value itself for fluent API.
+        \note The ownership of \c value will be transferred to this array on success.
+        \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient.
+        \note Amortized constant time complexity.
+    */
+    GenericValue& PushBack(GenericValue& value, Allocator& allocator) {
+        RAPIDJSON_ASSERT(IsArray());
+        if (data_.a.size >= data_.a.capacity)
+            Reserve(data_.a.capacity == 0 ? kDefaultArrayCapacity : (data_.a.capacity + (data_.a.capacity + 1) / 2), allocator);
+        GetElementsPointer()[data_.a.size++].RawAssign(value);
+        return *this;
+    }
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    GenericValue& PushBack(GenericValue&& value, Allocator& allocator) {
+        return PushBack(value, allocator);
+    }
+#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
+
+    //! Append a constant string reference at the end of the array.
+    /*! \param value        Constant string reference to be appended.
+        \param allocator    Allocator for reallocating memory. It must be the same one used previously. Commonly use GenericDocument::GetAllocator().
+        \pre IsArray() == true
+        \return The value itself for fluent API.
+        \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient.
+        \note Amortized constant time complexity.
+        \see GenericStringRef
+    */
+    GenericValue& PushBack(StringRefType value, Allocator& allocator) {
+        return (*this).template PushBack<StringRefType>(value, allocator);
+    }
+
+    //! Append a primitive value at the end of the array.
+    /*! \tparam T Either \ref Type, \c int, \c unsigned, \c int64_t, \c uint64_t
+        \param value Value of primitive type T to be appended.
+        \param allocator    Allocator for reallocating memory. It must be the same one as used before. Commonly use GenericDocument::GetAllocator().
+        \pre IsArray() == true
+        \return The value itself for fluent API.
+        \note If the number of elements to be appended is known, calls Reserve() once first may be more efficient.
+
+        \note The source type \c T explicitly disallows all pointer types,
+            especially (\c const) \ref Ch*.  This helps avoiding implicitly
+            referencing character strings with insufficient lifetime, use
+            \ref PushBack(GenericValue&, Allocator&) or \ref
+            PushBack(StringRefType, Allocator&).
+            All other pointer types would implicitly convert to \c bool,
+            use an explicit cast instead, if needed.
+        \note Amortized constant time complexity.
+    */
+    template <typename T>
+    RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericValue&))
+    PushBack(T value, Allocator& allocator) {
+        GenericValue v(value);
+        return PushBack(v, allocator);
+    }
+
+    //! Remove the last element in the array.
+    /*!
+        \note Constant time complexity.
+    */
+    GenericValue& PopBack() {
+        RAPIDJSON_ASSERT(IsArray());
+        RAPIDJSON_ASSERT(!Empty());
+        GetElementsPointer()[--data_.a.size].~GenericValue();
+        return *this;
+    }
+
+    //! Remove an element of array by iterator.
+    /*!
+        \param pos iterator to the element to remove
+        \pre IsArray() == true && \ref Begin() <= \c pos < \ref End()
+        \return Iterator following the removed element. If the iterator pos refers to the last element, the End() iterator is returned.
+        \note Linear time complexity.
+    */
+    ValueIterator Erase(ConstValueIterator pos) {
+        return Erase(pos, pos + 1);
+    }
+
+    //! Remove elements in the range [first, last) of the array.
+    /*!
+        \param first iterator to the first element to remove
+        \param last  iterator following the last element to remove
+        \pre IsArray() == true && \ref Begin() <= \c first <= \c last <= \ref End()
+        \return Iterator following the last removed element.
+        \note Linear time complexity.
+    */
+    ValueIterator Erase(ConstValueIterator first, ConstValueIterator last) {
+        RAPIDJSON_ASSERT(IsArray());
+        RAPIDJSON_ASSERT(data_.a.size > 0);
+        RAPIDJSON_ASSERT(GetElementsPointer() != 0);
+        RAPIDJSON_ASSERT(first >= Begin());
+        RAPIDJSON_ASSERT(first <= last);
+        RAPIDJSON_ASSERT(last <= End());
+        ValueIterator pos = Begin() + (first - Begin());
+        for (ValueIterator itr = pos; itr != last; ++itr)
+            itr->~GenericValue();       
+        std::memmove(pos, last, static_cast<size_t>(End() - last) * sizeof(GenericValue));
+        data_.a.size -= static_cast<SizeType>(last - first);
+        return pos;
+    }
+
+    Array GetArray() { RAPIDJSON_ASSERT(IsArray()); return Array(*this); }
+    ConstArray GetArray() const { RAPIDJSON_ASSERT(IsArray()); return ConstArray(*this); }
+
+    //@}
+
+    //!@name Number
+    //@{
+
+    int GetInt() const          { RAPIDJSON_ASSERT(data_.f.flags & kIntFlag);   return data_.n.i.i;   }
+    unsigned GetUint() const    { RAPIDJSON_ASSERT(data_.f.flags & kUintFlag);  return data_.n.u.u;   }
+    int64_t GetInt64() const    { RAPIDJSON_ASSERT(data_.f.flags & kInt64Flag); return data_.n.i64; }
+    uint64_t GetUint64() const  { RAPIDJSON_ASSERT(data_.f.flags & kUint64Flag); return data_.n.u64; }
+
+    //! Get the value as double type.
+    /*! \note If the value is 64-bit integer type, it may lose precision. Use \c IsLosslessDouble() to check whether the converison is lossless.
+    */
+    double GetDouble() const {
+        RAPIDJSON_ASSERT(IsNumber());
+        if ((data_.f.flags & kDoubleFlag) != 0)                return data_.n.d;   // exact type, no conversion.
+        if ((data_.f.flags & kIntFlag) != 0)                   return data_.n.i.i; // int -> double
+        if ((data_.f.flags & kUintFlag) != 0)                  return data_.n.u.u; // unsigned -> double
+        if ((data_.f.flags & kInt64Flag) != 0)                 return static_cast<double>(data_.n.i64); // int64_t -> double (may lose precision)
+        RAPIDJSON_ASSERT((data_.f.flags & kUint64Flag) != 0);  return static_cast<double>(data_.n.u64); // uint64_t -> double (may lose precision)
+    }
+
+    //! Get the value as float type.
+    /*! \note If the value is 64-bit integer type, it may lose precision. Use \c IsLosslessFloat() to check whether the converison is lossless.
+    */
+    float GetFloat() const {
+        return static_cast<float>(GetDouble());
+    }
+
+    GenericValue& SetInt(int i)             { this->~GenericValue(); new (this) GenericValue(i);    return *this; }
+    GenericValue& SetUint(unsigned u)       { this->~GenericValue(); new (this) GenericValue(u);    return *this; }
+    GenericValue& SetInt64(int64_t i64)     { this->~GenericValue(); new (this) GenericValue(i64);  return *this; }
+    GenericValue& SetUint64(uint64_t u64)   { this->~GenericValue(); new (this) GenericValue(u64);  return *this; }
+    GenericValue& SetDouble(double d)       { this->~GenericValue(); new (this) GenericValue(d);    return *this; }
+    GenericValue& SetFloat(float f)         { this->~GenericValue(); new (this) GenericValue(static_cast<double>(f)); return *this; }
+
+    //@}
+
+    //!@name String
+    //@{
+
+    const Ch* GetString() const { RAPIDJSON_ASSERT(IsString()); return (data_.f.flags & kInlineStrFlag) ? data_.ss.str : GetStringPointer(); }
+
+    //! Get the length of string.
+    /*! Since rapidjson permits "\\u0000" in the json string, strlen(v.GetString()) may not equal to v.GetStringLength().
+    */
+    SizeType GetStringLength() const { RAPIDJSON_ASSERT(IsString()); return ((data_.f.flags & kInlineStrFlag) ? (data_.ss.GetLength()) : data_.s.length); }
+
+    //! Set this value as a string without copying source string.
+    /*! This version has better performance with supplied length, and also support string containing null character.
+        \param s source string pointer. 
+        \param length The length of source string, excluding the trailing null terminator.
+        \return The value itself for fluent API.
+        \post IsString() == true && GetString() == s && GetStringLength() == length
+        \see SetString(StringRefType)
+    */
+    GenericValue& SetString(const Ch* s, SizeType length) { return SetString(StringRef(s, length)); }
+
+    //! Set this value as a string without copying source string.
+    /*! \param s source string reference
+        \return The value itself for fluent API.
+        \post IsString() == true && GetString() == s && GetStringLength() == s.length
+    */
+    GenericValue& SetString(StringRefType s) { this->~GenericValue(); SetStringRaw(s); return *this; }
+
+    //! Set this value as a string by copying from source string.
+    /*! This version has better performance with supplied length, and also support string containing null character.
+        \param s source string. 
+        \param length The length of source string, excluding the trailing null terminator.
+        \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \post IsString() == true && GetString() != s && strcmp(GetString(),s) == 0 && GetStringLength() == length
+    */
+    GenericValue& SetString(const Ch* s, SizeType length, Allocator& allocator) { this->~GenericValue(); SetStringRaw(StringRef(s, length), allocator); return *this; }
+
+    //! Set this value as a string by copying from source string.
     /*! \param s source string. 
-        \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator(). 
-        \return The value itself for fluent API. 
-        \post IsString() == true && GetString() != s.data() && strcmp(GetString(),s.data() == 0 && GetStringLength() == s.size() 
-        \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING. 
-    */ 
-    GenericValue& SetString(const std::basic_string<Ch>& s, Allocator& allocator) { return SetString(s.data(), SizeType(s.size()), allocator); } 
-#endif 
- 
-    //@} 
- 
-    //!@name Array 
-    //@{ 
- 
-    //! Templated version for checking whether this value is type T. 
-    /*! 
-        \tparam T Either \c bool, \c int, \c unsigned, \c int64_t, \c uint64_t, \c double, \c float, \c const \c char*, \c std::basic_string<Ch> 
-    */ 
-    template <typename T> 
-    bool Is() const { return internal::TypeHelper<ValueType, T>::Is(*this); } 
- 
-    template <typename T> 
-    T Get() const { return internal::TypeHelper<ValueType, T>::Get(*this); } 
- 
-    template <typename T> 
-    T Get() { return internal::TypeHelper<ValueType, T>::Get(*this); } 
- 
-    template<typename T> 
-    ValueType& Set(const T& data) { return internal::TypeHelper<ValueType, T>::Set(*this, data); } 
- 
-    template<typename T> 
-    ValueType& Set(const T& data, AllocatorType& allocator) { return internal::TypeHelper<ValueType, T>::Set(*this, data, allocator); } 
- 
-    //@} 
- 
-    //! Generate events of this value to a Handler. 
-    /*! This function adopts the GoF visitor pattern. 
-        Typical usage is to output this JSON value as JSON text via Writer, which is a Handler. 
-        It can also be used to deep clone this value via GenericDocument, which is also a Handler. 
-        \tparam Handler type of handler. 
-        \param handler An object implementing concept Handler. 
-    */ 
-    template <typename Handler> 
-    bool Accept(Handler& handler) const { 
-        switch(GetType()) { 
-        case kNullType:     return handler.Null(); 
-        case kFalseType:    return handler.Bool(false); 
-        case kTrueType:     return handler.Bool(true); 
- 
-        case kObjectType: 
-            if (RAPIDJSON_UNLIKELY(!handler.StartObject())) 
-                return false; 
-            for (ConstMemberIterator m = MemberBegin(); m != MemberEnd(); ++m) { 
-                RAPIDJSON_ASSERT(m->name.IsString()); // User may change the type of name by MemberIterator. 
-                if (RAPIDJSON_UNLIKELY(!handler.Key(m->name.GetString(), m->name.GetStringLength(), (m->name.data_.f.flags & kCopyFlag) != 0))) 
-                    return false; 
-                if (RAPIDJSON_UNLIKELY(!m->value.Accept(handler))) 
-                    return false; 
-            } 
-            return handler.EndObject(data_.o.size); 
- 
-        case kArrayType: 
-            if (RAPIDJSON_UNLIKELY(!handler.StartArray())) 
-                return false; 
-            for (const GenericValue* v = Begin(); v != End(); ++v) 
-                if (RAPIDJSON_UNLIKELY(!v->Accept(handler))) 
-                    return false; 
-            return handler.EndArray(data_.a.size); 
-     
-        case kStringType: 
-            return handler.String(GetString(), GetStringLength(), (data_.f.flags & kCopyFlag) != 0); 
-     
-        default: 
-            RAPIDJSON_ASSERT(GetType() == kNumberType); 
-            if (IsDouble())         return handler.Double(data_.n.d); 
-            else if (IsInt())       return handler.Int(data_.n.i.i); 
-            else if (IsUint())      return handler.Uint(data_.n.u.u); 
-            else if (IsInt64())     return handler.Int64(data_.n.i64); 
-            else                    return handler.Uint64(data_.n.u64); 
-        } 
-    } 
- 
-private: 
-    template <typename, typename> friend class GenericValue; 
-    template <typename, typename, typename> friend class GenericDocument; 
- 
-    enum { 
-        kBoolFlag       = 0x0008, 
-        kNumberFlag     = 0x0010, 
-        kIntFlag        = 0x0020, 
-        kUintFlag       = 0x0040, 
-        kInt64Flag      = 0x0080, 
-        kUint64Flag     = 0x0100, 
-        kDoubleFlag     = 0x0200, 
-        kStringFlag     = 0x0400, 
-        kCopyFlag       = 0x0800, 
-        kInlineStrFlag  = 0x1000, 
- 
-        // Initial flags of different types. 
-        kNullFlag = kNullType, 
-        kTrueFlag = kTrueType | kBoolFlag, 
-        kFalseFlag = kFalseType | kBoolFlag, 
-        kNumberIntFlag = kNumberType | kNumberFlag | kIntFlag | kInt64Flag, 
-        kNumberUintFlag = kNumberType | kNumberFlag | kUintFlag | kUint64Flag | kInt64Flag, 
-        kNumberInt64Flag = kNumberType | kNumberFlag | kInt64Flag, 
-        kNumberUint64Flag = kNumberType | kNumberFlag | kUint64Flag, 
-        kNumberDoubleFlag = kNumberType | kNumberFlag | kDoubleFlag, 
-        kNumberAnyFlag = kNumberType | kNumberFlag | kIntFlag | kInt64Flag | kUintFlag | kUint64Flag | kDoubleFlag, 
-        kConstStringFlag = kStringType | kStringFlag, 
-        kCopyStringFlag = kStringType | kStringFlag | kCopyFlag, 
-        kShortStringFlag = kStringType | kStringFlag | kCopyFlag | kInlineStrFlag, 
-        kObjectFlag = kObjectType, 
-        kArrayFlag = kArrayType, 
- 
-        kTypeMask = 0x07 
-    }; 
- 
-    static const SizeType kDefaultArrayCapacity = 16; 
-    static const SizeType kDefaultObjectCapacity = 16; 
- 
-    struct Flag { 
-#if RAPIDJSON_48BITPOINTER_OPTIMIZATION 
-        char payload[sizeof(SizeType) * 2 + 6];     // 2 x SizeType + lower 48-bit pointer 
-#elif RAPIDJSON_64BIT 
-        char payload[sizeof(SizeType) * 2 + sizeof(void*) + 6]; // 6 padding bytes 
-#else 
-        char payload[sizeof(SizeType) * 2 + sizeof(void*) + 2]; // 2 padding bytes 
-#endif 
-        uint16_t flags; 
-    }; 
- 
-    struct String { 
-        SizeType length; 
-        SizeType hashcode;  //!< reserved 
-        const Ch* str; 
-    };  // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode 
- 
-    // implementation detail: ShortString can represent zero-terminated strings up to MaxSize chars 
-    // (excluding the terminating zero) and store a value to determine the length of the contained 
-    // string in the last character str[LenPos] by storing "MaxSize - length" there. If the string 
-    // to store has the maximal length of MaxSize then str[LenPos] will be 0 and therefore act as 
-    // the string terminator as well. For getting the string length back from that value just use 
-    // "MaxSize - str[LenPos]". 
-    // This allows to store 13-chars strings in 32-bit mode, 21-chars strings in 64-bit mode, 
-    // 13-chars strings for RAPIDJSON_48BITPOINTER_OPTIMIZATION=1 inline (for `UTF8`-encoded strings). 
-    struct ShortString { 
-        enum { MaxChars = sizeof(static_cast<Flag*>(0)->payload) / sizeof(Ch), MaxSize = MaxChars - 1, LenPos = MaxSize }; 
-        Ch str[MaxChars]; 
- 
-        inline static bool Usable(SizeType len) { return                       (MaxSize >= len); } 
-        inline void     SetLength(SizeType len) { str[LenPos] = static_cast<Ch>(MaxSize -  len); } 
-        inline SizeType GetLength() const       { return  static_cast<SizeType>(MaxSize -  str[LenPos]); } 
-    };  // at most as many bytes as "String" above => 12 bytes in 32-bit mode, 16 bytes in 64-bit mode 
- 
-    // By using proper binary layout, retrieval of different integer types do not need conversions. 
-    union Number { 
-#if RAPIDJSON_ENDIAN == RAPIDJSON_LITTLEENDIAN 
-        struct I { 
-            int i; 
-            char padding[4]; 
-        }i; 
-        struct U { 
-            unsigned u; 
-            char padding2[4]; 
-        }u; 
-#else 
-        struct I { 
-            char padding[4]; 
-            int i; 
-        }i; 
-        struct U { 
-            char padding2[4]; 
-            unsigned u; 
-        }u; 
-#endif 
-        int64_t i64; 
-        uint64_t u64; 
-        double d; 
-    };  // 8 bytes 
- 
-    struct ObjectData { 
-        SizeType size; 
-        SizeType capacity; 
-        Member* members; 
-    };  // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode 
- 
-    struct ArrayData { 
-        SizeType size; 
-        SizeType capacity; 
-        GenericValue* elements; 
-    };  // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode 
- 
-    union Data { 
-        String s; 
-        ShortString ss; 
-        Number n; 
-        ObjectData o; 
-        ArrayData a; 
-        Flag f; 
-    };  // 16 bytes in 32-bit mode, 24 bytes in 64-bit mode, 16 bytes in 64-bit with RAPIDJSON_48BITPOINTER_OPTIMIZATION 
- 
-    RAPIDJSON_FORCEINLINE const Ch* GetStringPointer() const { return RAPIDJSON_GETPOINTER(Ch, data_.s.str); } 
-    RAPIDJSON_FORCEINLINE const Ch* SetStringPointer(const Ch* str) { return RAPIDJSON_SETPOINTER(Ch, data_.s.str, str); } 
-    RAPIDJSON_FORCEINLINE GenericValue* GetElementsPointer() const { return RAPIDJSON_GETPOINTER(GenericValue, data_.a.elements); } 
-    RAPIDJSON_FORCEINLINE GenericValue* SetElementsPointer(GenericValue* elements) { return RAPIDJSON_SETPOINTER(GenericValue, data_.a.elements, elements); } 
-    RAPIDJSON_FORCEINLINE Member* GetMembersPointer() const { return RAPIDJSON_GETPOINTER(Member, data_.o.members); } 
-    RAPIDJSON_FORCEINLINE Member* SetMembersPointer(Member* members) { return RAPIDJSON_SETPOINTER(Member, data_.o.members, members); } 
- 
-    // Initialize this value as array with initial data, without calling destructor. 
-    void SetArrayRaw(GenericValue* values, SizeType count, Allocator& allocator) { 
-        data_.f.flags = kArrayFlag; 
-        if (count) { 
-            GenericValue* e = static_cast<GenericValue*>(allocator.Malloc(count * sizeof(GenericValue))); 
-            SetElementsPointer(e); 
-            std::memcpy(e, values, count * sizeof(GenericValue)); 
-        } 
-        else 
-            SetElementsPointer(0); 
-        data_.a.size = data_.a.capacity = count; 
-    } 
- 
-    //! Initialize this value as object with initial data, without calling destructor. 
-    void SetObjectRaw(Member* members, SizeType count, Allocator& allocator) { 
-        data_.f.flags = kObjectFlag; 
-        if (count) { 
-            Member* m = static_cast<Member*>(allocator.Malloc(count * sizeof(Member))); 
-            SetMembersPointer(m); 
-            std::memcpy(m, members, count * sizeof(Member)); 
-        } 
-        else 
-            SetMembersPointer(0); 
-        data_.o.size = data_.o.capacity = count; 
-    } 
- 
-    //! Initialize this value as constant string, without calling destructor. 
-    void SetStringRaw(StringRefType s) RAPIDJSON_NOEXCEPT { 
-        data_.f.flags = kConstStringFlag; 
-        SetStringPointer(s); 
-        data_.s.length = s.length; 
-    } 
- 
-    //! Initialize this value as copy string with initial data, without calling destructor. 
-    void SetStringRaw(StringRefType s, Allocator& allocator) { 
-        Ch* str = 0; 
-        if (ShortString::Usable(s.length)) { 
-            data_.f.flags = kShortStringFlag; 
-            data_.ss.SetLength(s.length); 
-            str = data_.ss.str; 
-        } else { 
-            data_.f.flags = kCopyStringFlag; 
-            data_.s.length = s.length; 
-            str = static_cast<Ch *>(allocator.Malloc((s.length + 1) * sizeof(Ch))); 
-            SetStringPointer(str); 
-        } 
-        std::memcpy(str, s, s.length * sizeof(Ch)); 
-        str[s.length] = '\0'; 
-    } 
- 
-    //! Assignment without calling destructor 
-    void RawAssign(GenericValue& rhs) RAPIDJSON_NOEXCEPT { 
-        data_ = rhs.data_; 
-        // data_.f.flags = rhs.data_.f.flags; 
-        rhs.data_.f.flags = kNullFlag; 
-    } 
- 
-    template <typename SourceAllocator> 
-    bool StringEqual(const GenericValue<Encoding, SourceAllocator>& rhs) const { 
-        RAPIDJSON_ASSERT(IsString()); 
-        RAPIDJSON_ASSERT(rhs.IsString()); 
- 
-        const SizeType len1 = GetStringLength(); 
-        const SizeType len2 = rhs.GetStringLength(); 
-        if(len1 != len2) { return false; } 
- 
-        const Ch* const str1 = GetString(); 
-        const Ch* const str2 = rhs.GetString(); 
-        if(str1 == str2) { return true; } // fast path for constant string 
- 
-        return (std::memcmp(str1, str2, sizeof(Ch) * len1) == 0); 
-    } 
- 
-    Data data_; 
-}; 
- 
-//! GenericValue with UTF8 encoding 
-typedef GenericValue<UTF8<> > Value; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// GenericDocument  
- 
-//! A document for parsing JSON text as DOM. 
-/*! 
-    \note implements Handler concept 
-    \tparam Encoding Encoding for both parsing and string storage. 
-    \tparam Allocator Allocator for allocating memory for the DOM 
-    \tparam StackAllocator Allocator for allocating memory for stack during parsing. 
-    \warning Although GenericDocument inherits from GenericValue, the API does \b not provide any virtual functions, especially no virtual destructor.  To avoid memory leaks, do not \c delete a GenericDocument object via a pointer to a GenericValue. 
-*/ 
-template <typename Encoding, typename Allocator = MemoryPoolAllocator<>, typename StackAllocator = CrtAllocator> 
-class GenericDocument : public GenericValue<Encoding, Allocator> { 
-public: 
-    typedef typename Encoding::Ch Ch;                       //!< Character type derived from Encoding. 
-    typedef GenericValue<Encoding, Allocator> ValueType;    //!< Value type of the document. 
-    typedef Allocator AllocatorType;                        //!< Allocator type from template parameter. 
- 
-    //! Constructor 
-    /*! Creates an empty document of specified type. 
-        \param type             Mandatory type of object to create. 
-        \param allocator        Optional allocator for allocating memory. 
-        \param stackCapacity    Optional initial capacity of stack in bytes. 
-        \param stackAllocator   Optional allocator for allocating memory for stack. 
-    */ 
-    explicit GenericDocument(Type type, Allocator* allocator = 0, size_t stackCapacity = kDefaultStackCapacity, StackAllocator* stackAllocator = 0) : 
-        GenericValue<Encoding, Allocator>(type),  allocator_(allocator), ownAllocator_(0), stack_(stackAllocator, stackCapacity), parseResult_() 
-    { 
-        if (!allocator_) 
-            ownAllocator_ = allocator_ = RAPIDJSON_NEW(Allocator)(); 
-    } 
- 
-    //! Constructor 
-    /*! Creates an empty document which type is Null.  
-        \param allocator        Optional allocator for allocating memory. 
-        \param stackCapacity    Optional initial capacity of stack in bytes. 
-        \param stackAllocator   Optional allocator for allocating memory for stack. 
-    */ 
-    GenericDocument(Allocator* allocator = 0, size_t stackCapacity = kDefaultStackCapacity, StackAllocator* stackAllocator = 0) :  
-        allocator_(allocator), ownAllocator_(0), stack_(stackAllocator, stackCapacity), parseResult_() 
-    { 
-        if (!allocator_) 
-            ownAllocator_ = allocator_ = RAPIDJSON_NEW(Allocator)(); 
-    } 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    //! Move constructor in C++11 
-    GenericDocument(GenericDocument&& rhs) RAPIDJSON_NOEXCEPT 
-        : ValueType(std::forward<ValueType>(rhs)), // explicit cast to avoid prohibited move from Document 
-          allocator_(rhs.allocator_), 
-          ownAllocator_(rhs.ownAllocator_), 
-          stack_(std::move(rhs.stack_)), 
-          parseResult_(rhs.parseResult_) 
-    { 
-        rhs.allocator_ = 0; 
-        rhs.ownAllocator_ = 0; 
-        rhs.parseResult_ = ParseResult(); 
-    } 
-#endif 
- 
-    ~GenericDocument() { 
-        Destroy(); 
-    } 
- 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    //! Move assignment in C++11 
-    GenericDocument& operator=(GenericDocument&& rhs) RAPIDJSON_NOEXCEPT 
-    { 
-        // The cast to ValueType is necessary here, because otherwise it would 
-        // attempt to call GenericValue's templated assignment operator. 
-        ValueType::operator=(std::forward<ValueType>(rhs)); 
- 
-        // Calling the destructor here would prematurely call stack_'s destructor 
-        Destroy(); 
- 
-        allocator_ = rhs.allocator_; 
-        ownAllocator_ = rhs.ownAllocator_; 
-        stack_ = std::move(rhs.stack_); 
-        parseResult_ = rhs.parseResult_; 
- 
-        rhs.allocator_ = 0; 
-        rhs.ownAllocator_ = 0; 
-        rhs.parseResult_ = ParseResult(); 
- 
-        return *this; 
-    } 
-#endif 
- 
-    //! Exchange the contents of this document with those of another. 
-    /*! 
-        \param rhs Another document. 
-        \note Constant complexity. 
-        \see GenericValue::Swap 
-    */ 
-    GenericDocument& Swap(GenericDocument& rhs) RAPIDJSON_NOEXCEPT { 
-        ValueType::Swap(rhs); 
-        stack_.Swap(rhs.stack_); 
-        internal::Swap(allocator_, rhs.allocator_); 
-        internal::Swap(ownAllocator_, rhs.ownAllocator_); 
-        internal::Swap(parseResult_, rhs.parseResult_); 
-        return *this; 
-    } 
- 
-    //! free-standing swap function helper 
-    /*! 
-        Helper function to enable support for common swap implementation pattern based on \c std::swap: 
-        \code 
-        void swap(MyClass& a, MyClass& b) { 
-            using std::swap; 
-            swap(a.doc, b.doc); 
-            // ... 
-        } 
-        \endcode 
-        \see Swap() 
-     */ 
-    friend inline void swap(GenericDocument& a, GenericDocument& b) RAPIDJSON_NOEXCEPT { a.Swap(b); } 
- 
-    //! Populate this document by a generator which produces SAX events. 
-    /*! \tparam Generator A functor with <tt>bool f(Handler)</tt> prototype. 
-        \param g Generator functor which sends SAX events to the parameter. 
-        \return The document itself for fluent API. 
-    */ 
-    template <typename Generator> 
-    GenericDocument& Populate(Generator& g) { 
-        ClearStackOnExit scope(*this); 
-        if (g(*this)) { 
-            RAPIDJSON_ASSERT(stack_.GetSize() == sizeof(ValueType)); // Got one and only one root object 
-            ValueType::operator=(*stack_.template Pop<ValueType>(1));// Move value from stack to document 
-        } 
-        return *this; 
-    } 
- 
-    //!@name Parse from stream 
-    //!@{ 
- 
-    //! Parse JSON text from an input stream (with Encoding conversion) 
-    /*! \tparam parseFlags Combination of \ref ParseFlag. 
-        \tparam SourceEncoding Encoding of input stream 
-        \tparam InputStream Type of input stream, implementing Stream concept 
-        \param is Input stream to be parsed. 
-        \return The document itself for fluent API. 
-    */ 
-    template <unsigned parseFlags, typename SourceEncoding, typename InputStream> 
-    GenericDocument& ParseStream(InputStream& is) { 
-        GenericReader<SourceEncoding, Encoding, StackAllocator> reader( 
-            stack_.HasAllocator() ? &stack_.GetAllocator() : 0); 
-        ClearStackOnExit scope(*this); 
-        parseResult_ = reader.template Parse<parseFlags>(is, *this); 
-        if (parseResult_) { 
-            RAPIDJSON_ASSERT(stack_.GetSize() == sizeof(ValueType)); // Got one and only one root object 
-            ValueType::operator=(*stack_.template Pop<ValueType>(1));// Move value from stack to document 
-        } 
-        return *this; 
-    } 
- 
-    //! Parse JSON text from an input stream 
-    /*! \tparam parseFlags Combination of \ref ParseFlag. 
-        \tparam InputStream Type of input stream, implementing Stream concept 
-        \param is Input stream to be parsed. 
-        \return The document itself for fluent API. 
-    */ 
-    template <unsigned parseFlags, typename InputStream> 
-    GenericDocument& ParseStream(InputStream& is) { 
-        return ParseStream<parseFlags, Encoding, InputStream>(is); 
-    } 
- 
-    //! Parse JSON text from an input stream (with \ref kParseDefaultFlags) 
-    /*! \tparam InputStream Type of input stream, implementing Stream concept 
-        \param is Input stream to be parsed. 
-        \return The document itself for fluent API. 
-    */ 
-    template <typename InputStream> 
-    GenericDocument& ParseStream(InputStream& is) { 
-        return ParseStream<kParseDefaultFlags, Encoding, InputStream>(is); 
-    } 
-    //!@} 
- 
-    //!@name Parse in-place from mutable string 
-    //!@{ 
- 
-    //! Parse JSON text from a mutable string 
-    /*! \tparam parseFlags Combination of \ref ParseFlag. 
-        \param str Mutable zero-terminated string to be parsed. 
-        \return The document itself for fluent API. 
-    */ 
-    template <unsigned parseFlags> 
-    GenericDocument& ParseInsitu(Ch* str) { 
-        GenericInsituStringStream<Encoding> s(str); 
-        return ParseStream<parseFlags | kParseInsituFlag>(s); 
-    } 
- 
-    //! Parse JSON text from a mutable string (with \ref kParseDefaultFlags) 
-    /*! \param str Mutable zero-terminated string to be parsed. 
-        \return The document itself for fluent API. 
-    */ 
-    GenericDocument& ParseInsitu(Ch* str) { 
-        return ParseInsitu<kParseDefaultFlags>(str); 
-    } 
-    //!@} 
- 
-    //!@name Parse from read-only string 
-    //!@{ 
- 
-    //! Parse JSON text from a read-only string (with Encoding conversion) 
-    /*! \tparam parseFlags Combination of \ref ParseFlag (must not contain \ref kParseInsituFlag). 
-        \tparam SourceEncoding Transcoding from input Encoding 
-        \param str Read-only zero-terminated string to be parsed. 
-    */ 
-    template <unsigned parseFlags, typename SourceEncoding> 
-    GenericDocument& Parse(const typename SourceEncoding::Ch* str) { 
-        RAPIDJSON_ASSERT(!(parseFlags & kParseInsituFlag)); 
-        GenericStringStream<SourceEncoding> s(str); 
-        return ParseStream<parseFlags, SourceEncoding>(s); 
-    } 
- 
-    //! Parse JSON text from a read-only string 
-    /*! \tparam parseFlags Combination of \ref ParseFlag (must not contain \ref kParseInsituFlag). 
-        \param str Read-only zero-terminated string to be parsed. 
-    */ 
-    template <unsigned parseFlags> 
-    GenericDocument& Parse(const Ch* str) { 
-        return Parse<parseFlags, Encoding>(str); 
-    } 
- 
-    //! Parse JSON text from a read-only string (with \ref kParseDefaultFlags) 
-    /*! \param str Read-only zero-terminated string to be parsed. 
-    */ 
-    GenericDocument& Parse(const Ch* str) { 
-        return Parse<kParseDefaultFlags>(str); 
-    } 
- 
-    template <unsigned parseFlags, typename SourceEncoding> 
-    GenericDocument& Parse(const typename SourceEncoding::Ch* str, size_t length) { 
-        RAPIDJSON_ASSERT(!(parseFlags & kParseInsituFlag)); 
-        MemoryStream ms(reinterpret_cast<const char*>(str), length * sizeof(typename SourceEncoding::Ch)); 
-        EncodedInputStream<SourceEncoding, MemoryStream> is(ms); 
-        ParseStream<parseFlags, SourceEncoding>(is); 
-        return *this; 
-    } 
- 
-    template <unsigned parseFlags> 
-    GenericDocument& Parse(const Ch* str, size_t length) { 
-        return Parse<parseFlags, Encoding>(str, length); 
-    } 
-     
-    GenericDocument& Parse(const Ch* str, size_t length) { 
-        return Parse<kParseDefaultFlags>(str, length); 
-    } 
- 
-#if RAPIDJSON_HAS_STDSTRING 
-    template <unsigned parseFlags, typename SourceEncoding> 
-    GenericDocument& Parse(const std::basic_string<typename SourceEncoding::Ch>& str) { 
-        // c_str() is constant complexity according to standard. Should be faster than Parse(const char*, size_t) 
-        return Parse<parseFlags, SourceEncoding>(str.c_str()); 
-    } 
- 
-    template <unsigned parseFlags> 
-    GenericDocument& Parse(const std::basic_string<Ch>& str) { 
-        return Parse<parseFlags, Encoding>(str.c_str()); 
-    } 
- 
-    GenericDocument& Parse(const std::basic_string<Ch>& str) { 
-        return Parse<kParseDefaultFlags>(str); 
-    } 
-#endif // RAPIDJSON_HAS_STDSTRING     
- 
-    //!@} 
- 
-    //!@name Handling parse errors 
-    //!@{ 
- 
-    //! Whether a parse error has occured in the last parsing. 
-    bool HasParseError() const { return parseResult_.IsError(); } 
- 
-    //! Get the \ref ParseErrorCode of last parsing. 
-    ParseErrorCode GetParseError() const { return parseResult_.Code(); } 
- 
-    //! Get the position of last parsing error in input, 0 otherwise. 
-    size_t GetErrorOffset() const { return parseResult_.Offset(); } 
- 
-    //! Implicit conversion to get the last parse result 
-#ifndef __clang // -Wdocumentation 
-    /*! \return \ref ParseResult of the last parse operation 
- 
-        \code 
-          Document doc; 
-          ParseResult ok = doc.Parse(json); 
-          if (!ok) 
-            printf( "JSON parse error: %s (%u)\n", GetParseError_En(ok.Code()), ok.Offset()); 
-        \endcode 
-     */ 
-#endif 
-    operator ParseResult() const { return parseResult_; } 
-    //!@} 
- 
-    //! Get the allocator of this document. 
-    Allocator& GetAllocator() { 
-        RAPIDJSON_ASSERT(allocator_); 
-        return *allocator_; 
-    } 
- 
-    //! Get the capacity of stack in bytes. 
-    size_t GetStackCapacity() const { return stack_.GetCapacity(); } 
- 
-private: 
-    // clear stack on any exit from ParseStream, e.g. due to exception 
-    struct ClearStackOnExit { 
-        explicit ClearStackOnExit(GenericDocument& d) : d_(d) {} 
-        ~ClearStackOnExit() { d_.ClearStack(); } 
-    private: 
-        ClearStackOnExit(const ClearStackOnExit&); 
-        ClearStackOnExit& operator=(const ClearStackOnExit&); 
-        GenericDocument& d_; 
-    }; 
- 
-    // callers of the following private Handler functions 
-    // template <typename,typename,typename> friend class GenericReader; // for parsing 
-    template <typename, typename> friend class GenericValue; // for deep copying 
- 
-public: 
-    // Implementation of Handler 
-    bool Null() { new (stack_.template Push<ValueType>()) ValueType(); return true; } 
-    bool Bool(bool b) { new (stack_.template Push<ValueType>()) ValueType(b); return true; } 
-    bool Int(int i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; } 
-    bool Uint(unsigned i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; } 
-    bool Int64(int64_t i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; } 
-    bool Uint64(uint64_t i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; } 
-    bool Double(double d) { new (stack_.template Push<ValueType>()) ValueType(d); return true; } 
- 
-    bool RawNumber(const Ch* str, SizeType length, bool copy) {  
-        if (copy)  
-            new (stack_.template Push<ValueType>()) ValueType(str, length, GetAllocator()); 
-        else 
-            new (stack_.template Push<ValueType>()) ValueType(str, length); 
-        return true; 
-    } 
- 
-    bool String(const Ch* str, SizeType length, bool copy) {  
-        if (copy)  
-            new (stack_.template Push<ValueType>()) ValueType(str, length, GetAllocator()); 
-        else 
-            new (stack_.template Push<ValueType>()) ValueType(str, length); 
-        return true; 
-    } 
- 
-    bool StartObject() { new (stack_.template Push<ValueType>()) ValueType(kObjectType); return true; } 
-     
-    bool Key(const Ch* str, SizeType length, bool copy) { return String(str, length, copy); } 
- 
-    bool EndObject(SizeType memberCount) { 
-        typename ValueType::Member* members = stack_.template Pop<typename ValueType::Member>(memberCount); 
-        stack_.template Top<ValueType>()->SetObjectRaw(members, memberCount, GetAllocator()); 
-        return true; 
-    } 
- 
-    bool StartArray() { new (stack_.template Push<ValueType>()) ValueType(kArrayType); return true; } 
-     
-    bool EndArray(SizeType elementCount) { 
-        ValueType* elements = stack_.template Pop<ValueType>(elementCount); 
-        stack_.template Top<ValueType>()->SetArrayRaw(elements, elementCount, GetAllocator()); 
-        return true; 
-    } 
- 
-private: 
-    //! Prohibit copying 
-    GenericDocument(const GenericDocument&); 
-    //! Prohibit assignment 
-    GenericDocument& operator=(const GenericDocument&); 
- 
-    void ClearStack() { 
-        if (Allocator::kNeedFree) 
-            while (stack_.GetSize() > 0)    // Here assumes all elements in stack array are GenericValue (Member is actually 2 GenericValue objects) 
-                (stack_.template Pop<ValueType>(1))->~ValueType(); 
-        else 
-            stack_.Clear(); 
-        stack_.ShrinkToFit(); 
-    } 
- 
-    void Destroy() { 
-        RAPIDJSON_DELETE(ownAllocator_); 
-    } 
- 
-    static const size_t kDefaultStackCapacity = 1024; 
-    Allocator* allocator_; 
-    Allocator* ownAllocator_; 
-    internal::Stack<StackAllocator> stack_; 
-    ParseResult parseResult_; 
-}; 
- 
-//! GenericDocument with UTF8 encoding 
-typedef GenericDocument<UTF8<> > Document; 
- 
-//! Helper class for accessing Value of array type. 
-/*! 
-    Instance of this helper class is obtained by \c GenericValue::GetArray(). 
-    In addition to all APIs for array type, it provides range-based for loop if \c RAPIDJSON_HAS_CXX11_RANGE_FOR=1. 
-*/ 
-template <bool Const, typename ValueT> 
-class GenericArray { 
-public: 
-    typedef GenericArray<true, ValueT> ConstArray; 
-    typedef GenericArray<false, ValueT> Array; 
-    typedef ValueT PlainType; 
-    typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType; 
-    typedef ValueType* ValueIterator;  // This may be const or non-const iterator 
-    typedef const ValueT* ConstValueIterator; 
-    typedef typename ValueType::AllocatorType AllocatorType; 
-    typedef typename ValueType::StringRefType StringRefType; 
- 
-    template <typename, typename> 
-    friend class GenericValue; 
- 
-    GenericArray(const GenericArray& rhs) : value_(rhs.value_) {} 
-    GenericArray& operator=(const GenericArray& rhs) { value_ = rhs.value_; return *this; } 
-    ~GenericArray() {} 
- 
-    SizeType Size() const { return value_.Size(); } 
-    SizeType Capacity() const { return value_.Capacity(); } 
-    bool Empty() const { return value_.Empty(); } 
-    void Clear() const { value_.Clear(); } 
-    ValueType& operator[](SizeType index) const {  return value_[index]; } 
-    ValueIterator Begin() const { return value_.Begin(); } 
-    ValueIterator End() const { return value_.End(); } 
-    GenericArray Reserve(SizeType newCapacity, AllocatorType &allocator) const { value_.Reserve(newCapacity, allocator); return *this; } 
-    GenericArray PushBack(ValueType& value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; } 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    GenericArray PushBack(ValueType&& value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; } 
-#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    GenericArray PushBack(StringRefType value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; } 
-    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (const GenericArray&)) PushBack(T value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; } 
-    GenericArray PopBack() const { value_.PopBack(); return *this; } 
-    ValueIterator Erase(ConstValueIterator pos) const { return value_.Erase(pos); } 
-    ValueIterator Erase(ConstValueIterator first, ConstValueIterator last) const { return value_.Erase(first, last); } 
- 
-#if RAPIDJSON_HAS_CXX11_RANGE_FOR 
-    ValueIterator begin() const { return value_.Begin(); } 
-    ValueIterator end() const { return value_.End(); } 
-#endif 
- 
-private: 
-    GenericArray(); 
-    GenericArray(ValueType& value) : value_(value) {} 
-    ValueType& value_; 
-}; 
- 
-//! Helper class for accessing Value of object type. 
-/*! 
-    Instance of this helper class is obtained by \c GenericValue::GetObject(). 
-    In addition to all APIs for array type, it provides range-based for loop if \c RAPIDJSON_HAS_CXX11_RANGE_FOR=1. 
-*/ 
-template <bool Const, typename ValueT> 
-class GenericObject { 
-public: 
-    typedef GenericObject<true, ValueT> ConstObject; 
-    typedef GenericObject<false, ValueT> Object; 
-    typedef ValueT PlainType; 
-    typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType; 
-    typedef GenericMemberIterator<Const, typename ValueT::EncodingType, typename ValueT::AllocatorType> MemberIterator;  // This may be const or non-const iterator 
-    typedef GenericMemberIterator<true, typename ValueT::EncodingType, typename ValueT::AllocatorType> ConstMemberIterator; 
-    typedef typename ValueType::AllocatorType AllocatorType; 
-    typedef typename ValueType::StringRefType StringRefType; 
-    typedef typename ValueType::EncodingType EncodingType; 
-    typedef typename ValueType::Ch Ch; 
- 
-    template <typename, typename> 
-    friend class GenericValue; 
- 
-    GenericObject(const GenericObject& rhs) : value_(rhs.value_) {} 
-    GenericObject& operator=(const GenericObject& rhs) { value_ = rhs.value_; return *this; } 
-    ~GenericObject() {} 
- 
-    SizeType MemberCount() const { return value_.MemberCount(); } 
-    bool ObjectEmpty() const { return value_.ObjectEmpty(); } 
-    template <typename T> ValueType& operator[](T* name) const { return value_[name]; } 
-    template <typename SourceAllocator> ValueType& operator[](const GenericValue<EncodingType, SourceAllocator>& name) const { return value_[name]; } 
-#if RAPIDJSON_HAS_STDSTRING 
-    ValueType& operator[](const std::basic_string<Ch>& name) const { return value_[name]; } 
-#endif 
-    MemberIterator MemberBegin() const { return value_.MemberBegin(); } 
-    MemberIterator MemberEnd() const { return value_.MemberEnd(); } 
-    bool HasMember(const Ch* name) const { return value_.HasMember(name); } 
-#if RAPIDJSON_HAS_STDSTRING 
-    bool HasMember(const std::basic_string<Ch>& name) const { return value_.HasMember(name); } 
-#endif 
-    template <typename SourceAllocator> bool HasMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.HasMember(name); } 
-    MemberIterator FindMember(const Ch* name) const { return value_.FindMember(name); } 
-    template <typename SourceAllocator> MemberIterator FindMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.FindMember(name); } 
-#if RAPIDJSON_HAS_STDSTRING 
-    MemberIterator FindMember(const std::basic_string<Ch>& name) const { return value_.FindMember(name); } 
-#endif 
-    GenericObject AddMember(ValueType& name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    GenericObject AddMember(ValueType& name, StringRefType value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-#if RAPIDJSON_HAS_STDSTRING 
-    GenericObject AddMember(ValueType& name, std::basic_string<Ch>& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-#endif 
-    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (ValueType&)) AddMember(ValueType& name, T value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-#if RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    GenericObject AddMember(ValueType&& name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    GenericObject AddMember(ValueType&& name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    GenericObject AddMember(ValueType& name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    GenericObject AddMember(StringRefType name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS 
-    GenericObject AddMember(StringRefType name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    GenericObject AddMember(StringRefType name, StringRefType value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericObject)) AddMember(StringRefType name, T value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; } 
-    void RemoveAllMembers() { value_.RemoveAllMembers(); } 
-    bool RemoveMember(const Ch* name) const { return value_.RemoveMember(name); } 
-#if RAPIDJSON_HAS_STDSTRING 
-    bool RemoveMember(const std::basic_string<Ch>& name) const { return value_.RemoveMember(name); } 
-#endif 
-    template <typename SourceAllocator> bool RemoveMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.RemoveMember(name); } 
-    MemberIterator RemoveMember(MemberIterator m) const { return value_.RemoveMember(m); } 
-    MemberIterator EraseMember(ConstMemberIterator pos) const { return value_.EraseMember(pos); } 
-    MemberIterator EraseMember(ConstMemberIterator first, ConstMemberIterator last) const { return value_.EraseMember(first, last); } 
-    bool EraseMember(const Ch* name) const { return value_.EraseMember(name); } 
-#if RAPIDJSON_HAS_STDSTRING 
-    bool EraseMember(const std::basic_string<Ch>& name) const { return EraseMember(ValueType(StringRef(name))); } 
-#endif 
-    template <typename SourceAllocator> bool EraseMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.EraseMember(name); } 
- 
-#if RAPIDJSON_HAS_CXX11_RANGE_FOR 
-    MemberIterator begin() const { return value_.MemberBegin(); } 
-    MemberIterator end() const { return value_.MemberEnd(); } 
-#endif 
- 
-private: 
-    GenericObject(); 
-    GenericObject(ValueType& value) : value_(value) {} 
-    ValueType& value_; 
-}; 
- 
-RAPIDJSON_NAMESPACE_END 
-#ifdef _MINWINDEF_       // see: http://stackoverflow.com/questions/22744262/cant-call-stdmax-because-minwindef-h-defines-max 
-#ifndef NOMINMAX 
-#pragma pop_macro("min") 
-#pragma pop_macro("max") 
-#endif 
-#endif 
-RAPIDJSON_DIAG_POP 
- 
-#endif // RAPIDJSON_DOCUMENT_H_ 
+        \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \post IsString() == true && GetString() != s && strcmp(GetString(),s) == 0 && GetStringLength() == length
+    */
+    GenericValue& SetString(const Ch* s, Allocator& allocator) { return SetString(s, internal::StrLen(s), allocator); }
+
+#if RAPIDJSON_HAS_STDSTRING
+    //! Set this value as a string by copying from source string.
+    /*! \param s source string.
+        \param allocator Allocator for allocating copied buffer. Commonly use GenericDocument::GetAllocator().
+        \return The value itself for fluent API.
+        \post IsString() == true && GetString() != s.data() && strcmp(GetString(),s.data() == 0 && GetStringLength() == s.size()
+        \note Requires the definition of the preprocessor symbol \ref RAPIDJSON_HAS_STDSTRING.
+    */
+    GenericValue& SetString(const std::basic_string<Ch>& s, Allocator& allocator) { return SetString(s.data(), SizeType(s.size()), allocator); }
+#endif
+
+    //@}
+
+    //!@name Array
+    //@{
+
+    //! Templated version for checking whether this value is type T.
+    /*!
+        \tparam T Either \c bool, \c int, \c unsigned, \c int64_t, \c uint64_t, \c double, \c float, \c const \c char*, \c std::basic_string<Ch>
+    */
+    template <typename T>
+    bool Is() const { return internal::TypeHelper<ValueType, T>::Is(*this); }
+
+    template <typename T>
+    T Get() const { return internal::TypeHelper<ValueType, T>::Get(*this); }
+
+    template <typename T>
+    T Get() { return internal::TypeHelper<ValueType, T>::Get(*this); }
+
+    template<typename T>
+    ValueType& Set(const T& data) { return internal::TypeHelper<ValueType, T>::Set(*this, data); }
+
+    template<typename T>
+    ValueType& Set(const T& data, AllocatorType& allocator) { return internal::TypeHelper<ValueType, T>::Set(*this, data, allocator); }
+
+    //@}
+
+    //! Generate events of this value to a Handler.
+    /*! This function adopts the GoF visitor pattern.
+        Typical usage is to output this JSON value as JSON text via Writer, which is a Handler.
+        It can also be used to deep clone this value via GenericDocument, which is also a Handler.
+        \tparam Handler type of handler.
+        \param handler An object implementing concept Handler.
+    */
+    template <typename Handler>
+    bool Accept(Handler& handler) const {
+        switch(GetType()) {
+        case kNullType:     return handler.Null();
+        case kFalseType:    return handler.Bool(false);
+        case kTrueType:     return handler.Bool(true);
+
+        case kObjectType:
+            if (RAPIDJSON_UNLIKELY(!handler.StartObject()))
+                return false;
+            for (ConstMemberIterator m = MemberBegin(); m != MemberEnd(); ++m) {
+                RAPIDJSON_ASSERT(m->name.IsString()); // User may change the type of name by MemberIterator.
+                if (RAPIDJSON_UNLIKELY(!handler.Key(m->name.GetString(), m->name.GetStringLength(), (m->name.data_.f.flags & kCopyFlag) != 0)))
+                    return false;
+                if (RAPIDJSON_UNLIKELY(!m->value.Accept(handler)))
+                    return false;
+            }
+            return handler.EndObject(data_.o.size);
+
+        case kArrayType:
+            if (RAPIDJSON_UNLIKELY(!handler.StartArray()))
+                return false;
+            for (const GenericValue* v = Begin(); v != End(); ++v)
+                if (RAPIDJSON_UNLIKELY(!v->Accept(handler)))
+                    return false;
+            return handler.EndArray(data_.a.size);
+    
+        case kStringType:
+            return handler.String(GetString(), GetStringLength(), (data_.f.flags & kCopyFlag) != 0);
+    
+        default:
+            RAPIDJSON_ASSERT(GetType() == kNumberType);
+            if (IsDouble())         return handler.Double(data_.n.d);
+            else if (IsInt())       return handler.Int(data_.n.i.i);
+            else if (IsUint())      return handler.Uint(data_.n.u.u);
+            else if (IsInt64())     return handler.Int64(data_.n.i64);
+            else                    return handler.Uint64(data_.n.u64);
+        }
+    }
+
+private:
+    template <typename, typename> friend class GenericValue;
+    template <typename, typename, typename> friend class GenericDocument;
+
+    enum {
+        kBoolFlag       = 0x0008,
+        kNumberFlag     = 0x0010,
+        kIntFlag        = 0x0020,
+        kUintFlag       = 0x0040,
+        kInt64Flag      = 0x0080,
+        kUint64Flag     = 0x0100,
+        kDoubleFlag     = 0x0200,
+        kStringFlag     = 0x0400,
+        kCopyFlag       = 0x0800,
+        kInlineStrFlag  = 0x1000,
+
+        // Initial flags of different types.
+        kNullFlag = kNullType,
+        kTrueFlag = kTrueType | kBoolFlag,
+        kFalseFlag = kFalseType | kBoolFlag,
+        kNumberIntFlag = kNumberType | kNumberFlag | kIntFlag | kInt64Flag,
+        kNumberUintFlag = kNumberType | kNumberFlag | kUintFlag | kUint64Flag | kInt64Flag,
+        kNumberInt64Flag = kNumberType | kNumberFlag | kInt64Flag,
+        kNumberUint64Flag = kNumberType | kNumberFlag | kUint64Flag,
+        kNumberDoubleFlag = kNumberType | kNumberFlag | kDoubleFlag,
+        kNumberAnyFlag = kNumberType | kNumberFlag | kIntFlag | kInt64Flag | kUintFlag | kUint64Flag | kDoubleFlag,
+        kConstStringFlag = kStringType | kStringFlag,
+        kCopyStringFlag = kStringType | kStringFlag | kCopyFlag,
+        kShortStringFlag = kStringType | kStringFlag | kCopyFlag | kInlineStrFlag,
+        kObjectFlag = kObjectType,
+        kArrayFlag = kArrayType,
+
+        kTypeMask = 0x07
+    };
+
+    static const SizeType kDefaultArrayCapacity = 16;
+    static const SizeType kDefaultObjectCapacity = 16;
+
+    struct Flag {
+#if RAPIDJSON_48BITPOINTER_OPTIMIZATION
+        char payload[sizeof(SizeType) * 2 + 6];     // 2 x SizeType + lower 48-bit pointer
+#elif RAPIDJSON_64BIT
+        char payload[sizeof(SizeType) * 2 + sizeof(void*) + 6]; // 6 padding bytes
+#else
+        char payload[sizeof(SizeType) * 2 + sizeof(void*) + 2]; // 2 padding bytes
+#endif
+        uint16_t flags;
+    };
+
+    struct String {
+        SizeType length;
+        SizeType hashcode;  //!< reserved
+        const Ch* str;
+    };  // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
+
+    // implementation detail: ShortString can represent zero-terminated strings up to MaxSize chars
+    // (excluding the terminating zero) and store a value to determine the length of the contained
+    // string in the last character str[LenPos] by storing "MaxSize - length" there. If the string
+    // to store has the maximal length of MaxSize then str[LenPos] will be 0 and therefore act as
+    // the string terminator as well. For getting the string length back from that value just use
+    // "MaxSize - str[LenPos]".
+    // This allows to store 13-chars strings in 32-bit mode, 21-chars strings in 64-bit mode,
+    // 13-chars strings for RAPIDJSON_48BITPOINTER_OPTIMIZATION=1 inline (for `UTF8`-encoded strings).
+    struct ShortString {
+        enum { MaxChars = sizeof(static_cast<Flag*>(0)->payload) / sizeof(Ch), MaxSize = MaxChars - 1, LenPos = MaxSize };
+        Ch str[MaxChars];
+
+        inline static bool Usable(SizeType len) { return                       (MaxSize >= len); }
+        inline void     SetLength(SizeType len) { str[LenPos] = static_cast<Ch>(MaxSize -  len); }
+        inline SizeType GetLength() const       { return  static_cast<SizeType>(MaxSize -  str[LenPos]); }
+    };  // at most as many bytes as "String" above => 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
+
+    // By using proper binary layout, retrieval of different integer types do not need conversions.
+    union Number {
+#if RAPIDJSON_ENDIAN == RAPIDJSON_LITTLEENDIAN
+        struct I {
+            int i;
+            char padding[4];
+        }i;
+        struct U {
+            unsigned u;
+            char padding2[4];
+        }u;
+#else
+        struct I {
+            char padding[4];
+            int i;
+        }i;
+        struct U {
+            char padding2[4];
+            unsigned u;
+        }u;
+#endif
+        int64_t i64;
+        uint64_t u64;
+        double d;
+    };  // 8 bytes
+
+    struct ObjectData {
+        SizeType size;
+        SizeType capacity;
+        Member* members;
+    };  // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
+
+    struct ArrayData {
+        SizeType size;
+        SizeType capacity;
+        GenericValue* elements;
+    };  // 12 bytes in 32-bit mode, 16 bytes in 64-bit mode
+
+    union Data {
+        String s;
+        ShortString ss;
+        Number n;
+        ObjectData o;
+        ArrayData a;
+        Flag f;
+    };  // 16 bytes in 32-bit mode, 24 bytes in 64-bit mode, 16 bytes in 64-bit with RAPIDJSON_48BITPOINTER_OPTIMIZATION
+
+    RAPIDJSON_FORCEINLINE const Ch* GetStringPointer() const { return RAPIDJSON_GETPOINTER(Ch, data_.s.str); }
+    RAPIDJSON_FORCEINLINE const Ch* SetStringPointer(const Ch* str) { return RAPIDJSON_SETPOINTER(Ch, data_.s.str, str); }
+    RAPIDJSON_FORCEINLINE GenericValue* GetElementsPointer() const { return RAPIDJSON_GETPOINTER(GenericValue, data_.a.elements); }
+    RAPIDJSON_FORCEINLINE GenericValue* SetElementsPointer(GenericValue* elements) { return RAPIDJSON_SETPOINTER(GenericValue, data_.a.elements, elements); }
+    RAPIDJSON_FORCEINLINE Member* GetMembersPointer() const { return RAPIDJSON_GETPOINTER(Member, data_.o.members); }
+    RAPIDJSON_FORCEINLINE Member* SetMembersPointer(Member* members) { return RAPIDJSON_SETPOINTER(Member, data_.o.members, members); }
+
+    // Initialize this value as array with initial data, without calling destructor.
+    void SetArrayRaw(GenericValue* values, SizeType count, Allocator& allocator) {
+        data_.f.flags = kArrayFlag;
+        if (count) {
+            GenericValue* e = static_cast<GenericValue*>(allocator.Malloc(count * sizeof(GenericValue)));
+            SetElementsPointer(e);
+            std::memcpy(e, values, count * sizeof(GenericValue));
+        }
+        else
+            SetElementsPointer(0);
+        data_.a.size = data_.a.capacity = count;
+    }
+
+    //! Initialize this value as object with initial data, without calling destructor.
+    void SetObjectRaw(Member* members, SizeType count, Allocator& allocator) {
+        data_.f.flags = kObjectFlag;
+        if (count) {
+            Member* m = static_cast<Member*>(allocator.Malloc(count * sizeof(Member)));
+            SetMembersPointer(m);
+            std::memcpy(m, members, count * sizeof(Member));
+        }
+        else
+            SetMembersPointer(0);
+        data_.o.size = data_.o.capacity = count;
+    }
+
+    //! Initialize this value as constant string, without calling destructor.
+    void SetStringRaw(StringRefType s) RAPIDJSON_NOEXCEPT {
+        data_.f.flags = kConstStringFlag;
+        SetStringPointer(s);
+        data_.s.length = s.length;
+    }
+
+    //! Initialize this value as copy string with initial data, without calling destructor.
+    void SetStringRaw(StringRefType s, Allocator& allocator) {
+        Ch* str = 0;
+        if (ShortString::Usable(s.length)) {
+            data_.f.flags = kShortStringFlag;
+            data_.ss.SetLength(s.length);
+            str = data_.ss.str;
+        } else {
+            data_.f.flags = kCopyStringFlag;
+            data_.s.length = s.length;
+            str = static_cast<Ch *>(allocator.Malloc((s.length + 1) * sizeof(Ch)));
+            SetStringPointer(str);
+        }
+        std::memcpy(str, s, s.length * sizeof(Ch));
+        str[s.length] = '\0';
+    }
+
+    //! Assignment without calling destructor
+    void RawAssign(GenericValue& rhs) RAPIDJSON_NOEXCEPT {
+        data_ = rhs.data_;
+        // data_.f.flags = rhs.data_.f.flags;
+        rhs.data_.f.flags = kNullFlag;
+    }
+
+    template <typename SourceAllocator>
+    bool StringEqual(const GenericValue<Encoding, SourceAllocator>& rhs) const {
+        RAPIDJSON_ASSERT(IsString());
+        RAPIDJSON_ASSERT(rhs.IsString());
+
+        const SizeType len1 = GetStringLength();
+        const SizeType len2 = rhs.GetStringLength();
+        if(len1 != len2) { return false; }
+
+        const Ch* const str1 = GetString();
+        const Ch* const str2 = rhs.GetString();
+        if(str1 == str2) { return true; } // fast path for constant string
+
+        return (std::memcmp(str1, str2, sizeof(Ch) * len1) == 0);
+    }
+
+    Data data_;
+};
+
+//! GenericValue with UTF8 encoding
+typedef GenericValue<UTF8<> > Value;
+
+///////////////////////////////////////////////////////////////////////////////
+// GenericDocument 
+
+//! A document for parsing JSON text as DOM.
+/*!
+    \note implements Handler concept
+    \tparam Encoding Encoding for both parsing and string storage.
+    \tparam Allocator Allocator for allocating memory for the DOM
+    \tparam StackAllocator Allocator for allocating memory for stack during parsing.
+    \warning Although GenericDocument inherits from GenericValue, the API does \b not provide any virtual functions, especially no virtual destructor.  To avoid memory leaks, do not \c delete a GenericDocument object via a pointer to a GenericValue.
+*/
+template <typename Encoding, typename Allocator = MemoryPoolAllocator<>, typename StackAllocator = CrtAllocator>
+class GenericDocument : public GenericValue<Encoding, Allocator> {
+public:
+    typedef typename Encoding::Ch Ch;                       //!< Character type derived from Encoding.
+    typedef GenericValue<Encoding, Allocator> ValueType;    //!< Value type of the document.
+    typedef Allocator AllocatorType;                        //!< Allocator type from template parameter.
+
+    //! Constructor
+    /*! Creates an empty document of specified type.
+        \param type             Mandatory type of object to create.
+        \param allocator        Optional allocator for allocating memory.
+        \param stackCapacity    Optional initial capacity of stack in bytes.
+        \param stackAllocator   Optional allocator for allocating memory for stack.
+    */
+    explicit GenericDocument(Type type, Allocator* allocator = 0, size_t stackCapacity = kDefaultStackCapacity, StackAllocator* stackAllocator = 0) :
+        GenericValue<Encoding, Allocator>(type),  allocator_(allocator), ownAllocator_(0), stack_(stackAllocator, stackCapacity), parseResult_()
+    {
+        if (!allocator_)
+            ownAllocator_ = allocator_ = RAPIDJSON_NEW(Allocator)();
+    }
+
+    //! Constructor
+    /*! Creates an empty document which type is Null. 
+        \param allocator        Optional allocator for allocating memory.
+        \param stackCapacity    Optional initial capacity of stack in bytes.
+        \param stackAllocator   Optional allocator for allocating memory for stack.
+    */
+    GenericDocument(Allocator* allocator = 0, size_t stackCapacity = kDefaultStackCapacity, StackAllocator* stackAllocator = 0) : 
+        allocator_(allocator), ownAllocator_(0), stack_(stackAllocator, stackCapacity), parseResult_()
+    {
+        if (!allocator_)
+            ownAllocator_ = allocator_ = RAPIDJSON_NEW(Allocator)();
+    }
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    //! Move constructor in C++11
+    GenericDocument(GenericDocument&& rhs) RAPIDJSON_NOEXCEPT
+        : ValueType(std::forward<ValueType>(rhs)), // explicit cast to avoid prohibited move from Document
+          allocator_(rhs.allocator_),
+          ownAllocator_(rhs.ownAllocator_),
+          stack_(std::move(rhs.stack_)),
+          parseResult_(rhs.parseResult_)
+    {
+        rhs.allocator_ = 0;
+        rhs.ownAllocator_ = 0;
+        rhs.parseResult_ = ParseResult();
+    }
+#endif
+
+    ~GenericDocument() {
+        Destroy();
+    }
+
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    //! Move assignment in C++11
+    GenericDocument& operator=(GenericDocument&& rhs) RAPIDJSON_NOEXCEPT
+    {
+        // The cast to ValueType is necessary here, because otherwise it would
+        // attempt to call GenericValue's templated assignment operator.
+        ValueType::operator=(std::forward<ValueType>(rhs));
+
+        // Calling the destructor here would prematurely call stack_'s destructor
+        Destroy();
+
+        allocator_ = rhs.allocator_;
+        ownAllocator_ = rhs.ownAllocator_;
+        stack_ = std::move(rhs.stack_);
+        parseResult_ = rhs.parseResult_;
+
+        rhs.allocator_ = 0;
+        rhs.ownAllocator_ = 0;
+        rhs.parseResult_ = ParseResult();
+
+        return *this;
+    }
+#endif
+
+    //! Exchange the contents of this document with those of another.
+    /*!
+        \param rhs Another document.
+        \note Constant complexity.
+        \see GenericValue::Swap
+    */
+    GenericDocument& Swap(GenericDocument& rhs) RAPIDJSON_NOEXCEPT {
+        ValueType::Swap(rhs);
+        stack_.Swap(rhs.stack_);
+        internal::Swap(allocator_, rhs.allocator_);
+        internal::Swap(ownAllocator_, rhs.ownAllocator_);
+        internal::Swap(parseResult_, rhs.parseResult_);
+        return *this;
+    }
+
+    //! free-standing swap function helper
+    /*!
+        Helper function to enable support for common swap implementation pattern based on \c std::swap:
+        \code
+        void swap(MyClass& a, MyClass& b) {
+            using std::swap;
+            swap(a.doc, b.doc);
+            // ...
+        }
+        \endcode
+        \see Swap()
+     */
+    friend inline void swap(GenericDocument& a, GenericDocument& b) RAPIDJSON_NOEXCEPT { a.Swap(b); }
+
+    //! Populate this document by a generator which produces SAX events.
+    /*! \tparam Generator A functor with <tt>bool f(Handler)</tt> prototype.
+        \param g Generator functor which sends SAX events to the parameter.
+        \return The document itself for fluent API.
+    */
+    template <typename Generator>
+    GenericDocument& Populate(Generator& g) {
+        ClearStackOnExit scope(*this);
+        if (g(*this)) {
+            RAPIDJSON_ASSERT(stack_.GetSize() == sizeof(ValueType)); // Got one and only one root object
+            ValueType::operator=(*stack_.template Pop<ValueType>(1));// Move value from stack to document
+        }
+        return *this;
+    }
+
+    //!@name Parse from stream
+    //!@{
+
+    //! Parse JSON text from an input stream (with Encoding conversion)
+    /*! \tparam parseFlags Combination of \ref ParseFlag.
+        \tparam SourceEncoding Encoding of input stream
+        \tparam InputStream Type of input stream, implementing Stream concept
+        \param is Input stream to be parsed.
+        \return The document itself for fluent API.
+    */
+    template <unsigned parseFlags, typename SourceEncoding, typename InputStream>
+    GenericDocument& ParseStream(InputStream& is) {
+        GenericReader<SourceEncoding, Encoding, StackAllocator> reader(
+            stack_.HasAllocator() ? &stack_.GetAllocator() : 0);
+        ClearStackOnExit scope(*this);
+        parseResult_ = reader.template Parse<parseFlags>(is, *this);
+        if (parseResult_) {
+            RAPIDJSON_ASSERT(stack_.GetSize() == sizeof(ValueType)); // Got one and only one root object
+            ValueType::operator=(*stack_.template Pop<ValueType>(1));// Move value from stack to document
+        }
+        return *this;
+    }
+
+    //! Parse JSON text from an input stream
+    /*! \tparam parseFlags Combination of \ref ParseFlag.
+        \tparam InputStream Type of input stream, implementing Stream concept
+        \param is Input stream to be parsed.
+        \return The document itself for fluent API.
+    */
+    template <unsigned parseFlags, typename InputStream>
+    GenericDocument& ParseStream(InputStream& is) {
+        return ParseStream<parseFlags, Encoding, InputStream>(is);
+    }
+
+    //! Parse JSON text from an input stream (with \ref kParseDefaultFlags)
+    /*! \tparam InputStream Type of input stream, implementing Stream concept
+        \param is Input stream to be parsed.
+        \return The document itself for fluent API.
+    */
+    template <typename InputStream>
+    GenericDocument& ParseStream(InputStream& is) {
+        return ParseStream<kParseDefaultFlags, Encoding, InputStream>(is);
+    }
+    //!@}
+
+    //!@name Parse in-place from mutable string
+    //!@{
+
+    //! Parse JSON text from a mutable string
+    /*! \tparam parseFlags Combination of \ref ParseFlag.
+        \param str Mutable zero-terminated string to be parsed.
+        \return The document itself for fluent API.
+    */
+    template <unsigned parseFlags>
+    GenericDocument& ParseInsitu(Ch* str) {
+        GenericInsituStringStream<Encoding> s(str);
+        return ParseStream<parseFlags | kParseInsituFlag>(s);
+    }
+
+    //! Parse JSON text from a mutable string (with \ref kParseDefaultFlags)
+    /*! \param str Mutable zero-terminated string to be parsed.
+        \return The document itself for fluent API.
+    */
+    GenericDocument& ParseInsitu(Ch* str) {
+        return ParseInsitu<kParseDefaultFlags>(str);
+    }
+    //!@}
+
+    //!@name Parse from read-only string
+    //!@{
+
+    //! Parse JSON text from a read-only string (with Encoding conversion)
+    /*! \tparam parseFlags Combination of \ref ParseFlag (must not contain \ref kParseInsituFlag).
+        \tparam SourceEncoding Transcoding from input Encoding
+        \param str Read-only zero-terminated string to be parsed.
+    */
+    template <unsigned parseFlags, typename SourceEncoding>
+    GenericDocument& Parse(const typename SourceEncoding::Ch* str) {
+        RAPIDJSON_ASSERT(!(parseFlags & kParseInsituFlag));
+        GenericStringStream<SourceEncoding> s(str);
+        return ParseStream<parseFlags, SourceEncoding>(s);
+    }
+
+    //! Parse JSON text from a read-only string
+    /*! \tparam parseFlags Combination of \ref ParseFlag (must not contain \ref kParseInsituFlag).
+        \param str Read-only zero-terminated string to be parsed.
+    */
+    template <unsigned parseFlags>
+    GenericDocument& Parse(const Ch* str) {
+        return Parse<parseFlags, Encoding>(str);
+    }
+
+    //! Parse JSON text from a read-only string (with \ref kParseDefaultFlags)
+    /*! \param str Read-only zero-terminated string to be parsed.
+    */
+    GenericDocument& Parse(const Ch* str) {
+        return Parse<kParseDefaultFlags>(str);
+    }
+
+    template <unsigned parseFlags, typename SourceEncoding>
+    GenericDocument& Parse(const typename SourceEncoding::Ch* str, size_t length) {
+        RAPIDJSON_ASSERT(!(parseFlags & kParseInsituFlag));
+        MemoryStream ms(reinterpret_cast<const char*>(str), length * sizeof(typename SourceEncoding::Ch));
+        EncodedInputStream<SourceEncoding, MemoryStream> is(ms);
+        ParseStream<parseFlags, SourceEncoding>(is);
+        return *this;
+    }
+
+    template <unsigned parseFlags>
+    GenericDocument& Parse(const Ch* str, size_t length) {
+        return Parse<parseFlags, Encoding>(str, length);
+    }
+    
+    GenericDocument& Parse(const Ch* str, size_t length) {
+        return Parse<kParseDefaultFlags>(str, length);
+    }
+
+#if RAPIDJSON_HAS_STDSTRING
+    template <unsigned parseFlags, typename SourceEncoding>
+    GenericDocument& Parse(const std::basic_string<typename SourceEncoding::Ch>& str) {
+        // c_str() is constant complexity according to standard. Should be faster than Parse(const char*, size_t)
+        return Parse<parseFlags, SourceEncoding>(str.c_str());
+    }
+
+    template <unsigned parseFlags>
+    GenericDocument& Parse(const std::basic_string<Ch>& str) {
+        return Parse<parseFlags, Encoding>(str.c_str());
+    }
+
+    GenericDocument& Parse(const std::basic_string<Ch>& str) {
+        return Parse<kParseDefaultFlags>(str);
+    }
+#endif // RAPIDJSON_HAS_STDSTRING    
+
+    //!@}
+
+    //!@name Handling parse errors
+    //!@{
+
+    //! Whether a parse error has occured in the last parsing.
+    bool HasParseError() const { return parseResult_.IsError(); }
+
+    //! Get the \ref ParseErrorCode of last parsing.
+    ParseErrorCode GetParseError() const { return parseResult_.Code(); }
+
+    //! Get the position of last parsing error in input, 0 otherwise.
+    size_t GetErrorOffset() const { return parseResult_.Offset(); }
+
+    //! Implicit conversion to get the last parse result
+#ifndef __clang // -Wdocumentation
+    /*! \return \ref ParseResult of the last parse operation
+
+        \code
+          Document doc;
+          ParseResult ok = doc.Parse(json);
+          if (!ok)
+            printf( "JSON parse error: %s (%u)\n", GetParseError_En(ok.Code()), ok.Offset());
+        \endcode
+     */
+#endif
+    operator ParseResult() const { return parseResult_; }
+    //!@}
+
+    //! Get the allocator of this document.
+    Allocator& GetAllocator() {
+        RAPIDJSON_ASSERT(allocator_);
+        return *allocator_;
+    }
+
+    //! Get the capacity of stack in bytes.
+    size_t GetStackCapacity() const { return stack_.GetCapacity(); }
+
+private:
+    // clear stack on any exit from ParseStream, e.g. due to exception
+    struct ClearStackOnExit {
+        explicit ClearStackOnExit(GenericDocument& d) : d_(d) {}
+        ~ClearStackOnExit() { d_.ClearStack(); }
+    private:
+        ClearStackOnExit(const ClearStackOnExit&);
+        ClearStackOnExit& operator=(const ClearStackOnExit&);
+        GenericDocument& d_;
+    };
+
+    // callers of the following private Handler functions
+    // template <typename,typename,typename> friend class GenericReader; // for parsing
+    template <typename, typename> friend class GenericValue; // for deep copying
+
+public:
+    // Implementation of Handler
+    bool Null() { new (stack_.template Push<ValueType>()) ValueType(); return true; }
+    bool Bool(bool b) { new (stack_.template Push<ValueType>()) ValueType(b); return true; }
+    bool Int(int i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
+    bool Uint(unsigned i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
+    bool Int64(int64_t i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
+    bool Uint64(uint64_t i) { new (stack_.template Push<ValueType>()) ValueType(i); return true; }
+    bool Double(double d) { new (stack_.template Push<ValueType>()) ValueType(d); return true; }
+
+    bool RawNumber(const Ch* str, SizeType length, bool copy) { 
+        if (copy) 
+            new (stack_.template Push<ValueType>()) ValueType(str, length, GetAllocator());
+        else
+            new (stack_.template Push<ValueType>()) ValueType(str, length);
+        return true;
+    }
+
+    bool String(const Ch* str, SizeType length, bool copy) { 
+        if (copy) 
+            new (stack_.template Push<ValueType>()) ValueType(str, length, GetAllocator());
+        else
+            new (stack_.template Push<ValueType>()) ValueType(str, length);
+        return true;
+    }
+
+    bool StartObject() { new (stack_.template Push<ValueType>()) ValueType(kObjectType); return true; }
+    
+    bool Key(const Ch* str, SizeType length, bool copy) { return String(str, length, copy); }
+
+    bool EndObject(SizeType memberCount) {
+        typename ValueType::Member* members = stack_.template Pop<typename ValueType::Member>(memberCount);
+        stack_.template Top<ValueType>()->SetObjectRaw(members, memberCount, GetAllocator());
+        return true;
+    }
+
+    bool StartArray() { new (stack_.template Push<ValueType>()) ValueType(kArrayType); return true; }
+    
+    bool EndArray(SizeType elementCount) {
+        ValueType* elements = stack_.template Pop<ValueType>(elementCount);
+        stack_.template Top<ValueType>()->SetArrayRaw(elements, elementCount, GetAllocator());
+        return true;
+    }
+
+private:
+    //! Prohibit copying
+    GenericDocument(const GenericDocument&);
+    //! Prohibit assignment
+    GenericDocument& operator=(const GenericDocument&);
+
+    void ClearStack() {
+        if (Allocator::kNeedFree)
+            while (stack_.GetSize() > 0)    // Here assumes all elements in stack array are GenericValue (Member is actually 2 GenericValue objects)
+                (stack_.template Pop<ValueType>(1))->~ValueType();
+        else
+            stack_.Clear();
+        stack_.ShrinkToFit();
+    }
+
+    void Destroy() {
+        RAPIDJSON_DELETE(ownAllocator_);
+    }
+
+    static const size_t kDefaultStackCapacity = 1024;
+    Allocator* allocator_;
+    Allocator* ownAllocator_;
+    internal::Stack<StackAllocator> stack_;
+    ParseResult parseResult_;
+};
+
+//! GenericDocument with UTF8 encoding
+typedef GenericDocument<UTF8<> > Document;
+
+//! Helper class for accessing Value of array type.
+/*!
+    Instance of this helper class is obtained by \c GenericValue::GetArray().
+    In addition to all APIs for array type, it provides range-based for loop if \c RAPIDJSON_HAS_CXX11_RANGE_FOR=1.
+*/
+template <bool Const, typename ValueT>
+class GenericArray {
+public:
+    typedef GenericArray<true, ValueT> ConstArray;
+    typedef GenericArray<false, ValueT> Array;
+    typedef ValueT PlainType;
+    typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType;
+    typedef ValueType* ValueIterator;  // This may be const or non-const iterator
+    typedef const ValueT* ConstValueIterator;
+    typedef typename ValueType::AllocatorType AllocatorType;
+    typedef typename ValueType::StringRefType StringRefType;
+
+    template <typename, typename>
+    friend class GenericValue;
+
+    GenericArray(const GenericArray& rhs) : value_(rhs.value_) {}
+    GenericArray& operator=(const GenericArray& rhs) { value_ = rhs.value_; return *this; }
+    ~GenericArray() {}
+
+    SizeType Size() const { return value_.Size(); }
+    SizeType Capacity() const { return value_.Capacity(); }
+    bool Empty() const { return value_.Empty(); }
+    void Clear() const { value_.Clear(); }
+    ValueType& operator[](SizeType index) const {  return value_[index]; }
+    ValueIterator Begin() const { return value_.Begin(); }
+    ValueIterator End() const { return value_.End(); }
+    GenericArray Reserve(SizeType newCapacity, AllocatorType &allocator) const { value_.Reserve(newCapacity, allocator); return *this; }
+    GenericArray PushBack(ValueType& value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    GenericArray PushBack(ValueType&& value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
+#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    GenericArray PushBack(StringRefType value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
+    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (const GenericArray&)) PushBack(T value, AllocatorType& allocator) const { value_.PushBack(value, allocator); return *this; }
+    GenericArray PopBack() const { value_.PopBack(); return *this; }
+    ValueIterator Erase(ConstValueIterator pos) const { return value_.Erase(pos); }
+    ValueIterator Erase(ConstValueIterator first, ConstValueIterator last) const { return value_.Erase(first, last); }
+
+#if RAPIDJSON_HAS_CXX11_RANGE_FOR
+    ValueIterator begin() const { return value_.Begin(); }
+    ValueIterator end() const { return value_.End(); }
+#endif
+
+private:
+    GenericArray();
+    GenericArray(ValueType& value) : value_(value) {}
+    ValueType& value_;
+};
+
+//! Helper class for accessing Value of object type.
+/*!
+    Instance of this helper class is obtained by \c GenericValue::GetObject().
+    In addition to all APIs for array type, it provides range-based for loop if \c RAPIDJSON_HAS_CXX11_RANGE_FOR=1.
+*/
+template <bool Const, typename ValueT>
+class GenericObject {
+public:
+    typedef GenericObject<true, ValueT> ConstObject;
+    typedef GenericObject<false, ValueT> Object;
+    typedef ValueT PlainType;
+    typedef typename internal::MaybeAddConst<Const,PlainType>::Type ValueType;
+    typedef GenericMemberIterator<Const, typename ValueT::EncodingType, typename ValueT::AllocatorType> MemberIterator;  // This may be const or non-const iterator
+    typedef GenericMemberIterator<true, typename ValueT::EncodingType, typename ValueT::AllocatorType> ConstMemberIterator;
+    typedef typename ValueType::AllocatorType AllocatorType;
+    typedef typename ValueType::StringRefType StringRefType;
+    typedef typename ValueType::EncodingType EncodingType;
+    typedef typename ValueType::Ch Ch;
+
+    template <typename, typename>
+    friend class GenericValue;
+
+    GenericObject(const GenericObject& rhs) : value_(rhs.value_) {}
+    GenericObject& operator=(const GenericObject& rhs) { value_ = rhs.value_; return *this; }
+    ~GenericObject() {}
+
+    SizeType MemberCount() const { return value_.MemberCount(); }
+    bool ObjectEmpty() const { return value_.ObjectEmpty(); }
+    template <typename T> ValueType& operator[](T* name) const { return value_[name]; }
+    template <typename SourceAllocator> ValueType& operator[](const GenericValue<EncodingType, SourceAllocator>& name) const { return value_[name]; }
+#if RAPIDJSON_HAS_STDSTRING
+    ValueType& operator[](const std::basic_string<Ch>& name) const { return value_[name]; }
+#endif
+    MemberIterator MemberBegin() const { return value_.MemberBegin(); }
+    MemberIterator MemberEnd() const { return value_.MemberEnd(); }
+    bool HasMember(const Ch* name) const { return value_.HasMember(name); }
+#if RAPIDJSON_HAS_STDSTRING
+    bool HasMember(const std::basic_string<Ch>& name) const { return value_.HasMember(name); }
+#endif
+    template <typename SourceAllocator> bool HasMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.HasMember(name); }
+    MemberIterator FindMember(const Ch* name) const { return value_.FindMember(name); }
+    template <typename SourceAllocator> MemberIterator FindMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.FindMember(name); }
+#if RAPIDJSON_HAS_STDSTRING
+    MemberIterator FindMember(const std::basic_string<Ch>& name) const { return value_.FindMember(name); }
+#endif
+    GenericObject AddMember(ValueType& name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    GenericObject AddMember(ValueType& name, StringRefType value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+#if RAPIDJSON_HAS_STDSTRING
+    GenericObject AddMember(ValueType& name, std::basic_string<Ch>& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+#endif
+    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (ValueType&)) AddMember(ValueType& name, T value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+#if RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    GenericObject AddMember(ValueType&& name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    GenericObject AddMember(ValueType&& name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    GenericObject AddMember(ValueType& name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    GenericObject AddMember(StringRefType name, ValueType&& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+#endif // RAPIDJSON_HAS_CXX11_RVALUE_REFS
+    GenericObject AddMember(StringRefType name, ValueType& value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    GenericObject AddMember(StringRefType name, StringRefType value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    template <typename T> RAPIDJSON_DISABLEIF_RETURN((internal::OrExpr<internal::IsPointer<T>, internal::IsGenericValue<T> >), (GenericObject)) AddMember(StringRefType name, T value, AllocatorType& allocator) const { value_.AddMember(name, value, allocator); return *this; }
+    void RemoveAllMembers() { value_.RemoveAllMembers(); }
+    bool RemoveMember(const Ch* name) const { return value_.RemoveMember(name); }
+#if RAPIDJSON_HAS_STDSTRING
+    bool RemoveMember(const std::basic_string<Ch>& name) const { return value_.RemoveMember(name); }
+#endif
+    template <typename SourceAllocator> bool RemoveMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.RemoveMember(name); }
+    MemberIterator RemoveMember(MemberIterator m) const { return value_.RemoveMember(m); }
+    MemberIterator EraseMember(ConstMemberIterator pos) const { return value_.EraseMember(pos); }
+    MemberIterator EraseMember(ConstMemberIterator first, ConstMemberIterator last) const { return value_.EraseMember(first, last); }
+    bool EraseMember(const Ch* name) const { return value_.EraseMember(name); }
+#if RAPIDJSON_HAS_STDSTRING
+    bool EraseMember(const std::basic_string<Ch>& name) const { return EraseMember(ValueType(StringRef(name))); }
+#endif
+    template <typename SourceAllocator> bool EraseMember(const GenericValue<EncodingType, SourceAllocator>& name) const { return value_.EraseMember(name); }
+
+#if RAPIDJSON_HAS_CXX11_RANGE_FOR
+    MemberIterator begin() const { return value_.MemberBegin(); }
+    MemberIterator end() const { return value_.MemberEnd(); }
+#endif
+
+private:
+    GenericObject();
+    GenericObject(ValueType& value) : value_(value) {}
+    ValueType& value_;
+};
+
+RAPIDJSON_NAMESPACE_END
+#ifdef _MINWINDEF_       // see: http://stackoverflow.com/questions/22744262/cant-call-stdmax-because-minwindef-h-defines-max
+#ifndef NOMINMAX
+#pragma pop_macro("min")
+#pragma pop_macro("max")
+#endif
+#endif
+RAPIDJSON_DIAG_POP
+
+#endif // RAPIDJSON_DOCUMENT_H_

+ 298 - 298
contrib/libs/rapidjson/include/rapidjson/encodedstream.h

@@ -1,299 +1,299 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_ENCODEDSTREAM_H_ 
-#define RAPIDJSON_ENCODEDSTREAM_H_ 
- 
-#include "stream.h" 
-#include "memorystream.h" 
- 
-#ifdef __GNUC__ 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(effc++) 
-#endif 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(padded) 
-#endif 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-//! Input byte stream wrapper with a statically bound encoding. 
-/*! 
-    \tparam Encoding The interpretation of encoding of the stream. Either UTF8, UTF16LE, UTF16BE, UTF32LE, UTF32BE. 
-    \tparam InputByteStream Type of input byte stream. For example, FileReadStream. 
-*/ 
-template <typename Encoding, typename InputByteStream> 
-class EncodedInputStream { 
-    RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-public: 
-    typedef typename Encoding::Ch Ch; 
- 
-    EncodedInputStream(InputByteStream& is) : is_(is) {  
-        current_ = Encoding::TakeBOM(is_); 
-    } 
- 
-    Ch Peek() const { return current_; } 
-    Ch Take() { Ch c = current_; current_ = Encoding::Take(is_); return c; } 
-    size_t Tell() const { return is_.Tell(); } 
- 
-    // Not implemented 
-    void Put(Ch) { RAPIDJSON_ASSERT(false); } 
-    void Flush() { RAPIDJSON_ASSERT(false); }  
-    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; } 
-    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; } 
- 
-private: 
-    EncodedInputStream(const EncodedInputStream&); 
-    EncodedInputStream& operator=(const EncodedInputStream&); 
- 
-    InputByteStream& is_; 
-    Ch current_; 
-}; 
- 
-//! Specialized for UTF8 MemoryStream. 
-template <> 
-class EncodedInputStream<UTF8<>, MemoryStream> { 
-public: 
-    typedef UTF8<>::Ch Ch; 
- 
-    EncodedInputStream(MemoryStream& is) : is_(is) { 
-        if (static_cast<unsigned char>(is_.Peek()) == 0xEFu) is_.Take(); 
-        if (static_cast<unsigned char>(is_.Peek()) == 0xBBu) is_.Take(); 
-        if (static_cast<unsigned char>(is_.Peek()) == 0xBFu) is_.Take(); 
-    } 
-    Ch Peek() const { return is_.Peek(); } 
-    Ch Take() { return is_.Take(); } 
-    size_t Tell() const { return is_.Tell(); } 
- 
-    // Not implemented 
-    void Put(Ch) {} 
-    void Flush() {}  
-    Ch* PutBegin() { return 0; } 
-    size_t PutEnd(Ch*) { return 0; } 
- 
-    MemoryStream& is_; 
- 
-private: 
-    EncodedInputStream(const EncodedInputStream&); 
-    EncodedInputStream& operator=(const EncodedInputStream&); 
-}; 
- 
-//! Output byte stream wrapper with statically bound encoding. 
-/*! 
-    \tparam Encoding The interpretation of encoding of the stream. Either UTF8, UTF16LE, UTF16BE, UTF32LE, UTF32BE. 
-    \tparam OutputByteStream Type of input byte stream. For example, FileWriteStream. 
-*/ 
-template <typename Encoding, typename OutputByteStream> 
-class EncodedOutputStream { 
-    RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-public: 
-    typedef typename Encoding::Ch Ch; 
- 
-    EncodedOutputStream(OutputByteStream& os, bool putBOM = true) : os_(os) {  
-        if (putBOM) 
-            Encoding::PutBOM(os_); 
-    } 
- 
-    void Put(Ch c) { Encoding::Put(os_, c);  } 
-    void Flush() { os_.Flush(); } 
- 
-    // Not implemented 
-    Ch Peek() const { RAPIDJSON_ASSERT(false); return 0;} 
-    Ch Take() { RAPIDJSON_ASSERT(false); return 0;} 
-    size_t Tell() const { RAPIDJSON_ASSERT(false);  return 0; } 
-    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; } 
-    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; } 
- 
-private: 
-    EncodedOutputStream(const EncodedOutputStream&); 
-    EncodedOutputStream& operator=(const EncodedOutputStream&); 
- 
-    OutputByteStream& os_; 
-}; 
- 
-#define RAPIDJSON_ENCODINGS_FUNC(x) UTF8<Ch>::x, UTF16LE<Ch>::x, UTF16BE<Ch>::x, UTF32LE<Ch>::x, UTF32BE<Ch>::x 
- 
-//! Input stream wrapper with dynamically bound encoding and automatic encoding detection. 
-/*! 
-    \tparam CharType Type of character for reading. 
-    \tparam InputByteStream type of input byte stream to be wrapped. 
-*/ 
-template <typename CharType, typename InputByteStream> 
-class AutoUTFInputStream { 
-    RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-public: 
-    typedef CharType Ch; 
- 
-    //! Constructor. 
-    /*! 
-        \param is input stream to be wrapped. 
-        \param type UTF encoding type if it is not detected from the stream. 
-    */ 
-    AutoUTFInputStream(InputByteStream& is, UTFType type = kUTF8) : is_(&is), type_(type), hasBOM_(false) { 
-        RAPIDJSON_ASSERT(type >= kUTF8 && type <= kUTF32BE);         
-        DetectType(); 
-        static const TakeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Take) }; 
-        takeFunc_ = f[type_]; 
-        current_ = takeFunc_(*is_); 
-    } 
- 
-    UTFType GetType() const { return type_; } 
-    bool HasBOM() const { return hasBOM_; } 
- 
-    Ch Peek() const { return current_; } 
-    Ch Take() { Ch c = current_; current_ = takeFunc_(*is_); return c; } 
-    size_t Tell() const { return is_->Tell(); } 
- 
-    // Not implemented 
-    void Put(Ch) { RAPIDJSON_ASSERT(false); } 
-    void Flush() { RAPIDJSON_ASSERT(false); }  
-    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; } 
-    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; } 
- 
-private: 
-    AutoUTFInputStream(const AutoUTFInputStream&); 
-    AutoUTFInputStream& operator=(const AutoUTFInputStream&); 
- 
-    // Detect encoding type with BOM or RFC 4627 
-    void DetectType() { 
-        // BOM (Byte Order Mark): 
-        // 00 00 FE FF  UTF-32BE 
-        // FF FE 00 00  UTF-32LE 
-        // FE FF        UTF-16BE 
-        // FF FE        UTF-16LE 
-        // EF BB BF     UTF-8 
- 
-        const unsigned char* c = reinterpret_cast<const unsigned char *>(is_->Peek4()); 
-        if (!c) 
-            return; 
- 
-        unsigned bom = static_cast<unsigned>(c[0] | (c[1] << 8) | (c[2] << 16) | (c[3] << 24)); 
-        hasBOM_ = false; 
-        if (bom == 0xFFFE0000)                  { type_ = kUTF32BE; hasBOM_ = true; is_->Take(); is_->Take(); is_->Take(); is_->Take(); } 
-        else if (bom == 0x0000FEFF)             { type_ = kUTF32LE; hasBOM_ = true; is_->Take(); is_->Take(); is_->Take(); is_->Take(); } 
-        else if ((bom & 0xFFFF) == 0xFFFE)      { type_ = kUTF16BE; hasBOM_ = true; is_->Take(); is_->Take();                           } 
-        else if ((bom & 0xFFFF) == 0xFEFF)      { type_ = kUTF16LE; hasBOM_ = true; is_->Take(); is_->Take();                           } 
-        else if ((bom & 0xFFFFFF) == 0xBFBBEF)  { type_ = kUTF8;    hasBOM_ = true; is_->Take(); is_->Take(); is_->Take();              } 
- 
-        // RFC 4627: Section 3 
-        // "Since the first two characters of a JSON text will always be ASCII 
-        // characters [RFC0020], it is possible to determine whether an octet 
-        // stream is UTF-8, UTF-16 (BE or LE), or UTF-32 (BE or LE) by looking 
-        // at the pattern of nulls in the first four octets." 
-        // 00 00 00 xx  UTF-32BE 
-        // 00 xx 00 xx  UTF-16BE 
-        // xx 00 00 00  UTF-32LE 
-        // xx 00 xx 00  UTF-16LE 
-        // xx xx xx xx  UTF-8 
- 
-        if (!hasBOM_) { 
-            int pattern = (c[0] ? 1 : 0) | (c[1] ? 2 : 0) | (c[2] ? 4 : 0) | (c[3] ? 8 : 0); 
-            switch (pattern) { 
-            case 0x08: type_ = kUTF32BE; break; 
-            case 0x0A: type_ = kUTF16BE; break; 
-            case 0x01: type_ = kUTF32LE; break; 
-            case 0x05: type_ = kUTF16LE; break; 
-            case 0x0F: type_ = kUTF8;    break; 
-            default: break; // Use type defined by user. 
-            } 
-        } 
- 
-        // Runtime check whether the size of character type is sufficient. It only perform checks with assertion. 
-        if (type_ == kUTF16LE || type_ == kUTF16BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 2); 
-        if (type_ == kUTF32LE || type_ == kUTF32BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 4); 
-    } 
- 
-    typedef Ch (*TakeFunc)(InputByteStream& is); 
-    InputByteStream* is_; 
-    UTFType type_; 
-    Ch current_; 
-    TakeFunc takeFunc_; 
-    bool hasBOM_; 
-}; 
- 
-//! Output stream wrapper with dynamically bound encoding and automatic encoding detection. 
-/*! 
-    \tparam CharType Type of character for writing. 
-    \tparam OutputByteStream type of output byte stream to be wrapped. 
-*/ 
-template <typename CharType, typename OutputByteStream> 
-class AutoUTFOutputStream { 
-    RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-public: 
-    typedef CharType Ch; 
- 
-    //! Constructor. 
-    /*! 
-        \param os output stream to be wrapped. 
-        \param type UTF encoding type. 
-        \param putBOM Whether to write BOM at the beginning of the stream. 
-    */ 
-    AutoUTFOutputStream(OutputByteStream& os, UTFType type, bool putBOM) : os_(&os), type_(type) { 
-        RAPIDJSON_ASSERT(type >= kUTF8 && type <= kUTF32BE); 
- 
-        // Runtime check whether the size of character type is sufficient. It only perform checks with assertion. 
-        if (type_ == kUTF16LE || type_ == kUTF16BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 2); 
-        if (type_ == kUTF32LE || type_ == kUTF32BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 4); 
- 
-        static const PutFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Put) }; 
-        putFunc_ = f[type_]; 
- 
-        if (putBOM) 
-            PutBOM(); 
-    } 
- 
-    UTFType GetType() const { return type_; } 
- 
-    void Put(Ch c) { putFunc_(*os_, c); } 
-    void Flush() { os_->Flush(); }  
- 
-    // Not implemented 
-    Ch Peek() const { RAPIDJSON_ASSERT(false); return 0;} 
-    Ch Take() { RAPIDJSON_ASSERT(false); return 0;} 
-    size_t Tell() const { RAPIDJSON_ASSERT(false); return 0; } 
-    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; } 
-    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; } 
- 
-private: 
-    AutoUTFOutputStream(const AutoUTFOutputStream&); 
-    AutoUTFOutputStream& operator=(const AutoUTFOutputStream&); 
- 
-    void PutBOM() {  
-        typedef void (*PutBOMFunc)(OutputByteStream&); 
-        static const PutBOMFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(PutBOM) }; 
-        f[type_](*os_); 
-    } 
- 
-    typedef void (*PutFunc)(OutputByteStream&, Ch); 
- 
-    OutputByteStream* os_; 
-    UTFType type_; 
-    PutFunc putFunc_; 
-}; 
- 
-#undef RAPIDJSON_ENCODINGS_FUNC 
- 
-RAPIDJSON_NAMESPACE_END 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_POP 
-#endif 
- 
-#ifdef __GNUC__ 
-RAPIDJSON_DIAG_POP 
-#endif 
- 
-#endif // RAPIDJSON_FILESTREAM_H_ 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_ENCODEDSTREAM_H_
+#define RAPIDJSON_ENCODEDSTREAM_H_
+
+#include "stream.h"
+#include "memorystream.h"
+
+#ifdef __GNUC__
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(effc++)
+#endif
+
+#ifdef __clang__
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(padded)
+#endif
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+//! Input byte stream wrapper with a statically bound encoding.
+/*!
+    \tparam Encoding The interpretation of encoding of the stream. Either UTF8, UTF16LE, UTF16BE, UTF32LE, UTF32BE.
+    \tparam InputByteStream Type of input byte stream. For example, FileReadStream.
+*/
+template <typename Encoding, typename InputByteStream>
+class EncodedInputStream {
+    RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+public:
+    typedef typename Encoding::Ch Ch;
+
+    EncodedInputStream(InputByteStream& is) : is_(is) { 
+        current_ = Encoding::TakeBOM(is_);
+    }
+
+    Ch Peek() const { return current_; }
+    Ch Take() { Ch c = current_; current_ = Encoding::Take(is_); return c; }
+    size_t Tell() const { return is_.Tell(); }
+
+    // Not implemented
+    void Put(Ch) { RAPIDJSON_ASSERT(false); }
+    void Flush() { RAPIDJSON_ASSERT(false); } 
+    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; }
+    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; }
+
+private:
+    EncodedInputStream(const EncodedInputStream&);
+    EncodedInputStream& operator=(const EncodedInputStream&);
+
+    InputByteStream& is_;
+    Ch current_;
+};
+
+//! Specialized for UTF8 MemoryStream.
+template <>
+class EncodedInputStream<UTF8<>, MemoryStream> {
+public:
+    typedef UTF8<>::Ch Ch;
+
+    EncodedInputStream(MemoryStream& is) : is_(is) {
+        if (static_cast<unsigned char>(is_.Peek()) == 0xEFu) is_.Take();
+        if (static_cast<unsigned char>(is_.Peek()) == 0xBBu) is_.Take();
+        if (static_cast<unsigned char>(is_.Peek()) == 0xBFu) is_.Take();
+    }
+    Ch Peek() const { return is_.Peek(); }
+    Ch Take() { return is_.Take(); }
+    size_t Tell() const { return is_.Tell(); }
+
+    // Not implemented
+    void Put(Ch) {}
+    void Flush() {} 
+    Ch* PutBegin() { return 0; }
+    size_t PutEnd(Ch*) { return 0; }
+
+    MemoryStream& is_;
+
+private:
+    EncodedInputStream(const EncodedInputStream&);
+    EncodedInputStream& operator=(const EncodedInputStream&);
+};
+
+//! Output byte stream wrapper with statically bound encoding.
+/*!
+    \tparam Encoding The interpretation of encoding of the stream. Either UTF8, UTF16LE, UTF16BE, UTF32LE, UTF32BE.
+    \tparam OutputByteStream Type of input byte stream. For example, FileWriteStream.
+*/
+template <typename Encoding, typename OutputByteStream>
+class EncodedOutputStream {
+    RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+public:
+    typedef typename Encoding::Ch Ch;
+
+    EncodedOutputStream(OutputByteStream& os, bool putBOM = true) : os_(os) { 
+        if (putBOM)
+            Encoding::PutBOM(os_);
+    }
+
+    void Put(Ch c) { Encoding::Put(os_, c);  }
+    void Flush() { os_.Flush(); }
+
+    // Not implemented
+    Ch Peek() const { RAPIDJSON_ASSERT(false); return 0;}
+    Ch Take() { RAPIDJSON_ASSERT(false); return 0;}
+    size_t Tell() const { RAPIDJSON_ASSERT(false);  return 0; }
+    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; }
+    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; }
+
+private:
+    EncodedOutputStream(const EncodedOutputStream&);
+    EncodedOutputStream& operator=(const EncodedOutputStream&);
+
+    OutputByteStream& os_;
+};
+
+#define RAPIDJSON_ENCODINGS_FUNC(x) UTF8<Ch>::x, UTF16LE<Ch>::x, UTF16BE<Ch>::x, UTF32LE<Ch>::x, UTF32BE<Ch>::x
+
+//! Input stream wrapper with dynamically bound encoding and automatic encoding detection.
+/*!
+    \tparam CharType Type of character for reading.
+    \tparam InputByteStream type of input byte stream to be wrapped.
+*/
+template <typename CharType, typename InputByteStream>
+class AutoUTFInputStream {
+    RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+public:
+    typedef CharType Ch;
+
+    //! Constructor.
+    /*!
+        \param is input stream to be wrapped.
+        \param type UTF encoding type if it is not detected from the stream.
+    */
+    AutoUTFInputStream(InputByteStream& is, UTFType type = kUTF8) : is_(&is), type_(type), hasBOM_(false) {
+        RAPIDJSON_ASSERT(type >= kUTF8 && type <= kUTF32BE);        
+        DetectType();
+        static const TakeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Take) };
+        takeFunc_ = f[type_];
+        current_ = takeFunc_(*is_);
+    }
+
+    UTFType GetType() const { return type_; }
+    bool HasBOM() const { return hasBOM_; }
+
+    Ch Peek() const { return current_; }
+    Ch Take() { Ch c = current_; current_ = takeFunc_(*is_); return c; }
+    size_t Tell() const { return is_->Tell(); }
+
+    // Not implemented
+    void Put(Ch) { RAPIDJSON_ASSERT(false); }
+    void Flush() { RAPIDJSON_ASSERT(false); } 
+    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; }
+    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; }
+
+private:
+    AutoUTFInputStream(const AutoUTFInputStream&);
+    AutoUTFInputStream& operator=(const AutoUTFInputStream&);
+
+    // Detect encoding type with BOM or RFC 4627
+    void DetectType() {
+        // BOM (Byte Order Mark):
+        // 00 00 FE FF  UTF-32BE
+        // FF FE 00 00  UTF-32LE
+        // FE FF        UTF-16BE
+        // FF FE        UTF-16LE
+        // EF BB BF     UTF-8
+
+        const unsigned char* c = reinterpret_cast<const unsigned char *>(is_->Peek4());
+        if (!c)
+            return;
+
+        unsigned bom = static_cast<unsigned>(c[0] | (c[1] << 8) | (c[2] << 16) | (c[3] << 24));
+        hasBOM_ = false;
+        if (bom == 0xFFFE0000)                  { type_ = kUTF32BE; hasBOM_ = true; is_->Take(); is_->Take(); is_->Take(); is_->Take(); }
+        else if (bom == 0x0000FEFF)             { type_ = kUTF32LE; hasBOM_ = true; is_->Take(); is_->Take(); is_->Take(); is_->Take(); }
+        else if ((bom & 0xFFFF) == 0xFFFE)      { type_ = kUTF16BE; hasBOM_ = true; is_->Take(); is_->Take();                           }
+        else if ((bom & 0xFFFF) == 0xFEFF)      { type_ = kUTF16LE; hasBOM_ = true; is_->Take(); is_->Take();                           }
+        else if ((bom & 0xFFFFFF) == 0xBFBBEF)  { type_ = kUTF8;    hasBOM_ = true; is_->Take(); is_->Take(); is_->Take();              }
+
+        // RFC 4627: Section 3
+        // "Since the first two characters of a JSON text will always be ASCII
+        // characters [RFC0020], it is possible to determine whether an octet
+        // stream is UTF-8, UTF-16 (BE or LE), or UTF-32 (BE or LE) by looking
+        // at the pattern of nulls in the first four octets."
+        // 00 00 00 xx  UTF-32BE
+        // 00 xx 00 xx  UTF-16BE
+        // xx 00 00 00  UTF-32LE
+        // xx 00 xx 00  UTF-16LE
+        // xx xx xx xx  UTF-8
+
+        if (!hasBOM_) {
+            int pattern = (c[0] ? 1 : 0) | (c[1] ? 2 : 0) | (c[2] ? 4 : 0) | (c[3] ? 8 : 0);
+            switch (pattern) {
+            case 0x08: type_ = kUTF32BE; break;
+            case 0x0A: type_ = kUTF16BE; break;
+            case 0x01: type_ = kUTF32LE; break;
+            case 0x05: type_ = kUTF16LE; break;
+            case 0x0F: type_ = kUTF8;    break;
+            default: break; // Use type defined by user.
+            }
+        }
+
+        // Runtime check whether the size of character type is sufficient. It only perform checks with assertion.
+        if (type_ == kUTF16LE || type_ == kUTF16BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 2);
+        if (type_ == kUTF32LE || type_ == kUTF32BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 4);
+    }
+
+    typedef Ch (*TakeFunc)(InputByteStream& is);
+    InputByteStream* is_;
+    UTFType type_;
+    Ch current_;
+    TakeFunc takeFunc_;
+    bool hasBOM_;
+};
+
+//! Output stream wrapper with dynamically bound encoding and automatic encoding detection.
+/*!
+    \tparam CharType Type of character for writing.
+    \tparam OutputByteStream type of output byte stream to be wrapped.
+*/
+template <typename CharType, typename OutputByteStream>
+class AutoUTFOutputStream {
+    RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+public:
+    typedef CharType Ch;
+
+    //! Constructor.
+    /*!
+        \param os output stream to be wrapped.
+        \param type UTF encoding type.
+        \param putBOM Whether to write BOM at the beginning of the stream.
+    */
+    AutoUTFOutputStream(OutputByteStream& os, UTFType type, bool putBOM) : os_(&os), type_(type) {
+        RAPIDJSON_ASSERT(type >= kUTF8 && type <= kUTF32BE);
+
+        // Runtime check whether the size of character type is sufficient. It only perform checks with assertion.
+        if (type_ == kUTF16LE || type_ == kUTF16BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 2);
+        if (type_ == kUTF32LE || type_ == kUTF32BE) RAPIDJSON_ASSERT(sizeof(Ch) >= 4);
+
+        static const PutFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Put) };
+        putFunc_ = f[type_];
+
+        if (putBOM)
+            PutBOM();
+    }
+
+    UTFType GetType() const { return type_; }
+
+    void Put(Ch c) { putFunc_(*os_, c); }
+    void Flush() { os_->Flush(); } 
+
+    // Not implemented
+    Ch Peek() const { RAPIDJSON_ASSERT(false); return 0;}
+    Ch Take() { RAPIDJSON_ASSERT(false); return 0;}
+    size_t Tell() const { RAPIDJSON_ASSERT(false); return 0; }
+    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; }
+    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; }
+
+private:
+    AutoUTFOutputStream(const AutoUTFOutputStream&);
+    AutoUTFOutputStream& operator=(const AutoUTFOutputStream&);
+
+    void PutBOM() { 
+        typedef void (*PutBOMFunc)(OutputByteStream&);
+        static const PutBOMFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(PutBOM) };
+        f[type_](*os_);
+    }
+
+    typedef void (*PutFunc)(OutputByteStream&, Ch);
+
+    OutputByteStream* os_;
+    UTFType type_;
+    PutFunc putFunc_;
+};
+
+#undef RAPIDJSON_ENCODINGS_FUNC
+
+RAPIDJSON_NAMESPACE_END
+
+#ifdef __clang__
+RAPIDJSON_DIAG_POP
+#endif
+
+#ifdef __GNUC__
+RAPIDJSON_DIAG_POP
+#endif
+
+#endif // RAPIDJSON_FILESTREAM_H_

+ 714 - 714
contrib/libs/rapidjson/include/rapidjson/encodings.h

@@ -1,716 +1,716 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_ENCODINGS_H_ 
-#define RAPIDJSON_ENCODINGS_H_ 
- 
-#include "rapidjson.h" 
- 
-#ifdef _MSC_VER 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(4244) // conversion from 'type1' to 'type2', possible loss of data 
-RAPIDJSON_DIAG_OFF(4702)  // unreachable code 
-#elif defined(__GNUC__) 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(effc++) 
-RAPIDJSON_DIAG_OFF(overflow) 
-#endif 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// Encoding 
- 
-/*! \class rapidjson::Encoding 
-    \brief Concept for encoding of Unicode characters. 
- 
-\code 
-concept Encoding { 
-    typename Ch;    //! Type of character. A "character" is actually a code unit in unicode's definition. 
- 
-    enum { supportUnicode = 1 }; // or 0 if not supporting unicode 
- 
-    //! \brief Encode a Unicode codepoint to an output stream. 
-    //! \param os Output stream. 
-    //! \param codepoint An unicode codepoint, ranging from 0x0 to 0x10FFFF inclusively. 
-    template<typename OutputStream> 
-    static void Encode(OutputStream& os, unsigned codepoint); 
- 
-    //! \brief Decode a Unicode codepoint from an input stream. 
-    //! \param is Input stream. 
-    //! \param codepoint Output of the unicode codepoint. 
-    //! \return true if a valid codepoint can be decoded from the stream. 
-    template <typename InputStream> 
-    static bool Decode(InputStream& is, unsigned* codepoint); 
- 
-    //! \brief Validate one Unicode codepoint from an encoded stream. 
-    //! \param is Input stream to obtain codepoint. 
-    //! \param os Output for copying one codepoint. 
-    //! \return true if it is valid. 
-    //! \note This function just validating and copying the codepoint without actually decode it. 
-    template <typename InputStream, typename OutputStream> 
-    static bool Validate(InputStream& is, OutputStream& os); 
- 
-    // The following functions are deal with byte streams. 
- 
-    //! Take a character from input byte stream, skip BOM if exist. 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is); 
- 
-    //! Take a character from input byte stream. 
-    template <typename InputByteStream> 
-    static Ch Take(InputByteStream& is); 
- 
-    //! Put BOM to output byte stream. 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os); 
- 
-    //! Put a character to output byte stream. 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, Ch c); 
-}; 
-\endcode 
-*/ 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// UTF8 
- 
-//! UTF-8 encoding. 
-/*! http://en.wikipedia.org/wiki/UTF-8 
-    http://tools.ietf.org/html/rfc3629 
-    \tparam CharType Code unit for storing 8-bit UTF-8 data. Default is char. 
-    \note implements Encoding concept 
-*/ 
-template<typename CharType = char> 
-struct UTF8 { 
-    typedef CharType Ch; 
- 
-    enum { supportUnicode = 1 }; 
- 
-    template<typename OutputStream> 
-    static void Encode(OutputStream& os, unsigned codepoint) { 
-        if (codepoint <= 0x7F)  
-            os.Put(static_cast<Ch>(codepoint & 0xFF)); 
-        else if (codepoint <= 0x7FF) { 
-            os.Put(static_cast<Ch>(0xC0 | ((codepoint >> 6) & 0xFF))); 
-            os.Put(static_cast<Ch>(0x80 | ((codepoint & 0x3F)))); 
-        } 
-        else if (codepoint <= 0xFFFF) { 
-            os.Put(static_cast<Ch>(0xE0 | ((codepoint >> 12) & 0xFF))); 
-            os.Put(static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F))); 
-            os.Put(static_cast<Ch>(0x80 | (codepoint & 0x3F))); 
-        } 
-        else { 
-            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF); 
-            os.Put(static_cast<Ch>(0xF0 | ((codepoint >> 18) & 0xFF))); 
-            os.Put(static_cast<Ch>(0x80 | ((codepoint >> 12) & 0x3F))); 
-            os.Put(static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F))); 
-            os.Put(static_cast<Ch>(0x80 | (codepoint & 0x3F))); 
-        } 
-    } 
- 
-    template<typename OutputStream> 
-    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) { 
-        if (codepoint <= 0x7F)  
-            PutUnsafe(os, static_cast<Ch>(codepoint & 0xFF)); 
-        else if (codepoint <= 0x7FF) { 
-            PutUnsafe(os, static_cast<Ch>(0xC0 | ((codepoint >> 6) & 0xFF))); 
-            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint & 0x3F)))); 
-        } 
-        else if (codepoint <= 0xFFFF) { 
-            PutUnsafe(os, static_cast<Ch>(0xE0 | ((codepoint >> 12) & 0xFF))); 
-            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F))); 
-            PutUnsafe(os, static_cast<Ch>(0x80 | (codepoint & 0x3F))); 
-        } 
-        else { 
-            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF); 
-            PutUnsafe(os, static_cast<Ch>(0xF0 | ((codepoint >> 18) & 0xFF))); 
-            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint >> 12) & 0x3F))); 
-            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F))); 
-            PutUnsafe(os, static_cast<Ch>(0x80 | (codepoint & 0x3F))); 
-        } 
-    } 
- 
-    template <typename InputStream> 
-    static bool Decode(InputStream& is, unsigned* codepoint) { 
-#define COPY() c = is.Take(); *codepoint = (*codepoint << 6) | (static_cast<unsigned char>(c) & 0x3Fu) 
-#define TRANS(mask) result &= ((GetRange(static_cast<unsigned char>(c)) & mask) != 0) 
-#define TAIL() COPY(); TRANS(0x70) 
-        typename InputStream::Ch c = is.Take(); 
-        if (!(c & 0x80)) { 
-            *codepoint = static_cast<unsigned char>(c); 
-            return true; 
-        } 
- 
-        unsigned char type = GetRange(static_cast<unsigned char>(c)); 
-        if (type >= 32) { 
-            *codepoint = 0; 
-        } else { 
-            *codepoint = (0xFFu >> type) & static_cast<unsigned char>(c); 
-        } 
-        bool result = true; 
-        switch (type) { 
-        case 2: TAIL(); return result; 
-        case 3: TAIL(); TAIL(); return result; 
-        case 4: COPY(); TRANS(0x50); TAIL(); return result; 
-        case 5: COPY(); TRANS(0x10); TAIL(); TAIL(); return result; 
-        case 6: TAIL(); TAIL(); TAIL(); return result; 
-        case 10: COPY(); TRANS(0x20); TAIL(); return result; 
-        case 11: COPY(); TRANS(0x60); TAIL(); TAIL(); return result; 
-        default: return false; 
-        } 
-#undef COPY 
-#undef TRANS 
-#undef TAIL 
-    } 
- 
-    template <typename InputStream, typename OutputStream> 
-    static bool Validate(InputStream& is, OutputStream& os) { 
-#define COPY() os.Put(c = is.Take()) 
-#define TRANS(mask) result &= ((GetRange(static_cast<unsigned char>(c)) & mask) != 0) 
-#define TAIL() COPY(); TRANS(0x70) 
-        Ch c; 
-        COPY(); 
-        if (!(c & 0x80)) 
-            return true; 
- 
-        bool result = true; 
-        switch (GetRange(static_cast<unsigned char>(c))) { 
-        case 2: TAIL(); return result; 
-        case 3: TAIL(); TAIL(); return result; 
-        case 4: COPY(); TRANS(0x50); TAIL(); return result; 
-        case 5: COPY(); TRANS(0x10); TAIL(); TAIL(); return result; 
-        case 6: TAIL(); TAIL(); TAIL(); return result; 
-        case 10: COPY(); TRANS(0x20); TAIL(); return result; 
-        case 11: COPY(); TRANS(0x60); TAIL(); TAIL(); return result; 
-        default: return false; 
-        } 
-#undef COPY 
-#undef TRANS 
-#undef TAIL 
-    } 
- 
-    static unsigned char GetRange(unsigned char c) { 
-        // Referring to DFA of http://bjoern.hoehrmann.de/utf-8/decoder/dfa/ 
-        // With new mapping 1 -> 0x10, 7 -> 0x20, 9 -> 0x40, such that AND operation can test multiple types. 
-        static const unsigned char type[] = { 
-            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 
-            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 
-            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 
-            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 
-            0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10, 
-            0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40, 
-            0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20, 
-            0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20, 
-            8,8,2,2,2,2,2,2,2,2,2,2,2,2,2,2,  2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2, 
-            10,3,3,3,3,3,3,3,3,3,3,3,3,4,3,3, 11,6,6,6,5,8,8,8,8,8,8,8,8,8,8,8, 
-        }; 
-        return type[c]; 
-    } 
- 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        typename InputByteStream::Ch c = Take(is); 
-        if (static_cast<unsigned char>(c) != 0xEFu) return c; 
-        c = is.Take(); 
-        if (static_cast<unsigned char>(c) != 0xBBu) return c; 
-        c = is.Take(); 
-        if (static_cast<unsigned char>(c) != 0xBFu) return c; 
-        c = is.Take(); 
-        return c; 
-    } 
- 
-    template <typename InputByteStream> 
-    static Ch Take(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        return static_cast<Ch>(is.Take()); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xEFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xBBu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xBFu)); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, Ch c) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(c)); 
-    } 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// UTF16 
- 
-//! UTF-16 encoding. 
-/*! http://en.wikipedia.org/wiki/UTF-16 
-    http://tools.ietf.org/html/rfc2781 
-    \tparam CharType Type for storing 16-bit UTF-16 data. Default is wchar_t. C++11 may use char16_t instead. 
-    \note implements Encoding concept 
- 
-    \note For in-memory access, no need to concern endianness. The code units and code points are represented by CPU's endianness. 
-    For streaming, use UTF16LE and UTF16BE, which handle endianness. 
-*/ 
-template<typename CharType = wchar_t> 
-struct UTF16 { 
-    typedef CharType Ch; 
-    RAPIDJSON_STATIC_ASSERT(sizeof(Ch) >= 2); 
- 
-    enum { supportUnicode = 1 }; 
- 
-    template<typename OutputStream> 
-    static void Encode(OutputStream& os, unsigned codepoint) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 2); 
-        if (codepoint <= 0xFFFF) { 
-            RAPIDJSON_ASSERT(codepoint < 0xD800 || codepoint > 0xDFFF); // Code point itself cannot be surrogate pair  
-            os.Put(static_cast<typename OutputStream::Ch>(codepoint)); 
-        } 
-        else { 
-            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF); 
-            unsigned v = codepoint - 0x10000; 
-            os.Put(static_cast<typename OutputStream::Ch>((v >> 10) | 0xD800)); 
-            os.Put(static_cast<typename OutputStream::Ch>((v & 0x3FF) | 0xDC00)); 
-        } 
-    } 
- 
- 
-    template<typename OutputStream> 
-    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 2); 
-        if (codepoint <= 0xFFFF) { 
-            RAPIDJSON_ASSERT(codepoint < 0xD800 || codepoint > 0xDFFF); // Code point itself cannot be surrogate pair  
-            PutUnsafe(os, static_cast<typename OutputStream::Ch>(codepoint)); 
-        } 
-        else { 
-            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF); 
-            unsigned v = codepoint - 0x10000; 
-            PutUnsafe(os, static_cast<typename OutputStream::Ch>((v >> 10) | 0xD800)); 
-            PutUnsafe(os, static_cast<typename OutputStream::Ch>((v & 0x3FF) | 0xDC00)); 
-        } 
-    } 
- 
-    template <typename InputStream> 
-    static bool Decode(InputStream& is, unsigned* codepoint) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 2); 
-        typename InputStream::Ch c = is.Take(); 
-        if (c < 0xD800 || c > 0xDFFF) { 
-            *codepoint = static_cast<unsigned>(c); 
-            return true; 
-        } 
-        else if (c <= 0xDBFF) { 
-            *codepoint = (static_cast<unsigned>(c) & 0x3FF) << 10; 
-            c = is.Take(); 
-            *codepoint |= (static_cast<unsigned>(c) & 0x3FF); 
-            *codepoint += 0x10000; 
-            return c >= 0xDC00 && c <= 0xDFFF; 
-        } 
-        return false; 
-    } 
- 
-    template <typename InputStream, typename OutputStream> 
-    static bool Validate(InputStream& is, OutputStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 2); 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 2); 
-        typename InputStream::Ch c; 
-        os.Put(static_cast<typename OutputStream::Ch>(c = is.Take())); 
-        if (c < 0xD800 || c > 0xDFFF) 
-            return true; 
-        else if (c <= 0xDBFF) { 
-            os.Put(c = is.Take()); 
-            return c >= 0xDC00 && c <= 0xDFFF; 
-        } 
-        return false; 
-    } 
-}; 
- 
-//! UTF-16 little endian encoding. 
-template<typename CharType = wchar_t> 
-struct UTF16LE : UTF16<CharType> { 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        CharType c = Take(is); 
-        return static_cast<uint16_t>(c) == 0xFEFFu ? Take(is) : c; 
-    } 
- 
-    template <typename InputByteStream> 
-    static CharType Take(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        unsigned c = static_cast<uint8_t>(is.Take()); 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8; 
-        return static_cast<CharType>(c); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu)); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, CharType c) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(static_cast<unsigned>(c) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((static_cast<unsigned>(c) >> 8) & 0xFFu)); 
-    } 
-}; 
- 
-//! UTF-16 big endian encoding. 
-template<typename CharType = wchar_t> 
-struct UTF16BE : UTF16<CharType> { 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        CharType c = Take(is); 
-        return static_cast<uint16_t>(c) == 0xFEFFu ? Take(is) : c; 
-    } 
- 
-    template <typename InputByteStream> 
-    static CharType Take(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        unsigned c = static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8; 
-        c |= static_cast<uint8_t>(is.Take()); 
-        return static_cast<CharType>(c); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu)); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, CharType c) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((static_cast<unsigned>(c) >> 8) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(static_cast<unsigned>(c) & 0xFFu)); 
-    } 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// UTF32 
- 
-//! UTF-32 encoding.  
-/*! http://en.wikipedia.org/wiki/UTF-32 
-    \tparam CharType Type for storing 32-bit UTF-32 data. Default is unsigned. C++11 may use char32_t instead. 
-    \note implements Encoding concept 
- 
-    \note For in-memory access, no need to concern endianness. The code units and code points are represented by CPU's endianness. 
-    For streaming, use UTF32LE and UTF32BE, which handle endianness. 
-*/ 
-template<typename CharType = unsigned> 
-struct UTF32 { 
-    typedef CharType Ch; 
-    RAPIDJSON_STATIC_ASSERT(sizeof(Ch) >= 4); 
- 
-    enum { supportUnicode = 1 }; 
- 
-    template<typename OutputStream> 
-    static void Encode(OutputStream& os, unsigned codepoint) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 4); 
-        RAPIDJSON_ASSERT(codepoint <= 0x10FFFF); 
-        os.Put(codepoint); 
-    } 
- 
-    template<typename OutputStream> 
-    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 4); 
-        RAPIDJSON_ASSERT(codepoint <= 0x10FFFF); 
-        PutUnsafe(os, codepoint); 
-    } 
- 
-    template <typename InputStream> 
-    static bool Decode(InputStream& is, unsigned* codepoint) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 4); 
-        Ch c = is.Take(); 
-        *codepoint = c; 
-        return c <= 0x10FFFF; 
-    } 
- 
-    template <typename InputStream, typename OutputStream> 
-    static bool Validate(InputStream& is, OutputStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 4); 
-        Ch c; 
-        os.Put(c = is.Take()); 
-        return c <= 0x10FFFF; 
-    } 
-}; 
- 
-//! UTF-32 little endian enocoding. 
-template<typename CharType = unsigned> 
-struct UTF32LE : UTF32<CharType> { 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        CharType c = Take(is); 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_ENCODINGS_H_
+#define RAPIDJSON_ENCODINGS_H_
+
+#include "rapidjson.h"
+
+#ifdef _MSC_VER
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(4244) // conversion from 'type1' to 'type2', possible loss of data
+RAPIDJSON_DIAG_OFF(4702)  // unreachable code
+#elif defined(__GNUC__)
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(effc++)
+RAPIDJSON_DIAG_OFF(overflow)
+#endif
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+///////////////////////////////////////////////////////////////////////////////
+// Encoding
+
+/*! \class rapidjson::Encoding
+    \brief Concept for encoding of Unicode characters.
+
+\code
+concept Encoding {
+    typename Ch;    //! Type of character. A "character" is actually a code unit in unicode's definition.
+
+    enum { supportUnicode = 1 }; // or 0 if not supporting unicode
+
+    //! \brief Encode a Unicode codepoint to an output stream.
+    //! \param os Output stream.
+    //! \param codepoint An unicode codepoint, ranging from 0x0 to 0x10FFFF inclusively.
+    template<typename OutputStream>
+    static void Encode(OutputStream& os, unsigned codepoint);
+
+    //! \brief Decode a Unicode codepoint from an input stream.
+    //! \param is Input stream.
+    //! \param codepoint Output of the unicode codepoint.
+    //! \return true if a valid codepoint can be decoded from the stream.
+    template <typename InputStream>
+    static bool Decode(InputStream& is, unsigned* codepoint);
+
+    //! \brief Validate one Unicode codepoint from an encoded stream.
+    //! \param is Input stream to obtain codepoint.
+    //! \param os Output for copying one codepoint.
+    //! \return true if it is valid.
+    //! \note This function just validating and copying the codepoint without actually decode it.
+    template <typename InputStream, typename OutputStream>
+    static bool Validate(InputStream& is, OutputStream& os);
+
+    // The following functions are deal with byte streams.
+
+    //! Take a character from input byte stream, skip BOM if exist.
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is);
+
+    //! Take a character from input byte stream.
+    template <typename InputByteStream>
+    static Ch Take(InputByteStream& is);
+
+    //! Put BOM to output byte stream.
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os);
+
+    //! Put a character to output byte stream.
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, Ch c);
+};
+\endcode
+*/
+
+///////////////////////////////////////////////////////////////////////////////
+// UTF8
+
+//! UTF-8 encoding.
+/*! http://en.wikipedia.org/wiki/UTF-8
+    http://tools.ietf.org/html/rfc3629
+    \tparam CharType Code unit for storing 8-bit UTF-8 data. Default is char.
+    \note implements Encoding concept
+*/
+template<typename CharType = char>
+struct UTF8 {
+    typedef CharType Ch;
+
+    enum { supportUnicode = 1 };
+
+    template<typename OutputStream>
+    static void Encode(OutputStream& os, unsigned codepoint) {
+        if (codepoint <= 0x7F) 
+            os.Put(static_cast<Ch>(codepoint & 0xFF));
+        else if (codepoint <= 0x7FF) {
+            os.Put(static_cast<Ch>(0xC0 | ((codepoint >> 6) & 0xFF)));
+            os.Put(static_cast<Ch>(0x80 | ((codepoint & 0x3F))));
+        }
+        else if (codepoint <= 0xFFFF) {
+            os.Put(static_cast<Ch>(0xE0 | ((codepoint >> 12) & 0xFF)));
+            os.Put(static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F)));
+            os.Put(static_cast<Ch>(0x80 | (codepoint & 0x3F)));
+        }
+        else {
+            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF);
+            os.Put(static_cast<Ch>(0xF0 | ((codepoint >> 18) & 0xFF)));
+            os.Put(static_cast<Ch>(0x80 | ((codepoint >> 12) & 0x3F)));
+            os.Put(static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F)));
+            os.Put(static_cast<Ch>(0x80 | (codepoint & 0x3F)));
+        }
+    }
+
+    template<typename OutputStream>
+    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) {
+        if (codepoint <= 0x7F) 
+            PutUnsafe(os, static_cast<Ch>(codepoint & 0xFF));
+        else if (codepoint <= 0x7FF) {
+            PutUnsafe(os, static_cast<Ch>(0xC0 | ((codepoint >> 6) & 0xFF)));
+            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint & 0x3F))));
+        }
+        else if (codepoint <= 0xFFFF) {
+            PutUnsafe(os, static_cast<Ch>(0xE0 | ((codepoint >> 12) & 0xFF)));
+            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F)));
+            PutUnsafe(os, static_cast<Ch>(0x80 | (codepoint & 0x3F)));
+        }
+        else {
+            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF);
+            PutUnsafe(os, static_cast<Ch>(0xF0 | ((codepoint >> 18) & 0xFF)));
+            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint >> 12) & 0x3F)));
+            PutUnsafe(os, static_cast<Ch>(0x80 | ((codepoint >> 6) & 0x3F)));
+            PutUnsafe(os, static_cast<Ch>(0x80 | (codepoint & 0x3F)));
+        }
+    }
+
+    template <typename InputStream>
+    static bool Decode(InputStream& is, unsigned* codepoint) {
+#define COPY() c = is.Take(); *codepoint = (*codepoint << 6) | (static_cast<unsigned char>(c) & 0x3Fu)
+#define TRANS(mask) result &= ((GetRange(static_cast<unsigned char>(c)) & mask) != 0)
+#define TAIL() COPY(); TRANS(0x70)
+        typename InputStream::Ch c = is.Take();
+        if (!(c & 0x80)) {
+            *codepoint = static_cast<unsigned char>(c);
+            return true;
+        }
+
+        unsigned char type = GetRange(static_cast<unsigned char>(c));
+        if (type >= 32) {
+            *codepoint = 0;
+        } else {
+            *codepoint = (0xFFu >> type) & static_cast<unsigned char>(c);
+        }
+        bool result = true;
+        switch (type) {
+        case 2: TAIL(); return result;
+        case 3: TAIL(); TAIL(); return result;
+        case 4: COPY(); TRANS(0x50); TAIL(); return result;
+        case 5: COPY(); TRANS(0x10); TAIL(); TAIL(); return result;
+        case 6: TAIL(); TAIL(); TAIL(); return result;
+        case 10: COPY(); TRANS(0x20); TAIL(); return result;
+        case 11: COPY(); TRANS(0x60); TAIL(); TAIL(); return result;
+        default: return false;
+        }
+#undef COPY
+#undef TRANS
+#undef TAIL
+    }
+
+    template <typename InputStream, typename OutputStream>
+    static bool Validate(InputStream& is, OutputStream& os) {
+#define COPY() os.Put(c = is.Take())
+#define TRANS(mask) result &= ((GetRange(static_cast<unsigned char>(c)) & mask) != 0)
+#define TAIL() COPY(); TRANS(0x70)
+        Ch c;
+        COPY();
+        if (!(c & 0x80))
+            return true;
+
+        bool result = true;
+        switch (GetRange(static_cast<unsigned char>(c))) {
+        case 2: TAIL(); return result;
+        case 3: TAIL(); TAIL(); return result;
+        case 4: COPY(); TRANS(0x50); TAIL(); return result;
+        case 5: COPY(); TRANS(0x10); TAIL(); TAIL(); return result;
+        case 6: TAIL(); TAIL(); TAIL(); return result;
+        case 10: COPY(); TRANS(0x20); TAIL(); return result;
+        case 11: COPY(); TRANS(0x60); TAIL(); TAIL(); return result;
+        default: return false;
+        }
+#undef COPY
+#undef TRANS
+#undef TAIL
+    }
+
+    static unsigned char GetRange(unsigned char c) {
+        // Referring to DFA of http://bjoern.hoehrmann.de/utf-8/decoder/dfa/
+        // With new mapping 1 -> 0x10, 7 -> 0x20, 9 -> 0x40, such that AND operation can test multiple types.
+        static const unsigned char type[] = {
+            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+            0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,  0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
+            0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,
+            0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,0x40,
+            0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+            0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,0x20,
+            8,8,2,2,2,2,2,2,2,2,2,2,2,2,2,2,  2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,
+            10,3,3,3,3,3,3,3,3,3,3,3,3,4,3,3, 11,6,6,6,5,8,8,8,8,8,8,8,8,8,8,8,
+        };
+        return type[c];
+    }
+
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        typename InputByteStream::Ch c = Take(is);
+        if (static_cast<unsigned char>(c) != 0xEFu) return c;
+        c = is.Take();
+        if (static_cast<unsigned char>(c) != 0xBBu) return c;
+        c = is.Take();
+        if (static_cast<unsigned char>(c) != 0xBFu) return c;
+        c = is.Take();
+        return c;
+    }
+
+    template <typename InputByteStream>
+    static Ch Take(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        return static_cast<Ch>(is.Take());
+    }
+
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xEFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xBBu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xBFu));
+    }
+
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, Ch c) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(c));
+    }
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// UTF16
+
+//! UTF-16 encoding.
+/*! http://en.wikipedia.org/wiki/UTF-16
+    http://tools.ietf.org/html/rfc2781
+    \tparam CharType Type for storing 16-bit UTF-16 data. Default is wchar_t. C++11 may use char16_t instead.
+    \note implements Encoding concept
+
+    \note For in-memory access, no need to concern endianness. The code units and code points are represented by CPU's endianness.
+    For streaming, use UTF16LE and UTF16BE, which handle endianness.
+*/
+template<typename CharType = wchar_t>
+struct UTF16 {
+    typedef CharType Ch;
+    RAPIDJSON_STATIC_ASSERT(sizeof(Ch) >= 2);
+
+    enum { supportUnicode = 1 };
+
+    template<typename OutputStream>
+    static void Encode(OutputStream& os, unsigned codepoint) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 2);
+        if (codepoint <= 0xFFFF) {
+            RAPIDJSON_ASSERT(codepoint < 0xD800 || codepoint > 0xDFFF); // Code point itself cannot be surrogate pair 
+            os.Put(static_cast<typename OutputStream::Ch>(codepoint));
+        }
+        else {
+            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF);
+            unsigned v = codepoint - 0x10000;
+            os.Put(static_cast<typename OutputStream::Ch>((v >> 10) | 0xD800));
+            os.Put(static_cast<typename OutputStream::Ch>((v & 0x3FF) | 0xDC00));
+        }
+    }
+
+
+    template<typename OutputStream>
+    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 2);
+        if (codepoint <= 0xFFFF) {
+            RAPIDJSON_ASSERT(codepoint < 0xD800 || codepoint > 0xDFFF); // Code point itself cannot be surrogate pair 
+            PutUnsafe(os, static_cast<typename OutputStream::Ch>(codepoint));
+        }
+        else {
+            RAPIDJSON_ASSERT(codepoint <= 0x10FFFF);
+            unsigned v = codepoint - 0x10000;
+            PutUnsafe(os, static_cast<typename OutputStream::Ch>((v >> 10) | 0xD800));
+            PutUnsafe(os, static_cast<typename OutputStream::Ch>((v & 0x3FF) | 0xDC00));
+        }
+    }
+
+    template <typename InputStream>
+    static bool Decode(InputStream& is, unsigned* codepoint) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 2);
+        typename InputStream::Ch c = is.Take();
+        if (c < 0xD800 || c > 0xDFFF) {
+            *codepoint = static_cast<unsigned>(c);
+            return true;
+        }
+        else if (c <= 0xDBFF) {
+            *codepoint = (static_cast<unsigned>(c) & 0x3FF) << 10;
+            c = is.Take();
+            *codepoint |= (static_cast<unsigned>(c) & 0x3FF);
+            *codepoint += 0x10000;
+            return c >= 0xDC00 && c <= 0xDFFF;
+        }
+        return false;
+    }
+
+    template <typename InputStream, typename OutputStream>
+    static bool Validate(InputStream& is, OutputStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 2);
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 2);
+        typename InputStream::Ch c;
+        os.Put(static_cast<typename OutputStream::Ch>(c = is.Take()));
+        if (c < 0xD800 || c > 0xDFFF)
+            return true;
+        else if (c <= 0xDBFF) {
+            os.Put(c = is.Take());
+            return c >= 0xDC00 && c <= 0xDFFF;
+        }
+        return false;
+    }
+};
+
+//! UTF-16 little endian encoding.
+template<typename CharType = wchar_t>
+struct UTF16LE : UTF16<CharType> {
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        CharType c = Take(is);
+        return static_cast<uint16_t>(c) == 0xFEFFu ? Take(is) : c;
+    }
+
+    template <typename InputByteStream>
+    static CharType Take(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        unsigned c = static_cast<uint8_t>(is.Take());
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8;
+        return static_cast<CharType>(c);
+    }
+
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu));
+    }
+
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, CharType c) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(static_cast<unsigned>(c) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>((static_cast<unsigned>(c) >> 8) & 0xFFu));
+    }
+};
+
+//! UTF-16 big endian encoding.
+template<typename CharType = wchar_t>
+struct UTF16BE : UTF16<CharType> {
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        CharType c = Take(is);
+        return static_cast<uint16_t>(c) == 0xFEFFu ? Take(is) : c;
+    }
+
+    template <typename InputByteStream>
+    static CharType Take(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        unsigned c = static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8;
+        c |= static_cast<uint8_t>(is.Take());
+        return static_cast<CharType>(c);
+    }
+
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu));
+    }
+
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, CharType c) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>((static_cast<unsigned>(c) >> 8) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(static_cast<unsigned>(c) & 0xFFu));
+    }
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// UTF32
+
+//! UTF-32 encoding. 
+/*! http://en.wikipedia.org/wiki/UTF-32
+    \tparam CharType Type for storing 32-bit UTF-32 data. Default is unsigned. C++11 may use char32_t instead.
+    \note implements Encoding concept
+
+    \note For in-memory access, no need to concern endianness. The code units and code points are represented by CPU's endianness.
+    For streaming, use UTF32LE and UTF32BE, which handle endianness.
+*/
+template<typename CharType = unsigned>
+struct UTF32 {
+    typedef CharType Ch;
+    RAPIDJSON_STATIC_ASSERT(sizeof(Ch) >= 4);
+
+    enum { supportUnicode = 1 };
+
+    template<typename OutputStream>
+    static void Encode(OutputStream& os, unsigned codepoint) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 4);
+        RAPIDJSON_ASSERT(codepoint <= 0x10FFFF);
+        os.Put(codepoint);
+    }
+
+    template<typename OutputStream>
+    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputStream::Ch) >= 4);
+        RAPIDJSON_ASSERT(codepoint <= 0x10FFFF);
+        PutUnsafe(os, codepoint);
+    }
+
+    template <typename InputStream>
+    static bool Decode(InputStream& is, unsigned* codepoint) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 4);
+        Ch c = is.Take();
+        *codepoint = c;
+        return c <= 0x10FFFF;
+    }
+
+    template <typename InputStream, typename OutputStream>
+    static bool Validate(InputStream& is, OutputStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputStream::Ch) >= 4);
+        Ch c;
+        os.Put(c = is.Take());
+        return c <= 0x10FFFF;
+    }
+};
+
+//! UTF-32 little endian enocoding.
+template<typename CharType = unsigned>
+struct UTF32LE : UTF32<CharType> {
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        CharType c = Take(is);
+        return static_cast<uint32_t>(c) == 0x0000FEFFu ? Take(is) : c;
+    }
+
+    template <typename InputByteStream>
+    static CharType Take(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        unsigned c = static_cast<uint8_t>(is.Take());
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8;
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 16;
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 24;
+        return static_cast<CharType>(c);
+    }
+
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u));
+    }
+
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, CharType c) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(c & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 8) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 16) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 24) & 0xFFu));
+    }
+};
+
+//! UTF-32 big endian encoding.
+template<typename CharType = unsigned>
+struct UTF32BE : UTF32<CharType> {
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        CharType c = Take(is);
         return static_cast<uint32_t>(c) == 0x0000FEFFu ? Take(is) : c; 
-    } 
- 
-    template <typename InputByteStream> 
-    static CharType Take(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        unsigned c = static_cast<uint8_t>(is.Take()); 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8; 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 16; 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 24; 
-        return static_cast<CharType>(c); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u)); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, CharType c) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(c & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 8) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 16) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 24) & 0xFFu)); 
-    } 
-}; 
- 
-//! UTF-32 big endian encoding. 
-template<typename CharType = unsigned> 
-struct UTF32BE : UTF32<CharType> { 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        CharType c = Take(is); 
-        return static_cast<uint32_t>(c) == 0x0000FEFFu ? Take(is) : c;  
-    } 
- 
-    template <typename InputByteStream> 
-    static CharType Take(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        unsigned c = static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 24; 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 16; 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8; 
-        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())); 
-        return static_cast<CharType>(c); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu)); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, CharType c) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 24) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 16) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 8) & 0xFFu)); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(c & 0xFFu)); 
-    } 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// ASCII 
- 
-//! ASCII encoding. 
-/*! http://en.wikipedia.org/wiki/ASCII 
-    \tparam CharType Code unit for storing 7-bit ASCII data. Default is char. 
-    \note implements Encoding concept 
-*/ 
-template<typename CharType = char> 
-struct ASCII { 
-    typedef CharType Ch; 
- 
-    enum { supportUnicode = 0 }; 
- 
-    template<typename OutputStream> 
-    static void Encode(OutputStream& os, unsigned codepoint) { 
-        RAPIDJSON_ASSERT(codepoint <= 0x7F); 
-        os.Put(static_cast<Ch>(codepoint & 0xFF)); 
-    } 
- 
-    template<typename OutputStream> 
-    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) { 
-        RAPIDJSON_ASSERT(codepoint <= 0x7F); 
-        PutUnsafe(os, static_cast<Ch>(codepoint & 0xFF)); 
-    } 
- 
-    template <typename InputStream> 
-    static bool Decode(InputStream& is, unsigned* codepoint) { 
-        uint8_t c = static_cast<uint8_t>(is.Take()); 
-        *codepoint = c; 
-        return c <= 0X7F; 
-    } 
- 
-    template <typename InputStream, typename OutputStream> 
-    static bool Validate(InputStream& is, OutputStream& os) { 
-        uint8_t c = static_cast<uint8_t>(is.Take()); 
-        os.Put(static_cast<typename OutputStream::Ch>(c)); 
-        return c <= 0x7F; 
-    } 
- 
-    template <typename InputByteStream> 
-    static CharType TakeBOM(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        uint8_t c = static_cast<uint8_t>(Take(is)); 
-        return static_cast<Ch>(c); 
-    } 
- 
-    template <typename InputByteStream> 
-    static Ch Take(InputByteStream& is) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1); 
-        return static_cast<Ch>(is.Take()); 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void PutBOM(OutputByteStream& os) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        (void)os; 
-    } 
- 
-    template <typename OutputByteStream> 
-    static void Put(OutputByteStream& os, Ch c) { 
-        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1); 
-        os.Put(static_cast<typename OutputByteStream::Ch>(c)); 
-    } 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// AutoUTF 
- 
-//! Runtime-specified UTF encoding type of a stream. 
-enum UTFType { 
-    kUTF8 = 0,      //!< UTF-8. 
-    kUTF16LE = 1,   //!< UTF-16 little endian. 
-    kUTF16BE = 2,   //!< UTF-16 big endian. 
-    kUTF32LE = 3,   //!< UTF-32 little endian. 
-    kUTF32BE = 4    //!< UTF-32 big endian. 
-}; 
- 
-//! Dynamically select encoding according to stream's runtime-specified UTF encoding type. 
-/*! \note This class can be used with AutoUTFInputtStream and AutoUTFOutputStream, which provides GetType(). 
-*/ 
-template<typename CharType> 
-struct AutoUTF { 
-    typedef CharType Ch; 
- 
-    enum { supportUnicode = 1 }; 
- 
-#define RAPIDJSON_ENCODINGS_FUNC(x) UTF8<Ch>::x, UTF16LE<Ch>::x, UTF16BE<Ch>::x, UTF32LE<Ch>::x, UTF32BE<Ch>::x 
- 
-    template<typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static void Encode(OutputStream& os, unsigned codepoint) { 
-        typedef void (*EncodeFunc)(OutputStream&, unsigned); 
-        static const EncodeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Encode) }; 
-        (*f[os.GetType()])(os, codepoint); 
-    } 
- 
-    template<typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static void EncodeUnsafe(OutputStream& os, unsigned codepoint) { 
-        typedef void (*EncodeFunc)(OutputStream&, unsigned); 
-        static const EncodeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(EncodeUnsafe) }; 
-        (*f[os.GetType()])(os, codepoint); 
-    } 
- 
-    template <typename InputStream> 
-    RAPIDJSON_FORCEINLINE static bool Decode(InputStream& is, unsigned* codepoint) { 
-        typedef bool (*DecodeFunc)(InputStream&, unsigned*); 
-        static const DecodeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Decode) }; 
-        return (*f[is.GetType()])(is, codepoint); 
-    } 
- 
-    template <typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool Validate(InputStream& is, OutputStream& os) { 
-        typedef bool (*ValidateFunc)(InputStream&, OutputStream&); 
-        static const ValidateFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Validate) }; 
-        return (*f[is.GetType()])(is, os); 
-    } 
- 
-#undef RAPIDJSON_ENCODINGS_FUNC 
-}; 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// Transcoder 
- 
-//! Encoding conversion. 
-template<typename SourceEncoding, typename TargetEncoding> 
-struct Transcoder { 
-    //! Take one Unicode codepoint from source encoding, convert it to target encoding and put it to the output stream. 
-    template<typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool Transcode(InputStream& is, OutputStream& os) { 
-        unsigned codepoint; 
-        if (!SourceEncoding::Decode(is, &codepoint)) 
-            return false; 
-        TargetEncoding::Encode(os, codepoint); 
-        return true; 
-    } 
- 
-    template<typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool TranscodeUnsafe(InputStream& is, OutputStream& os) { 
-        unsigned codepoint; 
-        if (!SourceEncoding::Decode(is, &codepoint)) 
-            return false; 
-        TargetEncoding::EncodeUnsafe(os, codepoint); 
-        return true; 
-    } 
- 
-    //! Validate one Unicode codepoint from an encoded stream. 
-    template<typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool Validate(InputStream& is, OutputStream& os) { 
-        return Transcode(is, os);   // Since source/target encoding is different, must transcode. 
-    } 
-}; 
- 
-// Forward declaration. 
-template<typename Stream> 
-inline void PutUnsafe(Stream& stream, typename Stream::Ch c); 
- 
-//! Specialization of Transcoder with same source and target encoding. 
-template<typename Encoding> 
-struct Transcoder<Encoding, Encoding> { 
-    template<typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool Transcode(InputStream& is, OutputStream& os) { 
-        os.Put(is.Take());  // Just copy one code unit. This semantic is different from primary template class. 
-        return true; 
-    } 
-     
-    template<typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool TranscodeUnsafe(InputStream& is, OutputStream& os) { 
-        PutUnsafe(os, is.Take());  // Just copy one code unit. This semantic is different from primary template class. 
-        return true; 
-    } 
-     
-    template<typename InputStream, typename OutputStream> 
-    RAPIDJSON_FORCEINLINE static bool Validate(InputStream& is, OutputStream& os) { 
-        return Encoding::Validate(is, os);  // source/target encoding are the same 
-    } 
-}; 
- 
-RAPIDJSON_NAMESPACE_END 
- 
-#if defined(__GNUC__) || defined(_MSC_VER) 
-RAPIDJSON_DIAG_POP 
-#endif 
- 
-#endif // RAPIDJSON_ENCODINGS_H_ 
+    }
+
+    template <typename InputByteStream>
+    static CharType Take(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        unsigned c = static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 24;
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 16;
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take())) << 8;
+        c |= static_cast<unsigned>(static_cast<uint8_t>(is.Take()));
+        return static_cast<CharType>(c);
+    }
+
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0x00u));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFEu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(0xFFu));
+    }
+
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, CharType c) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 24) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 16) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>((c >> 8) & 0xFFu));
+        os.Put(static_cast<typename OutputByteStream::Ch>(c & 0xFFu));
+    }
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// ASCII
+
+//! ASCII encoding.
+/*! http://en.wikipedia.org/wiki/ASCII
+    \tparam CharType Code unit for storing 7-bit ASCII data. Default is char.
+    \note implements Encoding concept
+*/
+template<typename CharType = char>
+struct ASCII {
+    typedef CharType Ch;
+
+    enum { supportUnicode = 0 };
+
+    template<typename OutputStream>
+    static void Encode(OutputStream& os, unsigned codepoint) {
+        RAPIDJSON_ASSERT(codepoint <= 0x7F);
+        os.Put(static_cast<Ch>(codepoint & 0xFF));
+    }
+
+    template<typename OutputStream>
+    static void EncodeUnsafe(OutputStream& os, unsigned codepoint) {
+        RAPIDJSON_ASSERT(codepoint <= 0x7F);
+        PutUnsafe(os, static_cast<Ch>(codepoint & 0xFF));
+    }
+
+    template <typename InputStream>
+    static bool Decode(InputStream& is, unsigned* codepoint) {
+        uint8_t c = static_cast<uint8_t>(is.Take());
+        *codepoint = c;
+        return c <= 0X7F;
+    }
+
+    template <typename InputStream, typename OutputStream>
+    static bool Validate(InputStream& is, OutputStream& os) {
+        uint8_t c = static_cast<uint8_t>(is.Take());
+        os.Put(static_cast<typename OutputStream::Ch>(c));
+        return c <= 0x7F;
+    }
+
+    template <typename InputByteStream>
+    static CharType TakeBOM(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        uint8_t c = static_cast<uint8_t>(Take(is));
+        return static_cast<Ch>(c);
+    }
+
+    template <typename InputByteStream>
+    static Ch Take(InputByteStream& is) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename InputByteStream::Ch) == 1);
+        return static_cast<Ch>(is.Take());
+    }
+
+    template <typename OutputByteStream>
+    static void PutBOM(OutputByteStream& os) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        (void)os;
+    }
+
+    template <typename OutputByteStream>
+    static void Put(OutputByteStream& os, Ch c) {
+        RAPIDJSON_STATIC_ASSERT(sizeof(typename OutputByteStream::Ch) == 1);
+        os.Put(static_cast<typename OutputByteStream::Ch>(c));
+    }
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// AutoUTF
+
+//! Runtime-specified UTF encoding type of a stream.
+enum UTFType {
+    kUTF8 = 0,      //!< UTF-8.
+    kUTF16LE = 1,   //!< UTF-16 little endian.
+    kUTF16BE = 2,   //!< UTF-16 big endian.
+    kUTF32LE = 3,   //!< UTF-32 little endian.
+    kUTF32BE = 4    //!< UTF-32 big endian.
+};
+
+//! Dynamically select encoding according to stream's runtime-specified UTF encoding type.
+/*! \note This class can be used with AutoUTFInputtStream and AutoUTFOutputStream, which provides GetType().
+*/
+template<typename CharType>
+struct AutoUTF {
+    typedef CharType Ch;
+
+    enum { supportUnicode = 1 };
+
+#define RAPIDJSON_ENCODINGS_FUNC(x) UTF8<Ch>::x, UTF16LE<Ch>::x, UTF16BE<Ch>::x, UTF32LE<Ch>::x, UTF32BE<Ch>::x
+
+    template<typename OutputStream>
+    RAPIDJSON_FORCEINLINE static void Encode(OutputStream& os, unsigned codepoint) {
+        typedef void (*EncodeFunc)(OutputStream&, unsigned);
+        static const EncodeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Encode) };
+        (*f[os.GetType()])(os, codepoint);
+    }
+
+    template<typename OutputStream>
+    RAPIDJSON_FORCEINLINE static void EncodeUnsafe(OutputStream& os, unsigned codepoint) {
+        typedef void (*EncodeFunc)(OutputStream&, unsigned);
+        static const EncodeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(EncodeUnsafe) };
+        (*f[os.GetType()])(os, codepoint);
+    }
+
+    template <typename InputStream>
+    RAPIDJSON_FORCEINLINE static bool Decode(InputStream& is, unsigned* codepoint) {
+        typedef bool (*DecodeFunc)(InputStream&, unsigned*);
+        static const DecodeFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Decode) };
+        return (*f[is.GetType()])(is, codepoint);
+    }
+
+    template <typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool Validate(InputStream& is, OutputStream& os) {
+        typedef bool (*ValidateFunc)(InputStream&, OutputStream&);
+        static const ValidateFunc f[] = { RAPIDJSON_ENCODINGS_FUNC(Validate) };
+        return (*f[is.GetType()])(is, os);
+    }
+
+#undef RAPIDJSON_ENCODINGS_FUNC
+};
+
+///////////////////////////////////////////////////////////////////////////////
+// Transcoder
+
+//! Encoding conversion.
+template<typename SourceEncoding, typename TargetEncoding>
+struct Transcoder {
+    //! Take one Unicode codepoint from source encoding, convert it to target encoding and put it to the output stream.
+    template<typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool Transcode(InputStream& is, OutputStream& os) {
+        unsigned codepoint;
+        if (!SourceEncoding::Decode(is, &codepoint))
+            return false;
+        TargetEncoding::Encode(os, codepoint);
+        return true;
+    }
+
+    template<typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool TranscodeUnsafe(InputStream& is, OutputStream& os) {
+        unsigned codepoint;
+        if (!SourceEncoding::Decode(is, &codepoint))
+            return false;
+        TargetEncoding::EncodeUnsafe(os, codepoint);
+        return true;
+    }
+
+    //! Validate one Unicode codepoint from an encoded stream.
+    template<typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool Validate(InputStream& is, OutputStream& os) {
+        return Transcode(is, os);   // Since source/target encoding is different, must transcode.
+    }
+};
+
+// Forward declaration.
+template<typename Stream>
+inline void PutUnsafe(Stream& stream, typename Stream::Ch c);
+
+//! Specialization of Transcoder with same source and target encoding.
+template<typename Encoding>
+struct Transcoder<Encoding, Encoding> {
+    template<typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool Transcode(InputStream& is, OutputStream& os) {
+        os.Put(is.Take());  // Just copy one code unit. This semantic is different from primary template class.
+        return true;
+    }
+    
+    template<typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool TranscodeUnsafe(InputStream& is, OutputStream& os) {
+        PutUnsafe(os, is.Take());  // Just copy one code unit. This semantic is different from primary template class.
+        return true;
+    }
+    
+    template<typename InputStream, typename OutputStream>
+    RAPIDJSON_FORCEINLINE static bool Validate(InputStream& is, OutputStream& os) {
+        return Encoding::Validate(is, os);  // source/target encoding are the same
+    }
+};
+
+RAPIDJSON_NAMESPACE_END
+
+#if defined(__GNUC__) || defined(_MSC_VER)
+RAPIDJSON_DIAG_POP
+#endif
+
+#endif // RAPIDJSON_ENCODINGS_H_

+ 73 - 73
contrib/libs/rapidjson/include/rapidjson/error/en.h

@@ -1,74 +1,74 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_ERROR_EN_H_ 
-#define RAPIDJSON_ERROR_EN_H_ 
- 
-#include "error.h" 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(switch-enum) 
-RAPIDJSON_DIAG_OFF(covered-switch-default) 
-#endif 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-//! Maps error code of parsing into error message. 
-/*! 
-    \ingroup RAPIDJSON_ERRORS 
-    \param parseErrorCode Error code obtained in parsing. 
-    \return the error message. 
-    \note User can make a copy of this function for localization. 
-        Using switch-case is safer for future modification of error codes. 
-*/ 
-inline const RAPIDJSON_ERROR_CHARTYPE* GetParseError_En(ParseErrorCode parseErrorCode) { 
-    switch (parseErrorCode) { 
-        case kParseErrorNone:                           return RAPIDJSON_ERROR_STRING("No error."); 
- 
-        case kParseErrorDocumentEmpty:                  return RAPIDJSON_ERROR_STRING("The document is empty."); 
-        case kParseErrorDocumentRootNotSingular:        return RAPIDJSON_ERROR_STRING("The document root must not be followed by other values."); 
-     
-        case kParseErrorValueInvalid:                   return RAPIDJSON_ERROR_STRING("Invalid value."); 
-     
-        case kParseErrorObjectMissName:                 return RAPIDJSON_ERROR_STRING("Missing a name for object member."); 
-        case kParseErrorObjectMissColon:                return RAPIDJSON_ERROR_STRING("Missing a colon after a name of object member."); 
-        case kParseErrorObjectMissCommaOrCurlyBracket:  return RAPIDJSON_ERROR_STRING("Missing a comma or '}' after an object member."); 
-     
-        case kParseErrorArrayMissCommaOrSquareBracket:  return RAPIDJSON_ERROR_STRING("Missing a comma or ']' after an array element."); 
- 
-        case kParseErrorStringUnicodeEscapeInvalidHex:  return RAPIDJSON_ERROR_STRING("Incorrect hex digit after \\u escape in string."); 
-        case kParseErrorStringUnicodeSurrogateInvalid:  return RAPIDJSON_ERROR_STRING("The surrogate pair in string is invalid."); 
-        case kParseErrorStringEscapeInvalid:            return RAPIDJSON_ERROR_STRING("Invalid escape character in string."); 
-        case kParseErrorStringMissQuotationMark:        return RAPIDJSON_ERROR_STRING("Missing a closing quotation mark in string."); 
-        case kParseErrorStringInvalidEncoding:          return RAPIDJSON_ERROR_STRING("Invalid encoding in string."); 
- 
-        case kParseErrorNumberTooBig:                   return RAPIDJSON_ERROR_STRING("Number too big to be stored in double."); 
-        case kParseErrorNumberMissFraction:             return RAPIDJSON_ERROR_STRING("Miss fraction part in number."); 
-        case kParseErrorNumberMissExponent:             return RAPIDJSON_ERROR_STRING("Miss exponent in number."); 
- 
-        case kParseErrorTermination:                    return RAPIDJSON_ERROR_STRING("Terminate parsing due to Handler error."); 
-        case kParseErrorUnspecificSyntaxError:          return RAPIDJSON_ERROR_STRING("Unspecific syntax error."); 
- 
-        default:                                        return RAPIDJSON_ERROR_STRING("Unknown error."); 
-    } 
-} 
- 
-RAPIDJSON_NAMESPACE_END 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_POP 
-#endif 
- 
-#endif // RAPIDJSON_ERROR_EN_H_ 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_ERROR_EN_H_
+#define RAPIDJSON_ERROR_EN_H_
+
+#include "error.h"
+
+#ifdef __clang__
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(switch-enum)
+RAPIDJSON_DIAG_OFF(covered-switch-default)
+#endif
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+//! Maps error code of parsing into error message.
+/*!
+    \ingroup RAPIDJSON_ERRORS
+    \param parseErrorCode Error code obtained in parsing.
+    \return the error message.
+    \note User can make a copy of this function for localization.
+        Using switch-case is safer for future modification of error codes.
+*/
+inline const RAPIDJSON_ERROR_CHARTYPE* GetParseError_En(ParseErrorCode parseErrorCode) {
+    switch (parseErrorCode) {
+        case kParseErrorNone:                           return RAPIDJSON_ERROR_STRING("No error.");
+
+        case kParseErrorDocumentEmpty:                  return RAPIDJSON_ERROR_STRING("The document is empty.");
+        case kParseErrorDocumentRootNotSingular:        return RAPIDJSON_ERROR_STRING("The document root must not be followed by other values.");
+    
+        case kParseErrorValueInvalid:                   return RAPIDJSON_ERROR_STRING("Invalid value.");
+    
+        case kParseErrorObjectMissName:                 return RAPIDJSON_ERROR_STRING("Missing a name for object member.");
+        case kParseErrorObjectMissColon:                return RAPIDJSON_ERROR_STRING("Missing a colon after a name of object member.");
+        case kParseErrorObjectMissCommaOrCurlyBracket:  return RAPIDJSON_ERROR_STRING("Missing a comma or '}' after an object member.");
+    
+        case kParseErrorArrayMissCommaOrSquareBracket:  return RAPIDJSON_ERROR_STRING("Missing a comma or ']' after an array element.");
+
+        case kParseErrorStringUnicodeEscapeInvalidHex:  return RAPIDJSON_ERROR_STRING("Incorrect hex digit after \\u escape in string.");
+        case kParseErrorStringUnicodeSurrogateInvalid:  return RAPIDJSON_ERROR_STRING("The surrogate pair in string is invalid.");
+        case kParseErrorStringEscapeInvalid:            return RAPIDJSON_ERROR_STRING("Invalid escape character in string.");
+        case kParseErrorStringMissQuotationMark:        return RAPIDJSON_ERROR_STRING("Missing a closing quotation mark in string.");
+        case kParseErrorStringInvalidEncoding:          return RAPIDJSON_ERROR_STRING("Invalid encoding in string.");
+
+        case kParseErrorNumberTooBig:                   return RAPIDJSON_ERROR_STRING("Number too big to be stored in double.");
+        case kParseErrorNumberMissFraction:             return RAPIDJSON_ERROR_STRING("Miss fraction part in number.");
+        case kParseErrorNumberMissExponent:             return RAPIDJSON_ERROR_STRING("Miss exponent in number.");
+
+        case kParseErrorTermination:                    return RAPIDJSON_ERROR_STRING("Terminate parsing due to Handler error.");
+        case kParseErrorUnspecificSyntaxError:          return RAPIDJSON_ERROR_STRING("Unspecific syntax error.");
+
+        default:                                        return RAPIDJSON_ERROR_STRING("Unknown error.");
+    }
+}
+
+RAPIDJSON_NAMESPACE_END
+
+#ifdef __clang__
+RAPIDJSON_DIAG_POP
+#endif
+
+#endif // RAPIDJSON_ERROR_EN_H_

+ 154 - 154
contrib/libs/rapidjson/include/rapidjson/error/error.h

@@ -1,155 +1,155 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_ERROR_ERROR_H_ 
-#define RAPIDJSON_ERROR_ERROR_H_ 
- 
-#include "../rapidjson.h" 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(padded) 
-#endif 
- 
-/*! \file error.h */ 
- 
-/*! \defgroup RAPIDJSON_ERRORS RapidJSON error handling */ 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// RAPIDJSON_ERROR_CHARTYPE 
- 
-//! Character type of error messages. 
-/*! \ingroup RAPIDJSON_ERRORS 
-    The default character type is \c char. 
-    On Windows, user can define this macro as \c TCHAR for supporting both 
-    unicode/non-unicode settings. 
-*/ 
-#ifndef RAPIDJSON_ERROR_CHARTYPE 
-#define RAPIDJSON_ERROR_CHARTYPE char 
-#endif 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// RAPIDJSON_ERROR_STRING 
- 
-//! Macro for converting string literial to \ref RAPIDJSON_ERROR_CHARTYPE[]. 
-/*! \ingroup RAPIDJSON_ERRORS 
-    By default this conversion macro does nothing. 
-    On Windows, user can define this macro as \c _T(x) for supporting both 
-    unicode/non-unicode settings. 
-*/ 
-#ifndef RAPIDJSON_ERROR_STRING 
-#define RAPIDJSON_ERROR_STRING(x) x 
-#endif 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-/////////////////////////////////////////////////////////////////////////////// 
-// ParseErrorCode 
- 
-//! Error code of parsing. 
-/*! \ingroup RAPIDJSON_ERRORS 
-    \see GenericReader::Parse, GenericReader::GetParseErrorCode 
-*/ 
-enum ParseErrorCode { 
-    kParseErrorNone = 0,                        //!< No error. 
- 
-    kParseErrorDocumentEmpty,                   //!< The document is empty. 
-    kParseErrorDocumentRootNotSingular,         //!< The document root must not follow by other values. 
- 
-    kParseErrorValueInvalid,                    //!< Invalid value. 
- 
-    kParseErrorObjectMissName,                  //!< Missing a name for object member. 
-    kParseErrorObjectMissColon,                 //!< Missing a colon after a name of object member. 
-    kParseErrorObjectMissCommaOrCurlyBracket,   //!< Missing a comma or '}' after an object member. 
- 
-    kParseErrorArrayMissCommaOrSquareBracket,   //!< Missing a comma or ']' after an array element. 
- 
-    kParseErrorStringUnicodeEscapeInvalidHex,   //!< Incorrect hex digit after \\u escape in string. 
-    kParseErrorStringUnicodeSurrogateInvalid,   //!< The surrogate pair in string is invalid. 
-    kParseErrorStringEscapeInvalid,             //!< Invalid escape character in string. 
-    kParseErrorStringMissQuotationMark,         //!< Missing a closing quotation mark in string. 
-    kParseErrorStringInvalidEncoding,           //!< Invalid encoding in string. 
- 
-    kParseErrorNumberTooBig,                    //!< Number too big to be stored in double. 
-    kParseErrorNumberMissFraction,              //!< Miss fraction part in number. 
-    kParseErrorNumberMissExponent,              //!< Miss exponent in number. 
- 
-    kParseErrorTermination,                     //!< Parsing was terminated. 
-    kParseErrorUnspecificSyntaxError            //!< Unspecific syntax error. 
-}; 
- 
-//! Result of parsing (wraps ParseErrorCode) 
-/*! 
-    \ingroup RAPIDJSON_ERRORS 
-    \code 
-        Document doc; 
-        ParseResult ok = doc.Parse("[42]"); 
-        if (!ok) { 
-            fprintf(stderr, "JSON parse error: %s (%u)", 
-                    GetParseError_En(ok.Code()), ok.Offset()); 
-            exit(EXIT_FAILURE); 
-        } 
-    \endcode 
-    \see GenericReader::Parse, GenericDocument::Parse 
-*/ 
-struct ParseResult { 
-public: 
-    //! Default constructor, no error. 
-    ParseResult() : code_(kParseErrorNone), offset_(0) {} 
-    //! Constructor to set an error. 
-    ParseResult(ParseErrorCode code, size_t offset) : code_(code), offset_(offset) {} 
- 
-    //! Get the error code. 
-    ParseErrorCode Code() const { return code_; } 
-    //! Get the error offset, if \ref IsError(), 0 otherwise. 
-    size_t Offset() const { return offset_; } 
- 
-    //! Conversion to \c bool, returns \c true, iff !\ref IsError(). 
-    operator bool() const { return !IsError(); } 
-    //! Whether the result is an error. 
-    bool IsError() const { return code_ != kParseErrorNone; } 
- 
-    bool operator==(const ParseResult& that) const { return code_ == that.code_; } 
-    bool operator==(ParseErrorCode code) const { return code_ == code; } 
-    friend bool operator==(ParseErrorCode code, const ParseResult & err) { return code == err.code_; } 
- 
-    //! Reset error code. 
-    void Clear() { Set(kParseErrorNone); } 
-    //! Update error code and offset. 
-    void Set(ParseErrorCode code, size_t offset = 0) { code_ = code; offset_ = offset; } 
- 
-private: 
-    ParseErrorCode code_; 
-    size_t offset_; 
-}; 
- 
-//! Function pointer type of GetParseError(). 
-/*! \ingroup RAPIDJSON_ERRORS 
- 
-    This is the prototype for \c GetParseError_X(), where \c X is a locale. 
-    User can dynamically change locale in runtime, e.g.: 
-\code 
-    GetParseErrorFunc GetParseError = GetParseError_En; // or whatever 
-    const RAPIDJSON_ERROR_CHARTYPE* s = GetParseError(document.GetParseErrorCode()); 
-\endcode 
-*/ 
-typedef const RAPIDJSON_ERROR_CHARTYPE* (*GetParseErrorFunc)(ParseErrorCode); 
- 
-RAPIDJSON_NAMESPACE_END 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_POP 
-#endif 
- 
-#endif // RAPIDJSON_ERROR_ERROR_H_ 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_ERROR_ERROR_H_
+#define RAPIDJSON_ERROR_ERROR_H_
+
+#include "../rapidjson.h"
+
+#ifdef __clang__
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(padded)
+#endif
+
+/*! \file error.h */
+
+/*! \defgroup RAPIDJSON_ERRORS RapidJSON error handling */
+
+///////////////////////////////////////////////////////////////////////////////
+// RAPIDJSON_ERROR_CHARTYPE
+
+//! Character type of error messages.
+/*! \ingroup RAPIDJSON_ERRORS
+    The default character type is \c char.
+    On Windows, user can define this macro as \c TCHAR for supporting both
+    unicode/non-unicode settings.
+*/
+#ifndef RAPIDJSON_ERROR_CHARTYPE
+#define RAPIDJSON_ERROR_CHARTYPE char
+#endif
+
+///////////////////////////////////////////////////////////////////////////////
+// RAPIDJSON_ERROR_STRING
+
+//! Macro for converting string literial to \ref RAPIDJSON_ERROR_CHARTYPE[].
+/*! \ingroup RAPIDJSON_ERRORS
+    By default this conversion macro does nothing.
+    On Windows, user can define this macro as \c _T(x) for supporting both
+    unicode/non-unicode settings.
+*/
+#ifndef RAPIDJSON_ERROR_STRING
+#define RAPIDJSON_ERROR_STRING(x) x
+#endif
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+///////////////////////////////////////////////////////////////////////////////
+// ParseErrorCode
+
+//! Error code of parsing.
+/*! \ingroup RAPIDJSON_ERRORS
+    \see GenericReader::Parse, GenericReader::GetParseErrorCode
+*/
+enum ParseErrorCode {
+    kParseErrorNone = 0,                        //!< No error.
+
+    kParseErrorDocumentEmpty,                   //!< The document is empty.
+    kParseErrorDocumentRootNotSingular,         //!< The document root must not follow by other values.
+
+    kParseErrorValueInvalid,                    //!< Invalid value.
+
+    kParseErrorObjectMissName,                  //!< Missing a name for object member.
+    kParseErrorObjectMissColon,                 //!< Missing a colon after a name of object member.
+    kParseErrorObjectMissCommaOrCurlyBracket,   //!< Missing a comma or '}' after an object member.
+
+    kParseErrorArrayMissCommaOrSquareBracket,   //!< Missing a comma or ']' after an array element.
+
+    kParseErrorStringUnicodeEscapeInvalidHex,   //!< Incorrect hex digit after \\u escape in string.
+    kParseErrorStringUnicodeSurrogateInvalid,   //!< The surrogate pair in string is invalid.
+    kParseErrorStringEscapeInvalid,             //!< Invalid escape character in string.
+    kParseErrorStringMissQuotationMark,         //!< Missing a closing quotation mark in string.
+    kParseErrorStringInvalidEncoding,           //!< Invalid encoding in string.
+
+    kParseErrorNumberTooBig,                    //!< Number too big to be stored in double.
+    kParseErrorNumberMissFraction,              //!< Miss fraction part in number.
+    kParseErrorNumberMissExponent,              //!< Miss exponent in number.
+
+    kParseErrorTermination,                     //!< Parsing was terminated.
+    kParseErrorUnspecificSyntaxError            //!< Unspecific syntax error.
+};
+
+//! Result of parsing (wraps ParseErrorCode)
+/*!
+    \ingroup RAPIDJSON_ERRORS
+    \code
+        Document doc;
+        ParseResult ok = doc.Parse("[42]");
+        if (!ok) {
+            fprintf(stderr, "JSON parse error: %s (%u)",
+                    GetParseError_En(ok.Code()), ok.Offset());
+            exit(EXIT_FAILURE);
+        }
+    \endcode
+    \see GenericReader::Parse, GenericDocument::Parse
+*/
+struct ParseResult {
+public:
+    //! Default constructor, no error.
+    ParseResult() : code_(kParseErrorNone), offset_(0) {}
+    //! Constructor to set an error.
+    ParseResult(ParseErrorCode code, size_t offset) : code_(code), offset_(offset) {}
+
+    //! Get the error code.
+    ParseErrorCode Code() const { return code_; }
+    //! Get the error offset, if \ref IsError(), 0 otherwise.
+    size_t Offset() const { return offset_; }
+
+    //! Conversion to \c bool, returns \c true, iff !\ref IsError().
+    operator bool() const { return !IsError(); }
+    //! Whether the result is an error.
+    bool IsError() const { return code_ != kParseErrorNone; }
+
+    bool operator==(const ParseResult& that) const { return code_ == that.code_; }
+    bool operator==(ParseErrorCode code) const { return code_ == code; }
+    friend bool operator==(ParseErrorCode code, const ParseResult & err) { return code == err.code_; }
+
+    //! Reset error code.
+    void Clear() { Set(kParseErrorNone); }
+    //! Update error code and offset.
+    void Set(ParseErrorCode code, size_t offset = 0) { code_ = code; offset_ = offset; }
+
+private:
+    ParseErrorCode code_;
+    size_t offset_;
+};
+
+//! Function pointer type of GetParseError().
+/*! \ingroup RAPIDJSON_ERRORS
+
+    This is the prototype for \c GetParseError_X(), where \c X is a locale.
+    User can dynamically change locale in runtime, e.g.:
+\code
+    GetParseErrorFunc GetParseError = GetParseError_En; // or whatever
+    const RAPIDJSON_ERROR_CHARTYPE* s = GetParseError(document.GetParseErrorCode());
+\endcode
+*/
+typedef const RAPIDJSON_ERROR_CHARTYPE* (*GetParseErrorFunc)(ParseErrorCode);
+
+RAPIDJSON_NAMESPACE_END
+
+#ifdef __clang__
+RAPIDJSON_DIAG_POP
+#endif
+
+#endif // RAPIDJSON_ERROR_ERROR_H_

+ 98 - 98
contrib/libs/rapidjson/include/rapidjson/filereadstream.h

@@ -1,99 +1,99 @@
-// Tencent is pleased to support the open source community by making RapidJSON available. 
-//  
-// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved. 
+// Tencent is pleased to support the open source community by making RapidJSON available.
 // 
-// Licensed under the MIT License (the "License"); you may not use this file except 
-// in compliance with the License. You may obtain a copy of the License at 
-// 
-// http://opensource.org/licenses/MIT 
-// 
-// Unless required by applicable law or agreed to in writing, software distributed  
-// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR  
-// CONDITIONS OF ANY KIND, either express or implied. See the License for the  
-// specific language governing permissions and limitations under the License. 
- 
-#ifndef RAPIDJSON_FILEREADSTREAM_H_ 
-#define RAPIDJSON_FILEREADSTREAM_H_ 
- 
-#include "stream.h" 
-#include <cstdio> 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_PUSH 
-RAPIDJSON_DIAG_OFF(padded) 
-RAPIDJSON_DIAG_OFF(unreachable-code) 
-RAPIDJSON_DIAG_OFF(missing-noreturn) 
-#endif 
- 
-RAPIDJSON_NAMESPACE_BEGIN 
- 
-//! File byte stream for input using fread(). 
-/*! 
-    \note implements Stream concept 
-*/ 
-class FileReadStream { 
-public: 
-    typedef char Ch;    //!< Character type (byte). 
- 
-    //! Constructor. 
-    /*! 
-        \param fp File pointer opened for read. 
-        \param buffer user-supplied buffer. 
-        \param bufferSize size of buffer in bytes. Must >=4 bytes. 
-    */ 
-    FileReadStream(std::FILE* fp, char* buffer, size_t bufferSize) : fp_(fp), buffer_(buffer), bufferSize_(bufferSize), bufferLast_(0), current_(buffer_), readCount_(0), count_(0), eof_(false) {  
-        RAPIDJSON_ASSERT(fp_ != 0); 
-        RAPIDJSON_ASSERT(bufferSize >= 4); 
-        Read(); 
-    } 
- 
-    Ch Peek() const { return *current_; } 
-    Ch Take() { Ch c = *current_; Read(); return c; } 
-    size_t Tell() const { return count_ + static_cast<size_t>(current_ - buffer_); } 
- 
-    // Not implemented 
-    void Put(Ch) { RAPIDJSON_ASSERT(false); } 
-    void Flush() { RAPIDJSON_ASSERT(false); }  
-    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; } 
-    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; } 
- 
-    // For encoding detection only. 
-    const Ch* Peek4() const { 
-        return (current_ + 4 <= bufferLast_) ? current_ : 0; 
-    } 
- 
-private: 
-    void Read() { 
-        if (current_ < bufferLast_) 
-            ++current_; 
-        else if (!eof_) { 
-            count_ += readCount_; 
-            readCount_ = fread(buffer_, 1, bufferSize_, fp_); 
-            bufferLast_ = buffer_ + readCount_ - 1; 
-            current_ = buffer_; 
- 
-            if (readCount_ < bufferSize_) { 
-                buffer_[readCount_] = '\0'; 
-                ++bufferLast_; 
-                eof_ = true; 
-            } 
-        } 
-    } 
- 
-    std::FILE* fp_; 
-    Ch *buffer_; 
-    size_t bufferSize_; 
-    Ch *bufferLast_; 
-    Ch *current_; 
-    size_t readCount_; 
-    size_t count_;  //!< Number of characters read 
-    bool eof_; 
-}; 
- 
-RAPIDJSON_NAMESPACE_END 
- 
-#ifdef __clang__ 
-RAPIDJSON_DIAG_POP 
-#endif 
- 
-#endif // RAPIDJSON_FILESTREAM_H_ 
+// Copyright (C) 2015 THL A29 Limited, a Tencent company, and Milo Yip. All rights reserved.
+//
+// Licensed under the MIT License (the "License"); you may not use this file except
+// in compliance with the License. You may obtain a copy of the License at
+//
+// http://opensource.org/licenses/MIT
+//
+// Unless required by applicable law or agreed to in writing, software distributed 
+// under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 
+// CONDITIONS OF ANY KIND, either express or implied. See the License for the 
+// specific language governing permissions and limitations under the License.
+
+#ifndef RAPIDJSON_FILEREADSTREAM_H_
+#define RAPIDJSON_FILEREADSTREAM_H_
+
+#include "stream.h"
+#include <cstdio>
+
+#ifdef __clang__
+RAPIDJSON_DIAG_PUSH
+RAPIDJSON_DIAG_OFF(padded)
+RAPIDJSON_DIAG_OFF(unreachable-code)
+RAPIDJSON_DIAG_OFF(missing-noreturn)
+#endif
+
+RAPIDJSON_NAMESPACE_BEGIN
+
+//! File byte stream for input using fread().
+/*!
+    \note implements Stream concept
+*/
+class FileReadStream {
+public:
+    typedef char Ch;    //!< Character type (byte).
+
+    //! Constructor.
+    /*!
+        \param fp File pointer opened for read.
+        \param buffer user-supplied buffer.
+        \param bufferSize size of buffer in bytes. Must >=4 bytes.
+    */
+    FileReadStream(std::FILE* fp, char* buffer, size_t bufferSize) : fp_(fp), buffer_(buffer), bufferSize_(bufferSize), bufferLast_(0), current_(buffer_), readCount_(0), count_(0), eof_(false) { 
+        RAPIDJSON_ASSERT(fp_ != 0);
+        RAPIDJSON_ASSERT(bufferSize >= 4);
+        Read();
+    }
+
+    Ch Peek() const { return *current_; }
+    Ch Take() { Ch c = *current_; Read(); return c; }
+    size_t Tell() const { return count_ + static_cast<size_t>(current_ - buffer_); }
+
+    // Not implemented
+    void Put(Ch) { RAPIDJSON_ASSERT(false); }
+    void Flush() { RAPIDJSON_ASSERT(false); } 
+    Ch* PutBegin() { RAPIDJSON_ASSERT(false); return 0; }
+    size_t PutEnd(Ch*) { RAPIDJSON_ASSERT(false); return 0; }
+
+    // For encoding detection only.
+    const Ch* Peek4() const {
+        return (current_ + 4 <= bufferLast_) ? current_ : 0;
+    }
+
+private:
+    void Read() {
+        if (current_ < bufferLast_)
+            ++current_;
+        else if (!eof_) {
+            count_ += readCount_;
+            readCount_ = fread(buffer_, 1, bufferSize_, fp_);
+            bufferLast_ = buffer_ + readCount_ - 1;
+            current_ = buffer_;
+
+            if (readCount_ < bufferSize_) {
+                buffer_[readCount_] = '\0';
+                ++bufferLast_;
+                eof_ = true;
+            }
+        }
+    }
+
+    std::FILE* fp_;
+    Ch *buffer_;
+    size_t bufferSize_;
+    Ch *bufferLast_;
+    Ch *current_;
+    size_t readCount_;
+    size_t count_;  //!< Number of characters read
+    bool eof_;
+};
+
+RAPIDJSON_NAMESPACE_END
+
+#ifdef __clang__
+RAPIDJSON_DIAG_POP
+#endif
+
+#endif // RAPIDJSON_FILESTREAM_H_

Some files were not shown because too many files changed in this diff