[详细]Apache Shiro身份验证越权漏洞[CVE-2016-6802][CVE-2020-1957]

什么是shiro

        Apache Shiro是一个强大且易用的java安全框架,执行身份验证,授权,密码和会话管理,使用Shiro的API,可以快速获取任何应用程,从最小的移动应用到最大的网络和企业应用程序

shiro权限绕过的原因

        Apache Shiro是一个java的安全管理框架,可以和spring一起使用

        shiro框架通过拦截器来实现对用户访问权限的控制和拦截

        shiro常见的拦截器有anon,authc等

anon:匿名拦截器,不需要登录就可以访问,一般用于静态资源,或者移动端接口
authc:登录拦截器,需要登录认证才能访问资源

shiro权限绕过的限制条件

  • 网站同时使用shiro和spring
  • shiro满足特定的版本

Shiro拦截器

        Shiro框架通过拦截器功能来实现对用户访问的控制和拦截,Shiro中常见的拦截器有anon,authc等拦截器

1.anon为匿名拦截器,不需要登录就能访问,一般用于静态资源,或者移动端接口
2.authc为登录拦截器,需要认证才能访问资源

        用户可以在shiro.ini编写匹配URL配置,将会拦截匹配的URL,并执行响应的拦截器,从而实现对URL的访问控制,URL路径表达式通常为ANT格式,如下配置,访问/index.html主页的时候,shiro将不会对其进行登录判断anon拦截器不需要登录就能进行访问,而对于某些/api/敏感接口,shiro会使用authc拦截器来对其进行登录判断,有登录认证才能访问资源 

[urls]
/index.html=anon

/api/=authc

        Shiro的URL路径表达式为Ant格式,路径通配符支持?***等

?:匹配一个字符

*:匹配零个或者多个字符串

**:匹配路径中的零个或者多个路径

         在shiro中*可以表示-匹配零个或者多个字符串,例如:/*可以匹配/index这个页面,无法匹配搭配/index/这个路径,在authc拦截器中,如果管理员对/admin进行了authc拦截,用户直接访问/admin,authc会进行权限判断,这里我们假设将请求的URI设置为/*admin/,/*URL路径表达式将无法正确匹配因为不知道到底是路径还是页面接口,接着放行然后到spring(Servlet)拦截器,注意的是:spring中/admin形式和/hello/形式的URL访问的资源是一样的

        拦截器优先级:从上到下,从左到右,如果有匹配的拦截器就会阻断并返回,例如:访问js/a.js,第一个拦截器就是anon符合,就返回true了,不会再往下匹配了,注意最后一个拦截最后一句是/**=user,test意思就是除了上面的那些,其他的所有都要经过,user和frameperms.如果没有登陆user就会阻断,就不会执行到frameperms.test就是我们自定义实现的过滤器,从数据库中查询用户的权限,判断当前用户是否有权限访问拦截的URL

        springranin的配置

<property name= "filterChainDefinitions">
 <value>
  /js/** = anon
  /css/** = anon
  /images/** = anon
  /mvimg/**= anon
  /unauth = anon
  /getCaptcha=anon
  /login = anon
  /favicon.ico =anon 
  /index = user 
  /logout = logout
  /menu/leftMenu=user
  /**/ajax/** = user
  /**= user,test
 </value>
</property>

访问控制的含义

        访问控制广泛应用于各个系统中,抽象的说,都是某个主题对某个主体对某个客体需要实施某种操作,而系统对这种操作的限制就是权限控制

        在一个安全系统中,去欸的那个主体的身份是"认证"解决问题;而客体是一种资源,是主体发起的请求对象,在主体对客体进行操作的过程中,系统控制主体不能"无限制"的对客体进行操作,这个过程就是"访问控制"

CVE-2016-6802

        shiro版本: shiro < 1.5.0

        shiro于spring的URI中末尾的/不同导致的权限绕过

        这个版本shiro使用的/或者*进行匹配零个或多个字符串,/*后面的字符串都会匹配到此规则,例如/admin,但匹配不到/admin/因为*通配符无法匹配路径,

        假设/admin接口设置了authc拦截器,访问/admin将会被进行权限判断,如果请求的URI为/admin/,/*的URL路径表达式讲无法进行匹配,然后进行放行,然后进入到spring(servlet)拦截器,而spring中/admin形式和/admin/形式的URL访问的资源是一样的,从而导致了绕过

CVE-2020-1957

        shiro版本: shiro < 1.5.2

        payload:

/XXX/..;/admin/
/.;/admin/

        通过网络判断,网站处理URI时会先经过shiro处理,再转发到springboot进行路由分发工作,而在shiro中,在对URI中的;进行处理时会将URI进行截断,然后对/xxx/..进行权限校验,这样我们就可以成功访问到原本访问不到的接口了

        验证流程大致如下:

        客户端发起请求/xxx/..;/admin

        shiro处理之后返回/xxx/..校验通过

        springboot处理/xxx/..;/admin/返回/admin/

        最后访问到需要权限校验的资源

环境搭建

        启动docker服务

systemctl start docker

        安装docker 

        1.uname -a 内核版本大于3.1

       2.换源

vim /etc/apt/sources.list
删除所有内容更换为 注意可以使用gedit编译
#其他apt源
#此处,笔者仅添加中科达和阿里的,其他注释掉
 
#中科大
deb http://mirrors.ustc.edu.cn/kali kali-rolling main non-free contrib
deb-src http://mirrors.ustc.edu.cn/kali kali-rolling main non-free contrib
 
#阿里云
deb http://mirrors.aliyun.com/kali kali-rolling main non-free contrib
deb-src http://mirrors.aliyun.com/kali kali-rolling main non-free contrib
 
#清华大学
#deb http://mirrors.tuna.tsinghua.edu.cn/kali kali-rolling main contrib non-free
#deb-src https://mirrors.tuna.tsinghua.edu.cn/kali kali-rolling main contrib non-free
 
#浙大
#deb http://mirrors.zju.edu.cn/kali kali-rolling main contrib non-free
#deb-src http://mirrors.zju.edu.cn/kali kali-rolling main contrib non-free
 
#东软大学
#deb http://mirrors.neusoft.edu.cn/kali kali-rolling/main non-free contribp.kali.org/kali kali-rolling main non-free contrib
 
#重庆大学
#deb http://http.kali.org/kali kali-rolling main non-free contrib
#deb-src http://http.kali.org/kali kali-rolling main non-free contrib

         3.安装docker

apt-get update && apt-get upgrade && apt-get dist-upgrade

       下载vulhub靶场

https://github.com/vulhub/vulhub

wget https://github.com/vulhub/vulhub/archive/master.zip -O vulhub-master.zip

        搭建fastjson漏洞环境

unzip vulhub-master.zip   #解压vulhub-master.zip

cd vulhub-master/shiro/CVE-2020-1957  #vulhub-master目录下

docker-compose up -d #使用docker-compose拉取启动shiro靶场

        URL权限配置如下

@Bean
public ShiroFilterChainDefinition shiroFilterChainDefinition() {
    DefaultShiroFilterChainDefinition chainDefinition = new DefaultShiroFilterChainDefinition();
    chainDefinition.addPathDefinition("/login.html", "authc"); // need to accept POSTs from the login form
    chainDefinition.addPathDefinition("/logout", "logout");
    chainDefinition.addPathDefinition("/admin/**", "authc");
    return chainDefinition;
}

        环境启动后访问网址即可

         对于此页面我们进行192.168.1.1:8000/admin/访问

         流量包如下

 

漏洞原因[代码审计]

                在PathMatchingFilterChainResolver的FilterChain getChain函数下,PatchMatchingFilter根据URL路径匹配中配置的urI路径表达式来匹配输入URL,判断是否匹配拦截器,匹配成功将会返回响应拦截器执行链,让shirofither执行权限操作

                 使用pathmatches函数进行匹配如果我们在URI后面加入/就可以绕过pathmatches函数

  我们在patchMatches函数zhongshiro.util.AntPathMatcher类中doMatch的对于ant格式的pathPattern和requestURI进行匹配,简单来说/admin/1可以匹配/admin/*,shiro的Ant格式的pathPattern中的*通配符是不支持匹配路径的,/admin/1/是匹配不到/admin/*所以直接false我们也因此直接越权

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值