I’m getting crash, and I can’t figure out what is causing it. Here what I’m getting from crash report:
Exception Type: EXC_BAD_ACCESS (SIGSEGV)
Exception Subtype: KERN_INVALID_ADDRESS at 0x0000000c
Triggered by Thread: 0
Thread 0 Crashed:
0 AVFoundation 0x2f271946 -[AVPlayerPeriodicCaller _effectiveRateChanged] + 418
1 AVFoundation 0x2f270fc8 __43-[AVPlayerTimelyCaller _timebaseDidChange:]_block_invoke + 232
2 libdispatch.dylib 0x3b04ed50 _dispatch_call_block_and_release + 8
3 libdispatch.dylib 0x3b04ed3c _dispatch_client_callout + 20
4 libdispatch.dylib 0x3b0516be _dispatch_main_queue_callback_4CF + 274
5 CoreFoundation 0x3039b674 __CFRUNLOOP_IS_SERVICING_THE_MAIN_DISPATCH_QUEUE__ + 4
6 CoreFoundation 0x30399f40 __CFRunLoopRun + 1304
7 CoreFoundation 0x303047a4 CFRunLoopRunSpecific + 520
8 CoreFoundation 0x30304586 CFRunLoopRunInMode + 102
9 GraphicsServices 0x352716ce GSEventRunModal + 134
10 UIKit 0x32c6388c UIApplicationMain + 1132
11 my-app 0x00029dd4 main (main.m:16)
12 libdyld.dylib 0x3b063ab4 start + 0
As I understand it’s coming from addPeriodicTimeObserverForInterval:queue:usingBlock:
, so I’m always checking for block and queue to be correct. What else can cause this?
Thanks in advance.
Here is method that calls addPeriodicTimeObserverForInterval:queue:usingBlock:
- (void)addPeriodicTimeObserverForInterval:(CMTime)interval queue:(dispatch_queue_t)queue usingBlock:(void (^)(CMTime time))block
{
[block copy];
dispatch_async(self.operationQueue, ^{
//This method just makes sure, that self.player not nil
[self someMethodcompletionHandler:^{
if (self.observer) {
[self.player removeTimeObserver:self.observer];
self.observer = nil;
}
if (block && queue) {
self.observer = [self.player addPeriodicTimeObserverForInterval:interval
queue:queue
usingBlock:block];
}
}];
});
}
I figured it out. But I don’t know, why that works. So my question, why it works? Why self.operationQueue
better than just queue
?
self.observer = [self.player addPeriodicTimeObserverForInterval:interval
queue:self.operationQueue
usingBlock:^(CMTime time){
dispatch_async(queue, ^{
block(time);
});
}];
Official AVPlayer
documentation states:
Releasing the observer object without invoking removeTimeObserver: will result in undefined behavior
This means that you should keep the value returned from addPeriodicTimeObserverForInterval:queue:usingBlock:
and before the observer block is released make sure that you call removeTimeObserver:
Also note that block objects are allocated on the stack by default (not the heap) so to be sure that your block is not released when the frame ends you should retain the block by calling copy. To read more about block memory management see here.
User contributions licensed under CC BY-SA 3.0