Skip to content

Commit fb7d73a

Browse files
committed
PDFBOX-6189: Safely validate dimension to avoid OOM, by subbudvk; closes #437
git-svn-id: https://svn.apache.org/repos/asf/pdfbox/trunk@1932958 13f79535-47bb-0310-9956-ffa450edef68
1 parent da1f7b7 commit fb7d73a

2 files changed

Lines changed: 47 additions & 2 deletions

File tree

pdfbox/src/main/java/org/apache/pdfbox/filter/CCITTFaxFilter.java

Lines changed: 37 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -59,8 +59,43 @@ public DecodeResult decode(InputStream encoded, OutputStream decoded,
5959
// decompress data
6060
int k = decodeParms.getInt(COSName.K, 0);
6161
boolean encodedByteAlign = decodeParms.getBoolean(COSName.ENCODED_BYTE_ALIGN, false);
62-
int arraySize = (cols + 7) / 8 * rows;
63-
// TODO possible options??
62+
if (cols <= 0 || rows <= 0)
63+
{
64+
throw new IOException("Invalid CCITT image dimensions: cols=" + cols + ", rows=" + rows);
65+
}
66+
67+
long arraySizeLong = ((long) cols + 7) / 8 * rows;
68+
69+
long maxBytes = 256 * 1024 * 1024L;
70+
String sysProp = System.getProperty(Filter.SYSPROP_CCITTFAX_MAXBYTES);
71+
72+
if (sysProp != null)
73+
{
74+
try
75+
{
76+
long parsed = Long.parseLong(sysProp);
77+
if (parsed > 0)
78+
{
79+
maxBytes = parsed;
80+
}
81+
// else ignore zero/negative values
82+
}
83+
catch (NumberFormatException e)
84+
{
85+
// ignore invalid value, keep default
86+
}
87+
}
88+
89+
if (arraySizeLong > maxBytes)
90+
{
91+
throw new IOException(
92+
"CCITT decode buffer too large (" + arraySizeLong + " bytes) for cols=" + cols +
93+
", rows=" + rows + "; max allowed=" + maxBytes +
94+
"; increase " + Filter.SYSPROP_CCITTFAX_MAXBYTES + " to override"
95+
);
96+
}
97+
98+
int arraySize = (int) arraySizeLong;
6499
byte[] decompressed = new byte[arraySize];
65100
CCITTFaxDecoderStream s;
66101
int type;

pdfbox/src/main/java/org/apache/pdfbox/filter/Filter.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,16 @@ public abstract class Filter
6060
*/
6161
public static final String SYSPROP_DEFLATELEVEL = "org.apache.pdfbox.filter.deflatelevel";
6262

63+
/**
64+
* CCITTFax decode buffer size cap System Property. Sets the maximum number of bytes that
65+
* CCITTFaxFilter is allowed to pre-allocate for a single image decode buffer. PDF-controlled
66+
* /Columns and /Rows values are validated against this limit before allocation to prevent
67+
* denial-of-service via crafted image dimensions. The default is 256 MB. To raise the cap for
68+
* high-resolution legitimate documents, use
69+
* {@code System.setProperty(Filter.SYSPROP_CCITTFAX_MAXBYTES, String.valueOf(512 * 1024 * 1024L));}
70+
*/
71+
public static final String SYSPROP_CCITTFAX_MAXBYTES = "org.apache.pdfbox.filter.ccittmaxbytes";
72+
6373
/**
6474
* Constructor.
6575
*/

0 commit comments

Comments
 (0)