]>
git.saurik.com Git - apt.git/blob - test/interactive-helper/teestream.h
1 #ifndef APT_HELPER_TEESTREAM_H
2 #define APT_HELPER_TEESTREAM_H
4 /* 'basic' implementation of a streambuf which passes the output
5 to two 'real' streambufs emulating '| tee' on the shell
7 The main use is streaming debug output to std::clog as well as
8 a logfile easily, so don't expect that to be a bulletproof
12 #include <apt-pkg/macros.h>
14 template <typename CharT
, typename Traits
= std::char_traits
<CharT
>
15 > class basic_teebuf
: public std::basic_streambuf
<CharT
, Traits
>
18 basic_teebuf(std::basic_streambuf
<CharT
, Traits
> * const sb1
,
19 std::basic_streambuf
<CharT
, Traits
> * const sb2
)
22 virtual std::streamsize
xsputn(const CharT
* s
, std::streamsize c
) APT_OVERRIDE
24 return s2
->sputn(s
, s1
->sputn(s
, c
));
26 // overflow is the fallback of sputc which is non-virtual
27 typedef typename
Traits::int_type int_type
;
28 virtual int_type
overflow(int_type ch
= Traits::eof()) APT_OVERRIDE
30 auto const eof
= Traits::eof();
31 if (Traits::eq_int_type(ch
, Traits::eof()) == true)
34 auto const r1
= s1
->sputc(Traits::to_char_type(ch
));
35 auto const r2
= s2
->sputc(Traits::to_char_type(ch
));
36 return Traits::eq_int_type(r1
, eof
) ? r1
: r2
;
38 virtual void imbue(const std::locale
& loc
) APT_OVERRIDE
43 virtual int sync() APT_OVERRIDE
45 auto const r1
= s1
->pubsync();
46 auto const r2
= s2
->pubsync();
47 return r1
== 0 ? r2
: r1
;
50 std::basic_streambuf
<CharT
, Traits
> * const s1
;
51 std::basic_streambuf
<CharT
, Traits
> * const s2
;
53 template <typename CharT
, typename Traits
= std::char_traits
<CharT
>
54 > class basic_teeostream
: public std::basic_ostream
<CharT
, Traits
>
57 basic_teeostream(std::basic_ostream
<CharT
, Traits
> &o1
, std::basic_ostream
<CharT
, Traits
> &o2
) :
58 std::basic_ostream
<CharT
, Traits
>(&tbuf
), tbuf(o1
.rdbuf(), o2
.rdbuf()) {}
60 basic_teebuf
<CharT
, Traits
> tbuf
;