从只知道内存地址的 Swift 调用 C 函数
Call C function from Swift knowing only memory address
我在 C 中有一个非常简单的函数,它的指针被传递到 Swift。
void callback() {
NSLog(@"such pointer…");
}
如何在 Swift 中仅使用 指针调用它?这 NOT 关于简单地调用它——直接调用时它工作正常。尝试了以下和不同的签名转换变体,但它总是崩溃:
let pointer: UnsafePointer<@convention(c)() -> ()> = UnsafePointer(bitPattern: …)
let callback: @convention(c)() -> () = pointer.memory
Swift.print(callback) // (Function)
callback() // Handling crash with signal 11...
尝试用 typedef void(*Callback)();
定义 Callback
类型 – 同样的事情:
let pointer: UnsafePointer<Callback> = UnsafePointer(bitPattern: …)
let callback: Callback = pointer.memory
Swift.print(callback) // (Function)
callback() // Handling crash with signal 11...
为了检查它是否确实有效并指向正确的地址,我有另一个 Objective-C 函数,当使用回调指针从 Swift 调用时,它按预期工作。
void invokeCallback(uintptr_t callback) {
((void (*)()) callback)(); // such pointer…
}
与 中相同的方法应该适用于此。
Swift 3 的示例(假设 funcPtr
是一个
UnsafeRawPointer
包含函数的地址):
// Define function type:
typealias callbackFunc = @convention(c) () -> Void
// Convert pointer to function type:
let callback = unsafeBitCast(funcPtr, to: callbackFunc.self)
// Call function:
callback()
当然类型别名必须与实际的函数签名匹配,
函数必须是 "pure" C 函数(不是 Objective-C
方法)。
我在 C 中有一个非常简单的函数,它的指针被传递到 Swift。
void callback() {
NSLog(@"such pointer…");
}
如何在 Swift 中仅使用 指针调用它?这 NOT 关于简单地调用它——直接调用时它工作正常。尝试了以下和不同的签名转换变体,但它总是崩溃:
let pointer: UnsafePointer<@convention(c)() -> ()> = UnsafePointer(bitPattern: …)
let callback: @convention(c)() -> () = pointer.memory
Swift.print(callback) // (Function)
callback() // Handling crash with signal 11...
尝试用 typedef void(*Callback)();
定义 Callback
类型 – 同样的事情:
let pointer: UnsafePointer<Callback> = UnsafePointer(bitPattern: …)
let callback: Callback = pointer.memory
Swift.print(callback) // (Function)
callback() // Handling crash with signal 11...
为了检查它是否确实有效并指向正确的地址,我有另一个 Objective-C 函数,当使用回调指针从 Swift 调用时,它按预期工作。
void invokeCallback(uintptr_t callback) {
((void (*)()) callback)(); // such pointer…
}
与
Swift 3 的示例(假设 funcPtr
是一个
UnsafeRawPointer
包含函数的地址):
// Define function type:
typealias callbackFunc = @convention(c) () -> Void
// Convert pointer to function type:
let callback = unsafeBitCast(funcPtr, to: callbackFunc.self)
// Call function:
callback()
当然类型别名必须与实际的函数签名匹配, 函数必须是 "pure" C 函数(不是 Objective-C 方法)。