jjzjj

ios - sqlite3.dylib : illegal multi-threaded access to database connection

coder 2023-09-30 原文

我有一个使用 sqlite3 的 iOS 应用程序,我正面临着多线程问题,该应用程序因 illegal multi-threaded access to database connection 消息而崩溃。当然是因为我用的是多线程;问题是,我的 sqlite3 实例配置为使用多线程:

sqlite3_config(SQLITE_CONFIG_MULTITHREAD);

即使我使用的是多线程(sqlite3 build 也是使用多线程标志编译的),它会导致我的应用程序在多个线程同时写入或读取数据库时崩溃。

崩溃报告

Application Specific Information:
BUG IN CLIENT OF sqlite3.dylib: illegal multi-threaded access to database connection

Exception Type:  EXC_BREAKPOINT (SIGTRAP)
Exception Codes: 0x0000000000000001, 0x00000001823ed2fc
Termination Signal: Trace/BPT trap: 5
Termination Reason: Namespace SIGNAL, Code 0x5
Terminating Process: exc handler [0]
Triggered by Thread:  12

Thread 12 Crashed:

0   libsqlite3.dylib                0x00000001823ed2fc sqlite3MutexMisuseAssert + 144 (sqlite3.c:23788)
1   libsqlite3.dylib                0x00000001823ed2ec sqlite3MutexMisuseAssert + 128 (once.h:84)
2   libsqlite3.dylib                0x000000018235248c sqlite3LockAndPrepare + 320 (sqlite3.c:23801)
3   MyCodeCall.m ...........

我已经为这个问题苦苦挣扎了一段时间,不幸的是我在谷歌上找不到任何相关的引用资料。

更新

+(sqlite3*) getInstance {
  if (instance == NULL) {
    sqlite3_shutdown();
    sqlite3_config(SQLITE_CONFIG_MULTITHREAD);
    sqlite3_initialize();

    NSLog(@"isThreadSafe %d", sqlite3_threadsafe());

    const char *path = [@"./path/to/db/db.sqlite" cStringUsingEncoding:NSUTF8StringEncoding];

    if (sqlite3_open_v2(path, &database, SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE, NULL) != SQLITE_OK) {
      NSLog(@"Database opening failed!");
    }
  }

  return instance;
}

最佳答案

事实证明,只要您不同时使用同一连接,SQLITE_CONFIG_MULTITHREAD 模式在多线程环境中运行良好;这恰好是我遇到的确切情况。因此,要解决此问题,您可以为每个线程打开一个新连接,或者使用 SQLITE_CONFIG_SERIALIZED 在完全互斥模式下使用 SQLITE_OPEN_FULLMUTEX 标志打开连接。

辅助方法最终是这样的:

+(sqlite3*) getInstance {
  if (instance == NULL) {
    sqlite3_shutdown();
    sqlite3_config(SQLITE_CONFIG_SERIALIZED);
    sqlite3_initialize();

    NSLog(@"isThreadSafe %d", sqlite3_threadsafe());

    const char *path = [@"./path/to/db/db.sqlite" cStringUsingEncoding:NSUTF8StringEncoding];

    if (sqlite3_open_v2(path, &database, SQLITE_OPEN_READWRITE|SQLITE_OPEN_FULLMUTEX, NULL) != SQLITE_OK) {
      NSLog(@"Database opening failed!");
    }
  }

  return instance;
}

关于ios - sqlite3.dylib : illegal multi-threaded access to database connection,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49198831/

有关ios - sqlite3.dylib : illegal multi-threaded access to database connection的更多相关文章

随机推荐