1 // Copyright 2007-2010 Baptiste Lepilleur and The JsonCpp Authors
2 // Distributed under MIT license, or public domain if desired and
3 // recognized in your jurisdiction.
4 // See file LICENSE for detail or copy at http://jsoncpp.sourceforge.net/LICENSE
5 
6 #ifndef JSON_H_INCLUDED
7 #define JSON_H_INCLUDED
8 
9 #if !defined(JSON_IS_AMALGAMATION)
10 #include "forwards.h"
11 #endif // if !defined(JSON_IS_AMALGAMATION)
12 
13 // Conditional NORETURN attribute on the throw functions would:
14 // a) suppress false positives from static code analysis
15 // b) possibly improve optimization opportunities.
16 #if !defined(JSONCPP_NORETURN)
17 #if defined(_MSC_VER) && _MSC_VER == 1800
18 #define JSONCPP_NORETURN __declspec(noreturn)
19 #else
20 #define JSONCPP_NORETURN [[noreturn]]
21 #endif
22 #endif
23 
24 // Support for '= delete' with template declarations was a late addition
25 // to the c++11 standard and is rejected by clang 3.8 and Apple clang 8.2
26 // even though these declare themselves to be c++11 compilers.
27 #if !defined(JSONCPP_TEMPLATE_DELETE)
28 #if defined(__clang__) && defined(__apple_build_version__)
29 #if __apple_build_version__ <= 8000042
30 #define JSONCPP_TEMPLATE_DELETE
31 #endif
32 #elif defined(__clang__)
33 #if __clang_major__ == 3 && __clang_minor__ <= 8
34 #define JSONCPP_TEMPLATE_DELETE
35 #endif
36 #endif
37 #if !defined(JSONCPP_TEMPLATE_DELETE)
38 #define JSONCPP_TEMPLATE_DELETE = delete
39 #endif
40 #endif
41 
42 #include <array>
43 #include <exception>
44 #include <map>
45 #include <memory>
46 #include <string>
47 #include <vector>
48 
49 // Disable warning C4251: <data member>: <type> needs to have dll-interface to
50 // be used by...
51 #if defined(JSONCPP_DISABLE_DLL_INTERFACE_WARNING)
52 #pragma warning(push)
53 #pragma warning(disable : 4251)
54 #endif // if defined(JSONCPP_DISABLE_DLL_INTERFACE_WARNING)
55 
56 #if !defined(__SUNPRO_CC)
57 #pragma pack(push, 8)
58 #endif
59 
60 /** \brief JSON (JavaScript Object Notation).
61  */
62 namespace Json {
63 
64 #if JSON_USE_EXCEPTION
65 /** Base class for all exceptions we throw.
66  *
67  * We use nothing but these internally. Of course, STL can throw others.
68  */
69 class JSON_API Exception : public std::exception {
70 public:
71   Exception(String msg);
72   ~Exception() noexcept override;
73   char const* what() const noexcept override;
74 
75 protected:
76   String msg_;
77 };
78 
79 /** Exceptions which the user cannot easily avoid.
80  *
81  * E.g. out-of-memory (when we use malloc), stack-overflow, malicious input
82  *
83  * \remark derived from Json::Exception
84  */
85 class JSON_API RuntimeError : public Exception {
86 public:
87   RuntimeError(String const& msg);
88 };
89 
90 /** Exceptions thrown by JSON_ASSERT/JSON_FAIL macros.
91  *
92  * These are precondition-violations (user bugs) and internal errors (our bugs).
93  *
94  * \remark derived from Json::Exception
95  */
96 class JSON_API LogicError : public Exception {
97 public:
98   LogicError(String const& msg);
99 };
100 #endif
101 
102 /// used internally
103 JSONCPP_NORETURN void throwRuntimeError(String const& msg);
104 /// used internally
105 JSONCPP_NORETURN void throwLogicError(String const& msg);
106 
107 /** \brief Type of the value held by a Value object.
108  */
109 enum ValueType {
110   nullValue = 0, ///< 'null' value
111   intValue,      ///< signed integer value
112   uintValue,     ///< unsigned integer value
113   realValue,     ///< double value
114   stringValue,   ///< UTF-8 string value
115   booleanValue,  ///< bool value
116   arrayValue,    ///< array value (ordered list)
117   objectValue    ///< object value (collection of name/value pairs).
118 };
119 
120 enum CommentPlacement {
121   commentBefore = 0,      ///< a comment placed on the line before a value
122   commentAfterOnSameLine, ///< a comment just after a value on the same line
123   commentAfter, ///< a comment on the line after a value (only make sense for
124   /// root value)
125   numberOfCommentPlacement
126 };
127 
128 /** \brief Type of precision for formatting of real values.
129  */
130 enum PrecisionType {
131   significantDigits = 0, ///< we set max number of significant digits in string
132   decimalPlaces          ///< we set max number of digits after "." in string
133 };
134 
135 /** \brief Lightweight wrapper to tag static string.
136  *
137  * Value constructor and objectValue member assignment takes advantage of the
138  * StaticString and avoid the cost of string duplication when storing the
139  * string or the member name.
140  *
141  * Example of usage:
142  * \code
143  * Json::Value aValue( StaticString("some text") );
144  * Json::Value object;
145  * static const StaticString code("code");
146  * object[code] = 1234;
147  * \endcode
148  */
149 class JSON_API StaticString {
150 public:
StaticString(const char * czstring)151   explicit StaticString(const char* czstring) : c_str_(czstring) {}
152 
153   operator const char*() const { return c_str_; }
154 
c_str()155   const char* c_str() const { return c_str_; }
156 
157 private:
158   const char* c_str_;
159 };
160 
161 /** \brief Represents a <a HREF="http://www.json.org">JSON</a> value.
162  *
163  * This class is a discriminated union wrapper that can represents a:
164  * - signed integer [range: Value::minInt - Value::maxInt]
165  * - unsigned integer (range: 0 - Value::maxUInt)
166  * - double
167  * - UTF-8 string
168  * - boolean
169  * - 'null'
170  * - an ordered list of Value
171  * - collection of name/value pairs (javascript object)
172  *
173  * The type of the held value is represented by a #ValueType and
174  * can be obtained using type().
175  *
176  * Values of an #objectValue or #arrayValue can be accessed using operator[]()
177  * methods.
178  * Non-const methods will automatically create the a #nullValue element
179  * if it does not exist.
180  * The sequence of an #arrayValue will be automatically resized and initialized
181  * with #nullValue. resize() can be used to enlarge or truncate an #arrayValue.
182  *
183  * The get() methods can be used to obtain default value in the case the
184  * required element does not exist.
185  *
186  * It is possible to iterate over the list of member keys of an object using
187  * the getMemberNames() method.
188  *
189  * \note #Value string-length fit in size_t, but keys must be < 2^30.
190  * (The reason is an implementation detail.) A #CharReader will raise an
191  * exception if a bound is exceeded to avoid security holes in your app,
192  * but the Value API does *not* check bounds. That is the responsibility
193  * of the caller.
194  */
195 class JSON_API Value {
196   friend class ValueIteratorBase;
197 
198 public:
199   using Members = std::vector<String>;
200   using iterator = ValueIterator;
201   using const_iterator = ValueConstIterator;
202   using UInt = Json::UInt;
203   using Int = Json::Int;
204 #if defined(JSON_HAS_INT64)
205   using UInt64 = Json::UInt64;
206   using Int64 = Json::Int64;
207 #endif // defined(JSON_HAS_INT64)
208   using LargestInt = Json::LargestInt;
209   using LargestUInt = Json::LargestUInt;
210   using ArrayIndex = Json::ArrayIndex;
211 
212   // Required for boost integration, e. g. BOOST_TEST
213   using value_type = std::string;
214 
215 #if JSON_USE_NULLREF
216   // Binary compatibility kludges, do not use.
217   static const Value& null;
218   static const Value& nullRef;
219 #endif
220 
221   // null and nullRef are deprecated, use this instead.
222   static Value const& nullSingleton();
223 
224   /// Minimum signed integer value that can be stored in a Json::Value.
225   static constexpr LargestInt minLargestInt =
226       LargestInt(~(LargestUInt(-1) / 2));
227   /// Maximum signed integer value that can be stored in a Json::Value.
228   static constexpr LargestInt maxLargestInt = LargestInt(LargestUInt(-1) / 2);
229   /// Maximum unsigned integer value that can be stored in a Json::Value.
230   static constexpr LargestUInt maxLargestUInt = LargestUInt(-1);
231 
232   /// Minimum signed int value that can be stored in a Json::Value.
233   static constexpr Int minInt = Int(~(UInt(-1) / 2));
234   /// Maximum signed int value that can be stored in a Json::Value.
235   static constexpr Int maxInt = Int(UInt(-1) / 2);
236   /// Maximum unsigned int value that can be stored in a Json::Value.
237   static constexpr UInt maxUInt = UInt(-1);
238 
239 #if defined(JSON_HAS_INT64)
240   /// Minimum signed 64 bits int value that can be stored in a Json::Value.
241   static constexpr Int64 minInt64 = Int64(~(UInt64(-1) / 2));
242   /// Maximum signed 64 bits int value that can be stored in a Json::Value.
243   static constexpr Int64 maxInt64 = Int64(UInt64(-1) / 2);
244   /// Maximum unsigned 64 bits int value that can be stored in a Json::Value.
245   static constexpr UInt64 maxUInt64 = UInt64(-1);
246 #endif // defined(JSON_HAS_INT64)
247   /// Default precision for real value for string representation.
248   static constexpr UInt defaultRealPrecision = 17;
249   // The constant is hard-coded because some compiler have trouble
250   // converting Value::maxUInt64 to a double correctly (AIX/xlC).
251   // Assumes that UInt64 is a 64 bits integer.
252   static constexpr double maxUInt64AsDouble = 18446744073709551615.0;
253 // Workaround for bug in the NVIDIAs CUDA 9.1 nvcc compiler
254 // when using gcc and clang backend compilers.  CZString
255 // cannot be defined as private.  See issue #486
256 #ifdef __NVCC__
257 public:
258 #else
259 private:
260 #endif
261 #ifndef JSONCPP_DOC_EXCLUDE_IMPLEMENTATION
262   class CZString {
263   public:
264     enum DuplicationPolicy { noDuplication = 0, duplicate, duplicateOnCopy };
265     CZString(ArrayIndex index);
266     CZString(char const* str, unsigned length, DuplicationPolicy allocate);
267     CZString(CZString const& other);
268     CZString(CZString&& other);
269     ~CZString();
270     CZString& operator=(const CZString& other);
271     CZString& operator=(CZString&& other);
272 
273     bool operator<(CZString const& other) const;
274     bool operator==(CZString const& other) const;
275     ArrayIndex index() const;
276     // const char* c_str() const; ///< deprecated
277     char const* data() const;
278     unsigned length() const;
279     bool isStaticString() const;
280 
281   private:
282     void swap(CZString& other);
283 
284     struct StringStorage {
285       unsigned policy_ : 2;
286       unsigned length_ : 30; // 1GB max
287     };
288 
289     char const* cstr_; // actually, a prefixed string, unless policy is noDup
290     union {
291       ArrayIndex index_;
292       StringStorage storage_;
293     };
294   };
295 
296 public:
297   typedef std::map<CZString, Value> ObjectValues;
298 #endif // ifndef JSONCPP_DOC_EXCLUDE_IMPLEMENTATION
299 
300 public:
301   /**
302    * \brief Create a default Value of the given type.
303    *
304    * This is a very useful constructor.
305    * To create an empty array, pass arrayValue.
306    * To create an empty object, pass objectValue.
307    * Another Value can then be set to this one by assignment.
308    * This is useful since clear() and resize() will not alter types.
309    *
310    * Examples:
311    *   \code
312    *   Json::Value null_value; // null
313    *   Json::Value arr_value(Json::arrayValue); // []
314    *   Json::Value obj_value(Json::objectValue); // {}
315    *   \endcode
316    */
317   Value(ValueType type = nullValue);
318   Value(Int value);
319   Value(UInt value);
320 #if defined(JSON_HAS_INT64)
321   Value(Int64 value);
322   Value(UInt64 value);
323 #endif // if defined(JSON_HAS_INT64)
324   Value(double value);
325   Value(const char* value); ///< Copy til first 0. (NULL causes to seg-fault.)
326   Value(const char* begin, const char* end); ///< Copy all, incl zeroes.
327   /**
328    * \brief Constructs a value from a static string.
329    *
330    * Like other value string constructor but do not duplicate the string for
331    * internal storage. The given string must remain alive after the call to
332    * this constructor.
333    *
334    * \note This works only for null-terminated strings. (We cannot change the
335    * size of this class, so we have nowhere to store the length, which might be
336    * computed later for various operations.)
337    *
338    * Example of usage:
339    *   \code
340    *   static StaticString foo("some text");
341    *   Json::Value aValue(foo);
342    *   \endcode
343    */
344   Value(const StaticString& value);
345   Value(const String& value);
346   Value(bool value);
347   Value(std::nullptr_t ptr) = delete;
348   Value(const Value& other);
349   Value(Value&& other);
350   ~Value();
351 
352   /// \note Overwrite existing comments. To preserve comments, use
353   /// #swapPayload().
354   Value& operator=(const Value& other);
355   Value& operator=(Value&& other);
356 
357   /// Swap everything.
358   void swap(Value& other);
359   /// Swap values but leave comments and source offsets in place.
360   void swapPayload(Value& other);
361 
362   /// copy everything.
363   void copy(const Value& other);
364   /// copy values but leave comments and source offsets in place.
365   void copyPayload(const Value& other);
366 
367   ValueType type() const;
368 
369   /// Compare payload only, not comments etc.
370   bool operator<(const Value& other) const;
371   bool operator<=(const Value& other) const;
372   bool operator>=(const Value& other) const;
373   bool operator>(const Value& other) const;
374   bool operator==(const Value& other) const;
375   bool operator!=(const Value& other) const;
376   int compare(const Value& other) const;
377 
378   const char* asCString() const; ///< Embedded zeroes could cause you trouble!
379 #if JSONCPP_USING_SECURE_MEMORY
380   unsigned getCStringLength() const; // Allows you to understand the length of
381                                      // the CString
382 #endif
383   String asString() const; ///< Embedded zeroes are possible.
384   /** Get raw char* of string-value.
385    *  \return false if !string. (Seg-fault if str or end are NULL.)
386    */
387   bool getString(char const** begin, char const** end) const;
388   Int asInt() const;
389   UInt asUInt() const;
390 #if defined(JSON_HAS_INT64)
391   Int64 asInt64() const;
392   UInt64 asUInt64() const;
393 #endif // if defined(JSON_HAS_INT64)
394   LargestInt asLargestInt() const;
395   LargestUInt asLargestUInt() const;
396   float asFloat() const;
397   double asDouble() const;
398   bool asBool() const;
399 
400   bool isNull() const;
401   bool isBool() const;
402   bool isInt() const;
403   bool isInt64() const;
404   bool isUInt() const;
405   bool isUInt64() const;
406   bool isIntegral() const;
407   bool isDouble() const;
408   bool isNumeric() const;
409   bool isString() const;
410   bool isArray() const;
411   bool isObject() const;
412 
413   /// The `as<T>` and `is<T>` member function templates and specializations.
414   template <typename T> T as() const JSONCPP_TEMPLATE_DELETE;
415   template <typename T> bool is() const JSONCPP_TEMPLATE_DELETE;
416 
417   bool isConvertibleTo(ValueType other) const;
418 
419   /// Number of values in array or object
420   ArrayIndex size() const;
421 
422   /// \brief Return true if empty array, empty object, or null;
423   /// otherwise, false.
424   bool empty() const;
425 
426   /// Return !isNull()
427   explicit operator bool() const;
428 
429   /// Remove all object members and array elements.
430   /// \pre type() is arrayValue, objectValue, or nullValue
431   /// \post type() is unchanged
432   void clear();
433 
434   /// Resize the array to newSize elements.
435   /// New elements are initialized to null.
436   /// May only be called on nullValue or arrayValue.
437   /// \pre type() is arrayValue or nullValue
438   /// \post type() is arrayValue
439   void resize(ArrayIndex newSize);
440 
441   //@{
442   /// Access an array element (zero based index). If the array contains less
443   /// than index element, then null value are inserted in the array so that
444   /// its size is index+1.
445   /// (You may need to say 'value[0u]' to get your compiler to distinguish
446   /// this from the operator[] which takes a string.)
447   Value& operator[](ArrayIndex index);
448   Value& operator[](int index);
449   //@}
450 
451   //@{
452   /// Access an array element (zero based index).
453   /// (You may need to say 'value[0u]' to get your compiler to distinguish
454   /// this from the operator[] which takes a string.)
455   const Value& operator[](ArrayIndex index) const;
456   const Value& operator[](int index) const;
457   //@}
458 
459   /// If the array contains at least index+1 elements, returns the element
460   /// value, otherwise returns defaultValue.
461   Value get(ArrayIndex index, const Value& defaultValue) const;
462   /// Return true if index < size().
463   bool isValidIndex(ArrayIndex index) const;
464   /// \brief Append value to array at the end.
465   ///
466   /// Equivalent to jsonvalue[jsonvalue.size()] = value;
467   Value& append(const Value& value);
468   Value& append(Value&& value);
469 
470   /// \brief Insert value in array at specific index
471   bool insert(ArrayIndex index, const Value& newValue);
472   bool insert(ArrayIndex index, Value&& newValue);
473 
474   /// Access an object value by name, create a null member if it does not exist.
475   /// \note Because of our implementation, keys are limited to 2^30 -1 chars.
476   /// Exceeding that will cause an exception.
477   Value& operator[](const char* key);
478   /// Access an object value by name, returns null if there is no member with
479   /// that name.
480   const Value& operator[](const char* key) const;
481   /// Access an object value by name, create a null member if it does not exist.
482   /// \param key may contain embedded nulls.
483   Value& operator[](const String& key);
484   /// Access an object value by name, returns null if there is no member with
485   /// that name.
486   /// \param key may contain embedded nulls.
487   const Value& operator[](const String& key) const;
488   /** \brief Access an object value by name, create a null member if it does not
489    * exist.
490    *
491    * If the object has no entry for that name, then the member name used to
492    * store the new entry is not duplicated.
493    * Example of use:
494    *   \code
495    *   Json::Value object;
496    *   static const StaticString code("code");
497    *   object[code] = 1234;
498    *   \endcode
499    */
500   Value& operator[](const StaticString& key);
501   /// Return the member named key if it exist, defaultValue otherwise.
502   /// \note deep copy
503   Value get(const char* key, const Value& defaultValue) const;
504   /// Return the member named key if it exist, defaultValue otherwise.
505   /// \note deep copy
506   /// \note key may contain embedded nulls.
507   Value get(const char* begin, const char* end,
508             const Value& defaultValue) const;
509   /// Return the member named key if it exist, defaultValue otherwise.
510   /// \note deep copy
511   /// \param key may contain embedded nulls.
512   Value get(const String& key, const Value& defaultValue) const;
513   /// Most general and efficient version of isMember()const, get()const,
514   /// and operator[]const
515   /// \note As stated elsewhere, behavior is undefined if (end-begin) >= 2^30
516   Value const* find(char const* begin, char const* end) const;
517   /// Most general and efficient version of object-mutators.
518   /// \note As stated elsewhere, behavior is undefined if (end-begin) >= 2^30
519   /// \return non-zero, but JSON_ASSERT if this is neither object nor nullValue.
520   Value* demand(char const* begin, char const* end);
521   /// \brief Remove and return the named member.
522   ///
523   /// Do nothing if it did not exist.
524   /// \pre type() is objectValue or nullValue
525   /// \post type() is unchanged
526   void removeMember(const char* key);
527   /// Same as removeMember(const char*)
528   /// \param key may contain embedded nulls.
529   void removeMember(const String& key);
530   /// Same as removeMember(const char* begin, const char* end, Value* removed),
531   /// but 'key' is null-terminated.
532   bool removeMember(const char* key, Value* removed);
533   /** \brief Remove the named map member.
534    *
535    *  Update 'removed' iff removed.
536    *  \param key may contain embedded nulls.
537    *  \return true iff removed (no exceptions)
538    */
539   bool removeMember(String const& key, Value* removed);
540   /// Same as removeMember(String const& key, Value* removed)
541   bool removeMember(const char* begin, const char* end, Value* removed);
542   /** \brief Remove the indexed array element.
543    *
544    *  O(n) expensive operations.
545    *  Update 'removed' iff removed.
546    *  \return true if removed (no exceptions)
547    */
548   bool removeIndex(ArrayIndex index, Value* removed);
549 
550   /// Return true if the object has a member named key.
551   /// \note 'key' must be null-terminated.
552   bool isMember(const char* key) const;
553   /// Return true if the object has a member named key.
554   /// \param key may contain embedded nulls.
555   bool isMember(const String& key) const;
556   /// Same as isMember(String const& key)const
557   bool isMember(const char* begin, const char* end) const;
558 
559   /// \brief Return a list of the member names.
560   ///
561   /// If null, return an empty list.
562   /// \pre type() is objectValue or nullValue
563   /// \post if type() was nullValue, it remains nullValue
564   Members getMemberNames() const;
565 
566   /// deprecated Always pass len.
567   JSONCPP_DEPRECATED("Use setComment(String const&) instead.")
setComment(const char * comment,CommentPlacement placement)568   void setComment(const char* comment, CommentPlacement placement) {
569     setComment(String(comment, strlen(comment)), placement);
570   }
571   /// Comments must be //... or /* ... */
setComment(const char * comment,size_t len,CommentPlacement placement)572   void setComment(const char* comment, size_t len, CommentPlacement placement) {
573     setComment(String(comment, len), placement);
574   }
575   /// Comments must be //... or /* ... */
576   void setComment(String comment, CommentPlacement placement);
577   bool hasComment(CommentPlacement placement) const;
578   /// Include delimiters and embedded newlines.
579   String getComment(CommentPlacement placement) const;
580 
581   String toStyledString() const;
582 
583   const_iterator begin() const;
584   const_iterator end() const;
585 
586   iterator begin();
587   iterator end();
588 
589   // Accessors for the [start, limit) range of bytes within the JSON text from
590   // which this value was parsed, if any.
591   void setOffsetStart(ptrdiff_t start);
592   void setOffsetLimit(ptrdiff_t limit);
593   ptrdiff_t getOffsetStart() const;
594   ptrdiff_t getOffsetLimit() const;
595 
596 private:
setType(ValueType v)597   void setType(ValueType v) {
598     bits_.value_type_ = static_cast<unsigned char>(v);
599   }
isAllocated()600   bool isAllocated() const { return bits_.allocated_; }
setIsAllocated(bool v)601   void setIsAllocated(bool v) { bits_.allocated_ = v; }
602 
603   void initBasic(ValueType type, bool allocated = false);
604   void dupPayload(const Value& other);
605   void releasePayload();
606   void dupMeta(const Value& other);
607 
608   Value& resolveReference(const char* key);
609   Value& resolveReference(const char* key, const char* end);
610 
611   // struct MemberNamesTransform
612   //{
613   //   typedef const char *result_type;
614   //   const char *operator()( const CZString &name ) const
615   //   {
616   //      return name.c_str();
617   //   }
618   //};
619 
620   union ValueHolder {
621     LargestInt int_;
622     LargestUInt uint_;
623     double real_;
624     bool bool_;
625     char* string_; // if allocated_, ptr to { unsigned, char[] }.
626     ObjectValues* map_;
627   } value_;
628 
629   struct {
630     // Really a ValueType, but types should agree for bitfield packing.
631     unsigned int value_type_ : 8;
632     // Unless allocated_, string_ must be null-terminated.
633     unsigned int allocated_ : 1;
634   } bits_;
635 
636   class Comments {
637   public:
638     Comments() = default;
639     Comments(const Comments& that);
640     Comments(Comments&& that);
641     Comments& operator=(const Comments& that);
642     Comments& operator=(Comments&& that);
643     bool has(CommentPlacement slot) const;
644     String get(CommentPlacement slot) const;
645     void set(CommentPlacement slot, String comment);
646 
647   private:
648     using Array = std::array<String, numberOfCommentPlacement>;
649     std::unique_ptr<Array> ptr_;
650   };
651   Comments comments_;
652 
653   // [start, limit) byte offsets in the source JSON text from which this Value
654   // was extracted.
655   ptrdiff_t start_;
656   ptrdiff_t limit_;
657 };
658 
659 template <> inline bool Value::as<bool>() const { return asBool(); }
660 template <> inline bool Value::is<bool>() const { return isBool(); }
661 
662 template <> inline Int Value::as<Int>() const { return asInt(); }
663 template <> inline bool Value::is<Int>() const { return isInt(); }
664 
665 template <> inline UInt Value::as<UInt>() const { return asUInt(); }
666 template <> inline bool Value::is<UInt>() const { return isUInt(); }
667 
668 #if defined(JSON_HAS_INT64)
669 template <> inline Int64 Value::as<Int64>() const { return asInt64(); }
670 template <> inline bool Value::is<Int64>() const { return isInt64(); }
671 
672 template <> inline UInt64 Value::as<UInt64>() const { return asUInt64(); }
673 template <> inline bool Value::is<UInt64>() const { return isUInt64(); }
674 #endif
675 
676 template <> inline double Value::as<double>() const { return asDouble(); }
677 template <> inline bool Value::is<double>() const { return isDouble(); }
678 
679 template <> inline String Value::as<String>() const { return asString(); }
680 template <> inline bool Value::is<String>() const { return isString(); }
681 
682 /// These `as` specializations are type conversions, and do not have a
683 /// corresponding `is`.
684 template <> inline float Value::as<float>() const { return asFloat(); }
685 template <> inline const char* Value::as<const char*>() const {
686   return asCString();
687 }
688 
689 /** \brief Experimental and untested: represents an element of the "path" to
690  * access a node.
691  */
692 class JSON_API PathArgument {
693 public:
694   friend class Path;
695 
696   PathArgument();
697   PathArgument(ArrayIndex index);
698   PathArgument(const char* key);
699   PathArgument(String key);
700 
701 private:
702   enum Kind { kindNone = 0, kindIndex, kindKey };
703   String key_;
704   ArrayIndex index_{};
705   Kind kind_{kindNone};
706 };
707 
708 /** \brief Experimental and untested: represents a "path" to access a node.
709  *
710  * Syntax:
711  * - "." => root node
712  * - ".[n]" => elements at index 'n' of root node (an array value)
713  * - ".name" => member named 'name' of root node (an object value)
714  * - ".name1.name2.name3"
715  * - ".[0][1][2].name1[3]"
716  * - ".%" => member name is provided as parameter
717  * - ".[%]" => index is provided as parameter
718  */
719 class JSON_API Path {
720 public:
721   Path(const String& path, const PathArgument& a1 = PathArgument(),
722        const PathArgument& a2 = PathArgument(),
723        const PathArgument& a3 = PathArgument(),
724        const PathArgument& a4 = PathArgument(),
725        const PathArgument& a5 = PathArgument());
726 
727   const Value& resolve(const Value& root) const;
728   Value resolve(const Value& root, const Value& defaultValue) const;
729   /// Creates the "path" to access the specified node and returns a reference on
730   /// the node.
731   Value& make(Value& root) const;
732 
733 private:
734   using InArgs = std::vector<const PathArgument*>;
735   using Args = std::vector<PathArgument>;
736 
737   void makePath(const String& path, const InArgs& in);
738   void addPathInArg(const String& path, const InArgs& in,
739                     InArgs::const_iterator& itInArg, PathArgument::Kind kind);
740   static void invalidPath(const String& path, int location);
741 
742   Args args_;
743 };
744 
745 /** \brief base class for Value iterators.
746  *
747  */
748 class JSON_API ValueIteratorBase {
749 public:
750   using iterator_category = std::bidirectional_iterator_tag;
751   using size_t = unsigned int;
752   using difference_type = int;
753   using SelfType = ValueIteratorBase;
754 
755   bool operator==(const SelfType& other) const { return isEqual(other); }
756 
757   bool operator!=(const SelfType& other) const { return !isEqual(other); }
758 
759   difference_type operator-(const SelfType& other) const {
760     return other.computeDistance(*this);
761   }
762 
763   /// Return either the index or the member name of the referenced value as a
764   /// Value.
765   Value key() const;
766 
767   /// Return the index of the referenced Value, or -1 if it is not an
768   /// arrayValue.
769   UInt index() const;
770 
771   /// Return the member name of the referenced Value, or "" if it is not an
772   /// objectValue.
773   /// \note Avoid `c_str()` on result, as embedded zeroes are possible.
774   String name() const;
775 
776   /// Return the member name of the referenced Value. "" if it is not an
777   /// objectValue.
778   /// deprecated This cannot be used for UTF-8 strings, since there can be
779   /// embedded nulls.
780   JSONCPP_DEPRECATED("Use `key = name();` instead.")
781   char const* memberName() const;
782   /// Return the member name of the referenced Value, or NULL if it is not an
783   /// objectValue.
784   /// \note Better version than memberName(). Allows embedded nulls.
785   char const* memberName(char const** end) const;
786 
787 protected:
788   /*! Internal utility functions to assist with implementing
789    *   other iterator functions. The const and non-const versions
790    *   of the "deref" protected methods expose the protected
791    *   current_ member variable in a way that can often be
792    *   optimized away by the compiler.
793    */
794   const Value& deref() const;
795   Value& deref();
796 
797   void increment();
798 
799   void decrement();
800 
801   difference_type computeDistance(const SelfType& other) const;
802 
803   bool isEqual(const SelfType& other) const;
804 
805   void copy(const SelfType& other);
806 
807 private:
808   Value::ObjectValues::iterator current_;
809   // Indicates that iterator is for a null value.
810   bool isNull_{true};
811 
812 public:
813   // For some reason, BORLAND needs these at the end, rather
814   // than earlier. No idea why.
815   ValueIteratorBase();
816   explicit ValueIteratorBase(const Value::ObjectValues::iterator& current);
817 };
818 
819 /** \brief const iterator for object and array value.
820  *
821  */
822 class JSON_API ValueConstIterator : public ValueIteratorBase {
823   friend class Value;
824 
825 public:
826   using value_type = const Value;
827   // typedef unsigned int size_t;
828   // typedef int difference_type;
829   using reference = const Value&;
830   using pointer = const Value*;
831   using SelfType = ValueConstIterator;
832 
833   ValueConstIterator();
834   ValueConstIterator(ValueIterator const& other);
835 
836 private:
837   /*! internal Use by Value to create an iterator.
838    */
839   explicit ValueConstIterator(const Value::ObjectValues::iterator& current);
840 
841 public:
842   SelfType& operator=(const ValueIteratorBase& other);
843 
844   SelfType operator++(int) {
845     SelfType temp(*this);
846     ++*this;
847     return temp;
848   }
849 
850   SelfType operator--(int) {
851     SelfType temp(*this);
852     --*this;
853     return temp;
854   }
855 
856   SelfType& operator--() {
857     decrement();
858     return *this;
859   }
860 
861   SelfType& operator++() {
862     increment();
863     return *this;
864   }
865 
866   reference operator*() const { return deref(); }
867 
868   pointer operator->() const { return &deref(); }
869 };
870 
871 /** \brief Iterator for object and array value.
872  */
873 class JSON_API ValueIterator : public ValueIteratorBase {
874   friend class Value;
875 
876 public:
877   using value_type = Value;
878   using size_t = unsigned int;
879   using difference_type = int;
880   using reference = Value&;
881   using pointer = Value*;
882   using SelfType = ValueIterator;
883 
884   ValueIterator();
885   explicit ValueIterator(const ValueConstIterator& other);
886   ValueIterator(const ValueIterator& other);
887 
888 private:
889   /*! internal Use by Value to create an iterator.
890    */
891   explicit ValueIterator(const Value::ObjectValues::iterator& current);
892 
893 public:
894   SelfType& operator=(const SelfType& other);
895 
896   SelfType operator++(int) {
897     SelfType temp(*this);
898     ++*this;
899     return temp;
900   }
901 
902   SelfType operator--(int) {
903     SelfType temp(*this);
904     --*this;
905     return temp;
906   }
907 
908   SelfType& operator--() {
909     decrement();
910     return *this;
911   }
912 
913   SelfType& operator++() {
914     increment();
915     return *this;
916   }
917 
918   /*! The return value of non-const iterators can be
919    *  changed, so the these functions are not const
920    *  because the returned references/pointers can be used
921    *  to change state of the base class.
922    */
923   reference operator*() { return deref(); }
924   pointer operator->() { return &deref(); }
925 };
926 
swap(Value & a,Value & b)927 inline void swap(Value& a, Value& b) { a.swap(b); }
928 
929 } // namespace Json
930 
931 #if !defined(__SUNPRO_CC)
932 #pragma pack(pop)
933 #endif
934 
935 #if defined(JSONCPP_DISABLE_DLL_INTERFACE_WARNING)
936 #pragma warning(pop)
937 #endif // if defined(JSONCPP_DISABLE_DLL_INTERFACE_WARNING)
938 
939 #endif // JSON_H_INCLUDED
940