Can CF_RETURNS_RETAINED be used on C function pointer return values bridged to Swift?

https://developer.apple.com/documentation/swift/imported_c_and_objective-c_apis/working_with_core_foundation_types

If we define a C function that returns a CFType, Swift can (sometimes) bridge the memory management semantics. If Swift cannot bridge the memory management semantics, we can end up with an Unmanaged type:

CFStringRef CreateStringByAddingTwoStrings(CFStringRef s1, CFStringRef s2);

bridges to:

public func CreateStringByAddingTwoStrings(_ s1: CFString!, _ s2: CFString!) -> Unmanaged<CFString>!

We can improve the bridging with the CF_RETURNS_RETAINED annotation:

CFStringRef CreateStringByAddingTwoStrings(CFStringRef s1, CFStringRef s2) CF_RETURNS_RETAINED;

now bridges to:

public func CreateStringByAddingTwoStrings(_ s1: CFString!, _ s2: CFString!) -> CFString!

Alternatively, we can use the CF_IMPLICIT_BRIDGING_ENABLED macro on this function:

CF_IMPLICIT_BRIDGING_ENABLED

CFStringRef CreateStringByAddingTwoStrings(CFStringRef s1, CFStringRef s2);

CF_IMPLICIT_BRIDGING_DISABLED

What does not seem to be documented is how to improve bridging when function pointer return values should be annotated. For example:

typedef CFStringRef (*CreateStringByAddingTwoStrings)(CFStringRef, CFStringRef);

bridges to:

public typealias CreateStringByAddingTwoStrings = @convention(c) (CFString?, CFString?) -> Unmanaged<CFString>?

Is there any way to annotate the function pointer to properly communicate the memory management semantics? Adding the CF_RETURNS_RETAINED and CF_IMPLICIT_BRIDGING_ENABLED macros do not seem to help.

2 Likes