CVE-2022-1975 is a real-world reminder that even small mistakes in the Linux kernel can have big impacts. This vulnerability, discovered in May 2022, is found in the NFC (Near Field Communication) kernel code, specifically in the /net/nfc/netlink.c source file. By understanding and exploiting this bug, an attacker can crash (panic) the Linux kernel simply by simulating an NFC device from user space.

Let’s break down what happened, how it can be exploited, illustrate with some code, and link you to the original resources.

What is the Bug?

This CVE concerns a "sleep-in-atomic" bug. In kernel programming, some operations aren't allowed to "sleep" (i.e., wait/block), especially while holding certain locks. If they do, the kernel can crash or freeze. In this case, the NFC subsystem did exactly that — it called a function that could sleep while in an atomic context.

The problematic file is net/nfc/netlink.c. This code handles communication between user-space programs and the NFC subsystem in the Linux kernel.

The relevant part of the code is this function (simplified for clarity)

static int nfc_genl_dep_link(struct sk_buff *skb, struct genl_info *info)
{
    ...
    device = nfc_get_device(idx);
    if (!device)
        return -ENODEV;

    // [BUG] This function may sleep, but is called with locks still held!
    nfc_dep_link_up(device, ...);

    ...
}

The call to nfc_dep_link_up() can sleep, but the kernel is holding a lock (the RTNL_LOCK) at this point, which makes sleeping unsafe.

If an attacker from user-space issues a crafted netlink message (simulating an NFC device), the kernel code takes the dangerous path and may crash. This can be triggered without any special privileges other than the ability to interact with the nfc subsystem (which is sometimes available to unprivileged users, depending on system setup).

Kernel crashes (typically a panic or 'scheduling while atomic' error).

Here is a Python 3 code snippet demonstrating the *basic idea* of triggering the bug using netlink:

import socket
import struct

# Netlink constants for NFC
NETLINK_NFC = 19
NFC_GENL_ID = x1D  # Usually the NFC generic netlink family ID (may vary)
NFC_CMD_DEP_LINK_UP = xb  # DEP linkup command (see nfc-genl.h)

# Create netlink socket
s = socket.socket(socket.AF_NETLINK, socket.SOCK_RAW, NETLINK_NFC)

ifmsg = struct.pack("=IHHI", , , , )  # placeholder
genlhdr = struct.pack("=BBH", NFC_CMD_DEP_LINK_UP, 1, )
payload = genlhdr + ifmsg

# Netlink header
nlmsghdr = struct.pack("=IHHII", 16+len(payload),  # length
                               ,                 # message type (could be NFC family)
                               ,                 # flags
                               1,                 # seq
                               )                 # pid

# Complete message
msg = nlmsghdr + payload

# Send message
s.send(msg)

*WARNING: Running such code can crash your kernel!*

Denial of Service: The attack causes a kernel panic, leading to a full system crash.

- Potential for Privilege Escalation: In some scenarios, triggering kernel bugs can be a stepping stone to gaining higher privileges. However, this specific bug is best known as a DoS (Denial of Service).

# Fix

Linux devs fixed this by restructuring the code to not sleep while holding atomic locks.

The patch and technical analysis can be found in these references

- Kernel.org Patch
- Red Hat Bugzilla
- CVE Details for CVE-2022-1975

Recommendations

- Update Your Kernel: Make sure you run a Linux kernel version that includes the fix (Linux 5.18+ or with the relevant backported patch).

Restrict NFC Access: Unless you need NFC, consider blacklisting the module:

Add blacklist nfc to /etc/modprobe.d/blacklist.conf.

Summary

CVE-2022-1975 is a great example of how a small mistake in kernel code — calling a sleepable function while holding a lock — can let an attacker crash your Linux system by simulating NFC activity from user-space. Patch your systems, review permissions, and stay safe!

References

- Original kernel patch
- Red Hat Security Advisory
- NFC subsystem documentation

Timeline

Published on: 08/31/2022 16:15:00 UTC
Last modified on: 09/07/2022 16:49:00 UTC