1 //  Boost io/ios_state.hpp header file  --------------------------------------//
2 //  Slightly simplified for Exult.
3 //  Copyright 2002, 2005 Daryle Walker.  Use, modification, and distribution
4 //  are subject to the Boost Software License, Version 1.0.  (See accompanying
5 //  file LICENSE_1_0.txt or a copy at <http://www.boost.org/LICENSE_1_0.txt>.)
6 
7 //  See <http://www.boost.org/libs/io/> for the library's home page.
8 
9 #ifndef BOOST_IO_IOS_STATE_HPP
10 #define BOOST_IO_IOS_STATE_HPP
11 
12 #include <ios>        // for std::ios_base, std::basic_ios, etc.
13 #ifndef BOOST_NO_STD_LOCALE
14 #include <locale>     // for std::locale
15 #endif
16 #include <ostream>    // for std::basic_ostream
17 #include <streambuf>  // for std::basic_streambuf
18 #include <string>     // for std::char_traits
19 
20 
21 namespace boost
22 {
23 namespace io
24 {
25 
26 
27 //  Basic stream state saver class declarations  -----------------------------//
28 
29 class ios_flags_saver
30 {
31 public:
32     using state_type = ::std::ios_base;
33     using aspect_type = ::std::ios_base::fmtflags;
34 
ios_flags_saver(state_type & s)35     explicit  ios_flags_saver( state_type &s )
36         : s_save_( s ), a_save_( s.flags() )
37         {}
ios_flags_saver(state_type & s,aspect_type const & a)38     ios_flags_saver( state_type &s, aspect_type const &a )
39         : s_save_( s ), a_save_( s.flags(a) )
40         {}
~ios_flags_saver()41     ~ios_flags_saver()
42         { this->restore(); }
43     ios_flags_saver& operator=(const ios_flags_saver&) = delete;
44 
restore()45     void  restore()
46         { s_save_.flags( a_save_ ); }
47 
48 private:
49     state_type &       s_save_;
50     aspect_type const  a_save_;
51 };
52 
53 class ios_precision_saver
54 {
55 public:
56     using state_type = ::std::ios_base;
57     using aspect_type = ::std::streamsize;
58 
ios_precision_saver(state_type & s)59     explicit  ios_precision_saver( state_type &s )
60         : s_save_( s ), a_save_( s.precision() )
61         {}
ios_precision_saver(state_type & s,aspect_type const & a)62     ios_precision_saver( state_type &s, aspect_type const &a )
63         : s_save_( s ), a_save_( s.precision(a) )
64         {}
~ios_precision_saver()65     ~ios_precision_saver()
66         { this->restore(); }
67     ios_precision_saver& operator=(const ios_precision_saver&) = delete;
68 
restore()69     void  restore()
70         { s_save_.precision( a_save_ ); }
71 
72 private:
73     state_type &       s_save_;
74     aspect_type const  a_save_;
75 
76 };
77 
78 class ios_width_saver
79 {
80 public:
81     using state_type = ::std::ios_base;
82     using aspect_type = ::std::streamsize;
83 
ios_width_saver(state_type & s)84     explicit  ios_width_saver( state_type &s )
85         : s_save_( s ), a_save_( s.width() )
86         {}
ios_width_saver(state_type & s,aspect_type const & a)87     ios_width_saver( state_type &s, aspect_type const &a )
88         : s_save_( s ), a_save_( s.width(a) )
89         {}
~ios_width_saver()90     ~ios_width_saver()
91         { this->restore(); }
92     ios_width_saver& operator=(const ios_width_saver&) = delete;
93 
restore()94     void  restore()
95         { s_save_.width( a_save_ ); }
96 
97 private:
98     state_type &       s_save_;
99     aspect_type const  a_save_;
100 };
101 
102 
103 //  Advanced stream state saver class template declarations  -----------------//
104 
105 template < typename Ch, class Tr >
106 class basic_ios_iostate_saver
107 {
108 public:
109     using state_type = ::std::basic_ios<Ch, Tr>;
110     using aspect_type = ::std::ios_base::iostate;
111 
basic_ios_iostate_saver(state_type & s)112     explicit  basic_ios_iostate_saver( state_type &s )
113         : s_save_( s ), a_save_( s.rdstate() )
114         {}
basic_ios_iostate_saver(state_type & s,aspect_type const & a)115     basic_ios_iostate_saver( state_type &s, aspect_type const &a )
116         : s_save_( s ), a_save_( s.rdstate() )
117         { s.clear(a); }
~basic_ios_iostate_saver()118     ~basic_ios_iostate_saver()
119         { this->restore(); }
120     basic_ios_iostate_saver& operator=(const basic_ios_iostate_saver&) = delete;
121 
restore()122     void  restore()
123         { s_save_.clear( a_save_ ); }
124 
125 private:
126     state_type &       s_save_;
127     aspect_type const  a_save_;
128 };
129 
130 template < typename Ch, class Tr >
131 class basic_ios_exception_saver
132 {
133 public:
134     using state_type = ::std::basic_ios<Ch, Tr>;
135     using aspect_type = ::std::ios_base::iostate;
136 
basic_ios_exception_saver(state_type & s)137     explicit  basic_ios_exception_saver( state_type &s )
138         : s_save_( s ), a_save_( s.exceptions() )
139         {}
basic_ios_exception_saver(state_type & s,aspect_type const & a)140     basic_ios_exception_saver( state_type &s, aspect_type const &a )
141         : s_save_( s ), a_save_( s.exceptions() )
142         { s.exceptions(a); }
~basic_ios_exception_saver()143     ~basic_ios_exception_saver()
144         { this->restore(); }
145     basic_ios_exception_saver& operator=(const basic_ios_exception_saver&) = delete;
146 
restore()147     void  restore()
148         { s_save_.exceptions( a_save_ ); }
149 
150 private:
151     state_type &       s_save_;
152     aspect_type const  a_save_;
153 };
154 
155 template < typename Ch, class Tr >
156 class basic_ios_tie_saver
157 {
158 public:
159     using state_type = ::std::basic_ios<Ch, Tr>;
160     using aspect_type = ::std::basic_ostream<Ch, Tr> *;
161 
basic_ios_tie_saver(state_type & s)162     explicit  basic_ios_tie_saver( state_type &s )
163         : s_save_( s ), a_save_( s.tie() )
164         {}
basic_ios_tie_saver(state_type & s,aspect_type const & a)165     basic_ios_tie_saver( state_type &s, aspect_type const &a )
166         : s_save_( s ), a_save_( s.tie(a) )
167         {}
~basic_ios_tie_saver()168     ~basic_ios_tie_saver()
169         { this->restore(); }
170     basic_ios_tie_saver& operator=(const basic_ios_tie_saver&) = delete;
171 
restore()172     void  restore()
173         { s_save_.tie( a_save_ ); }
174 
175 private:
176     state_type &       s_save_;
177     aspect_type const  a_save_;
178 };
179 
180 template < typename Ch, class Tr >
181 class basic_ios_rdbuf_saver
182 {
183 public:
184     using state_type = ::std::basic_ios<Ch, Tr>;
185     using aspect_type = ::std::basic_streambuf<Ch, Tr> *;
186 
basic_ios_rdbuf_saver(state_type & s)187     explicit  basic_ios_rdbuf_saver( state_type &s )
188         : s_save_( s ), a_save_( s.rdbuf() )
189         {}
basic_ios_rdbuf_saver(state_type & s,aspect_type const & a)190     basic_ios_rdbuf_saver( state_type &s, aspect_type const &a )
191         : s_save_( s ), a_save_( s.rdbuf(a) )
192         {}
~basic_ios_rdbuf_saver()193     ~basic_ios_rdbuf_saver()
194         { this->restore(); }
195     basic_ios_rdbuf_saver& operator=(const basic_ios_rdbuf_saver&) = delete;
196 
restore()197     void  restore()
198         { s_save_.rdbuf( a_save_ ); }
199 
200 private:
201     state_type &       s_save_;
202     aspect_type const  a_save_;
203 };
204 
205 template < typename Ch, class Tr >
206 class basic_ios_fill_saver
207 {
208 public:
209     using state_type = ::std::basic_ios<Ch, Tr>;
210     using aspect_type = typename state_type::char_type;
211 
basic_ios_fill_saver(state_type & s)212     explicit  basic_ios_fill_saver( state_type &s )
213         : s_save_( s ), a_save_( s.fill() )
214         {}
basic_ios_fill_saver(state_type & s,aspect_type const & a)215     basic_ios_fill_saver( state_type &s, aspect_type const &a )
216         : s_save_( s ), a_save_( s.fill(a) )
217         {}
~basic_ios_fill_saver()218     ~basic_ios_fill_saver()
219         { this->restore(); }
220     basic_ios_fill_saver& operator=(const basic_ios_fill_saver&) = delete;
221 
restore()222     void  restore()
223         { s_save_.fill( a_save_ ); }
224 
225 private:
226     state_type &       s_save_;
227     aspect_type const  a_save_;
228 };
229 
230 using ios_fill_saver = basic_ios_fill_saver<char, std::char_traits<char>>;
231 
232 #ifndef BOOST_NO_STD_LOCALE
233 template < typename Ch, class Tr >
234 class basic_ios_locale_saver
235 {
236 public:
237     using state_type = ::std::basic_ios<Ch, Tr>;
238     using aspect_type = ::std::locale;
239 
basic_ios_locale_saver(state_type & s)240     explicit basic_ios_locale_saver( state_type &s )
241         : s_save_( s ), a_save_( s.getloc() )
242         {}
basic_ios_locale_saver(state_type & s,aspect_type const & a)243     basic_ios_locale_saver( state_type &s, aspect_type const &a )
244         : s_save_( s ), a_save_( s.imbue(a) )
245         {}
~basic_ios_locale_saver()246     ~basic_ios_locale_saver()
247         { this->restore(); }
248     basic_ios_locale_saver& operator=(const basic_ios_locale_saver&) = delete;
249 
restore()250     void  restore()
251         { s_save_.imbue( a_save_ ); }
252 
253 private:
254     state_type &       s_save_;
255     aspect_type const  a_save_;
256 };
257 #endif
258 
259 
260 //  User-defined stream state saver class declarations  ----------------------//
261 
262 class ios_iword_saver
263 {
264 public:
265     using state_type = ::std::ios_base;
266     using index_type = int;
267     using aspect_type = long;
268 
ios_iword_saver(state_type & s,index_type i)269     explicit ios_iword_saver( state_type &s, index_type i )
270         : s_save_( s ), a_save_( s.iword(i) ), i_save_( i )
271         {}
ios_iword_saver(state_type & s,index_type i,aspect_type const & a)272     ios_iword_saver( state_type &s, index_type i, aspect_type const &a )
273         : s_save_( s ), a_save_( s.iword(i) ), i_save_( i )
274         { s.iword(i) = a; }
~ios_iword_saver()275     ~ios_iword_saver()
276         { this->restore(); }
277     ios_iword_saver& operator=(const ios_iword_saver&) = delete;
278 
restore()279     void  restore()
280         { s_save_.iword( i_save_ ) = a_save_; }
281 
282 private:
283     state_type &       s_save_;
284     aspect_type const  a_save_;
285     index_type const   i_save_;
286 };
287 
288 class ios_pword_saver
289 {
290 public:
291     using state_type = ::std::ios_base;
292     using index_type = int;
293     using aspect_type = void *;
294 
ios_pword_saver(state_type & s,index_type i)295     explicit  ios_pword_saver( state_type &s, index_type i )
296         : s_save_( s ), a_save_( s.pword(i) ), i_save_( i )
297         {}
ios_pword_saver(state_type & s,index_type i,aspect_type const & a)298     ios_pword_saver( state_type &s, index_type i, aspect_type const &a )
299         : s_save_( s ), a_save_( s.pword(i) ), i_save_( i )
300         { s.pword(i) = a; }
~ios_pword_saver()301     ~ios_pword_saver()
302         { this->restore(); }
303     ios_pword_saver operator=(const ios_pword_saver&) = delete;
304 
restore()305     void  restore()
306         { s_save_.pword( i_save_ ) = a_save_; }
307 
308 private:
309     state_type &       s_save_;
310     aspect_type const  a_save_;
311     index_type const   i_save_;
312 };
313 
314 
315 //  Combined stream state saver class (template) declarations  ---------------//
316 
317 class ios_base_all_saver
318 {
319 public:
320     using state_type = ::std::ios_base;
321 
ios_base_all_saver(state_type & s)322     explicit  ios_base_all_saver( state_type &s )
323         : s_save_( s ), a1_save_( s.flags() ), a2_save_( s.precision() )
324         , a3_save_( s.width() )
325         {}
326 
~ios_base_all_saver()327     ~ios_base_all_saver()
328         { this->restore(); }
329     ios_base_all_saver& operator=(const ios_base_all_saver&) = delete;
330 
restore()331     void  restore()
332     {
333         s_save_.width( a3_save_ );
334         s_save_.precision( a2_save_ );
335         s_save_.flags( a1_save_ );
336     }
337 
338 private:
339     state_type &                s_save_;
340     state_type::fmtflags const  a1_save_;
341     ::std::streamsize const     a2_save_;
342     ::std::streamsize const     a3_save_;
343 };
344 
345 template < typename Ch, class Tr >
346 class basic_ios_all_saver
347 {
348 public:
349     using state_type = ::std::basic_ios<Ch, Tr>;
350 
basic_ios_all_saver(state_type & s)351     explicit  basic_ios_all_saver( state_type &s )
352         : s_save_( s ), a1_save_( s.flags() ), a2_save_( s.precision() )
353         , a3_save_( s.width() ), a4_save_( s.rdstate() )
354         , a5_save_( s.exceptions() ), a6_save_( s.tie() )
355         , a7_save_( s.rdbuf() ), a8_save_( s.fill() )
356         #ifndef BOOST_NO_STD_LOCALE
357         , a9_save_( s.getloc() )
358         #endif
359         {}
360 
~basic_ios_all_saver()361     ~basic_ios_all_saver()
362         { this->restore(); }
363     basic_ios_all_saver& operator=(const basic_ios_all_saver&) = delete;
364 
restore()365     void  restore()
366     {
367         #ifndef BOOST_NO_STD_LOCALE
368         s_save_.imbue( a9_save_ );
369         #endif
370         s_save_.fill( a8_save_ );
371         s_save_.rdbuf( a7_save_ );
372         s_save_.tie( a6_save_ );
373         s_save_.exceptions( a5_save_ );
374         s_save_.clear( a4_save_ );
375         s_save_.width( a3_save_ );
376         s_save_.precision( a2_save_ );
377         s_save_.flags( a1_save_ );
378     }
379 
380 private:
381     state_type &                            s_save_;
382     typename state_type::fmtflags const     a1_save_;
383     ::std::streamsize const                 a2_save_;
384     ::std::streamsize const                 a3_save_;
385     typename state_type::iostate const      a4_save_;
386     typename state_type::iostate const      a5_save_;
387     ::std::basic_ostream<Ch, Tr> * const    a6_save_;
388     ::std::basic_streambuf<Ch, Tr> * const  a7_save_;
389     typename state_type::char_type const    a8_save_;
390     #ifndef BOOST_NO_STD_LOCALE
391     ::std::locale const                     a9_save_;
392     #endif
393 };
394 
395 class ios_all_word_saver
396 {
397 public:
398     using state_type = ::std::ios_base;
399     using index_type = int;
400 
ios_all_word_saver(state_type & s,index_type i)401     ios_all_word_saver( state_type &s, index_type i )
402         : s_save_( s ), i_save_( i ), a1_save_( s.iword(i) )
403         , a2_save_( s.pword(i) )
404         {}
405 
~ios_all_word_saver()406     ~ios_all_word_saver()
407         { this->restore(); }
408     ios_all_word_saver& operator=(const ios_all_word_saver&) = delete;
409 
restore()410     void  restore()
411     {
412         s_save_.pword( i_save_ ) = a2_save_;
413         s_save_.iword( i_save_ ) = a1_save_;
414     }
415 
416 private:
417     state_type &      s_save_;
418     index_type const  i_save_;
419     long const        a1_save_;
420     void * const      a2_save_;
421 };
422 
423 
424 }  // namespace io
425 }  // namespace boost
426 
427 
428 #endif  // BOOST_IO_IOS_STATE_HPP
429