macOS serial port programming in swift

Appologies if not using the correct forum for this question? however it is closest I could find.


have been disappointed with the lack of Apple documention supporting serial port programming.

The best I've found is thiswebsite. Are there recommend swift libraries/frameworks for interacting with serial devices via USB? perhaps with some examples.


Hopefully

Replies

it is closest I could find

Not a problem. However, there is a better topic area, Core OS > Drivers and Device Access, and I’ve moved you thread there.

have been disappointed with the lack of Apple documention supporting serial port programming.

There’s two parts to this:

  • Discovering the available serial ports (A)

  • Talking to a serial port (B)

With regards B, macOS is much like any other BSD-flavoured UNIX, and you should consult standard UNIX resources on this topic. My ‘go to’ book for this sort of thing in Advanced Programming in the Unix Environment, although I must admit that I haven’t specifically consulted it for serial programming advice. Oh, and I’m two editions behind!

With regards A, the canonical example of how to find serial ports is SerialPortSample.

All of the above assumes that you’re coming from a C-based language. Doing this stuff in Swift is challenging because the relevant APIs do not have nice Swift wrappers (at least not from Apple). You’ll need to learn how to work with C APIs from Swift. The information in Imported C and Objective-C APIs can help.

Are there recommend swift libraries/frameworks for interacting with serial devices via USB?

To be clear, the USB-ness doesn’t matter here. Serial ports are exposed to apps in a way that’s independent of how they’re connected.

As for Swift-friendly higher-level APIs for serial, I don’t have any suggestions for you, alas. I’m sufficiently familiar with the low-level APIs that I just use them directly. Hopefully someone else will chime in.

Share and Enjoy

Quinn “The Eskimo!”
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1" + "@apple.com"

I had a similar question and your answer helped me, thanks.


I've downloaded and ran the SerialPortSample code, but it is not able to find any modems. I know a modem is connected, and I can see it and open it with 3rd party terminal apps.


I've recently upgraded to Catalina. Would this error have anything to do with the stricter security policies that it emposes?

Would this error have anything to do with the stricter security policies that it emposes?

Probably not. My suspicion is that you have an I/O Kit service matching problem. You should check the matching dictionary you pass

IOServiceGetMatchingServices
against the properties declared by the actual serial port hardware you plugged in. You can view those using the IORegistryExplorer app [1] or the
ioreg
command-line tool.

Share and Enjoy

Quinn “The Eskimo!”
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1" + "@apple.com"

[1] In Xcode, choose Xcode > Open Developer Tool > More Developer Tools, then search for the “Additional Tools” package corresponding to your Xcode. Download that, mount the disk image, and then look inside the

Hardware
folder.

I am afraid I am a bit out of my dept here, never doing device programming before, but as far as I can tell that is not muy issue.


I can see the device using ioreg:

    | |   |       | |   | |   | +-o AppleUSB20HubPort@14412300  
    | |   |       | |   | |   | | +-o USB-Serial Controller D@14412300  
    | |   |       | |   | |   | |   +-o AppleUSBHostLegacyClient  
    | |   |       | |   | |   | |   +-o AppleUSBHostCompositeDevice  
    | |   |       | |   | |   | |   +-o IOUSBHostInterface@0  
    | |   |       | |   | |   | |     +-o AppleUSBPLCOM  
    | |   |       | |   | |   | |       +-o IOSerialBSDClient 


and I can see it using IORegistryExplorer.


In findModems, the ServiceMatching is kIOSerialBSDServiceValue, which is "IOSerialBSDClient" and that is the service I see in ioreg (or am I reading it wrong?)


IOServiceGetMatchingServices() returns success with a valid iterator but it seems to be empty since IOIteratorNext() does not return anything useful.


I also have a couple of IOBluetoothSerialClient devices of type IOSerialBSDClient and they are also not being found.


Any clue as to what I may be missing?

The

findModems
function constructs its matching dictionary in two steps:
  • It calls

    IOServiceMatching
    with with
    kIOSerialBSDServiceValue
    . This will match any
    IOSerialBSDClient
    .
  • It then sets the

    kIOSerialBSDTypeKey
    property to
    kIOSerialBSDModemType
    . This will restrict the match to services that have their
    IOSerialBSDClientType
    property set to
    IOModemSerialStream
    .

Your

ioreg
dump shows that you meet the first criteria but it doesn’t show properties so I can’t tell whether it meets the second.

Share and Enjoy

Quinn “The Eskimo!”
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1" + "@apple.com"

Thanks, that was the issue. I've changed it to kIOSerialBSDRS232Type and I can now find my device (with all other serial port devices connected).

ORSSerialPort is a good open source framework but it does not work with tty devices.

Here is link to much simpler library that is not dependant in iokit and it does work just as well with virtual tty devices just as much as with physical serial devices.

https://github.com/kpishere/POSIXSerialPort
Would this link answer your question? Though it's Objective-C at this moment.
https://developer.apple.com/documentation/usbserialdriverkit