mirror of https://github.com/apache/poi.git
Bug 66425: Avoid a StackOverflowException found via oss-fuzz
We try to avoid causing StackOverflow, but it was possible to trigger one here with a specially crafted input-file. This puts a limit on the number of nested properties in place and logs a warning when the StyleSheet is not fully parsed. Should fix https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=61252 git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1911563 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
543d6ad54b
commit
2e8afc0c01
|
@ -20,6 +20,8 @@ package org.apache.poi.hwpf.model;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
|
|
||||||
|
import org.apache.logging.log4j.LogManager;
|
||||||
|
import org.apache.logging.log4j.Logger;
|
||||||
import org.apache.poi.hwpf.sprm.CharacterSprmUncompressor;
|
import org.apache.poi.hwpf.sprm.CharacterSprmUncompressor;
|
||||||
import org.apache.poi.hwpf.sprm.ParagraphSprmUncompressor;
|
import org.apache.poi.hwpf.sprm.ParagraphSprmUncompressor;
|
||||||
import org.apache.poi.hwpf.usermodel.CharacterProperties;
|
import org.apache.poi.hwpf.usermodel.CharacterProperties;
|
||||||
|
@ -39,6 +41,7 @@ import org.apache.poi.util.LittleEndianConsts;
|
||||||
*/
|
*/
|
||||||
@Internal
|
@Internal
|
||||||
public final class StyleSheet {
|
public final class StyleSheet {
|
||||||
|
private static final Logger LOG = LogManager.getLogger(StyleSheet.class);
|
||||||
|
|
||||||
public static final int NIL_STYLE = 4095;
|
public static final int NIL_STYLE = 4095;
|
||||||
// private static final int PAP_TYPE = 1;
|
// private static final int PAP_TYPE = 1;
|
||||||
|
@ -46,6 +49,9 @@ public final class StyleSheet {
|
||||||
// private static final int SEP_TYPE = 4;
|
// private static final int SEP_TYPE = 4;
|
||||||
// private static final int TAP_TYPE = 5;
|
// private static final int TAP_TYPE = 5;
|
||||||
|
|
||||||
|
private static final int MAX_PAPX_NESTING = 1000;
|
||||||
|
private static final int MAX_CHPX_NESTING = 1000;
|
||||||
|
|
||||||
@Deprecated
|
@Deprecated
|
||||||
private static final ParagraphProperties NIL_PAP = new ParagraphProperties();
|
private static final ParagraphProperties NIL_PAP = new ParagraphProperties();
|
||||||
@Deprecated
|
@Deprecated
|
||||||
|
@ -114,8 +120,8 @@ public final class StyleSheet {
|
||||||
}
|
}
|
||||||
for (int x = 0; x < _styleDescriptions.length; x++) {
|
for (int x = 0; x < _styleDescriptions.length; x++) {
|
||||||
if (_styleDescriptions[x] != null) {
|
if (_styleDescriptions[x] != null) {
|
||||||
createPap(x);
|
createPap(x, 0);
|
||||||
createChp(x);
|
createChp(x, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -203,7 +209,14 @@ public final class StyleSheet {
|
||||||
* ParagraphProperties from (and also place the finished PAP in)
|
* ParagraphProperties from (and also place the finished PAP in)
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
private void createPap(int istd) {
|
private void createPap(int istd, int nesting) {
|
||||||
|
if (nesting > MAX_PAPX_NESTING) {
|
||||||
|
LOG.warn("Encountered too deep nesting, cannot fully process stylesheet at " + istd +
|
||||||
|
" with more than " + MAX_PAPX_NESTING + " nested ParagraphProperties." +
|
||||||
|
" Some data could not be parsed.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
StyleDescription sd = _styleDescriptions[istd];
|
StyleDescription sd = _styleDescriptions[istd];
|
||||||
if (sd == null) {
|
if (sd == null) {
|
||||||
throw new IllegalStateException("Cannot create Pap, empty styleDescription, had : " + _styleDescriptions.length + " descriptions");
|
throw new IllegalStateException("Cannot create Pap, empty styleDescription, had : " + _styleDescriptions.length + " descriptions");
|
||||||
|
@ -227,7 +240,7 @@ public final class StyleSheet {
|
||||||
throw new IllegalStateException("Pap style " + istd + " claimed to have itself as its parent, which isn't allowed");
|
throw new IllegalStateException("Pap style " + istd + " claimed to have itself as its parent, which isn't allowed");
|
||||||
}
|
}
|
||||||
// Create the parent style
|
// Create the parent style
|
||||||
createPap(baseIndex);
|
createPap(baseIndex, nesting+1);
|
||||||
parentPAP = styleDescription.getPAP();
|
parentPAP = styleDescription.getPAP();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -253,7 +266,14 @@ public final class StyleSheet {
|
||||||
* CharacterProperties object from.
|
* CharacterProperties object from.
|
||||||
*/
|
*/
|
||||||
@Deprecated
|
@Deprecated
|
||||||
private void createChp(int istd) {
|
private void createChp(int istd, int nesting) {
|
||||||
|
if (nesting > MAX_CHPX_NESTING) {
|
||||||
|
LOG.warn("Encountered too deep nesting, cannot fully process stylesheet at " + istd +
|
||||||
|
" with more than " + MAX_CHPX_NESTING + " nested CharacterProperties." +
|
||||||
|
" Some data could not be parsed.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
StyleDescription sd = _styleDescriptions[istd];
|
StyleDescription sd = _styleDescriptions[istd];
|
||||||
if (sd == null) {
|
if (sd == null) {
|
||||||
throw new IllegalStateException("Cannot create Chp, empty styleDescription, had : " + _styleDescriptions.length + " descriptions");
|
throw new IllegalStateException("Cannot create Chp, empty styleDescription, had : " + _styleDescriptions.length + " descriptions");
|
||||||
|
@ -282,7 +302,7 @@ public final class StyleSheet {
|
||||||
|
|
||||||
parentCHP = styleDescription.getCHP();
|
parentCHP = styleDescription.getCHP();
|
||||||
if (parentCHP == null) {
|
if (parentCHP == null) {
|
||||||
createChp(baseIndex);
|
createChp(baseIndex, nesting + 1);
|
||||||
parentCHP = styleDescription.getCHP();
|
parentCHP = styleDescription.getCHP();
|
||||||
}
|
}
|
||||||
if (parentCHP == null) {
|
if (parentCHP == null) {
|
||||||
|
|
|
@ -58,7 +58,8 @@ public class TestWordToConverterSuite
|
||||||
// Corrupt files
|
// Corrupt files
|
||||||
"Fuzzed.doc",
|
"Fuzzed.doc",
|
||||||
"clusterfuzz-testcase-minimized-POIHWPFFuzzer-5418937293340672.doc",
|
"clusterfuzz-testcase-minimized-POIHWPFFuzzer-5418937293340672.doc",
|
||||||
"TestHPSFWritingFunctionality.doc"
|
"TestHPSFWritingFunctionality.doc",
|
||||||
|
"clusterfuzz-testcase-minimized-POIHWPFFuzzer-4947285593948160.doc"
|
||||||
);
|
);
|
||||||
|
|
||||||
public static Stream<Arguments> files() {
|
public static Stream<Arguments> files() {
|
||||||
|
|
|
@ -50,7 +50,8 @@ public class TestWordToTextConverter {
|
||||||
"TestRobert_Flaherty.doc",
|
"TestRobert_Flaherty.doc",
|
||||||
// Corrupt files
|
// Corrupt files
|
||||||
"clusterfuzz-testcase-minimized-POIHWPFFuzzer-5418937293340672.doc",
|
"clusterfuzz-testcase-minimized-POIHWPFFuzzer-5418937293340672.doc",
|
||||||
"TestHPSFWritingFunctionality.doc"
|
"TestHPSFWritingFunctionality.doc",
|
||||||
|
"clusterfuzz-testcase-minimized-POIHWPFFuzzer-4947285593948160.doc"
|
||||||
);
|
);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
Binary file not shown.
Binary file not shown.
Loading…
Reference in New Issue