TrinityCore
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
G3D::BinaryInput Class Reference

#include <BinaryInput.h>

Public Member Functions

 BinaryInput (const std::string &filename, G3DEndian fileEndian, bool compressed=false)
 
 BinaryInput (const uint8 *data, int64 dataLen, G3DEndian dataEndian, bool compressed=false, bool copyMemory=true)
 
virtual ~BinaryInput ()
 
void setEndian (G3DEndian endian)
 
G3DEndian endian () const
 
std::string getFilename () const
 
uint8 operator[] (int64 n)
 
int64 getLength () const
 
int64 size () const
 
int64 getPosition () const
 
const uint8getCArray ()
 
void setPosition (int64 p)
 
void reset ()
 
void readBytes (void *bytes, int64 n)
 
int8 readInt8 ()
 
bool readBool8 ()
 
uint8 readUInt8 ()
 
unorm8 readUNorm8 ()
 
uint16 readUInt16 ()
 
int16 readInt16 ()
 
uint32 readUInt32 ()
 
int32 readInt32 ()
 
uint64 readUInt64 ()
 
int64 readInt64 ()
 
float32 readFloat32 ()
 
float64 readFloat64 ()
 
std::string readString (int64 maxLength)
 
std::string readString ()
 
std::string readFixedLengthString (int numBytes)
 
std::string readStringNewline ()
 
std::string readStringEven ()
 
std::string readString32 ()
 
Vector4 readVector4 ()
 
Vector3 readVector3 ()
 
Vector2 readVector2 ()
 
Color4 readColor4 ()
 
Color3 readColor3 ()
 
void skip (int64 n)
 
bool hasMore () const
 
void beginBits ()
 
uint32 readBits (int numBits)
 
void endBits ()
 

Static Public Attributes

static const bool NO_COPY = false
 

Private Member Functions

void loadIntoMemory (int64 startPosition, int64 minLength=0)
 
void prepareToRead (int64 nbytes)
 
 BinaryInput (const BinaryInput &)
 
BinaryInputoperator= (const BinaryInput &)
 
bool operator== (const BinaryInput &)
 
void decompress ()
 

Private Attributes

G3DEndian m_fileEndian
 
std::string m_filename
 
bool m_swapBytes
 
int m_bitPos
 
uint32 m_bitString
 
int m_beginEndBits
 
int64 m_alreadyRead
 
int64 m_length
 
int64 m_bufferLength
 
uint8m_buffer
 
int64 m_pos
 
bool m_freeBuffer
 

Static Private Attributes

static const int64 INITIAL_BUFFER_LENGTH
 

Detailed Description

Sequential or random access byte-order independent binary file access. Files compressed with zlib and beginning with an unsigned 32-bit int size are transparently decompressed when the compressed = true flag is specified to the constructor.

For every readX method there are also versions that operate on a whole Array, std::vector, or C-array. e.g. readFloat32(Array<float32>& array, n) These methods resize the array or std::vector to the appropriate size before reading. For a C-array, they require the pointer to reference a memory block at least large enough to hold n elements.

Most classes define serialize/deserialize methods that use BinaryInput, BinaryOutput, TextInput, and TextOutput. There are text serializer functions for primitive types (e.g. int, std::string, float, double) but not binary serializers– you must call the BinaryInput::readInt32 or other appropriate function. This is because it would be very hard to debug the error sequence: serialize(1.0, bo); ... float f; deserialize(f, bi); in which a double is serialized and then deserialized as a float.

Constructor & Destructor Documentation

G3D::BinaryInput::BinaryInput ( const BinaryInput )
private
G3D::BinaryInput::BinaryInput ( const std::string &  filename,
G3DEndian  fileEndian,
bool  compressed = false 
)

If the file cannot be opened, a zero length buffer is presented. Automatically opens files that are inside zipfiles.

Parameters
compressedSet to true if and only if the file was compressed using BinaryOutput's zlib compression. This has nothing to do with whether the input is in a zipfile.
117  :
118  m_filename(filename),
119  m_bitPos(0),
120  m_bitString(0),
121  m_beginEndBits(0),
122  m_alreadyRead(0),
123  m_length(0),
124  m_bufferLength(0),
125  m_buffer(NULL),
126  m_pos(0),
127  m_freeBuffer(true) {
128 
129  setEndian(fileEndian);
130 
131 #if _HAVE_ZIP /* G3DFIX: Use ZIP-library only if defined */
132  std::string zipfile;
133  if (FileSystem::inZipfile(m_filename, zipfile)) {
134  // Load from zipfile
136  FileSystem::markFileUsed(zipfile);
137 
138  // Zipfiles require Unix-style slashes
139  std::string internalFile = FilePath::canonicalize(m_filename.substr(zipfile.length() + 1));
140  struct zip* z = zip_open(zipfile.c_str(), ZIP_CHECKCONS, NULL);
141  {
142  struct zip_stat info;
143  zip_stat_init( &info ); // TODO: Docs unclear if zip_stat_init is required.
144  zip_stat(z, internalFile.c_str(), ZIP_FL_NOCASE, &info);
145  m_bufferLength = m_length = info.size;
146  // sets machines up to use MMX, if they want
147  m_buffer = reinterpret_cast<uint8*>(System::alignedMalloc(m_length, 16));
148  struct zip_file* zf = zip_fopen( z, internalFile.c_str(), ZIP_FL_NOCASE );
149  if (zf == NULL) {
150  throw std::string("\"") + internalFile + "\" inside \"" + zipfile + "\" could not be opened.";
151  } else {
152  const int64 bytesRead = zip_fread( zf, m_buffer, m_length );
153  debugAssertM(bytesRead == m_length,
154  internalFile + " was corrupt because it unzipped to the wrong size.");
155  (void)bytesRead;
156  zip_fclose( zf );
157  }
158  }
159  zip_close( z );
160 
161  if (compressed) {
162  decompress();
163  }
164 
165  m_freeBuffer = true;
166  return;
167  }
168 #endif
169  // Figure out how big the file is and verify that it exists.
171 
172  // Read the file into memory
173  FILE* file = FileSystem::fopen(m_filename.c_str(), "rb");
174 
175  if (! file || (m_length == -1)) {
176  throw format("File not found: \"%s\"", m_filename.c_str());
177  return;
178  }
179 
180  if (! compressed && (m_length > INITIAL_BUFFER_LENGTH)) {
181  // Read only a subset of the file so we don't consume
182  // all available memory.
183  m_bufferLength = INITIAL_BUFFER_LENGTH;
184  } else {
185  // Either the length is fine or the file is compressed
186  // and requires us to read the whole thing for zlib.
187  m_bufferLength = m_length;
188  }
189 
191  m_buffer = (uint8*)System::alignedMalloc(m_bufferLength, 16);
192  if (m_buffer == NULL) {
193  if (compressed) {
194  throw "Not enough memory to load compressed file. (1)";
195  }
196 
197  // Try to allocate a small array; not much memory is available.
198  // Give up if we can't allocate even 1k.
199  while ((m_buffer == NULL) && (m_bufferLength > 1024)) {
200  m_bufferLength /= 2;
201  m_buffer = (uint8*)System::alignedMalloc(m_bufferLength, 16);
202  }
203  }
205 
206  (void)fread(m_buffer, m_bufferLength, sizeof(int8), file);
207  FileSystem::fclose(file);
208  file = NULL;
209 
210  if (compressed) {
211  if (m_bufferLength != m_length) {
212  throw "Not enough memory to load compressed file. (2)";
213  }
214 
215  decompress();
216  }
217 }
int8_t int8
Definition: Define.h:148
uint8 * m_buffer
Definition: BinaryInput.h:117
static const int64 INITIAL_BUFFER_LENGTH
Definition: BinaryInput.h:75
int64_t int64
Definition: Define.h:145
static void fclose(FILE *f)
Definition: FileSystem.h:290
arena_t NULL
Definition: jemalloc_internal.h:624
void decompress()
Definition: BinaryInput.cpp:242
#define debugAssertM(exp, message)
Definition: debugAssert.h:161
int m_bitPos
Definition: BinaryInput.h:92
int64 m_length
Definition: BinaryInput.h:113
void setEndian(G3DEndian endian)
Definition: BinaryInput.cpp:272
bool m_freeBuffer
Definition: BinaryInput.h:127
int64 m_bufferLength
Definition: BinaryInput.h:116
#define debugAssert(exp)
Definition: debugAssert.h:160
G3D::int16 z
Definition: Vector3int16.h:46
int64 m_pos
Definition: BinaryInput.h:122
static int64 size(const std::string &path)
Definition: FileSystem.h:462
std::string __cdecl format(const char *fmt...) G3D_CHECK_PRINTF_ARGS
static void * alignedMalloc(size_t bytes, size_t alignment)
Definition: System.cpp:1482
static std::string canonicalize(std::string x)
Definition: FileSystem.cpp:832
int64 m_alreadyRead
Definition: BinaryInput.h:107
static FILE * fopen(const char *filename, const char *mode)
Definition: FileSystem.h:282
static bool inZipfile(const std::string &path, std::string &zipfile)
Definition: FileSystem.h:264
uint8_t uint8
Definition: Define.h:152
int m_beginEndBits
Definition: BinaryInput.h:101
static void markFileUsed(const std::string &filename)
Definition: FileSystem.cpp:553
std::string m_filename
Definition: BinaryInput.h:87
uint32 m_bitString
Definition: BinaryInput.h:98

+ Here is the call graph for this function:

G3D::BinaryInput::BinaryInput ( const uint8 data,
int64  dataLen,
G3DEndian  dataEndian,
bool  compressed = false,
bool  copyMemory = true 
)

Creates input stream from an in memory source. Unless you specify copyMemory = false, the data is copied from the pointer, so you may deallocate it as soon as the object is constructed. It is an error to specify copyMemory = false and compressed = true.

To decompress part of a file, you can follow the following paradigm:

   BinaryInput master(...);

   // read from master to point where compressed data exists.

   BinaryInput subset(master.getCArray() + master.getPosition(), 
                      master.length() - master.getPosition(),
                      master.endian(), true, true);

   // Now read from subset (it is ok for master to go out of scope)

72  :
73  m_filename("<memory>"),
74  m_bitPos(0),
75  m_bitString(0),
76  m_beginEndBits(0),
77  m_alreadyRead(0),
78  m_bufferLength(0),
79  m_pos(0) {
80 
81  m_freeBuffer = copyMemory || compressed;
82 
83  setEndian(dataEndian);
84 
85  if (compressed) {
86  // Read the decompressed size from the first 4 bytes
88 
91 
92  unsigned long L = (unsigned long)m_length;
93  // Decompress with zlib
94  int64 result = uncompress(m_buffer, &L, data + 4, (uLong)dataLen - 4);
95  m_length = L;
96  m_bufferLength = L;
97  debugAssert(result == Z_OK); (void)result;
98 
99  } else {
100  m_length = dataLen;
102  if (! copyMemory) {
104  m_buffer = const_cast<uint8*>(data);
105  } else {
108  System::memcpy(m_buffer, data, dataLen);
109  }
110  }
111 }
uint8 * m_buffer
Definition: BinaryInput.h:117
static void memcpy(void *dst, const void *src, size_t numBytes)
Definition: System.cpp:643
int64_t int64
Definition: Define.h:145
unsigned long uLong
Definition: zconf.h:371
int m_bitPos
Definition: BinaryInput.h:92
int64 m_length
Definition: BinaryInput.h:113
void setEndian(G3DEndian endian)
Definition: BinaryInput.cpp:272
bool m_freeBuffer
Definition: BinaryInput.h:127
int64 m_bufferLength
Definition: BinaryInput.h:116
#define debugAssert(exp)
Definition: debugAssert.h:160
int64 m_pos
Definition: BinaryInput.h:122
bool m_swapBytes
Definition: BinaryInput.h:89
static void * alignedMalloc(size_t bytes, size_t alignment)
Definition: System.cpp:1482
int64 m_alreadyRead
Definition: BinaryInput.h:107
#define Z_OK
Definition: zlib.h:173
uint8_t uint8
Definition: Define.h:152
int m_beginEndBits
Definition: BinaryInput.h:101
std::string m_filename
Definition: BinaryInput.h:87
uint32 m_bitString
Definition: BinaryInput.h:98
static uint32 readUInt32FromBuffer(const uint8 *data, bool swapBytes)
Definition: BinaryInput.cpp:53

+ Here is the call graph for this function:

G3D::BinaryInput::~BinaryInput ( )
virtual
219  {
220 
221  if (m_freeBuffer) {
223  }
224  m_buffer = NULL;
225 }
uint8 * m_buffer
Definition: BinaryInput.h:117
arena_t NULL
Definition: jemalloc_internal.h:624
static void alignedFree(void *ptr)
Definition: System.cpp:1546
bool m_freeBuffer
Definition: BinaryInput.h:127

+ Here is the call graph for this function:

Member Function Documentation

void G3D::BinaryInput::beginBits ( )

Prepares for bit reading via readBits. Only readBits can be called between beginBits and endBits without corrupting the data stream.

520  {
522  m_beginEndBits = 1;
523  m_bitPos = 0;
524 
525  debugAssertM(hasMore(), "Can't call beginBits when at the end of a file");
527 }
#define debugAssertM(exp, message)
Definition: debugAssert.h:161
int m_bitPos
Definition: BinaryInput.h:92
uint8 readUInt8()
Definition: BinaryInput.h:278
#define debugAssert(exp)
Definition: debugAssert.h:160
bool hasMore() const
Definition: BinaryInput.h:417
int m_beginEndBits
Definition: BinaryInput.h:101
uint32 m_bitString
Definition: BinaryInput.h:98

+ Here is the call graph for this function:

void G3D::BinaryInput::decompress ( )
private

Buffer is compressed; replace it with a decompressed version

242  {
243  // Decompress
244  // Use the existing buffer as the source, allocate
245  // a new buffer to use as the destination.
246 
247  int64 tempLength = m_length;
249 
250  // The file couldn't have better than 500:1 compression
251  alwaysAssertM(m_length < m_bufferLength * 500, "Compressed file header is corrupted");
252 
253  uint8* tempBuffer = m_buffer;
255 
257  debugAssert(isValidHeapPointer(tempBuffer));
259 
260  unsigned long L = (unsigned long)m_length;
261  int64 result = (int64)uncompress(m_buffer, &L, tempBuffer + 4, (uLong)tempLength - 4);
262  m_length = L;
264 
265  debugAssertM(result == Z_OK, "BinaryInput/zlib detected corruption in " + m_filename);
266  (void)result;
267 
268  System::alignedFree(tempBuffer);
269 }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64_t int64
Definition: Define.h:145
unsigned long uLong
Definition: zconf.h:371
static void alignedFree(void *ptr)
Definition: System.cpp:1546
#define debugAssertM(exp, message)
Definition: debugAssert.h:161
int64 m_length
Definition: BinaryInput.h:113
int64 m_bufferLength
Definition: BinaryInput.h:116
#define debugAssert(exp)
Definition: debugAssert.h:160
bool m_swapBytes
Definition: BinaryInput.h:89
static void * alignedMalloc(size_t bytes, size_t alignment)
Definition: System.cpp:1482
int64_t int64
Definition: g3dmath.h:169
#define Z_OK
Definition: zlib.h:173
uint8_t uint8
Definition: Define.h:152
#define alwaysAssertM(exp, message)
Definition: debugAssert.h:165
std::string m_filename
Definition: BinaryInput.h:87
bool isValidHeapPointer(const void *x)
Definition: debug.h:38
static uint32 readUInt32FromBuffer(const uint8 *data, bool swapBytes)
Definition: BinaryInput.cpp:53

+ Here is the call graph for this function:

void G3D::BinaryInput::endBits ( )

Ends bit-reading.

558  {
560  if (m_bitPos == 0) {
561  // Put back the last byte we read
562  --m_pos;
563  }
564  m_beginEndBits = 0;
565  m_bitPos = 0;
566 }
int m_bitPos
Definition: BinaryInput.h:92
#define debugAssert(exp)
Definition: debugAssert.h:160
int64 m_pos
Definition: BinaryInput.h:122
int m_beginEndBits
Definition: BinaryInput.h:101
G3DEndian G3D::BinaryInput::endian ( ) const
inline
199  {
200  return m_fileEndian;
201  }
G3DEndian m_fileEndian
Definition: BinaryInput.h:86
const uint8* G3D::BinaryInput::getCArray ( )
inline

Returns a pointer to the internal memory buffer. May throw an exception for huge files.

241  {
242  if (m_alreadyRead > 0 || m_bufferLength < m_length) {
243  throw "Cannot getCArray for a huge file";
244  }
245  return m_buffer;
246  }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64 m_length
Definition: BinaryInput.h:113
int64 m_bufferLength
Definition: BinaryInput.h:116
int64 m_alreadyRead
Definition: BinaryInput.h:107

+ Here is the caller graph for this function:

std::string G3D::BinaryInput::getFilename ( ) const
inline
203  {
204  return m_filename;
205  }
std::string m_filename
Definition: BinaryInput.h:87
int64 G3D::BinaryInput::getLength ( ) const
inline

Returns the length of the file in bytes.

221  {
222  return m_length;
223  }
int64 m_length
Definition: BinaryInput.h:113

+ Here is the caller graph for this function:

int64 G3D::BinaryInput::getPosition ( ) const
inline

Returns the current byte position in the file, where 0 is the beginning and getLength() - 1 is the end.

233  {
234  return m_pos + m_alreadyRead;
235  }
int64 m_pos
Definition: BinaryInput.h:122
int64 m_alreadyRead
Definition: BinaryInput.h:107
bool G3D::BinaryInput::hasMore ( ) const
inline

Returns true if the position is not at the end of the file

417  {
418  return m_pos + m_alreadyRead < m_length;
419  }
int64 m_length
Definition: BinaryInput.h:113
int64 m_pos
Definition: BinaryInput.h:122
int64 m_alreadyRead
Definition: BinaryInput.h:107

+ Here is the caller graph for this function:

void G3D::BinaryInput::loadIntoMemory ( int64  startPosition,
int64  minLength = 0 
)
private

Ensures that we are able to read at least minLength from startPosition (relative to start of file).

278  {
279  // Load the next section of the file
280  debugAssertM(m_filename != "<memory>", "Read past end of file.");
281 
282  int64 absPos = m_alreadyRead + m_pos;
283 
284  if (m_bufferLength < minLength) {
285  // The current buffer isn't big enough to hold the chunk we want to read.
286  // This happens if there was little memory available during the initial constructor
287  // read but more memory has since been freed.
288  m_bufferLength = minLength;
291  if (m_buffer == NULL) {
292  throw "Tried to read a larger memory chunk than could fit in memory. (2)";
293  }
294  }
295 
296  m_alreadyRead = startPosition;
297 
298 # ifdef G3D_WINDOWS
299  FILE* file = fopen(m_filename.c_str(), "rb");
300  debugAssert(file);
301  size_t ret = fseek(file, (off_t)m_alreadyRead, SEEK_SET);
302  debugAssert(ret == 0);
303  size_t toRead = (size_t)G3D::min(m_bufferLength, m_length - m_alreadyRead);
304  ret = fread(m_buffer, 1, toRead, file);
305  debugAssert(ret == toRead);
306  fclose(file);
307  file = NULL;
308 
309 # else
310  FILE* file = fopen(m_filename.c_str(), "rb");
311  debugAssert(file);
312  int ret = fseeko(file, (off_t)m_alreadyRead, SEEK_SET);
313  debugAssert(ret == 0);
314  size_t toRead = (size_t)G3D::min<int64>(m_bufferLength, m_length - m_alreadyRead);
315  ret = fread(m_buffer, 1, toRead, file);
316  debugAssert((size_t)ret == (size_t)toRead);
317  fclose(file);
318  file = NULL;
319 # endif
320 
321  m_pos = absPos - m_alreadyRead;
322  debugAssert(m_pos >= 0);
323 }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64_t int64
Definition: Define.h:145
arena_t NULL
Definition: jemalloc_internal.h:624
static void * realloc(void *block, size_t bytes)
Definition: System.cpp:1463
#define debugAssertM(exp, message)
Definition: debugAssert.h:161
int64 m_length
Definition: BinaryInput.h:113
bool m_freeBuffer
Definition: BinaryInput.h:127
T min(const T &x, const T &y)
Definition: g3dmath.h:305
int64 m_bufferLength
Definition: BinaryInput.h:116
#define debugAssert(exp)
Definition: debugAssert.h:160
int64 m_pos
Definition: BinaryInput.h:122
#define SEEK_SET
Definition: zconf.h:475
int64 m_alreadyRead
Definition: BinaryInput.h:107
uint8_t uint8
Definition: Define.h:152
std::string m_filename
Definition: BinaryInput.h:87

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

BinaryInput& G3D::BinaryInput::operator= ( const BinaryInput )
private
bool G3D::BinaryInput::operator== ( const BinaryInput )
private
uint8 G3D::BinaryInput::operator[] ( int64  n)
inline

Performs bounds checks in debug mode. [] are relative to the start of the file, not the current position. Seeks to the new position before reading (and leaves that as the current position)

213  {
214  setPosition(n);
215  return readUInt8();
216  }
void setPosition(int64 p)
Definition: BinaryInput.h:252
uint8 readUInt8()
Definition: BinaryInput.h:278

+ Here is the call graph for this function:

void G3D::BinaryInput::prepareToRead ( int64  nbytes)
private

Verifies that at least this number of bytes can be read.

326  {
327  debugAssertM(m_length > 0, m_filename + " not found or corrupt.");
328  debugAssertM(m_pos + nbytes + m_alreadyRead <= m_length, "Read past end of file.");
329 
330  if (m_pos + nbytes > m_bufferLength) {
331  loadIntoMemory(m_pos + m_alreadyRead, nbytes);
332  }
333 }
#define debugAssertM(exp, message)
Definition: debugAssert.h:161
int64 m_length
Definition: BinaryInput.h:113
void loadIntoMemory(int64 startPosition, int64 minLength=0)
Definition: BinaryInput.cpp:278
int64 m_bufferLength
Definition: BinaryInput.h:116
int64 m_pos
Definition: BinaryInput.h:122
int64 m_alreadyRead
Definition: BinaryInput.h:107
std::string m_filename
Definition: BinaryInput.h:87

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

uint32 G3D::BinaryInput::readBits ( int  numBits)

Can only be called between beginBits and endBits

530  {
532 
533  uint32 out = 0;
534 
535  const int total = numBits;
536  while (numBits > 0) {
537  if (m_bitPos > 7) {
538  // Consume a new byte for reading. We do this at the beginning
539  // of the loop so that we don't try to read past the end of the file.
540  m_bitPos = 0;
542  }
543 
544  // Slide the lowest bit of the bitString into
545  // the correct position.
546  out |= (m_bitString & 1) << (total - numBits);
547 
548  // Shift over to the next bit
549  m_bitString = m_bitString >> 1;
550  ++m_bitPos;
551  --numBits;
552  }
553 
554  return out;
555 }
int m_bitPos
Definition: BinaryInput.h:92
uint8 readUInt8()
Definition: BinaryInput.h:278
#define debugAssert(exp)
Definition: debugAssert.h:160
uint32_t uint32
Definition: Define.h:150
int m_beginEndBits
Definition: BinaryInput.h:101
uint32 m_bitString
Definition: BinaryInput.h:98

+ Here is the call graph for this function:

void G3D::BinaryInput::readBool8 ( )
inline
274  {
275  return (readInt8() != 0);
276  }
int8 readInt8()
Definition: BinaryInput.h:269

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

void G3D::BinaryInput::readBytes ( void *  bytes,
int64  n 
)
336  {
337  prepareToRead(n);
338  debugAssert(isValidPointer(bytes));
339 
340  memcpy(bytes, m_buffer + m_pos, n);
341  m_pos += n;
342 }
uint8 * m_buffer
Definition: BinaryInput.h:117
bool isValidPointer(const void *x)
Definition: debug.h:54
#define debugAssert(exp)
Definition: debugAssert.h:160
int64 m_pos
Definition: BinaryInput.h:122
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

Color3 G3D::BinaryInput::readColor3 ( )
512  {
513  float r = readFloat32();
514  float g = readFloat32();
515  float b = readFloat32();
516  return Color3(r, g, b);
517 }
float32 readFloat32()
Definition: BinaryInput.h:352

+ Here is the call graph for this function:

Color4 G3D::BinaryInput::readColor4 ( )
503  {
504  float r = readFloat32();
505  float g = readFloat32();
506  float b = readFloat32();
507  float a = readFloat32();
508  return Color4(r, g, b, a);
509 }
float32 readFloat32()
Definition: BinaryInput.h:352

+ Here is the call graph for this function:

std::string G3D::BinaryInput::readFixedLengthString ( int  numBytes)

Read a string (which may contain NULLs) of exactly numBytes bytes, including the final terminator if there is one. If there is a NULL in the string before the end, then only the part up to the first NULL is returned although all bytes are read.

228  {
229  Array<char> str;
230  str.resize(numBytes + 1);
231 
232  // Ensure NULL termination
233  str.last() = '\0';
234 
235  readBytes(str.getCArray(), numBytes);
236 
237  // Copy up to the first NULL
238  return std::string(str.getCArray());
239 }
void readBytes(void *bytes, int64 n)
Definition: BinaryInput.cpp:336

+ Here is the call graph for this function:

float32 G3D::BinaryInput::readFloat32 ( )
inline
352  {
353  union {
354  uint32 a;
355  float32 b;
356  };
357  a = readUInt32();
358  return b;
359  }
uint32 readUInt32()
Definition: BinaryInput.h:314
float float32
Definition: g3dmath.h:172
uint32_t uint32
Definition: Define.h:150

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

float64 G3D::BinaryInput::readFloat64 ( )
inline
361  {
362  union {
363  uint64 a;
364  float64 b;
365  };
366  a = readUInt64();
367  return b;
368  }
double float64
Definition: g3dmath.h:173
uint64_t uint64
Definition: Define.h:149
uint64 readUInt64()
Definition: BinaryInput.cpp:346

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int16 G3D::BinaryInput::readInt16 ( )
inline
309  {
310  uint16 a = readUInt16();
311  return *(int16*)&a;
312  }
uint16_t uint16
Definition: Define.h:151
int16_t int16
Definition: Define.h:147
uint16 readUInt16()
Definition: BinaryInput.h:287

+ Here is the call graph for this function:

int32 G3D::BinaryInput::readInt32 ( )
inline
340  {
341  uint32 a = readUInt32();
342  return *(int32*)&a;
343  }
uint32 readUInt32()
Definition: BinaryInput.h:314
int32_t int32
Definition: Define.h:146
uint32_t uint32
Definition: Define.h:150

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int64 G3D::BinaryInput::readInt64 ( )
inline
347  {
348  uint64 a = readUInt64();
349  return *(int64*)&a;
350  }
int64_t int64
Definition: Define.h:145
uint64_t uint64
Definition: Define.h:149
uint64 readUInt64()
Definition: BinaryInput.cpp:346

+ Here is the call graph for this function:

int8 G3D::BinaryInput::readInt8 ( )
inline
269  {
270  prepareToRead(1);
271  return m_buffer[m_pos++];
272  }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64 m_pos
Definition: BinaryInput.h:122
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

std::string G3D::BinaryInput::readString ( int64  maxLength)

Always consumes maxLength characters. Reads a string until NULL or maxLength characters. Does not require NULL termination.

368  {
369  prepareToRead(maxLength);
370 
371  int64 n = 0;
372  while ((m_buffer[m_pos + n] != '\0') && (n != maxLength)) {
373  ++n;
374  }
375 
376  std::string s((char*)(m_buffer + m_pos), n);
377 
378  m_pos += maxLength;
379 
380  return s;
381 }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64_t int64
Definition: Define.h:145
int64 m_pos
Definition: BinaryInput.h:122
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326

+ Here is the call graph for this function:

std::string G3D::BinaryInput::readString ( )

Reads a string until NULL or end of file.

384  {
385  prepareToRead(1);
386 
387  int64 n = 0;
388  bool hasNull = true;
389 
390  while(m_buffer[m_pos + n] != '\0') {
391  ++n;
392 
393  if ((m_pos + m_alreadyRead + n) == m_length) {
394  hasNull = false;
395  break;
396  }
397 
398  prepareToRead(n + 1);
399  }
400 
401  std::string s((char*)(m_buffer + m_pos), n);
402  m_pos += n;
403 
404  if (hasNull) {
405  skip(1);
406  }
407 
408  return s;
409 }
uint8 * m_buffer
Definition: BinaryInput.h:117
void skip(int64 n)
Definition: BinaryInput.h:410
int64_t int64
Definition: Define.h:145
int64 m_length
Definition: BinaryInput.h:113
int64 m_pos
Definition: BinaryInput.h:122
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326
int64 m_alreadyRead
Definition: BinaryInput.h:107

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

std::string G3D::BinaryInput::readString32 ( )

Reads a uint32 and then calls readString(maxLength) with that value as the length.

473  {
474  int len = readUInt32();
475  return readString(len);
476 }
std::string readString()
Definition: BinaryInput.cpp:384
uint32 readUInt32()
Definition: BinaryInput.h:314

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

std::string G3D::BinaryInput::readStringEven ( )

Reads until NULL or the end of the file is encountered. If the string has odd length (including NULL), reads another byte. This is a common format for 16-bit alignment in files.

464  {
465  std::string x = readString();
466  if (hasMore() && (G3D::isOdd((int)x.length() + 1))) {
467  skip(1);
468  }
469  return x;
470 }
void skip(int64 n)
Definition: BinaryInput.h:410
std::string readString()
Definition: BinaryInput.cpp:384
bool isOdd(int num)
Definition: g3dmath.h:790
bool hasMore() const
Definition: BinaryInput.h:417
G3D::int16 x
Definition: Vector2int16.h:37

+ Here is the call graph for this function:

std::string G3D::BinaryInput::readStringNewline ( )

Reads a string until NULL, newline ("&#92;r", "&#92;n", "&#92;r&#92;n", "&#92;n&#92;r") or the end of the file is encountered. Consumes the newline.

415  {
416  prepareToRead(1);
417 
418  int64 n = 0;
419  bool hasNull = true;
420  bool hasNewline = false;
421 
422  while(m_buffer[m_pos + n] != '\0') {
423  if ((m_pos + m_alreadyRead + n + 1) == m_length) {
424  hasNull = false;
425  break;
426  }
427 
428  if (isNewline(m_buffer[m_pos + n])) {
429  hasNull = false;
430  hasNewline = true;
431  break;
432  }
433 
434  ++n;
435  prepareToRead(n + 1);
436  }
437 
438  std::string s((char*)(m_buffer + m_pos), n);
439  m_pos += n;
440 
441  if (hasNull) {
442  skip(1);
443  }
444 
445  if (hasNewline) {
446  if ((m_pos + m_alreadyRead + 2) != m_length) {
447  prepareToRead(2);
448  if (m_buffer[m_pos] == '\r' && m_buffer[m_pos + 1] == '\n') {
449  skip(2);
450  } else if (m_buffer[m_pos] == '\n' && m_buffer[m_pos + 1] == '\r') {
451  skip(2);
452  } else {
453  skip(1);
454  }
455  } else {
456  skip(1);
457  }
458  }
459 
460  return s;
461 }
uint8 * m_buffer
Definition: BinaryInput.h:117
void skip(int64 n)
Definition: BinaryInput.h:410
int64_t int64
Definition: Define.h:145
int64 m_length
Definition: BinaryInput.h:113
bool isNewline(const unsigned char c)
Definition: stringutils.h:157
int64 m_pos
Definition: BinaryInput.h:122
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326
int64 m_alreadyRead
Definition: BinaryInput.h:107

+ Here is the call graph for this function:

uint16 G3D::BinaryInput::readUInt16 ( )
inline
287  {
288  prepareToRead(2);
289 
290  m_pos += 2;
291  if (m_swapBytes) {
292  uint8 out[2];
293  out[0] = m_buffer[m_pos - 1];
294  out[1] = m_buffer[m_pos - 2];
295  return *(uint16*)out;
296  } else {
297  #ifdef G3D_ALLOW_UNALIGNED_WRITES
298  return *(uint16*)(&m_buffer[m_pos - 2]);
299  #else
300  uint8 out[2];
301  out[0] = m_buffer[m_pos - 2];
302  out[1] = m_buffer[m_pos - 1];
303  return *(uint16*)out;
304  #endif
305  }
306 
307  }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64 m_pos
Definition: BinaryInput.h:122
uint16_t uint16
Definition: Define.h:151
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326
bool m_swapBytes
Definition: BinaryInput.h:89
uint8_t uint8
Definition: Define.h:152

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

uint32 G3D::BinaryInput::readUInt32 ( )
inline
314  {
315  prepareToRead(4);
316 
317  m_pos += 4;
318  if (m_swapBytes) {
319  uint8 out[4];
320  out[0] = m_buffer[m_pos - 1];
321  out[1] = m_buffer[m_pos - 2];
322  out[2] = m_buffer[m_pos - 3];
323  out[3] = m_buffer[m_pos - 4];
324  return *(uint32*)out;
325  } else {
326  #ifdef G3D_ALLOW_UNALIGNED_WRITES
327  return *(uint32*)(&m_buffer[m_pos - 4]);
328  #else
329  uint8 out[4];
330  out[0] = m_buffer[m_pos - 4];
331  out[1] = m_buffer[m_pos - 3];
332  out[2] = m_buffer[m_pos - 2];
333  out[3] = m_buffer[m_pos - 1];
334  return *(uint32*)out;
335  #endif
336  }
337  }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64 m_pos
Definition: BinaryInput.h:122
uint32_t uint32
Definition: Define.h:150
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326
bool m_swapBytes
Definition: BinaryInput.h:89
uint8_t uint8
Definition: Define.h:152

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

uint64 G3D::BinaryInput::readUInt64 ( )
346  {
347  prepareToRead(8);
348  uint8 out[8];
349 
350  if (m_swapBytes) {
351  out[0] = m_buffer[m_pos + 7];
352  out[1] = m_buffer[m_pos + 6];
353  out[2] = m_buffer[m_pos + 5];
354  out[3] = m_buffer[m_pos + 4];
355  out[4] = m_buffer[m_pos + 3];
356  out[5] = m_buffer[m_pos + 2];
357  out[6] = m_buffer[m_pos + 1];
358  out[7] = m_buffer[m_pos + 0];
359  } else {
360  *(uint64*)out = *(uint64*)(m_buffer + m_pos);
361  }
362 
363  m_pos += 8;
364  return *(uint64*)out;
365 }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64 m_pos
Definition: BinaryInput.h:122
uint64_t uint64
Definition: Define.h:149
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326
bool m_swapBytes
Definition: BinaryInput.h:89
uint8_t uint8
Definition: Define.h:152

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

uint8 G3D::BinaryInput::readUInt8 ( )
inline
278  {
279  prepareToRead(1);
280  return ((uint8*)m_buffer)[m_pos++];
281  }
uint8 * m_buffer
Definition: BinaryInput.h:117
int64 m_pos
Definition: BinaryInput.h:122
void prepareToRead(int64 nbytes)
Definition: BinaryInput.cpp:326
uint8_t uint8
Definition: Define.h:152

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

unorm8 G3D::BinaryInput::readUNorm8 ( )
inline
283  {
284  return unorm8::fromBits(readUInt8());
285  }
static unorm16 fromBits(uint16 b)
Definition: unorm16.h:43
uint8 readUInt8()
Definition: BinaryInput.h:278

+ Here is the call graph for this function:

Vector2 G3D::BinaryInput::readVector2 ( )
496  {
497  float x = readFloat32();
498  float y = readFloat32();
499  return Vector2(x, y);
500 }
float32 readFloat32()
Definition: BinaryInput.h:352
G3D::int16 y
Definition: Vector2int16.h:38
G3D::int16 x
Definition: Vector2int16.h:37

+ Here is the call graph for this function:

Vector3 G3D::BinaryInput::readVector3 ( )
488  {
489  float x = readFloat32();
490  float y = readFloat32();
491  float z = readFloat32();
492  return Vector3(x, y, z);
493 }
float32 readFloat32()
Definition: BinaryInput.h:352
G3D::int16 z
Definition: Vector3int16.h:46
G3D::int16 y
Definition: Vector2int16.h:38
G3D::int16 x
Definition: Vector2int16.h:37

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

Vector4 G3D::BinaryInput::readVector4 ( )
479  {
480  float x = readFloat32();
481  float y = readFloat32();
482  float z = readFloat32();
483  float w = readFloat32();
484  return Vector4(x, y, z, w);
485 }
float32 readFloat32()
Definition: BinaryInput.h:352
G3D::int16 z
Definition: Vector3int16.h:46
G3D::int16 y
Definition: Vector2int16.h:38
G3D::int16 x
Definition: Vector2int16.h:37

+ Here is the call graph for this function:

void G3D::BinaryInput::reset ( )
inline

Goes back to the beginning of the file.

263  {
264  setPosition(0);
265  }
void setPosition(int64 p)
Definition: BinaryInput.h:252

+ Here is the call graph for this function:

void G3D::BinaryInput::setEndian ( G3DEndian  endian)

Change the endian-ness of the file. This only changes the interpretation of the file for future read calls; the underlying data is unmodified.

272  {
273  m_fileEndian = e;
275 }
G3DEndian m_fileEndian
Definition: BinaryInput.h:86
bool m_swapBytes
Definition: BinaryInput.h:89
static G3DEndian machineEndian()
Definition: System.h:219

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

void G3D::BinaryInput::setPosition ( int64  p)
inline

Sets the position. Cannot set past length. May throw a char* when seeking backwards more than 10 MB on a huge file.

252  {
253  debugAssertM(p <= m_length, "Read past end of file");
254  m_pos = p - m_alreadyRead;
255  if ((m_pos < 0) || (m_pos > m_bufferLength)) {
256  loadIntoMemory(m_pos + m_alreadyRead);
257  }
258  }
#define debugAssertM(exp, message)
Definition: debugAssert.h:161
int64 m_length
Definition: BinaryInput.h:113
void loadIntoMemory(int64 startPosition, int64 minLength=0)
Definition: BinaryInput.cpp:278
int64 m_bufferLength
Definition: BinaryInput.h:116
int64 m_pos
Definition: BinaryInput.h:122
int64 m_alreadyRead
Definition: BinaryInput.h:107

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int64 G3D::BinaryInput::size ( ) const
inline
225  {
226  return getLength();
227  }
int64 getLength() const
Definition: BinaryInput.h:221

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

void G3D::BinaryInput::skip ( int64  n)
inline

Skips ahead n bytes.

410  {
412  }
void setPosition(int64 p)
Definition: BinaryInput.h:252
int64 m_pos
Definition: BinaryInput.h:122
int64 m_alreadyRead
Definition: BinaryInput.h:107

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

Member Data Documentation

const int64 G3D::BinaryInput::INITIAL_BUFFER_LENGTH
staticprivate
Initial value:
=
750000000
int64 G3D::BinaryInput::m_alreadyRead
private

When operating on huge files, we cannot load the whole file into memory. This is the file position to which buffer[0] corresponds. Even 32-bit code can load 64-bit files in chunks, so this is not size_t

int G3D::BinaryInput::m_beginEndBits
private

1 when between beginBits and endBits, 0 otherwise.

int G3D::BinaryInput::m_bitPos
private

Next position to read from in bitString during readBits.

uint32 G3D::BinaryInput::m_bitString
private

Bits currently being read by readBits. Contains at most 8 (low) bits. Note that beginBits/readBits actually consumes one extra byte, which will be restored by writeBits.

uint8* G3D::BinaryInput::m_buffer
private
int64 G3D::BinaryInput::m_bufferLength
private

Length of the array referenced by buffer. May go past the end of the file!

G3DEndian G3D::BinaryInput::m_fileEndian
private

is the file big or little endian

std::string G3D::BinaryInput::m_filename
private
bool G3D::BinaryInput::m_freeBuffer
private

When true, the buffer is freed in the destructor.

int64 G3D::BinaryInput::m_length
private

Length of the entire file, in bytes. For the length of the buffer, see bufferLength

int64 G3D::BinaryInput::m_pos
private

Next byte in file, relative to buffer.

bool G3D::BinaryInput::m_swapBytes
private
const bool G3D::BinaryInput::NO_COPY = false
static

false, constant to use with the copyMemory option


The documentation for this class was generated from the following files: