This is an automated email from the git hooks/post-receive script. guillem pushed a commit to branch master in repository dpkg.
commit 2a6d9275c0bdd44f306adf816cfcec95204d0e54 Author: Guillem Jover <[email protected]> Date: Sun Feb 15 23:58:34 2015 +0100 libdpkg: Simplify namevalue parsing code This removes the special fallback value from the name/value table, so that we cannot accidentally parse it as a valid value. --- dselect/pkgdisplay.cc | 1 - lib/dpkg/fields.c | 87 ++++++++++++++++++++++++++++++------------------ lib/dpkg/namevalue.c | 8 ++--- lib/dpkg/namevalue.h | 2 -- lib/dpkg/pkg-namevalue.c | 1 - 5 files changed, 56 insertions(+), 43 deletions(-) diff --git a/dselect/pkgdisplay.cc b/dselect/pkgdisplay.cc index 7b9b017..e264a9e 100644 --- a/dselect/pkgdisplay.cc +++ b/dselect/pkgdisplay.cc @@ -63,7 +63,6 @@ const char N_("Standard"), N_("Optional"), N_("Extra"), - N_("!Bug!"), N_("Unclassified"), nullptr }, diff --git a/lib/dpkg/fields.c b/lib/dpkg/fields.c index abbf23e..831b53d 100644 --- a/lib/dpkg/fields.c +++ b/lib/dpkg/fields.c @@ -40,45 +40,57 @@ #include <dpkg/pkg-spec.h> #include <dpkg/triglib.h> +/** + * Flags to parse a name associated to a value. + */ +enum parse_nv_flags { + /** Expect no more words (default). */ + PARSE_NV_LAST = 0, + /** Expect another word after the parsed name. */ + PARSE_NV_NEXT = DPKG_BIT(0), + /** Do not fail if there is no name with an associated value found. */ + PARSE_NV_FALLBACK = DPKG_BIT(1), +}; + +/** + * Parses a name and returns its associated value. + * + * Gets a pointer to the string to parse in @a strp, and modifies the pointer + * to the string to point to the end of the parsed text. If no value is found + * for the name and #PARSE_NV_FALLBACK is set in @a flags then @a strp is set + * to NULL and returns -1, otherwise a parse error is emitted. + */ static int -parse_nv_next(struct parsedb_state *ps, - const char *what, const struct namevalue *nv_head, - const char **strp) +parse_nv(struct parsedb_state *ps, enum parse_nv_flags flags, + const char **strp, const struct namevalue *nv_head, const char *what) { const char *str_start = *strp, *str_end; const struct namevalue *nv; + int value; if (str_start[0] == '\0') parse_error(ps, _("%s is missing"), what); nv = namevalue_find_by_name(nv_head, str_start); - if (nv == NULL) - parse_error(ps, _("'%.50s' is not allowed for %s"), str_start, what); + if (nv == NULL) { + /* We got no match, skip further string validation. */ + if (!(flags & PARSE_NV_FALLBACK)) + parse_error(ps, _("'%.50s' is not allowed for %s"), str_start, what); - /* We got the fallback value, skip further string validation. */ - if (nv->length == 0) { str_end = NULL; + value = -1; } else { str_end = str_start + nv->length; while (c_isspace(str_end[0])) str_end++; + value = nv->value; } - *strp = str_end; - - return nv->value; -} - -static int -parse_nv_last(struct parsedb_state *ps, - const char *what, const struct namevalue *nv_head, - const char *str) -{ - int value; - value = parse_nv_next(ps, what, nv_head, &str); - if (str_is_set(str)) + if (!(flags & PARSE_NV_NEXT) && str_is_set(str_end)) parse_error(ps, _("junk after %s"), what); + *strp = str_end; + return value; } @@ -162,8 +174,8 @@ f_boolean(struct pkginfo *pkg, struct pkgbin *pkgbin, if (!*value) return; - boolean = parse_nv_last(ps, _("yes/no in boolean field"), - booleaninfos, value); + boolean = parse_nv(ps, PARSE_NV_LAST, &value, booleaninfos, + _("yes/no in boolean field")); STRUCTFIELD(pkgbin, fip->integer, bool) = boolean; } @@ -177,8 +189,8 @@ f_multiarch(struct pkginfo *pkg, struct pkgbin *pkgbin, if (!*value) return; - multiarch = parse_nv_last(ps, _("foreign/allowed/same/no in quadstate field"), - multiarchinfos, value); + multiarch = parse_nv(ps, PARSE_NV_LAST, &value, multiarchinfos, + _("foreign/allowed/same/no in quadstate field")); STRUCTFIELD(pkgbin, fip->integer, int) = multiarch; } @@ -207,11 +219,20 @@ f_priority(struct pkginfo *pkg, struct pkgbin *pkgbin, struct parsedb_state *ps, const char *value, const struct fieldinfo *fip) { + const char *str = value; + int priority; + if (!*value) return; - pkg->priority = parse_nv_last(ps, _("word in 'Priority' field"), - priorityinfos, value); - if (pkg->priority == PKG_PRIO_OTHER) + + priority = parse_nv(ps, PARSE_NV_LAST | PARSE_NV_FALLBACK, &str, + priorityinfos, _("word in 'Priority' field")); + + if (str == NULL) { + pkg->priority = PKG_PRIO_OTHER; pkg->otherpriority = nfstrsave(value); + } else { + pkg->priority = priority; + } } void @@ -226,12 +247,12 @@ f_status(struct pkginfo *pkg, struct pkgbin *pkgbin, if (ps->flags & pdb_recordavailable) return; - pkg->want = parse_nv_next(ps, _("first (want) word in 'Status' field"), - wantinfos, &value); - pkg->eflag = parse_nv_next(ps, _("second (error) word in 'Status' field"), - eflaginfos, &value); - pkg->status = parse_nv_last(ps, _("third (status) word in 'Status' field"), - statusinfos, value); + pkg->want = parse_nv(ps, PARSE_NV_NEXT, &value, wantinfos, + _("first (want) word in 'Status' field")); + pkg->eflag = parse_nv(ps, PARSE_NV_NEXT, &value, eflaginfos, + _("second (error) word in 'Status' field")); + pkg->status = parse_nv(ps, PARSE_NV_LAST, &value, statusinfos, + _("third (status) word in 'Status' field")); } void diff --git a/lib/dpkg/namevalue.c b/lib/dpkg/namevalue.c index f3536a6..f585446 100644 --- a/lib/dpkg/namevalue.c +++ b/lib/dpkg/namevalue.c @@ -29,16 +29,12 @@ const struct namevalue * namevalue_find_by_name(const struct namevalue *head, const char *str) { - const struct namevalue *nv, *nv_fallback = NULL; + const struct namevalue *nv; for (nv = head; nv->name; nv++) { - if (nv->length == 0) { - nv_fallback = nv; - continue; - } if (strncasecmp(str, nv->name, nv->length) == 0) return nv; } - return nv_fallback; + return NULL; } diff --git a/lib/dpkg/namevalue.h b/lib/dpkg/namevalue.h index 65f8bd8..0bcbe93 100644 --- a/lib/dpkg/namevalue.h +++ b/lib/dpkg/namevalue.h @@ -40,8 +40,6 @@ struct namevalue { #define NAMEVALUE_DEF(n, v) \ [v] = { .name = n, .value = v, .length = sizeof(n) - 1 } -#define NAMEVALUE_FALLBACK_DEF(n, v) \ - [v] = { .name = n, .value = v, .length = 0 } const struct namevalue *namevalue_find_by_name(const struct namevalue *head, const char *str); diff --git a/lib/dpkg/pkg-namevalue.c b/lib/dpkg/pkg-namevalue.c index 6304ed5..be30332 100644 --- a/lib/dpkg/pkg-namevalue.c +++ b/lib/dpkg/pkg-namevalue.c @@ -45,7 +45,6 @@ const struct namevalue priorityinfos[] = { NAMEVALUE_DEF("standard", PKG_PRIO_STANDARD), NAMEVALUE_DEF("optional", PKG_PRIO_OPTIONAL), NAMEVALUE_DEF("extra", PKG_PRIO_EXTRA), - NAMEVALUE_FALLBACK_DEF("this is a bug - please report", PKG_PRIO_OTHER), NAMEVALUE_DEF("unknown", PKG_PRIO_UNKNOWN), { .name = NULL } }; -- Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/dpkg/dpkg.git -- To UNSUBSCRIBE, email to [email protected] with a subject of "unsubscribe". Trouble? Contact [email protected]

