尝试一次我得到CrashIfClientProvidedBogusAudioBufferList
异常AudioConverterFillComplexBuffer
回调返回。为什么会引发此异常的可能原因是什么?
供引用,这是我的电话
AudioConverterFillComplexBuffer(audioConverterRef,
fillComplexCallback,
&convertInfo,
&framesToDecode,
&localPcmBufferList,
和回调:
func fillComplexxCallback(myConverter: AudioConverterRef, packetNumber: UnsafeMutablePointer<UInt32>,
ioData: UnsafeMutablePointer<AudioBufferList>, aspd: UnsafeMutablePointer<UnsafeMutablePointer<AudioStreamPacketDescription>>,
userInfo: UnsafeMutablePointer<Void>) -> OSStatus {
var convertInfo = UnsafeMutablePointer<AudioConvertInfo>(userInfo).memory
if (packetNumber.memory > (convertInfo.audioBuffer.mDataByteSize / convertInfo.numberOfPackets)) {
packetNumber.memory = (convertInfo.audioBuffer.mDataByteSize / convertInfo.numberOfPackets)
}
ioData.memory.mNumberBuffers = 1
var buffer = AudioBuffer(mNumberChannels: 2, mDataByteSize: convertInfo.audioBuffer.mDataByteSize, mData: ioData.memory.mBuffers.mData)
ioData.memory.mBuffers = buffer
/* if the following is uncommented out, a exception is thrown */
// aspd.memory = convertInfo.packetDescriptions
packetNumber.memory = convertInfo.numberOfPackets
convertInfo.done = true
return 0
}
这是
AudioConvertInfo's
结构:struct AudioConvertInfo {
var done: Bool! //conversion of audio is finished
var numberOfPackets: UInt32!
var audioBuffer: AudioBuffer!
var audioPlayer: CCPlayer!
var packetDescriptions: AudioStreamPacketDescription!
init(done: Bool?, numberOfPackets: UInt32?, audioBuffer: AudioBuffer?, packetDescriptions: AudioStreamPacketDescription!, audioPlayer: CCPlayer!) {
self.done = done
self.numberOfPackets = numberOfPackets
self.audioBuffer = audioBuffer
self.packetDescriptions = packetDescriptions
self.audioPlayer = audioPlayer
}
}
我似乎找不到任何可靠的文档。我注意到aspd(
AudioStreamPacketDescription
)返回nil。确定音频数据缓冲区中一个数据包大小不同或音频数据包之间存在非音频数据的数据包,这一点很重要。此代码将在aspd.memory = convertInfo.packetDescriptions上引发异常,但是如果注释掉该代码,则会抛出CrashIfClientProvidedBogusAudioBufferList。我的理论是,如果我弄清楚为什么AudioStreamPacketDescription为nil,则此回调将正常工作 最佳答案
好像AudioStreamPacketDescription is nil
没问题。
根据Apple文档,它可以为零,基本上取决于音频格式:
AudioConverterComplexInputDataProc
AudioConverterFillComplexBuffer
真正的问题在这一行中的AudioConvertInfo
结构中:
var packetDescriptions: AudioStreamPacketDescription!
结构仅保留单个
AudioStreamPacketDescription
结构。然后在
fillComplexCallback
函数中使用它:outDataPacketDescription.memory.memory = convertInfo.packetDescriptions
因此,您尝试将单个
AudioStreamPacketDescription
结构设置为需要outDataPacketDescription
结构数组的参数AudioStreamPacketDescription
(而不仅仅是单个实例)。可以通过保留和使用
AudioStreamPacketDescription
结构数组来解决此问题。AudioConvertInfo
结构的更新版本:struct AudioConvertInfo {
var done: Bool!
var numberOfPackets: UInt32!
var audioBuffer: AudioBuffer!
var audioPlayer: CCPlayer!
var packetDescriptions: UnsafeMutablePointer<AudioStreamPacketDescription>!
init(done: Bool?, numberOfPackets: UInt32?, audioBuffer: AudioBuffer?, packetDescriptions: UnsafeMutablePointer<AudioStreamPacketDescription>!, audioPlayer: CCPlayer!) {
self.done = done
self.numberOfPackets = numberOfPackets
self.audioBuffer = audioBuffer
self.packetDescriptions = packetDescriptions
self.audioPlayer = audioPlayer
}
}
// Usage:
convertInfo = AudioConvertInfo(done: false, numberOfPackets: numberPackets, audioBuffer: AudioBuffer(mNumberChannels: 2, mDataByteSize: numberBytes, mData: &iData), packetDescriptions: packetDescriptions, audioPlayer: self)
fillComplexCallback
函数的更新版本:func fillComplexCallback(inAudioConverter: AudioConverterRef, ioNumberDataPackets: UnsafeMutablePointer<UInt32>, ioData: UnsafeMutablePointer<AudioBufferList>, outDataPacketDescription: UnsafeMutablePointer<UnsafeMutablePointer<AudioStreamPacketDescription>>, inUserData: UnsafeMutablePointer<Void>) -> OSStatus {
var convertInfo = UnsafeMutablePointer<AudioConvertInfo>(inUserData).memory
if convertInfo.done == true {
ioNumberDataPackets.memory = 0
return 100
}
ioData.memory.mNumberBuffers = 1
let buffer = convertInfo.audioBuffer
ioData.memory.mBuffers = buffer
if outDataPacketDescription != nil {
outDataPacketDescription.memory = convertInfo.packetDescriptions
}
ioNumberDataPackets.memory = convertInfo.numberOfPackets
convertInfo.done = true
return 0
}
// Usage:
status = AudioConverterFillComplexBuffer(audioConverterRef, fillComplexCallback, &convertInfo!, &framesToDecode, &localPcmBufferList!, nil)
希望它能解决您的问题。
关于ios - (快速)如何在AudioStreamPacketDescription为nil时调试CrashIfClientProvidedBogusAudioBufferList?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/31708398/