GoAhead 内存信息泄漏漏洞分析

2019-12-17 约 381 字 预计阅读 2 分钟

声明:本文 【GoAhead 内存信息泄漏漏洞分析】 由作者 shuozhang 于 2019-12-17 09:11:31 首发 先知社区 曾经 浏览数 344 次

感谢 shuozhang 的辛苦付出!

0x1 漏洞描述

GoAhead 是一个开源、简单、轻巧、功能强大、可以在多个平台运行的嵌入式Web Server。很多厂商的产品使用过GoAhead,比如IBM、HP、Oracle、波音、D-link。

GoAhead 版本 4.X 到 5.0存在一个内存信息泄漏漏洞。

漏洞信息一

漏洞信息二

0x2 漏洞复现

wget https://github.com/embedthis/goahead/archive/v5.0.0.zip
unzip v5.0.0
cd goahead-5.0.0
#编译GoAhead
make
#运行GoAhead Web服务器
sudo ./build/linux-x64-default/bin/goahead -v ./ 0.0.0.0:8888

访问goahead服务器

漏洞发生在文件http.c的websRedirect函数,websRedirect顾名思义,处理跳转的请求。

在route.txt中配置一条可以跳转的路由,比如: 强制跳转到login.html页面

route uri=/ auth=form handler=continue redirect=401@/login.html

此时访问根目录,当http头host字段太长时,导致内存信息泄漏。

0x3 漏洞分析

在websRedirect函数,会将http head中的host信息拷贝到hostbuf中,后期会拼接http字符串返回给用户,显示页面的跳转信息。

1625 PUBLIC void websRedirect(Webs *wp, cchar *uri)
   1 {
   2     .....
   3     char    hostbuf[ME_GOAHEAD_LIMIT_STRING];
          .....
          .....
  13     if ((host = (wp->host ? wp->host : websHostUrl)) != 0) {
  14         scopy(hostbuf, sizeof(hostbuf), host);
                ....
                ...

ME_GOAHEAD_LIMIT_STRING的值为256,当host长度大于256时。scopy为防止发生溢出,不进行复制,返回-1。

scopy函数

14151 PUBLIC ssize scopy(char *dest, ssize destMax, cchar *src)
    1 {
    2     ssize      len;
    3
    4     assert(src);
    5     assert(dest);
    6     assert(0 < dest && destMax < MAXINT);
    7
    8     len = slen(src);
    9     if (destMax <= len) {
   10         return -1;
   11     }
   12     strcpy(dest, src);
   13     return len;
   14 }

scopy没有进行拷贝,hostbuf也没有初始化,此时hostbuf内存的信息为内存中的随机的信息,并且将这些信息返回给客户端,导致了内存信息泄漏。这就是为什么上面burp suite response会出现乱码的原因。

1625 PUBLIC void websRedirect(Webs *wp, cchar *uri)
   1 {
            .....
            .....
            .....

  22     if (smatch(uri, "http://") || smatch(uri, "https://")) {
  23         /* Protocol switch with existing Uri */
  24         scheme = sncmp(uri, "https", 5) == 0 ? "https" : "http";
  25         uri = location = makeUri(scheme, hostbuf, 0, wp->url);
  26     }
  27     secure = strstr(uri, "https://") != 0;
  28     fullyQualified = strstr(uri, "http://") || strstr(uri, "https://");
  29     if (!fullyQualified) {
  30         port = originalPort;
  31         if (wp->flags & WEBS_SECURE) {
  32             secure = 1;
  33         }
  34     }
  35     scheme = secure ? "https" : "http";
  36     if (port <= 0) {
  37         port = secure ? defaultSslPort : defaultHttpPort;
  38     }
  39     if (strstr(uri, "https:///")) {
  40         /* Short-hand for redirect to https */
  41         uri = location = makeUri(scheme, hostbuf, port, &uri[8]);
  42
  43     } else if (strstr(uri, "http:///")) {
  44         uri = location = makeUri(scheme, hostbuf, port, &uri[7]);
  45     } else if (!fullyQualified) {
  46         uri = location = makeUri(scheme, hostbuf, port, uri);
  47     }
  48     message = sfmt("<html><head></head><body>\r\n\
  49         This document has moved to a new <a href=\"%s\">location</a>.\r\n\
  50         Please update your documents to reflect the new location.\r\n\
  51         </body></html>\r\n", uri);
  52     len = slen(message);
  53     websSetStatus(wp, HTTP_CODE_MOVED_TEMPORARILY);
  54     websWriteHeaders(wp, len + 2, uri);
  55     websWriteEndHeaders(wp);
  56     websWriteBlock(wp, message, len);
  57     websWriteBlock(wp, "\r\n", 2);
  58     websDone(wp);
  59     wfree(message);
  60     wfree(location);
  61 }

0x4 总结一下

漏洞产生的原因是因为没有初始化内存,可能我见识比较少,感觉这种漏洞比较不常见,挖到这个漏洞的Dbappsecurity老哥是代码审计到的?

关键词:[‘安全技术’, ‘漏洞分析’]


author

旭达网络

旭达网络技术博客,曾记录各种技术问题,一贴搞定.
本文采用知识共享署名 4.0 国际许可协议进行许可。

We notice you're using an adblocker. If you like our webite please keep us running by whitelisting this site in your ad blocker. We’re serving quality, related ads only. Thank you!

I've whitelisted your website.

Not now