/* * Copyright 2011 Google Inc. * * Use of this source code is governed by a BSD-style license that can be * found in the LICENSE file. */ #include <stdlib.h> #include <string.h> #include "SkData.h" #include "SkFlate.h" #include "SkStream.h" #include "Test.h" // A memory stream that reports zero size with the standard call, like // an unseekable file stream would. class SkZeroSizeMemStream : public SkMemoryStream { public: virtual size_t read(void* buffer, size_t size) { if (buffer == NULL && size == 0) return 0; if (buffer == NULL && size == kGetSizeKey) size = 0; return SkMemoryStream::read(buffer, size); } static const size_t kGetSizeKey = 0xDEADBEEF; }; static void TestFlate(skiatest::Reporter* reporter, SkMemoryStream* testStream, size_t dataSize) { if (testStream == NULL) return; SkMemoryStream testData(dataSize); uint8_t* data = (uint8_t*)testData.getMemoryBase(); srand(0); // Make data deterministic. for (size_t i = 0; i < dataSize; i++) data[i] = rand() & 0xFF; testStream->setMemory(testData.getMemoryBase(), dataSize, true); SkDynamicMemoryWStream compressed; bool status = SkFlate::Deflate(testStream, &compressed); REPORTER_ASSERT(reporter, status); // Check that the input data wasn't changed. size_t inputSize = testStream->getLength(); if (inputSize == 0) inputSize = testStream->read(NULL, SkZeroSizeMemStream::kGetSizeKey); REPORTER_ASSERT(reporter, testData.getLength() == inputSize); REPORTER_ASSERT(reporter, memcmp(testData.getMemoryBase(), testStream->getMemoryBase(), testData.getLength()) == 0); // Assume there are two test sizes, big and small. if (dataSize < 1024) REPORTER_ASSERT(reporter, compressed.getOffset() < 1024); else REPORTER_ASSERT(reporter, compressed.getOffset() > 1024); SkAutoDataUnref data1(compressed.copyToData()); testStream->setData(data1.get())->unref(); SkDynamicMemoryWStream uncompressed; status = SkFlate::Inflate(testStream, &uncompressed); REPORTER_ASSERT(reporter, status); // Check that the input data wasn't changed. inputSize = testStream->getLength(); if (inputSize == 0) inputSize = testStream->read(NULL, SkZeroSizeMemStream::kGetSizeKey); REPORTER_ASSERT(reporter, data1->size() == inputSize); REPORTER_ASSERT(reporter, memcmp(testStream->getMemoryBase(), data1->data(), data1->size()) == 0); // Check that the uncompressed data matches the source data. SkAutoDataUnref data2(uncompressed.copyToData()); REPORTER_ASSERT(reporter, testData.getLength() == uncompressed.getOffset()); REPORTER_ASSERT(reporter, memcmp(testData.getMemoryBase(), data2->data(), testData.getLength()) == 0); } DEF_TEST(Flate, reporter) { TestFlate(reporter, NULL, 0); #if defined(SK_ZLIB_INCLUDE) && !defined(SK_DEBUG) REPORTER_ASSERT(reporter, SkFlate::HaveFlate()); SkMemoryStream memStream; TestFlate(reporter, &memStream, 512); TestFlate(reporter, &memStream, 10240); SkZeroSizeMemStream fileStream; TestFlate(reporter, &fileStream, 512); TestFlate(reporter, &fileStream, 10240); #endif }