180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru/* 380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * Copyright 2006 The Android Open Source Project 480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * 580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * Use of this source code is governed by a BSD-style license that can be 680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * found in the LICENSE file. 780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 1080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#ifndef SkBuffer_DEFINED 1180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#define SkBuffer_DEFINED 1280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 1380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkScalar.h" 1480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 1580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru/** \class SkRBuffer 1680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 1780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru Light weight class for reading data from a memory block. 1880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru The RBuffer is given the buffer to read from, with either a specified size 1980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru or no size (in which case no range checking is performed). It is iillegal 2080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru to attempt to read a value from an empty RBuffer (data == null). 2180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru*/ 2280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruclass SkRBuffer : SkNoncopyable { 2380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querupublic: 2480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkRBuffer() : fData(0), fPos(0), fStop(0) {} 2580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru /** Initialize RBuffer with a data pointer, but no specified length. 2680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru This signals the RBuffer to not perform range checks during reading. 2780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 2880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkRBuffer(const void* data) { 2980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fData = (const char*)data; 3080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fPos = (const char*)data; 3180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fStop = 0; // no bounds checking 3280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 3380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru /** Initialize RBuffer with a data point and length. 3480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 3580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkRBuffer(const void* data, size_t size) { 3680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkASSERT(data != 0 || size == 0); 3780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fData = (const char*)data; 3880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fPos = (const char*)data; 3980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fStop = (const char*)data + size; 4080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 4180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 42910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger virtual ~SkRBuffer() { } 43910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger 4480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru /** Return the number of bytes that have been read from the beginning 4580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru of the data pointer. 4680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 4780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru size_t pos() const { return fPos - fData; } 4880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru /** Return the total size of the data pointer. Only defined if the length was 4980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru specified in the constructor or in a call to reset(). 5080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 5180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru size_t size() const { return fStop - fData; } 5280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru /** Return true if the buffer has read to the end of the data pointer. 5380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru Only defined if the length was specified in the constructor or in a call 5480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru to reset(). Always returns true if the length was not specified. 5580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 5680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru bool eof() const { return fPos >= fStop; } 5780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 5880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru /** Read the specified number of bytes from the data pointer. If buffer is not 5980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru null, copy those bytes into buffer. 6080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */ 61910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger virtual bool read(void* buffer, size_t size) { 6280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru if (size) { 6380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru this->readNoSizeCheck(buffer, size); 6480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 65910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger return true; 6680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 6780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 6880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru const void* skip(size_t size); // return start of skipped data 6980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru size_t skipToAlign4(); 7080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 71910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readPtr(void** ptr) { return read(ptr, sizeof(void*)); } 72910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readScalar(SkScalar* x) { return read(x, 4); } 73910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readU32(uint32_t* x) { return read(x, 4); } 74910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readS32(int32_t* x) { return read(x, 4); } 75910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readU16(uint16_t* x) { return read(x, 2); } 76910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readS16(int16_t* x) { return read(x, 2); } 77910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readU8(uint8_t* x) { return read(x, 1); } 78910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool readBool(bool* x) { 79910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger uint8_t u8; 80910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger if (this->readU8(&u8)) { 81910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger *x = (u8 != 0); 82910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger return true; 83910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger } 84910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger return false; 85910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger } 8680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 87910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenbergerprotected: 8880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void readNoSizeCheck(void* buffer, size_t size); 8980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 9080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru const char* fData; 9180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru const char* fPos; 9280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru const char* fStop; 9380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}; 9480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 95910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger/** \class SkRBufferWithSizeCheck 96910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger 97910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger Same as SkRBuffer, except that a size check is performed before the read operation and an 98910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger error is set if the read operation is attempting to read past the end of the data. 99910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger*/ 100910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenbergerclass SkRBufferWithSizeCheck : public SkRBuffer { 101910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenbergerpublic: 102910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger SkRBufferWithSizeCheck(const void* data, size_t size) : SkRBuffer(data, size), fError(false) {} 103910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger 104910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger /** Read the specified number of bytes from the data pointer. If buffer is not 105910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger null and the number of bytes to read does not overflow this object's data, 106910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger copy those bytes into buffer. 107910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger */ 108910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger virtual bool read(void* buffer, size_t size) SK_OVERRIDE; 109910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger 110910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger /** Returns whether or not a read operation attempted to read past the end of the data. 111910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger */ 112910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool isValid() const { return !fError; } 113910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenbergerprivate: 114910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger bool fError; 115910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger}; 116910f694aefb0b671dd8522a9afe9b6be645701c1Derek Sollenberger 11780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru/** \class SkWBuffer 11880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 11980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru Light weight class for writing data to a memory block. 12080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru The WBuffer is given the buffer to write into, with either a specified size 12180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru or no size, in which case no range checking is performed. An empty WBuffer 12280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru is legal, in which case no data is ever written, but the relative pos() 12380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru is updated. 12480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru*/ 12580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruclass SkWBuffer : SkNoncopyable { 12680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querupublic: 12780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkWBuffer() : fData(0), fPos(0), fStop(0) {} 12880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkWBuffer(void* data) { reset(data); } 12980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkWBuffer(void* data, size_t size) { reset(data, size); } 13080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 13180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void reset(void* data) { 13280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fData = (char*)data; 13380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fPos = (char*)data; 13480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fStop = 0; // no bounds checking 13580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 13680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 13780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void reset(void* data, size_t size) { 13880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru SkASSERT(data != 0 || size == 0); 13980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fData = (char*)data; 14080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fPos = (char*)data; 14180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru fStop = (char*)data + size; 14280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 14380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 14480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru size_t pos() const { return fPos - fData; } 14580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void* skip(size_t size); // return start of skipped data 14680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 14780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void write(const void* buffer, size_t size) { 14880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru if (size) { 14980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru this->writeNoSizeCheck(buffer, size); 15080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 15180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru } 15280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 15380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru size_t padToAlign4(); 15480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 15580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void writePtr(const void* x) { this->writeNoSizeCheck(&x, sizeof(x)); } 15680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void writeScalar(SkScalar x) { this->writeNoSizeCheck(&x, 4); } 15780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void write32(int32_t x) { this->writeNoSizeCheck(&x, 4); } 15880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void write16(int16_t x) { this->writeNoSizeCheck(&x, 2); } 15980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void write8(int8_t x) { this->writeNoSizeCheck(&x, 1); } 16080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void writeBool(bool x) { this->write8(x); } 16180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 16280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queruprivate: 16380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru void writeNoSizeCheck(const void* buffer, size_t size); 16480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 16580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru char* fData; 16680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru char* fPos; 16780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru char* fStop; 16880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}; 16980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru 17080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#endif 171