sec_protocol_options... detect/bypass?

I'm investigating the new network framework for use in a server scenario. I can write a trivial server with no security that detects a tls/ssl clientHello and then report that security was needed. Likewise I can write the server code so that it is preconfigured with a certificate so as to use an appropriate level of security. However, I currently can't see how I'd go about configuring the security of the protocol with some sort of bypass/fallback so as to say: if no "clientHello" received then treat comms as *****/insecure and continue? (and yes, I'd later check the tls status of the connection to decide what is appropriate to do...)

Am I missing something in the API, or are my requirements a bit of an outlier?

Replies

I’d like to clarify your requirements here. Reading through your post I believe that you want to create a server that peeks at the first few bytes sent to it by the client, uses those to determine whether the client is speaking TCP or TLS-over-TCP, and then adapts accordingly. Is that right?

Share and Enjoy

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

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

Correct.


I can imagine a solution where I have a TCP server, and when it detects that it's receiving TLS then it starts relaying messages back/forth to a different socket which is a TLS enabled server. So my question becomes, can the new nw_ framework offer a more elegant/efficient solution?

Correct.

OK, then I don’t think there’s a good way to do this. Most protocols that do this have an explicit StartTLS command. While StartTLS is supported by other APIs in our system, it is not yet supported by the Network framework (r. 45256384). And even if it were, it wouldn’t meet this requirement.

Share and Enjoy

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

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

Using the old CFStream/CFSocket network framework I've just now successfully written a server that can detect and switch between tls/non-tls.


The solution was surprisingly trivial: in the socket accept callback, firstly use recv(... MSG_PEEK) to grab the first 6 bytes of the message and check for a SSL/TLS header, and then after use CFStreamCreatePairWithSocket(), setting kCFStreamPropertySSLSettings if appropriate.



Unfortunately, I can't see how to implement a similar approach using the new network framework.

Firstly, it appears that the socket nw_listener_t is configured to use TLS (or not), rather than the individual connections made on it.

Secondly, I've not seen an equivalent way of message peeking, or even getting the raw socket.

The solution was surprisingly trivial

That’s quite tricky.

I've not seen an equivalent way of message peeking

Such a mechanism does not exist.

or even getting the … socket.

Nor does that, at least in general. Network framework was designed to work in conjunction with our user space networking stack, and that stack does not have an underlying socket because sockets are a kernel-only concept.

Now, on macOS, Network framework does actually talk to the kernel, but that’s just a compatibility measure: We can’t enable the user space networking stack on the Mac while continuing to support Network Kernel Extensions (NKEs). NKEs have been informally deprecated for a while now, so the expectation is that they’ll be formally deprecated and then removed in future OS releases, at which point macOS will work like all our other OSes in this regard.

You can learn more about the background to this in:

All of this is to say that, if you can’t do what you want with Network framework, the time to an enhancement request for the facilities that you need is now.

Please post your bug number, just for the record.

Share and Enjoy

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

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

50515104