在控制器内调用startDeviceMotionUpdatesToQueue时得到OSSpinLockLock [英] I get OSSpinLockLock when calling startDeviceMotionUpdatesToQueue inside a controller

查看:154
本文介绍了在控制器内调用startDeviceMotionUpdatesToQueue时得到OSSpinLockLock的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我的根控制器中,我有一个CMMotionManager

In my root controller I have a property with the CMMotionManager

@property (strong, nonatomic) CMMotionManager *MManager;

在它的getter中,我进行了惰性实例化.当控制器的视图加载时,我调用此方法

In its getter I do lazy instantiation. When the controller's view loads, I call this method

- (void)reloadAccelerometer {
    NSLog(@"Away we go");
    self.MManager.deviceMotionUpdateInterval = 10.0/60.0;
    [self.MManager startDeviceMotionUpdatesToQueue:self.queue withHandler:^(CMDeviceMotion *motion, NSError *error) {
        NSLog(@"Y values is: %f", motion.userAcceleration.y);
    }];
}

我在NSLog中看到"Away we go",然后应用立即崩溃,并且得到了该线程日志

I see "Away we go" in the NSLog and then immediately the app crashes and I get this thread log

libsystem_platform.dylib`spin_lock$VARIANT$mp:
0x39a87814:  movs   r1, #1

libsystem_platform.dylib`OSSpinLockLock$VARIANT$mp + 2:
0x39a87816:  ldrex  r2, [r0]
0x39a8781a:  cmp    r2, #0
0x39a8781c:  it     ne
0x39a8781e:  bne.w  0x39a893ec                ; _OSSpinLockLockSlow$shim
0x39a87822:  strex  r2, r1, [r0]
0x39a87826:  cmp    r2, #0
0x39a87828:  bne    0x39a87816                ; OSSpinLockLock$VARIANT$mp + 2
0x39a8782a:  dmb    ish
0x39a8782e:  bx     lr

我怎么了?我将reloadAccelerometer放在错误的位置了吗?

What's my mistake? Did i place reloadAccelerometer in the wrong place?

推荐答案

我试图在我的iOS应用中做类似的事情,并花了永远来找出崩溃的原因.这是一个非常隐秘的(令人讨厌的)异常.在阅读完崩溃报告后,我终于弄清了这件事,该报告涉及OSSpinLock线程/队列管理问题有关.

I was trying to do something similar in my iOS app and spent forever trying to figure out what the cause of the crash was. This was a very cryptic (and pesky) exception. I eventually figured it out after reading through the crash reports that OSSpinLock has to do with a thread / queue management issue.

NSOperationQueue是这里的罪魁祸首.您的代码未显示您如何创建NSOperationQueue,但是我认为它是这样的:

The NSOperationQueue is the culprit here. Your code doesn't show how you were creating your NSOperationQueue, but I assume it was something like this:

NSOperationQueue *aQueue = [[NSOperationQueue alloc] init]; // Do NOT do this
[self.MManager startDeviceMotionUpdatesToQueue:aQueue withHandler:^(CMDeviceMotion *motion, NSError *error) {
    NSLog(@"Y values is: %f", motion.userAcceleration.y);
}];

事实证明,这不是使用NSOperationQueue的方式.该aQueue对象是导致崩溃的原因.

It turns out that this is not the way to use the NSOperationQueue. That aQueue object is the cause of the crash.

要正确设置操作队列并避免崩溃,应将CMMotionManager移至其他线程.然后告诉NSOperationQueue使用 currentQueue ,而不是mainQueue.苹果建议不要在mainQueue上运行它,但是,如果您的应用当前正在主队列中运行,那么我看不到currentQueue有什么不同.我尝试使用GCD将下面的代码移到另一个队列中,但从未调用过任何代码.

To properly setup the operation queue and avoid a crash, you should move your CMMotionManager to a different thread. Then tell NSOperationQueue to use the currentQueue, NOT the mainQueue. Apple recommends that it is not run on the mainQueue, however if your app is currently running in the main queue then I don't see how the currentQueue is any different. I tried moving the code below to a different queue using GCD, but no code was ever called.

这是您最终代码的外观:

Here's what your final code should look like:

// Check if Motion / Location services are available
if (motionManager.deviceMotionAvailable == YES && motionManager.accelerometerAvailable == YES) {
    NSLog(@"Away we go");
    self.MManager.deviceMotionUpdateInterval = 10.0/60.0;
    [self.MManager startDeviceMotionUpdatesToQueue:[NSOperationQueue currentQueue] withHandler:^(CMDeviceMotion *motion, NSError *error) {
        NSLog(@"Y values is: %f", motion.userAcceleration.y);
     }];
} else {
    // Motion / Accelerometer services unavailable
}

我还应该注意,据我所知,您创建的CMMotionManager属性对于(strong, nonatomic)是正确的.

I should also note that your creation of the CMMotionManager property (to my knowledge) is correct with (strong, nonatomic).

这篇关于在控制器内调用startDeviceMotionUpdatesToQueue时得到OSSpinLockLock的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆