| /////////1/////////2/////////3/////////4/////////5/////////6/////////7/////////8 |
| // basic_text_iprimitive.ipp: |
| |
| // (C) Copyright 2002 Robert Ramey - http://www.rrsd.com . |
| // Distributed under the Boost Software License, Version 1.0. (See |
| // accompanying file LICENSE_1_0.txt or copy at |
| // http://www.boost.org/LICENSE_1_0.txt) |
| |
| // See http://www.boost.org for updates, documentation, and revision history. |
| |
| #include <cstddef> // size_t |
| #include <cstddef> // NULL |
| |
| #include <boost/config.hpp> |
| #if defined(BOOST_NO_STDC_NAMESPACE) |
| namespace std{ |
| using ::size_t; |
| } // namespace std |
| #endif |
| |
| #include <boost/serialization/throw_exception.hpp> |
| #include <boost/serialization/pfto.hpp> |
| |
| #include <boost/archive/basic_text_iprimitive.hpp> |
| #include <boost/archive/codecvt_null.hpp> |
| #include <boost/archive/add_facet.hpp> |
| |
| #include <boost/archive/iterators/remove_whitespace.hpp> |
| #include <boost/archive/iterators/istream_iterator.hpp> |
| #include <boost/archive/iterators/binary_from_base64.hpp> |
| #include <boost/archive/iterators/transform_width.hpp> |
| |
| namespace boost { |
| namespace archive { |
| |
| namespace { |
| template<class CharType> |
| bool is_whitespace(CharType c); |
| |
| template<> |
| bool is_whitespace(char t){ |
| return 0 != std::isspace(t); |
| } |
| |
| #ifndef BOOST_NO_CWCHAR |
| template<> |
| bool is_whitespace(wchar_t t){ |
| return 0 != std::iswspace(t); |
| } |
| #endif |
| } |
| |
| // translate base64 text into binary and copy into buffer |
| // until buffer is full. |
| template<class IStream> |
| BOOST_ARCHIVE_OR_WARCHIVE_DECL(void) |
| basic_text_iprimitive<IStream>::load_binary( |
| void *address, |
| std::size_t count |
| ){ |
| typedef BOOST_DEDUCED_TYPENAME IStream::char_type CharType; |
| |
| if(0 == count) |
| return; |
| |
| assert( |
| static_cast<std::size_t>((std::numeric_limits<std::streamsize>::max)()) |
| > (count + sizeof(CharType) - 1)/sizeof(CharType) |
| ); |
| |
| if(is.fail()) |
| boost::serialization::throw_exception( |
| archive_exception(archive_exception::input_stream_error) |
| ); |
| // convert from base64 to binary |
| typedef BOOST_DEDUCED_TYPENAME |
| iterators::transform_width< |
| iterators::binary_from_base64< |
| iterators::remove_whitespace< |
| iterators::istream_iterator<CharType> |
| > |
| ,CharType |
| > |
| ,8 |
| ,6 |
| ,CharType |
| > |
| binary; |
| |
| binary ti_begin = binary( |
| BOOST_MAKE_PFTO_WRAPPER( |
| iterators::istream_iterator<CharType>(is) |
| ) |
| ); |
| |
| char * caddr = static_cast<char *>(address); |
| |
| // take care that we don't increment anymore than necessary |
| while(--count > 0){ |
| *caddr++ = static_cast<char>(*ti_begin); |
| ++ti_begin; |
| } |
| *caddr++ = static_cast<char>(*ti_begin); |
| |
| iterators::istream_iterator<CharType> i; |
| for(;;){ |
| BOOST_DEDUCED_TYPENAME IStream::int_type r; |
| r = is.get(); |
| if(is.eof()) |
| break; |
| if(is_whitespace(static_cast<CharType>(r))) |
| break; |
| } |
| } |
| |
| template<class IStream> |
| BOOST_ARCHIVE_OR_WARCHIVE_DECL(BOOST_PP_EMPTY()) |
| basic_text_iprimitive<IStream>::basic_text_iprimitive( |
| IStream &is_, |
| bool no_codecvt |
| ) : |
| #ifndef BOOST_NO_STD_LOCALE |
| is(is_), |
| flags_saver(is_), |
| precision_saver(is_), |
| archive_locale(NULL), |
| locale_saver(* is_.rdbuf()) |
| { |
| if(! no_codecvt){ |
| archive_locale.reset( |
| add_facet( |
| std::locale::classic(), |
| new codecvt_null<BOOST_DEDUCED_TYPENAME IStream::char_type> |
| ) |
| ); |
| is.imbue(* archive_locale); |
| } |
| is >> std::noboolalpha; |
| } |
| #else |
| is(is_), |
| flags_saver(is_), |
| precision_saver(is_) |
| {} |
| #endif |
| |
| template<class IStream> |
| BOOST_ARCHIVE_OR_WARCHIVE_DECL(BOOST_PP_EMPTY()) |
| basic_text_iprimitive<IStream>::~basic_text_iprimitive(){ |
| is.sync(); |
| } |
| |
| } // namespace archive |
| } // namespace boost |