VirtualBox

source: vbox/trunk/include/iprt/nocrt/ostream@ 96354

最後變更 在這個檔案從96354是 96354,由 vboxsync 提交於 3 年 前

IPRT/nocrt: Defined cout and cerr; implemented ostream::flush and fixed a compile issue. bugref:10261

  • 屬性 svn:eol-style 設為 native
  • 屬性 svn:keywords 設為 Author Date Id Revision
檔案大小: 9.5 KB
 
1/** @file
2 * IPRT / No-CRT - Minimal C++ ostream header.
3 */
4
5/*
6 * Copyright (C) 2022 Oracle Corporation
7 *
8 * This file is part of VirtualBox Open Source Edition (OSE), as
9 * available from http://www.alldomusa.eu.org. This file is free software;
10 * you can redistribute it and/or modify it under the terms of the GNU
11 * General Public License (GPL) as published by the Free Software
12 * Foundation, in version 2 as it comes in the "COPYING" file of the
13 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
14 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
15 *
16 * The contents of this file may alternatively be used under the terms
17 * of the Common Development and Distribution License Version 1.0
18 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
19 * VirtualBox OSE distribution, in which case the provisions of the
20 * CDDL are applicable instead of those of the GPL.
21 *
22 * You may elect to license modified versions of this file under the
23 * terms and conditions of either the GPL or the CDDL or both.
24 */
25
26#ifndef IPRT_INCLUDED_nocrt_ostream
27#define IPRT_INCLUDED_nocrt_ostream
28#ifndef RT_WITHOUT_PRAGMA_ONCE
29# pragma once
30#endif
31
32/* Currently all in the ios header. */
33#include <iprt/nocrt/ios>
34
35namespace std
36{
37 /**
38 * Basic output stream.
39 */
40 template<typename a_CharType, typename a_CharTraits /*= std::char_traits<a_CharType>*/ >
41 class basic_ostream : public basic_ios<a_CharType, a_CharTraits>
42 {
43 protected:
44 /** Sentry class that performs pre and post output work. */
45 class sentry
46 {
47 private:
48 basic_ostream &m_rParent;
49
50 public:
51 explicit sentry(basic_ostream &a_rParent)
52 : m_rParent(a_rParent)
53 {
54 if (a_rParent.good())
55 {
56 basic_ostream *pTiedStream = a_rParent.tie();
57 if (!pTiedStream)
58 { /* likely? */ }
59 else
60 {
61 pTiedStream->flush();
62 if (!pTiedStream->good())
63 a_rParent.setstate(failbit);
64 }
65 }
66 }
67
68 explicit operator bool() const
69 {
70 return m_rParent.good();
71 }
72
73 ~sentry()
74 {
75 if ( (m_rParent.flags() & std::ios_base::unitbuf)
76 && m_rParent.good())
77 m_rParent.rdbuf()->pubsync();
78 }
79 };
80
81 public:
82 explicit basic_ostream(std::basic_streambuf<a_CharType,a_CharTraits> *a_pBuf)
83 : basic_ios(a_pBuf)
84 { }
85
86 /** For cerr initialization.
87 * @internal */
88 explicit basic_ostream(std::basic_streambuf<a_CharType,a_CharTraits> *a_pBuf,
89 std::basic_ostream<a_CharType, a_CharTraits> *a_pTiedStream,
90 bool a_fUnbuffered)
91 : basic_ios(a_pBuf)
92 {
93 m_pTiedStream = a_pTiedStream;
94 if (!a_fUnbuffered)
95 setf(std::ios_base::unitbuf);
96 }
97
98 private:
99 basic_ostream(basic_ostream const &a_rSrc); /* not copyable */
100 basic_ostream &operator=(basic_ostream const &a_rSrc); /* not copyable */
101
102 public:
103 virtual ~basic_ostream()
104 {
105 }
106
107 public:
108 basic_ostream &put(char_type a_ch)
109 {
110 sentry PrePost(*this);
111 if (PrePost)
112 {
113 if (m_pBuf->sputc(a_ch) == traits_type::eof())
114 m_fState |= badbit;
115 }
116 return *this;
117 }
118
119 basic_ostream &write(const char_type *a_pchSrc, std::streamsize a_cchToWrite)
120 {
121 sentry PrePost(*this);
122 if (PrePost)
123 {
124 std::streamsize cchWritten = m_pBuf->sputn(a_pchSrc, a_cchToWrite);
125 if (cchWritten != a_cchToWrite)
126 m_fState |= badbit;
127 }
128 return *this;
129 }
130
131 basic_ostream &flush()
132 {
133 if (m_pBuf)
134 m_pBuf->pubsync();
135 return *this;
136 }
137
138 pos_type tellp() RT_NOEXCEPT;
139 basic_ostream &seekp(pos_type a_off) RT_NOEXCEPT;
140 basic_ostream &seekp(off_type a_off, seekdir enmDir) RT_NOEXCEPT;
141
142 /** @name Internal support methods
143 * @{ */
144 inline basic_ostream &intWrite(const char *a_pchSrc, std::streamsize a_cchToWrite); /**< Internal method outputting char buffers. */
145
146 /** @returns 8, 10 or 16. */
147 inline unsigned intGetIntegerBase() const RT_NOEXCEPT
148 {
149 switch (m_fFlags & basefield)
150 {
151 default:
152 case dec: return 10;
153 case hex: return 16;
154 case oct: return 8;
155 }
156 }
157
158 /** @returns RTSTR_F_XXX . */
159 inline unsigned intGetIntegerFlags() const RT_NOEXCEPT
160 {
161 unsigned fFlags = 0;
162 if (m_fFlags & uppercase)
163 fFlags |= RTSTR_F_CAPITAL;
164 if (m_fFlags & showbase)
165 fFlags |= RTSTR_F_SPECIAL;
166 if (m_fFlags & showpos)
167 fFlags |= RTSTR_F_PLUS;
168 return fFlags;
169 }
170
171 basic_ostream &formatInteger(uint64_t a_uValue, uint32_t a_fFlags, unsigned a_uBase = 0)
172 {
173 a_fFlags |= intGetIntegerFlags();
174 char szTmp[72];
175 int cchTmp = RTStrFormatNumber(szTmp, a_uValue, !a_uBase ? intGetIntegerBase() : a_uBase, 0, 0, a_fFlags);
176
177 /** @todo apply cchWidth and padding. */
178
179 return intWrite(szTmp, cchTmp);
180 }
181
182 /** @} */
183 };
184
185 /** @name Character and string output.
186 * @{ */
187 /** @todo not sure if this really works... */
188 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
189 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, char a_ch)
190 {
191 return a_rDst.put(a_ch);
192 }
193
194 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
195 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, const char *a_psz)
196 {
197 return a_rDst.intWrite(a_psz, strlen(a_psz));
198 }
199 /** @} */
200
201 /** @name Integer formatting.
202 * @{ */
203 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
204 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, signed char a_iValue)
205 {
206 return a_rDst.formatInteger(a_iValue, RTSTR_F_8BIT | RTSTR_F_VALSIGNED);
207 }
208
209 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
210 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, unsigned char a_uValue)
211 {
212 return a_rDst.formatInteger(a_uValue, RTSTR_F_8BIT);
213 }
214
215 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
216 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, short a_iValue)
217 {
218 return a_rDst.formatInteger(a_iValue, RTSTR_F_16BIT | RTSTR_F_VALSIGNED);
219 }
220
221 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
222 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, unsigned short a_uValue)
223 {
224 return a_rDst.formatInteger(a_uValue, RTSTR_F_16BIT);
225 }
226
227 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
228 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, int a_iValue)
229 {
230 return a_rDst.formatInteger(a_iValue, RTSTR_F_32BIT | RTSTR_F_VALSIGNED);
231 }
232
233 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
234 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, unsigned int a_uValue)
235 {
236 return a_rDst.formatInteger(a_uValue, RTSTR_F_32BIT | RTSTR_F_VALSIGNED);
237 }
238
239 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
240 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, long a_iValue)
241 {
242 return a_rDst.formatInteger(a_iValue, (sizeof(a_iValue) > sizeof(int32_t) ? RTSTR_F_64BIT : RTSTR_F_32BIT));
243 }
244
245 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
246 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, unsigned long a_uValue)
247 {
248 return a_rDst.formatInteger(a_uValue,
249 RTSTR_F_VALSIGNED | (sizeof(a_uValue) > sizeof(uint32_t) ? RTSTR_F_64BIT : RTSTR_F_32BIT));
250 }
251
252 template<typename a_CharType, typename a_CharTraits = std::char_traits<a_CharType> >
253 basic_ostream<a_CharType, a_CharTraits> &operator<<(basic_ostream<a_CharType, a_CharTraits> &a_rDst, void const *a_pvValue)
254 {
255 return a_rDst.formatInteger((uintptr_t)a_pvValue,
256 (sizeof(a_pvValue) > sizeof(uint32_t) ? RTSTR_F_64BIT : RTSTR_F_32BIT), 16);
257 }
258 /** @} */
259
260 template<>
261 inline basic_ostream<char> &basic_ostream<char>::intWrite(const char *a_pchSrc, std::streamsize a_cchToWrite)
262 {
263 return write(a_pchSrc, a_cchToWrite);
264 }
265
266
267}
268
269#endif /* !IPRT_INCLUDED_nocrt_ostream */
270
注意: 瀏覽 TracBrowser 來幫助您使用儲存庫瀏覽器

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette