编译与反编译:
JAVA web:
-
分层架构:为了方便清楚包与包之间的业务逻辑关系
-
视图层(View 视图)
-
控制层(Controller、Action 控制层)
-
服务层(Service)
-
业务逻辑层BO(business object)
-
实体层(entity 实体对象、VO(value object) 值对象 、模型层(bean)。
-
持久层(dao- Data Access Object 数据访问层、PO(persistant object) 持久对象)
-
-
-
模块化开发:
-
Maven
-
-
Gradle
-
OSGi ( Open Service Gateway Initiative 可实现模块热部署)
-
-
Servlet: Servlet 是在 Java Web容器 上运行的 小程序 ,通常我们用 Servlet 来处理一些较为复杂的服务器端的业务逻辑。值得注意的是在 Servlet3.0 之后( Tomcat7+ )可以使用注解方式配置 Servlet 了。
-
-
Servlet3.0 之前的版本都需要在 web.xml 中配置, Servlet 是 两对标签 ,由 <servlet> 和 <servlet-mapping> 组成, Spring MVC框架就是基于Servlet技术 实现的。
-
实现一个 Servlet 很简单,只需要继承 javax.servlet.http.HttpServlet 类并重写 doXXX 方法或者 service 方法
-
JSP、Servlet之间的关系
-
JSP、JSPX文件是可以直接被Java容器直接解析的动态脚本,jsp和其他脚本语言无异,不但可以用于页面数据展示,也可以用来处理后端业务逻辑。
-
从本质上说JSP就是一个Servlet,因为jsp文件最终会被编译成class文件,而这个Class文件实际上就是一个特殊的Servlet。
-
-
-
Filter
-
Filter是JavaWeb中的过滤器,用于过滤URL请求。通过Filter我们可以实现URL请求资源权限验证、用户登陆检测等功能。
-
Filter是一个接口,实现一个Filter只需要重写 init 、 doFilter 、 destroy 方法即可,其中过滤逻辑都在 doFilter 方法中实现。
-
Filter和Servlet一样是Java Web中最为核心的部分,使用Servlet和Filter可以实现后端接口开发和权限控制,当然使用Filter机制也可以实现MVC框架, Struts2 实现机制就是使用的Filter。
-
Filter的配置类似于Servlet,由 <filter> 和 <filter-mapping> 两组标签组成,如果Servlet版本大于3.0同样可以使用注解的方式配置Filter。
-
-
Filter和Servlet代码审计技巧总结:
对于基于
Filter
和
Servlet
实现的简单架构项目,代码审计的重心集中于找出所有的
Filter分析其过滤规则,找出是否有做全局的安全过滤、敏感的URL地址是否有做权限校验并尝试绕过Filter
过滤。第二点则是找出所有的
Servlet
,分析
Servlet
的业务是否存在安全问题,如果存在安全问题是否可以利用?是否有权限访问?利用时是否被Filter过滤?等问题,切勿看到
Servlet
、
JSP
中的漏洞点就妄下定论,不要忘了
Servlet前面很有可能存在一个全局安全过滤的Filter
。
Filter和Servlet技术异同总结:
-
Filter和Servlet都需要在web.xml或注解(@WebFilter、@WebServlet)中配置,而且配置方式是非常的相似的。
-
Filter和Servlet都可以处理来自Http请求的请求,两者都有request、response对象。
-
Filter和Servlet基础概念不一样,Servlet定义是容器端小程序,用于直接处理后端业务逻辑,而Filter的思想则是实现对Java Web请求资源的拦截过滤。
-
Filter和Servlet虽然概念上不太一样,但都可以处理Http请求,都可以用来实现MVC控制器( Struts2和Spring框架分别基于Filter和Servlet 技术实现的)。
-
一般来说Filter通常配置在MVC、Servlet和JSP请求 前面,常用于后端 权限控制、统一的Http请求 参数过滤(统一的XSS、SQL注入、Struts2命令执行等攻击检测处理)处理,其核心主要体现在请求 过滤上,而Servlet更多的是用来 处理后端业务请求上。
Sping控制器
Spring Controller注解:
-
@Controller
-
@RestController
-
@RepositoryRestController
Spring MVC请求配置注解:
-
@RequestMapping
-
@GetMapping
-
@PostMapping
-
@PutMapping
-
@DeleteMapping
-
@PatchMapping
XML配置bean容器(老旧的Spring项目)
<bean name="/test.do" class="org.javaweb.codereview.controller.TestController"/>
Strust2控制器
Struts2主要的开发模式是基于xml配置,在
struts.xml
中配置Action地址和对应的处理类。
不过Struts2(
2.1.6
版本开始)也可以使用
struts2-convention-plugin
插件来实现基于注解方式的配置。
快速找出Http请求请求URL(查找请控制器、查找请求注解)
代码审计中我们可以选择优先从
Controller
、
Servlet
和
JSP
中入手,也可以选择从漏洞点反向推出Http请求的入口地址
IDEA全局搜索:ctrl+shift+F
Find命令查找class文件:
-
查找 请求处理注解: find ~/cms/ -type f -name "*.class" |xargs grep -E "RequestMapping|GetMapping|PostMapping|PutMapping|DeleteMapping|PatchMapping|RepositoryRestResource"
-
查找 控制器: find ~/cms/ -type f -name "*.class" |xargs grep -E "Controller|@RestController|RepositoryRestController"
问:如何快速找出Http请求的请求url?答:IDEA全局搜索或者find搜索class文件:三个控制器、七个请求注解(*****Mapping)
JAVA语言的动态性相关技术:
利用这些动态性的技术从而挖出的相关漏洞,危害巨大
-
Java反射机制
-
MethodHandle(类似于反射,但效率远高于反射)
-
JDK动态代理
-
使用JVM上的动态语言(如:Groovy、JRuby、Jython) JVM上居然还有动态语言?
-
表达式库(如:OGNL、MVEL、SpEL、EL)
-
JSP 、 JSPX 、 Quercus (Resin容器提供了PHP5支持)
-
字节码库(如:Asm、Javassist、Cglib、BCEL)
-
ScriptEngineManager(脚本引擎)。
-
动态编译(如:JDT、JavaCompiler)
-
ClassLoader 、 URLClassLoader
-
模版引擎(如: Freemarker 、 Velocity )
-
序列化、反序列化(包含 Java 对象序列化 、 XML 、 JSON 等)
-
JNI、JNA(Java调用C/C++)
-
OSGi(Open Service Gateway Initiative)
-
RMI(Java远程方法调用,基于对象序列化机制实现)
-
WebService
-
JDWP ( Java Platform Debugger Architecture Java调试协议)
-
JMX(Java Management Extensions)
JAVA反射机制: java反射调用漏洞
Java反射机制可以无视类方法、变量访问权限修饰符,可以调用任何类的任意方法、访问并修改成员变量值。也就是说只要发现一处Java反射调用漏洞几乎就可以为所欲为了。当然前提可能需要你能控制反射的类名、方法名和参数。
一行代码即可实现反射调用Runtime执行本地命令:
Runtime.class.getMethod("exec", String.class).invoke(Runtime.class.getMethod("getRuntime").invoke(null), "whoami")
Java反射获取类方法有两种方式:
-
getMethod(xxx),getMethods()
-
getDeclaredMethod(xxx)、getDeclaredMethods()。
区别在于getMethod会返回当前类和父类的所有public方法,而getDeclaredMethod返回的是当前的所有方法。
Java反射获取类成员变量有两种方式:
-
getField(xxx)、getFields()
-
getDeclaredField(xxx)、getDeclaredFields()
getField和getDeclaredField区别同上,如果想要调用private修饰的Field或者Method只需要设置下setAccessible为true就可以了,如:xxxMethod.setAccessible(true)。
JDK7+ MethodHandle
JDK7开始Java提供了MethodHandle可以非常方便的访问和调用类方法,MethodHandle的能力和Java反射机制相似,但效率却远高出Java反射机制,但MethodHandle也并不是那么完美的,缺点是MethodHandle必须要求JDK版本大于等于1.7,MethodHandle也无法像反射那样调用私有方法和变量。
JAVA代码审计Checklist
-
业务层安全
-
代码实现
-
服务架构
ORM框架在运行时就能参照映射文件的信息,把对象持久化到数据库中。当前ORM框架主要有五种:Hibernate(Nhibernate),iBATIS,mybatis,EclipseLink,JFinal。
业务层面代码审计Checklist
-
验证码:
-
不过期的验证码导致可爆破
-
第三方API未做请求限制导致轰炸
-
验证码明文传输
-
-
加密算法:
-
数据传输未加密
-
硬编码或弱加密
-
cookie直接明文存储用户名和密码
-
验证码明文传输
-
-
CSRF
-
未采用验证码或Token
-
-
ORM框架(对象持久化到数据库的框架)
-
横向越权(订单遍历,个人信息遍历...)
-
纵向越权(创建管理员用户...)
-
-
逻辑漏洞
-
找回密码可通过修改返回包绕过旧密码
-
条件竞争(并发支付)
-
-
API
-
第三方API不安全的调用
-
未做请求限制导致轰炸
-
-
异常处理
-
不安全的异常处理代码,导致爆出数据库信息或绝对路径
-
代码层面代码审计Checklist
-
任意文件上传、下载、重命名、删除、遍历等
-
SQL注入
-
XXE(XML实体dtd注入攻击)
-
系统命令执行
-
反序列化攻击(攻击发生在反序列化的过程之中)
-
JAVA反射攻击( Java反射机制可以无视类方法、变量访问权限修饰符,可以 调用任何类的任意方法、访问并修改成员变量值)
-
SSRF(服务器端请求伪造)
-
java文件名空字节截断漏洞(某历史遗留问题 ,受影响版本 JDK<1.7.40)
-
文件上传、下载、重命名、删除、遍历等
-
修复方案: fileName.indexOf('\u0000')
-
快速发现任意文件读取漏洞:
-
JDK原始的 java.io.FileInputStream 类
-
JDK原始的 java.io.RandomAccessFile 类
-
Apache Commons IO提供的 org.apache.commons.io.FileUtils 类
-
JDK1.7新增的基于NIO非阻塞异步读取文件的java.nio.channels.AsynchronousFileChannel类。
-
JDK1.7新增的基于NIO读取文件的java.nio.file.Files类。常用方法如:Files.readAllBytes、Files.readAllLines