I have a C function 

    void myfunc(const void *ptr);
    
which is imported to Swift as

    func myfunc(_ ptr: UnsafeRawPointer!)
    
This compiles and runs without problems:

    let data = Data(bytes: [1, 2, 3, 4])
    data.withUnsafeBytes { (ptr) in myfunc(ptr) } // (A)

and the type of `ptr` is inferred as `UnsafePointer<Void>`. But adding an 
explicit type
annotation produces a compiler warning:

    data.withUnsafeBytes { (ptr: UnsafePointer<Void>) in myfunc(ptr) } // (B)
    // warning: UnsafePointer<Void> has been replaced by UnsafeRawPointer
    
which is understandable in the view of "SE-0107 UnsafeRawPointer API".

The "Fix-it" replaces `UnsafePointer<Void>` by `UnsafeRawPointer`, and that 
does not
compile anymore:

    data.withUnsafeBytes { (ptr: UnsafeRawPointer) in myfunc(ptr) } // (C)
    // error: cannot convert value of type 'Void' to closure result type '_'

because there is no `withUnsafeBytes()` method taking a 
`(UnsafeRawPointer)->ResultType`
closure.


My questions are:

1. Why are (A) and (B) treated differently?

2. Is (A) "legal", or should one use some non-void pointer

    data.withUnsafeBytes { (ptr: UnsafePointer<Int8>) in myfunc(ptr) } // (D)
    
   (which feels wrong to me because it is converted back to a void pointer when
   calling the function).

3. Or should there be a `withUnsafeRawPointer()` method which makes (C) compile 
as

      data.withUnsafeRawBytes { (ptr: UnsafeRawPointer) in myfunc(ptr) }

   This would also allow to access the data at byte offsets more easily, e.g.

       data.withUnsafeRawBytes { ptr in
           let u16 = ptr.load(fromByteOffset: 4, as: UInt16.self)
       }
    
   Does that makes sense?

Regards, Martin



    




 
_______________________________________________
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users

Reply via email to