Commit 8b3797569d0b09bf358e344136ce4d8a60e7a214

Authored by m-holger
1 parent 71077f11

Add new method QPDFParser::make_description

Avoid creating new identical descriptions for each content stream token.
libqpdf/QPDFObjectHandle.cc
@@ -1621,6 +1621,7 @@ QPDFObjectHandle::parseContentStream_data( @@ -1621,6 +1621,7 @@ QPDFObjectHandle::parseContentStream_data(
1621 auto input = BufferInputSource(description, stream_data.get()); 1621 auto input = BufferInputSource(description, stream_data.get());
1622 Tokenizer tokenizer; 1622 Tokenizer tokenizer;
1623 tokenizer.allowEOF(); 1623 tokenizer.allowEOF();
  1624 + auto sp_description = QPDFParser::make_description(description, "content");
1624 bool empty = false; 1625 bool empty = false;
1625 while (QIntC::to_size(input.tell()) < stream_length) { 1626 while (QIntC::to_size(input.tell()) < stream_length) {
1626 // Read a token and seek to the beginning. The offset we get from this process is the 1627 // Read a token and seek to the beginning. The offset we get from this process is the
@@ -1630,7 +1631,7 @@ QPDFObjectHandle::parseContentStream_data( @@ -1630,7 +1631,7 @@ QPDFObjectHandle::parseContentStream_data(
1630 qpdf_offset_t offset = input.getLastOffset(); 1631 qpdf_offset_t offset = input.getLastOffset();
1631 input.seek(offset, SEEK_SET); 1632 input.seek(offset, SEEK_SET);
1632 auto obj = 1633 auto obj =
1633 - QPDFParser(input, "content", tokenizer, nullptr, context, false).parse(empty, true); 1634 + QPDFParser(input, sp_description, "content", tokenizer, context).parse(empty, true);
1634 if (!obj) { 1635 if (!obj) {
1635 // EOF 1636 // EOF
1636 break; 1637 break;
libqpdf/qpdf/QPDFParser.hh
@@ -26,9 +26,7 @@ class QPDFParser @@ -26,9 +26,7 @@ class QPDFParser
26 tokenizer(*tokenizer.m), 26 tokenizer(*tokenizer.m),
27 decrypter(decrypter), 27 decrypter(decrypter),
28 context(context), 28 context(context),
29 - description(  
30 - std::make_shared<QPDFObject::Description>(  
31 - std::string(input.getName() + ", " + object_description + " at offset $PO"))), 29 + description(make_description(input.getName(), object_description)),
32 parse_pdf(parse_pdf) 30 parse_pdf(parse_pdf)
33 { 31 {
34 } 32 }
@@ -45,16 +43,39 @@ class QPDFParser @@ -45,16 +43,39 @@ class QPDFParser
45 tokenizer(tokenizer), 43 tokenizer(tokenizer),
46 decrypter(decrypter), 44 decrypter(decrypter),
47 context(context), 45 context(context),
48 - description(  
49 - std::make_shared<QPDFObject::Description>(  
50 - std::string(input.getName() + ", " + object_description + " at offset $PO"))), 46 + description(make_description(input.getName(), object_description)),
51 parse_pdf(parse_pdf) 47 parse_pdf(parse_pdf)
52 { 48 {
53 } 49 }
  50 +
  51 + // Used by parseContentStream_data only
  52 + QPDFParser(
  53 + InputSource& input,
  54 + std::shared_ptr<QPDFObject::Description> sp_description,
  55 + std::string const& object_description,
  56 + qpdf::Tokenizer& tokenizer,
  57 + QPDF* context) :
  58 + input(input),
  59 + object_description(object_description),
  60 + tokenizer(tokenizer),
  61 + decrypter(nullptr),
  62 + context(context),
  63 + description(std::move(sp_description)),
  64 + parse_pdf(false)
  65 + {
  66 + }
54 ~QPDFParser() = default; 67 ~QPDFParser() = default;
55 68
56 QPDFObjectHandle parse(bool& empty, bool content_stream); 69 QPDFObjectHandle parse(bool& empty, bool content_stream);
57 70
  71 + static std::shared_ptr<QPDFObject::Description>
  72 + make_description(std::string const& input_name, std::string const& object_description)
  73 + {
  74 + using namespace std::literals;
  75 + return std::make_shared<QPDFObject::Description>(
  76 + input_name + ", " + object_description + " at offset $PO");
  77 + }
  78 +
58 private: 79 private:
59 // Parser state. Note: 80 // Parser state. Note:
60 // state <= st_dictionary_value == (state = st_dictionary_key || state = st_dictionary_value) 81 // state <= st_dictionary_value == (state = st_dictionary_key || state = st_dictionary_value)