X-Git-Url: https://pd.if.org/git/?a=blobdiff_plain;f=lib%2Fzpm.c;h=b8b77b0861b2e3f9a28d16b71fbe56f54ab0425a;hb=b7a4dd34227b6cf84908ffde9f2c4395f29fe1b4;hp=1565bec495fbd3c23c7eb316c3a99954d1029e5e;hpb=539c670031a08f48ed16c0873f3a9ff0cf80c53d;p=zpackage diff --git a/lib/zpm.c b/lib/zpm.c index 1565bec..b8b77b0 100644 --- a/lib/zpm.c +++ b/lib/zpm.c @@ -114,18 +114,6 @@ void uncompresslzma(void *buf, size_t bufsize, FILE *out); #define SQLERROR(x) fprintf(stderr, "%s %d: %s\n", __func__, __LINE__, (x)) #endif -static char *dupstr(char *s) { - size_t n; - char *d; - - n = strlen(s); - d = malloc(n+1); - if (d) { - d = strcpy(d, s); - } - return d; -} - #if 0 int zpm_newpkg(struct zpm *z, char *base, char *version, int release) { char *sql = "insert or ignore into packages (package,version,release) values (?,?,?)"; @@ -284,64 +272,126 @@ int zpm_db_initialize(struct zpm *pkg) { return 1; } -/* NULL? Create? */ -int zpm_open(struct zpm *pkg, char *path) { - int rc; + +/* assumes pkg->db is set */ +static int setupdb(struct zpm *zpm) { char *errstr = 0; - sqlite3 *db = 0; int appid, dbver; - pkg->db = 0; - pkg->path = 0; - pkg->version = 0; - pkg->release = 0; - pkg->pkgname = 0; - pkg->installed = 0; + zpm->error = 0; + + appid = zpm_db_pragma(zpm, 1); + dbver = zpm_db_pragma(zpm, 2); + + if (appid != 0x5a504442) { + fprintf(stderr, "unknown database type\n"); + zpm->error = 1; + return 0; + } + + if (dbver > 1) { + fprintf(stderr, "version %d zpm db detected, this program only works with version 1 databases\n", dbver); + zpm->error = 1; + return 0; + } + + sqlite3_exec(zpm->db, "pragma foreign_keys = ON;", NULL, NULL, &errstr); + + if (errstr) { + free(zpm->errmsg); + zpm->errmsg = strdup(errstr); + fprintf(stderr, "sqlite foreign key error: %s\n", errstr); + sqlite3_free(errstr); + zpm->error = 1; + return 0; + } + + /* TODO add vercmp */ + + return 1; +} + +struct zpm *zpm_clearmem(struct zpm *zpm) { + if (!zpm) { + zpm = malloc(sizeof *zpm); + } + + if (zpm) { + *zpm = (struct zpm){0}; + } + + return zpm; +} + +int zpm_init(struct zpm *pkg, char *path) { + int rc; + sqlite3 *db = 0; + int appid; + + zpm_clearmem(pkg); - rc = sqlite3_open(path, &db); + rc = sqlite3_open_v2(path, &db, SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE, NULL); if (rc) { SQLERROR(sqlite3_errmsg(db)); sqlite3_close(db); return 0; } pkg->db = db; - pkg->path = dupstr(path); + pkg->path = strdup(path); appid = zpm_db_pragma(pkg, 1); - dbver = zpm_db_pragma(pkg, 2); - //fprintf(stderr, "db appid = %x, dbver = %d\n", appid, dbver); switch (appid) { case 0: if (!zpm_db_initialize(pkg)) { sqlite3_close(db); return 1; }; break; - case 0x5a504442: break; + case 0x5a504442: + /* already initialized */ + break; default: fprintf(stderr, "unknown database type\n"); sqlite3_close(db); return 0; break; } - if (dbver > 1) { - fprintf(stderr, "version %d zpm db detected, this program only works with version 1 databases\n", dbver); - sqlite3_close(db); - return 0; - } - sqlite3_exec(pkg->db, "pragma foreign_keys = ON;", NULL, NULL, &errstr); - if (errstr) { - fprintf(stderr, "sqlite foreign key error: %s\n", errstr); - sqlite3_free(errstr); + if (!setupdb(pkg)) { sqlite3_close(db); + pkg->db = 0; return 0; } + zpm_addvercmp(pkg); + + return 1; +} + +int zpm_open(struct zpm *zpm, char *path) { + int rc; + sqlite3 *db = 0; + + zpm_clearmem(zpm); + rc = sqlite3_open_v2(path, &db, SQLITE_OPEN_READWRITE, NULL); + if (rc) { + SQLERROR(sqlite3_errmsg(db)); + sqlite3_close(db); + zpm->error = 1; + fprintf(stderr, "path = %s\n", path); + return 0; + } + zpm->db = db; + zpm->path = strdup(path); - /* TODO if this is a new database, create structures */ + if (!setupdb(zpm)) { + sqlite3_close(db); + zpm->db = 0; + zpm->error = 1; + return 0; + } + zpm_addvercmp(zpm); - /* get a package. what if more than one? what if none? */ return 1; } @@ -370,32 +420,6 @@ int zpm_addvercmp(struct zpm *pkg) { ); } -/* set package struct variables, database, environment, then command line */ -int zpm_readopts(struct zpm *pkg, int ac, char **av) { - char *ev; - - if (!pkg) { - return -1; - } - - ev = getenv("ZPMPACKAGE"); - if (ev) { - pkg->pkgname = dupstr(ev); - } - ev = getenv("ZPMPKGREL"); - if (ev) { - pkg->release = strtol(ev, 0, 0); - } - ev = getenv("ZPMPKGVER"); - if (ev) { - pkg->version = dupstr(ev); - } - - /* now, parse the options, return optind so the caller can adjust if needed */ - - return av ? ac : 1; -} - int zpm_extract(struct zpm *pkg, char *hash, char *path, int mode) { int rc; @@ -478,7 +502,7 @@ int zpm_extract(struct zpm *pkg, char *hash, char *path, int mode) { return 1; } -static sqlite3_stmt *run_for_hash(sqlite3 *db, char *sql, char *hash) { +static int run_for_hash(sqlite3 *db, char *sql, char *hash) { int rc; sqlite3_stmt *ifile; @@ -491,10 +515,17 @@ static sqlite3_stmt *run_for_hash(sqlite3 *db, char *sql, char *hash) { /* hash, filename */ sqlite3_bind_text(ifile, 1, hash, 64, SQLITE_STATIC); + do { + rc = sqlite3_step(ifile); + } while (rc == SQLITE_ROW); + + sqlite3_finalize(ifile); - return ifile; + return rc == SQLITE_DONE; } +#define SQLERP(db, msg) fprintf(stderr, "%s: %s\n", msg, sqlite3_errmsg(db)) + static int set_elf_info(sqlite3 *db, char *hash, char *content, size_t length) { if (length >= sizeof (Elf64_Ehdr) && libelf_iself(content)) { char *strtab; @@ -505,54 +536,21 @@ static int set_elf_info(sqlite3 *db, char *hash, char *content, size_t length) { sqlite3_stmt *ifile; int rc; - /* go ahead and set up elf information now */ /* clear existing for this hash */ - ifile = run_for_hash(db, "delete from elfinfo where file = ?", hash); - do { - rc = sqlite3_step(ifile); -#if 0 - if (rc == SQLITE_ROW) { - int nc; - fprintf(stderr, "delete row has %d columns: ", sqlite3_column_count(ifile)); - nc = sqlite3_column_count(ifile); - for (i = 0; i < nc; i++) { - char *r; - r = sqlite3_column_text(ifile, i); - fprintf(stderr, ", %s", r); - } - fprintf(stderr, "\n"); - } -#endif - } while (rc == SQLITE_ROW); - if (rc != SQLITE_DONE) { - SQLERROR(sqlite3_errmsg(db)); - sqlite3_finalize(ifile); - fprintf(stderr, "error clearing elf info: %d\n", rc); + if (!run_for_hash(db, "delete from elfinfo where file = ?", hash)) { + SQLERP(db, "error clearing elf info"); return 0; } - sqlite3_finalize(ifile); - ifile = run_for_hash(db, "delete from elflibraries where file = ?", hash); - do { - rc = sqlite3_step(ifile); - } while (rc == SQLITE_ROW); - if (rc != SQLITE_DONE) { - SQLERROR(sqlite3_errmsg(db)); - sqlite3_finalize(ifile); - fprintf(stderr, "error clearing elf library: %d\n", rc); + + if (!run_for_hash(db, "delete from elflibraries where file = ?", hash)) { + SQLERP(db, "error clearing elf library"); return 0; } - sqlite3_finalize(ifile); - ifile = run_for_hash(db, "delete from elfneeded where file = ?", hash); - do { - rc = sqlite3_step(ifile); - } while (rc == SQLITE_ROW); - if (rc != SQLITE_DONE) { - SQLERROR(sqlite3_errmsg(db)); - sqlite3_finalize(ifile); - fprintf(stderr, "error clearing elf needed\n"); + + if (!run_for_hash(db, "delete from elfneeded where file = ?", hash)) { + SQLERP(db, "error clearing elf needed"); return 0; } - sqlite3_finalize(ifile); hdr = libelf_header(content); /* if lib, set soname */ @@ -616,9 +614,8 @@ static int set_elf_info(sqlite3 *db, char *hash, char *content, size_t length) { #endif rc = sqlite3_step(ifile); if (rc != SQLITE_DONE) { - SQLERROR(sqlite3_errmsg(db)); + SQLERP(db, "error setting needed library"); sqlite3_finalize(ifile); - fprintf(stderr, "error setting needed library\n"); return 0; } sqlite3_reset(ifile); @@ -632,7 +629,7 @@ static int set_elf_info(sqlite3 *db, char *hash, char *content, size_t length) { } #if 1 -int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { +int zpm_import(struct zpm *zpm, char *path, uint32_t flags, char *hash) { int fd; void *content; struct stat sbuf; @@ -647,7 +644,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { size_t outlen = 0; void *outbuf; - if (!pkg || !pkg->db || !path) { + if (!zpm || !zpm->db || !path) { return 0; } @@ -662,12 +659,12 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { /* mmap the file */ fd = open(path, O_RDONLY); if (fd == -1) { - pkg->error = errno; + zpm->error = errno; fprintf(stderr, "%s can't open %s: %s\n", __FUNCTION__, path,strerror(errno)); return 0; } if (fstat(fd, &sbuf) == -1) { - pkg->error = errno; + zpm->error = errno; fprintf(stderr, "%s can't fstat %s: %s\n", __FUNCTION__, path,strerror(errno)); return 0; } @@ -685,14 +682,14 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { } /* TODO this is ok, just stored differently */ fprintf(stderr, "%s can't import %s file: %s\n", __FUNCTION__, ftype, path); - pkg->error = EINVAL; + zpm->error = EINVAL; return 0; } content = mmap(0, sbuf.st_size, PROT_READ,MAP_PRIVATE, fd, 0); close(fd); if (!content) { - pkg->error = errno; + zpm->error = errno; fprintf(stderr, "%s can't mmap %s: %s\n", __FUNCTION__, path,strerror(errno)); return 0; } @@ -708,7 +705,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { //fprintf(stderr, "file %s: %s\n", path, hash); /* TODO check null */ - sqlite3 *db = pkg->db; + sqlite3 *db = zpm->db; /* prepare and bind */ @@ -729,7 +726,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { if (rc != SQLITE_ROW) { /* didn't find a row */ SQLERROR(sqlite3_errmsg(db)); - zpm_rollback(pkg); + zpm_rollback(zpm); munmap(content, sbuf.st_size); return 0; } @@ -769,7 +766,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { /* start a transaction */ // do that outside of here - //zpm_begin(pkg); + //zpm_begin(zpm); /* insert */ if (haverow) { @@ -782,7 +779,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { if (rc != SQLITE_OK) { SQLERROR(sqlite3_errmsg(db)); fprintf(stderr, "cant prepare data\n"); - zpm_rollback(pkg); + zpm_rollback(zpm); munmap(content, sbuf.st_size); return 0; } @@ -791,7 +788,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { if (rc != SQLITE_OK) { SQLERROR(sqlite3_errmsg(db)); fprintf(stderr, "cant bind size\n"); - zpm_rollback(pkg); + zpm_rollback(zpm); munmap(content, sbuf.st_size); return 0; } @@ -799,7 +796,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { if (rc != SQLITE_OK) { SQLERROR(sqlite3_errmsg(db)); fprintf(stderr, "cant bind content\n"); - zpm_rollback(pkg); + zpm_rollback(zpm); munmap(content, sbuf.st_size); return 0; } @@ -807,7 +804,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { if (rc != SQLITE_OK) { SQLERROR(sqlite3_errmsg(db)); fprintf(stderr, "cant bind hash\n"); - zpm_rollback(pkg); + zpm_rollback(zpm); munmap(content, sbuf.st_size); return 0; } @@ -815,20 +812,20 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { if (rc != SQLITE_DONE) { SQLERROR(sqlite3_errmsg(db)); sqlite3_finalize(ifile); - zpm_rollback(pkg); + zpm_rollback(zpm); munmap(content, sbuf.st_size); return 0; } sqlite3_finalize(ifile); /* commit */ - //zpm_commit(pkg); + //zpm_commit(zpm); /* don't need the original file now */ } - if (!set_elf_info(pkg->db, hash, content, sbuf.st_size)) { + if (!set_elf_info(zpm->db, hash, content, sbuf.st_size)) { fprintf(stderr, "setting elf info failed\n"); munmap(content, sbuf.st_size); return 0; @@ -837,7 +834,7 @@ int zpm_import(struct zpm *pkg, char *path, uint32_t flags, char *hash) { munmap(content, sbuf.st_size); /* if package and not nopackage flag, add to package */ - if (pkg->pkgname && (!ZPM_NOPACKAGE)) { + if (zpm->current_package->name && (!ZPM_NOPACKAGE)) { /* TODO */ }