mirror of
https://github.com/qpdf/qpdf.git
synced 2025-01-22 22:58:33 +00:00
Handle invalid encryption Length (fixes #333)
This commit is contained in:
parent
551dfbf697
commit
c5ed1b8075
@ -1,5 +1,8 @@
|
||||
2019-06-22 Jay Berkenbilt <ejb@ql.org>
|
||||
|
||||
* Handle encrypted files with missing or invalid /Length entries
|
||||
in the encryption dictionary.
|
||||
|
||||
* QPDFWriter: allow calling set*EncryptionParameters before
|
||||
calling setFilename. Fixes #336.
|
||||
|
||||
|
@ -935,22 +935,38 @@ QPDF::initializeEncryption()
|
||||
pad_short_parameter(Perms, Perms_key_bytes_V5);
|
||||
}
|
||||
|
||||
int Length = 40;
|
||||
if (encryption_dict.getKey("/Length").isInteger())
|
||||
int Length = 0;
|
||||
if (V <= 1)
|
||||
{
|
||||
Length = encryption_dict.getKey("/Length").getIntValueAsInt();
|
||||
if (R < 3)
|
||||
Length = 40;
|
||||
}
|
||||
else if (V == 4)
|
||||
{
|
||||
Length = 128;
|
||||
}
|
||||
else if (V == 5)
|
||||
{
|
||||
Length = 256;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (encryption_dict.getKey("/Length").isInteger())
|
||||
{
|
||||
// Force Length to 40 regardless of what the file says.
|
||||
Length = 40;
|
||||
Length = encryption_dict.getKey("/Length").getIntValueAsInt();
|
||||
if ((Length % 8) || (Length < 40) || (Length > 128))
|
||||
{
|
||||
Length = 0;
|
||||
}
|
||||
}
|
||||
if ((Length % 8) || (Length < 40) || (Length > 256))
|
||||
{
|
||||
throw QPDFExc(qpdf_e_damaged_pdf, this->m->file->getName(),
|
||||
"encryption dictionary",
|
||||
this->m->file->getLastOffset(),
|
||||
"invalid /Length value in encryption dictionary");
|
||||
}
|
||||
if (Length == 0)
|
||||
{
|
||||
Length = 128;
|
||||
}
|
||||
}
|
||||
if (Length == 0)
|
||||
{
|
||||
// Still no Length? Just take a guess.
|
||||
Length = 128;
|
||||
}
|
||||
|
||||
this->m->encp->encrypt_metadata = true;
|
||||
|
@ -4353,6 +4353,14 @@ print "\n";
|
||||
segmentation fault.
|
||||
</para>
|
||||
</listitem>
|
||||
<listitem>
|
||||
<para>
|
||||
When reading encrypted files, follow the spec more closely
|
||||
regarding encryption key length. This allows qpdf to open
|
||||
encrypted files in most cases when they have invalid or
|
||||
missing /Length keys in the encryption dictionary.
|
||||
</para>
|
||||
</listitem>
|
||||
</itemizedlist>
|
||||
</listitem>
|
||||
<listitem>
|
||||
|
@ -3523,7 +3523,7 @@ foreach my $d (@enc_key)
|
||||
}
|
||||
|
||||
# Miscellaneous encryption tests
|
||||
$n_tests += 2;
|
||||
$n_tests += 3;
|
||||
|
||||
$td->runtest("set encryption before set filename",
|
||||
{$td->COMMAND => "test_driver 63 minimal.pdf"},
|
||||
@ -3534,6 +3534,11 @@ $td->runtest("check file's validity",
|
||||
{$td->FILE => "encrypt-before-filename.out",
|
||||
$td->EXIT_STATUS => 0},
|
||||
$td->NORMALIZE_NEWLINES);
|
||||
$td->runtest("handle missing/invalid Length",
|
||||
{$td->COMMAND => "qpdf --check bad-encryption-length.pdf"},
|
||||
{$td->FILE => "bad-encryption-length.out",
|
||||
$td->EXIT_STATUS => 0},
|
||||
$td->NORMALIZE_NEWLINES);
|
||||
|
||||
show_ntests();
|
||||
# ----------
|
||||
|
17
qpdf/qtest/qpdf/bad-encryption-length.out
Normal file
17
qpdf/qtest/qpdf/bad-encryption-length.out
Normal file
@ -0,0 +1,17 @@
|
||||
checking bad-encryption-length.pdf
|
||||
PDF Version: 1.4
|
||||
R = 3
|
||||
P = -4
|
||||
User password =
|
||||
extract for accessibility: allowed
|
||||
extract for any purpose: allowed
|
||||
print low resolution: allowed
|
||||
print high resolution: allowed
|
||||
modify document assembly: allowed
|
||||
modify forms: allowed
|
||||
modify annotations: allowed
|
||||
modify other: allowed
|
||||
modify anything: allowed
|
||||
File is not linearized
|
||||
No syntax or stream encoding errors found; the file may still contain
|
||||
errors that qpdf cannot detect
|
39
qpdf/qtest/qpdf/bad-encryption-length.pdf
Normal file
39
qpdf/qtest/qpdf/bad-encryption-length.pdf
Normal file
@ -0,0 +1,39 @@
|
||||
%PDF-1.4
|
||||
%¿÷¢þ
|
||||
1 0 obj
|
||||
<< /Pages 2 0 R /Type /Catalog >>
|
||||
endobj
|
||||
2 0 obj
|
||||
<< /Count 1 /Kids [ 3 0 R ] /Type /Pages >>
|
||||
endobj
|
||||
3 0 obj
|
||||
<< /Contents 4 0 R /MediaBox [ 0 0 612 792 ] /Parent 2 0 R /Resources << /Font << /F1 5 0 R >> /ProcSet 6 0 R >> /Type /Page >>
|
||||
endobj
|
||||
4 0 obj
|
||||
<< /Length 48 /Filter /FlateDecode >>
|
||||
stream
|
||||
u|+»[ –ØÄksBþSX¼A*–¥O¨<<3C>®"<22>
J(<28>V¡¢zÉüL[}-šendstream
|
||||
endobj
|
||||
5 0 obj
|
||||
<< /BaseFont /Helvetica /Encoding /WinAnsiEncoding /Name /F1 /Subtype /Type1 /Type /Font >>
|
||||
endobj
|
||||
6 0 obj
|
||||
[ /PDF /Text ]
|
||||
endobj
|
||||
7 0 obj
|
||||
<< /Filter /Standard /Wength 128 /O <77b8fb098022d3ab34237ea5643c08710ea5123fc5f88bf993a68cca5f12b40f> /P -4 /R 3 /U <72ba254904669105f93c01524fceaa320122456a91bae5134273a6db134c87c4> /V 2 >>
|
||||
endobj
|
||||
xref
|
||||
0 8
|
||||
0000000000 65535 f
|
||||
0000000015 00000 n
|
||||
0000000064 00000 n
|
||||
0000000123 00000 n
|
||||
0000000266 00000 n
|
||||
0000000384 00000 n
|
||||
0000000491 00000 n
|
||||
0000000521 00000 n
|
||||
trailer << /Root 1 0 R /Size 8 /ID [<2dc7d3d0f5f5b44e5b39ff85e8a4f70c><2dc7d3d0f5f5b44e5b39ff85e8a4f70c>] /Encrypt 7 0 R >>
|
||||
startxref
|
||||
728
|
||||
%%EOF
|
Loading…
x
Reference in New Issue
Block a user