Skip to Content.
Sympa Menu

xom-interest - [XOM-interest] Code review needed

xom-interest AT lists.ibiblio.org

Subject: XOM API for Processing XML with Java

List archive

Chronological Thread  
  • From: Elliotte Rusty Harold <elharo AT ibiblio.org>
  • To: XOM interest <xom-interest AT lists.ibiblio.org>
  • Subject: [XOM-interest] Code review needed
  • Date: Sun, 18 May 2014 10:46:29 -0400

My initial efforts to mitigate the billion laughs attack succeeded. However
this document snuck by:

<?xml version="1.0"?>
<!DOCTYPE root [
<!ENTITY ha1 "ha ha ha ha ha ha ha ha ha ha ha ha ha ha ha">
<!ENTITY ha1 "ha ha ha ha ha ha ha ha ha ha ha ha ha ha ha">
<!ENTITY ha2 "&ha1; &ha1; &ha1; &ha1; &ha1; &ha1; &ha1; &ha1; &ha1; &ha1;
&ha1; &ha1; &ha1; &ha1; &ha1;">
<!ENTITY ha3 "&ha2; &ha2; &ha2; &ha2; &ha2; &ha2; &ha2; &ha2; &ha2; &ha2;
&ha2; &ha2; &ha2; &ha2; &ha2;">
<!ENTITY ha4 "&ha3; &ha3; &ha3; &ha3; &ha3; &ha3; &ha3; &ha3; &ha3; &ha3;
&ha3; &ha3; &ha3; &ha3; &ha3;">
<!ENTITY ha5 "&ha4; &ha4; &ha4; &ha4; &ha4; &ha4; &ha4; &ha4; &ha4; &ha4;
&ha4; &ha4; &ha4; &ha4; &ha4;">
<!ENTITY ha6 "&ha5; &ha5; &ha5; &ha5; &ha5; &ha5; &ha5; &ha5; &ha5; &ha5;
&ha5; &ha5; &ha5; &ha5; &ha5;">
<!ENTITY ha7 "&ha6; &ha6; &ha6; &ha6; &ha6; &ha6; &ha6; &ha6; &ha6; &ha6;
&ha6; &ha6; &ha6; &ha6; &ha6;">
<!ENTITY ha8 "&ha7; &ha7; &ha7; &ha7; &ha7; &ha7; &ha7; &ha7; &ha7; &ha7;
&ha7; &ha7; &ha7; &ha7; &ha7;">
<!ENTITY ha9 "&ha8; &ha8; &ha8; &ha8; &ha8; &ha8; &ha8; &ha8; &ha8; &ha8;
&ha8; &ha8; &ha8; &ha8; &ha8;">
<!ENTITY ha "&ha9; &ha9; &ha9; &ha9; &ha9; &ha9; &ha9; &ha9; &ha9; &ha9;
&ha9; &ha9; &ha9; &ha9; &ha9;">
]>
<root name='&ha;'>Ha!</root>


In particular, rather than causing an out of memory error, it seems to have
hung Xerces, possibly pushing it into an infinite loop.

So here's my thought. In addition to setting a maximum memory size on
documents, I will set a maximum execution *time*. I.e. I'll move the parse
into a separate thread and abort it if it exceeds a configurable amount of
time. The code is something like this:

Document result = null;
try {
ParseJob job = new ParseJob(in);
Thread t = new Thread(job);
t.start();
t.join(60000);
if (job.getProblem() != null) {
throw job.getProblem();
}
result = handler.getDocument();
}




private class ParseJob implements Runnable {

private InputSource in;
Exception problem = null;

ParseJob(InputSource in) {
this.in = in;
}

public void run() {
try {
parser.parse(in);
} catch (Exception throwable) {
this.problem = throwable;
}
}

Exception getProblem() {
return problem;
}
}

Yes, this would be easier if I weren't trying to maintain compatibility
with Java 1.4.

What do folks think? Am I making any obvious mistakes?


--
Elliotte Rusty Harold
elharo AT ibiblio.org




Archive powered by MHonArc 2.6.24.

Top of Page