Reputation: 412
I am currently developing a macOS application that involves communication with a System Extension (DEXT) created using DriverKit. Despite the extension appearing to be correctly installed and activated, I'm encountering an issue establishing communication between my app and the DEXT.
Here are the details:
com.Henhen1227.KeySoundboard.SoundboardDriver
.systemextensionsctl list
indicates that the DEXT is installed and active:--- com.apple.system_extension.driver_extension
enabled active teamID bundleID (version) name [state]
* * ---------- com.Henhen1227.KeySoundboard.SoundboardDriver (1.0/1) com.Henhen1227.KeySoundboard.SoundboardDriver [activated enabled]
In the app, I attempt to establish a connection to the DEXT using IOServiceGetMatchingService, but no matching services are returned, hence a connection to the user client is not established.
The ioreg -l -b
command does not yield any information related to my DEXT.
I'm working with macOS 13.4.1 and Xcode 14.3.1 (14E300c). The code for my DEXT is closely modeled on Apple's sample code for creating an audio driver, found here. Interestingly, even when I attempt to run the unmodified sample code (ensuring proper signing and setup), I face the same issue.
The relevant snippets (from Apple's sample project):
Activating the extension (current called in viewDidLoad)
/// - Tag: ActivateExtension
func activateExtension(_ dextIdentifier: String) {
let request = OSSystemExtensionRequest
.activationRequest(forExtensionWithIdentifier: dextIdentifier,
queue: .main)
print(dextIdentifier)
print(request.description)
request.delegate = self
OSSystemExtensionManager.shared.submitRequest(request)
}
Called on main thread 5 seconds after activate extension is called. Keeps returning "Driver Extension is not running."
// Open a user client instance, which initiates communication with the driver.
- (NSString*) open
{
if (_ioObject == IO_OBJECT_NULL && _ioConnection == IO_OBJECT_NULL)
{
// Get the IOKit main port.
mach_port_t theMainPort = MACH_PORT_NULL;
kern_return_t theKernelError = IOMainPort(bootstrap_port, &theMainPort);
NSLog(@"theMainPort: %u, theKernelError: %u", theMainPort, theKernelError);
if (theKernelError != kIOReturnSuccess)
{
return @"Failed to get IOMainPort.";
}
// Create a matching dictionary for the driver class. Note that classes
// published by a dext need to be matched by class name rather than
// other methods. So be sure to use IOServiceNameMatching rather than
// IOServiceMatching to construct the dictionary.
CFDictionaryRef theMatchingDictionary = IOServiceNameMatching(kSoundboardDriverClassName); // kSoundboardDriverClassName = "SoundboardDriver"
NSLog(@"theMatchingDictionary: %@", theMatchingDictionary);
io_service_t matchedService = IOServiceGetMatchingService(theMainPort, theMatchingDictionary);
NSLog(@"matchedService: %u", matchedService);
theKernelError = IOObjectRelease(matchedService);
NSLog(@"IOObjectRelease theKernelError: %u", theKernelError);
if (theKernelError != KERN_SUCCESS) {
return @"IOServiceGetMatchingService failed with error: %u";
}
if (matchedService)
{
_ioObject = matchedService;
theKernelError = IOServiceOpen(_ioObject, mach_task_self(), 0, &_ioConnection);
NSLog(@"_ioObject: %u, _ioConnection: %u, IOServiceOpen theKernelError: %u", _ioObject, _ioConnection, theKernelError);
if (theKernelError == kIOReturnSuccess)
{
OSStatus error = [self checkDeviceCustomProperties];
if (error)
{
return @"Connection to user client succeeded, but custom properties could not be validated";
}
return @"Connection to user client succeeded";
}
else
{
_ioObject = IO_OBJECT_NULL;
_ioConnection = IO_OBJECT_NULL;
return [NSString stringWithFormat:@"Failed to open user client connection, error:%u.", theKernelError];
}
}
return @"Driver Extension is not running";
}
return @"User client is already connected";
}
I'd greatly appreciate any insight or advice on this matter. What could be causing these issues and how might I resolve them to establish a connection to the DEXT from my app?
Thank you for your time and help!
Edit 1:
Looking into the console app, I see the following fault when I try to run the extension:
activateDecision found two entries for teamID("5BHAWQJGY5") com.Henhen1227.KeySoundboard.SoundboardDriver in state:
7B8B8559-3F37-4236-B39B-DE0CB791DD37 (1.1): terminating_for_upgrade_via_delegate
11C738A7-A013-4464-95C6-0AB5829B66CC (1.1): activated_enabled
Running systemextensionsctl list
again returns two extensions:
5BHAWQJGY5 com.Henhen1227.KeySoundboard.SoundboardDriver (1.1/2) SoundboardDriver [terminating for upgrade via delegate]
* * 5BHAWQJGY5 com.Henhen1227.KeySoundboard.SoundboardDriver (1.1/2) SoundboardDriver [activated enabled]
Upvotes: 3
Views: 220