背景描述

用CodeQL检测响应包是否包含敏感信息的想法最开始是我的同学haoran分享给我的。之前已经实现了SQLi跟XSS的检测,在翻阅SOC中的漏洞时感觉我也需要实现这样的一个功能,对安全漏洞以及隐私合规都会有用处。

文后附有完整代码。

分析所有情景

ResultInfo是自定义的一个应答结果类,可以将实际返回的数据放入ResultInfo.success方法中格式化输出。
image.png

情景一
限定MethodAccess的Method,然后获取第一个Arguement作为实际返回的对象
image.png

情景二
ReturnType是泛型,且泛型参数不为空时,可以通过获取泛型内部的参数类型作为实际返回的对象
image.png
考虑多层嵌套的情景
image.png

情景三
排除ReturnType是ModelAndView的情况
image.png

情景四
同情景二的处理方式,当作泛型处理
image.png

情景五
可以同情景一的处理方式
image.png

情景六
类中的字段是包含敏感字段的类是
image.png

情景七
返回的是Map类型时
1)考虑key是敏感字段时
2)考虑value类型是敏感的类型时
3)考虑value类型是泛型时
image.png

情景七
haoran告诉了我这个情景,这一种情景可以通过本地污点追踪的方式进行匹配。
后来我想了一下,应该是可以全部通过本地污点追踪的形式进行匹配,最开始没有使用数据流的方式是因为考虑到可能没必要,但是全部实现以后,感觉应该还是数据流的形式更简便,下一次分享数据流的形式实现此需求。
image.png
需要注意下面这种情景不适合使用污点追踪,
image.png

思路描述

方案一
确定真正需要关注的返回值,actureReturn

自定义一个Method类MyMethod,筛选出需要关心的类
自定义一个ReturnType类MyReturnType,在构造函数里面判断是关心的返回类型,定义一个谓词获取DTO对象所有的字段
自定义一个ReturnStmt类MyReturnStmt,在构造函数里面判断是关心的返回类型, 定义一个谓词获取DTO对象所有的字段

如下采用全是正向的追踪方式,一直追踪到Field

  1. from Method m, MyReturnType myReturnType, MyReturnStmt myReturnStmt, Field returnField
  2. where
  3. m instanceof MyMethod and
  4. (
  5. myReturnType = m.getReturnType() and returnField = myReturnType.getReturnField()
  6. or
  7. myReturnStmt.getEnclosingCallable() = m and returnField = myReturnStmt.getReturnField()
  8. )
  9. select m,returnField

方案二

另一种方式,先获取所有定义了敏感字段的DTO对象
1)自定义一个Class类,MyClass,筛选出所有定义了敏感字段的DTO对象
2)ReturnType内部是否包含MyClass
3)ReturnStmt内部是否包含MyClass

对于Map类型的返回值
1)keyType是string,key是mobile时
2)keyType是MyClass时
3)keyType是泛型,内部是MyClass类型时

部分细节描述

首先需要根据自己项目的实际情况,配置关心的敏感字段的名称,后面会校验变量名、Map的key、类里面的字段名是否是这些值,如果是则认为是敏感的变量、类。
image.png
根据自己的情况,配置项目中映射URL的标注名,只关心可以通过URL直接访问到的方法
image.png
对于一些没有编译进CodeQL数据库的类,无法进入到类的内部比对字段名,可以手动配置这个类的类名
image.png