CVE-2024-1086 / Netfilter Zero-Day

CVE-2024-1086: Linux Netfilter nf_tables Double Free Teardown

How an improper verdict handling bug in net/netfilter/nf_tables_api.c caused double reference drops on network packets, enabling container root breakouts.

💡 비유를 통한 쉬운 설명 (ELI5)

Think of a ticket inspector on a train. A passenger hands over a ticket. The first inspector punches the ticket and marks it as used. Then, because the passenger sneezes, an unhandled rule causes a second inspector to grab the exact same ticket and punch it again. In Linux networking, dropping a packet twice freed its memory twice, allowing malicious code to masquerade as the train conductor.

핵심 개념 및 서브시스템 용어 해설

Netfilter / nf_tables
The Linux kernel's modern packet filtering, network address translation (NAT), and packet mangling framework.
NF_DROP Verdict
A netfilter rule evaluation outcome instructing the kernel to drop and deallocate the incoming network packet (`sk_buff`).
sk_buff (Socket Buffer)
The core kernel data structure representing every network packet traveling through the Linux networking stack.
User Namespaces (unshare)
A Linux security isolation feature allowing unprivileged users to obtain root inside a sandbox, commonly abused to access nf_tables.

단계별 공격 실행 메커니즘

Step 1

1. Namespace Creation

An unprivileged user creates an isolated network namespace via unshare(CLONE_NEWUSER | CLONE_NEWNET).

Step 2

2. Injecting Malformed Rule

The attacker loads a custom nftables rule returning a negative verdict code mismanaged by the hook pipeline.

Step 3

3. Triggering Double Free

The packet processing engine drops the sk_buff, but the error return path drops the exact same packet a second time.

Step 4

4. Spraying Heap Allocations

The attacker sprays fake Page Middle Directory (PMD) entries into the freed memory, achieving full arbitrary physical memory write.

소스 코드 비교: 치명적 취약점 vs 보안 강화 패치

일반 개발자가 쉽게 이해할 수 있는 고수준 소스 코드로 제공 (어셈블리/바이너리 제외).

패치되지 않은 취약점
// VULNERABLE: net/netfilter/nf_tables_api.c before patch
static int nf_tables_newrule(struct sk_buff *skb, const struct nfnl_info *info, ...) {
    // ROOT CAUSE:
    // If verdict evaluation returns an invalid negative integer,
    // the evaluation loop treats it as both NF_DROP and an internal error!
    if (verdict < 0) {
        kfree_skb(skb); // First free of socket buffer!
        return verdict; // Calling hook also invokes kfree_skb(), triggering DOUBLE FREE!
    }
    return 0;
}
보안 강화 패치
// SECURE: net/netfilter/nf_tables_api.c patch
static int nf_tables_newrule(struct sk_buff *skb, const struct nfnl_info *info, ...) {
    // 1. Strict verdict assertion
    if (verdict < 0) {
        // Clear ownership flags to guarantee only one caller deallocates skb
        nf_tables_rule_destroy(rule);
        
        // Let the upper caller handle the single, orderly drop:
        return -EINVAL; 
    }
    return 0;
}

엔지니어링 보안 강화 체크리스트

← 전체 보안 디렉터리 보기 모든 플랫폼 보안 업데이트 →