X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=ext%2Frepo_deb.c;h=5af0c70b942b5537410b59f3d9da5c8d12c90296;hb=2d84f3efc00621de607022f3d7bb91f6c109fc69;hp=7e967a700eb8dd82f1f66228e81afb0634dcb8fe;hpb=5702cc433a97b2365801855bdc5572f940d8bc9a;p=platform%2Fupstream%2Flibsolv.git diff --git a/ext/repo_deb.c b/ext/repo_deb.c index 7e967a7..5af0c70 100644 --- a/ext/repo_deb.c +++ b/ext/repo_deb.c @@ -122,7 +122,14 @@ parseonedep(Pool *pool, char *p) while (*p == ' ' || *p == '\t' || *p == '\n') p++; } - name = pool_strn2id(pool, n, ne - n, 1); + if (ne - n > 4 && ne[-4] == ':' && !strncmp(ne - 4, ":any", 4)) + { + /* multiarch annotation */ + name = pool_strn2id(pool, n, ne - n - 4, 1); + name = pool_rel2id(pool, name, ARCH_ANY, REL_MULTIARCH, 1); + } + else + name = pool_strn2id(pool, n, ne - n, 1); if (e) { evr = pool_strn2id(pool, e, ee - e, 1); @@ -274,7 +281,7 @@ control2solvable(Solvable *s, Repodata *data, char *control) break; case 'R' << 8 | 'E': if (!strcasecmp(tag, "replaces")) - s->obsoletes = makedeps(repo, q, s->conflicts, 0); + s->obsoletes = makedeps(repo, q, s->obsoletes, 0); else if (!strcasecmp(tag, "recommends")) s->recommends = makedeps(repo, q, s->recommends, 0); break; @@ -329,22 +336,30 @@ control2solvable(Solvable *s, Repodata *data, char *control) if (s->obsoletes) { /* obsoletes only count when the packages also conflict */ + /* XXX: should not transcode here */ int i, j, k; - Id d; + Id d, cid; for (i = j = s->obsoletes; (d = repo->idarraydata[i]) != 0; i++) { - if (s->conflicts) + if (!s->conflicts) + continue; + for (k = s->conflicts; (cid = repo->idarraydata[k]) != 0; k++) { - for (k = s->conflicts; repo->idarraydata[k] != 0; k++) - if (repo->idarraydata[k] == d) - break; - if (repo->idarraydata[k]) + if (repo->idarraydata[k] == cid) + break; + if (ISRELDEP(cid)) { - repo->idarraydata[j++] = d; + Reldep *rd = GETRELDEP(pool, cid); + if (rd->flags < 8 && rd->name == d) + break; /* specialize obsoletes */ } } + if (cid) + repo->idarraydata[j++] = cid; } repo->idarraydata[j] = 0; + if (j == s->obsoletes) + s->obsoletes = 0; } } @@ -414,12 +429,12 @@ repo_add_debpackages(Repo *repo, FILE *fp, int flags) } int -repo_add_debdb(Repo *repo, const char *rootdir, int flags) +repo_add_debdb(Repo *repo, int flags) { FILE *fp; const char *path = "/var/lib/dpkg/status"; - if (rootdir) - path = pool_tmpjoin(repo->pool, rootdir, path, 0); + if (flags & REPO_USE_ROOTDIR) + path = pool_prepend_rootdir_tmp(repo->pool, path); if ((fp = fopen(path, "r")) == 0) return pool_error(repo->pool, -1, "%s: %s", path, strerror(errno)); repo_add_debpackages(repo, fp, flags); @@ -427,13 +442,13 @@ repo_add_debdb(Repo *repo, const char *rootdir, int flags) return 0; } -int -repo_add_debs(Repo *repo, const char **debs, int ndebs, int flags) +Id +repo_add_deb(Repo *repo, const char *deb, int flags) { Pool *pool = repo->pool; Repodata *data; unsigned char buf[4096], *bp; - int i, l, l2, vlen, clen, ctarlen; + int l, l2, vlen, clen, ctarlen; unsigned char *ctgz; unsigned char pkgid[16]; unsigned char *ctar; @@ -443,170 +458,158 @@ repo_add_debs(Repo *repo, const char **debs, int ndebs, int flags) struct stat stb; data = repo_add_repodata(repo, flags); - for (i = 0; i < ndebs; i++) + if ((fp = fopen(flags & REPO_USE_ROOTDIR ? pool_prepend_rootdir_tmp(pool, deb) : deb, "r")) == 0) { - if ((fp = fopen(debs[i], "r")) == 0) - { - perror(debs[i]); - continue; - } - if (fstat(fileno(fp), &stb)) - { - perror("stat"); - continue; - } - l = fread(buf, 1, sizeof(buf), fp); - if (l < 8 + 60 || strncmp((char *)buf, "!\ndebian-binary ", 8 + 16) != 0) - { - fprintf(stderr, "%s: not a deb package\n", debs[i]); - fclose(fp); - continue; - } - vlen = atoi((char *)buf + 8 + 48); - if (vlen < 0 || vlen > l) - { - fprintf(stderr, "%s: not a deb package\n", debs[i]); - fclose(fp); - continue; - } - vlen += vlen & 1; - if (l < 8 + 60 + vlen + 60) - { - fprintf(stderr, "%s: unhandled deb package\n", debs[i]); - fclose(fp); - continue; - } - if (strncmp((char *)buf + 8 + 60 + vlen, "control.tar.gz ", 16) != 0) - { - fprintf(stderr, "%s: control.tar.gz is not second entry\n", debs[i]); - fclose(fp); - continue; - } - clen = atoi((char *)buf + 8 + 60 + vlen + 48); - if (clen <= 0) - { - fprintf(stderr, "%s: control.tar.gz has illegal size\n", debs[i]); - fclose(fp); - continue; - } - ctgz = solv_calloc(1, clen + 4); - bp = buf + 8 + 60 + vlen + 60; - l -= 8 + 60 + vlen + 60; - if (l > clen) - l = clen; - if (l) - memcpy(ctgz, bp, l); - if (l < clen) - { - if (fread(ctgz + l, clen - l, 1, fp) != 1) - { - fprintf(stderr, "%s: unexpected EOF\n", debs[i]); - solv_free(ctgz); - fclose(fp); - continue; - } - } + pool_error(pool, -1, "%s: %s", deb, strerror(errno)); + return 0; + } + if (fstat(fileno(fp), &stb)) + { + pool_error(pool, -1, "fstat: %s", strerror(errno)); fclose(fp); - gotpkgid = 0; - if (flags & DEBS_ADD_WITH_PKGID) - { - void *handle = solv_chksum_create(REPOKEY_TYPE_MD5); - solv_chksum_add(handle, ctgz, clen); - solv_chksum_free(handle, pkgid); - gotpkgid = 1; - } - if (ctgz[0] != 0x1f || ctgz[1] != 0x8b) - { - fprintf(stderr, "%s: control.tar.gz is not gzipped\n", debs[i]); - solv_free(ctgz); - continue; - } - if (ctgz[2] != 8 || (ctgz[3] & 0xe0) != 0) + return 0; + } + l = fread(buf, 1, sizeof(buf), fp); + if (l < 8 + 60 || strncmp((char *)buf, "!\ndebian-binary ", 8 + 16) != 0) + { + pool_error(pool, -1, "%s: not a deb package", deb); + fclose(fp); + return 0; + } + vlen = atoi((char *)buf + 8 + 48); + if (vlen < 0 || vlen > l) + { + pool_error(pool, -1, "%s: not a deb package", deb); + fclose(fp); + return 0; + } + vlen += vlen & 1; + if (l < 8 + 60 + vlen + 60) + { + pool_error(pool, -1, "%s: unhandled deb package", deb); + fclose(fp); + return 0; + } + if (strncmp((char *)buf + 8 + 60 + vlen, "control.tar.gz ", 16) != 0) + { + pool_error(pool, -1, "%s: control.tar.gz is not second entry", deb); + fclose(fp); + return 0; + } + clen = atoi((char *)buf + 8 + 60 + vlen + 48); + if (clen <= 0 || clen >= 0x100000) + { + pool_error(pool, -1, "%s: control.tar.gz has illegal size", deb); + fclose(fp); + return 0; + } + ctgz = solv_calloc(1, clen + 4); + bp = buf + 8 + 60 + vlen + 60; + l -= 8 + 60 + vlen + 60; + if (l > clen) + l = clen; + if (l) + memcpy(ctgz, bp, l); + if (l < clen) + { + if (fread(ctgz + l, clen - l, 1, fp) != 1) { - fprintf(stderr, "%s: control.tar.gz is compressed in a strange way\n", debs[i]); + pool_error(pool, -1, "%s: unexpected EOF", deb); solv_free(ctgz); - continue; - } - bp = ctgz + 4; - bp += 6; /* skip time, xflags and OS code */ - if (ctgz[3] & 0x04) - { - /* skip extra field */ - l = bp[0] | bp[1] << 8; - bp += l + 2; - if (bp >= ctgz + clen) - { - fprintf(stderr, "%s: corrupt gzip\n", debs[i]); - solv_free(ctgz); - continue; - } + fclose(fp); + return 0; } - if (ctgz[3] & 0x08) /* orig filename */ - while (*bp) - bp++; - if (ctgz[3] & 0x10) /* file comment */ - while (*bp) - bp++; - if (ctgz[3] & 0x02) /* header crc */ - bp += 2; + } + fclose(fp); + gotpkgid = 0; + if (flags & DEBS_ADD_WITH_PKGID) + { + Chksum *chk = solv_chksum_create(REPOKEY_TYPE_MD5); + solv_chksum_add(chk, ctgz, clen); + solv_chksum_free(chk, pkgid); + gotpkgid = 1; + } + if (ctgz[0] != 0x1f || ctgz[1] != 0x8b) + { + pool_error(pool, -1, "%s: control.tar.gz is not gzipped", deb); + solv_free(ctgz); + return 0; + } + if (ctgz[2] != 8 || (ctgz[3] & 0xe0) != 0) + { + pool_error(pool, -1, "%s: control.tar.gz is compressed in a strange way", deb); + solv_free(ctgz); + return 0; + } + bp = ctgz + 4; + bp += 6; /* skip time, xflags and OS code */ + if (ctgz[3] & 0x04) + { + /* skip extra field */ + l = bp[0] | bp[1] << 8; + bp += l + 2; if (bp >= ctgz + clen) { - fprintf(stderr, "%s: corrupt control.tar.gz\n", debs[i]); + pool_error(pool, -1, "%s: control.tar.gz is corrupt", deb); solv_free(ctgz); - continue; + return 0; } - ctar = decompress(bp, ctgz + clen - bp, &ctarlen); + } + if (ctgz[3] & 0x08) /* orig filename */ + while (*bp) + bp++; + if (ctgz[3] & 0x10) /* file comment */ + while (*bp) + bp++; + if (ctgz[3] & 0x02) /* header crc */ + bp += 2; + if (bp >= ctgz + clen) + { + pool_error(pool, -1, "%s: control.tar.gz is corrupt", deb); solv_free(ctgz); - if (!ctar) - { - fprintf(stderr, "%s: corrupt control.tar.gz\n", debs[i]); - continue; - } - bp = ctar; - l = ctarlen; - while (l > 512) - { - int j; - l2 = 0; - for (j = 124; j < 124 + 12; j++) - if (bp[j] >= '0' && bp[j] <= '7') - l2 = l2 * 8 + (bp[j] - '0'); - if (!strcmp((char *)bp, "./control") || !strcmp((char *)bp, "control")) - break; - l2 = 512 + ((l2 + 511) & ~511); - l -= l2; - bp += l2; - } - if (l <= 512 || l - 512 - l2 <= 0 || l2 <= 0) - { - fprintf(stderr, "%s: control.tar.gz contains no control file\n", debs[i]); - free(ctar); - continue; - } - memmove(ctar, bp + 512, l2); - ctar = solv_realloc(ctar, l2 + 1); - ctar[l2] = 0; - s = pool_id2solvable(pool, repo_add_solvable(repo)); - control2solvable(s, data, (char *)ctar); - repodata_set_location(data, s - pool->solvables, 0, 0, debs[i]); - if (S_ISREG(stb.st_mode)) - repodata_set_num(data, s - pool->solvables, SOLVABLE_DOWNLOADSIZE, (unsigned long long)stb.st_size); - if (gotpkgid) - repodata_set_bin_checksum(data, s - pool->solvables, SOLVABLE_PKGID, REPOKEY_TYPE_MD5, pkgid); - solv_free(ctar); + return 0; } + ctar = decompress(bp, ctgz + clen - bp, &ctarlen); + solv_free(ctgz); + if (!ctar) + { + pool_error(pool, -1, "%s: control.tar.gz is corrupt", deb); + return 0; + } + bp = ctar; + l = ctarlen; + while (l > 512) + { + int j; + l2 = 0; + for (j = 124; j < 124 + 12; j++) + if (bp[j] >= '0' && bp[j] <= '7') + l2 = l2 * 8 + (bp[j] - '0'); + if (!strcmp((char *)bp, "./control") || !strcmp((char *)bp, "control")) + break; + l2 = 512 + ((l2 + 511) & ~511); + l -= l2; + bp += l2; + } + if (l <= 512 || l - 512 - l2 <= 0 || l2 <= 0) + { + pool_error(pool, -1, "%s: control.tar.gz contains no control file", deb); + free(ctar); + return 0; + } + memmove(ctar, bp + 512, l2); + ctar = solv_realloc(ctar, l2 + 1); + ctar[l2] = 0; + s = pool_id2solvable(pool, repo_add_solvable(repo)); + control2solvable(s, data, (char *)ctar); + if (!(flags & REPO_NO_LOCATION)) + repodata_set_location(data, s - pool->solvables, 0, 0, deb); + if (S_ISREG(stb.st_mode)) + repodata_set_num(data, s - pool->solvables, SOLVABLE_DOWNLOADSIZE, (unsigned long long)stb.st_size); + if (gotpkgid) + repodata_set_bin_checksum(data, s - pool->solvables, SOLVABLE_PKGID, REPOKEY_TYPE_MD5, pkgid); + solv_free(ctar); if (!(flags & REPO_NO_INTERNALIZE)) repodata_internalize(data); - return 0; -} - -Id -repo_add_deb(Repo *repo, const char *deb, int flags) -{ - int end = repo->end; - repo_add_debs(repo, &deb, 1, flags); - if (end == repo->end) - return 0; - else - return repo->end - 1; + return s - pool->solvables; }