GitLab满分漏洞已被利用:先保全日志,再判断文件是否外泄

新加坡网络安全局在9月17日发布的 GitLab安全警报 中称,攻击者正利用CVE-2026-85706读取服务器文件,公开概念验证代码也已出现。该漏洞的CVSS 3.1评分为10.0,利用不要求攻击者事先登录。
风险集中在GitLab Self-Managed:受影响的是GitLab CE和EE 18.7.0至19.1.7、19.2.0至19.2.5,以及19.3.0至19.3.1。管理员必须升级,但在升级或重启之前应先保存日志;补丁只能阻止后续利用,不能说明此前是否已有文件内容离开服务器。
三个版本线受影响,在野利用已经确认
CVE-2026-85706位于repository commits API。攻击者可在POST请求的file.path参数中提供任意服务器路径,使GitLab打开预期上传缓冲区之外的文件;问题涉及路径限制不当和身份验证缺失。
Rapid7的漏洞分析 记录了明确的修复界线:18.7至19.1版本线需升级到19.1.8,19.2版本线需升级到19.2.6,19.3版本线需升级到19.3.2;CISA已在9月11日依据主动利用证据将该漏洞纳入Known Exploited Vulnerabilities目录。GitLab.com已经修补,GitLab Dedicated客户无需为该漏洞采取行动,采用Linux package、源码或Helm部署的受影响自建实例则需自行升级和调查。
“已被利用”并不表示每台暴露在互联网中的旧版实例都已遭到入侵,但升级也不能替代取证。文件被服务器打开、文件字节被写入HTTP响应,以及泄露的凭据随后被使用,是三个需要分别验证的事实。
先保全日志,避免重启切断证据链
GitLab的取证说明 要求在升级或重启前快照日志,因为重启会轮转Workhorse日志,并可能覆盖调查所需的记录;该说明还指出,恢复api_error中的实际响应内容需要连续解析两层JSON,否则换行和引号仍会保持转义形式,可能妨碍识别多行密钥。
Linux package部署应保存全部轮转版本的gitlab-rails/api_json.log、当前GitLab Workhorse日志以及Nginx日志。源码部署需要保留相应的api_json.log;Helm部署则需收集Webservice Pod和Workhorse sidecar或Pod的日志。
证据副本应作为可能含有秘密的材料保存。发生披露时,api_error会以明文包含客户端实际收到的文件片段,其中可能出现令牌、密码或私钥;解析出的结果不宜直接显示在普通终端或写入未受保护的工单。
候选记录可从POST /api/v4/projects/:id/repository/commits请求中筛选,重点检查file.path和metadata.path是否指向上传沙箱之外的位置。路由、参数名和路径都可能经过百分号编码,因此仅匹配一种固定拼写可能漏掉请求;每条候选记录还需保留correlation_id,以便关联Workhorse访问日志。
HTTP状态码不能证明内容已经外泄
漏洞会让服务器读取目标文件,但内容只有在后续百分号解码失败、错误消息嵌入出错片段时才会返回客户端。因此,HTTP 200、400或401只能描述请求处理结果,不能单独证明文件内容已经外泄,也不能证明文件从未被读取。
是否触发披露取决于被解析的文件片段:其中出现“%”且后面不是两个十六进制字符时,解码会失败,相关片段才可能进入响应。若文件中不存在这种序列,服务器仍可能已经读取文件,但不会通过这条错误路径把文件字节传给客户端。
目标文件大小和请求中的file.size同样不能用于估算泄露量。响应还包含固定的JSON包装和转义字符,因此written_bytes可能大于一个较小目标文件的大小;对大文件而言,返回的也可能只是触发解析错误的局部片段。
用correlation_id连接Rails与Workhorse日志
判定时,应先从Rails的api_json.log提取可疑请求及correlation_id,再在Workhorse访问日志中找到同一标识对应的access记录。Workhorse的written_bytes记录该请求实际发送给客户端的响应字节数,Rails的api_error则保存发给客户端的错误字符串,两者共同界定是否存在内容披露。
管理员需要为本实例建立“文件不存在”时的响应基线。固定错误正文通常产生54字节响应,但反向代理、响应压缩以及补丁前后的行为差异都可能改变Workhorse记录的数值,因此54字节只能作为近似参照,不能直接套用于全部历史请求。
- api_error为空或缺失,written_bytes处于不存在文件的基线:路径没有解析到可读文件,现有记录未显示文件内容被返回。
- api_error为空或缺失,written_bytes低于该基线:路径可能有效且文件已被读取,但解码成功,没有文件内容进入错误响应。
- api_error包含目标文件片段,written_bytes高于基线:可以确认该片段已返回客户端,披露范围应以恢复出的实际字节为准。
对发生披露的请求,written_bytes应与api_error字符串的字节长度相互印证。若两者不一致,应检查代理、压缩或日志采集链路是否改写或截断响应;若缺少对应日志、无法通过correlation_id关联记录,或日志转发器截断了api_error,就不能据此得出“没有外泄”的确定结论。
凭据处置范围取决于实际返回的片段
如果恢复出的响应片段中出现令牌、密码或私钥,处置范围应以具体内容为依据,并核查相关系统在可疑请求之后的认证活动。仅存在于目标文件其他位置、却没有进入任何返回片段的凭据,不能凭单次请求断言已经传给攻击者;针对同一文件的多次请求仍需逐条关联。
截至目前,可以确认的是该漏洞已进入主动利用阶段,受影响的自建实例需要升级到对应修复版或更新版本。完整日志可以分别支持“服务器读取了文件”“某段内容返回给客户端”和“哪些凭据需要处置”三类结论;记录不完整时,严谨的表述只能是现有日志未发现披露证据,而不是实例从未遭到利用。
订阅我们的新闻通讯
将最新 Web3、AI 和加密货币新闻直接发送到您的邮箱。