1
/* Copyright (C) 2004-2008 Garrett A. Kajmowicz
3
This file is part of the uClibc++ Library.
5
This library is free software; you can redistribute it and/or
6
modify it under the terms of the GNU Lesser General Public
7
License as published by the Free Software Foundation; either
8
version 2.1 of the License, or (at your option) any later version.
10
This library is distributed in the hope that it will be useful,
11
but WITHOUT ANY WARRANTY; without even the implied warranty of
12
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
Lesser General Public License for more details.
15
You should have received a copy of the GNU Lesser General Public
16
License along with this library; if not, write to the Free Software
17
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20
#include <basic_definitions>
22
#ifndef STD_HEADER_OSTREAM
23
#define STD_HEADER_OSTREAM 1
28
#include <ostream_helpers>
30
#if defined( __AVR__ )
31
#include <avr/pgmspace.h>
32
class __FlashStringHelper;
35
#pragma GCC visibility push(default)
38
template <class charT, class traits > class basic_ostream;
39
typedef basic_ostream<char> ostream;
41
#ifdef __UCLIBCXX_HAS_WCHAR__
42
typedef basic_ostream<wchar_t> wostream;
45
template <class charT, class traits> basic_ostream<charT,traits>& endl(basic_ostream<charT,traits>& os);
46
template <class charT, class traits> basic_ostream<charT,traits>& ends(basic_ostream<charT,traits>& os);
47
template <class charT, class traits> basic_ostream<charT,traits>& flush(basic_ostream<charT,traits>& os);
49
template <class charT, class traits > class _UCXXEXPORT basic_ostream
50
: virtual public basic_ios<charT,traits>
54
typedef charT char_type;
55
typedef typename traits::int_type int_type;
56
typedef typename traits::pos_type pos_type;
57
typedef typename traits::off_type off_type;
58
typedef traits traits_type;
61
_UCXXEXPORT basic_ostream(basic_streambuf<charT,traits>* sb)
62
: basic_ios<charT, traits>(sb)
64
basic_ios<charT,traits>::init(sb);
66
virtual _UCXXEXPORT ~basic_ostream();
70
_UCXXEXPORT basic_ostream<charT,traits>& operator<<(basic_ostream<charT,traits>& (*pf)(basic_ostream<charT,traits>&)){
73
_UCXXEXPORT basic_ostream<charT,traits>& operator<<(basic_ios<charT,traits>& (*pf)(basic_ios<charT,traits>&)){
77
_UCXXEXPORT basic_ostream<charT,traits>& operator<<(ios_base& (*pf)(ios_base&)){
81
basic_ostream<charT,traits>& operator<<(bool n);
82
basic_ostream<charT,traits>& operator<<(short n);
83
basic_ostream<charT,traits>& operator<<(unsigned short n);
84
basic_ostream<charT,traits>& operator<<(int n);
85
basic_ostream<charT,traits>& operator<<(unsigned int n);
86
basic_ostream<charT,traits>& operator<<(long n);
87
basic_ostream<charT,traits>& operator<<(unsigned long n);
88
basic_ostream<charT,traits>& operator<<(float f);
89
basic_ostream<charT,traits>& operator<<(double f);
90
basic_ostream<charT,traits>& operator<<(long double f);
91
basic_ostream<charT,traits>& operator<<(void* p);
92
basic_ostream<charT,traits>& operator<<(basic_streambuf<char_type,traits>* sb);
93
#if defined( __AVR__ )
94
basic_ostream<charT,traits>& operator<<(const __FlashStringHelper* p);
97
_UCXXEXPORT basic_ostream<charT,traits>& put(char_type c){
98
if(basic_ostream<charT,traits>::traits_type::eq_int_type(
99
basic_ios<charT, traits>::mstreambuf->sputc(c),
100
basic_ostream<charT,traits>::traits_type::eof()))
102
basic_ios<charT,traits>::setstate(ios_base::eofbit);
106
_UCXXEXPORT basic_ostream<charT,traits>& write(const char_type* s, streamsize n){
107
if(basic_ostream<charT,traits>::traits_type::eq_int_type(
108
basic_ios<charT, traits>::mstreambuf->sputn(s, n),
109
basic_ostream<charT,traits>::traits_type::eof())
111
basic_ios<charT,traits>::setstate(ios_base::eofbit);
115
_UCXXEXPORT basic_ostream<charT,traits>& flush(){
116
if(basic_ios<charT, traits>::mstreambuf->pubsync() == -1){
117
basic_ios<charT,traits>::setstate(ios_base::badbit);
121
_UCXXEXPORT pos_type tellp(){
122
if(basic_ios<charT,traits>::fail() != false){
125
return basic_ios<charT,traits>::rdbuf()->pubseekoff(0, ios_base::cur, ios_base::out);
127
_UCXXEXPORT basic_ostream<charT,traits>& seekp(pos_type pos){
128
if( basic_ios<charT,traits>::fail() != true ){
129
basic_ios<charT,traits>::rdbuf()->pubseekpos(pos);
133
_UCXXEXPORT basic_ostream<charT,traits>& seekp(off_type off, ios_base::seekdir dir){
134
if( basic_ios<charT,traits>::fail() != true){
135
basic_ios<charT,traits>::rdbuf()->pubseekoff(off, dir);
140
_UCXXEXPORT void printout(const char_type* s, streamsize n){
141
streamsize extra = ios::width() - n;
142
if ((ios::flags()&ios::adjustfield) == ios::right){
149
if ((ios::flags()&ios::adjustfield) == ios::left) {
155
// Width value only applies for the next output operation. Reset to zero.
160
basic_ostream(const basic_ostream<charT,traits> &){ }
161
basic_ostream<charT,traits> & operator=(const basic_ostream<charT,traits> &){ return *this; }
164
//Implementations of template functions. To allow for partial specialization
166
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>::~basic_ostream(){ }
168
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(bool n){
170
if( basic_ios<charT,traits>::flags() & ios_base::boolalpha){
174
printout("false", 5);
183
if(basic_ios<charT,traits>::flags() & ios_base::unitbuf){
189
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
190
basic_ostream<charT, traits>::operator<<(unsigned short n){
192
__ostream_printout<traits, charT, unsigned long int>::printout(*this, n);
196
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(short n){
198
__ostream_printout<traits, charT, long int>::printout(*this, n);
202
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(int n){
204
__ostream_printout<traits, charT, long int>::printout(*this, n);
208
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(unsigned int n){
210
__ostream_printout<traits, charT, unsigned long int>::printout(*this, n);
214
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(long n){
216
__ostream_printout<traits, charT, long >::printout(*this, n);
220
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
221
basic_ostream<charT, traits>::operator<<(unsigned long n)
224
__ostream_printout<traits, charT, unsigned long >::printout(*this, n);
228
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(float f){
230
__ostream_printout<traits, charT, double >::printout(*this, f);
234
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(double f){
236
__ostream_printout<traits, charT, double >::printout(*this, f);
240
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(long double f){
242
__ostream_printout<traits, charT, long double >::printout(*this, f);
246
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(void* p){
249
printout(buffer, snprintf(buffer, 20, "%p", p) );
250
if(basic_ios<charT,traits>::flags() & ios_base::unitbuf){
255
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
256
basic_ostream<charT, traits>::operator<<(basic_streambuf<charT,traits>* sb)
260
basic_ios<charT,traits>::setstate(ios_base::badbit);
264
typename traits::int_type c;
266
while(basic_ios<charT,traits>::good() && (c = sb->sbumpc()) != traits::eof() ){
270
if(basic_ios<charT,traits>::flags() & ios_base::unitbuf){
275
#if defined( __AVR__ )
276
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& basic_ostream<charT, traits>::operator<<(const __FlashStringHelper* p ){
279
size_t p_len = strlcpy_P(buffer,reinterpret_cast<const char*>(p),sizeof(buffer));
280
printout(buffer, (p_len>=sizeof(buffer)) ? sizeof(buffer) - 1 : p_len );
281
if(basic_ios<charT,traits>::flags() & ios_base::unitbuf){
289
/*Template Specializations*/
291
#ifdef __UCLIBCXX_EXPAND_OSTREAM_CHAR__
292
#ifndef __UCLIBCXX_COMPILE_OSTREAM__
294
#ifdef __UCLIBCXX_EXPAND_CONSTRUCTORS_DESTRUCTORS__
296
template <> _UCXXEXPORT ostream::~basic_ostream();
298
#endif // __UCLIBCXX_EXPAND_CONSTRUCTORS_DESTRUCTORS__
300
template <> _UCXXEXPORT ostream & ostream::flush();
302
template <> _UCXXEXPORT ostream & ostream::operator<<(bool n);
303
template <> _UCXXEXPORT ostream & ostream::operator<<(short int n);
304
template <> _UCXXEXPORT ostream & ostream::operator<<(unsigned short int n);
305
template <> _UCXXEXPORT ostream & ostream::operator<<(int n);
306
template <> _UCXXEXPORT ostream & ostream::operator<<(unsigned int n);
307
template <> _UCXXEXPORT ostream & ostream::operator<<(long n);
308
template <> _UCXXEXPORT ostream & ostream::operator<<(unsigned long n);
309
template <> _UCXXEXPORT ostream & ostream::operator<<(float f);
310
template <> _UCXXEXPORT ostream & ostream::operator<<(double f);
311
template <> _UCXXEXPORT ostream & ostream::operator<<(long double f);
312
template <> _UCXXEXPORT ostream & ostream::operator<<(void* p);
313
template <> _UCXXEXPORT ostream & ostream::operator<<(basic_streambuf<char, char_traits<char> >* sb);
317
template <class charT,class traits = char_traits<charT> >
318
class _UCXXEXPORT basic_ostream<charT,traits>::sentry
322
explicit _UCXXEXPORT sentry(basic_ostream<charT,traits>& os): ok(true){
323
if(os.good() !=0){ //Prepare for output
326
//Flush any tied buffer
331
_UCXXEXPORT ~sentry() { }
332
_UCXXEXPORT operator bool() {
338
#ifdef __UCLIBCXX_EXPAND_OSTREAM_CHAR__
339
#ifndef __UCLIBCXX_COMPILE_OSTREAM__
340
#ifdef __UCLIBCXX_EXPAND_CONSTRUCTORS_DESTRUCTORS__
342
template <> _UCXXEXPORT ostream::sentry::sentry(ostream & os);
343
template <> _UCXXEXPORT ostream::sentry::~sentry();
345
#endif //__UCLIBCXX_EXPAND_CONSTRUCTORS_DESTRUCTORS__
350
//Non - class functions
353
template<class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
354
operator<<(basic_ostream<charT,traits>& out, charT c)
356
typename basic_ostream<charT,traits>::sentry s(out);
361
template<class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
362
operator<<(basic_ostream<charT,traits>& out, char c)
364
typename basic_ostream<charT,traits>::sentry s(out);
369
template<class traits> _UCXXEXPORT basic_ostream<char,traits>&
370
operator<<(basic_ostream<char,traits>& out, char c)
372
typename basic_ostream<char,traits>::sentry s(out);
377
// signed and unsigned
378
template<class traits> _UCXXEXPORT basic_ostream<char,traits>&
379
operator<<(basic_ostream<char,traits>& out, signed char c)
381
typename basic_ostream<char,traits>::sentry s(out);
386
template<class traits> _UCXXEXPORT basic_ostream<char,traits>&
387
operator<<(basic_ostream<char,traits>& out, unsigned char c)
389
typename basic_ostream<char,traits>::sentry s(out);
394
template<class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
395
operator<<(basic_ostream<charT,traits>& out, const charT* c)
397
typename basic_ostream<charT,traits>::sentry s(out);
398
out.printout(c, traits::length(c) );
402
template<class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
403
operator<<(basic_ostream<charT,traits>& out, const char* c)
405
typename basic_ostream<charT,traits>::sentry s(out);
406
out.printout(c, char_traits<char>::length(c) );
410
// partial specializations
411
template<class traits> _UCXXEXPORT basic_ostream<char,traits>&
412
operator<<(basic_ostream<char,traits>& out, const char* c)
414
typename basic_ostream<char,traits>::sentry s(out);
415
out.printout(c, traits::length(c));
419
#ifdef __UCLIBCXX_HAS_WCHAR__
420
template<class traits> _UCXXEXPORT basic_ostream<wchar_t,traits>&
421
operator<<(basic_ostream<wchar_t,traits>& out, const char* c)
423
typename basic_ostream<wchar_t, traits>::sentry s(out);
424
size_t numChars = char_traits<char>::length(c);
425
wchar_t * temp = new wchar_t[numChars];
427
for(size_t i=0; i < numChars; ++i){
428
temp[i] = out.widen(c[i]);
431
out.printout(temp, numChars);
436
// signed and unsigned
437
template<class traits> _UCXXEXPORT basic_ostream<char,traits>&
438
operator<<(basic_ostream<char,traits>& out, const signed char* c)
440
typename basic_ostream<char,traits>::sentry s(out);
441
out.printout(reinterpret_cast<const char *>(c), traits::length( reinterpret_cast<const char *>(c)));
445
template<class traits> _UCXXEXPORT basic_ostream<char,traits>&
446
operator<<(basic_ostream<char,traits>& out, const unsigned char* c)
448
typename basic_ostream<char,traits>::sentry s(out);
449
out.printout(reinterpret_cast<const char *>(c), traits::length( reinterpret_cast<const char *>(c)));
453
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
454
endl(basic_ostream<charT,traits>& os)
456
typename basic_ostream<charT,traits>::sentry s(os);
462
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>&
463
ends(basic_ostream<charT,traits>& os)
465
typename basic_ostream<charT,traits>::sentry s(os);
466
os.put(traits::eos());
470
template <class charT, class traits> _UCXXEXPORT basic_ostream<charT,traits>& flush(basic_ostream<charT,traits>& os){
471
typename basic_ostream<charT,traits>::sentry s(os);
477
#ifdef __UCLIBCXX_EXPAND_OSTREAM_CHAR__
478
#ifndef __UCLIBCXX_COMPILE_OSTREAM__
479
template <> _UCXXEXPORT ostream & endl(ostream & os);
480
template <> _UCXXEXPORT ostream & flush(ostream & os);
481
template <> _UCXXEXPORT ostream & operator<<(ostream & out, char c);
482
template <> _UCXXEXPORT ostream & operator<<(ostream & out, const char* c);
483
template <> _UCXXEXPORT ostream & operator<<(ostream & out, unsigned char c);
484
template <> _UCXXEXPORT ostream & operator<<(ostream & out, unsigned const char* c);
490
#ifndef __STRICT_ANSI__
492
//Support for output of long long data types
494
template<class Ch, class Tr> _UCXXEXPORT basic_ostream<Ch, Tr>&
495
operator<<(basic_ostream<Ch, Tr>& os, signed long long int i)
497
typename basic_ostream<Ch, Tr>::sentry s(os);
498
__ostream_printout<Tr, Ch, signed long long int>::printout(os, i);
503
template<class Ch, class Tr> _UCXXEXPORT basic_ostream<Ch, Tr>&
504
operator<<(basic_ostream<Ch, Tr>& os, unsigned long long int i)
506
typename basic_ostream<Ch, Tr>::sentry s(os);
507
__ostream_printout<Tr, Ch, unsigned long long int>::printout(os, i);
512
#endif //__STRICT_ANSI__
519
#pragma GCC visibility pop