diff --git a/test/src/test/java/hudson/util/XStream2Security247Test.java b/test/src/test/java/hudson/util/XStream2Security247Test.java index 0e4cdd5bb52aedd6037ad1ce7508284573d11a8c..1da4ae949e40623e3d9bc57abdbfb2dcf55c3153 100644 --- a/test/src/test/java/hudson/util/XStream2Security247Test.java +++ b/test/src/test/java/hudson/util/XStream2Security247Test.java @@ -1,35 +1,65 @@ package hudson.util; -import hudson.Functions; import hudson.model.Items; -import org.apache.commons.io.FileUtils; +import org.apache.commons.io.*; +import org.apache.commons.io.IOUtils; +import org.junit.Before; import org.junit.Rule; import org.junit.Test; +import org.junit.rules.TemporaryFolder; import org.jvnet.hudson.test.Issue; import org.jvnet.hudson.test.JenkinsRule; +import org.kohsuke.stapler.StaplerRequest; +import org.kohsuke.stapler.StaplerResponse; +import org.mockito.Mock; +import org.mockito.MockitoAnnotations; +import javax.servlet.ServletInputStream; import java.io.File; +import java.io.IOException; +import java.io.InputStream; import static org.junit.Assert.assertFalse; +import static org.mockito.Mockito.when; public class XStream2Security247Test { @Rule public JenkinsRule j = new JenkinsRule(); + @Rule + public TemporaryFolder f = new TemporaryFolder(); + + @Mock + private StaplerRequest req; + + @Mock + private StaplerResponse rsp; + + @Before + public void setUp() throws Exception { + MockitoAnnotations.initMocks(this); + } + @Test @Issue("SECURITY-247") - public void dontUnmarshalMethodClosure() throws Exception { - if (Functions.isWindows()) return; - File exploitFile = new File("/tmp/jenkins-security247test"); + public void testXmlLoad() throws Exception { + File exploitFile = f.newFile(); try { // be extra sure there's no file already if (exploitFile.exists() && !exploitFile.delete()) { throw new IllegalStateException("file exists and cannot be deleted"); } File tempJobDir = new File(j.jenkins.getRootDir(), "security247"); - FileUtils.copyInputStreamToFile(XStream2Security247Test.class.getResourceAsStream("/hudson/util/XStream2Security247Test/config.xml"), - new File(tempJobDir, "config.xml")); + + String exploitXml = org.apache.commons.io.IOUtils.toString( + XStream2Security247Test.class.getResourceAsStream( + "/hudson/util/XStream2Security247Test/config.xml"), "UTF-8"); + + exploitXml = exploitXml.replace("@TOKEN@", exploitFile.getAbsolutePath()); + + FileUtils.write(new File(tempJobDir, "config.xml"), exploitXml); + try { Items.load(j.jenkins, tempJobDir); } catch (Exception e) { @@ -40,4 +70,51 @@ public class XStream2Security247Test { exploitFile.delete(); } } + + @Test + @Issue("SECURITY-247") + public void testPostJobXml() throws Exception { + File exploitFile = f.newFile(); + try { + // be extra sure there's no file already + if (exploitFile.exists() && !exploitFile.delete()) { + throw new IllegalStateException("file exists and cannot be deleted"); + } + File tempJobDir = new File(j.jenkins.getRootDir(), "security247"); + + String exploitXml = org.apache.commons.io.IOUtils.toString( + XStream2Security247Test.class.getResourceAsStream( + "/hudson/util/XStream2Security247Test/config.xml"), "UTF-8"); + + exploitXml = exploitXml.replace("@TOKEN@", exploitFile.getAbsolutePath()); + + when(req.getMethod()).thenReturn("POST"); + when(req.getInputStream()).thenReturn(new Stream(IOUtils.toInputStream(exploitXml))); + when(req.getContentType()).thenReturn("application/xml"); + when(req.getParameter("name")).thenReturn("foo"); + + try { + j.jenkins.doCreateItem(req, rsp); + } catch (Exception e) { + // don't care + } + + assertFalse("no file should be created here", exploitFile.exists()); + } finally { + exploitFile.delete(); + } + } + + private static class Stream extends ServletInputStream { + private final InputStream inner; + + public Stream(final InputStream inner) { + this.inner = inner; + } + + @Override + public int read() throws IOException { + return inner.read(); + } + } } diff --git a/test/src/test/resources/hudson/util/XStream2Security247Test/config.xml b/test/src/test/resources/hudson/util/XStream2Security247Test/config.xml index ee66135977e642e9dc1b3bfbda7aa149d6ace3f5..5b9b22ab59d97b2e898ddebad6f5a75d237696ac 100644 --- a/test/src/test/resources/hudson/util/XStream2Security247Test/config.xml +++ b/test/src/test/resources/hudson/util/XStream2Security247Test/config.xml @@ -9,7 +9,7 @@ touch - /tmp/jenkins-security247test + @TOKEN@ false