We try to avoid throwing NullPointerException, ClassCastExceptions and StackOverflowException, but it was possible to trigger them Fixes https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=62530 and https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=62491 git-svn-id: https://svn.apache.org/repos/asf/poi/trunk@1912433 13f79535-47bb-0310-9956-ffa450edef68tags/REL_5_2_4
public class WordToTextConverter extends AbstractWordConverter { | public class WordToTextConverter extends AbstractWordConverter { | ||||
private static final Logger LOG = LogManager.getLogger(WordToTextConverter.class); | private static final Logger LOG = LogManager.getLogger(WordToTextConverter.class); | ||||
private static final int MAX_NESTED_CHILD_NODES = 400; | |||||
private static final int MAX_NESTED_CHILD_NODES = 300; | |||||
public static String getText( DirectoryNode root ) throws Exception | public static String getText( DirectoryNode root ) throws Exception | ||||
{ | { |
import org.apache.poi.POIDataSamples; | import org.apache.poi.POIDataSamples; | ||||
import org.apache.poi.hslf.exceptions.EncryptedPowerPointFileException; | import org.apache.poi.hslf.exceptions.EncryptedPowerPointFileException; | ||||
import org.apache.poi.hslf.exceptions.HSLFException; | |||||
import org.apache.poi.hslf.exceptions.OldPowerPointFormatException; | import org.apache.poi.hslf.exceptions.OldPowerPointFormatException; | ||||
import org.apache.poi.util.IOUtils; | import org.apache.poi.util.IOUtils; | ||||
import org.apache.commons.io.output.NullPrintStream; | import org.apache.commons.io.output.NullPrintStream; | ||||
EXCLUDED.put("clusterfuzz-testcase-minimized-POIFuzzer-5429732352851968.ppt", FileNotFoundException.class); | EXCLUDED.put("clusterfuzz-testcase-minimized-POIFuzzer-5429732352851968.ppt", FileNotFoundException.class); | ||||
EXCLUDED.put("clusterfuzz-testcase-minimized-POIFuzzer-5681320547975168.ppt", FileNotFoundException.class); | EXCLUDED.put("clusterfuzz-testcase-minimized-POIFuzzer-5681320547975168.ppt", FileNotFoundException.class); | ||||
EXCLUDED.put("clusterfuzz-testcase-minimized-POIHSLFFuzzer-5962760801091584.ppt", RuntimeException.class); | EXCLUDED.put("clusterfuzz-testcase-minimized-POIHSLFFuzzer-5962760801091584.ppt", RuntimeException.class); | ||||
EXCLUDED.put("clusterfuzz-testcase-minimized-POIHSLFFuzzer-5231088823566336.ppt", FileNotFoundException.class); | |||||
} | } | ||||
public static Stream<Arguments> files() { | public static Stream<Arguments> files() { |
// work around two files which works here but not in other tests | // work around two files which works here but not in other tests | ||||
if (pFile.getName().equals("clusterfuzz-testcase-minimized-POIFuzzer-5429732352851968.ppt") || | if (pFile.getName().equals("clusterfuzz-testcase-minimized-POIFuzzer-5429732352851968.ppt") || | ||||
pFile.getName().equals("clusterfuzz-testcase-minimized-POIFuzzer-5681320547975168.ppt")) { | |||||
pFile.getName().equals("clusterfuzz-testcase-minimized-POIFuzzer-5681320547975168.ppt") || | |||||
pFile.getName().equals("clusterfuzz-testcase-minimized-POIHSLFFuzzer-5231088823566336.ppt")) { | |||||
throw new FileNotFoundException(); | throw new FileNotFoundException(); | ||||
} | } | ||||
} | } |
out.writeShort(priority); | out.writeShort(priority); | ||||
out.writeShort(template_type); | out.writeShort(template_type); | ||||
out.writeByte(template_param_length); | out.writeByte(template_param_length); | ||||
out.write(template_params); | |||||
if (template_params != null) { | |||||
out.write(template_params); | |||||
} | |||||
byte type = getConditionType(); | byte type = getConditionType(); | ||||
if (type == CONDITION_TYPE_COLOR_SCALE) { | if (type == CONDITION_TYPE_COLOR_SCALE) { | ||||
len += getFormulaSize(getFormula1()); | len += getFormulaSize(getFormula1()); | ||||
len += getFormulaSize(getFormula2()); | len += getFormulaSize(getFormula2()); | ||||
len += 2 + getFormulaSize(formula_scale); | len += 2 + getFormulaSize(formula_scale); | ||||
len += 6 + template_params.length; | |||||
len += 6 + (template_params == null ? 0 : template_params.length); | |||||
byte type = getConditionType(); | byte type = getConditionType(); | ||||
if (type == CONDITION_TYPE_COLOR_SCALE) { | if (type == CONDITION_TYPE_COLOR_SCALE) { |
blockSize = getIntAttr(passwordKey, "blockSize"); | blockSize = getIntAttr(passwordKey, "blockSize"); | ||||
keyBits = getIntAttr(passwordKey, "keyBits"); | keyBits = getIntAttr(passwordKey, "keyBits"); | ||||
hashSize = getIntAttr(passwordKey, "hashSize"); | hashSize = getIntAttr(passwordKey, "hashSize"); | ||||
cipherAlgorithm = CipherAlgorithm.fromXmlId(passwordKey.getAttribute("cipherAlgorithm"), keyBits); | |||||
cipherAlgorithm = CipherAlgorithm.fromXmlId(passwordKey.getAttribute("cipherAlgorithm"), keyBits == null ? -1 : keyBits); | |||||
cipherChaining = ChainingMode.fromXmlId(passwordKey.getAttribute("cipherChaining")); | cipherChaining = ChainingMode.fromXmlId(passwordKey.getAttribute("cipherChaining")); | ||||
hashAlgorithm = HashAlgorithm.fromEcmaId(passwordKey.getAttribute("hashAlgorithm")); | hashAlgorithm = HashAlgorithm.fromEcmaId(passwordKey.getAttribute("hashAlgorithm")); | ||||
saltValue = getBinAttr(passwordKey, "saltValue"); | saltValue = getBinAttr(passwordKey, "saltValue"); |
excludes.put("61300.xls", IndexOutOfBoundsException.class); | excludes.put("61300.xls", IndexOutOfBoundsException.class); | ||||
excludes.put("poi-fuzz.xls", RecordFormatException.class); | excludes.put("poi-fuzz.xls", RecordFormatException.class); | ||||
excludes.put("protected_66115.xls", RecordFormatException.class); | excludes.put("protected_66115.xls", RecordFormatException.class); | ||||
excludes.put("clusterfuzz-testcase-minimized-POIHSSFFuzzer-5786329142919168.xls", IllegalStateException.class); | |||||
return excludes; | return excludes; | ||||
} | } |
@Override | @Override | ||||
void runOneFile(File fileIn) throws Exception { | void runOneFile(File fileIn) throws Exception { | ||||
// replace with System.out for manual tests | // replace with System.out for manual tests | ||||
PrintWriter out = new PrintWriter(new NullWriter()); | |||||
PrintWriter out = new PrintWriter(NullWriter.INSTANCE); | |||||
final Function<FormulaRecord, String> lister = (doListFormula) ? this::listFormula : this::parseFormulaRecord; | final Function<FormulaRecord, String> lister = (doListFormula) ? this::listFormula : this::parseFormulaRecord; | ||||
import java.io.InputStream; | import java.io.InputStream; | ||||
import java.io.PrintWriter; | import java.io.PrintWriter; | ||||
import java.util.Locale; | import java.util.Locale; | ||||
import java.util.Map; | |||||
import org.apache.commons.io.output.NullWriter; | import org.apache.commons.io.output.NullWriter; | ||||
import org.apache.poi.hssf.record.ContinueRecord; | import org.apache.poi.hssf.record.ContinueRecord; | ||||
import org.apache.poi.hssf.record.RecordFactory; | import org.apache.poi.hssf.record.RecordFactory; | ||||
import org.apache.poi.hssf.record.RecordInputStream; | import org.apache.poi.hssf.record.RecordInputStream; | ||||
import org.apache.poi.poifs.filesystem.POIFSFileSystem; | import org.apache.poi.poifs.filesystem.POIFSFileSystem; | ||||
import org.apache.poi.util.RecordFormatException; | |||||
/** | /** | ||||
* This is a low-level debugging class, which simply prints out what records come in what order. | * This is a low-level debugging class, which simply prints out what records come in what order. | ||||
*/ | */ | ||||
class TestRecordLister extends BaseTestIteratingXLS { | class TestRecordLister extends BaseTestIteratingXLS { | ||||
@Override | |||||
protected Map<String, Class<? extends Throwable>> getExcludes() { | |||||
Map<String, Class<? extends Throwable>> excludes = super.getExcludes(); | |||||
excludes.put("clusterfuzz-testcase-minimized-POIHSSFFuzzer-5786329142919168.xls", RecordFormatException.class); | |||||
return excludes; | |||||
} | |||||
@Override | @Override | ||||
void runOneFile(File fileIn) throws IOException { | void runOneFile(File fileIn) throws IOException { | ||||
// replace it with System.out if you like it more verbatim | // replace it with System.out if you like it more verbatim | ||||
PrintWriter out = new PrintWriter(new NullWriter()); | |||||
PrintWriter out = new PrintWriter(NullWriter.INSTANCE); | |||||
try (POIFSFileSystem fs = new POIFSFileSystem(fileIn, true); | try (POIFSFileSystem fs = new POIFSFileSystem(fileIn, true); | ||||
InputStream din = BiffViewer.getPOIFSInputStream(fs)) { | InputStream din = BiffViewer.getPOIFSInputStream(fs)) { |
import static org.junit.jupiter.api.Assertions.assertTrue; | import static org.junit.jupiter.api.Assertions.assertTrue; | ||||
import static org.junit.jupiter.api.Assertions.fail; | import static org.junit.jupiter.api.Assertions.fail; | ||||
import java.io.ByteArrayOutputStream; | |||||
import java.io.File; | import java.io.File; | ||||
import java.io.FileInputStream; | import java.io.FileInputStream; | ||||
import java.io.FileOutputStream; | import java.io.FileOutputStream; | ||||
import java.io.IOException; | import java.io.IOException; | ||||
import java.io.InputStream; | import java.io.InputStream; | ||||
import java.io.OutputStream; | |||||
import java.util.ArrayList; | import java.util.ArrayList; | ||||
import java.util.Collection; | import java.util.Collection; | ||||
import java.util.List; | import java.util.List; | ||||
import org.apache.poi.ss.usermodel.Sheet; | import org.apache.poi.ss.usermodel.Sheet; | ||||
import org.apache.poi.ss.usermodel.SheetConditionalFormatting; | import org.apache.poi.ss.usermodel.SheetConditionalFormatting; | ||||
import org.apache.poi.ss.usermodel.Workbook; | import org.apache.poi.ss.usermodel.Workbook; | ||||
import org.apache.poi.ss.usermodel.WorkbookFactory; | |||||
import org.apache.poi.ss.util.CellRangeAddress; | import org.apache.poi.ss.util.CellRangeAddress; | ||||
import org.apache.poi.util.IOUtils; | import org.apache.poi.util.IOUtils; | ||||
import org.apache.poi.util.TempFile; | import org.apache.poi.util.TempFile; | ||||
void createDrawing() { | void createDrawing() { | ||||
// the dimensions for this image are different than for XSSF and SXSSF | // the dimensions for this image are different than for XSSF and SXSSF | ||||
} | } | ||||
@Test | |||||
void writeInvalidFile() throws Exception { | |||||
try (Workbook wb = WorkbookFactory.create( | |||||
samples.getFile("clusterfuzz-testcase-minimized-POIHSSFFuzzer-5786329142919168.xls"), | |||||
null, true)) { | |||||
try (OutputStream out = new ByteArrayOutputStream()) { | |||||
wb.write(out); | |||||
} | |||||
} | |||||
} | |||||
} | } |