Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

IOCreatePlugInInterfaceForService returns mysterious error

I am trying to use some old IOKit functionality in a new Swift 4.0 Mac app (not iOS). I have created a bridging header to use an existing Objective C third party framework, DDHidLib, and I am current working in Xcode 9.

The code that attempts to create a plug in interface for a usb gamepad falls over on IOCreatePlugInInterfaceForService, returning a non-zero error.

The truly bizarre thing is I have an older app created in a previous version of Xcode that uses the same framework and works correctly after opening in the new Xcode 9. This previous project is still Swift using a bridging header for the same Obj-C framework. I have checked the build settings and tried to make everything match, but I get the same result; the old app works but any new apps do not.

Is there a way to either: find out the exact differences in build settings/compilers to see what the elusive difference may be, OR to step into the IOCreatePlugInInterfaceForService IOKit method to see what may be causing the error to be returned in one project but not another?

EDIT: Here is the method that is failing:

- (BOOL) createDeviceInterfaceWithError: (NSError **) error_; {
io_name_t className;
IOCFPlugInInterface ** plugInInterface = NULL;
SInt32 score = 0;
NSError * error = nil;
BOOL result = NO;

mDeviceInterface = NULL;

NSXReturnError(IOObjectGetClass(mHidDevice, className));
if (error)
    goto done;

NSXReturnError(IOCreatePlugInInterfaceForService(mHidDevice, kIOHIDDeviceUserClientTypeID,kIOCFPlugInInterfaceID,&plugInInterface,&score));
if (error)
    goto done;

//Call a method of the intermediate plug-in to create the device interface
NSXReturnError((*plugInInterface)->QueryInterface(plugInInterface, CFUUIDGetUUIDBytes(kIOHIDDeviceInterfaceID), (LPVOID) &mDeviceInterface));
if (error)
    goto done;

result = YES;

done:
    if (plugInInterface != NULL)
    {
        (*plugInInterface)->Release(plugInInterface);
    }
    if (error_)
        *error_ = error;
    return result;
}

In the old version that works, IOCreatePlugInInterfaceForService always returns a value of 0. In all the versions that don't work, the return value appears to always be -536870210. The mHidDevice in this function is the io_object_t handle for the device.

EDIT2: Here is the IORegistryExplorer page for the device

Here is the IORegistryExplorer page for the device

like image 885
user3746571 Avatar asked Feb 16 '18 17:02

user3746571


1 Answers

Finally managed to resolve this after weeks of head scratching. The new Xcode 9 uses app sandboxing to basically prevent access to USB, bluetooth, camera and microphone etc. by default in a new app. Once I switched this off it reverted to it's expected behaviour.

Glad it was such a simple answer in the end but disappointed Xcode does not provide more descriptive error messages or responses to let a user know they are essentially preventing themselves from accessing the parts of the system they need.

like image 110
user3746571 Avatar answered Sep 29 '22 08:09

user3746571