Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
wine-mirror
GitHub Repository: wine-mirror/wine
Path: blob/master/libs/c++/src/strstream.cpp
12346 views
1
//===------------------------ strstream.cpp -------------------------------===//
2
//
3
// The LLVM Compiler Infrastructure
4
//
5
// This file is dual licensed under the MIT and the University of Illinois Open
6
// Source Licenses. See LICENSE.TXT for details.
7
//
8
//===----------------------------------------------------------------------===//
9
10
#include "strstream"
11
#include "algorithm"
12
#include "climits"
13
#include "cstring"
14
#include "cstdlib"
15
#include "__debug"
16
#include "__undef_macros"
17
18
_LIBCPP_BEGIN_NAMESPACE_STD
19
20
strstreambuf::strstreambuf(streamsize __alsize)
21
: __strmode_(__dynamic),
22
__alsize_(__alsize),
23
__palloc_(nullptr),
24
__pfree_(nullptr)
25
{
26
}
27
28
strstreambuf::strstreambuf(void* (*__palloc)(size_t), void (*__pfree)(void*))
29
: __strmode_(__dynamic),
30
__alsize_(__default_alsize),
31
__palloc_(__palloc),
32
__pfree_(__pfree)
33
{
34
}
35
36
void
37
strstreambuf::__init(char* __gnext, streamsize __n, char* __pbeg)
38
{
39
if (__n == 0)
40
__n = static_cast<streamsize>(strlen(__gnext));
41
else if (__n < 0)
42
__n = INT_MAX;
43
if (__pbeg == nullptr)
44
setg(__gnext, __gnext, __gnext + __n);
45
else
46
{
47
setg(__gnext, __gnext, __pbeg);
48
setp(__pbeg, __pbeg + __n);
49
}
50
}
51
52
strstreambuf::strstreambuf(char* __gnext, streamsize __n, char* __pbeg)
53
: __strmode_(),
54
__alsize_(__default_alsize),
55
__palloc_(nullptr),
56
__pfree_(nullptr)
57
{
58
__init(__gnext, __n, __pbeg);
59
}
60
61
strstreambuf::strstreambuf(const char* __gnext, streamsize __n)
62
: __strmode_(__constant),
63
__alsize_(__default_alsize),
64
__palloc_(nullptr),
65
__pfree_(nullptr)
66
{
67
__init(const_cast<char *>(__gnext), __n, nullptr);
68
}
69
70
strstreambuf::strstreambuf(signed char* __gnext, streamsize __n, signed char* __pbeg)
71
: __strmode_(),
72
__alsize_(__default_alsize),
73
__palloc_(nullptr),
74
__pfree_(nullptr)
75
{
76
__init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, reinterpret_cast<char*>(__pbeg));
77
}
78
79
strstreambuf::strstreambuf(const signed char* __gnext, streamsize __n)
80
: __strmode_(__constant),
81
__alsize_(__default_alsize),
82
__palloc_(nullptr),
83
__pfree_(nullptr)
84
{
85
__init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, nullptr);
86
}
87
88
strstreambuf::strstreambuf(unsigned char* __gnext, streamsize __n, unsigned char* __pbeg)
89
: __strmode_(),
90
__alsize_(__default_alsize),
91
__palloc_(nullptr),
92
__pfree_(nullptr)
93
{
94
__init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, reinterpret_cast<char*>(__pbeg));
95
}
96
97
strstreambuf::strstreambuf(const unsigned char* __gnext, streamsize __n)
98
: __strmode_(__constant),
99
__alsize_(__default_alsize),
100
__palloc_(nullptr),
101
__pfree_(nullptr)
102
{
103
__init(const_cast<char *>(reinterpret_cast<const char*>(__gnext)), __n, nullptr);
104
}
105
106
strstreambuf::~strstreambuf()
107
{
108
if (eback() && (__strmode_ & __allocated) != 0 && (__strmode_ & __frozen) == 0)
109
{
110
if (__pfree_)
111
__pfree_(eback());
112
else
113
delete [] eback();
114
}
115
}
116
117
void
118
strstreambuf::swap(strstreambuf& __rhs)
119
{
120
streambuf::swap(__rhs);
121
_VSTD::swap(__strmode_, __rhs.__strmode_);
122
_VSTD::swap(__alsize_, __rhs.__alsize_);
123
_VSTD::swap(__palloc_, __rhs.__palloc_);
124
_VSTD::swap(__pfree_, __rhs.__pfree_);
125
}
126
127
void
128
strstreambuf::freeze(bool __freezefl)
129
{
130
if (__strmode_ & __dynamic)
131
{
132
if (__freezefl)
133
__strmode_ |= __frozen;
134
else
135
__strmode_ &= ~__frozen;
136
}
137
}
138
139
char*
140
strstreambuf::str()
141
{
142
if (__strmode_ & __dynamic)
143
__strmode_ |= __frozen;
144
return eback();
145
}
146
147
int
148
strstreambuf::pcount() const
149
{
150
return static_cast<int>(pptr() - pbase());
151
}
152
153
strstreambuf::int_type
154
strstreambuf::overflow(int_type __c)
155
{
156
if (__c == EOF)
157
return int_type(0);
158
if (pptr() == epptr())
159
{
160
if ((__strmode_ & __dynamic) == 0 || (__strmode_ & __frozen) != 0)
161
return int_type(EOF);
162
size_t old_size = static_cast<size_t> ((epptr() ? epptr() : egptr()) - eback());
163
size_t new_size = max<size_t>(static_cast<size_t>(__alsize_), 2*old_size);
164
if (new_size == 0)
165
new_size = __default_alsize;
166
char* buf = nullptr;
167
if (__palloc_)
168
buf = static_cast<char*>(__palloc_(new_size));
169
else
170
buf = new char[new_size];
171
if (buf == nullptr)
172
return int_type(EOF);
173
if (old_size != 0) {
174
_LIBCPP_ASSERT(eback(), "overflow copying from NULL");
175
memcpy(buf, eback(), static_cast<size_t>(old_size));
176
}
177
ptrdiff_t ninp = gptr() - eback();
178
ptrdiff_t einp = egptr() - eback();
179
ptrdiff_t nout = pptr() - pbase();
180
if (__strmode_ & __allocated)
181
{
182
if (__pfree_)
183
__pfree_(eback());
184
else
185
delete [] eback();
186
}
187
setg(buf, buf + ninp, buf + einp);
188
setp(buf + einp, buf + new_size);
189
__pbump(nout);
190
__strmode_ |= __allocated;
191
}
192
*pptr() = static_cast<char>(__c);
193
pbump(1);
194
return int_type(static_cast<unsigned char>(__c));
195
}
196
197
strstreambuf::int_type
198
strstreambuf::pbackfail(int_type __c)
199
{
200
if (eback() == gptr())
201
return EOF;
202
if (__c == EOF)
203
{
204
gbump(-1);
205
return int_type(0);
206
}
207
if (__strmode_ & __constant)
208
{
209
if (gptr()[-1] == static_cast<char>(__c))
210
{
211
gbump(-1);
212
return __c;
213
}
214
return EOF;
215
}
216
gbump(-1);
217
*gptr() = static_cast<char>(__c);
218
return __c;
219
}
220
221
strstreambuf::int_type
222
strstreambuf::underflow()
223
{
224
if (gptr() == egptr())
225
{
226
if (egptr() >= pptr())
227
return EOF;
228
setg(eback(), gptr(), pptr());
229
}
230
return int_type(static_cast<unsigned char>(*gptr()));
231
}
232
233
strstreambuf::pos_type
234
strstreambuf::seekoff(off_type __off, ios_base::seekdir __way, ios_base::openmode __which)
235
{
236
off_type __p(-1);
237
bool pos_in = (__which & ios::in) != 0;
238
bool pos_out = (__which & ios::out) != 0;
239
bool legal = false;
240
switch (__way)
241
{
242
case ios::beg:
243
case ios::end:
244
if (pos_in || pos_out)
245
legal = true;
246
break;
247
case ios::cur:
248
if (pos_in != pos_out)
249
legal = true;
250
break;
251
}
252
if (pos_in && gptr() == nullptr)
253
legal = false;
254
if (pos_out && pptr() == nullptr)
255
legal = false;
256
if (legal)
257
{
258
off_type newoff;
259
char* seekhigh = epptr() ? epptr() : egptr();
260
switch (__way)
261
{
262
case ios::beg:
263
newoff = 0;
264
break;
265
case ios::cur:
266
newoff = (pos_in ? gptr() : pptr()) - eback();
267
break;
268
case ios::end:
269
newoff = seekhigh - eback();
270
break;
271
default:
272
_LIBCPP_UNREACHABLE();
273
}
274
newoff += __off;
275
if (0 <= newoff && newoff <= seekhigh - eback())
276
{
277
char* newpos = eback() + newoff;
278
if (pos_in)
279
setg(eback(), newpos, _VSTD::max(newpos, egptr()));
280
if (pos_out)
281
{
282
// min(pbase, newpos), newpos, epptr()
283
__off = epptr() - newpos;
284
setp(min(pbase(), newpos), epptr());
285
__pbump((epptr() - pbase()) - __off);
286
}
287
__p = newoff;
288
}
289
}
290
return pos_type(__p);
291
}
292
293
strstreambuf::pos_type
294
strstreambuf::seekpos(pos_type __sp, ios_base::openmode __which)
295
{
296
off_type __p(-1);
297
bool pos_in = (__which & ios::in) != 0;
298
bool pos_out = (__which & ios::out) != 0;
299
if (pos_in || pos_out)
300
{
301
if (!((pos_in && gptr() == nullptr) || (pos_out && pptr() == nullptr)))
302
{
303
off_type newoff = __sp;
304
char* seekhigh = epptr() ? epptr() : egptr();
305
if (0 <= newoff && newoff <= seekhigh - eback())
306
{
307
char* newpos = eback() + newoff;
308
if (pos_in)
309
setg(eback(), newpos, _VSTD::max(newpos, egptr()));
310
if (pos_out)
311
{
312
// min(pbase, newpos), newpos, epptr()
313
off_type temp = epptr() - newpos;
314
setp(min(pbase(), newpos), epptr());
315
__pbump((epptr() - pbase()) - temp);
316
}
317
__p = newoff;
318
}
319
}
320
}
321
return pos_type(__p);
322
}
323
324
istrstream::~istrstream()
325
{
326
}
327
328
ostrstream::~ostrstream()
329
{
330
}
331
332
strstream::~strstream()
333
{
334
}
335
336
_LIBCPP_END_NAMESPACE_STD
337
338