diff --git a/boot/src/main/java/com/taobao/arthas/boot/DownloadUtils.java b/boot/src/main/java/com/taobao/arthas/boot/DownloadUtils.java index beb47cc4c..298e4dd33 100644 --- a/boot/src/main/java/com/taobao/arthas/boot/DownloadUtils.java +++ b/boot/src/main/java/com/taobao/arthas/boot/DownloadUtils.java @@ -185,9 +185,18 @@ public class DownloadUtils { * @return * @throws Exception */ - private static Document transformMavenMetaData(String mavenMetaData) throws Exception { + static Document transformMavenMetaData(String mavenMetaData) throws Exception { ByteArrayInputStream inputStream = new ByteArrayInputStream(mavenMetaData.getBytes("UTF-8")); DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance(); + //disable XXE before newDocumentBuilder + dbFactory.setFeature("http://javax.xml.XMLConstants/feature/secure-processing", true); + dbFactory.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true); + dbFactory.setFeature("http://xml.org/sax/features/external-parameter-entities", false); + dbFactory.setFeature("http://xml.org/sax/features/external-general-entities", false); + dbFactory.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false); + dbFactory.setXIncludeAware(false); + dbFactory.setExpandEntityReferences(false); + //create doc builder DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); return dBuilder.parse(inputStream); } diff --git a/boot/src/test/java/com/taobao/arthas/boot/DownloadUtilsTest.java b/boot/src/test/java/com/taobao/arthas/boot/DownloadUtilsTest.java index 043becb88..d30e10632 100644 --- a/boot/src/test/java/com/taobao/arthas/boot/DownloadUtilsTest.java +++ b/boot/src/test/java/com/taobao/arthas/boot/DownloadUtilsTest.java @@ -9,18 +9,26 @@ import java.net.URL; import java.util.ArrayList; import org.junit.Assert; +import org.w3c.dom.Document; + import static com.taobao.arthas.boot.DownloadUtils.*; public class DownloadUtilsTest { @Test public void testReadMavenReleaseVersion() { - Assert.assertNull(readMavenReleaseVersion("")); + //check 'center' repo + String releaseVersion = readMavenReleaseVersion(readMavenMetaData("center", false)); + Assert.assertNotNull(releaseVersion); + Assert.assertNotEquals("releaseVersion is empty", "", releaseVersion.trim()); + //check 'aliyun' repo + String aliyunReleaseVersion = readMavenReleaseVersion(readMavenMetaData("aliyun", false)); + Assert.assertEquals("releaseVersion is not match between repo 'center' and 'aliyun'", releaseVersion, aliyunReleaseVersion); } @Test public void testReadAllMavenVersion() { - Assert.assertEquals(new ArrayList(), readAllMavenVersion("")); + Assert.assertNotEquals(new ArrayList(), readAllMavenVersion(readMavenMetaData("center", false))); } @Test @@ -35,4 +43,22 @@ public class DownloadUtilsTest { String url = "https://repo1.maven.org/maven2/com/taobao/arthas/arthas-packaging/maven-metadata.xml"; Assert.assertEquals(IOUtils.toString(new URL(url).openStream()), readMavenMetaData("center", false)); } + + @Test + public void testXXE() throws Exception { + try { + //from https://blog.spoock.com/2018/10/23/java-xxe/ + String playload = "\n" + + "\n" + + " ]>\n" + + "&xxe;"; + Document document = transformMavenMetaData(playload); + } catch (org.xml.sax.SAXParseException e) { + String message = e.getMessage(); + Assert.assertTrue("XXE is not disabled", message.contains("disallow-doctype-decl")); + return; + } + Assert.fail("XXE is not disabled"); + } }