У меня есть программа сервер / клиент, где сервер порождает дочернего элемента с помощью fork () для каждого подключенного клиента. Затем клиент отправляет на сервер команды для выполнения определенных запросов к базе данных sqlite3 (INSERT INTO, SELECT, DELETE FROM). Примечание: Я открываю базу данных после fork (), как указано здесь: https://www.sqlite.org/howtocorrupt.html в 2.6
Проблема
Прекрасно работает, когда 1 клиент подключен, но когда есть 2 подключенных: когда один из них выполняет первый запрос, который изменяет базу данных (например, INSERT INTO), с этого момента только он может продолжать изменять. Остальные получают ошибку : база данных заблокирована . Даже после того, как клиент, блокирующий .db, завершает работу, другой по-прежнему не может измениться.
Я пытался:
- PRAGMA journal_mode = wal в терминале sqlite3
- выполнение вручную BEGIN TRANSACTION; до запроса INSERT и COMMIT; после
- sqlite3_close (db) после запроса INSERT и повторное открытие после
Наблюдение:
Я знаю, что использование потоков, вероятно, будет более безопасным и решит проблему, но я хотел бы попробовать все с помощью fork () перед изменением Вся структура проекта.
Код сервера (я удалил ненужные части кода):
int main () {
sqlite3* db;
//code for connection...
while (1) {
client = accept(sd, (struct sockaddr *) &from, &length);
if (-1 == (pid = fork())) {
perror("Error at fork");
}
if (pid == 0) {
if (sqlite3_open("./Database.db", &db))
perror("Error: Could not open database.\n")
while (1) {
sprintf(query, "INSERT INTO table VALUES ('%s','%s','%s','%s','%s','%s');",string1, string2,string3,string4,string5,string6);
if(sqlite3_exec(db, query, NULL, 0, &error) != SQLITE_OK){
printf("%s", sqlite3_errmsg(db));
fflush(stdout);
}
}
}
Спасибо за потраченное время!