gpt4 book ai didi

swift - 将 Swift uuid_t 传递给 C 函数

转载 作者:行者123 更新时间:2023-11-28 06:15:24 24 4
gpt4 key购买 nike

如何使用 Swift 将 UUID 传递给采用 uuid_t 的 C 函数?

假设我在桥接 header 中声明了以下函数:

bool my_set_uuid(uuid_t uuid);

在 Swift 中,我试图向它传递一个新的 UUID:

let uuid = UUID()
my_set_uuid(uuid.uuid)

我收到以下错误:“无法转换‘uuid_t’类型的值(又名‘(UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8, UInt8)') 到预期的参数类型 'UnsafeMutablePointer!'"

我知道这是因为 UUID.uuid 是 uuid_t 类型,它被实现为一个 16 字节的 C 数组,在 Swift 中变成了 16 个 UInt8 的元组。但为什么我不能将 C uuid_t 传递给 C?它似乎在期待一个指针。

因此,我尝试使用 withUnsafeMutableBytes 创建一个指向我的 uuid 的指针。我发现这行得通:

let _: UInt8 = withUnsafeMutablePointer(to: &uuid.0) { ptr in
my_set_uuid(ptr)
return 0
}

但我还了解到 &uuid.0 是不安全的,因为我在我的 C 函数中使用了整个元组(作为数组)。此外,我对 let _: UInt8return 0 所做的所有修饰似乎都是错误的。

最佳答案

这样使用&uuid.0确实不安全。由于 Swift 编译器可能会在临时区域中创建单个元素的副本,并将该区域的地址传递给函数。这在优化代码中可能不会发生,但您无法预测 Swift 生成的代码。

为了让你的代码安全,你可能需要这样写:

    let uuid = UUID()
var rawUuid = uuid.uuid
// (You can rewrite the two lines above into a sigle line as `var rawUuid = UUID().uuid`
let result = withUnsafeMutablePointer(to: &rawUuid) {uuidPtr in
uuidPtr.withMemoryRebound(to: UInt8.self, capacity: MemoryLayout<uuid_t>.size) {bytePtr in
my_set_uuid(bytePtr)
}
}

(result获取my_set_uuid(bytePtr)的值,如果想忽略结果,将let result替换为 _.)

uuid_t 是 C 中固定大小的数组类型,这在 Swift 中很难使用。也许 Swift 中的元组类型应该有更好的方法来处理这种用例。

关于swift - 将 Swift uuid_t 传递给 C 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45291728/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com