论坛首页 漏洞分析研究区 阅读主题

[分享]CVE-2021-3156漏洞分析:从sudo堆溢出到提权的技术剖析

157 浏览 0 回复
#1 楼主 2026-06-01 21:09:06
概述2021年1月,一个影响近十年所有Linux发行版的严重本地提权漏洞被发现,该漏洞被分配编号CVE-2021-3156,因其利用方式被安全社区称为“Baron Samedit”。该漏洞允许任何非特权用户在默认配置的Linux系统上获得root权限,影响了从Ubuntu、Debian到CentOS、RedHat等主流发行版。漏洞基本信息CVE编号:CVE-2021-3156漏洞类型:基于堆的缓冲区溢出影响范围:sudo 1.8.2 - 1.8.31p2, 1.9.0 - 1.9.5p1CVSS评分:7.8(高危)发现者:Qualys安全研究团队技术背景:sudo与参数解析sudo是Linux/Unix系统中用于临时提升权限的核心工具,它允许授权用户以root身份执行命令。在执行过程中,sudo需要对用户输入的命令参数进行解析和处理。漏洞存在于sudoers策略插件中,具体位置在sudoers.so模块的set_cmnd()函数。该函数负责将命令行参数复制到堆缓冲区中,用于日志记录和策略匹配。漏洞原理分析1. 根本原因漏洞的核心问题在于命令行参数解析时的逻辑错误。当sudo以特殊模式(-s或-i选项)运行时,它会在参数后添加反斜杠转义,但错误地判断了何时需要添加转义。关键代码段(简化):c复制下载// 漏洞代码逻辑for (size = 0, av = NewArgv + 1; *av; av++) {
    size += strlen(*av) + 1;
    if (size >= cmnd_size) {
        cmnd_size += 8192;
        user_cmnd = realloc(user_cmnd, cmnd_size);
    // 错误:没有正确检查转义条件
    for (from = *av; *from; from++) {
        if (from[0] == '\\' && !isspace(from[1]))
            continue;  // 错误逻辑:跳过而不复制反斜杠
        *user_cmnd++ = *from;
    *user_cmnd++ = ' ';}2. 触发条件要触发漏洞,需要满足:sudo以-s(启动shell)或-i(模拟初始登录)选项运行命令行参数以单个反斜杠\结尾该反斜杠后跟空白字符(空格、制表符等)例如:bash复制下载sudo -s '\' `perl -e 'print "A" x 1000'`3. 溢出机制当遇到上述情况时:解析器看到反斜杠加空白字符的组合它错误地认为需要跳过反斜杠而不复制但缓冲区指针仍向前移动,导致写入位置计算错误后续复制操作会超出分配的堆缓冲区边界漏洞利用技术分析堆布局与内存破坏堆风水(Heap Feng Shui):攻击者通过控制分配和释放操作,精心布局堆内存目标是在user_cmnd缓冲区后放置敏感数据或控制结构溢出目标:c复制下载struct service_user {
    char *name;
    char *library;
    int free_name;};通过覆盖service_user结构,可以控制library指针,实现任意代码执行利用步骤:
a. 通过多次分配和释放操作塑造堆布局
b. 触发缓冲区溢出,覆盖相邻的service_user结构
c. 将library指针指向攻击者控制的路径
d. 触发nss_load_library()调用,加载恶意库
e. 恶意库的构造函数以root权限执行实际利用的限制与挑战ASLR绕过:需要信息泄露或部分覆盖技术堆分配随机性:现代glibc的堆分配具有一定随机性大小限制:溢出数据量受命令行长度限制修复方案分析官方补丁sudo项目发布了1.9.5p2版本修复此漏洞,主要修改包括:正确转义处理:c复制下载// 修复后的逻辑for (size = 0, av = NewArgv + 1; *av; av++) {
    size += strlen(*av) + 1;
    if (size >= cmnd_size) {
        cmnd_size += 8192;
        user_cmnd = realloc(user_cmnd, cmnd_size);
    // 修复:正确处理所有情况
    for (from = *av; *from; from++) {
        if (from[0] == '\\' && !isspace((unsigned char)from[1])) {
            if (from[1] != '\0') {
                // 复制反斜杠
                *user_cmnd++ = *from;
        } else {
            *user_cmnd++ = *from;
    *user_cmnd++ = ' ';}边界检查增强:添加更严格的缓冲区边界检查改进大小计算逻辑临时缓解措施在补丁可用前,系统管理员可以采用以下缓解措施:删除sudo的setuid位:bash复制下载chmod 0755 /usr/bin/sudo但这会破坏sudo的正常功能限制sudo使用:bash复制下载# 在/etc/sudoers中添加Defaults !use_pty使用sudo的noexec功能:bash复制下载# 限制shell执行admin ALL=(ALL) ALL, !/bin/bash, !/bin/sh漏洞影响与启示影响评估广泛性:影响2011年以来几乎所有Linux发行版严重性:本地提权,无需用户交互隐蔽性:漏洞存在于核心系统工具中安全启示输入验证的重要性:即使是信任边界内的工具也需要严格的输入验证最小权限原则:sudo这样的特权工具应尽量减少攻击面代码审计的必要性:关键安全工具的代码需要定期审计深度防御:即使单个漏洞被利用,其他安全机制应能提供保护检测与响应漏洞检测:bash复制下载# 简单的检测脚本sudoedit -s '\' `perl -e 'print "A" x 100'` 2>&1 | grep -q "malloc" && echo "VULNERABLE"入侵检测:监控异常的sudo使用模式检查/etc/ld.so.preload等文件的变化使用审计子系统记录所有sudo调用总结CVE-2021-3156是一个典型的逻辑漏洞导致的缓冲区溢出案例,它展示了几个重要安全原则:边界检查失败:即使是最成熟的工具也可能存在基本的缓冲区处理错误路径组合触发:多个条件组合才能触发的漏洞可能长期潜伏权限提升影响:系统核心工具的漏洞影响尤为严重这个漏洞也提醒我们,安全是一个持续的过程,即使是被广泛使用和审计的工具也可能存在严重的安全问题。定期的更新、深度防

...(已截断)

---
来源: 看雪论坛
原文链接: https://bbs.kanxue.com/thread-289340.htm

暂无回复,快来抢沙发吧!

请登录后参与讨论

立即登录 注册账号