| Index: src/core/SkSecureReader32.cpp
|
| diff --git a/src/core/SkSecureReader32.cpp b/src/core/SkSecureReader32.cpp
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..e630fcb37776aed2fc10cf2ead43ac62b6a3565c
|
| --- /dev/null
|
| +++ b/src/core/SkSecureReader32.cpp
|
| @@ -0,0 +1,136 @@
|
| +/*
|
| + * Copyright 2013 Google Inc.
|
| + *
|
| + * Use of this source code is governed by a BSD-style license that can be
|
| + * found in the LICENSE file.
|
| + */
|
| +
|
| +///////////////////////////////////////////////////////////////////////////////
|
| +
|
| +#include "SkSecureReader32.h"
|
| +#include "SkString.h"
|
| +
|
| +SkSecureReader32::SkSecureReader32() : fCurr(NULL), fStop(NULL), fBase(NULL), fError(false) {
|
| +}
|
| +
|
| +SkSecureReader32::SkSecureReader32(const void* data, size_t size) : fError(false) {
|
| + this->setMemory(data, size);
|
| +}
|
| +
|
| +void SkSecureReader32::setMemory(const void* data, size_t size) {
|
| + fError |= (!ptr_align_4(data) || (SkAlign4(size) != size));
|
| + SkASSERT(!fError);
|
| +
|
| + fBase = fCurr = (const char*)data;
|
| + fStop = (const char*)data + size;
|
| +}
|
| +
|
| +uint32_t SkSecureReader32::size() const {
|
| + return SkToU32(fStop - fBase);
|
| +}
|
| +
|
| +uint32_t SkSecureReader32::offset() const {
|
| + return SkToU32(fCurr - fBase);
|
| +}
|
| +
|
| +bool SkSecureReader32::eof() const {
|
| + return fCurr >= fStop;
|
| +}
|
| +
|
| +const void* SkSecureReader32::base() const {
|
| + return fBase;
|
| +}
|
| +
|
| +const void* SkSecureReader32::peek() const {
|
| + return fCurr;
|
| +}
|
| +
|
| +bool SkSecureReader32::isAvailable(uint32_t size) const {
|
| + return fCurr + size <= fStop;
|
| +}
|
| +
|
| +bool SkSecureReader32::readBool() {
|
| + return this->readInt() != 0;
|
| +}
|
| +
|
| +int32_t SkSecureReader32::readInt() {
|
| + int32_t value = 0;
|
| + size_t inc = sizeof(value);
|
| + fError |= !ptr_align_4(fCurr) || !this->isAvailable(inc);
|
| + if (!fError) {
|
| + value = *(const int32_t*)fCurr;
|
| + fCurr += inc;
|
| + }
|
| + return value;
|
| +}
|
| +
|
| +SkScalar SkSecureReader32::readScalar() {
|
| + SkScalar value = 0;
|
| + size_t inc = sizeof(value);
|
| + fError |= !ptr_align_4(fCurr) || !this->isAvailable(inc);
|
| + if (!fError) {
|
| + value = *(const SkScalar*)fCurr;
|
| + fCurr += inc;
|
| + }
|
| + return value;
|
| +}
|
| +
|
| +const void* SkSecureReader32::skip(size_t size) {
|
| + size_t inc = SkAlign4(size);
|
| + fError |= !ptr_align_4(fCurr) || !this->isAvailable(inc);
|
| + const void* addr = fCurr;
|
| + if (!fError) {
|
| + fCurr += inc;
|
| + }
|
| + return addr;
|
| +}
|
| +
|
| +int32_t SkSecureReader32::readS32() {
|
| + return this->readInt();
|
| +}
|
| +
|
| +uint32_t SkSecureReader32::readU32() {
|
| + return this->readInt();
|
| +}
|
| +
|
| +void SkSecureReader32::readPath(SkPath* path) {
|
| + size_t size = path->readFromMemory(this->peek());
|
| + fError |= (SkAlign4(size) != size);
|
| + if (!fError) {
|
| + (void)this->skip(size);
|
| + }
|
| +}
|
| +
|
| +void SkSecureReader32::readMatrix(SkMatrix* matrix) {
|
| + size_t size = matrix->readFromMemory(this->peek());
|
| + fError |= (SkAlign4(size) != size);
|
| + if (!fError) {
|
| + (void)this->skip(size);
|
| + }
|
| +}
|
| +
|
| +void SkSecureReader32::readRegion(SkRegion* rgn) {
|
| + size_t size = rgn->readFromMemory(this->peek());
|
| + fError |= (SkAlign4(size) != size);
|
| + if (!fError) {
|
| + (void)this->skip(size);
|
| + }
|
| +}
|
| +
|
| +/*
|
| + * Strings are stored as: length[4-bytes] + string_data + '\0' + pad_to_mul_4
|
| + */
|
| +
|
| +const char* SkSecureReader32::readString(size_t* outLen) {
|
| + size_t len = this->readInt();
|
| + const void* ptr = this->peek();
|
| +
|
| + // skip over the string + '\0' and then pad to a multiple of 4
|
| + size_t alignedSize = SkAlign4(len + 1);
|
| + this->skip(alignedSize);
|
| +
|
| + if (outLen) {
|
| + *outLen = fError ? 0 : len;
|
| + }
|
| + return fError ? NULL : (const char*)ptr;
|
| +}
|
|
|