Radish alpha
H
rad:z3QDZAW2FAfuLvihrhiyDC9fAD8G9
HardenedBSD Package Manager
Radicle
Git
switch pkg delete to new world order
Baptiste Daroussin committed 13 years ago
commit 5532933443f094ecc61e57ffa6a1ad0fcf7d31d7
parent d5a93ca
3 files changed +88 -101
modified libpkg/pkg_jobs.c
@@ -43,7 +43,7 @@
#include "private/pkgdb.h"

static int get_remote_pkg(struct pkg_jobs *j, const char *pattern, match_t m, bool root);
-
static struct pkg * get_local_pkg(struct pkg_jobs *j, const char *origin);
+
static struct pkg *get_local_pkg(struct pkg_jobs *j, const char *origin, unsigned flag);
static int pkg_jobs_fetch(struct pkg_jobs *j);
static bool newer_than_local_pkg(struct pkg_jobs *j, struct pkg *rp, bool force);
static bool new_pkg_version(struct pkg_jobs *j);
@@ -122,6 +122,71 @@ pkg_jobs_add(struct pkg_jobs *j, match_t match, char **argv, int argc)
}

static int
+
populate_local_rdeps(struct pkg_jobs *j, struct pkg *p)
+
{
+
	struct pkg *pkg;
+
	struct pkg_dep *d = NULL;
+
	char *origin;
+

+
	while (pkg_rdeps(p, &d) == EPKG_OK) {
+
		HASH_FIND_STR(j->bulk, __DECONST(char *, pkg_dep_get(d, PKG_DEP_ORIGIN)), pkg);
+
		if (pkg != NULL)
+
			continue;
+
		HASH_FIND_STR(j->seen, __DECONST(char *, pkg_dep_get(d, PKG_DEP_ORIGIN)), pkg);
+
		if (pkg != NULL)
+
			continue;
+
		if ((pkg = get_local_pkg(j, pkg_dep_get(d, PKG_DEP_ORIGIN), PKG_LOAD_BASIC|PKG_LOAD_RDEPS)) == NULL) {
+
			pkg_emit_error("Missing reverse dependency matching '%s'", pkg_dep_get(d, PKG_DEP_ORIGIN));
+
			return (EPKG_FATAL);
+
		}
+
		pkg_get(pkg, PKG_ORIGIN, &origin);
+
		HASH_ADD_KEYPTR(hh, j->bulk, origin, strlen(origin), pkg);
+
		populate_local_rdeps(j, pkg);
+
	}
+

+
	return (EPKG_OK);
+
}
+

+
static void
+
remove_from_rdeps(struct pkg_jobs *j, const char *origin)
+
{
+
	struct pkg *pkg, *tmp;
+
	struct pkg_dep *d;
+

+
	HASH_ITER(hh, j->bulk, pkg, tmp) {
+
		HASH_FIND_STR(pkg->rdeps, __DECONST(char *, origin), d);
+
		if (d != NULL) {
+
			HASH_DEL(pkg->rdeps, d);
+
			pkg_dep_free(d);
+
		}
+
	}
+
}
+

+
static int
+
reverse_order_pool(struct pkg_jobs *j)
+
{
+
	struct pkg *pkg, *tmp;
+
	char *origin;
+
	unsigned int nb;
+

+
	nb = HASH_COUNT(j->bulk);
+
	HASH_ITER(hh, j->bulk, pkg, tmp) {
+
		pkg_get(pkg, PKG_ORIGIN, &origin);
+
		if (HASH_COUNT(pkg->rdeps) == 0) {
+
			HASH_DEL(j->bulk, pkg);
+
			HASH_ADD_KEYPTR(hh, j->jobs, origin, strlen(origin), pkg);
+
			remove_from_rdeps(j, origin);
+
		}
+
	}
+

+
	if (nb == HASH_COUNT(j->bulk)) {
+
		pkg_emit_error("Eror while ordering the jobs probably a circular dependency");
+
		return (EPKG_FATAL);
+
	}
+

+
	return (EPKG_OK);
+
}
+
static int
jobs_solve_deinstall(struct pkg_jobs *j)
{
	struct job_pattern *jp = NULL;
@@ -134,17 +199,26 @@ jobs_solve_deinstall(struct pkg_jobs *j)
		recursive = true;

	LL_FOREACH(j->patterns, jp) {
-
		if ((it = pkgdb_query_delete(j->db, jp->match, jp->nb,
-
		    jp->pattern, recursive)) == NULL)
+
		if ((it = pkgdb_query(j->db, jp->pattern[0], jp->match)) == NULL)
			return (EPKG_FATAL);

-
		while (pkgdb_it_next(it, &pkg, PKG_LOAD_BASIC) == EPKG_OK) {
+
		while (pkgdb_it_next(it, &pkg, PKG_LOAD_BASIC|PKG_LOAD_RDEPS) == EPKG_OK) {
			pkg_get(pkg, PKG_ORIGIN, &origin);
-
			HASH_ADD_KEYPTR(hh, j->jobs, origin, strlen(origin), pkg);
+
			HASH_ADD_KEYPTR(hh, j->bulk, origin, strlen(origin), pkg);
+
			if (recursive)
+
				populate_local_rdeps(j, pkg);
			pkg = NULL;
		}
		pkgdb_it_free(it);
	}
+

+
	HASH_FREE(j->seen, pkg, pkg_free);
+

+
	while (HASH_COUNT(j->bulk) > 0) {
+
		if (reverse_order_pool(j) != EPKG_OK)
+
			return (EPKG_FATAL);
+
	}
+

	j->solved = true;

	return( EPKG_OK);
@@ -335,11 +409,11 @@ new_pkg_version(struct pkg_jobs *j)
	const char *origin = "ports-mgmt/pkg";

	/* determine local pkgng */
-
	p = get_local_pkg(j, origin);
+
	p = get_local_pkg(j, origin, PKG_LOAD_BASIC);

	if (p == NULL) {
		origin = "ports-mgmt/pkg-devel";
-
		p = get_local_pkg(j, origin);
+
		p = get_local_pkg(j, origin, PKG_LOAD_BASIC);
	}

	/* you are using git version skip */
@@ -429,15 +503,19 @@ get_remote_pkg(struct pkg_jobs *j, const char *pattern, match_t m, bool root)
}

static struct pkg *
-
get_local_pkg(struct pkg_jobs *j, const char *origin)
+
get_local_pkg(struct pkg_jobs *j, const char *origin, unsigned flag)
{
	struct pkg *pkg = NULL;
	struct pkgdb_it *it;

+
	if (flag == 0) {
+
		flag = PKG_LOAD_BASIC|PKG_LOAD_DEPS|PKG_LOAD_OPTIONS|PKG_LOAD_SHLIBS_REQUIRED;
+
	}
+

	if ((it = pkgdb_query(j->db, origin, MATCH_EXACT)) == NULL)
		return (NULL);

-
	if (pkgdb_it_next(it, &pkg, PKG_LOAD_BASIC|PKG_LOAD_DEPS|PKG_LOAD_OPTIONS|PKG_LOAD_SHLIBS_REQUIRED) != EPKG_OK)
+
	if (pkgdb_it_next(it, &pkg, flag) != EPKG_OK)
		pkg = NULL;

	pkgdb_it_free(it);
@@ -457,7 +535,7 @@ newer_than_local_pkg(struct pkg_jobs *j, struct pkg *rp, bool force)
	int cmp = 0, ret1, ret2;

	pkg_get(rp, PKG_ORIGIN, &origin);
-
	lp = get_local_pkg(j, origin);
+
	lp = get_local_pkg(j, origin, 0);

	/* obviously yes because local doesn't exists */
	if (lp == NULL) {
modified libpkg/pkgdb.c
@@ -3269,96 +3269,6 @@ pkgdb_compact(struct pkgdb *db)
}

struct pkgdb_it *
-
pkgdb_query_delete(struct pkgdb *db, match_t match, int nbpkgs, char **pkgs,
-
		   int recursive)
-
{
-
	sqlite3_stmt	*stmt = NULL;
-

-
	struct sbuf	*sql = sbuf_new_auto();
-
	const char	*how = NULL;
-
	int		 i = 0, ret;
-

-
	assert(db != NULL);
-

-
	const char	 sqlsel[] = ""
-
		"SELECT id, p.origin, name, version, comment, desc, "
-
		"message, arch, maintainer, www, prefix, locked,"
-
		"flatsize, (SELECT COUNT(*) FROM deps AS d "
-
		"WHERE d.origin = del.origin) AS weight "
-
		"FROM packages AS p, delete_job AS del WHERE id = pkgid "
-
		"ORDER BY weight ASC;";
-

-
	sbuf_cat(sql, "INSERT OR IGNORE INTO delete_job (origin, pkgid) "
-
			"SELECT p.origin, p.id FROM packages AS p ");
-

-
	how = pkgdb_get_match_how(match);
-

-
	sql_exec(db->sqlite, "DROP TABLE IF EXISTS delete_job; "
-
			"CREATE TEMPORARY TABLE IF NOT EXISTS delete_job ("
-
			"origin TEXT UNIQUE NOT NULL, pkgid INTEGER);"
-
			);
-

-
	if (how != NULL) {
-
		sbuf_cat(sql, " WHERE ");
-
		sbuf_printf(sql, how, "p.name");
-
		sbuf_cat(sql, " OR ");
-
		sbuf_printf(sql, how, "p.origin");
-
		sbuf_cat(sql, " OR ");
-
		sbuf_printf(sql, how, "p.name || \"-\" || p.version");
-
		sbuf_finish(sql);
-

-
		for (i = 0; i < nbpkgs; i++) {
-
			ret = sqlite3_prepare_v2(db->sqlite, sbuf_get(sql), -1,
-
			    &stmt, NULL);
-
			if (ret != SQLITE_OK) {
-
				ERROR_SQLITE(db->sqlite);
-
				sbuf_delete(sql);
-
				return (NULL);
-
			}
-
			sqlite3_bind_text(stmt, 1, pkgs[i], -1, SQLITE_STATIC);
-
			while (sqlite3_step(stmt) != SQLITE_DONE);
-
		}
-
	} else {
-
		sbuf_finish(sql);
-
		ret = sqlite3_prepare_v2(db->sqlite, sbuf_get(sql), -1,
-
		    &stmt, NULL);
-
		if (ret != SQLITE_OK) {
-
			ERROR_SQLITE(db->sqlite);
-
			sbuf_delete(sql);
-
			return (NULL);
-
		}
-
		sqlite3_bind_text(stmt, 1, pkgs[i], -1, SQLITE_STATIC);
-
		while (sqlite3_step(stmt) != SQLITE_DONE);
-
	}
-

-
	sqlite3_finalize(stmt);
-

-
	if (recursive) {
-
		do {
-
			sql_exec(db->sqlite, ""
-
			    "INSERT OR IGNORE INTO delete_job(origin, pkgid) "
-
			     "SELECT p.origin, p.id "
-
			     "FROM deps AS d, packages AS p, "
-
				 "delete_job AS del "
-
			     "WHERE d.origin = del.origin "
-
				 "AND p.id = d.package_id");
-
		} while (sqlite3_changes(db->sqlite) != 0);
-
	}
-

-
	if (sqlite3_prepare_v2(db->sqlite, sqlsel, -1, &stmt, NULL)
-
	    != SQLITE_OK) {
-
		ERROR_SQLITE(db->sqlite);
-
		sbuf_delete(sql);
-
		return (NULL);
-
	}
-

-
	sbuf_finish(sql);
-
	sbuf_delete(sql);
-

-
	return (pkgdb_it_new(db, stmt, PKG_INSTALLED, PKGDB_IT_FLAG_ONCE));
-
}
-

-
struct pkgdb_it *
pkgdb_rquery(struct pkgdb *db, const char *pattern, match_t match,
    const char *repo)
{
modified libpkg/private/pkgdb.h
@@ -65,7 +65,6 @@ int pkgdb_transaction_rollback(sqlite3 *sqlite, const char *savepoint);

struct pkgdb_it *pkgdb_it_new(struct pkgdb *db, sqlite3_stmt *s, int type, short flags);

-
struct pkgdb_it *pkgdb_query_delete(struct pkgdb *db, match_t type, int nbpkgs, char **pkgs, int recursive);
struct pkgdb_it *pkgdb_query_fetch(struct pkgdb *db, match_t type, int nbpkgs, char **pkgs, const char *reponame, unsigned flags);

int pkgdb_obtain_lock(struct pkgdb *db);