123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178 |
- /*
- * dpkg - main program for package management
- * verify.c - verify package integrity
- *
- * Copyright © 2012-2015 Guillem Jover <guillem@debian.org>
- *
- * This is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <https://www.gnu.org/licenses/>.
- */
- #include <config.h>
- #include <compat.h>
- #include <string.h>
- #include <stdbool.h>
- #include <stdio.h>
- #include <dpkg/i18n.h>
- #include <dpkg/dpkg.h>
- #include <dpkg/dpkg-db.h>
- #include <dpkg/options.h>
- #include "filesdb.h"
- #include "infodb.h"
- #include "main.h"
- enum verify_result {
- VERIFY_NONE,
- VERIFY_PASS,
- VERIFY_FAIL,
- };
- struct verify_checks {
- enum verify_result md5sum;
- };
- typedef void verify_output_func(struct filenamenode *, struct verify_checks *);
- static int
- verify_result_rpm(enum verify_result result, int check)
- {
- switch (result) {
- case VERIFY_FAIL:
- return check;
- case VERIFY_PASS:
- return '.';
- case VERIFY_NONE:
- default:
- return '?';
- }
- }
- static void
- verify_output_rpm(struct filenamenode *namenode, struct verify_checks *checks)
- {
- char result[9];
- int attr;
- memset(result, '?', sizeof(result));
- result[2] = verify_result_rpm(checks->md5sum, '5');
- if (namenode->flags & fnnf_old_conff)
- attr = 'c';
- else
- attr = ' ';
- printf("%.9s %c %s\n", result, attr, namenode->name);
- }
- static verify_output_func *verify_output = verify_output_rpm;
- bool
- verify_set_output(const char *name)
- {
- if (strcmp(name, "rpm") == 0)
- verify_output = verify_output_rpm;
- else
- return false;
- return true;
- }
- static void
- verify_package(struct pkginfo *pkg)
- {
- struct fileinlist *file;
- struct varbuf filename = VARBUF_INIT;
- ensure_packagefiles_available(pkg);
- parse_filehash(pkg, &pkg->installed);
- pkg_conffiles_mark_old(pkg);
- for (file = pkg->clientdata->files; file; file = file->next) {
- struct verify_checks checks;
- struct filenamenode *fnn;
- char hash[MD5HASHLEN + 1];
- int failures = 0;
- fnn = namenodetouse(file->namenode, pkg, &pkg->installed);
- if (strcmp(fnn->newhash, EMPTYHASHFLAG) == 0) {
- if (fnn->oldhash == NULL)
- continue;
- else
- fnn->newhash = fnn->oldhash;
- }
- varbuf_reset(&filename);
- varbuf_add_str(&filename, instdir);
- varbuf_add_str(&filename, fnn->name);
- varbuf_end_str(&filename);
- memset(&checks, 0, sizeof(checks));
- md5hash(pkg, hash, filename.buf);
- if (strcmp(hash, fnn->newhash) != 0) {
- checks.md5sum = VERIFY_FAIL;
- failures++;
- }
- if (failures)
- verify_output(fnn, &checks);
- }
- varbuf_destroy(&filename);
- }
- int
- verify(const char *const *argv)
- {
- struct pkginfo *pkg;
- int rc = 0;
- modstatdb_open(msdbrw_readonly);
- ensure_diversions();
- if (!*argv) {
- struct pkgiterator *iter;
- iter = pkg_db_iter_new();
- while ((pkg = pkg_db_iter_next_pkg(iter)))
- verify_package(pkg);
- pkg_db_iter_free(iter);
- } else {
- const char *thisarg;
- while ((thisarg = *argv++)) {
- pkg = dpkg_options_parse_pkgname(cipaction, thisarg);
- if (pkg->status == PKG_STAT_NOTINSTALLED) {
- notice(_("package '%s' is not installed"),
- pkg_name(pkg, pnaw_nonambig));
- rc = 1;
- continue;
- }
- verify_package(pkg);
- }
- }
- modstatdb_shutdown();
- m_output(stdout, _("<standard output>"));
- return rc;
- }
|