How macOS is moving away from kernel extensions

The CrowdStrike catastrophe has drawn attention to differences between modern macOS and Windows, and how kernel extensions (kexts) are being replaced in macOS by System Extensions. This article summarises what is changing, and how much progress macOS has made as of Sonoma 14.5.

Kernel space

The XNU kernel at the heart of macOS consists of central systems derived from Mach, BSD and I/O Kit. This runs at the highest level of privilege, in kernel space, often referred to as Ring 0 on Intel systems, although that term isn’t used for Arm CPUs as they have Exception Levels with EL0 as the least-privileged or user space. The kernel provides support for a great many services to interface with hardware and higher-level functions such as network protocols and file systems, that are almost entirely delivered as kexts running in Intel Ring 1.

Currently, in macOS Sonoma there are well over 650 kexts included in the System volume, three third-party kexts including SoftRAID that are in /Library/Extensions, and three that are firmlinked from outside the Signed System Volume (SSV), so they can be updated without creating a whole new sealed system snapshot.

Third-party code that needs direct access to kernel space has in the past used Kernel Programming Interfaces (KPIs) only accessible from kexts. These have included:

I/O Kit drivers, including USB
PCI and Thunderbolt
Serial port drivers
Audio drivers
Network drivers, for network filters
Storage drivers
File systems.

Long and sometimes bitter experience of third-party kexts has demonstrated how their bugs and incompatibilities have resulted in kernel panics, where the kernel has no choice but to force a restart. Those risk losing data, and (in older file systems including HFS+) in leaving the file system in an unstable state, requiring repair. While recent models of Mac will restart rather than just shut down following a panic, the user needs to log back in and clean up before the Mac can be used again. When this happens at scale, as occurred with CrowdStrike, it has major impact.

User space extensions

Instead of delivering access to these features in kernel space using KPIs, macOS is transitioning to access in user space, where third-party code is delivered in System Extensions, running in Intel Ring 3 (Arm EL0). This transition involves Apple providing new and modified system kexts with their replacement interfaces for the System Extension to plug into.

One particularly relevant example is support for Endpoint Security, requiring monitoring of system events to discover potentially malicious activity. In the past this was handled by third-party kexts relying on KPIs, but should now be performed by a client System Extension that registers with Endpoint Security to receive notifications of different types of event, such as processes executing and file systems being mounted. These are documented at length, and are constrained to those events that Apple chooses to expose. If a security software developer wants access to other events, then they have to ask Apple to add them to Endpoint Security.

Deprecation and substitutes

Although Apple has been making discouraging noises about kexts for years, until it provided fully functional alternatives, developers had nowhere else to go and had to stay with kexts and KPIs. Many of those were officially deprecated in Catalina, and in Big Sur kexts using those no longer load by default. Among those affected are:

Various KPIs now available in Endpoint Security
Networking KPIs now available in Network Extensions
IOHID input devices
USB drivers now available in USBDriverKit and USBSerialDriverKit
PCI drivers now available in PCIDriverKit and NetworkingDriverKit.

Network Extensions include changing Wi-Fi configuration, a Hotspot Helper to integrate with hotspots, VPN using built-in and custom protocols, network relaying, DNS configuration, and content filters.

Some replacements have been slower to arrive, and the following are among those made obligatory in Monterey 12.3 and later:

Audio using AudioDriverKit
Bluetooth using CoreBluetooth
SCSI drivers now available in SCSIControllerDriverKit.

One of the last significant features to be transitioned to System Extensions is file system support, coming to user space in Sequoia as FSKit. Although it does now have a little documentation, that reveals that this initial release only supports simple file systems with one volume in each container; support for more sophisticated file systems is coming, but I don’t think Apple has announced when.

Penalties

Intel Macs have no restrictions or security limitations when using kexts, but Secure Boot in Apple silicon Macs won’t load any third-party kexts when run at Full Security. This makes the use of kexts on M-series Macs awkward to say the least. Apple has detailed the process of downgrading security and permitting loading of a kext, involving:

Start up in Recovery mode and select Options.
Open Startup Security Utility.
Downgrade boot security to Reduced Security.
Enable the loading of third-party kexts.
Restart in normal mode, and proceed to install the app with its kext installation steps, involving authorising the new kext in Privacy & Security settings.
Once the kext has been fully installed, and built into the Auxiliary Kernel Collection, restart.

Problems

Just as there are no clear-cut classes of app, kexts don’t all fall into neat groups. Although now widely implemented in some areas, such as Endpoint Security and Network Extensions, in others System Extensions still don’t fully replace KPIs. One good example is SoftRAID, a widely used driver supporting software RAID, which has had to be incorporated into macOS distributions as it still can’t be implemented in user space.

Kits to replace KPIs are also immature. Although I have been evaluating and reviewing products such as Little Snitch and various security suites using Network Extensions and Endpoint Security without encountering any problems, developers complain that support in macOS remains unstable and has vulnerabilities. When there’s a bug in that support, it may result in a kernel panic, causing the problem that this is intended to address.

macOS hasn’t completely replaced kexts yet, but is well on the way to achieving that. The benefits to stability and security are already being realised: I like to have a steady supply of panic logs to use in articles here, but I think the last I experienced was over three years ago, back in Big Sur, the result of a bug in iBoot firmware that has long since been fixed. Maybe I’ll have to start deliberately panicking VMs next. I’ll leave you with what used to be a common sight, lest we forget.

A traditional kernel panic prior to OS X 10.8.