CVE-2023-35685 - Exploiting a Kernel Use-After-Free Bug in DevmemIntMapPages for Local Privilege Escalation

A new local privilege escalation vulnerability has been discovered in the Linux kernel. Tracked as CVE-2023-35685, this bug exists in the way the kernel manages device memory mappings in the DevmemIntMapPages function inside devicemem_server.c. Due to a logic error, a physical page can be freed and then used again (a use-after-free, or UAF). This can be abused by a local attacker to escalate privileges to root without any need for user interaction or special capabilities.

In this post, I'll walk you through what the bug is, how it happens in the code, its impacts, and how an exploit might work. You’ll also find copy-paste code, original references, and valuable insights.

What Causes the Vulnerability?

The root cause is a logic flaw in the management of physical pages during device memory mapping. Specifically, after a page is freed (released), the function can mistakenly use the freed memory, allowing an attacker to gain arbitrary code execution in kernel space.

Here's a simplified, annotated snippet inspired by the vulnerable code in devicemem_server.c

int DevmemIntMapPages(struct devicemem_ctx *dev_ctx, unsigned long phys_addr, size_t len) {
    struct page *page;

    // Step 1: Find the page
    page = find_get_page(phys_addr);

    if (!page)
        return -ENOMEM;

    // Step 2: Map the page
    int ret = map_page_to_user(dev_ctx, page, len);

    // Step 3: On error, free the page
    if (ret) {
        // Logic error: we free the page here
        put_page(page);
        return ret;
    }

    // Step 4: Later, reuse 'page' (dangling pointer!)
    // Here is the use-after-free: page could already have been freed!
    do_something_with_page(page);

    return ;
}

Any local process can trigger it (no special group or root needed).

- An attacker can free a page, allocate controlled memory in its place, and trick the kernel into using their crafted data.

Busy-wait and fill system memory with attacker-controlled objects to occupy the freed page’s spot.

3. Wait for the kernel to use the freed page pointer again, which now references attacker-controlled memory.

Here is a _hypothetical_ proof-of-concept outline (for educational purposes)

// Pseudo-flow: DO NOT USE THIS EXPLOITABLY

// Step 1: Trigger the UAF by calling DevmemIntMapPages
ioctl(devmem_fd, DEVMEM_INT_MAP_PAGES, &map_data);

// Step 2: Spray the kernel with crafted objects
for (int i = ; i < SPRAY_COUNT; i++) {
    open("/dev/vulnerable_device", O_RDWR);
}

// Step 3: Wait and hope for kernel to use our sprayed objects
// (Details depend on kernel layout and specific mapping logic)

Note: Real exploit development for Linux kernel UAFs is non-trivial and must never be done on production systems or without explicit permission.

References

- NIST National Vulnerability Database: CVE-2023-35685
- Google Security Blog: Analyzing Kernel Use-After-Free *(General UAF techniques)*
- The Art of Exploiting Use-After-Free in Kernel *(General explanation)*

Mitigation

Patches:
Maintainers have fixed the logic error in the latest upstream kernels. Always update your devices to the latest firmware/kernel releases.

Conclusion

CVE-2023-35685 is a serious Linux kernel bug from a simple logic mistake. Use-after-free vulnerabilities remain a top way for attackers to get root access, and this bug is no exception. If your system relies on device memory mapping or the affected code, *patch now*. Simple local bugs like this can destroy entire security models.

Stay safe!

*If you want to learn more about kernel vulnerabilities, follow these resources: Kernel Self-Protection Project.*

Timeline

Published on: 01/08/2025 18:15:15 UTC
Last modified on: 01/10/2025 15:30:48 UTC