X-Git-Url: https://pd.if.org/git/?a=blobdiff_plain;f=src%2Fverify.c;fp=src%2Fverify.c;h=14112c2ae7a6071dc2f3a69e46a10e26d5216bb1;hb=5dd3c3e64a9574112dda77a5afc167f5daa53fd8;hp=0000000000000000000000000000000000000000;hpb=bd21f0a1265b43ad5f05353a39db31c16826f05c;p=zpackage diff --git a/src/verify.c b/src/verify.c new file mode 100644 index 0000000..14112c2 --- /dev/null +++ b/src/verify.c @@ -0,0 +1,189 @@ +#define _POSIX_C_SOURCE 200112L +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include "zpm.h" +#include "t/ctap/ctap.h" + +struct config { + char *dbfile; + int plan; + int ran; + int failed; + int quiet; + int failed_only; + int tap; + int check_owner; + int check_group; + int check_perms; + int check_content; /* ignored for config files */ + int check_mtime; +}; + +static void usage() { + printf("usage: zpm foreach-path [-fncC] args ...\n"); +} + +static char *column(char *col, int ncols, char **vals, char **cols) { + int i = 0; + char *val = NULL; + + for (i=0; i < ncols; i++) { + if (!strcmp(col, cols[i])) { + val = vals[i]; + break; + } + } + return val; +} + +static int count_plan(void *f, int ncols, char **vals, char **cols) { + struct config *conf = f; + + int ftype, configfile = 0; + char *v; + + v = column("filetype", ncols, vals, cols); + ftype = *v; + v = column("configuration", ncols, vals, cols); + if (*v == '1') { + configfile = 1; + } + + if (ftype == 'r' && !configfile) { + conf->plan++; + } + + conf->plan++; + + return 0; +} + +static int verify(void *f, int ncols, char **vals, char **cols) { + struct config *conf = f; + char *path; + struct stat st; + int rv; + int ftype, configfile = 0; + char *v, *hash, ehash[ZPM_HASH_STRLEN+1]; + + path = column("path", ncols, vals, cols); + hash = column("hash", ncols, vals, cols); + v = column("filetype", ncols, vals, cols); + ftype = *v; + v = column("configuration", ncols, vals, cols); + if (*v == '1') { + configfile = 1; + } + + conf->ran++; + + rv = lstat(path, &st); + if (rv == -1) { + switch (errno) { + case ENOENT: ok(0, "%s does not exist", path); + break; + default: ok(0, "cannot stat %s: %s", path, strerror(errno)); + conf->failed++; + break; + } + if (ftype == 'r' && !configfile) { + skip("no hash"); + } + return 0; + } + + ok(1, "%s exists", path); + + if (ftype == 'r' && !configfile) { + zpm_hash(path, ehash, 0); + if (!is_string(ehash, hash, "hash %s", path)) { + conf->failed++; + } + } + + return 0; +} + +int main(int ac, char **av) { + struct zpm pkg; + char *s; + int opt; + char *pkgid; + + struct config conf = { 0 }; + conf.dbfile = "/var/lib/zpm/local.db"; + + if ((s = getenv("ZPMDB"))) { + /* TODO does this need to be copied ? */ + conf.dbfile = s; + } + + while ((opt = getopt(ac, av, "f:")) != -1) { + switch (opt) { + case 'f': conf.dbfile = optarg; + break; + default: + usage(); + exit(EXIT_FAILURE); + break; + } + } + + int argn = optind; + + if (!zpm_open(&pkg, conf.dbfile)) { + fprintf(stderr, "can't open zpm db %s\n", conf.dbfile); + exit(EXIT_FAILURE); + } + char *errmsg = 0; + + if (argn < ac) { + pkgid = av[argn]; + argn++; + } else { + fprintf(stderr, "must specify pkgid\n"); + usage(); + exit(EXIT_FAILURE); + } + + /* TODO lookup pkgid via zpm-findpkg equivalent */ + + if (!zpm_foreach_path(&pkg, pkgid, 0, count_plan, &conf, &errmsg)) { + if (errmsg) { + fprintf(stderr, "database error: %s\n", errmsg); + exit(EXIT_FAILURE); + } + if (pkg.error == 1) { + fprintf(stderr, "unable to allocate memory\n"); + } + fprintf(stderr, "unable to plan\n"); + exit(EXIT_FAILURE); + } + + plan(conf.plan); + + if (!zpm_foreach_path(&pkg, pkgid, 0, verify, &conf, &errmsg)) { + if (errmsg) { + fprintf(stderr, "database error: %s\n", errmsg); + exit(EXIT_FAILURE); + } + if (pkg.error == 1) { + fprintf(stderr, "unable to allocate memory\n"); + } + exit(EXIT_FAILURE); + } + + zpm_close(&pkg); + return conf.failed ? 1 : 0; +}