sources/network/bytestream.cpp

branch
protocol5
changeset 195
be953e1621d9
parent 175
18f2d2de1929
parent 191
2e6cbacafdc7
equal deleted inserted replaced
176:060a13878ca0 195:be953e1621d9
1 /* 1 /*
2 Copyright 2014 - 2016 Teemu Piippo 2 Copyright 2014 - 2021 Teemu Piippo
3 All rights reserved. 3 All rights reserved.
4 4
5 Redistribution and use in source and binary forms, with or without 5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions 6 modification, are permitted provided that the following conditions
7 are met: 7 are met:
34 34
35 /*! 35 /*!
36 * \brief Constructs a byte cursor. The cursor is placed to the beginning of the stream. 36 * \brief Constructs a byte cursor. The cursor is placed to the beginning of the stream.
37 * \param data 37 * \param data
38 */ 38 */
39 Bytestream::Bytestream(ByteArray& data) : 39 Bytestream::Bytestream(std::vector<unsigned char>& data) :
40 m_data(data), 40 m_data(data),
41 m_position(0) {} 41 m_position(0) {}
42 42
43 /*! 43 /*!
44 * \brief Ensures that the specified amount of bytes can be read. Raises IOError if this is not the case. 44 * \brief Ensures that the specified amount of bytes can be read. Raises IOError if this is not the case.
47 void Bytestream::ensureReadSpace(int bytes) 47 void Bytestream::ensureReadSpace(int bytes)
48 { 48 {
49 if (bytesLeft() < bytes) 49 if (bytesLeft() < bytes)
50 { 50 {
51 int bytesPast = bytes - bytesLeft(); 51 int bytesPast = bytes - bytesLeft();
52 String message; 52 std::string message;
53 message.sprintf("attempted to read %d byte%s past the end of bytestream", bytesPast, plural(bytesPast)); 53 message = sprintf("attempted to read %d byte%s past the end of bytestream", bytesPast, plural(bytesPast));
54 throw IOError (message); 54 throw IOError (message);
55 } 55 }
56 } 56 }
57 57
58 /*! 58 /*!
64 } 64 }
65 65
66 /*! 66 /*!
67 * \returns an iterator to the current data position. 67 * \returns an iterator to the current data position.
68 */ 68 */
69 ByteArray::Iterator Bytestream::getCurrentIterator() 69 std::vector<unsigned char>::iterator Bytestream::getCurrentIterator()
70 { 70 {
71 return m_data.begin() + m_position; 71 return m_data.begin() + m_position;
72 } 72 }
73 73
74 /*! 74 /*!
88 int16_t Bytestream::readShort() 88 int16_t Bytestream::readShort()
89 { 89 {
90 ensureReadSpace (2); 90 ensureReadSpace (2);
91 int16_t result = 0; 91 int16_t result = 0;
92 92
93 for (int i : range(2)) 93 for (int i : {0, 1})
94 result |= read() << (i * 8); 94 result |= read() << (i * 8);
95 95
96 return result; 96 return result;
97 } 97 }
98 98
102 */ 102 */
103 int32_t Bytestream::readLong() 103 int32_t Bytestream::readLong()
104 { 104 {
105 ensureReadSpace (4); 105 ensureReadSpace (4);
106 int32_t result = 0; 106 int32_t result = 0;
107 107
108 for (int i : range(4)) 108 for (int i = 0; i < 4; i += 1)
109 result |= read() << (i * 8); 109 result |= read() << (i * 8);
110 110
111 return result; 111 return result;
112 } 112 }
113 113
125 125
126 /*! 126 /*!
127 * \brief Reads in characters until a null terminator is encountered. 127 * \brief Reads in characters until a null terminator is encountered.
128 * \returns the read string. 128 * \returns the read string.
129 */ 129 */
130 String Bytestream::readString() 130 std::string Bytestream::readString()
131 { 131 {
132 String result; 132 std::string result;
133 133
134 for (char byte; (byte = readByte()) != '\0';) 134 for (char byte; (byte = readByte()) != '\0';)
135 { 135 {
136 if (result.length() < MAX_NETWORK_STRING) 136 if (result.length() < MAX_NETWORK_STRING)
137 result += byte; 137 result += byte;
143 /*! 143 /*!
144 * \brief Reads in a buffer of the specified length. 144 * \brief Reads in a buffer of the specified length.
145 * \param length Amount of bytes to read. 145 * \param length Amount of bytes to read.
146 * \returns the read buffer. 146 * \returns the read buffer.
147 */ 147 */
148 ByteArray Bytestream::readBuffer(int length) 148 std::vector<unsigned char> Bytestream::readBuffer(int length)
149 { 149 {
150 ensureReadSpace(length); 150 ensureReadSpace(length);
151 ByteArray result(length); 151 std::vector<unsigned char> result(length);
152 memcpy(result.data(), m_data.data() + m_position, length); 152 memcpy(result.data(), m_data.data() + m_position, length);
153 m_position += length; 153 m_position += length;
154 return result; 154 return result;
155 } 155 }
156 156
158 * \brief Writes an integer to the end of the data as one byte. 158 * \brief Writes an integer to the end of the data as one byte.
159 * \param value Value to write 159 * \param value Value to write
160 */ 160 */
161 void Bytestream::writeByte(int8_t value) 161 void Bytestream::writeByte(int8_t value)
162 { 162 {
163 m_data.append(value); 163 m_data.push_back(value);
164 } 164 }
165 165
166 /*! 166 /*!
167 * \brief Writes an integer to the end of the data as 2 bytes. 167 * \brief Writes an integer to the end of the data as 2 bytes.
168 * \param value Value to write 168 * \param value Value to write
169 */ 169 */
170 void Bytestream::writeShort(int16_t value) 170 void Bytestream::writeShort(int16_t value)
171 { 171 {
172 for (int i : range(2)) 172 m_data.reserve(m_data.size() + 2);
173 m_data.append((value >> (i * 8)) & 0xFF); 173 for (int i : {0, 1})
174 m_data.push_back((value >> (i * 8)) & 0xFF);
174 } 175 }
175 176
176 /*! 177 /*!
177 * \brief Writes an integer to the end of the data as 4 bytes. 178 * \brief Writes an integer to the end of the data as 4 bytes.
178 * \param value Value to write 179 * \param value Value to write
179 */ 180 */
180 void Bytestream::writeLong(int32_t value) 181 void Bytestream::writeLong(int32_t value)
181 { 182 {
182 for (int i : range(4)) 183 m_data.reserve(m_data.size() + 4);
183 m_data.append((value >> (i * 8)) & 0xFF); 184 for (int i = 0; i < 4; i += 1)
185 m_data.push_back((value >> (i * 8)) & 0xFF);
184 } 186 }
185 187
186 /*! 188 /*!
187 * \brief Writes a floating-point number to the end of the data. 189 * \brief Writes a floating-point number to the end of the data.
188 * \param value Value to write. 190 * \param value Value to write.
197 199
198 /*! 200 /*!
199 * \brief Writes the given string to the end of the data. 201 * \brief Writes the given string to the end of the data.
200 * \param text String to write. 202 * \param text String to write.
201 */ 203 */
202 void Bytestream::writeString(const String& string) 204 void Bytestream::writeString(const std::string& string)
203 { 205 {
204 m_data.append(string.toBytes(), string.length()); 206 const int oldSize = m_data.size();
205 m_data.append(0); 207 m_data.reserve(m_data.size() + string.length() + 1);
208 m_data.resize(m_data.size() + string.length());
209 std::copy(string.begin(), string.end(), m_data.begin() + oldSize);
210 m_data.push_back(0);
206 } 211 }
207 212
208 /*! 213 /*!
209 * \returns the current position the stream cursor in the data. 214 * \returns the current position the stream cursor in the data.
210 */ 215 */

mercurial