1 // (C) Copyright 2008 CodeRage, LLC (turkanis at coderage dot com) 2 // (C) Copyright 2003-2007 Jonathan Turkanis 3 // Distributed under the Boost Software License, Version 1.0. (See accompanying 4 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt.) 5 6 // See http://www.boost.org/libs/iostreams for documentation. 7 8 #ifndef BOOST_IOSTREAMS_STREAM_BUFFER_HPP_INCLUDED 9 #define BOOST_IOSTREAMS_STREAM_BUFFER_HPP_INCLUDED 10 11 #if defined(_MSC_VER) 12 # pragma once 13 #endif 14 15 #include <memory> // allocator. 16 #include <boost/config.hpp> // BOOST_DEDUCED_TYPENAME. 17 #include <boost/iostreams/detail/char_traits.hpp> 18 #include <boost/iostreams/detail/config/overload_resolution.hpp> 19 #include <boost/iostreams/detail/forward.hpp> 20 #include <boost/iostreams/detail/ios.hpp> // failure, streamsize. 21 #include <boost/iostreams/detail/streambuf/direct_streambuf.hpp> 22 #include <boost/iostreams/detail/streambuf/indirect_streambuf.hpp> 23 #include <boost/iostreams/traits.hpp> 24 #include <boost/static_assert.hpp> 25 #include <boost/throw_exception.hpp> 26 #include <boost/type_traits/is_convertible.hpp> 27 28 // Must come last. 29 #include <boost/iostreams/detail/config/disable_warnings.hpp> // MSVC. 30 31 namespace boost { namespace iostreams { namespace detail { 32 33 template<typename T, typename Tr, typename Alloc, typename Mode> 34 struct stream_buffer_traits { 35 typedef typename 36 mpl::if_< 37 is_convertible< 38 BOOST_DEDUCED_TYPENAME category_of<T>::type, 39 direct_tag 40 >, 41 direct_streambuf<T, Tr>, 42 indirect_streambuf<T, Tr, Alloc, Mode> 43 >::type type; 44 }; 45 46 } } } // End namespaces detail, iostreams, boost 47 48 #ifdef BOOST_IOSTREAMS_BROKEN_OVERLOAD_RESOLUTION 49 # include <boost/iostreams/detail/broken_overload_resolution/stream_buffer.hpp> 50 #else 51 52 namespace boost { namespace iostreams { 53 54 template< typename T, 55 typename Tr = 56 BOOST_IOSTREAMS_CHAR_TRAITS( 57 BOOST_DEDUCED_TYPENAME char_type_of<T>::type 58 ), 59 typename Alloc = 60 std::allocator< 61 BOOST_DEDUCED_TYPENAME char_type_of<T>::type 62 >, 63 typename Mode = BOOST_DEDUCED_TYPENAME mode_of<T>::type > 64 class stream_buffer 65 : public detail::stream_buffer_traits<T, Tr, Alloc, Mode>::type 66 { 67 private: 68 BOOST_STATIC_ASSERT(( 69 is_convertible< 70 BOOST_DEDUCED_TYPENAME iostreams::category_of<T>::type, Mode 71 >::value 72 )); 73 typedef typename 74 detail::stream_buffer_traits< 75 T, Tr, Alloc, Mode 76 >::type base_type; 77 public: 78 typedef typename char_type_of<T>::type char_type; 79 struct category 80 : Mode, 81 closable_tag, 82 streambuf_tag 83 { }; 84 BOOST_IOSTREAMS_STREAMBUF_TYPEDEFS(Tr) 85 public: stream_buffer()86 stream_buffer() { } ~stream_buffer()87 ~stream_buffer() 88 { 89 try { 90 if (this->is_open() && this->auto_close()) 91 this->close(); 92 } catch (...) { } 93 } BOOST_IOSTREAMS_FORWARD(stream_buffer,open_impl,T,BOOST_IOSTREAMS_PUSH_PARAMS,BOOST_IOSTREAMS_PUSH_ARGS)94 BOOST_IOSTREAMS_FORWARD( stream_buffer, open_impl, T, 95 BOOST_IOSTREAMS_PUSH_PARAMS, 96 BOOST_IOSTREAMS_PUSH_ARGS ) 97 T& operator*() { return *this->component(); } operator ->()98 T* operator->() { return this->component(); } 99 private: open_impl(const T & t BOOST_IOSTREAMS_PUSH_PARAMS ())100 void open_impl(const T& t BOOST_IOSTREAMS_PUSH_PARAMS()) 101 { // Used for forwarding. 102 if (this->is_open()) 103 boost::throw_exception( 104 BOOST_IOSTREAMS_FAILURE("already open") 105 ); 106 base_type::open(t BOOST_IOSTREAMS_PUSH_ARGS()); 107 } 108 }; 109 110 } } // End namespaces iostreams, boost. 111 112 #endif // #ifdef BOOST_IOSTREAMS_BROKEN_OVERLOAD_RESOLUTION 113 114 #include <boost/iostreams/detail/config/enable_warnings.hpp> // MSVC. 115 116 #endif // #ifndef BOOST_IOSTREAMS_STREAM_BUFFER_HPP_INCLUDED 117