Ugly, not-to-be-pushed sucking in of all of Boost to get windows to work.
[dyninst.git] / external / boost / iostreams / detail / vc6 / read.hpp
1 // (C) Copyright Jonathan Turkanis 2005.
2 // Distributed under the Boost Software License, Version 1.0. (See accompanying
3 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt.)
4
5 // See http://www.boost.org/libs/iostreams for documentation.
6
7 namespace boost { namespace iostreams {
8
9 namespace detail {
10
11 template<typename T> 
12 struct read_device_impl;
13
14 template<typename T> 
15 struct read_filter_impl;
16
17 } // End namespace detail.
18
19 template<typename T>
20 typename int_type_of<T>::type get(T& t)
21 {
22     typedef typename detail::unwrapped_type<T>::type unwrapped;
23     return detail::read_device_impl<T>::inner<unwrapped>::get(detail::unwrap(t));
24 }
25
26 template<typename T>
27 inline std::streamsize
28 read(T& t, typename char_type_of<T>::type* s, std::streamsize n)
29 {
30     typedef typename detail::unwrapped_type<T>::type unwrapped;
31     return detail::read_device_impl<T>::inner<unwrapped>::read(detail::unwrap(t), s, n);
32 }
33
34 template<typename T, typename Source>
35 std::streamsize
36 read(T& t, Source& src, typename char_type_of<T>::type* s, std::streamsize n)
37 {
38     typedef typename detail::unwrapped_type<T>::type unwrapped;
39     return detail::read_filter_impl<T>::inner<unwrapped>::read(detail::unwrap(t), src, s, n);
40 }
41
42 template<typename T>
43 bool putback(T& t, typename char_type_of<T>::type c)
44 {
45     typedef typename detail::unwrapped_type<T>::type unwrapped;
46     return detail::read_device_impl<T>::inner<unwrapped>::putback(detail::unwrap(t), c);
47 }
48
49 //----------------------------------------------------------------------------//
50
51 namespace detail {
52
53 // Helper function for adding -1 as EOF indicator.
54 inline std::streamsize check_eof(std::streamsize n) { return n != 0 ? n : -1; }
55
56 // Helper templates for reading from streambufs.
57 template<bool IsLinked>
58 struct true_eof_impl;
59
60 template<>
61 struct true_eof_impl<true> {
62     template<typename T>
63     static bool true_eof(T& t) { return t.true_eof(); }
64 };
65
66 template<>
67 struct true_eof_impl<false> {
68     template<typename T>
69     static bool true_eof(T& t) { return true; }
70 };
71
72 template<typename T>
73 inline bool true_eof(T& t)
74 {
75     const bool linked = is_linked<T>::value;
76     return true_eof_impl<linked>::true_eof(t);
77 }
78                     
79 //------------------Definition of read_device_impl----------------------------//
80
81 template<typename T>
82 struct read_device_impl
83     : mpl::if_<
84           detail::is_custom<T>,
85           operations<T>,
86           read_device_impl<
87               BOOST_DEDUCED_TYPENAME
88               detail::dispatch<
89                   T, istream_tag, streambuf_tag, input
90               >::type
91           >
92       >::type
93     { };
94
95 template<>
96 struct read_device_impl<istream_tag> {
97     template<typename T>
98     struct inner {
99         static typename int_type_of<T>::type get(T& t)
100         { return t.get(); }
101
102         static std::streamsize
103         read(T& t, typename char_type_of<T>::type* s, std::streamsize n)
104         { return check_eof(t.rdbuf()->sgetn(s, n)); }
105
106         static bool putback(T& t, typename char_type_of<T>::type c)
107         {
108             typedef typename char_type_of<T>::type          char_type;
109             typedef BOOST_IOSTREAMS_CHAR_TRAITS(char_type)  traits_type;
110             return !traits_type::eq_int_type( t.rdbuf()->sputbackc(c),
111                                               traits_type::eof() );
112         }
113     };
114 };
115
116 template<>
117 struct read_device_impl<streambuf_tag> {
118     template<typename T>
119     struct inner {
120         static typename int_type_of<T>::type
121         get(T& t)
122         {
123             typedef typename char_type_of<T>::type  char_type;
124             typedef char_traits<char_type>          traits_type;
125             typename int_type_of<T>::type c;
126             return !traits_type::is_eof(c = t.sbumpc()) ||
127                     detail::true_eof(t)
128                         ?
129                     c : traits_type::would_block();
130         }
131
132         static std::streamsize
133         read(T& t, typename char_type_of<T>::type* s, std::streamsize n)
134         {
135             std::streamsize amt;
136             return (amt = t.sgetn(s, n)) != 0 ?
137                 amt :
138                 detail::true_eof(t) ?
139                     -1 :
140                     0;
141         }
142
143         static bool putback(T& t, typename char_type_of<T>::type c)
144         {
145             typedef typename char_type_of<T>::type  char_type;
146             typedef char_traits<char_type>          traits_type;
147             return !traits_type::is_eof(t.sputbackc(c));
148         }
149     };
150 };
151
152 template<>
153 struct read_device_impl<input> {
154     template<typename T>
155     struct inner {
156         static typename int_type_of<T>::type
157         get(T& t)
158         {
159             typedef typename char_type_of<T>::type  char_type;
160             typedef char_traits<char_type>          traits_type;
161             char_type c;
162             std::streamsize amt;
163             return (amt = t.read(&c, 1)) == 1 ?
164                 traits_type::to_int_type(c) :
165                 amt == -1 ?
166                     traits_type::eof() :
167                     traits_type::would_block();
168         }
169
170         template<typename T>
171         static std::streamsize
172         read(T& t, typename char_type_of<T>::type* s, std::streamsize n)
173         { return t.read(s, n); }
174
175         template<typename T>
176         static bool putback(T& t, typename char_type_of<T>::type c)
177         {   // T must be Peekable.
178             return t.putback(c);
179         }
180     };
181 };
182
183 //------------------Definition of read_filter_impl----------------------------//
184
185 template<typename T>
186 struct read_filter_impl
187     : mpl::if_<
188           detail::is_custom<T>,
189           operations<T>,
190           read_filter_impl<
191               BOOST_DEDUCED_TYPENAME
192               detail::dispatch<
193                   T, multichar_tag, any_tag
194               >::type
195           >
196       >::type
197     { };
198
199 template<>
200 struct read_filter_impl<multichar_tag> {
201     template<typename T>
202     struct inner {
203         template<typename Source>
204         static std::streamsize read
205             ( T& t, Source& src, typename char_type_of<T>::type* s,   
206               std::streamsize n )
207         { return t.read(src, s, n); }
208     };
209 };
210
211 template<>
212 struct read_filter_impl<any_tag> {
213     template<typename T>
214     struct inner {
215         template<typename Source>
216         static std::streamsize read
217             ( T& t, Source& src, typename char_type_of<T>::type* s, 
218               std::streamsize n )
219         {
220             typedef typename char_type_of<T>::type  char_type;
221             typedef char_traits<char_type>          traits_type;
222             for (std::streamsize off = 0; off < n; ++off) {
223                 typename traits_type::int_type c = t.get(src);
224                 if (traits_type::is_eof(c))
225                     return check_eof(off);
226                 if (traits_type::would_block(c))
227                     return off;
228                 s[off] = traits_type::to_char_type(c);
229             }
230             return n;
231         }
232     };
233 };
234
235 } // End namespace detail.
236
237 } } // End namespaces iostreams, boost.