Chris@16: // (C) Copyright 2008 CodeRage, LLC (turkanis at coderage dot com) Chris@16: // (C) Copyright 2003-2007 Jonathan Turkanis Chris@16: // Distributed under the Boost Software License, Version 1.0. (See accompanying Chris@16: // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt.) Chris@16: Chris@16: // See http://www.boost.org/libs/iostreams for documentation. Chris@16: Chris@16: // To do: handle bidirection streams and output-seekable components. Chris@16: Chris@16: #ifndef BOOST_IOSTREAMS_SKIP_HPP_INCLUDED Chris@16: #define BOOST_IOSTREAMS_SKIP_HPP_INCLUDED Chris@16: Chris@16: #if defined(_MSC_VER) && (_MSC_VER >= 1020) Chris@16: # pragma once Chris@16: #endif Chris@16: Chris@16: #include Chris@16: #include // failure. Chris@16: #include Chris@16: #include Chris@16: #include Chris@16: #include Chris@16: #include Chris@16: #include Chris@16: #include Chris@16: #include Chris@16: Chris@16: namespace boost { namespace iostreams { Chris@16: Chris@16: namespace detail { Chris@16: Chris@16: template Chris@16: void skip(Device& dev, stream_offset off, mpl::true_) Chris@16: { iostreams::seek(dev, off, BOOST_IOS::cur); } Chris@16: Chris@16: template Chris@16: void skip(Device& dev, stream_offset off, mpl::false_) Chris@16: { // gcc 2.95 needs namespace qualification for char_traits. Chris@16: typedef typename char_type_of::type char_type; Chris@16: typedef iostreams::char_traits traits_type; Chris@16: for (stream_offset z = 0; z < off; ) { Chris@16: typename traits_type::int_type c; Chris@16: if (traits_type::is_eof(c = iostreams::get(dev))) Chris@16: boost::throw_exception(BOOST_IOSTREAMS_FAILURE("bad skip offset")); Chris@16: if (!traits_type::would_block(c)) Chris@16: ++z; Chris@16: } Chris@16: } Chris@16: Chris@16: template Chris@16: void skip( Filter& flt, Device& dev, stream_offset off, Chris@16: BOOST_IOS::openmode which, mpl::true_ ) Chris@16: { boost::iostreams::seek(flt, dev, off, BOOST_IOS::cur, which); } Chris@16: Chris@16: template Chris@16: void skip( Filter& flt, Device& dev, stream_offset off, Chris@16: BOOST_IOS::openmode, mpl::false_ ) Chris@16: { Chris@16: typedef typename char_type_of::type char_type; Chris@16: char_type c; Chris@16: for (stream_offset z = 0; z < off; ) { Chris@16: std::streamsize amt; Chris@16: if ((amt = iostreams::read(flt, dev, &c, 1)) == -1) Chris@16: boost::throw_exception(BOOST_IOSTREAMS_FAILURE("bad skip offset")); Chris@16: if (amt == 1) Chris@16: ++z; Chris@16: } Chris@16: } Chris@16: Chris@16: } // End namespace detail. Chris@16: Chris@16: template Chris@16: void skip(Device& dev, stream_offset off) Chris@16: { Chris@16: typedef typename mode_of::type mode; Chris@16: typedef mpl::or_< Chris@16: is_convertible, Chris@16: is_convertible Chris@16: > can_seek; Chris@16: BOOST_STATIC_ASSERT( Chris@16: (can_seek::value || is_convertible::value) Chris@16: ); Chris@16: detail::skip(dev, off, can_seek()); Chris@16: } Chris@16: Chris@16: template Chris@16: void skip( Filter& flt, Device& dev, stream_offset off, Chris@16: BOOST_IOS::openmode which = BOOST_IOS::in | BOOST_IOS::out ) Chris@16: { Chris@16: typedef typename mode_of::type filter_mode; Chris@16: typedef typename mode_of::type device_mode; Chris@16: typedef mpl::or_< Chris@16: mpl::and_< Chris@16: is_convertible, Chris@16: is_convertible Chris@16: >, Chris@16: mpl::and_< Chris@16: is_convertible, Chris@16: is_convertible Chris@16: > Chris@16: > can_seek; Chris@16: BOOST_STATIC_ASSERT( Chris@16: ( can_seek::value || Chris@16: (is_convertible::value && Chris@16: is_convertible::value) ) Chris@16: ); Chris@16: detail::skip(flt, dev, off, which, can_seek()); Chris@16: } Chris@16: Chris@16: } } // End namespaces iostreams, boost. Chris@16: Chris@16: #endif // #ifndef BOOST_IOSTREAMS_SKIP_HPP_INCLUDED //------------------------//