我试图在Swift中实现AES 128,并且最近遇到了将Swift字符串写入CChar
数组的问题:
let testString = "myTestString"
var keyPtr = [CChar](count: kCCKeySizeAES128 + 1, repeatedValue: 0)
bzero(&keyPtr, strideof(keyPtr.dynamicType))
testString.getCString(&keyPtr, maxLength: strideof(keyPtr.dynamicType), encoding: NSUTF8StringEncoding)
print(keyPtr)
在32位设备(iPad 2,iPad 4)上,记录:
[109, 121, 84, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
在64位设备(iPhone 6,Macbook Pro i7)上记录:
[109, 121, 84, 101, 115, 116, 83, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
64位情况是正确的结果,而32位结果不是。
我也遇到了withCString
同样的问题:
testString.withCString({
print($0)
})
在32位设备上,这会记录0x7a992094
,而64位设备会记录0x00007f853c123760
。
如何在所有架构中使getCString
或withCString
的结果相同?这是CChar
的大小还是不同架构上的数组的问题?
答案 0 :(得分:1)
不好的一点是:strideof(keyPtr.dynamicType)
它与strideof(Array<CChar>)
相同,其值在32位中为4,在64位中为8。
您需要像这样修改代码:
bzero(&keyPtr, keyPtr.count) //<-this is not needed, as you are specifying `0` for `repeatedValue`.
testString.getCString(&keyPtr, maxLength: keyPtr.count, encoding: NSUTF8StringEncoding)
答案 1 :(得分:1)
为了完整起见,因为您询问了withCString()
:
该方法调用创建临时C String表示
(即NUL终止的CChar
)序列
Swift字符串,并调用设置为地址$0
的闭包
(该字符串中的第一个字符)所以$0
是指针
因此取决于平台,32位或64位。
您可以使用以下命令将该C字符串复制到给定数组:
testString.withCString { strlcpy(&keyPtr, $0, keyPtr.count) }