1 // 2 // Copyright (c) 2012 The ANGLE Project Authors. All rights reserved. 3 // Use of this source code is governed by a BSD-style license that can be 4 // found in the LICENSE file. 5 // 6 7 // BinaryStream.h: Provides binary serialization of simple types. 8 9 #ifndef LIBGLESV2_BINARYSTREAM_H_ 10 #define LIBGLESV2_BINARYSTREAM_H_ 11 12 #include "common/angleutils.h" 13 #include "common/mathutil.h" 14 15 #include <cstddef> 16 #include <string> 17 #include <vector> 18 19 namespace gl 20 { 21 22 class BinaryInputStream 23 { 24 public: 25 BinaryInputStream(const void *data, size_t length) 26 { 27 mError = false; 28 mOffset = 0; 29 mData = static_cast<const char*>(data); 30 mLength = length; 31 } 32 33 // readInt will generate an error for bool types 34 template <class IntT> 35 IntT readInt() 36 { 37 int value; 38 read(&value); 39 return static_cast<IntT>(value); 40 } 41 42 template <class IntT> 43 void readInt(IntT *outValue) 44 { 45 *outValue = readInt<IntT>(); 46 } 47 48 bool readBool() 49 { 50 int value; 51 read(&value); 52 return (value > 0); 53 } 54 55 void readBool(bool *outValue) 56 { 57 *outValue = readBool(); 58 } 59 60 void readBytes(unsigned char outArray[], size_t count) 61 { 62 read<unsigned char>(outArray, count); 63 } 64 65 std::string readString() 66 { 67 std::string outString; 68 readString(&outString); 69 return outString; 70 } 71 72 void readString(std::string *v) 73 { 74 size_t length; 75 readInt(&length); 76 77 if (mError) 78 { 79 return; 80 } 81 82 if (mOffset + length > mLength) 83 { 84 mError = true; 85 return; 86 } 87 88 v->assign(mData + mOffset, length); 89 mOffset += length; 90 } 91 92 void skip(size_t length) 93 { 94 if (mOffset + length > mLength) 95 { 96 mError = true; 97 return; 98 } 99 100 mOffset += length; 101 } 102 103 size_t offset() const 104 { 105 return mOffset; 106 } 107 108 bool error() const 109 { 110 return mError; 111 } 112 113 bool endOfStream() const 114 { 115 return mOffset == mLength; 116 } 117 118 private: 119 DISALLOW_COPY_AND_ASSIGN(BinaryInputStream); 120 bool mError; 121 size_t mOffset; 122 const char *mData; 123 size_t mLength; 124 125 template <typename T> 126 void read(T *v, size_t num) 127 { 128 META_ASSERT(std::is_fundamental<T>::value); 129 130 size_t length = num * sizeof(T); 131 132 if (mOffset + length > mLength) 133 { 134 mError = true; 135 return; 136 } 137 138 memcpy(v, mData + mOffset, length); 139 mOffset += length; 140 } 141 142 template <typename T> 143 void read(T *v) 144 { 145 read(v, 1); 146 } 147 148 }; 149 150 class BinaryOutputStream 151 { 152 public: 153 BinaryOutputStream() 154 { 155 } 156 157 // writeInt also handles bool types 158 template <class IntT> 159 void writeInt(IntT param) 160 { 161 ASSERT(rx::IsIntegerCastSafe<int>(param)); 162 int intValue = static_cast<int>(param); 163 write(&intValue, 1); 164 } 165 166 void writeString(const std::string &v) 167 { 168 writeInt(v.length()); 169 write(v.c_str(), v.length()); 170 } 171 172 void writeBytes(const unsigned char *bytes, size_t count) 173 { 174 write(bytes, count); 175 } 176 177 size_t length() const 178 { 179 return mData.size(); 180 } 181 182 const void* data() const 183 { 184 return mData.size() ? &mData[0] : NULL; 185 } 186 187 private: 188 DISALLOW_COPY_AND_ASSIGN(BinaryOutputStream); 189 std::vector<char> mData; 190 191 template <typename T> 192 void write(const T *v, size_t num) 193 { 194 META_ASSERT(std::is_fundamental<T>::value); 195 const char *asBytes = reinterpret_cast<const char*>(v); 196 mData.insert(mData.end(), asBytes, asBytes + num * sizeof(T)); 197 } 198 199 }; 200 } 201 202 #endif // LIBGLESV2_BINARYSTREAM_H_ 203