[evolution-data-server/evolution-data-server-3-12] Limit SQLite busy-wait for a lock



commit 7bd7d8c3c659840509d055a278113b4b4e53ad7c
Author: Milan Crha <mcrha redhat com>
Date:   Wed Nov 19 11:13:51 2014 +0100

    Limit SQLite busy-wait for a lock
    
    The previous busy-wait could cause flood of the kernel with a lock
    request, with basically no outer limit. This change adds a 15 seconds
    time limit with a 100 ms delay between each lock request.

 .../libedata-book/e-book-backend-sqlitedb.c        |    9 ++++++++-
 addressbook/libedata-book/e-book-sqlite.c          |    8 +++++++-
 camel/camel-db.c                                   |   10 +++++++++-
 3 files changed, 24 insertions(+), 3 deletions(-)
---
diff --git a/addressbook/libedata-book/e-book-backend-sqlitedb.c 
b/addressbook/libedata-book/e-book-backend-sqlitedb.c
index 7f5396c..2793e47 100644
--- a/addressbook/libedata-book/e-book-backend-sqlitedb.c
+++ b/addressbook/libedata-book/e-book-backend-sqlitedb.c
@@ -321,15 +321,22 @@ book_backend_sql_exec_real (sqlite3 *db,
                             GError **error)
 {
        gchar *errmsg = NULL;
-       gint ret = -1;
+       gint ret = -1, retries = 0;
 
        ret = sqlite3_exec (db, stmt, callback, data, &errmsg);
        while (ret == SQLITE_BUSY || ret == SQLITE_LOCKED || ret == -1) {
+               /* try for ~15 seconds, then give up */
+               if (retries > 150)
+                       break;
+               retries++;
+
                if (errmsg) {
                        sqlite3_free (errmsg);
                        errmsg = NULL;
                }
                g_thread_yield ();
+               g_usleep (100 * 1000); /* Sleep for 100 ms */
+
                ret = sqlite3_exec (db, stmt, callback, data, &errmsg);
        }
 
diff --git a/addressbook/libedata-book/e-book-sqlite.c b/addressbook/libedata-book/e-book-sqlite.c
index 427f6de..e3770fe 100644
--- a/addressbook/libedata-book/e-book-sqlite.c
+++ b/addressbook/libedata-book/e-book-sqlite.c
@@ -1082,7 +1082,7 @@ ebsql_exec (EBookSqlite *ebsql,
 {
        gboolean had_cancel;
        gchar *errmsg = NULL;
-       gint ret = -1;
+       gint ret = -1, retries = 0;
        gint64 t1 = 0, t2;
 
        /* Debug output for statements and query plans */
@@ -1106,11 +1106,17 @@ ebsql_exec (EBookSqlite *ebsql,
        ret = sqlite3_exec (ebsql->priv->db, stmt, callback, data, &errmsg);
 
        while (ret == SQLITE_BUSY || ret == SQLITE_LOCKED || ret == -1) {
+               /* try for ~15 seconds, then give up */
+               if (retries > 150)
+                       break;
+               retries++;
+
                if (errmsg) {
                        sqlite3_free (errmsg);
                        errmsg = NULL;
                }
                g_thread_yield ();
+               g_usleep (100 * 1000); /* Sleep for 100 ms */
 
                if (t1)
                        t1 = g_get_monotonic_time();
diff --git a/camel/camel-db.c b/camel/camel-db.c
index cf0e71f..fb0e581 100644
--- a/camel/camel-db.c
+++ b/camel/camel-db.c
@@ -480,16 +480,24 @@ cdb_sql_exec (sqlite3 *db,
               GError **error)
 {
        gchar *errmsg = NULL;
-       gint   ret = -1;
+       gint   ret = -1, retries = 0;
 
        d (g_print ("Camel SQL Exec:\n%s\n", stmt));
 
        ret = sqlite3_exec (db, stmt, callback, data, &errmsg);
        while (ret == SQLITE_BUSY || ret == SQLITE_LOCKED || ret == -1) {
+               /* try for ~15 seconds, then give up */
+               if (retries > 150)
+                       break;
+               retries++;
+
                if (errmsg) {
                        sqlite3_free (errmsg);
                        errmsg = NULL;
                }
+               g_thread_yield ();
+               g_usleep (100 * 1000); /* Sleep for 100 ms */
+
                ret = sqlite3_exec (db, stmt, NULL, NULL, &errmsg);
        }
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]