为什么当我不使用局部变量时,我会收到 EXC 错误访问?



我有一段代码,它将数据从AudioFileID读取到缓冲区中。

- (void)handle:(void *)aqData audioQueue:(AudioQueueRef) audioQueue buffer:(AudioQueueBufferRef) buffer
{
TestViewController *vc = (__bridge TestViewController *)aqData;
EDCAudioFile *file = vc.file;
UInt32 numPackets = file.numberOfPacketsToRead;
UInt32 numBytesReadFromFile;
OSStatus err = AudioFileReadPacketData(file.audioFile, NO, &numBytesReadFromFile, vc.mPacketDescs, file.currentPacket, &numPackets, buffer->mAudioData);

当我在我的方法中声明一个局部变量时,一切都很好,比如

EDCAudioFile *file = vc.file;
OSStatus err = AudioFileReadPacketData(file.audioFile, NO, &numBytesReadFromFile, vc.mPacketDescs, file.currentPacket, &numPackets, buffer->mAudioData);

EDCAudioFile是一个类,它包含AudioFileID的属性,如下所示:

@property (nonatomic, assign) AudioFileID audioFile;

但当我把它改成时

OSStatus err = AudioFileReadPacketData(vc.file.audioFile, NO, &numBytesReadFromFile, vc.mPacketDescs, file.currentPacket, &numPackets, buffer->mAudioData);

而vc包含这个属性

@property (nonatomic, strong) EDCAudioFile *file;

它与EXC坏访问线程1地址0x4一起崩溃。当我从模态视图控制器中选择一首歌曲时,该方法被调用为这样,该方法创建了一个具有16个缓冲区的音频队列,并用音频数据填充它们。

for (int i=0; i < 16; i++) {
    AudioQueueAllocateBuffer(self.mQueue, file.bufferByteSize, &_mBuffers[i]);
    handleOutputBuffer((__bridge void*) self, self.mQueue, _mBuffers[i]);
}
...
static void handleOutputBuffer (void *aqData, AudioQueueRef audioQueue, AudioQueueBufferRef buffer)
{
     TestViewController *vc = (__bridge TestViewController *)aqData;
     [vc handle:aqData audioQueue:audioQueue buffer:buffer];
}

当i=1和i=0时,它确实崩溃了。OSStatus报告了一个错误,代码为:2003334207

NSZombie告诉,这个代码甚至不会在我的IPhone 5上崩溃,而是在我的iPad Mini上崩溃。方法在主线程上调用。

正如我在第一块代码中所说的,一切都很好,我可以在iPhone和iPad上播放音乐。

我很感激能得到的每一个帮助。

哦,这是我的堆栈跟踪:堆栈跟踪

这背后的原因是我遵循了Apple指南音频队列指南播放音频,现在我想通过创建一个包含所有所需信息的类来尝试使其更加面向对象,因为苹果使用了一个结构。

我刚刚通过更改这行来修复它

- (void)handle:(void *)aqData audioQueue:(AudioQueueRef) audioQueue buffer:(AudioQueueBufferRef) buffer

到这个

- (void)handle:(TestViewController *)aqData audioQueue:(AudioQueueRef) audioQueue buffer:(AudioQueueBufferRef) buffer
{
    UInt32 numBytesReadFromFile;
    UInt32 numPackets = vc.file.numberOfPacketsToRead;
    AudioFileReadPacketData(vc.file.audioFile, NO, &numBytesReadFromFile, vc.packetDescs, vc.file.currentPacket, &numPackets, buffer->mAudioData);

最新更新