| Index: testing/libfuzzer/pdf_hint_table_fuzzer.cc
|
| diff --git a/testing/libfuzzer/pdf_hint_table_fuzzer.cc b/testing/libfuzzer/pdf_hint_table_fuzzer.cc
|
| index b01c87216b694bded3cfdeb79125d25aa2859037..ec51517fc00b8d954e5696590b0048aa338c61b0 100644
|
| --- a/testing/libfuzzer/pdf_hint_table_fuzzer.cc
|
| +++ b/testing/libfuzzer/pdf_hint_table_fuzzer.cc
|
| @@ -4,18 +4,11 @@
|
|
|
| #include <cstdint>
|
|
|
| +#include "core/fpdfapi/parser/cpdf_array.h"
|
| #include "core/fpdfapi/parser/cpdf_dictionary.h"
|
| #include "core/fpdfapi/parser/cpdf_hint_tables.h"
|
| -
|
| -struct DummyLinearizedDictionary {
|
| - int end_of_first_page_offset;
|
| - int number_of_pages;
|
| - int first_page_object_number;
|
| - int first_page_number;
|
| - int primary_hint_stream_offset;
|
| - int primary_hint_stream_length;
|
| - int shared_hint_table_offset;
|
| -};
|
| +#include "core/fpdfapi/parser/cpdf_linearized.h"
|
| +#include "third_party/base/ptr_util.h"
|
|
|
| int32_t GetData(const int32_t** data32, const uint8_t** data, size_t* size) {
|
| const int32_t* ret = *data32;
|
| @@ -27,64 +20,70 @@ int32_t GetData(const int32_t** data32, const uint8_t** data, size_t* size) {
|
|
|
| class HintTableForFuzzing : public CPDF_HintTables {
|
| public:
|
| - HintTableForFuzzing(DummyLinearizedDictionary* dict,
|
| - CPDF_Dictionary* linearized_dict)
|
| - : CPDF_HintTables(nullptr, linearized_dict), dict_(dict) {}
|
| + HintTableForFuzzing(CPDF_Linearized* pLinearized,
|
| + int shared_hint_table_offset)
|
| + : CPDF_HintTables(nullptr, pLinearized),
|
| + shared_hint_table_offset_(shared_hint_table_offset) {}
|
| ~HintTableForFuzzing() {}
|
|
|
| void Fuzz(const uint8_t* data, size_t size) {
|
| - if (dict_->shared_hint_table_offset <= 0)
|
| + if (shared_hint_table_offset_ <= 0)
|
| return;
|
|
|
| - if (size < static_cast<size_t>(dict_->shared_hint_table_offset))
|
| + if (size < static_cast<size_t>(shared_hint_table_offset_))
|
| return;
|
|
|
| CFX_BitStream bs;
|
| bs.Init(data, size);
|
| if (!ReadPageHintTable(&bs))
|
| return;
|
| - ReadSharedObjHintTable(&bs, dict_->shared_hint_table_offset);
|
| + ReadSharedObjHintTable(&bs, shared_hint_table_offset_);
|
| }
|
|
|
| private:
|
| - int GetEndOfFirstPageOffset() const override {
|
| - return dict_->end_of_first_page_offset;
|
| - }
|
| - int GetNumberOfPages() const override { return dict_->number_of_pages; }
|
| - int GetFirstPageObjectNumber() const override {
|
| - return dict_->first_page_object_number;
|
| - }
|
| - int GetFirstPageNumber() const override { return dict_->first_page_number; }
|
| - int ReadPrimaryHintStreamOffset() const override {
|
| - return dict_->primary_hint_stream_offset;
|
| - }
|
| - int ReadPrimaryHintStreamLength() const override {
|
| - return dict_->primary_hint_stream_length;
|
| - }
|
| + int shared_hint_table_offset_;
|
| +};
|
|
|
| - DummyLinearizedDictionary* const dict_;
|
| +class FakeLinearized : public CPDF_Linearized {
|
| + public:
|
| + explicit FakeLinearized(CPDF_Dictionary* linearized_dict)
|
| + : CPDF_Linearized(linearized_dict) {}
|
| };
|
|
|
| extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
|
| - // Need 28 bytes for |dummy_dict|.
|
| + // Need 28 bytes for |linearized_dict|.
|
| // The header section of page offset hint table is 36 bytes.
|
| // The header section of shared object hint table is 24 bytes.
|
| if (size < 28 + 36 + 24)
|
| return 0;
|
|
|
| const int32_t* data32 = reinterpret_cast<const int32_t*>(data);
|
| - DummyLinearizedDictionary dummy_dict;
|
| - dummy_dict.end_of_first_page_offset = GetData(&data32, &data, &size);
|
| - dummy_dict.number_of_pages = GetData(&data32, &data, &size);
|
| - dummy_dict.first_page_object_number = GetData(&data32, &data, &size);
|
| - dummy_dict.first_page_number = GetData(&data32, &data, &size);
|
| - dummy_dict.primary_hint_stream_offset = GetData(&data32, &data, &size);
|
| - dummy_dict.primary_hint_stream_length = GetData(&data32, &data, &size);
|
| - dummy_dict.shared_hint_table_offset = GetData(&data32, &data, &size);
|
|
|
| - std::unique_ptr<CPDF_Dictionary> dummy_linearized_dict(new CPDF_Dictionary);
|
| + auto linearized_dict = pdfium::MakeUnique<CPDF_Dictionary>();
|
| + // Set initial value.
|
| + linearized_dict->SetBooleanFor("Linearized", true);
|
| + // Set first page end offset
|
| + linearized_dict->SetIntegerFor("E", GetData(&data32, &data, &size));
|
| + // Set page count
|
| + linearized_dict->SetIntegerFor("N", GetData(&data32, &data, &size));
|
| + // Set first page obj num
|
| + linearized_dict->SetIntegerFor("O", GetData(&data32, &data, &size));
|
| + // Set first page no
|
| + linearized_dict->SetIntegerFor("P", GetData(&data32, &data, &size));
|
| +
|
| + auto hint_info = pdfium::MakeUnique<CPDF_Array>();
|
| + // Add primary hint stream offset
|
| + hint_info->AddInteger(GetData(&data32, &data, &size));
|
| + // Add primary hint stream size
|
| + hint_info->AddInteger(GetData(&data32, &data, &size));
|
| + // Set hint stream info.
|
| + linearized_dict->SetFor("H", hint_info.release());
|
| +
|
| + const int shared_hint_table_offset = GetData(&data32, &data, &size);
|
| +
|
| {
|
| - HintTableForFuzzing hint_table(&dummy_dict, dummy_linearized_dict.get());
|
| + FakeLinearized linearized(linearized_dict.get());
|
| + HintTableForFuzzing hint_table(&linearized, shared_hint_table_offset);
|
| hint_table.Fuzz(data, size);
|
| }
|
| return 0;
|
|
|