blob: 740bff2c727550da18ad8a1b463deb744850d620 [file] [log] [blame]
henrike@webrtc.orgf0488722014-05-13 18:00:261/*
2 * Copyright 2004 The WebRTC Project Authors. All rights reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
Mirko Bonadei92ea95e2017-09-15 04:47:3111#ifndef RTC_BASE_BYTEBUFFER_H_
12#define RTC_BASE_BYTEBUFFER_H_
henrike@webrtc.orgf0488722014-05-13 18:00:2613
Henrik Kjellanderec78f1c2017-06-29 05:52:5014#include <string>
henrike@webrtc.orgf0488722014-05-13 18:00:2615
Mirko Bonadei92ea95e2017-09-15 04:47:3116#include "rtc_base/basictypes.h"
17#include "rtc_base/buffer.h"
Joachim Bauch4c6a30c2018-03-07 23:55:3318#include "rtc_base/byteorder.h"
Mirko Bonadei92ea95e2017-09-15 04:47:3119#include "rtc_base/constructormagic.h"
Henrik Kjellanderec78f1c2017-06-29 05:52:5020
21namespace rtc {
22
23class ByteBuffer {
24 public:
25 enum ByteOrder {
26 ORDER_NETWORK = 0, // Default, use network byte order (big endian).
27 ORDER_HOST, // Use the native order of the host.
28 };
29
30 explicit ByteBuffer(ByteOrder byte_order) : byte_order_(byte_order) {}
31
32 ByteOrder Order() const { return byte_order_; }
33
34 private:
35 ByteOrder byte_order_;
36
37 RTC_DISALLOW_COPY_AND_ASSIGN(ByteBuffer);
38};
39
Joachim Bauch4c6a30c2018-03-07 23:55:3340template <class BufferClassT>
41class ByteBufferWriterT : public ByteBuffer {
42 public:
43 // |byte_order| defines order of bytes in the buffer.
44 ByteBufferWriterT() : ByteBuffer(ORDER_NETWORK) {
45 Construct(nullptr, kDefaultCapacity);
46 }
47 explicit ByteBufferWriterT(ByteOrder byte_order) : ByteBuffer(byte_order) {
48 Construct(nullptr, kDefaultCapacity);
49 }
50 ByteBufferWriterT(const char* bytes, size_t len) : ByteBuffer(ORDER_NETWORK) {
51 Construct(bytes, len);
52 }
53 ByteBufferWriterT(const char* bytes, size_t len, ByteOrder byte_order)
54 : ByteBuffer(byte_order) {
55 Construct(bytes, len);
56 }
57
58 const char* Data() const { return buffer_.data(); }
59 size_t Length() const { return buffer_.size(); }
60 size_t Capacity() const { return buffer_.capacity(); }
61
62 // Write value to the buffer. Resizes the buffer when it is
63 // neccessary.
64 void WriteUInt8(uint8_t val) {
65 WriteBytes(reinterpret_cast<const char*>(&val), 1);
66 }
67 void WriteUInt16(uint16_t val) {
68 uint16_t v = (Order() == ORDER_NETWORK) ? HostToNetwork16(val) : val;
69 WriteBytes(reinterpret_cast<const char*>(&v), 2);
70 }
71 void WriteUInt24(uint32_t val) {
72 uint32_t v = (Order() == ORDER_NETWORK) ? HostToNetwork32(val) : val;
73 char* start = reinterpret_cast<char*>(&v);
74 if (Order() == ORDER_NETWORK || IsHostBigEndian()) {
75 ++start;
76 }
77 WriteBytes(start, 3);
78 }
79 void WriteUInt32(uint32_t val) {
80 uint32_t v = (Order() == ORDER_NETWORK) ? HostToNetwork32(val) : val;
81 WriteBytes(reinterpret_cast<const char*>(&v), 4);
82 }
83 void WriteUInt64(uint64_t val) {
84 uint64_t v = (Order() == ORDER_NETWORK) ? HostToNetwork64(val) : val;
85 WriteBytes(reinterpret_cast<const char*>(&v), 8);
86 }
87 // Serializes an unsigned varint in the format described by
88 // https://developers.google.com/protocol-buffers/docs/encoding#varints
89 // with the caveat that integers are 64-bit, not 128-bit.
90 void WriteUVarint(uint64_t val) {
91 while (val >= 0x80) {
92 // Write 7 bits at a time, then set the msb to a continuation byte
93 // (msb=1).
94 char byte = static_cast<char>(val) | 0x80;
95 WriteBytes(&byte, 1);
96 val >>= 7;
97 }
98 char last_byte = static_cast<char>(val);
99 WriteBytes(&last_byte, 1);
100 }
101 void WriteString(const std::string& val) {
102 WriteBytes(val.c_str(), val.size());
103 }
104 void WriteBytes(const char* val, size_t len) { buffer_.AppendData(val, len); }
105
106 // Reserves the given number of bytes and returns a char* that can be written
107 // into. Useful for functions that require a char* buffer and not a
108 // ByteBufferWriter.
109 char* ReserveWriteBuffer(size_t len) {
110 buffer_.SetSize(buffer_.size() + len);
111 return buffer_.data();
112 }
113
114 // Resize the buffer to the specified |size|.
115 void Resize(size_t size) { buffer_.SetSize(size); }
116
117 // Clears the contents of the buffer. After this, Length() will be 0.
118 void Clear() { buffer_.Clear(); }
119
120 private:
121 static constexpr size_t kDefaultCapacity = 4096;
122
123 void Construct(const char* bytes, size_t size) {
124 if (bytes) {
125 buffer_.AppendData(bytes, size);
126 } else {
127 buffer_.EnsureCapacity(size);
128 }
129 }
130
131 BufferClassT buffer_;
132
133 // There are sensible ways to define these, but they aren't needed in our code
134 // base.
135 RTC_DISALLOW_COPY_AND_ASSIGN(ByteBufferWriterT);
136};
137
138class ByteBufferWriter : public ByteBufferWriterT<BufferT<char>> {
Henrik Kjellanderec78f1c2017-06-29 05:52:50139 public:
140 // |byte_order| defines order of bytes in the buffer.
141 ByteBufferWriter();
142 explicit ByteBufferWriter(ByteOrder byte_order);
143 ByteBufferWriter(const char* bytes, size_t len);
144 ByteBufferWriter(const char* bytes, size_t len, ByteOrder byte_order);
145
Henrik Kjellanderec78f1c2017-06-29 05:52:50146 private:
Henrik Kjellanderec78f1c2017-06-29 05:52:50147 RTC_DISALLOW_COPY_AND_ASSIGN(ByteBufferWriter);
148};
149
150// The ByteBufferReader references the passed data, i.e. the pointer must be
151// valid during the lifetime of the reader.
152class ByteBufferReader : public ByteBuffer {
153 public:
154 ByteBufferReader(const char* bytes, size_t len);
155 ByteBufferReader(const char* bytes, size_t len, ByteOrder byte_order);
156
157 // Initializes buffer from a zero-terminated string.
158 explicit ByteBufferReader(const char* bytes);
159
160 explicit ByteBufferReader(const Buffer& buf);
161
162 explicit ByteBufferReader(const ByteBufferWriter& buf);
163
164 // Returns start of unprocessed data.
165 const char* Data() const { return bytes_ + start_; }
166 // Returns number of unprocessed bytes.
167 size_t Length() const { return end_ - start_; }
168
169 // Read a next value from the buffer. Return false if there isn't
170 // enough data left for the specified type.
171 bool ReadUInt8(uint8_t* val);
172 bool ReadUInt16(uint16_t* val);
173 bool ReadUInt24(uint32_t* val);
174 bool ReadUInt32(uint32_t* val);
175 bool ReadUInt64(uint64_t* val);
176 bool ReadUVarint(uint64_t* val);
177 bool ReadBytes(char* val, size_t len);
178
179 // Appends next |len| bytes from the buffer to |val|. Returns false
180 // if there is less than |len| bytes left.
181 bool ReadString(std::string* val, size_t len);
182
183 // Moves current position |size| bytes forward. Returns false if
184 // there is less than |size| bytes left in the buffer. Consume doesn't
185 // permanently remove data, so remembered read positions are still valid
186 // after this call.
187 bool Consume(size_t size);
188
189 private:
190 void Construct(const char* bytes, size_t size);
191
192 const char* bytes_;
193 size_t size_;
194 size_t start_;
195 size_t end_;
196
197 RTC_DISALLOW_COPY_AND_ASSIGN(ByteBufferReader);
198};
199
200} // namespace rtc
henrike@webrtc.orgf0488722014-05-13 18:00:26201
Mirko Bonadei92ea95e2017-09-15 04:47:31202#endif // RTC_BASE_BYTEBUFFER_H_