首先查看依赖中是否引入了freemarker,由于此系统采用的maven,所以直接到pom.xml中寻找即可:
发现确实引用了freemarker模板。
代码层分析
关于freemarker的攻击方式,可利用的点在于模版语法本身,直接渲染用户输入payload会被转码而失效,所以一般的利用场景为上传或者修改模版文件,正好这里是一处可以加载模板的功能点。
漏洞点位于该路径:
ofcms-admin/src/main/java/com/ofsoft/cms/admin/controller/cms/TemplateController.java
中的save方法
*左右滑动查看更多
找到入口点
String fileContent = getRequest().getParameter("file_content")
*左右滑动查看更多
分析这段代码:
我们可以看到只是对传入的参数file_Content只进行了一个简单的替换,把"<"和">"替换为了"<"和">",也就是进行了一个HTML实体编码的解码,然后就直接将fileContent写入了原来的文件名中,未做其他限制,攻击者可以将可执行系统命令的恶意代码存入Freemarker模板,而Freemarker在渲染页面时,就会执行恶意代码。
漏洞利用
我们在后台中找到一处可以修改模板的地方:
后台->模板设置->模板文件->模板目录->修改html
*左右滑动查看更多
payload
<
*左右滑动查看更多
点击保存,重新访问一下index.html就可以了,calc命令已经执行成功了。
加固建议
1、进行适当的转义:在使用Freemarker模板引擎输出变量时,必须确保进行适当的转义,防止恶意代码注入。
2、避免使用用户控制的数据作为模板文件的路径和模板名称:使用硬编码的路径或从受信任的数据源中获取路径和模板名称。
3、避免使用eval()方法:尽量避免使用eval()方法,因为它可以执行任意代码。
4、避免使用不安全的Freemarker指令:尽可能避免使用不安全的指令,如#assign和#include,并确保正确转义任何用户控制的数据。
漏洞点位于
ofcms-admin/src/main/java/com/ofsoft/cms/admin/controller/cms/TemplateController.java
中的getTemplates方法。
*左右滑动查看更多
代码层分析
这里使用get方式获取三个参数dir、up_dir、res_path:
这一段代码对传进来的参数加一些前缀,最后反正都要路径遍历,这些前缀也不重要。
接下来看这个if语句,这里是重点,我们右键跟进下File和getSiteTempplateResourcePath方法:
getSiteTempplateResourcePath方法:
这里是获取它返回网站模板资源的路径。
File类的构造函数
这里笔者让chatgpt解释了下,最重要的点就是使用resolve方法将两个路径合成一个路径。
总的来说就是用resolve方法直接拼接网站路径和获取的dir值,没有任何过滤。主要没有过滤掉 ".."符号,我们就能在网页里使用../../来跳转目录。
继续回来往下走,这里利用listFiles方法返回pathfile目录下的文件夹传给dirs数组:
同理,这里使用listFiles方法返回pathfile目录下的所有的html、xml、css、js文件传给files数组:
定义了一个fileName变量用来接收file_name参数,接下来通过遍历files数组查找文件名为fileName的文件将其存储在变量editfile中,如果在files数组中未找到文件名为fileName的文件,则将files数组的第一个文件赋值给editFile。
接着往下发现使用readString方法读取editFile,最后通过setAttr方法将数据传递给View并在View中显示出来,全程无参数过滤,也就造成了路径遍历漏洞。
可能有小伙伴看的比较混乱,我这里再拉通代码解释一下。
1.接收传参并赋值
2.初步规范dir变量
3.路径拼接
4.获取以html、xml、css、js结尾的文件存储在files数组中:
5.获取文件名,遍历后存储在变量editfile中:
6.读取文件
漏洞利用
我们构造参数访问:
http://localhost:8080/ofcms_admin_war/admin/cms/template/getTemplates.html?file_name=web.xml&dir=../../&dir_name=
注:dir_name的值有没有都没关系
*左右滑动查看更多
漏洞利用成功。
加固建议
1、输入验证:对用户输入的数据进行验证和过滤,确保输入的数据不包含非法字符和路径分隔符等。
2、使用绝对路径:使用绝对路径而不是相对路径来引用文件和目录,可以避免路径遍历漏洞。在代码中应该始终使用绝对路径来访问文件和目录。
3、权限控制:对文件和目录进行适当的权限控制,确保只有授权的用户才能访问敏感的文件和目录。
4、文件名转义:对文件名进行转义,以防止攻击者利用文件名来执行路径遍历攻击。
5、限制访问:对公开的文件和目录进行限制,确保只有需要公开的文件和目录才能被访问。
漏洞点仍然位于
ofcms-admin/src/main/java/com/ofsoft/cms/admin/controller/cms/TemplateController.java
中的save方法
*左右滑动查看更多
代码层分析
经过简单分析,可以发现这里的res_path dirs file_name file_content 参数都是用户输入的,可以控制的 并且没有进行任何的过滤处理。
抓包,对文件名进行修改,利用../跳转目录在static静态目录下写入webshell,对文件内容进行修改写入恶意的jsp文件。
跳转到static静态目录下写入webshell是因为使用了JFinal 框架的过滤器配置,对整个应用程序进行拦截:
也就是所有的url都会经过JFinal过滤器,看看JFinalFilter,右键跟进:
重点看doFilter方法中的try内容:
看看哪些方法调用了handle,有哪些过滤。选中handle,右键->Go To->Implementation(s):
发现ActionHandler类中重写了handle()方法:
如果URL中包含static/直接就会renturn,跳出过滤,所以可以将shell文件安心放在static目录下:
漏洞利用
后台->模板设置->模板文件->模板目录->修改html
*左右滑动查看更多
上传冰蝎马
点击保存进行抓包:
抓包修改filename和filecontent字段,这里注意要把冰蝎马进行url编码。
可以看到已经上传成功了,在apache-tomcat-8.5.69webappsofcms_admin_warstatic目录下:
使用冰蝎进行连接:
1、输入验证:对用户输入的数据进行验证和过滤,确保输入的数据不包含非法字符和文件路径分隔符等。
2、使用固定的文件名:不要使用用户输入的数据作为文件名或文件路径,而是使用固定的文件名或生成随机的文件名。在使用文件时,始终使用绝对路径来避免使用相对路径。
3、权限控制:对文件和目录进行适当的权限控制,确保只有授权的用户才能访问敏感的文件和目录。应该避免在可写的目录中保存敏感文件。
4、文件类型验证:对上传的文件类型进行验证,确保只有允许的文件类型才能上传。同时,上传的文件应该保存在受限的目录中,以限制攻击者的访问权限。
5、文件名转义:对文件名进行转义,以防止攻击者利用文件名来执行任意文件写入攻击。
四、总结
第一次审计开源java项目,还是学到了很多的思路和技巧。
审计的思路大致可以分为:
查看依赖、版本、过滤器
查看控制器
查看可控变量,正向追踪变量传递过程
具体漏洞,具体分析
小结:灰盒的审计还是能找到点入手,但有些点还是需要看下其他文章才能完全理解,自己纯白盒的审计能力还需要继续学习。
往期回顾
原文始发于微信公众号(安恒信息安全服务):九维团队-绿队(改进)| OFCMSV1.1.2审计练习(下)
- 左青龙
- 微信扫一扫
-
- 右白虎
- 微信扫一扫
-
评论