Build system improvements
[ustl.git] / mistream.cc
blob5741c34deaa688bc1e2d0890184deb5c91b625c5
1 // This file is part of the ustl library, an STL implementation.
2 //
3 // Copyright (C) 2005 by Mike Sharov <msharov@users.sourceforge.net>
4 // This file is free software, distributed under the MIT License.
5 //
6 // mstream.cpp
7 //
8 // Helper classes to read and write packed binary streams.
9 //
11 #include "mistream.h"
12 #include "sostream.h"
13 #include "ustring.h"
14 #include "ualgo.h"
16 namespace ustl {
18 //--------------------------------------------------------------------
20 /// \brief Constructs a stream attached to nothing.
21 /// A stream attached to nothing is not usable. Call Link() functions
22 /// inherited from cmemlink to attach to some memory block.
23 ///
24 istream::istream (void)
25 : cmemlink (),
26 m_Pos (0)
30 /// Attaches the stream to a block at \p p of size \p n.
31 istream::istream (const void* p, size_type n)
32 : cmemlink (p, n),
33 m_Pos (0)
37 /// Attaches to the block pointed to by \p source.
38 istream::istream (const cmemlink& source)
39 : cmemlink (source),
40 m_Pos (0)
44 /// Attaches to the block pointed to by source of size source.pos()
45 istream::istream (const ostream& source)
46 : cmemlink (source.begin(), source.pos()),
47 m_Pos (0)
51 /// Swaps contents with \p is
52 void istream::swap (istream& is)
54 cmemlink::swap (is);
55 ::ustl::swap (m_Pos, is.m_Pos);
58 /// Checks that \p n bytes are available in the stream, or else throws.
59 void istream::verify_remaining (const char* op, const char* type, size_t n) const
61 if (remaining() < n)
62 throw stream_bounds_exception (op, type, pos(), n, remaining());
65 /// Reads \p n bytes into \p buffer.
66 void istream::read (void* buffer, size_type n)
68 #ifdef WANT_STREAM_BOUNDS_CHECKING
69 verify_remaining ("read", "binary data", n);
70 #else
71 assert (remaining() >= n && "Reading past end of buffer. Make sure you are reading the right format.");
72 #endif
73 copy_n (ipos(), n, reinterpret_cast<value_type*>(buffer));
74 m_Pos += n;
77 /// Reads a null-terminated string into \p str.
78 void istream::read_strz (string& str)
80 const_iterator zp = find (ipos(), end(), string::c_Terminator);
81 if (zp == end())
82 zp = ipos();
83 const size_type strl = distance (ipos(), zp);
84 str.resize (strl);
85 copy (ipos(), zp, str.begin());
86 m_Pos += strl + 1;
89 /// Reads at most \p n bytes into \p s.
90 istream::size_type istream::readsome (void* s, size_type n)
92 if (remaining() < n)
93 underflow (n);
94 const size_type ntr (min (n, remaining()));
95 read (s, ntr);
96 return (ntr);
99 /// Writes all unread bytes into \p os.
100 void istream::write (ostream& os) const
102 os.write (ipos(), remaining());
105 /// Writes the object to stream \p os.
106 void istream::text_write (ostringstream& os) const
108 os.write (ipos(), remaining());
111 /// Links to \p p of size \p n
112 void istream::unlink (void) throw()
114 cmemlink::unlink();
115 m_Pos = 0;
118 //--------------------------------------------------------------------
120 /// \brief Constructs a stream attached to nothing.
121 /// A stream attached to nothing is not usable. Call Link() functions
122 /// inherited from memlink to attach to some memory block.
124 ostream::ostream (void)
125 : memlink (),
126 m_Pos (0)
130 /// Attaches the stream to a block at \p p of size \p n.
131 ostream::ostream (void* p, size_type n)
132 : memlink (p, n),
133 m_Pos (0)
137 /// Attaches to the block pointed to by \p source.
138 ostream::ostream (const memlink& source)
139 : memlink (source),
140 m_Pos (0)
144 /// Links to \p p of size \p n
145 void ostream::unlink (void) throw()
147 memlink::unlink();
148 m_Pos = 0;
151 /// Checks that \p n bytes are available in the stream, or else throws.
152 void ostream::verify_remaining (const char* op, const char* type, size_t n) const
154 if (remaining() < n)
155 throw stream_bounds_exception (op, type, pos(), n, remaining());
158 /// Aligns the write pointer on \p grain. The skipped bytes are zeroed.
159 void ostream::align (size_type grain)
161 const size_t r = pos() % grain;
162 size_t nb = grain - r;
163 if (!r) nb = 0;
164 #ifdef WANT_STREAM_BOUNDS_CHECKING
165 verify_remaining ("align", "padding", nb);
166 #else
167 assert (remaining() >= nb && "Buffer overrun. Check your stream size calculations.");
168 #endif
169 fill_n (ipos(), nb, '\x0');
170 m_Pos += nb;
173 /// Writes \p n bytes from \p buffer.
174 void ostream::write (const void* buffer, size_type n)
176 #ifdef WANT_STREAM_BOUNDS_CHECKING
177 verify_remaining ("write", "binary data", n);
178 #else
179 assert (remaining() >= n && "Buffer overrun. Check your stream size calculations.");
180 #endif
181 copy_n (const_iterator(buffer), n, ipos());
182 m_Pos += n;
185 /// Writes \p str as a null-terminated string.
186 void ostream::write_strz (const char* str)
188 write (str, strlen(str));
189 iwrite (string::c_Terminator);
192 /// Writes all available data from \p is.
193 void ostream::read (istream& is)
195 is.write (*this);
196 is.seek (is.size());
199 /// Writes all written data to \p os.
200 void ostream::text_write (ostringstream& os) const
202 os.write (begin(), pos());
205 /// Inserts an empty area of \p size, at \p start.
206 void ostream::insert (iterator start, size_type s)
208 memlink::insert (start, s);
209 m_Pos += s;
212 /// Erases an area of \p size, at \p start.
213 void ostream::erase (iterator start, size_type s)
215 m_Pos -= s;
216 memlink::erase (start, s);
219 /// Swaps with \p os
220 void ostream::swap (ostream& os)
222 memlink::swap (os);
223 ::ustl::swap (m_Pos, os.m_Pos);
226 //--------------------------------------------------------------------
228 } // namespace ustl