Satoshi MailBeta Open in Satoshi Mail

JSON Spirit library from http://www.codeproject.com/KB/recipes/JSON_Spirit.aspx, MIT license

Commit by Satoshi Nakamoto (s_nakamoto) on 10 February 2010 · SVN r58 · release v0.2.2 · 13 files, +1,968 −0

Open in Satoshi Mail View on GitHub

Files changed

json/LICENSE.txt
@@ -0,0 +1,24 @@
+The MIT License
+
+Copyright (c) 2007 - 2009 John W. Wilkinson
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without
+restriction, including without limitation the rights to use,
+copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the
+Software is furnished to do so, subject to the following
+conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+OTHER DEALINGS IN THE SOFTWARE.
json/json_spirit.h
@@ -0,0 +1,18 @@
+#ifndef JSON_SPIRIT
+#define JSON_SPIRIT
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include "json_spirit_value.h"
+#include "json_spirit_reader.h"
+#include "json_spirit_writer.h"
+#include "json_spirit_utils.h"
+
+#endif
json/json_spirit_error_position.h
@@ -0,0 +1,54 @@
+#ifndef JSON_SPIRIT_ERROR_POSITION
+#define JSON_SPIRIT_ERROR_POSITION
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include <string>
+
+namespace json_spirit
+{
+    // An Error_position exception is thrown by the "read_or_throw" functions below on finding an error.
+    // Note the "read_or_throw" functions are around 3 times slower than the standard functions "read" 
+    // functions that return a bool.
+    //
+    struct Error_position
+    {
+        Error_position();
+        Error_position( unsigned int line, unsigned int column, const std::string& reason );
+        bool operator==( const Error_position& lhs ) const;
+        unsigned int line_;
+        unsigned int column_;
+        std::string reason_;
+    };
+
+    inline Error_position::Error_position()
+    :   line_( 0 )
+    ,   column_( 0 )
+    {
+    }
+
+    inline Error_position::Error_position( unsigned int line, unsigned int column, const std::string& reason )
+    :   line_( line )
+    ,   column_( column )
+    ,   reason_( reason )
+    {
+    }
+
+    inline bool Error_position::operator==( const Error_position& lhs ) const
+    {
+        if( this == &lhs ) return true;
+
+        return ( reason_ == lhs.reason_ ) &&
+               ( line_   == lhs.line_ ) &&
+               ( column_ == lhs.column_ ); 
+}
+}
+
+#endif
json/json_spirit_reader.cpp
@@ -0,0 +1,137 @@
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#include "json_spirit_reader.h"
+#include "json_spirit_reader_template.h"
+
+using namespace json_spirit;
+
+bool json_spirit::read( const std::string& s, Value& value )
+{
+    return read_string( s, value );
+}
+
+void json_spirit::read_or_throw( const std::string& s, Value& value )
+{
+    read_string_or_throw( s, value );
+}
+
+bool json_spirit::read( std::istream& is, Value& value )
+{
+    return read_stream( is, value );
+}
+
+void json_spirit::read_or_throw( std::istream& is, Value& value )
+{
+    read_stream_or_throw( is, value );
+}
+
+bool json_spirit::read( std::string::const_iterator& begin, std::string::const_iterator end, Value& value )
+{
+    return read_range( begin, end, value );
+}
+
+void json_spirit::read_or_throw( std::string::const_iterator& begin, std::string::const_iterator end, Value& value )
+{
+    begin = read_range_or_throw( begin, end, value );
+}
+
+#ifndef BOOST_NO_STD_WSTRING
+
+bool json_spirit::read( const std::wstring& s, wValue& value )
+{
+    return read_string( s, value );
+}
+
+void json_spirit::read_or_throw( const std::wstring& s, wValue& value )
+{
+    read_string_or_throw( s, value );
+}
+
+bool json_spirit::read( std::wistream& is, wValue& value )
+{
+    return read_stream( is, value );
+}
+
+void json_spirit::read_or_throw( std::wistream& is, wValue& value )
+{
+    read_stream_or_throw( is, value );
+}
+
+bool json_spirit::read( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wValue& value )
+{
+    return read_range( begin, end, value );
+}
+
+void json_spirit::read_or_throw( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wValue& value )
+{
+    begin = read_range_or_throw( begin, end, value );
+}
+
+#endif
+
+bool json_spirit::read( const std::string& s, mValue& value )
+{
+    return read_string( s, value );
+}
+
+void json_spirit::read_or_throw( const std::string& s, mValue& value )
+{
+    read_string_or_throw( s, value );
+}
+
+bool json_spirit::read( std::istream& is, mValue& value )
+{
+    return read_stream( is, value );
+}
+
+void json_spirit::read_or_throw( std::istream& is, mValue& value )
+{
+    read_stream_or_throw( is, value );
+}
+
+bool json_spirit::read( std::string::const_iterator& begin, std::string::const_iterator end, mValue& value )
+{
+    return read_range( begin, end, value );
+}
+
+void json_spirit::read_or_throw( std::string::const_iterator& begin, std::string::const_iterator end, mValue& value )
+{
+    begin = read_range_or_throw( begin, end, value );
+}
+
+#ifndef BOOST_NO_STD_WSTRING
+
+bool json_spirit::read( const std::wstring& s, wmValue& value )
+{
+    return read_string( s, value );
+}
+
+void json_spirit::read_or_throw( const std::wstring& s, wmValue& value )
+{
+    read_string_or_throw( s, value );
+}
+
+bool json_spirit::read( std::wistream& is, wmValue& value )
+{
+    return read_stream( is, value );
+}
+
+void json_spirit::read_or_throw( std::wistream& is, wmValue& value )
+{
+    read_stream_or_throw( is, value );
+}
+
+bool json_spirit::read( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wmValue& value )
+{
+    return read_range( begin, end, value );
+}
+
+void json_spirit::read_or_throw( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wmValue& value )
+{
+    begin = read_range_or_throw( begin, end, value );
+}
+
+#endif
json/json_spirit_reader.h
@@ -0,0 +1,62 @@
+#ifndef JSON_SPIRIT_READER
+#define JSON_SPIRIT_READER
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include "json_spirit_value.h"
+#include "json_spirit_error_position.h"
+#include <iostream>
+
+namespace json_spirit
+{
+    // functions to reads a JSON values
+
+    bool read( const std::string& s, Value& value );
+    bool read( std::istream& is,     Value& value );
+    bool read( std::string::const_iterator& begin, std::string::const_iterator end, Value& value );
+
+    void read_or_throw( const std::string& s, Value& value );  
+    void read_or_throw( std::istream& is,     Value& value );
+    void read_or_throw( std::string::const_iterator& begin, std::string::const_iterator end, Value& value );
+
+#ifndef BOOST_NO_STD_WSTRING
+
+    bool read( const std::wstring& s, wValue& value );
+    bool read( std::wistream&  is,    wValue& value );
+    bool read( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wValue& value );    
+
+    void read_or_throw( const std::wstring& s, wValue& value );
+    void read_or_throw( std::wistream& is,     wValue& value );
+    void read_or_throw( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wValue& value );
+
+#endif
+
+    bool read( const std::string& s, mValue& value );
+    bool read( std::istream& is,     mValue& value );
+    bool read( std::string::const_iterator& begin, std::string::const_iterator end, mValue& value );
+
+    void read_or_throw( const std::string& s, mValue& value );  
+    void read_or_throw( std::istream& is,     mValue& value );
+    void read_or_throw( std::string::const_iterator& begin, std::string::const_iterator end, mValue& value );
+
+#ifndef BOOST_NO_STD_WSTRING
+
+    bool read( const std::wstring& s, wmValue& value );
+    bool read( std::wistream& is,     wmValue& value );
+    bool read( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wmValue& value );    
+
+    void read_or_throw( const std::wstring& s, wmValue& value );
+    void read_or_throw( std::wistream& is,     wmValue& value );
+    void read_or_throw( std::wstring::const_iterator& begin, std::wstring::const_iterator end, wmValue& value );
+
+#endif
+}
+
+#endif
json/json_spirit_reader_template.h
@@ -0,0 +1,612 @@
+#ifndef JSON_SPIRIT_READER_TEMPLATE
+#define JSON_SPIRIT_READER_TEMPLATE
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#include "json_spirit_value.h"
+#include "json_spirit_error_position.h"
+
+//#define BOOST_SPIRIT_THREADSAFE  // uncomment for multithreaded use, requires linking to boost.thread
+
+#include <boost/bind.hpp>
+#include <boost/function.hpp>
+#include <boost/version.hpp>
+
+#if BOOST_VERSION >= 103800
+    #include <boost/spirit/include/classic_core.hpp>
+    #include <boost/spirit/include/classic_confix.hpp>
+    #include <boost/spirit/include/classic_escape_char.hpp>
+    #include <boost/spirit/include/classic_multi_pass.hpp>
+    #include <boost/spirit/include/classic_position_iterator.hpp>
+    #define spirit_namespace boost::spirit::classic
+#else
+    #include <boost/spirit/core.hpp>
+    #include <boost/spirit/utility/confix.hpp>
+    #include <boost/spirit/utility/escape_char.hpp>
+    #include <boost/spirit/iterator/multi_pass.hpp>
+    #include <boost/spirit/iterator/position_iterator.hpp>
+    #define spirit_namespace boost::spirit
+#endif
+
+namespace json_spirit
+{
+    const spirit_namespace::int_parser < boost::int64_t >  int64_p  = spirit_namespace::int_parser < boost::int64_t  >();
+    const spirit_namespace::uint_parser< boost::uint64_t > uint64_p = spirit_namespace::uint_parser< boost::uint64_t >();
+
+    template< class Iter_type >
+    bool is_eq( Iter_type first, Iter_type last, const char* c_str )
+    {
+        for( Iter_type i = first; i != last; ++i, ++c_str )
+        {
+            if( *c_str == 0 ) return false;
+
+            if( *i != *c_str ) return false;
+        }
+
+        return true;
+    }
+
+    template< class Char_type >
+    Char_type hex_to_num( const Char_type c )
+    {
+        if( ( c >= '0' ) && ( c <= '9' ) ) return c - '0';
+        if( ( c >= 'a' ) && ( c <= 'f' ) ) return c - 'a' + 10;
+        if( ( c >= 'A' ) && ( c <= 'F' ) ) return c - 'A' + 10;
+        return 0;
+    }
+
+    template< class Char_type, class Iter_type >
+    Char_type hex_str_to_char( Iter_type& begin )
+    {
+        const Char_type c1( *( ++begin ) );
+        const Char_type c2( *( ++begin ) );
+
+        return ( hex_to_num( c1 ) << 4 ) + hex_to_num( c2 );
+    }       
+
+    template< class Char_type, class Iter_type >
+    Char_type unicode_str_to_char( Iter_type& begin )
+    {
+        const Char_type c1( *( ++begin ) );
+        const Char_type c2( *( ++begin ) );
+        const Char_type c3( *( ++begin ) );
+        const Char_type c4( *( ++begin ) );
+
+        return ( hex_to_num( c1 ) << 12 ) + 
+               ( hex_to_num( c2 ) <<  8 ) + 
+               ( hex_to_num( c3 ) <<  4 ) + 
+               hex_to_num( c4 );
+    }
+
+    template< class String_type >
+    void append_esc_char_and_incr_iter( String_type& s, 
+                                        typename String_type::const_iterator& begin, 
+                                        typename String_type::const_iterator end )
+    {
+        typedef typename String_type::value_type Char_type;
+             
+        const Char_type c2( *begin );
+
+        switch( c2 )
+        {
+            case 't':  s += '\t'; break;
+            case 'b':  s += '\b'; break;
+            case 'f':  s += '\f'; break;
+            case 'n':  s += '\n'; break;
+            case 'r':  s += '\r'; break;
+            case '\\': s += '\\'; break;
+            case '/':  s += '/';  break;
+            case '"':  s += '"';  break;
+            case 'x':  
+            {
+                if( end - begin >= 3 )  //  expecting "xHH..."
+                {
+                    s += hex_str_to_char< Char_type >( begin );  
+                }
+                break;
+            }
+            case 'u':  
+            {
+                if( end - begin >= 5 )  //  expecting "uHHHH..."
+                {
+                    s += unicode_str_to_char< Char_type >( begin );  
+                }
+                break;
+            }
+        }
+    }
+
+    template< class String_type >
+    String_type substitute_esc_chars( typename String_type::const_iterator begin, 
+                                   typename String_type::const_iterator end )
+    {
+        typedef typename String_type::const_iterator Iter_type;
+
+        if( end - begin < 2 ) return String_type( begin, end );
+
+        String_type result;
+        
+        result.reserve( end - begin );
+
+        const Iter_type end_minus_1( end - 1 );
+
+        Iter_type substr_start = begin;
+        Iter_type i = begin;
+
+        for( ; i < end_minus_1; ++i )
+        {
+            if( *i == '\\' )
+            {
+                result.append( substr_start, i );
+
+                ++i;  // skip the '\'
+             
+                append_esc_char_and_incr_iter( result, i, end );
+
+                substr_start = i + 1;
+            }
+        }
+
+        result.append( substr_start, end );
+
+        return result;
+    }
+
+    template< class String_type >
+    String_type get_str_( typename String_type::const_iterator begin, 
+                       typename String_type::const_iterator end )
+    {
+        assert( end - begin >= 2 );
+
+        typedef typename String_type::const_iterator Iter_type;
+
+        Iter_type str_without_quotes( ++begin );
+        Iter_type end_without_quotes( --end );
+
+        return substitute_esc_chars< String_type >( str_without_quotes, end_without_quotes );
+    }
+
+    inline std::string get_str( std::string::const_iterator begin, std::string::const_iterator end )
+    {
+        return get_str_< std::string >( begin, end );
+    }
+
+    inline std::wstring get_str( std::wstring::const_iterator begin, std::wstring::const_iterator end )
+    {
+        return get_str_< std::wstring >( begin, end );
+    }
+    
+    template< class String_type, class Iter_type >
+    String_type get_str( Iter_type begin, Iter_type end )
+    {
+        const String_type tmp( begin, end );  // convert multipass iterators to string iterators
+
+        return get_str( tmp.begin(), tmp.end() );
+    }
+
+    // this class's methods get called by the spirit parse resulting
+    // in the creation of a JSON object or array
+    //
+    // NB Iter_type could be a std::string iterator, wstring iterator, a position iterator or a multipass iterator
+    //
+    template< class Value_type, class Iter_type >
+    class Semantic_actions 
+    {
+    public:
+
+        typedef typename Value_type::Config_type Config_type;
+        typedef typename Config_type::String_type String_type;
+        typedef typename Config_type::Object_type Object_type;
+        typedef typename Config_type::Array_type Array_type;
+        typedef typename String_type::value_type Char_type;
+
+        Semantic_actions( Value_type& value )
+        :   value_( value )
+        ,   current_p_( 0 )
+        {
+        }
+
+        void begin_obj( Char_type c )
+        {
+            assert( c == '{' );
+
+            begin_compound< Object_type >();
+        }
+
+        void end_obj( Char_type c )
+        {
+            assert( c == '}' );
+
+            end_compound();
+        }
+
+        void begin_array( Char_type c )
+        {
+            assert( c == '[' );
+     
+            begin_compound< Array_type >();
+        }
+
+        void end_array( Char_type c )
+        {
+            assert( c == ']' );
+
+            end_compound();
+        }
+
+        void new_name( Iter_type begin, Iter_type end )
+        {
+            assert( current_p_->type() == obj_type );
+
+            name_ = get_str< String_type >( begin, end );
+        }
+
+        void new_str( Iter_type begin, Iter_type end )
+        {
+            add_to_current( get_str< String_type >( begin, end ) );
+        }
+
+        void new_true( Iter_type begin, Iter_type end )
+        {
+            assert( is_eq( begin, end, "true" ) );
+
+            add_to_current( true );
+        }
+
+        void new_false( Iter_type begin, Iter_type end )
+        {
+            assert( is_eq( begin, end, "false" ) );
+
+            add_to_current( false );
+        }
+
+        void new_null( Iter_type begin, Iter_type end )
+        {
+            assert( is_eq( begin, end, "null" ) );
+
+            add_to_current( Value_type() );
+        }
+
+        void new_int( boost::int64_t i )
+        {
+            add_to_current( i );
+        }
+
+        void new_uint64( boost::uint64_t ui )
+        {
+            add_to_current( ui );
+        }
+
+        void new_real( double d )
+        {
+            add_to_current( d );
+        }
+
+    private:
+
+        Semantic_actions& operator=( const Semantic_actions& ); 
+                                    // to prevent "assignment operator could not be generated" warning
+
+        Value_type* add_first( const Value_type& value )
+        {
+            assert( current_p_ == 0 );
+
+            value_ = value;
+            current_p_ = &value_;
+            return current_p_;
json/json_spirit_stream_reader.h
@@ -0,0 +1,70 @@
+#ifndef JSON_SPIRIT_READ_STREAM
+#define JSON_SPIRIT_READ_STREAM
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include "json_spirit_reader_template.h"
+
+namespace json_spirit
+{
+    // these classes allows you to read multiple top level contiguous values from a stream,
+    // the normal stream read functions have a bug that prevent multiple top level values 
+    // from being read unless they are separated by spaces
+
+    template< class Istream_type, class Value_type >
+    class Stream_reader
+    {
+    public:
+
+        Stream_reader( Istream_type& is )
+        :   iters_( is )
+        {
+        }
+
+        bool read_next( Value_type& value )
+        {
+            return read_range( iters_.begin_, iters_.end_, value );
+        }
+
+    private:
+
+        typedef Multi_pass_iters< Istream_type > Mp_iters;
+
+        Mp_iters iters_;
+    };
+
+    template< class Istream_type, class Value_type >
+    class Stream_reader_thrower
+    {
+    public:
+
+        Stream_reader_thrower( Istream_type& is )
+        :   iters_( is )
+        ,    posn_begin_( iters_.begin_, iters_.end_ )
+        ,    posn_end_( iters_.end_, iters_.end_ )
+        {
+        }
+
+        void read_next( Value_type& value )
+        {
+            posn_begin_ = read_range_or_throw( posn_begin_, posn_end_, value );
+        }
+
+    private:
+
+        typedef Multi_pass_iters< Istream_type > Mp_iters;
+        typedef spirit_namespace::position_iterator< typename Mp_iters::Mp_iter > Posn_iter_t;
+
+        Mp_iters iters_;
+        Posn_iter_t posn_begin_, posn_end_;
+    };
+}
+
+#endif
json/json_spirit_utils.h
@@ -0,0 +1,61 @@
+#ifndef JSON_SPIRIT_UTILS
+#define JSON_SPIRIT_UTILS
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include "json_spirit_value.h"
+#include <map>
+
+namespace json_spirit
+{ 
+    template< class Obj_t, class Map_t >
+    void obj_to_map( const Obj_t& obj, Map_t& mp_obj )
+    {
+        mp_obj.clear();
+
+        for( typename Obj_t::const_iterator i = obj.begin(); i != obj.end(); ++i )
+        {
+            mp_obj[ i->name_ ] = i->value_;
+        }
+    }
+
+    template< class Obj_t, class Map_t >
+    void map_to_obj( const Map_t& mp_obj, Obj_t& obj )
+    {
+        obj.clear();
+
+        for( typename Map_t::const_iterator i = mp_obj.begin(); i != mp_obj.end(); ++i )
+        {
+            obj.push_back( typename Obj_t::value_type( i->first, i->second ) );
+        }
+    }
+
+    typedef std::map< std::string, Value > Mapped_obj;
+
+#ifndef BOOST_NO_STD_WSTRING
+    typedef std::map< std::wstring, wValue > wMapped_obj;
+#endif
+
+    template< class Object_type, class String_type >
+    const typename Object_type::value_type::Value_type& find_value( const Object_type& obj, const String_type& name )
+    {
+        for( typename Object_type::const_iterator i = obj.begin(); i != obj.end(); ++i )
+        {
+            if( i->name_ == name )
+            {
+                return i->value_;
+            }
+        }
+
+        return Object_type::value_type::Value_type::null;
+    }
+}
+
+#endif
json/json_spirit_value.cpp
@@ -0,0 +1,8 @@
+/* Copyright (c) 2007 John W Wilkinson
+
+   This source code can be used for any purpose as long as
+   this comment is retained. */
+
+// json spirit version 2.00
+
+#include "json_spirit_value.h"
json/json_spirit_value.h
@@ -0,0 +1,532 @@
+#ifndef JSON_SPIRIT_VALUE
+#define JSON_SPIRIT_VALUE
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include <vector>
+#include <map>
+#include <string>
+#include <cassert>
+#include <sstream>
+#include <stdexcept>
+#include <boost/config.hpp> 
+#include <boost/cstdint.hpp> 
+#include <boost/shared_ptr.hpp> 
+#include <boost/variant.hpp> 
+
+namespace json_spirit
+{
+    enum Value_type{ obj_type, array_type, str_type, bool_type, int_type, real_type, null_type };
+
+    template< class Config >    // Config determines whether the value uses std::string or std::wstring and
+                                // whether JSON Objects are represented as vectors or maps
+    class Value_impl
+    {
+    public:
+
+        typedef Config Config_type;
+        typedef typename Config::String_type String_type;
+        typedef typename Config::Object_type Object;
+        typedef typename Config::Array_type Array;
+        typedef typename String_type::const_pointer Const_str_ptr;  // eg const char*
+
+        Value_impl();  // creates null value
+        Value_impl( Const_str_ptr      value ); 
+        Value_impl( const String_type& value );
+        Value_impl( const Object&      value );
+        Value_impl( const Array&       value );
+        Value_impl( bool               value );
+        Value_impl( int                value );
+        Value_impl( boost::int64_t     value );
+        Value_impl( boost::uint64_t    value );
+        Value_impl( double             value );
+
+        Value_impl( const Value_impl& other );
+
+        bool operator==( const Value_impl& lhs ) const;
+
+        Value_impl& operator=( const Value_impl& lhs );
+
+        Value_type type() const;
+
+        bool is_uint64() const;
+        bool is_null() const;
+
+        const String_type& get_str()    const;
+        const Object&      get_obj()    const;
+        const Array&       get_array()  const;
+        bool               get_bool()   const;
+        int                get_int()    const;
+        boost::int64_t     get_int64()  const;
+        boost::uint64_t    get_uint64() const;
+        double             get_real()   const;
+
+        Object& get_obj();
+        Array&  get_array();
+
+        template< typename T > T get_value() const;  // example usage: int    i = value.get_value< int >();
+                                                     // or             double d = value.get_value< double >();
+
+        static const Value_impl null;
+
+    private:
+
+        void check_type( const Value_type vtype ) const;
+
+        typedef boost::variant< String_type, 
+                                boost::recursive_wrapper< Object >, boost::recursive_wrapper< Array >, 
+                                bool, boost::int64_t, double > Variant;
+
+        Value_type type_;
+        Variant v_;
+        bool is_uint64_;
+    };
+
+    // vector objects
+
+    template< class Config >
+    struct Pair_impl
+    {
+        typedef typename Config::String_type String_type;
+        typedef typename Config::Value_type Value_type;
+
+        Pair_impl( const String_type& name, const Value_type& value );
+
+        bool operator==( const Pair_impl& lhs ) const;
+
+        String_type name_;
+        Value_type value_;
+    };
+
+    template< class String >
+    struct Config_vector
+    {
+        typedef String String_type;
+        typedef Value_impl< Config_vector > Value_type;
+        typedef Pair_impl < Config_vector > Pair_type;
+        typedef std::vector< Value_type > Array_type;
+        typedef std::vector< Pair_type > Object_type;
+
+        static Value_type& add( Object_type& obj, const String_type& name, const Value_type& value )
+        {
+            obj.push_back( Pair_type( name , value ) );
+
+            return obj.back().value_;
+        }
+                
+        static String_type get_name( const Pair_type& pair )
+        {
+            return pair.name_;
+        }
+                
+        static Value_type get_value( const Pair_type& pair )
+        {
+            return pair.value_;
+        }
+    };
+
+    // typedefs for ASCII
+
+    typedef Config_vector< std::string > Config;
+
+    typedef Config::Value_type  Value;
+    typedef Config::Pair_type   Pair;
+    typedef Config::Object_type Object;
+    typedef Config::Array_type  Array;
+
+    // typedefs for Unicode
+
+#ifndef BOOST_NO_STD_WSTRING
+
+    typedef Config_vector< std::wstring > wConfig;
+
+    typedef wConfig::Value_type  wValue;
+    typedef wConfig::Pair_type   wPair;
+    typedef wConfig::Object_type wObject;
+    typedef wConfig::Array_type  wArray;
+#endif
+
+    // map objects
+
+    template< class String >
+    struct Config_map
+    {
+        typedef String String_type;
+        typedef Value_impl< Config_map > Value_type;
+        typedef std::vector< Value_type > Array_type;
+        typedef std::map< String_type, Value_type > Object_type;
+        typedef typename Object_type::value_type Pair_type;
+
+        static Value_type& add( Object_type& obj, const String_type& name, const Value_type& value )
+        {
+            return obj[ name ] = value;
+        }
+                
+        static String_type get_name( const Pair_type& pair )
+        {
+            return pair.first;
+        }
+                
+        static Value_type get_value( const Pair_type& pair )
+        {
+            return pair.second;
+        }
+    };
+
+    // typedefs for ASCII
+
+    typedef Config_map< std::string > mConfig;
+
+    typedef mConfig::Value_type  mValue;
+    typedef mConfig::Object_type mObject;
+    typedef mConfig::Array_type  mArray;
+
+    // typedefs for Unicode
+
+#ifndef BOOST_NO_STD_WSTRING
+
+    typedef Config_map< std::wstring > wmConfig;
+
+    typedef wmConfig::Value_type  wmValue;
+    typedef wmConfig::Object_type wmObject;
+    typedef wmConfig::Array_type  wmArray;
+
+#endif
+
+    ///////////////////////////////////////////////////////////////////////////////////////////////
+    //
+    // implementation
+
+    template< class Config >
+    const Value_impl< Config > Value_impl< Config >::null;
+
+    template< class Config >
+    Value_impl< Config >::Value_impl()
+    :   type_( null_type )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( const Const_str_ptr value )
+    :   type_( str_type )
+    ,   v_( String_type( value ) )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( const String_type& value )
+    :   type_( str_type )
+    ,   v_( value )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( const Object& value )
+    :   type_( obj_type )
+    ,   v_( value )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( const Array& value )
+    :   type_( array_type )
+    ,   v_( value )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( bool value )
+    :   type_( bool_type )
+    ,   v_( value )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( int value )
+    :   type_( int_type )
+    ,   v_( static_cast< boost::int64_t >( value ) )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( boost::int64_t value )
+    :   type_( int_type )
+    ,   v_( value )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( boost::uint64_t value )
+    :   type_( int_type )
+    ,   v_( static_cast< boost::int64_t >( value ) )
+    ,   is_uint64_( true )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( double value )
+    :   type_( real_type )
+    ,   v_( value )
+    ,   is_uint64_( false )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >::Value_impl( const Value_impl< Config >& other )
+    :   type_( other.type() )
+    ,   v_( other.v_ )
+    ,   is_uint64_( other.is_uint64_ )
+    {
+    }
+
+    template< class Config >
+    Value_impl< Config >& Value_impl< Config >::operator=( const Value_impl& lhs )
+    {
json/json_spirit_writer.cpp
@@ -0,0 +1,95 @@
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#include "json_spirit_writer.h"
+#include "json_spirit_writer_template.h"
+
+void json_spirit::write( const Value& value, std::ostream& os )
+{
+    write_stream( value, os, false );
+}
+
+void json_spirit::write_formatted( const Value& value, std::ostream& os )
+{
+    write_stream( value, os, true );
+}
+
+std::string json_spirit::write( const Value& value )
+{
+    return write_string( value, false );
+}
+
+std::string json_spirit::write_formatted( const Value& value )
+{
+    return write_string( value, true );
+}
+
+#ifndef BOOST_NO_STD_WSTRING
+
+void json_spirit::write( const wValue& value, std::wostream& os )
+{
+    write_stream( value, os, false );
+}
+
+void json_spirit::write_formatted( const wValue& value, std::wostream& os )
+{
+    write_stream( value, os, true );
+}
+
+std::wstring json_spirit::write( const wValue&  value )
+{
+    return write_string( value, false );
+}
+
+std::wstring json_spirit::write_formatted( const wValue&  value )
+{
+    return write_string( value, true );
+}
+
+#endif
+
+void json_spirit::write( const mValue& value, std::ostream& os )
+{
+    write_stream( value, os, false );
+}
+
+void json_spirit::write_formatted( const mValue& value, std::ostream& os )
+{
+    write_stream( value, os, true );
+}
+
+std::string json_spirit::write( const mValue& value )
+{
+    return write_string( value, false );
+}
+
+std::string json_spirit::write_formatted( const mValue& value )
+{
+    return write_string( value, true );
+}
+
+#ifndef BOOST_NO_STD_WSTRING
+
+void json_spirit::write( const wmValue& value, std::wostream& os )
+{
+    write_stream( value, os, false );
+}
+
+void json_spirit::write_formatted( const wmValue& value, std::wostream& os )
+{
+    write_stream( value, os, true );
+}
+
+std::wstring json_spirit::write( const wmValue&  value )
+{
+    return write_string( value, false );
+}
+
+std::wstring json_spirit::write_formatted( const wmValue&  value )
+{
+    return write_string( value, true );
+}
+
+#endif
json/json_spirit_writer.h
@@ -0,0 +1,50 @@
+#ifndef JSON_SPIRIT_WRITER
+#define JSON_SPIRIT_WRITER
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#if defined(_MSC_VER) && (_MSC_VER >= 1020)
+# pragma once
+#endif
+
+#include "json_spirit_value.h"
+#include <iostream>
+
+namespace json_spirit
+{
+    // functions to convert JSON Values to text, 
+    // the "formatted" versions add whitespace to format the output nicely
+
+    void         write          ( const Value& value, std::ostream&  os );
+    void         write_formatted( const Value& value, std::ostream&  os );
+    std::string  write          ( const Value& value );
+    std::string  write_formatted( const Value& value );
+
+#ifndef BOOST_NO_STD_WSTRING
+
+    void         write          ( const wValue& value, std::wostream& os );
+    void         write_formatted( const wValue& value, std::wostream& os );
+    std::wstring write          ( const wValue& value );
+    std::wstring write_formatted( const wValue& value );
+
+#endif
+
+    void         write          ( const mValue& value, std::ostream&  os );
+    void         write_formatted( const mValue& value, std::ostream&  os );
+    std::string  write          ( const mValue& value );
+    std::string  write_formatted( const mValue& value );
+
+#ifndef BOOST_NO_STD_WSTRING
+
+    void         write          ( const wmValue& value, std::wostream& os );
+    void         write_formatted( const wmValue& value, std::wostream& os );
+    std::wstring write          ( const wmValue& value );
+    std::wstring write_formatted( const wmValue& value );
+
+#endif
+}
+
+#endif
json/json_spirit_writer_template.h
@@ -0,0 +1,245 @@
+#ifndef JSON_SPIRIT_WRITER_TEMPLATE
+#define JSON_SPIRIT_WRITER_TEMPLATE
+
+//          Copyright John W. Wilkinson 2007 - 2009.
+// Distributed under the MIT License, see accompanying file LICENSE.txt
+
+// json spirit version 4.03
+
+#include "json_spirit_value.h"
+
+#include <cassert>
+#include <sstream>
+#include <iomanip>
+
+namespace json_spirit
+{
+    inline char to_hex_char( unsigned int c )
+    {
+        assert( c <= 0xF );
+
+        const char ch = static_cast< char >( c );
+
+        if( ch < 10 ) return '0' + ch;
+
+        return 'A' - 10 + ch;
+    }
+
+    template< class String_type >
+    String_type non_printable_to_string( unsigned int c )
+    {
+        typedef typename String_type::value_type Char_type;
+
+        String_type result( 6, '\\' );
+
+        result[1] = 'u';
+
+        result[ 5 ] = to_hex_char( c & 0x000F ); c >>= 4;
+        result[ 4 ] = to_hex_char( c & 0x000F ); c >>= 4;
+        result[ 3 ] = to_hex_char( c & 0x000F ); c >>= 4;
+        result[ 2 ] = to_hex_char( c & 0x000F );
+
+        return result;
+    }
+
+    template< typename Char_type, class String_type >
+    bool add_esc_char( Char_type c, String_type& s )
+    {
+        switch( c )
+        {
+            case '"':  s += to_str< String_type >( "\\\"" ); return true;
+            case '\\': s += to_str< String_type >( "\\\\" ); return true;
+            case '\b': s += to_str< String_type >( "\\b"  ); return true;
+            case '\f': s += to_str< String_type >( "\\f"  ); return true;
+            case '\n': s += to_str< String_type >( "\\n"  ); return true;
+            case '\r': s += to_str< String_type >( "\\r"  ); return true;
+            case '\t': s += to_str< String_type >( "\\t"  ); return true;
+        }
+
+        return false;
+    }
+
+    template< class String_type >
+    String_type add_esc_chars( const String_type& s )
+    {
+        typedef typename String_type::const_iterator Iter_type;
+        typedef typename String_type::value_type     Char_type;
+
+        String_type result;
+
+        const Iter_type end( s.end() );
+
+        for( Iter_type i = s.begin(); i != end; ++i )
+        {
+            const Char_type c( *i );
+
+            if( add_esc_char( c, result ) ) continue;
+
+            const wint_t unsigned_c( ( c >= 0 ) ? c : 256 + c );
+
+            if( iswprint( unsigned_c ) )
+            {
+                result += c;
+            }
+            else
+            {
+                result += non_printable_to_string< String_type >( unsigned_c );
+            }
+        }
+
+        return result;
+    }
+
+    // this class generates the JSON text,
+    // it keeps track of the indentation level etc.
+    //
+    template< class Value_type, class Ostream_type >
+    class Generator
+    {
+        typedef typename Value_type::Config_type Config_type;
+        typedef typename Config_type::String_type String_type;
+        typedef typename Config_type::Object_type Object_type;
+        typedef typename Config_type::Array_type Array_type;
+        typedef typename String_type::value_type Char_type;
+        typedef typename Object_type::value_type Obj_member_type;
+
+    public:
+
+        Generator( const Value_type& value, Ostream_type& os, bool pretty )
+        :   os_( os )
+        ,   indentation_level_( 0 )
+        ,   pretty_( pretty )
+        {
+            output( value );
+        }
+
+    private:
+
+        void output( const Value_type& value )
+        {
+            switch( value.type() )
+            {
+                case obj_type:   output( value.get_obj() );   break;
+                case array_type: output( value.get_array() ); break;
+                case str_type:   output( value.get_str() );   break;
+                case bool_type:  output( value.get_bool() );  break;
+                case int_type:   output_int( value );         break;
+                case real_type:  os_ << std::showpoint << std::setprecision( 16 ) 
+                                     << value.get_real();     break;
+                case null_type:  os_ << "null";               break;
+                default: assert( false );
+            }
+        }
+
+        void output( const Object_type& obj )
+        {
+            output_array_or_obj( obj, '{', '}' );
+        }
+
+        void output( const Array_type& arr )
+        {
+            output_array_or_obj( arr, '[', ']' );
+        }
+
+        void output( const Obj_member_type& member )
+        {
+            output( Config_type::get_name( member ) ); space(); 
+            os_ << ':'; space(); 
+            output( Config_type::get_value( member ) );
+        }
+
+        void output_int( const Value_type& value )
+        {
+            if( value.is_uint64() )
+            {
+                os_ << value.get_uint64();
+            }
+            else
+            {
+               os_ << value.get_int64();
+            }
+        }
+
+        void output( const String_type& s )
+        {
+            os_ << '"' << add_esc_chars( s ) << '"';
+        }
+
+        void output( bool b )
+        {
+            os_ << to_str< String_type >( b ? "true" : "false" );
+        }
+
+        template< class T >
+        void output_array_or_obj( const T& t, Char_type start_char, Char_type end_char )
+        {
+            os_ << start_char; new_line();
+
+            ++indentation_level_;
+            
+            for( typename T::const_iterator i = t.begin(); i != t.end(); ++i )
+            {
+                indent(); output( *i );
+
+                typename T::const_iterator next = i;
+
+                if( ++next != t.end())
+                {
+                    os_ << ',';
+                }
+
+                new_line();
+            }
+
+            --indentation_level_;
+
+            indent(); os_ << end_char;
+        }
+        
+        void indent()
+        {
+            if( !pretty_ ) return;
+
+            for( int i = 0; i < indentation_level_; ++i )
+            { 
+                os_ << "    ";
+            }
+        }
+
+        void space()
+        {
+            if( pretty_ ) os_ << ' ';
+        }
+
+        void new_line()
+        {
+            if( pretty_ ) os_ << '\n';
+        }
+
+        Generator& operator=( const Generator& ); // to prevent "assignment operator could not be generated" warning
+
+        Ostream_type& os_;
+        int indentation_level_;
+        bool pretty_;
+    };
+
+    template< class Value_type, class Ostream_type >
+    void write_stream( const Value_type& value, Ostream_type& os, bool pretty )
+    {
+        Generator< Value_type, Ostream_type >( value, os, pretty );
+    }
+
+    template< class Value_type >
+    typename Value_type::String_type write_string( const Value_type& value, bool pretty )
+    {
+        typedef typename Value_type::String_type::value_type Char_type;
+
+        std::basic_ostringstream< Char_type > os;
+
+        write_stream( value, os, pretty );
+
+        return os.str();
+    }
+}
+
+#endif