[Midnightbsd-cvs] src [7767] trunk/lib/libmport: attempt to standardize the select count * code for indexes

laffer1 at midnightbsd.org laffer1 at midnightbsd.org
Sat Aug 27 16:28:24 EDT 2016


Revision: 7767
          http://svnweb.midnightbsd.org/src/?rev=7767
Author:   laffer1
Date:     2016-08-27 16:28:24 -0400 (Sat, 27 Aug 2016)
Log Message:
-----------
attempt to standardize the select count * code for indexes

Modified Paths:
--------------
    trunk/lib/libmport/db.c
    trunk/lib/libmport/index.c
    trunk/lib/libmport/mport_private.h

Modified: trunk/lib/libmport/db.c
===================================================================
--- trunk/lib/libmport/db.c	2016-08-27 14:28:28 UTC (rev 7766)
+++ trunk/lib/libmport/db.c	2016-08-27 20:28:24 UTC (rev 7767)
@@ -129,6 +129,54 @@
 	return result;
 }
 
+int
+mport_db_count(sqlite3 *db, int *count, const char *fmt, ...) {
+	va_list args;
+	char *sql;
+	__block int result = MPORT_OK;
+	__block char *err;
+	__block int realCount = 0;
+
+	va_start(args, fmt);
+	sql = sqlite3_vmprintf(fmt, args);
+	va_end(args);
+
+	if (sql == NULL)
+		RETURN_ERROR(MPORT_ERR_FATAL, "Couldn't allocate memory for sql statement");
+
+	dispatch_sync(mportSQLSerial, ^{
+		sqlite3_stmt *stmt;
+		int sqlcode = sqlite3_prepare_v2(db, sql, -1, &stmt, NULL);
+		if (sqlcode == SQLITE_BUSY || sqlcode == SQLITE_LOCKED) {
+			sleep(1);
+			if (sqlite3_prepare_v2(db, sql, -1, &stmt, NULL) != SQLITE_OK) {
+				err = (char *) sqlite3_errmsg(db);
+				result = MPORT_ERR_FATAL;
+				return;
+			}
+		} else if (sqlcode != SQLITE_OK) {
+			err = (char *) sqlite3_errmsg(db);
+			result = MPORT_ERR_FATAL;
+			return;
+		}
+
+		sqlite3_free(sql);
+
+		if (sqlite3_step(stmt) != SQLITE_ROW) {
+			sqlite3_finalize(stmt);
+			return;
+		}
+
+		realCount = sqlite3_column_int(stmt, 0);
+		sqlite3_finalize(stmt);
+	});
+	*count = realCount;
+
+	if (result == MPORT_ERR_FATAL)
+		SET_ERRORX(result, "sql error preparing '%s' : %s", sql, err);
+	return result;
+}
+
   
 
 /* mport_attach_stub_db(sqlite *db, const char *tmpdir) 

Modified: trunk/lib/libmport/index.c
===================================================================
--- trunk/lib/libmport/index.c	2016-08-27 14:28:28 UTC (rev 7766)
+++ trunk/lib/libmport/index.c	2016-08-27 20:28:24 UTC (rev 7767)
@@ -43,6 +43,7 @@
 static time_t get_time(void);
 static int lookup_alias(mportInstance *, const char *, char **);
 static int attach_index_db(sqlite3 *db);
+static void populate_row(sqlite3_stmt *stmt, mportIndexEntry *e);
 
 /*
  * Loads the index database.  The index contains a list of bundles that are
@@ -89,7 +90,7 @@
 	return (MPORT_OK);
 }
 
-int
+static int
 attach_index_db(sqlite3 *db)
 {
 
@@ -141,17 +142,17 @@
 
 /* return 1 if the index is younger than the max age, 0 otherwise */
 static int
-index_is_recentish(void) 
+index_is_recentish(void)
 {
-  struct stat st;
-  
-  if (stat(MPORT_INDEX_FILE, &st) != 0) 
-    return 0;
-   
-  if ((st.st_birthtime + MPORT_MAX_INDEX_AGE) < get_time()) 
-    return 0;
-    
-  return 1;
+	struct stat st;
+
+	if (stat(MPORT_INDEX_FILE, &st) != 0)
+		return 0;
+
+	if ((st.st_birthtime + MPORT_MAX_INDEX_AGE) < get_time())
+		return 0;
+
+	return 1;
 }
 
 static int
@@ -188,6 +189,7 @@
 static time_t 
 get_time(void) {
 	struct timespec now;
+
 	if (clock_gettime(CLOCK_REALTIME, &now) != 0)
 		RETURN_ERROR(MPORT_ERR_FATAL, strerror(errno));
 
@@ -203,66 +205,49 @@
  */
 int mport_index_get_mirror_list(mportInstance *mport, char ***list_p, int *list_size)
 {
-  char **list;
-  int len, ret, i;
-  sqlite3_stmt *stmt;
-  
-  /* XXX the country is hard coded until a configuration system is created */    
-  if (mport_db_prepare(mport->db, &stmt, "SELECT COUNT(*) FROM idx.mirrors WHERE country='us'") != MPORT_OK) {
-	  sqlite3_finalize(stmt);
-	  RETURN_CURRENT_ERROR;
-  }
+	char **list;
+	int ret, i;
+	int len;
+	sqlite3_stmt *stmt;
 
-  switch (sqlite3_step(stmt)) {
-    case SQLITE_ROW:
-      len = sqlite3_column_int(stmt, 0);
-      sqlite3_finalize(stmt);
-      break;
-    case SQLITE_DONE:
-      SET_ERROR(MPORT_ERR_FATAL, "A 'SELECT COUNT(*)...' statement returned no rows.");
-      sqlite3_finalize(stmt);
-      RETURN_CURRENT_ERROR;
-      break;
-    default:
-      SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
-      sqlite3_finalize(stmt);
-      RETURN_CURRENT_ERROR;
-  }
- 
-  *list_size = len; 
-  list = calloc(len + 1, sizeof(char *));
-  *list_p = list;  
-  i = 0;
-    
-  if (mport_db_prepare(mport->db, &stmt, "SELECT mirror FROM idx.mirrors WHERE country='us'") != MPORT_OK) {
-	  sqlite3_finalize(stmt);
-	  RETURN_CURRENT_ERROR;
-  }
-    
-  while (1) {
-    ret = sqlite3_step(stmt);
-    
-    if (ret == SQLITE_ROW) {
-      list[i] = strdup(sqlite3_column_text(stmt, 0));
-      
-      if (list[i] == NULL) {
-        sqlite3_finalize(stmt);
-        RETURN_ERROR(MPORT_ERR_FATAL, "Out of memory.");
-      }
-      
-      i++;
-    } else if (ret == SQLITE_DONE) {
-      list[i] = NULL;
-      break;
-    } else {
-      list[i] = NULL;
-      sqlite3_finalize(stmt);
-      RETURN_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
-    }
-  }
-  
-  sqlite3_finalize(stmt);
-  return MPORT_OK;
+	/* XXX the country is hard coded until a configuration system is created */
+	if (mport_db_count(mport->db, &len, "SELECT COUNT(*) FROM idx.mirrors WHERE country='us'") != MPORT_OK)
+		RETURN_CURRENT_ERROR;
+
+	*list_size = len;
+	list = calloc((size_t) len + 1, sizeof(char *));
+	*list_p = list;
+	i = 0;
+
+	if (mport_db_prepare(mport->db, &stmt, "SELECT mirror FROM idx.mirrors WHERE country='us'") != MPORT_OK) {
+		sqlite3_finalize(stmt);
+		RETURN_CURRENT_ERROR;
+	}
+
+	while (1) {
+		ret = sqlite3_step(stmt);
+
+		if (ret == SQLITE_ROW) {
+			list[i] = strdup((const char *) sqlite3_column_text(stmt, 0));
+
+			if (list[i] == NULL) {
+				sqlite3_finalize(stmt);
+				RETURN_ERROR(MPORT_ERR_FATAL, "Out of memory.");
+			}
+
+			i++;
+		} else if (ret == SQLITE_DONE) {
+			list[i] = NULL;
+			break;
+		} else {
+			list[i] = NULL;
+			sqlite3_finalize(stmt);
+			RETURN_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
+		}
+	}
+
+	sqlite3_finalize(stmt);
+	return MPORT_OK;
 }
 
 /*
@@ -276,84 +261,65 @@
 MPORT_PUBLIC_API int 
 mport_index_lookup_pkgname(mportInstance *mport, const char *pkgname, mportIndexEntry ***entry_vec)
 {
-  char *lookup = NULL;
-  int count, i = 0, step;
-  sqlite3_stmt *stmt;
-  int ret = MPORT_OK;
-  mportIndexEntry **e;
-  
-  MPORT_CHECK_FOR_INDEX(mport, "mport_index_lookup_pkgname()")
+	char *lookup = NULL;
+	int count;
+	int i = 0, step;
+	sqlite3_stmt *stmt;
+	int ret = MPORT_OK;
+	mportIndexEntry **e;
 
-  if (lookup_alias(mport, pkgname, &lookup) != MPORT_OK)
-    RETURN_CURRENT_ERROR;
+	MPORT_CHECK_FOR_INDEX(mport, "mport_index_lookup_pkgname()")
 
-  if (mport_db_prepare(mport->db, &stmt, "SELECT COUNT(*) FROM idx.packages WHERE pkg GLOB %Q", lookup) != MPORT_OK) {
-	  sqlite3_finalize(stmt);
-	  RETURN_CURRENT_ERROR;
-  }
- 
-  switch (sqlite3_step(stmt)) {
-    case SQLITE_ROW:
-      count = sqlite3_column_int(stmt, 0);
-      break;
-    case SQLITE_DONE:
-      ret = SET_ERROR(MPORT_ERR_FATAL, "No rows returned from a 'SELECT COUNT(*)' query.");
-      goto DONE;
-      break;
-    default:
-      ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
-      goto DONE;
-      break;
-  }
-  
-  sqlite3_finalize(stmt);
-  
-  e = (mportIndexEntry **)calloc(count + 1, sizeof(mportIndexEntry *));
-  *entry_vec = e;
-  
-  if (count == 0) 
-    return MPORT_OK;
-  
-  if (mport_db_prepare(mport->db, &stmt, "SELECT pkg, version, comment, bundlefile, license, hash FROM idx.packages WHERE pkg GLOB %Q", lookup) != MPORT_OK) {
-    ret = mport_err_code();
-    goto DONE;
-  }
-  
-  while (1) {
-    step = sqlite3_step(stmt);
-    
-    if (step == SQLITE_ROW) {
-      if ((e[i] = (mportIndexEntry *)calloc(1, sizeof(mportIndexEntry))) == NULL) {
-        ret = MPORT_ERR_FATAL;
-        goto DONE;
-      }
+	if (lookup_alias(mport, pkgname, &lookup) != MPORT_OK)
+		RETURN_CURRENT_ERROR;
+
+	if (mport_db_count(mport->db, &count,"SELECT count(*) FROM idx.packages  WHERE pkg GLOB %Q", lookup) != MPORT_OK)
+		RETURN_CURRENT_ERROR;
+
+	e = (mportIndexEntry **) calloc((size_t) count + 1, sizeof(mportIndexEntry *));
+	*entry_vec = e;
+
+	if (count == 0)
+		return MPORT_OK;
+
+	if (mport_db_prepare(mport->db, &stmt,
+	                     "SELECT pkg, version, comment, bundlefile, license, hash FROM idx.packages WHERE pkg GLOB %Q",
+	                     lookup) != MPORT_OK) {
+		ret = mport_err_code();
+		goto DONE;
+	}
+
+	while (1) {
+		step = sqlite3_step(stmt);
+
+		if (step == SQLITE_ROW) {
+			if ((e[i] = (mportIndexEntry *) calloc(1, sizeof(mportIndexEntry))) == NULL) {
+				ret = MPORT_ERR_FATAL;
+				goto DONE;
+			}
+
+			populate_row(stmt, e[i]);
+
+			if (e[i]->pkgname == NULL || e[i]->version == NULL || e[i]->comment == NULL || e[i]->license == NULL ||
+			    e[i]->bundlefile == NULL) {
+				ret = MPORT_ERR_FATAL;
+				goto DONE;
+			}
+
+			i++;
+		} else if (step == SQLITE_DONE) {
+			e[i] = NULL;
+			goto DONE;
+		} else {
+			ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
+			goto DONE;
+		}
+	}
       
-      e[i]->pkgname    = strdup(sqlite3_column_text(stmt, 0));
-      e[i]->version    = strdup(sqlite3_column_text(stmt, 1));
-      e[i]->comment    = strdup(sqlite3_column_text(stmt, 2));
-      e[i]->bundlefile = strdup(sqlite3_column_text(stmt, 3));
-      e[i]->license    = strdup(sqlite3_column_text(stmt, 4));
-      e[i]->hash       = strdup(sqlite3_column_text(stmt, 5));
-      
-      if (e[i]->pkgname == NULL || e[i]->version == NULL || e[i]->comment == NULL || e[i]->license == NULL || e[i]->bundlefile == NULL) {
-        ret = MPORT_ERR_FATAL;
-        goto DONE;
-      }
-      
-      i++;
-    } else if (step == SQLITE_DONE) {
-      e[i] = NULL;
-      goto DONE;
-    } else {
-      ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
-      goto DONE;
-    }
-  }
-      
   DONE:
     free(lookup);
-    sqlite3_finalize(stmt);
-    return ret; 
+	sqlite3_finalize(stmt);
+	return ret;
 }
 
 
@@ -373,7 +339,8 @@
 {
   va_list args;
   sqlite3_stmt *stmt;
-  int ret = MPORT_OK, len;
+  int ret = MPORT_OK;
+	int len;
   int i = 0, step;
   char *where;
   sqlite3 *db = mport->db;
@@ -386,21 +353,10 @@
   if (where == NULL)
     RETURN_ERROR(MPORT_ERR_FATAL, "Could not build where clause");
 
+	if (mport_db_count(mport->db, &len,"SELECT count(*) FROM idx.packages  WHERE %s", where) != MPORT_OK)
+		RETURN_CURRENT_ERROR;
 
-  if (mport_db_prepare(db, &stmt, "SELECT count(*) FROM idx.packages WHERE %s", where) != MPORT_OK) {
-    sqlite3_finalize(stmt);
-    RETURN_CURRENT_ERROR;
-  }
-
-  if (sqlite3_step(stmt) != SQLITE_ROW) {
-    sqlite3_finalize(stmt);
-    RETURN_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(db));
-  }
-
-  len = sqlite3_column_int(stmt, 0);
-  sqlite3_finalize(stmt);
-
-  e = (mportIndexEntry **)calloc(len + 1, sizeof(mportIndexEntry *));
+  e = (mportIndexEntry **)calloc((size_t) len + 1, sizeof(mportIndexEntry *));
   *entry_vec = e;
 
   if (len == 0) {
@@ -422,12 +378,7 @@
         break;
       }
 
-      e[i]->pkgname    = strdup(sqlite3_column_text(stmt, 0));
-      e[i]->version    = strdup(sqlite3_column_text(stmt, 1));
-      e[i]->comment    = strdup(sqlite3_column_text(stmt, 2));
-      e[i]->bundlefile = strdup(sqlite3_column_text(stmt, 3));
-      e[i]->license    = strdup(sqlite3_column_text(stmt, 4));
-      e[i]->hash       = strdup(sqlite3_column_text(stmt, 5));
+	    populate_row(stmt, e[i]);
 
       if (e[i]->pkgname == NULL || e[i]->version == NULL || e[i]->comment == NULL || e[i]->license == NULL || e[i]->bundlefile == NULL) {
         ret = MPORT_ERR_FATAL;
@@ -454,101 +405,105 @@
 MPORT_PUBLIC_API int 
 mport_index_list(mportInstance *mport, mportIndexEntry ***entry_vec)
 {
-  sqlite3_stmt *stmt;
-  int ret = MPORT_OK, len;
-  int i = 0, step;
-  sqlite3 *db = mport->db;
-  mportIndexEntry **e;
+	sqlite3_stmt *stmt;
+	int ret = MPORT_OK;
+	int len;
+	int i = 0, step;
+	sqlite3 *db = mport->db;
+	mportIndexEntry **e;
 
-  if (mport_db_prepare(db, &stmt, "SELECT count(*) FROM idx.packages") != MPORT_OK) {
-    sqlite3_finalize(stmt);
-    RETURN_CURRENT_ERROR;
-  }
+	if (mport_db_count(mport->db, &len,"SELECT count(*) FROM idx.packages") != MPORT_OK)
+		RETURN_CURRENT_ERROR;
 
-  if (sqlite3_step(stmt) != SQLITE_ROW) {
-    sqlite3_finalize(stmt);
-    RETURN_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(db));
-  }
+	e = (mportIndexEntry **) calloc((size_t) len + 1, sizeof(mportIndexEntry *));
+	*entry_vec = e;
 
-  len = sqlite3_column_int(stmt, 0);
-  sqlite3_finalize(stmt);
+	if (len == 0) {
+		return MPORT_OK;
+	}
 
-  e = (mportIndexEntry **)calloc(len + 1, sizeof(mportIndexEntry *));
-  *entry_vec = e;
+	if (mport_db_prepare(db, &stmt, "SELECT pkg, version, comment, bundlefile, license, hash FROM idx.packages") !=
+	    MPORT_OK) {
+		sqlite3_finalize(stmt);
+		RETURN_CURRENT_ERROR;
+	}
 
-  if (len == 0) {
-    return MPORT_OK;
-  }
+	while (1) {
+		step = sqlite3_step(stmt);
 
-  if (mport_db_prepare(db, &stmt, "SELECT pkg, version, comment, bundlefile, license, hash FROM idx.packages") != MPORT_OK) {
-    sqlite3_finalize(stmt);
-    RETURN_CURRENT_ERROR;
-  }
+		if (step == SQLITE_ROW) {
+			if ((e[i] = (mportIndexEntry *) calloc(1, sizeof(mportIndexEntry))) == NULL) {
+				ret = MPORT_ERR_FATAL;
+				break;
+			}
 
-  while (1) {
-    step = sqlite3_step(stmt);
+			populate_row(stmt, e[i]);
 
-    if (step == SQLITE_ROW) {
-      if ((e[i] = (mportIndexEntry *)calloc(1, sizeof(mportIndexEntry))) == NULL) {
-        ret = MPORT_ERR_FATAL;
-        break;
-      }
+			if (e[i]->pkgname == NULL || e[i]->version == NULL || e[i]->comment == NULL || e[i]->license == NULL ||
+			    e[i]->bundlefile == NULL) {
+				ret = MPORT_ERR_FATAL;
+				break;
+			}
 
-      e[i]->pkgname    = strdup((const char *) sqlite3_column_text(stmt, 0));
-      e[i]->version    = strdup((const char *) sqlite3_column_text(stmt, 1));
-      e[i]->comment    = strdup((const char *) sqlite3_column_text(stmt, 2));
-      e[i]->bundlefile = strdup((const char *) sqlite3_column_text(stmt, 3));
-      e[i]->license    = strdup((const char *) sqlite3_column_text(stmt, 4));
-      e[i]->hash       = strdup((const char *) sqlite3_column_text(stmt, 5));
+			i++;
+		} else if (step == SQLITE_DONE) {
+			e[i] = NULL;
+			break;
+		} else {
+			ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
+			break;
+		}
+	}
 
-      if (e[i]->pkgname == NULL || e[i]->version == NULL || e[i]->comment == NULL || e[i]->license == NULL || e[i]->bundlefile == NULL) {
-        ret = MPORT_ERR_FATAL;
-        break;
-      }
+	sqlite3_finalize(stmt);
 
-      i++;
-    } else if (step == SQLITE_DONE) {
-      e[i] = NULL;
-      break;
-    } else {
-      ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
-      break;
-    }
-  }
+	return ret;
+}
 
-  sqlite3_finalize(stmt);
+static void
+populate_row(sqlite3_stmt *stmt, mportIndexEntry *e) {
 
-  return ret;
+		e->pkgname = strdup((const char *) sqlite3_column_text(stmt, 0));
+		e->version = strdup((const char *) sqlite3_column_text(stmt, 1));
+		e->comment = strdup((const char *) sqlite3_column_text(stmt, 2));
+		e->bundlefile = strdup((const char *) sqlite3_column_text(stmt, 3));
+		e->license = strdup((const char *) sqlite3_column_text(stmt, 4));
+		e->hash = strdup((const char *) sqlite3_column_text(stmt, 5));
 }
 
 
-static int lookup_alias(mportInstance *mport, const char *query, char **result)
+static int
+lookup_alias(mportInstance *mport, const char *query, char **result)
 {
 	sqlite3_stmt *stmt;
-	int ret = MPORT_OK;
+	__block int ret = MPORT_OK;
 
 	if (mport_db_prepare(mport->db, &stmt, "SELECT pkg FROM idx.aliases WHERE alias=%Q", query) != MPORT_OK)
 		RETURN_CURRENT_ERROR;
 
-	switch (sqlite3_step(stmt)) {
-		case SQLITE_ROW:
-			*result = strdup((const char *) sqlite3_column_text(stmt, 0));
-			break;
-		case SQLITE_DONE:
-			*result = strdup(query);
-			break;
-		default:
-			ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
-			break;
-	}
+	dispatch_sync(mportSQLSerial, ^{
+		switch (sqlite3_step(stmt)) {
+			case SQLITE_ROW:
+				*result = strdup((const char *) sqlite3_column_text(stmt, 0));
+				break;
+			case SQLITE_DONE:
+				*result = strdup(query);
+				break;
+			default:
+				ret = SET_ERROR(MPORT_ERR_FATAL, sqlite3_errmsg(mport->db));
+				break;
+		}
 
-	sqlite3_finalize(stmt);
+		sqlite3_finalize(stmt);
+	});
+
 	return ret;
 }
 
 
 /* free a vector of mportIndexEntry structs */
-MPORT_PUBLIC_API void mport_index_entry_free_vec(mportIndexEntry **e)
+MPORT_PUBLIC_API void
+mport_index_entry_free_vec(mportIndexEntry **e)
 {
 
 	if (e == NULL)
@@ -562,7 +517,8 @@
 
 
 /* free a mportIndexEntry struct */
-MPORT_PUBLIC_API void mport_index_entry_free(mportIndexEntry *e)
+MPORT_PUBLIC_API void
+mport_index_entry_free(mportIndexEntry *e)
 {
 
 	if (e == NULL)

Modified: trunk/lib/libmport/mport_private.h
===================================================================
--- trunk/lib/libmport/mport_private.h	2016-08-27 14:28:28 UTC (rev 7766)
+++ trunk/lib/libmport/mport_private.h	2016-08-27 20:28:24 UTC (rev 7767)
@@ -73,6 +73,7 @@
 int mport_detach_stub_db(sqlite3 *);
 int mport_db_do(sqlite3 *, const char *, ...);
 int mport_db_prepare(sqlite3 *, sqlite3_stmt **, const char *, ...);
+int mport_db_count(sqlite3 *, int *, const char *, ...);
 
 /* pkgmeta */
 int mport_pkgmeta_read_stub(mportInstance *, mportPackageMeta ***);



More information about the Midnightbsd-cvs mailing list