Xcode14 & iOS16中VOIP流崩溃:需改用Local Push Connectivity
问题:iOS 16下设置VOIP类型Socket流导致APP启动崩溃
环境与崩溃现象
在Xcode 14 & iOS 16环境下,APP启动后立即崩溃,排查后确定崩溃发生在调用inputStream!.open()和outputStream!.open()打开流的环节。
相关代码
流定义
private var inputStream: InputStream! private var outputStream: OutputStream!
流创建代码
var readStream: Unmanaged<CFReadStream>? var writeStream: Unmanaged<CFWriteStream>? CFStreamCreatePairWithSocketToHost(nil, connectionConfiguration.host, connectionConfiguration.port, &readStream, &writeStream) inputStream = readStream!.takeRetainedValue() outputStream = writeStream!.takeRetainedValue() inputStream.setProperty(StreamSocketSecurityLevel.negotiatedSSL, forKey: .socketSecurityLevelKey) outputStream.setProperty(StreamSocketSecurityLevel.negotiatedSSL, forKey: .socketSecurityLevelKey) inputStream.setProperty(StreamNetworkServiceTypeValue.voIP, forKey: Stream.PropertyKey.networkServiceType) outputStream.setProperty(StreamNetworkServiceTypeValue.voIP, forKey: Stream.PropertyKey.networkServiceType)
流配置代码
inputStream!.delegate = self outputStream!.delegate = self inputStream!.schedule(in: .main, forMode: RunLoop.Mode.default) outputStream!.schedule(in: .main, forMode: RunLoop.Mode.default)
崩溃触发代码
inputStream!.open() outputStream!.open()
崩溃日志
libsp.dylib`spd_checkin_socket.cold.1: 0x21c764464 <+0>: adrp x8, 144598 0x21c764468 <+4>: adrp x9, 0 0x21c76446c <+8>: add x9, x9, #0xa3f ; "Linked against modern SDK, VOIP socket will not wake. Use Local Push Connectivity instead" 0x21c764470 <+12>: str x9, [x8, #0x390] -> 0x21c764474 <+16>: brk #0x1
问题原因
iOS 16及后续版本中,苹果彻底废弃了通过设置networkServiceType为.voIP来创建VOIP类型Socket的方式,系统会直接触发崩溃,强制开发者使用Local Push Connectivity框架实现需要后台唤醒的网络连接需求。
解决方案
1. 移除VOIP类型设置(立即修复崩溃)
删除流创建代码中设置networkServiceType为.voIP的两行代码:
// 移除以下两行代码 // inputStream.setProperty(StreamNetworkServiceTypeValue.voIP, forKey: Stream.PropertyKey.networkServiceType) // outputStream.setProperty(StreamNetworkServiceTypeValue.voIP, forKey: Stream.PropertyKey.networkServiceType)
如果你的业务仅需要前台Socket连接,不需要后台唤醒,这一步即可解决崩溃问题,Socket能正常建立。
2. 改用Local Push Connectivity实现后台连接(针对需要后台唤醒的场景)
若需APP在后台保持网络连接并被唤醒,需使用苹果官方的Local Push Connectivity方案:
- 向项目中添加
PushKit框架 - 实现
PKPushRegistry注册VOIP类型推送,通过推送事件唤醒APP后再建立Socket连接 - 建立Socket时,使用默认的
networkServiceType或根据业务选择.default等合适类型,不再设置.voIP
内容的提问来源于stack exchange,提问作者Tomasz Rybkowski
相关产品推荐
相关产品推荐

