From a0c2c6ed83a166d35ad3d3e8b22a08aae5420731 Mon Sep 17 00:00:00 2001 From: Panu Matilainen Date: Fri, 19 Mar 2010 17:56:53 +0200 Subject: [PATCH] Rip RPMDBI_PACKAGES iteration support out of rpmgi - lift the tag-filtering part into query code, that's at least somewhat useful - rpmgi is now just a glorified path argument iterator --- lib/query.c | 50 ++++++++++++++++++++++++++++-- lib/rpmgi.c | 101 ++---------------------------------------------------------- 2 files changed, 51 insertions(+), 100 deletions(-) diff --git a/lib/query.c b/lib/query.c index 91a5ac5..d3f92b2 100644 --- a/lib/query.c +++ b/lib/query.c @@ -314,10 +314,13 @@ int rpmQueryVerify(QVA_t qva, rpmts ts, const char * arg) switch (qva->qva_source) { case RPMQV_RPM: - case RPMQV_ALL: res = rpmgiShowMatches(qva, ts); break; + case RPMQV_ALL: + res = rpmcliShowMatches(qva, ts); + break; + case RPMQV_SPECFILE: res = ((qva->qva_specQuery != NULL) ? qva->qva_specQuery(ts, qva, arg) : 1); @@ -541,13 +544,56 @@ static int rpmcliArgIterHelper(rpmts ts, QVA_t qva, rpmTag tag, ARGV_const_t arg return ec; } +/* + * Apply extra query filters. By default patterns applied to package + * name, others can be specified with = + */ +static rpmRC applyFilters(rpmdbMatchIterator mi, ARGV_const_t argv) +{ + rpmRC rc = RPMRC_OK; + + for (ARGV_const_t arg = argv; arg && *arg != NULL; arg++) { + rpmTag tag = RPMTAG_NAME; + char a[strlen(*arg)+1], *ae; + const char *pat = a; + + strcpy(a, *arg); + + /* Parse for "tag=pattern" args. */ + if ((ae = strchr(a, '=')) != NULL) { + *ae++ = '\0'; + tag = rpmTagGetValue(a); + if (tag == RPMTAG_NOT_FOUND) { + rpmlog(RPMLOG_ERR, _("unknown tag: \"%s\"\n"), a); + rc = RPMRC_FAIL; + break; + } + pat = ae; + } + + rpmdbSetIteratorRE(mi, tag, RPMMIRE_DEFAULT, pat); + } + + return rc; +} + int rpmcliArgIter(rpmts ts, QVA_t qva, ARGV_const_t argv) { int ec = 0; + /* + * This is all wonderfully inconsistent... sort it out once + * rpmgi is out of the picture. + */ switch (qva->qva_source) { case RPMQV_ALL: - ec = rpmcliArgIterHelper(ts, qva, RPMDBI_PACKAGES, argv, RPMGI_NONE); + qva->qva_mi = rpmtsInitIterator(ts, RPMDBI_PACKAGES, NULL, 0); + if (applyFilters(qva->qva_mi, argv) != RPMRC_OK) { + ec = 1; + qva->qva_mi = rpmdbFreeIterator(qva->qva_mi); + } else { + ec += rpmQueryVerify(qva, ts, NULL); + } break; case RPMQV_RPM: ec = rpmcliArgIterHelper(ts, qva, RPMDBI_ARGLIST, argv, giFlags); diff --git a/lib/rpmgi.c b/lib/rpmgi.c index 12ddb43..d015de2 100644 --- a/lib/rpmgi.c +++ b/lib/rpmgi.c @@ -27,9 +27,6 @@ rpmgiFlags giFlags = RPMGI_NONE; */ struct rpmgi_s { rpmts ts; /*!< Iterator transaction set. */ - rpmTag tag; /*!< Iterator type. */ - const void * keyp; /*!< Iterator key. */ - size_t keylen; /*!< Iterator key length. */ rpmgiFlags flags; /*!< Iterator control bits. */ int active; /*!< Iterator is active? */ @@ -37,8 +34,6 @@ struct rpmgi_s { int errors; Header h; /*!< Current iterator header. */ - rpmdbMatchIterator mi; - ARGV_t argv; int argc; }; @@ -176,8 +171,8 @@ static rpmRC rpmgiGlobArgv(rpmgi gi, ARGV_const_t argv) int ac = 0; int xx; - /* XXX Expand globs only if requested or for gi specific tags */ - if ((gi->flags & RPMGI_NOGLOB) || !(gi->tag == RPMDBI_ARGLIST)) { + /* XXX Expand globs only if requested */ + if ((gi->flags & RPMGI_NOGLOB)) { if (argv != NULL) { while (argv[ac] != NULL) ac++; @@ -203,59 +198,6 @@ static rpmRC rpmgiGlobArgv(rpmgi gi, ARGV_const_t argv) return rpmrc; } -/** - * Return rpmdb match iterator with filters (if any) set. - * @param gi generalized iterator - * @returns RPMRC_OK on success - */ -static rpmRC rpmgiInitFilter(rpmgi gi) -{ - rpmRC rpmrc = RPMRC_OK; - ARGV_t av; - int res = 0; - - gi->mi = rpmtsInitIterator(gi->ts, gi->tag, gi->keyp, gi->keylen); - -if (_rpmgi_debug < 0) -fprintf(stderr, "*** gi %p\tmi %p\n", gi, gi->mi); - - if (gi->argv != NULL) - for (av = gi->argv; *av != NULL; av++) { - rpmTag tag = RPMTAG_NAME; - const char * pat; - char * a, * ae; - - pat = a = xstrdup(*av); - tag = RPMTAG_NAME; - - /* Parse for "tag=pattern" args. */ - if ((ae = strchr(a, '=')) != NULL) { - *ae++ = '\0'; - tag = rpmTagGetValue(a); - if (tag == RPMTAG_NOT_FOUND) { - rpmlog(RPMLOG_ERR, _("unknown tag: \"%s\"\n"), a); - res = 1; - } - pat = ae; - } - - if (!res) { -if (_rpmgi_debug < 0) -fprintf(stderr, "\tav %p[%ld]: \"%s\" -> %s ~= \"%s\"\n", gi->argv, (long) (av - gi->argv), *av, rpmTagGetName(tag), pat); - res = rpmdbSetIteratorRE(gi->mi, tag, RPMMIRE_DEFAULT, pat); - } - a = _free(a); - - if (res == 0) - continue; - - rpmrc = RPMRC_FAIL; - break; - } - - return rpmrc; -} - rpmgi rpmgiFree(rpmgi gi) { if (gi == NULL) @@ -265,9 +207,6 @@ rpmgi rpmgiFree(rpmgi gi) gi->argv = argvFree(gi->argv); - gi->mi = rpmdbFreeIterator(gi->mi); - gi->ts = rpmtsFree(gi->ts); - memset(gi, 0, sizeof(*gi)); /* XXX trash and burn */ gi = _free(gi); return NULL; @@ -281,9 +220,6 @@ rpmgi rpmgiNew(rpmts ts, rpmTag tag, const void * keyp, size_t keylen) return NULL; gi->ts = rpmtsLink(ts, __FUNCTION__); - gi->tag = tag; - gi->keyp = keyp; - gi->keylen = keylen; gi->flags = 0; gi->active = 0; @@ -291,7 +227,6 @@ rpmgi rpmgiNew(rpmts ts, rpmTag tag, const void * keyp, size_t keylen) gi->errors = 0; gi->h = NULL; - gi->mi = NULL; gi->argv = argvNew(); gi->argc = 0; @@ -308,34 +243,7 @@ rpmRC rpmgiNext(rpmgi gi) /* Free header from previous iteration. */ gi->h = headerFree(gi->h); - if (++gi->i >= 0) - switch (gi->tag) { - default: - case RPMDBI_PACKAGES: - if (!gi->active) { - rpmrc = rpmgiInitFilter(gi); - if (rpmrc != RPMRC_OK) - goto enditer; - gi->active = 1; - } - if (gi->mi != NULL) { /* XXX unnecessary */ - Header h = rpmdbNextIterator(gi->mi); - if (h != NULL) { - gi->h = headerLink(h); - rpmrc = RPMRC_OK; - /* XXX header reference held by iterator, so no headerFree */ - } else - rpmrc = RPMRC_NOTFOUND; - } - if (rpmrc != RPMRC_OK) { - goto enditer; - } - break; - case RPMDBI_ARGLIST: - /* XXX gi->active initialize? */ -if (_rpmgi_debug < 0) -fprintf(stderr, "*** gi %p\t%p[%d]: %s\n", gi, gi->argv, gi->i, gi->argv[gi->i]); - + if (++gi->i >= 0) { /* * Read next header, lazily expanding manifests as found, * count + skip errors. @@ -350,14 +258,11 @@ fprintf(stderr, "*** gi %p\t%p[%d]: %s\n", gi, gi->argv, gi->i, gi->argv[gi->i]) if (rpmrc != RPMRC_OK) /* XXX check this */ goto enditer; - - break; } return rpmrc; enditer: - gi->mi = rpmdbFreeIterator(gi->mi); gi->h = headerFree(gi->h); gi->i = -1; gi->active = 0; -- 2.7.4