Fix null pointer issue on array copy

This commit is contained in:
Jay Berkenbilt 2024-01-12 07:11:46 -05:00
parent 2c97aaddd5
commit ebb10f3256
7 changed files with 24 additions and 4 deletions

View File

@ -109,7 +109,9 @@ set(CORPUS_OTHER
28262.fuzz
30507.fuzz
37740.fuzz
57639.fuzz)
57639.fuzz
65681.fuzz
)
set(CORPUS_DIR ${CMAKE_CURRENT_BINARY_DIR}/qpdf_corpus)
file(MAKE_DIRECTORY ${CORPUS_DIR})

BIN
fuzz/qpdf_extra/65681.fuzz Normal file

Binary file not shown.

View File

@ -20,7 +20,7 @@ my @fuzzers = (
['pngpredictor' => 1],
['runlength' => 6],
['tiffpredictor' => 1],
['qpdf' => 53], # increment when adding new files
['qpdf' => 54], # increment when adding new files
);
my $n_tests = 0;

View File

@ -1,5 +1,6 @@
#include <qpdf/QPDF_Array.hh>
#include <qpdf/QTC.hh>
#include <qpdf/QPDFObjectHandle.hh>
#include <qpdf/QPDFObject_private.hh>
@ -74,8 +75,10 @@ QPDF_Array::copy(bool shallow)
if (shallow) {
return do_create(new QPDF_Array(*this));
} else {
QTC::TC("qpdf", "QPDF_Array copy", sp ? 0 : 1);
if (sp) {
auto* result = new QPDF_Array();
result->sp = std::make_unique<Sparse>();
result->sp->size = sp->size;
for (auto const& element: sp->elements) {
auto const& obj = element.second;

View File

@ -692,3 +692,4 @@ QPDF recover xref stream 0
QPDFJob misplaced page range 0
QPDFJob duplicated range 0
QPDFJob json over/under no file 0
QPDF_Array copy 1

View File

@ -29,5 +29,9 @@ $td->runtest("run check file",
{$td->COMMAND => "qpdf --check a.pdf"},
{$td->FILE => "many-nulls.out", $td->EXIT_STATUS => 0},
$td->NORMALIZE_NEWLINES);
$td->runtest("copy sparse array",
{$td->COMMAND => "test_driver 97 many-nulls.pdf"},
{$td->STRING => "test 97 done\n", $td->EXIT_STATUS => 0},
$td->NORMALIZE_NEWLINES);
cleanup();
$td->report(3);
$td->report(4);

View File

@ -3366,6 +3366,16 @@ test_96(QPDF& pdf, char const* arg2)
assert(s.unparseBinary() == "<abc0>");
}
static void
test_97(QPDF& pdf, char const* arg2)
{
// Shallow array copy. This test uses many-nulls.pdf.
auto nulls = pdf.getTrailer().getKey("/Nulls").getArrayItem(0);
assert(nulls.isArray() && nulls.getArrayNItems() > 10000);
auto nulls2 = nulls.shallowCopy();
assert(nulls.unparse() == nulls2.unparse());
}
void
runtest(int n, char const* filename1, char const* arg2)
{
@ -3467,7 +3477,7 @@ runtest(int n, char const* filename1, char const* arg2)
{78, test_78}, {79, test_79}, {80, test_80}, {81, test_81}, {82, test_82}, {83, test_83},
{84, test_84}, {85, test_85}, {86, test_86}, {87, test_87}, {88, test_88}, {89, test_89},
{90, test_90}, {91, test_91}, {92, test_92}, {93, test_93}, {94, test_94}, {95, test_95},
{96, test_96}};
{96, test_96}, {97, test_97}};
auto fn = test_functions.find(n);
if (fn == test_functions.end()) {