Gain user-space access to hardware devices and drivers using IOKit.

Posts under IOKit tag

200 Posts

Post

Replies

Boosts

Views

Activity

Capturing USB traffic
Hi, I want to capture the USB traffic for my app running on High Sierra. I brought the if XHC20 up and can capture the traffic using Wireshark nightly builds. But I only see incoming traffic (from device to host) but not the other direction. Any ideas what is going wrong here?Starting the IF:> sudo ifconfig XHC20 upAfter that I can select the IF in Wireshark and start capturing packets. I can see incoming traffic from attached devices but not the outbound messages.
8
0
15k
Mar ’23
Correct way to read out information about current energy usage battery&charger/adapter
I'm looking for a way to read out the current energy drain of various macOS devices that should be backwards compatible at least to macOS 12. So far I already had a couple of good idea – well initially I thought so – to get that data from ioreg or IOKit, reading out AppleSmartBattery object. I'm trying to write a small program in Rust that collects the energy usage of our companies macOS devices and record this how much happened while in the office and how much on the road. Therefore I need to consider cases where the battery is charging as well as the battery is full and energy is drawn from the power adapter or usb-c connected display directly via PD. So far I was able to read the desired data out via ioreg with plist output and parse the information into a struct. The issue I have testing this out that my 1st approach of going for PowerTelemetryData which would be perfect is only available on macOS 13+ systems. The second approach reading out the subobjects of BatterData and PowerOutDetails seem to only be available on macOS 12 devices now and then. Any suggestions or hints?
1
0
1.1k
Feb ’23
stop charging while plugged in
Is it possible to change the internal operating system of apple's charging methods? So if I want to make an app or some code to make a MacBook stop charging at a certain percentage while it's still plugged in and then let the battery drain until 20%, it automatically starts charging again to 80%. All while it's plugged in. Does apple allow this? to make something like this?
2
0
1k
Feb ’23
Reading EDID data on Apple M1 devices
Is there any way to read EDID data in new Apple M1 devices since the below code snippet does not work in M1 machines however it works in Intel based Mac. io_object_t object = -1;       io_iterator_t iterator;     CFMutableDictionaryRef matching = IOServiceMatching("IODisplayConnect");     kern_return_t kernResult = IOServiceGetMatchingServices(kIOMasterPortDefault, matching, &iterator);       if (KERN_SUCCESS == kernResult && iterator != 0) {           object = IOIteratorNext(iterator);           while (object != 0) {               CFDictionaryRef dict = IODisplayCreateInfoDictionary(object, kIODisplayOnlyPreferredName);       /*        process data here        */               object = IOIteratorNext(iterator);     }     IOObjectRelease(iterator);   } Also tried replacing "IODisplayConnect" by "IODPDevice" but still get an empty iterator.
5
0
5.6k
Feb ’23
Improving battery reading when the machine wakes.
I am using the CFProperty "AppleRawCurrentCapacity" value from IOServiceGetMathcingService( kIOMainPortDefault, IOServiceMatching( "AppleSmartBattery" ) ) to obtain the mAh value of the MacBook's battery. Once when the app receives the NSWorkspace notification of display sleep, and once again when receiving the NSWorkspace notification of display wake. I then calculate how much battery was expended during sleep by deducting the pre value from post value. The results can wildly vary, from it using 16 mAh per hour, to gaining 10 mAh an hour (without being plugged in). Sometimes a 10 hour sleep doesn't use any mAh... Which is clearly wrong. When my app detects the key kIOPMPSInvalidWakeSecondsKey is present, I set a timer for that period + 3 seconds and attempt to read the battery values again. Yet the results can still wildly vary. I see on Intel Macs there is a kIOPMPSMaxErrKey (set to 9 on a 2019 16"), however I don't see this on M1, and don't know how it can help, if it does exist. Can anyone give me any pointers as to what I am doing wrong, or in the direction of obtaining reliable mAh values? I like mAh as it's more precise that the standard integer values of 0 - 100, but I don't have to stick with mAh, I'd just don't like reporting that a 16 hour sleep didn't use any battery, when I know it's not true. Thanks
1
0
1.2k
Jan ’23
iPad 10th Gen and IOKitLib/IOHIDManager
I'm creating an iPad room information app which needs to communicate over USB with an LED light strip. The USB controller is HID class, vendor ID is 0x20a0 and product ID is 0x41e5. It requires sending a simple feature report to control the LEDs. I've got it working on the Mac using IOKit, and compiling on the 10th gen USB C iPad using copied headers and bridging IOKitLib and IOHIDManager, but sandboxing prevents the code executing on the iPad (IOServiceOpen failed: 0xe00002e2). Is joining the MFi program really the only way to get this to get the necessary entitlements? At our current scale, we don't need to distribute in the App Store.
0
0
1.4k
Jan ’23
Querying for electronics relevant information of my MacBook via native code
Howdy! I have been experimenting with my system's electronics (MacBook Pro 13-inch, M1, 2020) by using software probe written in C/C++ type program. The idea is to extract the relevant information just like it is presented in Apple > About This Mac > System Report, for my cross-platform Engine. I have been tinkering with a tool dmidecode. It works just fine on Linux and Windows. For MacOS, I need to find a graceful way of obtaining the AppleSMBIOS service, in this context. To my best of knowledge, the service is nonexistent as I have checked by C code and some application named IORegistryExplorer (courtesy Google). Just wondering if someone has been on such endurance and how much satisfaction has been achieved upon the topic. Thanks a lot!
9
0
1.9k
Jan ’23
USB device ID
I am new to Mac and got a question. Got a third party USB device and its old library source which has the device old Vendor ID. The device with new Vendor ID is not compatible with old library. So change the Vendor ID in the old source, rebuild it, and use the lib?. Can I use the device in a new Mac?.
3
1
5.4k
Jan ’23
Issues with MSI(x) handling
I've a basic IOPCIDevice driver for a custom device that supports MSI(x). The interrupt filter doesn't get called if I passthe msi index to the IOFilterInterruptEventSource. That's a first problem.The filter is continously called if I don't pass the msi index. That's a 2nd problem.Interrupt was triggered when I initialized the device. In the filter I cleared the cause register. For some reasonintr mask register was already cleared when the filter is called which is another problem.Any clues/pointers?
3
0
1.8k
Dec ’22
How can I use USBmakebmRequestType with DriverKit
I'm building a driver in C++ for my iPad using DriverKit. I'm trying to make a request to a control endpoint, so I'm trying to use DeviceRequest: https://developer.apple.com/documentation/usbdriverkit/iousbhostinterface/3182582-devicerequest But the first parameter ask for USBmakebmRequestType which it's a macro defined in IOKit > USB.h I tried to #include <IOKit/USB.h> and #include <IOKit/usb/USB.h> and  but it doesn't find the header. Any idea? thanks.
1
0
1.6k
Dec ’22
Different Drivers for Individual Interfaces
Hello We have a USB camera. My Mac can recognize it and we can get frames with any software. There is a physical button on it and the vendor says the camera is UVC-compliant. But button doesn't work anyway. I captured some USB traffic data and saw that it has two interfaces. One for streaming and other one for interrupting (like button click). I read UVC 1.5 standards to understand it and it is working like written in UVC 1.5. So, I can get a data with an interrupt transfer when clicking the button. I checked these two interfaces, they use UVCAssistant for driver(System Extension). I tried to use libusb, I can get data from button click. But for frames I had to use libuvc, but it wasn't work for my camera (I think it is related with USB descriptor parsing in libuvc). I thought that I should write a driver for single interface and so second interface will use same UVC assistant driver and first interface will use my driver. I wrote a driver and it matches with first interface. But second interface is empty (unhandled by any driver). I want to load UVCAssistant for second interface of USB port. How can I do this? Output before loading my driver After loading: IOKitPersonalities that I used:
2
0
1.7k
Dec ’22
IOKit or IOUSBHost for USB device acces from user space
USB-Devices without macOS support Every so often I find usefull USB consumer hardware without any macOS support. At best accompanied with some sample code aimed at Linux using libUSB and/or a datasheet [1]. Using code snippets from long since archived IOKit documentation I can deal with that. IOUSBHost Using working IOKit based ObjC Foundation command-line code[2] as reference I am attempting to use theIOUSBHost framework (ObjC Foundation tool). IOUSBHost documentation[3] has all the ingredients but lacks a recipy. Starting with a plugged-in USBDevice and using its idVendor and idProduct[4] I can initialize and destroy base class IOUSBObject and get notified when I unplug the USBDevice. initialize and destroy IOUSBHostDevice[5] and retrieve various descriptors [6] and configure with value: 0, and even do a vendor bmRequestType request without error. But since I already beforehand know the content of my descriptors I can start with IOUSBHostInterface?[7] , needed for my 3 pipes, interrupt, bulk in and out. But Error:Unable to open io_service_t object and create user client. with reason: Exclusive open of usb object failed, whether I asked for exclusive access or not. So I could do with some guidance on how to use IOUSBHost[8]. Let Any Pointer bring joy. Using: Apple M1 Max, MacOS 13.0.1 (22A400), Xcode 14.1 (14B47b) Alternatives considered: Raspberry Pi using UDP (JSON;) over wifi. [1] e.g. https://www.digchip.com/datasheets/parts/datasheet/280/DS2490-pdf.php [2] depending on usage this might need a runloop [3] including dec 2022 https://www.usb.org/sites/default/files/usb_32_202206.zip I failed to find the phrase 'Host-mode'. HINT start by inspecting chapter 9 to get a taste of the terms like function, class, address and value and number. Those wordings will also appear in Apple's documentation. NOTE Tables in chapter 9: Assuming D[n]: stands for bitNr[n] in a bitmap where D[0] is the least significant bit. USEFULL No. [4] use the IORegistryExplorer.app and/or ioreg in Terminal [5] IOUSBHostInterface.h tells me: CFMutableDictionaryRef to be used with IOService matching methods. To be released by caller. But as far a I know CFFoundation is now under ARC. [6] IOUSBInterfaceDescriptor * next = IOUSBGetNextInterfaceDescriptor(configurationDescriptor, nil); while (next != nil) // needs cast (IOUSBDescriptorHeader *)next [7] signed to run locally [8] My next step would be using Swift. Off topic but related and disturbing in a type safe world https://forums.swift.org/t/nsdata-data-vs-data-withunsafebytes/50231/5 Please please please never use NSData.bytes in Swift code. Is this why IOUSBHostObject ioDataWithCapacity uses NSMutableData? Quote: Because the kernel backs the NSMutableData object, the length and capacity aren’t mutable. Any changes to the length or capacity throws an exception. Effectively treating NSMutableData as NSData, only the compiler complains beforehand when an attempt is made to modify the length of NSData (data.bytes ARE mutable)
0
1
2.1k
Dec ’22
How do I invert the luminosity of the display using a color matrix or something else?
I recently came across a program that used data tables to invert the display, however it was a windows only application and I am wondering how I can write a similar thing for Mac, or if there is one already available. The app and config file is attached below so you can sort of dissect how it works Config File: [negativescreen.conf](https://developer.apple.com/forums/content/attachment/f4b67ed7-fa71-4ee6-9c0d-18febe2c3381) Readme file: [README.md](https://developer.apple.com/forums/content/attachment/86bd72f6-46c9-42d5-a925-561f75f24ae8) Window$ Executable: [NegativeScreen.exe](https://developer.apple.com/forums/content/attachment/a4478bd5-d5c7-41dd-9302-0e1a929372c2)
0
0
1.6k
Dec ’22
Serial Communication Application
We have been looking into developing an application for iOS that will allow the phone to connect to a sensor through a serial connection. The purpose is to change the settings of the sensor using the phone. However, I have been made aware that we would be unable to develop such an app unless we enroll in the MFI program. We considered alternatives such as using Redpark’s cables and their SDKs, but according to them publishing would not be possible. They mentioned we could develop the app and publish through Apple Business Manager to distribute to corporate customers, but as far as I could tell, this requires the customer to be enrolled in the Apple Business Manager program as well. What we wish to do is publish publicly in both iOS and Android, but for iOS there doesn’t seem to be support for serial communication, and I am assuming appropriate APIs/SDKs are available only through the MFI program. I would like to know what options we have and how we can explore them. Thank you very much for your time.
3
0
3.9k
Dec ’22
DriverKit Share Memory from User Client to App for Streaming
Does anyone have an example of streaming video data from a user client to a client app? I have successfully set up a DriverKit USB hardware driver that commands a device to successfully fill the same IOBufferMemoryDescriptor at 30fps with new data (verified in driver). I have also managed to map this buffer to the application using CopyClientMemoryForType in the user client and IOConnectMapMemory64 in the app. I have also confirmed the data is the intended image data. What I CAN NOT do is see updates in the mapped memory in the app. I map and unmap the data, but the contents don't change. No matter how many times I map, CopyClientMemoryForType is called once. How should changes to the underlying dext space memory be reflected/synchronized to the app? Can I not share a single buffer (4-12MB, ringed) and synchronize updates?
1
0
1.2k
Nov ’22
DriverKit demo app doubts
Hello everyone, I downloaded the demo app from the driverkit demo located at https://developer.apple.com/documentation/driverkit/communicating_between_a_driverkit_extension_and_a_client_app, I downloaded the files and followed the process in the two possible ways by letting xcode automatically sign the app and by me creating the provisioning profiles, everything compiles but I am facing this particular issue whenever I try to invoke the system installation of the driver:2022-11-16 00:45:12.425147-0600 DriverKitSampleApp[5837:69830] sysex didFailWithError: The operation couldn’t be completed. (OSSystemExtensionErrorDomain error 9.) There is very little to none information on the web, and I dont know what else to do at this point.
1
0
1.4k
Nov ’22
How to get data from the device using IOBufferMemoryDescriptor in driverKit
I'm trying to create a driver for my usb device, using iOS and DriverKit. I'm basing my code in the example used in WWDC: https://github.com/knightsc/USBApp My driver starts fine when the device is connected and the readCompleted method is called fine, but the action->GetReference() gets only \0 characteres. Also in order to know that the usb device is actually working I've connected it to my mac first and using PyUSB I can see that it's returning data in chunks of 1024 bytes in the interface 0. This is the data I get in PyUSB: array('B', [6, 0, 1, 0, 2, 0, 3, 0, 4, 0, 5, 0, 6, 0, 7, 0, 8, 0, 9, 0, 10, 0, 11, 0, 12, 0, 13, 0, 14, 0, 15, 0, 16, 0, 17, 0, 18, 0, 19, 0, 20, 0, 21, 0, 22, 0, 23, 0, 24, 0, 25, 0, 26, 0, 27, 0, 28, 0, 29, 0, 30, 0, 31, 0, 32, 0, 33, 0, 34, 0, 35, 0, 36, 0, 37, 0, 38, 0, 39, 0, 40, 0, 41, 0, 42, 0, 43, 0, 44, 0, 45, 0, 46, 0, 47, 0, 48, 0, 49, 0, 50, 0, 51, 0, 52, 0, 53, 0, 54, 0, 55, 0, 56, 0, 57, 0, 58, 0, 59, 0, 60, 0, 61, 0, 62, 0, 63, 0, 64, 0, 65, 0, 66, 0, 67, 0, 68, 0, 69, 0, 70, 0, 71, 0, 72, 0, 73, 0, 74, 0, 75, 0, 76, 0, 77, 0, 78, 0, 79, 0, 80, 0, 81, 0, 82, 0, 83, 0, 84, 0, 85, 0, 86, 0, 87, 0, 88, 0, 89, 0, 90, 0, 91, 0, 92, 0, 93, 0, 94, 0, 95, 0, 96, 0, 97, 0, 98, 0, 99, 0, 100, 0, 101, 0, 102, 0, 103, 0, 104, 0, 105, 0, 106, 0, 107, 0, 108, 0, 109, 0, 110, 0, 111, 0, 112, 0, 113, 0, 114, 0, 115, 0, 116, 0, 117, 0, 118, 0, 119, 0, 120, 0, 121, 0, 122, 0, 123, 0, 124, 0, 125, 0, 126, 0, 127, 0, 128, 0, 129, 0, 130, 0, 131, 0, 132, 0, 133, 0, 134, 0, 135, 0, 136, 0, 137, 0, 138, 0, 139, 0, 140, 0, 141, 0, 142, 0, 143, 0, 144, 0, 145, 0, 146, 0, 147, 0, 148, 0, 149, 0, 150, 0, 151, 0, 152, 0, 153, 0, 154, 0, 155, 0, 156, 0, 157, 0, 158, 0, 159, 0, 160, 0, 161, 0, 162, 0, 163, 0, 164, 0, 165, 0, 166, 0, 167, 0, 168, 0, 169, 0, 170, 0, 171, 0, 172, 0, 173, 0, 174, 0, 175, 0, 176, 0, 177, 0, 178, 0, 179, 0, 180, 0, 181, 0, 182, 0, 183, 0, 184, 0, 185, 0, 186, 0, 187, 0, 188, 0, 189, 0, 190, 0, 191, 0, 192, 0, 193, 0, 194, 0, 195, 0, 196, 0, 197, 0, 198, 0, 199, 0, 200, 0, 201, 0, 202, 0, 203, 0, 204, 0, 205, 0, 206, 0, 207, 0, 208, 0, 209, 0, 210, 0, 211, 0, 212, 0, 213, 0, 214, 0, 215, 0, 216, 0, 217, 0, 218, 0, 219, 0, 220, 0, 221, 0, 222, 0, 223, 0, 224, 0, 225, 0, 226, 0, 227, 0, 228, 0, 229, 0, 230, 0, 231, 0, 232, 0, 233, 0, 234, 0, 235, 0, 236, 0, 237, 0, 238, 0, 239, 0, 240, 0, 241, 0, 242, 0, 243, 0, 244, 0, 245, 0, 246, 0, 247, 0, 248, 0, 249, 0, 250, 0, 251, 0, 252, 0, 253, 0, 254, 0, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]) This is the Ivars: struct Mk1dDriver_IVars { IOUSBHostInterface *interface; IOUSBHostPipe *inPipe; OSAction *ioCompleteCallback; IOBufferMemoryDescriptor *inData; uint16_t maxPacketSize; }; This is the Start method: kern_return_t IMPL(Mk1dDriver, Start) { kern_return_t ret; IOUSBStandardEndpointDescriptors descriptors; ret = Start(provider, SUPERDISPATCH); __Require(kIOReturnSuccess == ret, Exit); ret = RegisterService(); if (ret != kIOReturnSuccess) { Log("Start() - Failed to register service with error: 0x%08x.", ret); goto Exit; } ivars->interface = OSDynamicCast(IOUSBHostInterface, provider); __Require_Action(NULL != ivars->interface, Exit, ret = kIOReturnNoDevice); ret = ivars->interface->Open(this, 0, NULL); __Require(kIOReturnSuccess == ret, Exit); ret = ivars->interface->CopyPipe(kMyEndpointAddress, &ivars->inPipe); __Require(kIOReturnSuccess == ret, Exit); ret = ivars->interface->CreateIOBuffer(kIOMemoryDirectionIn, 1024, &ivars->inData); __Require(kIOReturnSuccess == ret, Exit); ret = OSAction::Create(this, Mk1dDriver_ReadComplete_ID, IOUSBHostPipe_CompleteAsyncIO_ID, 0, &ivars->ioCompleteCallback); __Require(kIOReturnSuccess == ret, Exit); ret = ivars->inPipe->AsyncIO(ivars->inData, ivars->maxPacketSize, ivars->ioCompleteCallback, 0); __Require(kIOReturnSuccess == ret, Exit); os_log(OS_LOG_DEFAULT,"Finish"); // WWDC slides don't show the full function // i.e. this is still unfinished Exit: return ret; } The only difference in this compared with the code from Apple is that I set capacity in the method CreateIOBuffer to 1024. This is because if I leave it to 0 it will return an error that memory could not be allocated: kIOReturnNoMemory And the ReadComplete method: void IMPL(Mk1dDriver, ReadComplete) { char output[1024]; memcpy(action->GetReference(), &output, 1024); os_log(OS_LOG_DEFAULT,"ReadComplete"); If I put a breakpoint in the log, I can see all the positions in output will be \0 Any idea what I'm doing wrong? Could this be because the iPad is a device under Supervision? Thanks
0
0
2.1k
Nov ’22
IOKit on iOS/iPadOS 16.0+
According to https://developer.apple.com/documentation/iokit IOKit is supported for iOS/iPadOS 16.0+. I was trying to figure out what that exactly meant by using Xcode 14.1 and build for iPadOS 16.1. But I just get "No such module 'IOKit'" if I have import IOKit in any Swift file. Wondering if it is an error in the documentation or if I have to do something extraordinary? Thanks :)
1
1
3k
Nov ’22
Capturing USB traffic
Hi, I want to capture the USB traffic for my app running on High Sierra. I brought the if XHC20 up and can capture the traffic using Wireshark nightly builds. But I only see incoming traffic (from device to host) but not the other direction. Any ideas what is going wrong here?Starting the IF:&gt; sudo ifconfig XHC20 upAfter that I can select the IF in Wireshark and start capturing packets. I can see incoming traffic from attached devices but not the outbound messages.
Replies
8
Boosts
0
Views
15k
Activity
Mar ’23
Correct way to read out information about current energy usage battery&charger/adapter
I'm looking for a way to read out the current energy drain of various macOS devices that should be backwards compatible at least to macOS 12. So far I already had a couple of good idea – well initially I thought so – to get that data from ioreg or IOKit, reading out AppleSmartBattery object. I'm trying to write a small program in Rust that collects the energy usage of our companies macOS devices and record this how much happened while in the office and how much on the road. Therefore I need to consider cases where the battery is charging as well as the battery is full and energy is drawn from the power adapter or usb-c connected display directly via PD. So far I was able to read the desired data out via ioreg with plist output and parse the information into a struct. The issue I have testing this out that my 1st approach of going for PowerTelemetryData which would be perfect is only available on macOS 13+ systems. The second approach reading out the subobjects of BatterData and PowerOutDetails seem to only be available on macOS 12 devices now and then. Any suggestions or hints?
Replies
1
Boosts
0
Views
1.1k
Activity
Feb ’23
stop charging while plugged in
Is it possible to change the internal operating system of apple's charging methods? So if I want to make an app or some code to make a MacBook stop charging at a certain percentage while it's still plugged in and then let the battery drain until 20%, it automatically starts charging again to 80%. All while it's plugged in. Does apple allow this? to make something like this?
Replies
2
Boosts
0
Views
1k
Activity
Feb ’23
Reading EDID data on Apple M1 devices
Is there any way to read EDID data in new Apple M1 devices since the below code snippet does not work in M1 machines however it works in Intel based Mac. io_object_t object = -1;       io_iterator_t iterator;     CFMutableDictionaryRef matching = IOServiceMatching("IODisplayConnect");     kern_return_t kernResult = IOServiceGetMatchingServices(kIOMasterPortDefault, matching, &amp;amp;iterator);       if (KERN_SUCCESS == kernResult &amp;amp;&amp;amp; iterator != 0) {           object = IOIteratorNext(iterator);           while (object != 0) {               CFDictionaryRef dict = IODisplayCreateInfoDictionary(object, kIODisplayOnlyPreferredName);       /*        process data here        */               object = IOIteratorNext(iterator);     }     IOObjectRelease(iterator);   } Also tried replacing "IODisplayConnect" by "IODPDevice" but still get an empty iterator.
Replies
5
Boosts
0
Views
5.6k
Activity
Feb ’23
Improving battery reading when the machine wakes.
I am using the CFProperty "AppleRawCurrentCapacity" value from IOServiceGetMathcingService( kIOMainPortDefault, IOServiceMatching( "AppleSmartBattery" ) ) to obtain the mAh value of the MacBook's battery. Once when the app receives the NSWorkspace notification of display sleep, and once again when receiving the NSWorkspace notification of display wake. I then calculate how much battery was expended during sleep by deducting the pre value from post value. The results can wildly vary, from it using 16 mAh per hour, to gaining 10 mAh an hour (without being plugged in). Sometimes a 10 hour sleep doesn't use any mAh... Which is clearly wrong. When my app detects the key kIOPMPSInvalidWakeSecondsKey is present, I set a timer for that period + 3 seconds and attempt to read the battery values again. Yet the results can still wildly vary. I see on Intel Macs there is a kIOPMPSMaxErrKey (set to 9 on a 2019 16"), however I don't see this on M1, and don't know how it can help, if it does exist. Can anyone give me any pointers as to what I am doing wrong, or in the direction of obtaining reliable mAh values? I like mAh as it's more precise that the standard integer values of 0 - 100, but I don't have to stick with mAh, I'd just don't like reporting that a 16 hour sleep didn't use any battery, when I know it's not true. Thanks
Replies
1
Boosts
0
Views
1.2k
Activity
Jan ’23
iPad 10th Gen and IOKitLib/IOHIDManager
I'm creating an iPad room information app which needs to communicate over USB with an LED light strip. The USB controller is HID class, vendor ID is 0x20a0 and product ID is 0x41e5. It requires sending a simple feature report to control the LEDs. I've got it working on the Mac using IOKit, and compiling on the 10th gen USB C iPad using copied headers and bridging IOKitLib and IOHIDManager, but sandboxing prevents the code executing on the iPad (IOServiceOpen failed: 0xe00002e2). Is joining the MFi program really the only way to get this to get the necessary entitlements? At our current scale, we don't need to distribute in the App Store.
Replies
0
Boosts
0
Views
1.4k
Activity
Jan ’23
M1 Mac does not support DDC/CI
The DDC/CI application can work well on MacbookPro/Mac Pro (Big Sur), but it doesn't work on M1 Mac (both macOS 11.0.1 and 11.1). M1’s graphics card is Apple, not Intel or AMD. Does this incompatible issue relate with new graphics card or kernel change? Any alternative solution for M1?
Replies
6
Boosts
1
Views
12k
Activity
Jan ’23
Querying for electronics relevant information of my MacBook via native code
Howdy! I have been experimenting with my system's electronics (MacBook Pro 13-inch, M1, 2020) by using software probe written in C/C++ type program. The idea is to extract the relevant information just like it is presented in Apple > About This Mac > System Report, for my cross-platform Engine. I have been tinkering with a tool dmidecode. It works just fine on Linux and Windows. For MacOS, I need to find a graceful way of obtaining the AppleSMBIOS service, in this context. To my best of knowledge, the service is nonexistent as I have checked by C code and some application named IORegistryExplorer (courtesy Google). Just wondering if someone has been on such endurance and how much satisfaction has been achieved upon the topic. Thanks a lot!
Replies
9
Boosts
0
Views
1.9k
Activity
Jan ’23
USB device ID
I am new to Mac and got a question. Got a third party USB device and its old library source which has the device old Vendor ID. The device with new Vendor ID is not compatible with old library. So change the Vendor ID in the old source, rebuild it, and use the lib?. Can I use the device in a new Mac?.
Replies
3
Boosts
1
Views
5.4k
Activity
Jan ’23
Issues with MSI(x) handling
I've a basic IOPCIDevice driver for a custom device that supports MSI(x). The interrupt filter doesn't get called if I passthe msi index to the IOFilterInterruptEventSource. That's a first problem.The filter is continously called if I don't pass the msi index. That's a 2nd problem.Interrupt was triggered when I initialized the device. In the filter I cleared the cause register. For some reasonintr mask register was already cleared when the filter is called which is another problem.Any clues/pointers?
Replies
3
Boosts
0
Views
1.8k
Activity
Dec ’22
How can I use USBmakebmRequestType with DriverKit
I'm building a driver in C++ for my iPad using DriverKit. I'm trying to make a request to a control endpoint, so I'm trying to use DeviceRequest: https://developer.apple.com/documentation/usbdriverkit/iousbhostinterface/3182582-devicerequest But the first parameter ask for USBmakebmRequestType which it's a macro defined in IOKit > USB.h I tried to #include <IOKit/USB.h> and #include <IOKit/usb/USB.h> and  but it doesn't find the header. Any idea? thanks.
Replies
1
Boosts
0
Views
1.6k
Activity
Dec ’22
Different Drivers for Individual Interfaces
Hello We have a USB camera. My Mac can recognize it and we can get frames with any software. There is a physical button on it and the vendor says the camera is UVC-compliant. But button doesn't work anyway. I captured some USB traffic data and saw that it has two interfaces. One for streaming and other one for interrupting (like button click). I read UVC 1.5 standards to understand it and it is working like written in UVC 1.5. So, I can get a data with an interrupt transfer when clicking the button. I checked these two interfaces, they use UVCAssistant for driver(System Extension). I tried to use libusb, I can get data from button click. But for frames I had to use libuvc, but it wasn't work for my camera (I think it is related with USB descriptor parsing in libuvc). I thought that I should write a driver for single interface and so second interface will use same UVC assistant driver and first interface will use my driver. I wrote a driver and it matches with first interface. But second interface is empty (unhandled by any driver). I want to load UVCAssistant for second interface of USB port. How can I do this? Output before loading my driver After loading: IOKitPersonalities that I used:
Replies
2
Boosts
0
Views
1.7k
Activity
Dec ’22
IOKit or IOUSBHost for USB device acces from user space
USB-Devices without macOS support Every so often I find usefull USB consumer hardware without any macOS support. At best accompanied with some sample code aimed at Linux using libUSB and/or a datasheet [1]. Using code snippets from long since archived IOKit documentation I can deal with that. IOUSBHost Using working IOKit based ObjC Foundation command-line code[2] as reference I am attempting to use theIOUSBHost framework (ObjC Foundation tool). IOUSBHost documentation[3] has all the ingredients but lacks a recipy. Starting with a plugged-in USBDevice and using its idVendor and idProduct[4] I can initialize and destroy base class IOUSBObject and get notified when I unplug the USBDevice. initialize and destroy IOUSBHostDevice[5] and retrieve various descriptors [6] and configure with value: 0, and even do a vendor bmRequestType request without error. But since I already beforehand know the content of my descriptors I can start with IOUSBHostInterface?[7] , needed for my 3 pipes, interrupt, bulk in and out. But Error:Unable to open io_service_t object and create user client. with reason: Exclusive open of usb object failed, whether I asked for exclusive access or not. So I could do with some guidance on how to use IOUSBHost[8]. Let Any Pointer bring joy. Using: Apple M1 Max, MacOS 13.0.1 (22A400), Xcode 14.1 (14B47b) Alternatives considered: Raspberry Pi using UDP (JSON;) over wifi. [1] e.g. https://www.digchip.com/datasheets/parts/datasheet/280/DS2490-pdf.php [2] depending on usage this might need a runloop [3] including dec 2022 https://www.usb.org/sites/default/files/usb_32_202206.zip I failed to find the phrase 'Host-mode'. HINT start by inspecting chapter 9 to get a taste of the terms like function, class, address and value and number. Those wordings will also appear in Apple's documentation. NOTE Tables in chapter 9: Assuming D[n]: stands for bitNr[n] in a bitmap where D[0] is the least significant bit. USEFULL No. [4] use the IORegistryExplorer.app and/or ioreg in Terminal [5] IOUSBHostInterface.h tells me: CFMutableDictionaryRef to be used with IOService matching methods. To be released by caller. But as far a I know CFFoundation is now under ARC. [6] IOUSBInterfaceDescriptor * next = IOUSBGetNextInterfaceDescriptor(configurationDescriptor, nil); while (next != nil) // needs cast (IOUSBDescriptorHeader *)next [7] signed to run locally [8] My next step would be using Swift. Off topic but related and disturbing in a type safe world https://forums.swift.org/t/nsdata-data-vs-data-withunsafebytes/50231/5 Please please please never use NSData.bytes in Swift code. Is this why IOUSBHostObject ioDataWithCapacity uses NSMutableData? Quote: Because the kernel backs the NSMutableData object, the length and capacity aren’t mutable. Any changes to the length or capacity throws an exception. Effectively treating NSMutableData as NSData, only the compiler complains beforehand when an attempt is made to modify the length of NSData (data.bytes ARE mutable)
Replies
0
Boosts
1
Views
2.1k
Activity
Dec ’22
How do I invert the luminosity of the display using a color matrix or something else?
I recently came across a program that used data tables to invert the display, however it was a windows only application and I am wondering how I can write a similar thing for Mac, or if there is one already available. The app and config file is attached below so you can sort of dissect how it works Config File: [negativescreen.conf](https://developer.apple.com/forums/content/attachment/f4b67ed7-fa71-4ee6-9c0d-18febe2c3381) Readme file: [README.md](https://developer.apple.com/forums/content/attachment/86bd72f6-46c9-42d5-a925-561f75f24ae8) Window$ Executable: [NegativeScreen.exe](https://developer.apple.com/forums/content/attachment/a4478bd5-d5c7-41dd-9302-0e1a929372c2)
Replies
0
Boosts
0
Views
1.6k
Activity
Dec ’22
Serial Communication Application
We have been looking into developing an application for iOS that will allow the phone to connect to a sensor through a serial connection. The purpose is to change the settings of the sensor using the phone. However, I have been made aware that we would be unable to develop such an app unless we enroll in the MFI program. We considered alternatives such as using Redpark’s cables and their SDKs, but according to them publishing would not be possible. They mentioned we could develop the app and publish through Apple Business Manager to distribute to corporate customers, but as far as I could tell, this requires the customer to be enrolled in the Apple Business Manager program as well. What we wish to do is publish publicly in both iOS and Android, but for iOS there doesn’t seem to be support for serial communication, and I am assuming appropriate APIs/SDKs are available only through the MFI program. I would like to know what options we have and how we can explore them. Thank you very much for your time.
Replies
3
Boosts
0
Views
3.9k
Activity
Dec ’22
iOS USB device access
Hi, allAccessing USB device on MAC OSX platform, the “App Sandbox”=YES and”com.apple.security.device.usb”=YES Must be increased to entitlents file.How to Implement USB Access in iOS Platform?
Replies
9
Boosts
1
Views
8.2k
Activity
Nov ’22
DriverKit Share Memory from User Client to App for Streaming
Does anyone have an example of streaming video data from a user client to a client app? I have successfully set up a DriverKit USB hardware driver that commands a device to successfully fill the same IOBufferMemoryDescriptor at 30fps with new data (verified in driver). I have also managed to map this buffer to the application using CopyClientMemoryForType in the user client and IOConnectMapMemory64 in the app. I have also confirmed the data is the intended image data. What I CAN NOT do is see updates in the mapped memory in the app. I map and unmap the data, but the contents don't change. No matter how many times I map, CopyClientMemoryForType is called once. How should changes to the underlying dext space memory be reflected/synchronized to the app? Can I not share a single buffer (4-12MB, ringed) and synchronize updates?
Replies
1
Boosts
0
Views
1.2k
Activity
Nov ’22
DriverKit demo app doubts
Hello everyone, I downloaded the demo app from the driverkit demo located at https://developer.apple.com/documentation/driverkit/communicating_between_a_driverkit_extension_and_a_client_app, I downloaded the files and followed the process in the two possible ways by letting xcode automatically sign the app and by me creating the provisioning profiles, everything compiles but I am facing this particular issue whenever I try to invoke the system installation of the driver:2022-11-16 00:45:12.425147-0600 DriverKitSampleApp[5837:69830] sysex didFailWithError: The operation couldn’t be completed. (OSSystemExtensionErrorDomain error 9.) There is very little to none information on the web, and I dont know what else to do at this point.
Replies
1
Boosts
0
Views
1.4k
Activity
Nov ’22
How to get data from the device using IOBufferMemoryDescriptor in driverKit
I'm trying to create a driver for my usb device, using iOS and DriverKit. I'm basing my code in the example used in WWDC: https://github.com/knightsc/USBApp My driver starts fine when the device is connected and the readCompleted method is called fine, but the action->GetReference() gets only \0 characteres. Also in order to know that the usb device is actually working I've connected it to my mac first and using PyUSB I can see that it's returning data in chunks of 1024 bytes in the interface 0. This is the data I get in PyUSB: array('B', [6, 0, 1, 0, 2, 0, 3, 0, 4, 0, 5, 0, 6, 0, 7, 0, 8, 0, 9, 0, 10, 0, 11, 0, 12, 0, 13, 0, 14, 0, 15, 0, 16, 0, 17, 0, 18, 0, 19, 0, 20, 0, 21, 0, 22, 0, 23, 0, 24, 0, 25, 0, 26, 0, 27, 0, 28, 0, 29, 0, 30, 0, 31, 0, 32, 0, 33, 0, 34, 0, 35, 0, 36, 0, 37, 0, 38, 0, 39, 0, 40, 0, 41, 0, 42, 0, 43, 0, 44, 0, 45, 0, 46, 0, 47, 0, 48, 0, 49, 0, 50, 0, 51, 0, 52, 0, 53, 0, 54, 0, 55, 0, 56, 0, 57, 0, 58, 0, 59, 0, 60, 0, 61, 0, 62, 0, 63, 0, 64, 0, 65, 0, 66, 0, 67, 0, 68, 0, 69, 0, 70, 0, 71, 0, 72, 0, 73, 0, 74, 0, 75, 0, 76, 0, 77, 0, 78, 0, 79, 0, 80, 0, 81, 0, 82, 0, 83, 0, 84, 0, 85, 0, 86, 0, 87, 0, 88, 0, 89, 0, 90, 0, 91, 0, 92, 0, 93, 0, 94, 0, 95, 0, 96, 0, 97, 0, 98, 0, 99, 0, 100, 0, 101, 0, 102, 0, 103, 0, 104, 0, 105, 0, 106, 0, 107, 0, 108, 0, 109, 0, 110, 0, 111, 0, 112, 0, 113, 0, 114, 0, 115, 0, 116, 0, 117, 0, 118, 0, 119, 0, 120, 0, 121, 0, 122, 0, 123, 0, 124, 0, 125, 0, 126, 0, 127, 0, 128, 0, 129, 0, 130, 0, 131, 0, 132, 0, 133, 0, 134, 0, 135, 0, 136, 0, 137, 0, 138, 0, 139, 0, 140, 0, 141, 0, 142, 0, 143, 0, 144, 0, 145, 0, 146, 0, 147, 0, 148, 0, 149, 0, 150, 0, 151, 0, 152, 0, 153, 0, 154, 0, 155, 0, 156, 0, 157, 0, 158, 0, 159, 0, 160, 0, 161, 0, 162, 0, 163, 0, 164, 0, 165, 0, 166, 0, 167, 0, 168, 0, 169, 0, 170, 0, 171, 0, 172, 0, 173, 0, 174, 0, 175, 0, 176, 0, 177, 0, 178, 0, 179, 0, 180, 0, 181, 0, 182, 0, 183, 0, 184, 0, 185, 0, 186, 0, 187, 0, 188, 0, 189, 0, 190, 0, 191, 0, 192, 0, 193, 0, 194, 0, 195, 0, 196, 0, 197, 0, 198, 0, 199, 0, 200, 0, 201, 0, 202, 0, 203, 0, 204, 0, 205, 0, 206, 0, 207, 0, 208, 0, 209, 0, 210, 0, 211, 0, 212, 0, 213, 0, 214, 0, 215, 0, 216, 0, 217, 0, 218, 0, 219, 0, 220, 0, 221, 0, 222, 0, 223, 0, 224, 0, 225, 0, 226, 0, 227, 0, 228, 0, 229, 0, 230, 0, 231, 0, 232, 0, 233, 0, 234, 0, 235, 0, 236, 0, 237, 0, 238, 0, 239, 0, 240, 0, 241, 0, 242, 0, 243, 0, 244, 0, 245, 0, 246, 0, 247, 0, 248, 0, 249, 0, 250, 0, 251, 0, 252, 0, 253, 0, 254, 0, 255, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]) This is the Ivars: struct Mk1dDriver_IVars { IOUSBHostInterface *interface; IOUSBHostPipe *inPipe; OSAction *ioCompleteCallback; IOBufferMemoryDescriptor *inData; uint16_t maxPacketSize; }; This is the Start method: kern_return_t IMPL(Mk1dDriver, Start) { kern_return_t ret; IOUSBStandardEndpointDescriptors descriptors; ret = Start(provider, SUPERDISPATCH); __Require(kIOReturnSuccess == ret, Exit); ret = RegisterService(); if (ret != kIOReturnSuccess) { Log("Start() - Failed to register service with error: 0x%08x.", ret); goto Exit; } ivars->interface = OSDynamicCast(IOUSBHostInterface, provider); __Require_Action(NULL != ivars->interface, Exit, ret = kIOReturnNoDevice); ret = ivars->interface->Open(this, 0, NULL); __Require(kIOReturnSuccess == ret, Exit); ret = ivars->interface->CopyPipe(kMyEndpointAddress, &ivars->inPipe); __Require(kIOReturnSuccess == ret, Exit); ret = ivars->interface->CreateIOBuffer(kIOMemoryDirectionIn, 1024, &ivars->inData); __Require(kIOReturnSuccess == ret, Exit); ret = OSAction::Create(this, Mk1dDriver_ReadComplete_ID, IOUSBHostPipe_CompleteAsyncIO_ID, 0, &ivars->ioCompleteCallback); __Require(kIOReturnSuccess == ret, Exit); ret = ivars->inPipe->AsyncIO(ivars->inData, ivars->maxPacketSize, ivars->ioCompleteCallback, 0); __Require(kIOReturnSuccess == ret, Exit); os_log(OS_LOG_DEFAULT,"Finish"); // WWDC slides don't show the full function // i.e. this is still unfinished Exit: return ret; } The only difference in this compared with the code from Apple is that I set capacity in the method CreateIOBuffer to 1024. This is because if I leave it to 0 it will return an error that memory could not be allocated: kIOReturnNoMemory And the ReadComplete method: void IMPL(Mk1dDriver, ReadComplete) { char output[1024]; memcpy(action->GetReference(), &output, 1024); os_log(OS_LOG_DEFAULT,"ReadComplete"); If I put a breakpoint in the log, I can see all the positions in output will be \0 Any idea what I'm doing wrong? Could this be because the iPad is a device under Supervision? Thanks
Replies
0
Boosts
0
Views
2.1k
Activity
Nov ’22
IOKit on iOS/iPadOS 16.0+
According to https://developer.apple.com/documentation/iokit IOKit is supported for iOS/iPadOS 16.0+. I was trying to figure out what that exactly meant by using Xcode 14.1 and build for iPadOS 16.1. But I just get "No such module 'IOKit'" if I have import IOKit in any Swift file. Wondering if it is an error in the documentation or if I have to do something extraordinary? Thanks :)
Replies
1
Boosts
1
Views
3k
Activity
Nov ’22