Date: Sun, 28 Jul 2013 16:31:22 GMT From: mattbw@FreeBSD.org To: svn-soc-all@FreeBSD.org Subject: socsvn commit: r255265 - in soc2013/mattbw/backend: . query Message-ID: <201307281631.r6SGVMAT041129@socsvn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: mattbw Date: Sun Jul 28 16:31:22 2013 New Revision: 255265 URL: http://svnweb.FreeBSD.org/socsvn/?view=rev&rev=255265 Log: (*still untested*) Move ID-to-pkg match to pkgutils, implement job check. The checking of packages to see if they match PackageIDs is now in pkgutils.c as 'pkgutils_pkg_match_id'; the query system now uses this instead of doing its own check. Some very rough code in 'jobs.c' has been laid down for checking to see if packages added to a job match their PackageIDs. This needs to be checked for errors and also expanded so that other checks (for example, update status) can be added without significant overhead. Modified: soc2013/mattbw/backend/jobs.c soc2013/mattbw/backend/jobs.h soc2013/mattbw/backend/pkgutils.c soc2013/mattbw/backend/pkgutils.h soc2013/mattbw/backend/query/core.c Modified: soc2013/mattbw/backend/jobs.c ============================================================================== --- soc2013/mattbw/backend/jobs.c Sun Jul 28 13:56:59 2013 (r255264) +++ soc2013/mattbw/backend/jobs.c Sun Jul 28 16:31:22 2013 (r255265) @@ -23,6 +23,7 @@ #include <assert.h> /* assert */ #include <glib.h> /* gchar, g_... */ #include <stdbool.h> /* bool, true, false */ +#include <string.h> /* strcmp */ #include "pk-backend.h" /* pk_..., Pk... */ #include "pkg.h" /* pkg_... */ @@ -55,6 +56,85 @@ return success; } +/* Checks a solved job against a string vector of PackageIDs to ensure any + * packages that match the PackageIDs match them fully. + */ +bool +jobs_check_package_ids(struct pkg_jobs *jobs, gchar **package_ids) +{ + bool success; + guint count; + guint i; + const char *name; + const char *version; + gchar *match_id; + struct pkg *pkg; + gchar ***id_splits; + + assert(jobs != NULL); + assert(package_ids != NULL); + + success = false; + pkg = NULL; + id_splits = NULL; + match_id = NULL; + + count = g_strv_length(package_ids); + if (count == 0) + goto cleanup; + + /* Split all the IDs first so we don't have to do it multiple times */ + id_splits = calloc(count, sizeof(gchar **)); + if (id_splits == NULL) + goto cleanup; + + for (i = 0; i < count; i++) { + id_splits[i] = pk_package_id_split(package_ids[i]); + if (id_splits[i] == NULL) + break; + } + + if (i < count) + goto cleanup; + + /* Now do the actual checking, per package. */ + success = true; + while (success && pkg_jobs(jobs, &pkg) == EPKG_OK) { + assert(pkg != NULL); + + name = version = NULL; + pkg_get(pkg, PKG_NAME, &name, PKG_VERSION, &version); + + /* Does this package's name and version match a PackageID? */ + for (i = 0; i < count; i++) { + if ((strcmp(name, + id_splits[i][PK_PACKAGE_ID_NAME]) == 0) && + (strcmp(version, + id_splits[i][PK_PACKAGE_ID_VERSION]) == 0)) { + /* Does the rest of the PackageID match up? */ + match_id = pkgutils_pkg_match_id(pkg, + id_splits[i]); + + if (match_id == NULL) + success = false; + else + free(match_id); + } + } + } + +cleanup: + if (id_splits != NULL) { + for (i = 0; i < count; i++) + g_strfreev(id_splits[i]); + free(id_splits); + } + + /*pkg_free(pkg);*/ + + return success; +} + /* Adds each PackageID into an already created job. Returns NULL on failure * and a vector of added package name-versions to be freed after solution * on success. Modified: soc2013/mattbw/backend/jobs.h ============================================================================== --- soc2013/mattbw/backend/jobs.h Sun Jul 28 13:56:59 2013 (r255264) +++ soc2013/mattbw/backend/jobs.h Sun Jul 28 16:31:22 2013 (r255265) @@ -27,6 +27,7 @@ typedef PkInfoEnum (*pkg_info_ptr) (struct pkg *pkg); bool jobs_apply(struct pkg_jobs *jobs, PkBackend *backend, PkErrorEnum no_jobs, PkErrorEnum job_failed); +bool jobs_check_package_ids(struct pkg_jobs *jobs, gchar **package_ids); char **jobs_add_package_ids(struct pkg_jobs *jobs, gchar **package_ids); void jobs_emit_packages(struct pkg_jobs *jobs, PkBackend *backend, pkg_info_ptr info); Modified: soc2013/mattbw/backend/pkgutils.c ============================================================================== --- soc2013/mattbw/backend/pkgutils.c Sun Jul 28 13:56:59 2013 (r255264) +++ soc2013/mattbw/backend/pkgutils.c Sun Jul 28 16:31:22 2013 (r255265) @@ -173,6 +173,61 @@ } /* + * Compares a package to a split PackageID; returns the package's canonical + * PackageID if they match and NULL otherwise. + */ +gchar * +pkgutils_pkg_match_id(struct pkg *pkg, gchar **split_id) +{ + bool success; + int i; + gchar *match_id; + const char **pkg_id_bits; + + assert(pkg != NULL); + assert(split_id != NULL); + assert(g_strv_length(split_id) == 4); + + success = false; + match_id = NULL; + + pkg_id_bits = calloc(4, sizeof(const char *)); + if (pkg_id_bits == NULL) + goto cleanup; + + match_id = pkgutils_pkg_to_id_through(pkg, pkg_id_bits); + if (match_id == NULL) + goto cleanup; + + /* + * Succeed if this package's PackageID fields match the + * original PackageID. Of course, the original ID might have + * missing fields (NULLs), so we treat a comparison involving + * one as a success. This means using our "weak strcmp" + * instead of normal strcmp or even g_strcmp0. + */ + for (success = true, i = PK_PACKAGE_ID_NAME; + success && i <= PK_PACKAGE_ID_DATA; + i++) + success = string_match(split_id[i], pkg_id_bits[i]); + +cleanup: + if (!success) { + if (match_id != NULL) { + g_free(match_id); + match_id = NULL; + } + } + assert (success || match_id == NULL); + assert (!success || match_id != NULL); + + /* The strings inside this are owned by 'pkg'. Don't free them */ + free(pkg_id_bits); + + return match_id; +} + +/* * Converts a package to a PackageID. */ gchar * Modified: soc2013/mattbw/backend/pkgutils.h ============================================================================== --- soc2013/mattbw/backend/pkgutils.h Sun Jul 28 13:56:59 2013 (r255264) +++ soc2013/mattbw/backend/pkgutils.h Sun Jul 28 16:31:22 2013 (r255265) @@ -24,13 +24,14 @@ #include <glib.h> #include "pk-backend.h" #include "pkg.h" - + PkInfoEnum pkgutils_pkg_current_state(struct pkg *pkg); PkInfoEnum pkgutils_pkg_install_state(struct pkg *pkg); PkInfoEnum pkgutils_pkg_remove_state(struct pkg *pkg); char *pkgutils_package_id_namever(gchar *package_id); char *pkgutils_pkg_namever(struct pkg *pkg); const char *pkgutils_pk_repo_of(struct pkg *pkg); +gchar *pkgutils_pkg_match_id(struct pkg *pkg, gchar **split_id); gchar *pkgutils_pkg_to_id(struct pkg *pkg); gchar *pkgutils_pkg_to_id_through(struct pkg *pkg, const gchar **strv); void pkgutils_add_old_version(struct pkgdb *db, struct pkg *pkg, struct pkg **old_p); Modified: soc2013/mattbw/backend/query/core.c ============================================================================== --- soc2013/mattbw/backend/query/core.c Sun Jul 28 13:56:59 2013 (r255264) +++ soc2013/mattbw/backend/query/core.c Sun Jul 28 16:31:22 2013 (r255265) @@ -346,42 +346,19 @@ static gchar * match_pkg(struct pkg *pkg, struct query *q) { - bool matches; - int i; gchar *match_id; - const char **pkg_id_bits; assert(pkg != NULL); assert(q != NULL); - pkg_id_bits = calloc(4, sizeof(const char *)); - match_id = pkgutils_pkg_to_id_through(pkg, pkg_id_bits); /* No need to do a PackageID match if we're looking for a name. */ if (q->s->type == QUERY_SINGLE_NAME) - matches = true; - else { - /* - * Succeed if this package's PackageID fields match the - * original PackageID. Of course, the original ID might have - * missing fields (NULLs), so we treat a comparison involving - * one as a success. This means using our "weak strcmp" - * instead of normal strcmp or even g_strcmp0. - */ - for (matches = true, i = PK_PACKAGE_ID_NAME; - matches && i <= PK_PACKAGE_ID_DATA; - i++) - matches = string_match((q->id_strv)[i], - pkg_id_bits[i]); - } + match_id = pkgutils_pkg_to_id(pkg); + else + match_id = pkgutils_pkg_match_id(pkg, q->id_strv); - free(pkg_id_bits); - - if (matches == false) { - g_free(match_id); - match_id = NULL; - } return match_id; }
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201307281631.r6SGVMAT041129>