ostream_insert.h revision 171828
1// Helpers for ostream inserters -*- C++ -*-
2
3// Copyright (C) 2007 Free Software Foundation, Inc.
4//
5// This file is part of the GNU ISO C++ Library.  This library is free
6// software; you can redistribute it and/or modify it under the
7// terms of the GNU General Public License as published by the
8// Free Software Foundation; either version 2, or (at your option)
9// any later version.
10
11// This library is distributed in the hope that it will be useful,
12// but WITHOUT ANY WARRANTY; without even the implied warranty of
13// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14// GNU General Public License for more details.
15
16// You should have received a copy of the GNU General Public License along
17// with this library; see the file COPYING.  If not, write to the Free
18// Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
19// USA.
20
21// As a special exception, you may use this file as part of a free software
22// library without restriction.  Specifically, if other files instantiate
23// templates or use macros or inline functions from this file, or you compile
24// this file and link it with other files to produce an executable, this
25// file does not by itself cause the resulting executable to be covered by
26// the GNU General Public License.  This exception does not however
27// invalidate any other reasons why the executable file might be covered by
28// the GNU General Public License.
29
30/** @file ostream_insert.h
31 *  This is an internal header file, included by other library headers.
32 *  You should not attempt to use it directly.
33 */
34
35#ifndef _OSTREAM_INSERT_H
36#define _OSTREAM_INSERT_H 1
37
38#pragma GCC system_header
39
40#include <iosfwd>
41
42_GLIBCXX_BEGIN_NAMESPACE(std)
43
44  template<typename _CharT, typename _Traits>
45    inline void
46    __ostream_write(basic_ostream<_CharT, _Traits>& __out,
47		    const _CharT* __s, streamsize __n)
48    {
49      typedef basic_ostream<_CharT, _Traits>       __ostream_type;
50      typedef typename __ostream_type::ios_base    __ios_base;
51
52      const streamsize __put = __out.rdbuf()->sputn(__s, __n);
53      if (__put != __n)
54	__out.setstate(__ios_base::badbit);
55    }
56
57  template<typename _CharT, typename _Traits>
58    inline void
59    __ostream_fill(basic_ostream<_CharT, _Traits>& __out, streamsize __n)
60    {
61      typedef basic_ostream<_CharT, _Traits>       __ostream_type;
62      typedef typename __ostream_type::ios_base    __ios_base;
63
64      const _CharT __c = __out.fill();
65      for (; __n > 0; --__n)
66	{
67	  const typename _Traits::int_type __put = __out.rdbuf()->sputc(__c);
68	  if (_Traits::eq_int_type(__put, _Traits::eof()))
69	    {
70	      __out.setstate(__ios_base::badbit);
71	      break;
72	    }
73	}
74    }
75
76  template<typename _CharT, typename _Traits>
77    basic_ostream<_CharT, _Traits>&
78    __ostream_insert(basic_ostream<_CharT, _Traits>& __out,
79		     const _CharT* __s, streamsize __n)
80    {
81      typedef basic_ostream<_CharT, _Traits>       __ostream_type;
82      typedef typename __ostream_type::ios_base    __ios_base;
83
84      typename __ostream_type::sentry __cerb(__out);
85      if (__cerb)
86	{
87	  try
88	    {
89	      const streamsize __w = __out.width();
90	      if (__w > __n)
91		{
92		  const bool __left = ((__out.flags()
93					& __ios_base::adjustfield)
94				       == __ios_base::left);
95		  if (!__left)
96		    __ostream_fill(__out, __w - __n);
97		  if (__out.good())
98		    __ostream_write(__out, __s, __n);
99		  if (__left && __out.good())
100		    __ostream_fill(__out, __w - __n);
101		}
102	      else
103		__ostream_write(__out, __s, __n);
104	      __out.width(0);
105	    }
106	  catch(...)
107	    { __out._M_setstate(__ios_base::badbit); }
108	}
109      return __out;
110    }
111
112  // Inhibit implicit instantiations for required instantiations,
113  // which are defined via explicit instantiations elsewhere.
114  // NB:  This syntax is a GNU extension.
115#if _GLIBCXX_EXTERN_TEMPLATE
116  extern template ostream& __ostream_insert(ostream&, const char*, streamsize);
117
118#ifdef _GLIBCXX_USE_WCHAR_T
119  extern template wostream& __ostream_insert(wostream&, const wchar_t*,
120					     streamsize);
121#endif
122#endif
123
124_GLIBCXX_END_NAMESPACE
125
126#endif /* _OSTREAM_INSERT_H */
127