Thanks very much for your notes Olaf. I've done as you suggest... I already had SQLITE_THREADSAFE=2 defined, but didn't have the SQLITE_OMIT_SHARED_CACHE asserted (assuming private cache to be the default).
The Objective-C method that each thread calls to do the actual querying (bracketed only by timing logic) is: /*! * Get the array of all results of the agents query */ - (NSArray *)agentDetails { sqlite3_stmt *statement; NSMutableArray *rowsArray = nil; // TTT sqlite3 *database; if (sqlite3_open_v2([DBFILE UTF8String], &database, 0, NULL) != SQLITE_OK) NSAssert1(0, @"Failed to open database with message '%s'.", sqlite3_errmsg(database)); if (sqlite3_prepare_v2(database, [AGENT_DETAILS_SQL UTF8String], -1, &statement, NULL) == SQLITE_OK) { rowsArray = [NSMutableArray arrayWithCapacity:1000]; while (sqlite3_step(statement) == SQLITE_ROW) { NSString *login = stringOrEmpty(sqlite3_column_text(statement, 0)); NSString *datasetID = stringOrEmpty(sqlite3_column_text(statement, 1)); NSString *fullName = stringOrEmpty(sqlite3_column_text(statement, 2)); NSString *lastName = stringOrEmpty(sqlite3_column_text(statement, 3)); NSString *firstName = stringOrEmpty(sqlite3_column_text(statement, 4)); // Make a row dictionary NSDictionary *rowDict = [NSDictionary dictionaryWithObjectsAndKeys: login, @"login", datasetID, @"datasetID", fullName, @"fullName", lastName, @"lastName", firstName, @"firstName", nil]; [rowsArray addObject:rowDict]; } } else { NSAssert1(0, @"Failed to run query.\nError message '%s'.", sqlite3_errmsg(database)); } // Finish statement sqlite3_finalize(statement); // TTT sqlite3_close(database); return rowsArray; } The results are similar to before: 010-03-05 09:08:57.916 SQLiteTest[76760:a0f] SQLite says multithreading is ON 2010-03-05 09:08:57.918 SQLiteTest[76760:a0f] SQLite's multithreading value is 2 2010-03-05 09:08:57.921 SQLiteTest[76760:5503] Starting query on thread <NSThread: 0x10050bbc0>{name = (null), num = 4} 2010-03-05 09:08:57.921 SQLiteTest[76760:1b03] Starting query on thread <NSThread: 0x100511430>{name = (null), num = 3} 2010-03-05 09:08:57.921 SQLiteTest[76760:5603] Starting query on thread <NSThread: 0x102e07080>{name = (null), num = 5} 2010-03-05 09:08:57.921 SQLiteTest[76760:4403] Starting query on thread <NSThread: 0x100223820>{name = (null), num = 2} 2010-03-05 09:08:57.921 SQLiteTest[76760:5703] Starting query on thread <NSThread: 0x10051e980>{name = (null), num = 6} 2010-03-05 09:09:08.561 SQLiteTest[76760:5803] Starting query on thread <NSThread: 0x103037e00>{name = (null), num = 7} 2010-03-05 09:09:08.619 SQLiteTest[76760:5603] Finished query on thread <NSThread: 0x102e07080>{name = (null), num = 5} in 10.70s 2010-03-05 09:09:08.620 SQLiteTest[76760:1b03] Finished query on thread <NSThread: 0x100511430>{name = (null), num = 3} in 10.70s 2010-03-05 09:09:08.620 SQLiteTest[76760:4403] Finished query on thread <NSThread: 0x100223820>{name = (null), num = 2} in 10.70s 2010-03-05 09:09:08.620 SQLiteTest[76760:5503] Finished query on thread <NSThread: 0x10050bbc0>{name = (null), num = 4} in 10.70s 2010-03-05 09:09:08.620 SQLiteTest[76760:5703] Finished query on thread <NSThread: 0x10051e980>{name = (null), num = 6} in 10.70s 2010-03-05 09:09:10.446 SQLiteTest[76760:5803] Finished query on thread <NSThread: 0x103037e00>{name = (null), num = 7} in 1.88s 2010-03-05 09:09:10.449 SQLiteTest[76760:a0f] Finished all queries in 12.53s I'm not familiar with the details of your last paragraph, specifically "dynamic access-mode-switches", but at some cost of time I could try a similar experiment on Linux to see if the behaviour differs. As noted, this is currently all running on Mac OS X 10.6 (Snow Leopard). Perhaps there are few people trying to get truly concurrent querying across multiple threads in this manner, but naturally I'd be interested to hear from any others running on the Mac who might have some related experience. -- Luke On 2010-03-05, at 3:50 AM, Olaf Schmidt wrote: > > "Luke Evans" <luk...@me.com> schrieb im Newsbeitrag > news:3be16206-d0c6-4041-a3a6-ca3c069ee...@me.com... > >> It's Objective-C, but all the SQLite interfacing bits are pure C >> directly driving the SQLite API compiled into the program >> (3.6.22 amalgamation). > Just to make sure ... do you really create different DB-Handles > (over dedicated DBOpen-Calls) in each of your threads? > > Aside from that, could you recompile the SQLite-library > on your system explicitely with: > SQLITE_THREADSAFE=2 > and > SQLITE_OMIT_SHARED_CACHE > > And then just open the DBHandles without giving > explicit "sqlite_open_v2() Flags"? > > Maybe (if that solves these "serialized Read-access-issues") > it could indicate, that the "dynamic access-mode-switches" > in sqlite_open_v2() do not work as expected in threaded > mode (at least on your system-OS). > > Olaf > > > > > > > > _______________________________________________ > sqlite-users mailing list > sqlite-users@sqlite.org > http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users > _______________________________________________ sqlite-users mailing list sqlite-users@sqlite.org http://sqlite.org:8080/cgi-bin/mailman/listinfo/sqlite-users