Android的NDK互斥锁(android NDK mutex locking)

2019-08-03 15:26发布

我已经移植一个跨平台的C ++引擎到Android,并注意到它会调用时的pthread_mutex_lock莫名其妙地(和反复无常)块。 这台发动机已经工作多年在多个平台上,并且有问题的代码在多年没有改变,所以我怀疑这是一个僵局或其它bug的代码。 它必须是我的端口到Android ..

到目前为止,在代码中的几个地方上封锁的pthread_mutex_lock。 这并不完全是可重复的两种。 当它挂起,有一个在logcat的没有可疑的输出。

我修改这样互斥代码(编辑为简洁起见...真正的代码检查所有的返回值):

void MutexCreate( Mutex* m )
{
#ifdef WINDOWS
    InitializeCriticalSection( m );
#else ANDROID
    pthread_mutex_init( m, NULL );
#endif
}


void MutexDestroy( Mutex* m )
{
#ifdef WINDOWS
    DeleteCriticalSection( m );
#else ANDROID
    pthread_mutex_destroy( m, NULL );
#endif
}

void MutexLock( Mutex* m )
{
#ifdef WINDOWS
    EnterCriticalSection( m );
#else ANDROID
    pthread_mutex_lock( m );
#endif
}

void MutexUnlock( Mutex* m )
{
#ifdef WINDOWS
    LeaveCriticalSection( m );
#else ANDROID
    pthread_mutex_unlock( m );
#endif
}

我试图修改MutexCreate进行错误检查和递归互斥体,但是这并不重要。 我没有得到,甚至错误或任何日志输出,所以要么这意味着我的互斥代码就好了,或者没有被显示的错误/日志。 究竟是怎样的OS通知你坏互斥的使用?

该发动机大量使用了静态变量,包括互斥的。 我看不出,但是这有什么问题? 我对此表示怀疑,因为我修改了很多互斥的堆上进行分配,而是和发生相同的行为。 但是,这可能是因为我错过了一些静态互斥。 我可能是在抓救命稻草这里。

我看了几参考,包括:

http://pubs.opengroup.org/onlinepubs/7908799/xsh/pthread_mutex_init.html

http://www.embedded-linux.co.uk/tutorial/mutex_mutandis

http://linux.die.net/man/3/pthread_mutex_init

Android的NDK互斥

Android的NDK问题调用pthread_mutex_unlock问题

Answer 1:

该“errorcheck”互斥量将检查两件事情(如尝试使用非递归互斥体递归),但不壮观。

你说:“真正的代码检查所有的返回值”,那么想必你的代码爆炸如有并行线程调用返回一个非零值。 (不知道为什么你的pthread_mutex_destroy有两个参数;假设复制和粘贴错误。)

该并行线程代码被广泛的Android内使用,并没有已知的挂断,所以这个问题是不可能在并行线程实现本身。

当前实现互斥的适合在32位,因此,如果您打印*(pthread_mutex_t* mut)作为一个整数,你应该能够找出什么状态,它是在(从技术上说,这什么样的状态在过去的某个点)。 在仿生/ libc中/仿生/ pthread.c的定义是:

/* a mutex is implemented as a 32-bit integer holding the following fields
 *
 * bits:     name     description
 * 31-16     tid      owner thread's kernel id (recursive and errorcheck only)
 * 15-14     type     mutex type
 * 13        shared   process-shared flag
 * 12-2      counter  counter of recursive mutexes
 * 1-0       state    lock state (0, 1 or 2)
 */

“快”的互斥体的类型为0,并且不设置tid场。 事实上,一个通用的互斥将具有0的值(不保持),1(保持),或2(举行,争用)。 如果你看到一个快速互斥体,它的值是不是其中之一,可能存在问题出现了,跺着脚就可以了。

这也意味着,如果您配置程序使用递归互斥体,你可以看到哪个线程通过拉动位出拥有互斥量(通过打印互斥值时的tryLock表示你即将来搪塞,或者用gdb倾倒状态在挂起的进程)。 也就是说,加上输出ps -t ,会让你知道,如果锁定互斥体的线程仍然存在。



文章来源: android NDK mutex locking