OpenRasp分析

什么是RASP:

RASP =》Runtime Application Self-Protection 运行时自我保护系统
它与waf不同的是,可以结合上下文在Hook应用的底层代码,检测程序最终传入的参数来判断是否有威胁。

传统的waf缺陷是:

1.正则缺陷、或者前后中间件的差异性导致绕过问题
2.无法结合程序的上下文分析,分析程序是否受影响
3.就算是程序本身没有SQL注入,只要发起了sql注入流量,就会产生告警

RASP:

1.以最终到达函数的参数为依据,不考虑前面任何转化或者差异性。
2.输入可以是文件流、对象、普通参数。
3.可以结合上下文来对POC进行拦截,不会对所有特殊字符都进行拦截。相对准备率达到99%。
4.预防框架级的0day,而waf依赖及时更新规则。
5.对较大的数据包(如上传会因为效率问题会做一些让步)不再惧怕

RASP缺点:

1.有一定的性能损耗。
2.对程序侵入较大,以Agent的方式侵入。有可能因为Agent的问题,导致业务挂了。
3.开发成本大,不可跨语言使用,每个语言需要单独开发。
4.以java为例,涉及Class操作,学习成本大。(目前较流量的两个框架: ASM 、javassist)。
5.目前没有较好的热部署最佳实践。

OpenRasp的优势:

作为一款开源产品,OpenRASP可定制化更强,比如我们在v0.21里增加了DB2数据库的支持,目前商业产品均不支持;另外,我们的检测算法、框架都是完全开源的,可随意修改,增加攻击检测插件

侵入方式:

  1. 代理Onload方式加载
  2. 代理OnAttach方式加载

入口文件:

测试前

入口类

测试前

进行初始化操作

JarFileHelper.addJarToBootstrap(inst);
readVersion();
ModuleLoader.load(mode, action, inst);
测试前

加载至Bootstrap优先于其它系统类启动类加载器,

为什么要将rasp.jar加载至Bootstrap

1.JarFileHelper.addJarToBootstrap(inst)加载至Bootstrap优先于其它系统类启动类加载器,
Bootstrap是Java类加载层次中最顶层的类加载器,负责加载JDK中的核心类库,如:rt.jar、resources.jar、charsets.jar等,将rasp.jar加载到Bootstrap可以用来Hook 来自于BootstrapClassLoader加载的一些系统基础类如File类,因为由 BootstrapClassLoader 加载的类的时候,无法从该类调用非 BootstrapClassLoader 加载的类中的接口。
方式一:inst.appendToBootstrapClassLoaderSearch方式,OpenRasp就是利用的这种方式
方式二:也可以使用jvm参数的方式-Xbootclasspath/p:path,让jvm优先于bootstrap默认路径加载指定路径的所有文件;
其中有一些坑,就是我已经加入了Bootstrap但是依旧还是没有Hook到File,更别提调用非Bootstrap的接口了。测试发现在启动premain方法时,其实基础的核心类库已经加载完毕了。必须进行retransform方法进行重新转化才可以Hook核心类库,并对其修改。

2.从MANIFEST.MF获取相应的版本信息

ModuleLoader.load(mode, action, inst);—》readVersion();
测试前

3.构建ModuleLoader加载rasp-engine.jar

如果Action等于install
测试前

引擎启动类

加载V8引擎

初始化插件系统

初始化Hook节点的管理类

初始化Transformer类

测试前
JS.Initialize() 插件初始化
测试前

获取Hook点原始调用栈信息
测试前

会将/plugins目录下的脚本进行读取,并进行插件更新
测试前
InitFileWatcher
会创建以目录为单位的文件监听,如果文件进行增删改,就执行插件更新
测试前
CheckerManager 初始化Hook节点的管理类
将 name和Checker加入枚举MAP中,供后面的检查使用
测试前

initTransformer(inst);
初始化Transformer类
对类进行转换
测试前
构造方法会添加一个Transformer类
测试前

会在com.baidu.openrasp.hook包下查找带@HookAnnotation的类
new出实例添加至HashSet()
测试前
并将他们加入咱们前面所说的Hooks里
测试前

如果Hooks里的类和calssName相同,那就对类进行转化。
hook.transformClass(ctClass)会对类的方法进行Hook并进行修改
测试前
会根据所需要的类型进行转换
测试前

以HttpClient为例
HookMethod会在setURL之前添加checkHttpUri方法
测试前
进而对URL是否非法进行判断
测试前
将提取的url详细参数提取存入params带入HookHandler.doCheck(CheckParameter.Type.SSRF, params);方法进行检测
当cpu超过90%禁用所有hook节点,因为安全是业务的附属品,如果业务挂了,安全搞得再好也没有意义
测试前
启用V8对进行检测
测试前
测试前

会用JNI的当时去检查

type.getName(), 插件的名称
params.getByteArray(),
params.size(),
new Context(checkParameter.getRequest()), 上下文
type == Type.REQUEST,
(int) Config.getConfig().getPluginTimeout()
测试前

修改规则的话,不用重启服务器
测试前
/plugins/official/plugin.js 会根据自定义的规则和算法进行检测
测试前

如果:
block 阻断
ignore 风险日志记录

文章作者: Screw
文章链接: http://screwsec.com/2019/11/16/OpenRasp%E5%88%86%E6%9E%90/
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 Screw's blog