Using Swift Concurrency with internally-synchronized Concurrency-unaware APIs

I'm trying to audit some of my code to ensure it continues to work with future editions of Swift, namely when Swift Concurrency checking is tightened up. The code I have uses C APIs that are internally synchronized but have not been audited for Swift Concurrency, and I suspect will never be. Here's a very simple example for macOS:

import Darwin

Task {
	print(errno)
}

When using a Swift 5.7 toolchain (from Xcode 14) with -Xfrontend -warn-concurrency, I get a warning about this code:

<stdin>:4:8: warning: reference to var 'errno' is not concurrency-safe because it involves shared mutable state
        print(errno)
              ^
Darwin.errno:1:12: note: var declared here
public var errno: Int32 { get set }
           ^

This…makes sense, but I know errno is safe to access concurrently. But how should I tell Swift about this? I tried @preconurrency import Darwin, but doesn't seem to do anything. Actually, it just adds another warning:

<stdin>:4:8: warning: reference to var 'errno' is not concurrency-safe because it involves shared mutable state
        print(errno)
              ^
Darwin.errno:1:12: note: var declared here
public var errno: Int32 { get set }
           ^
<stdin>:1:17: remark: '@preconcurrency' attribute on module 'Darwin' is unused
@preconcurrency import Darwin
~~~~~~~~~~~~~~~~^

Is this behavior correct? I feel like this is the kind of thing @preconurrency was designed for but it seems to not work here. Am I holding it wrong?

1 Like