Correctly escape namespace URIs in namespace declarations.
diff --git a/axis-rt-core/src/main/java/org/apache/axis/encoding/SerializationContext.java b/axis-rt-core/src/main/java/org/apache/axis/encoding/SerializationContext.java
index 0cf0ac9..f33ec28 100644
--- a/axis-rt-core/src/main/java/org/apache/axis/encoding/SerializationContext.java
+++ b/axis-rt-core/src/main/java/org/apache/axis/encoding/SerializationContext.java
@@ -1181,12 +1181,13 @@
sb.append(':');
sb.append(map.getPrefix());
}
- if ((vecQNames==null) || (vecQNames.indexOf(sb.toString())==-1)) {
+ String qname = sb.toString();
+ if ((vecQNames==null) || (vecQNames.indexOf(qname)==-1)) {
writer.write(' ');
- sb.append("=\"");
- sb.append(map.getNamespaceURI());
- sb.append('"');
- writer.write(sb.toString());
+ writer.write(qname);
+ writer.write("=\"");
+ getEncoder().writeEncoded(writer, map.getNamespaceURI());
+ writer.write('"');
}
}
}
diff --git a/axis-war/pom.xml b/axis-war/pom.xml
index f2fed9c..09aa21e 100644
--- a/axis-war/pom.xml
+++ b/axis-war/pom.xml
@@ -28,6 +28,9 @@
<artifactId>axis-war</artifactId>
<packaging>war</packaging>
<name>Axis :: WAR</name>
+ <properties>
+ <javaVersion>1.5</javaVersion>
+ </properties>
<dependencies>
<dependency>
<groupId>${project.groupId}</groupId>
@@ -64,11 +67,21 @@
<scope>test</scope>
</dependency>
<dependency>
+ <groupId>com.google.truth</groupId>
+ <artifactId>truth</artifactId>
+ <scope>test</scope>
+ </dependency>
+ <dependency>
<groupId>httpunit</groupId>
<artifactId>httpunit</artifactId>
<version>1.6.1</version>
<scope>test</scope>
</dependency>
+ <dependency>
+ <groupId>commons-io</groupId>
+ <artifactId>commons-io</artifactId>
+ <scope>test</scope>
+ </dependency>
</dependencies>
<build>
<plugins>
diff --git a/axis-war/src/test/java/org/apache/axis/war/Utils.java b/axis-war/src/test/java/org/apache/axis/war/Utils.java
new file mode 100644
index 0000000..77d03ee
--- /dev/null
+++ b/axis-war/src/test/java/org/apache/axis/war/Utils.java
@@ -0,0 +1,33 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.axis.war;
+
+import static org.junit.Assert.assertNotNull;
+
+public final class Utils {
+ private static String URL_PROPERTY = "test.functional.webapp.url";
+
+ private Utils() {}
+
+ public static String getWebappUrl() {
+ String url = System.getProperty(URL_PROPERTY);
+ assertNotNull(URL_PROPERTY + " not set", url);
+ return url;
+ }
+}
diff --git a/axis-war/src/test/java/org/apache/axis/war/XssTest.java b/axis-war/src/test/java/org/apache/axis/war/XssTest.java
new file mode 100644
index 0000000..0504e1a
--- /dev/null
+++ b/axis-war/src/test/java/org/apache/axis/war/XssTest.java
@@ -0,0 +1,57 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.axis.war;
+
+import static com.google.common.truth.Truth.assertThat;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.HttpURLConnection;
+import java.net.URL;
+
+import org.apache.commons.io.IOUtils;
+import org.junit.Test;
+
+public class XssTest {
+ /**
+ * Tests for potential XSS vulnerability in the Version service.
+ * <p>
+ * The Version service returns a body with whatever namespace URI was used in the request. If
+ * the namespace URI is not properly encoded in the response, then this creates a potential
+ * XSS vulnerability.
+ *
+ * @throws Exception
+ */
+ @Test
+ public void testGetVersion() throws Exception {
+ HttpURLConnection conn = (HttpURLConnection)new URL(Utils.getWebappUrl() + "/services/Version").openConnection();
+ conn.setDoInput(true);
+ conn.setDoOutput(true);
+ conn.setRequestProperty("SOAPAction", "");
+ conn.setRequestProperty("Content-Type", "text/xml;charset=UTF-8");
+ InputStream payload = XssTest.class.getResourceAsStream("getVersion-xss.xml");
+ OutputStream out = conn.getOutputStream();
+ IOUtils.copy(payload, out);
+ payload.close();
+ out.close();
+ assertThat(conn.getResponseCode()).isEqualTo(200);
+ InputStream in = conn.getInputStream();
+ assertThat(IOUtils.toString(in, "UTF-8")).doesNotContain("<script");
+ }
+}
diff --git a/axis-war/src/test/java/test/httpunit/HttpUnitTestBase.java b/axis-war/src/test/java/test/httpunit/HttpUnitTestBase.java
index 8ca191a..98a66b5 100644
--- a/axis-war/src/test/java/test/httpunit/HttpUnitTestBase.java
+++ b/axis-war/src/test/java/test/httpunit/HttpUnitTestBase.java
@@ -22,6 +22,7 @@
import java.io.*;
import java.net.MalformedURLException;
+import org.apache.axis.war.Utils;
import org.xml.sax.SAXException;
/**
@@ -38,14 +39,12 @@
super(s);
}
- private static String URL_PROPERTY="test.functional.webapp.url";
/**
* The JUnit setup method
*
*/
public void setUp() throws Exception {
- url=System.getProperty(URL_PROPERTY);
- assertNotNull(URL_PROPERTY+" not set",url);
+ url = Utils.getWebappUrl();
HttpUnitOptions.setExceptionsThrownOnErrorStatus(true);
HttpUnitOptions.setMatchesIgnoreCase(true);
HttpUnitOptions.setParserWarningsEnabled(true);
diff --git a/axis-war/src/test/resources/org/apache/axis/war/getVersion-xss.xml b/axis-war/src/test/resources/org/apache/axis/war/getVersion-xss.xml
new file mode 100644
index 0000000..380009e
--- /dev/null
+++ b/axis-war/src/test/resources/org/apache/axis/war/getVersion-xss.xml
@@ -0,0 +1,9 @@
+<soapenv:Envelope
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns:xsd="http://www.w3.org/2001/XMLSchema"
+ xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
+ xmlns:axis="http://axis.apache.org        "><script xmlns="http://www.w3.org/1999/xhtml">
            alert('Hello');
        </script>">
+ <soapenv:Body>
+ <axis:getVersion soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
+ </soapenv:Body>
+</soapenv:Envelope>
diff --git a/pom.xml b/pom.xml
index 7f34c11..022c64b 100644
--- a/pom.xml
+++ b/pom.xml
@@ -110,6 +110,11 @@
<version>4.12</version>
</dependency>
<dependency>
+ <groupId>com.google.truth</groupId>
+ <artifactId>truth</artifactId>
+ <version>0.40</version>
+ </dependency>
+ <dependency>
<groupId>xmlunit</groupId>
<artifactId>xmlunit</artifactId>
<version>1.0</version>