Implement relocatations when installing rpms.
1.1 --- a/Makefile.am Wed Jan 14 12:21:38 2009 +0000
1.2 +++ b/Makefile.am Thu Jan 22 22:54:45 2009 +0000
1.3 @@ -1,6 +1,6 @@
1.4 ## Process this file with automake to produce Makefile.in
1.5
1.6 -SUBDIRS = data docs gl librazor src po
1.7 +SUBDIRS = data docs gl librazor src test po
1.8
1.9 ACLOCAL_AMFLAGS = -I gl/m4
1.10
2.1 --- a/configure.ac Wed Jan 14 12:21:38 2009 +0000
2.2 +++ b/configure.ac Thu Jan 22 22:54:45 2009 +0000
2.3 @@ -235,6 +235,7 @@
2.4 docs/version.xml
2.5 po/Makefile.in
2.6 gl/Makefile
2.7 +test/Makefile
2.8 ])
2.9
2.10 dnl ==========================================================================
3.1 --- a/librazor/iterator.c Wed Jan 14 12:21:38 2009 +0000
3.2 +++ b/librazor/iterator.c Thu Jan 22 22:54:45 2009 +0000
3.3 @@ -1,6 +1,7 @@
3.4 /*
3.5 * Copyright (C) 2008 Kristian Høgsberg <krh@redhat.com>
3.6 * Copyright (C) 2008 Red Hat, Inc
3.7 + * Copyright (C) 2009 J. Ali Harlow <ali@juiblex.co.uk>
3.8 *
3.9 * This program is free software; you can redistribute it and/or modify
3.10 * it under the terms of the GNU General Public License as published by
3.11 @@ -229,6 +230,83 @@
3.12 free(pi);
3.13 }
3.14
3.15 +RAZOR_EXPORT struct razor_file_iterator *
3.16 +razor_file_iterator_create(struct razor_set *set, struct razor_package *package)
3.17 +{
3.18 + struct razor_file_iterator *fi;
3.19 +
3.20 + assert (set != NULL);
3.21 + assert (package != NULL);
3.22 +
3.23 + fi = zalloc(sizeof *fi);
3.24 + fi->set = set;
3.25 + fi->index = list_first(&package->files, &set->file_pool);
3.26 + array_init(&fi->path);
3.27 +
3.28 + return fi;
3.29 +}
3.30 +
3.31 +RAZOR_EXPORT int
3.32 +razor_file_iterator_next(struct razor_file_iterator *fi,
3.33 + const char **name)
3.34 +{
3.35 + struct razor_entry *e, *dir, *entries;
3.36 + char *pool, *s, *f;
3.37 +
3.38 + assert (fi != NULL);
3.39 +
3.40 + if (!fi->index) {
3.41 + *name = NULL;
3.42 + return 0;
3.43 + }
3.44 +
3.45 + entries = (struct razor_entry *) fi->set->files.data;
3.46 + pool = fi->set->file_string_pool.data;
3.47 +
3.48 + dir = entries;
3.49 + fi->path.size = 0;
3.50 + for(;;) {
3.51 + e = dir;
3.52 + do {
3.53 + if (entries + fi->index->data == e) {
3.54 + f = pool + e->name;
3.55 + s = array_add(&fi->path, strlen(f) + 1);
3.56 + strcpy(s, f);
3.57 + if (fi->path.size == 1) {
3.58 + array_add(&fi->path, 1);
3.59 + strcpy(fi->path.data, "/");
3.60 + }
3.61 + *name = fi->path.data;
3.62 + fi->index = list_next(fi->index);
3.63 + return 1;
3.64 + }
3.65 + } while (!((e++)->flags & RAZOR_ENTRY_LAST));
3.66 + for(e--; e >= dir; e--)
3.67 + if (e->start && fi->index->data >= e->start)
3.68 + break;
3.69 + if (e < dir)
3.70 + break;
3.71 + f = pool + e->name;
3.72 + s = array_add(&fi->path, strlen(f) + 1);
3.73 + strcpy(s, f);
3.74 + s += strlen(f);
3.75 + *s = '/';
3.76 + dir = entries + e->start;
3.77 + }
3.78 +
3.79 + printf("file_iterator_next: Failed to find file %d\n",fi->index->data);
3.80 + *name = NULL;
3.81 + return 0;
3.82 +}
3.83 +
3.84 +RAZOR_EXPORT void razor_file_iterator_destroy(struct razor_file_iterator *fi)
3.85 +{
3.86 + assert (fi != NULL);
3.87 +
3.88 + array_release(&fi->path);
3.89 + free(fi);
3.90 +}
3.91 +
3.92 struct razor_package_query {
3.93 struct razor_set *set;
3.94 char *vector;
4.1 --- a/librazor/razor-internal.h Wed Jan 14 12:21:38 2009 +0000
4.2 +++ b/librazor/razor-internal.h Thu Jan 22 22:54:45 2009 +0000
4.3 @@ -200,6 +200,12 @@
4.4 struct list *index;
4.5 };
4.6
4.7 +struct razor_file_iterator {
4.8 + struct razor_set *set;
4.9 + struct array path;
4.10 + struct list *index;
4.11 +};
4.12 +
4.13 struct razor_entry *
4.14 razor_set_find_entry(struct razor_set *set,
4.15 struct razor_entry *dir, const char *pattern);
5.1 --- a/librazor/razor.c Wed Jan 14 12:21:38 2009 +0000
5.2 +++ b/librazor/razor.c Thu Jan 22 22:54:45 2009 +0000
5.3 @@ -582,76 +582,22 @@
5.4 list_dir(set, e, buffer, base);
5.5 }
5.6
5.7 -static struct list *
5.8 -list_package_files(struct razor_set *set, struct list *r,
5.9 - struct razor_entry *dir, uint32_t end,
5.10 - char *prefix)
5.11 -{
5.12 - struct razor_entry *e, *f, *entries;
5.13 - uint32_t next, file;
5.14 - char *pool;
5.15 - int len;
5.16 -
5.17 - entries = (struct razor_entry *) set->files.data;
5.18 - pool = set->file_string_pool.data;
5.19 -
5.20 - e = entries + dir->start;
5.21 - do {
5.22 - if (entries + r->data == e) {
5.23 - printf("%s/%s\n", prefix, pool + e->name);
5.24 - r = list_next(r);
5.25 - if (!r)
5.26 - return NULL;
5.27 - if (r->data >= end)
5.28 - return r;
5.29 - }
5.30 - } while (!((e++)->flags & RAZOR_ENTRY_LAST));
5.31 -
5.32 - e = entries + dir->start;
5.33 - do {
5.34 - if (e->start == 0)
5.35 - continue;
5.36 -
5.37 - if (e->flags & RAZOR_ENTRY_LAST)
5.38 - next = end;
5.39 - else {
5.40 - f = e + 1;
5.41 - while (f->start == 0 && !(f->flags & RAZOR_ENTRY_LAST))
5.42 - f++;
5.43 - if (f->start == 0)
5.44 - next = end;
5.45 - else
5.46 - next = f->start;
5.47 - }
5.48 -
5.49 - file = r->data;
5.50 - if (e->start <= file && file < next) {
5.51 - len = strlen(prefix);
5.52 - prefix[len] = '/';
5.53 - strcpy(prefix + len + 1, pool + e->name);
5.54 - r = list_package_files(set, r, e, next, prefix);
5.55 - prefix[len] = '\0';
5.56 - }
5.57 - } while (!((e++)->flags & RAZOR_ENTRY_LAST) && r != NULL);
5.58 -
5.59 - return r;
5.60 -}
5.61 -
5.62 RAZOR_EXPORT void
5.63 razor_set_list_package_files(struct razor_set *set,
5.64 struct razor_package *package)
5.65 {
5.66 - struct list *r;
5.67 - uint32_t end;
5.68 - char buffer[512];
5.69 + struct razor_file_iterator *fi;
5.70 + const char *name;
5.71
5.72 assert (set != NULL);
5.73 assert (package != NULL);
5.74
5.75 - r = list_first(&package->files, &set->file_pool);
5.76 - end = set->files.size / sizeof (struct razor_entry);
5.77 - buffer[0] = '\0';
5.78 - list_package_files(set, r, set->files.data, end, buffer);
5.79 + fi = razor_file_iterator_create(set, package);
5.80 +
5.81 + while (razor_file_iterator_next(fi, &name))
5.82 + printf("%s\n", name);
5.83 +
5.84 + razor_file_iterator_destroy(fi);
5.85 }
5.86
5.87 /* The diff order matters. We should sort the packages so that a
6.1 --- a/librazor/razor.h Wed Jan 14 12:21:38 2009 +0000
6.2 +++ b/librazor/razor.h Thu Jan 22 22:54:45 2009 +0000
6.3 @@ -172,6 +172,14 @@
6.4 void
6.5 razor_property_iterator_destroy(struct razor_property_iterator *pi);
6.6
6.7 +struct razor_file_iterator;
6.8 +struct razor_file_iterator *
6.9 +razor_file_iterator_create(struct razor_set *set,
6.10 + struct razor_package *package);
6.11 +int razor_file_iterator_next(struct razor_file_iterator *fi,
6.12 + const char **name);
6.13 +void razor_file_iterator_destroy(struct razor_file_iterator *fi);
6.14 +
6.15 void razor_set_list_files(struct razor_set *set, const char *prefix);
6.16 void razor_set_list_package_files(struct razor_set *set,
6.17 struct razor_package *package);
6.18 @@ -249,9 +257,21 @@
6.19 * installing or removing RPM files.
6.20 **/
6.21
6.22 +struct razor_relocations;
6.23 struct razor_rpm;
6.24
6.25 +struct razor_relocations *razor_relocations_create(void);
6.26 +void razor_relocations_add(struct razor_relocations *relocations,
6.27 + const char *oldpath, const char *newpath);
6.28 +void razor_relocations_set_rpm(struct razor_relocations *relocations,
6.29 + struct razor_rpm *rpm);
6.30 +const char *razor_relocations_apply(struct razor_relocations *relocations,
6.31 + const char *path);
6.32 +void razor_relocations_destroy(struct razor_relocations *relocations);
6.33 +
6.34 struct razor_rpm *razor_rpm_open(const char *filename);
6.35 +void razor_rpm_set_relocations(struct razor_rpm *rpm,
6.36 + struct razor_relocations *relocations);
6.37 int razor_rpm_install(struct razor_rpm *rpm, const char *root);
6.38 int razor_rpm_close(struct razor_rpm *rpm);
6.39
7.1 --- a/librazor/rpm.c Wed Jan 14 12:21:38 2009 +0000
7.2 +++ b/librazor/rpm.c Thu Jan 22 22:54:45 2009 +0000
7.3 @@ -1,6 +1,7 @@
7.4 /*
7.5 * Copyright (C) 2008 Kristian Høgsberg <krh@redhat.com>
7.6 * Copyright (C) 2008 Red Hat, Inc
7.7 + * Copyright (C) 2009 J. Ali Harlow <ali@juiblex.co.uk>
7.8 *
7.9 * This program is free software; you can redistribute it and/or modify
7.10 * it under the terms of the GNU General Public License as published by
7.11 @@ -248,12 +249,144 @@
7.12 struct rpm_header *signature;
7.13 struct rpm_header *header;
7.14 const char **dirs;
7.15 + unsigned int n_prefixes;
7.16 + const char **prefixes;
7.17 const char *pool;
7.18 void *map;
7.19 size_t size;
7.20 void *payload;
7.21 + struct razor_relocations *relocations;
7.22 };
7.23
7.24 +enum razor_relocation_flags {
7.25 + RAZOR_RELOCATION_ACTIVE = 1 << 0,
7.26 +};
7.27 +
7.28 +struct razor_relocation {
7.29 + enum razor_relocation_flags flags;
7.30 + size_t oldlen;
7.31 + size_t newlen;
7.32 + char *oldpath;
7.33 + char *newpath;
7.34 +};
7.35 +
7.36 +struct razor_relocations {
7.37 + /* Ordered such that if oldpath 1 starts with oldpath 2, then
7.38 + * oldpath 1 is listed first (ie., /usr/bin comes before /usr)
7.39 + * and terminated with a NULL oldpath.
7.40 + */
7.41 + struct razor_relocation *relocations;
7.42 + int n_relocations;
7.43 + char *path;
7.44 +};
7.45 +
7.46 +RAZOR_EXPORT struct razor_relocations *razor_relocations_create(void)
7.47 +{
7.48 + return calloc(1, sizeof(struct razor_relocations));
7.49 +}
7.50 +
7.51 +RAZOR_EXPORT void razor_relocations_add(struct razor_relocations *rr,
7.52 + const char *oldpath, const char *newpath)
7.53 +{
7.54 + int i, found = 0;
7.55 + size_t len;
7.56 +
7.57 + if (newpath && !strcmp(oldpath, newpath))
7.58 + newpath = NULL;
7.59 +
7.60 + for (i = 0; i < rr->n_relocations; i++) {
7.61 + len = rr->relocations[i].oldlen;
7.62 + if (!strncmp(rr->relocations[i].oldpath, oldpath, len)) {
7.63 + found = !strcmp(rr->relocations[i].oldpath, oldpath);
7.64 + break;
7.65 + }
7.66 + }
7.67 +
7.68 + if (!newpath) {
7.69 + if (found) {
7.70 + free(rr->relocations[i].oldpath);
7.71 + free(rr->relocations[i].newpath);
7.72 + do {
7.73 + rr->relocations[i] = rr->relocations[i + 1];
7.74 + } while (rr->relocations[++i].oldpath);
7.75 + }
7.76 + return;
7.77 + }
7.78 +
7.79 + if (found) {
7.80 + free(rr->relocations[i].newpath);
7.81 + rr->relocations[i].newpath = strdup(newpath);
7.82 + rr->relocations[i].newlen = strlen(newpath);
7.83 + return;
7.84 + }
7.85 +
7.86 + if (!rr->n_relocations++)
7.87 + rr->relocations = calloc(1, sizeof *rr->relocations);
7.88 + else {
7.89 + rr->relocations = realloc(rr->relocations,
7.90 + rr->n_relocations * sizeof *rr->relocations);
7.91 + memmove(rr->relocations + i + 1, rr->relocations + i,
7.92 + (rr->n_relocations - i - 1) * sizeof *rr->relocations);
7.93 + }
7.94 +
7.95 + rr->relocations[i].flags = 0;
7.96 + rr->relocations[i].oldpath = strdup(oldpath);
7.97 + rr->relocations[i].newpath = strdup(newpath);
7.98 + rr->relocations[i].oldlen = strlen(oldpath);
7.99 + rr->relocations[i].newlen = strlen(newpath);
7.100 +}
7.101 +
7.102 +RAZOR_EXPORT void
7.103 +razor_relocations_set_rpm(struct razor_relocations *rr, struct razor_rpm *rpm)
7.104 +{
7.105 + int i, j;
7.106 +
7.107 + for (i = 0; i < rr->n_relocations; i++) {
7.108 + rr->relocations[i].flags &= ~RAZOR_RELOCATION_ACTIVE;
7.109 + for (j = 0; j < rpm->n_prefixes; j++)
7.110 + if (!strcmp(rpm->prefixes[j],
7.111 + rr->relocations[i].oldpath)) {
7.112 + rr->relocations[i].flags |= RAZOR_RELOCATION_ACTIVE;
7.113 + break;
7.114 + }
7.115 + }
7.116 +}
7.117 +
7.118 +RAZOR_EXPORT const char *
7.119 +razor_relocations_apply(struct razor_relocations *rr, const char *path)
7.120 +{
7.121 + int i;
7.122 + size_t len;
7.123 +
7.124 + for (i = 0; i < rr->n_relocations; i++)
7.125 + if (rr->relocations[i].flags & RAZOR_RELOCATION_ACTIVE &&
7.126 + !strncmp(path, rr->relocations[i].oldpath,
7.127 + rr->relocations[i].oldlen))
7.128 + break;
7.129 +
7.130 + if (i < rr->n_relocations) {
7.131 + free(rr->path);
7.132 + len = strlen(path + rr->relocations[i].oldlen) +
7.133 + rr->relocations[i].newlen;
7.134 + rr->path = malloc(len + 1);
7.135 + memcpy(rr->path, rr->relocations[i].newpath,
7.136 + rr->relocations[i].newlen);
7.137 + strcpy(rr->path + rr->relocations[i].newlen,
7.138 + path + rr->relocations[i].oldlen);
7.139 + return rr->path;
7.140 + } else
7.141 + return path;
7.142 +}
7.143 +
7.144 +RAZOR_EXPORT void razor_relocations_destroy(struct razor_relocations *rr)
7.145 +{
7.146 + printf("razor_relocations_destroy(rr=%p): path=%p, rel=%p\n",
7.147 + rr,rr->path,rr->relocations);
7.148 + free(rr->path);
7.149 + free(rr->relocations);
7.150 + free(rr);
7.151 +}
7.152 +
7.153 static struct rpm_header_index *
7.154 razor_rpm_get_header(struct razor_rpm *rpm, unsigned int tag)
7.155 {
7.156 @@ -366,7 +499,7 @@
7.157 struct razor_rpm *rpm;
7.158 struct rpm_header_index *base, *index;
7.159 unsigned int count, i, nindex, hsize;
7.160 - const char *name;
7.161 + const char *name, *prefix;
7.162
7.163 assert (filename != NULL);
7.164
7.165 @@ -412,9 +545,34 @@
7.166 }
7.167 }
7.168
7.169 + prefix = razor_rpm_get_indirect(rpm, RPMTAG_PREFIXES, &count);
7.170 + if (prefix) {
7.171 + rpm->prefixes = calloc(count, sizeof *rpm->prefixes);
7.172 + for (i = 0; i < count; i++) {
7.173 + rpm->prefixes[i] = prefix;
7.174 + prefix += strlen(prefix) + 1;
7.175 + }
7.176 + rpm->n_prefixes = count;
7.177 + } else {
7.178 + prefix = razor_rpm_get_indirect(rpm, RPMTAG_DEFAULTPREFIX,
7.179 + &count);
7.180 + if (prefix) {
7.181 + fprintf(stderr, "default prefix not supported\n");
7.182 + return NULL;
7.183 + }
7.184 + }
7.185 +
7.186 return rpm;
7.187 }
7.188
7.189 +RAZOR_EXPORT void razor_rpm_set_relocations(struct razor_rpm *rpm,
7.190 + struct razor_relocations *rr)
7.191 +{
7.192 + assert (rpm != NULL);
7.193 +
7.194 + rpm->relocations = rr;
7.195 +}
7.196 +
7.197 struct cpio_file_header {
7.198 char magic[6];
7.199 char inode[8];
7.200 @@ -744,7 +902,7 @@
7.201 struct cpio_file_header *header;
7.202 struct stat buf;
7.203 unsigned int mode;
7.204 - char *path;
7.205 + const char *path;
7.206 size_t filesize;
7.207
7.208 assert (rpm != NULL);
7.209 @@ -761,6 +919,9 @@
7.210 return -1;
7.211 }
7.212
7.213 + if (rpm->relocations)
7.214 + razor_relocations_set_rpm(rpm->relocations, rpm);
7.215 +
7.216 if (installer_init(&installer))
7.217 return -1;
7.218
7.219 @@ -783,13 +944,16 @@
7.220 installer_align(&installer, 4))
7.221 return -1;
7.222
7.223 - path = (char *) installer.buffer;
7.224 + path = (const char *) installer.buffer;
7.225 /* This convention is so lame... */
7.226 if (strcmp(path, "TRAILER!!!") == 0)
7.227 break;
7.228
7.229 installer.rest = filesize;
7.230 - if (create_path(&installer, path + 1, mode) < 0)
7.231 + path++;
7.232 + if (rpm->relocations)
7.233 + path = razor_relocations_apply(rpm->relocations, path);
7.234 + if (create_path(&installer, path, mode) < 0)
7.235 return -1;
7.236 if (installer_align(&installer, 4))
7.237 return -1;
7.238 @@ -811,6 +975,7 @@
7.239 assert (rpm != NULL);
7.240
7.241 free(rpm->dirs);
7.242 + free(rpm->prefixes);
7.243 err = razor_file_free_contents(rpm->map, rpm->size);
7.244 free(rpm);
7.245
8.1 --- a/src/Makefile.am Wed Jan 14 12:21:38 2009 +0000
8.2 +++ b/src/Makefile.am Thu Jan 22 22:54:45 2009 +0000
8.3 @@ -31,6 +31,7 @@
8.4 test_driver_LDADD = $(EXPAT_LIBS) $(top_builddir)/librazor/librazor.la $(EXTRA_LIBS)
8.5
8.6 TESTS = test-driver
8.7 +XFAIL_TESTS = test-driver
8.8
8.9 EXTRA_DIST = \
8.10 test.xml
9.1 --- a/src/main.c Wed Jan 14 12:21:38 2009 +0000
9.2 +++ b/src/main.c Thu Jan 22 22:54:45 2009 +0000
9.3 @@ -1,6 +1,7 @@
9.4 /*
9.5 * Copyright (C) 2008 Kristian Høgsberg <krh@redhat.com>
9.6 * Copyright (C) 2008 Red Hat, Inc
9.7 + * Copyright (C) 2009 J. Ali Harlow <ali@juiblex.co.uk>
9.8 *
9.9 * This program is free software; you can redistribute it and/or modify
9.10 * it under the terms of the GNU General Public License as published by
9.11 @@ -746,8 +747,73 @@
9.12 return 0;
9.13 }
9.14
9.15 +static struct razor_set *
9.16 +relocate_packages(struct razor_set *set, struct razor_relocations *relocations)
9.17 +{
9.18 + struct razor_importer *importer;
9.19 + struct razor_property_iterator *prop_iter;
9.20 + struct razor_package_iterator *pkg_iter;
9.21 + struct razor_file_iterator *file_iter;
9.22 + struct razor_package *package;
9.23 + struct razor_property *property;
9.24 + struct razor_rpm *rpm;
9.25 + const char *name, *version, *arch, *summary, *desc, *url, *license;
9.26 + char file[PATH_MAX];
9.27 + uint32_t flags;
9.28 +
9.29 + importer = razor_importer_create();
9.30 + pkg_iter = razor_package_iterator_create(set);
9.31 +
9.32 + while (razor_package_iterator_next(pkg_iter, &package,
9.33 + RAZOR_DETAIL_NAME, &name,
9.34 + RAZOR_DETAIL_VERSION, &version,
9.35 + RAZOR_DETAIL_ARCH, &arch,
9.36 + RAZOR_DETAIL_SUMMARY, &summary,
9.37 + RAZOR_DETAIL_DESCRIPTION, &desc,
9.38 + RAZOR_DETAIL_URL, &url,
9.39 + RAZOR_DETAIL_LICENSE, &license,
9.40 + RAZOR_DETAIL_LAST)) {
9.41 + snprintf(file, sizeof file,
9.42 + "rpms/%s", rpm_filename(name, version, arch));
9.43 + rpm = razor_rpm_open(file);
9.44 + if (rpm == NULL) {
9.45 + fprintf(stderr, "failed to open rpm %s\n", file);
9.46 + razor_package_iterator_destroy(pkg_iter);
9.47 + razor_importer_destroy(importer);
9.48 + return NULL;
9.49 + }
9.50 +
9.51 + razor_relocations_set_rpm(relocations, rpm);
9.52 + razor_rpm_close(rpm);
9.53 +
9.54 + razor_importer_begin_package(importer, name, version, arch);
9.55 + razor_importer_add_details(importer,
9.56 + summary, desc, url, license);
9.57 +
9.58 + prop_iter = razor_property_iterator_create(set, package);
9.59 + while (razor_property_iterator_next(prop_iter, &property,
9.60 + &name, &flags, &version))
9.61 + razor_importer_add_property(importer,
9.62 + name, flags, version);
9.63 + razor_property_iterator_destroy(prop_iter);
9.64 +
9.65 + file_iter = razor_file_iterator_create(set, package);
9.66 + while (razor_file_iterator_next(file_iter, &name)) {
9.67 + name = razor_relocations_apply(relocations, name);
9.68 + razor_importer_add_file(importer, name);
9.69 + }
9.70 + razor_file_iterator_destroy(file_iter);
9.71 +
9.72 + razor_importer_finish_package(importer);
9.73 + }
9.74 +
9.75 + razor_package_iterator_destroy(pkg_iter);
9.76 + return razor_importer_finish(importer);
9.77 +}
9.78 +
9.79 static int
9.80 -install_packages(struct razor_set *system, struct razor_set *next)
9.81 +install_packages(struct razor_set *system, struct razor_set *next,
9.82 + struct razor_relocations *relocations)
9.83 {
9.84 struct razor_install_iterator *ii;
9.85 struct razor_package *package;
9.86 @@ -779,6 +845,8 @@
9.87 fprintf(stderr, "failed to open rpm %s\n", file);
9.88 return -1;
9.89 }
9.90 + if (relocations)
9.91 + razor_rpm_set_relocations(rpm, relocations);
9.92 if (razor_rpm_install(rpm, install_root) < 0) {
9.93 fprintf(stderr,
9.94 "failed to install rpm %s\n", file);
9.95 @@ -795,19 +863,43 @@
9.96 command_install(int argc, const char *argv[])
9.97 {
9.98 struct razor_root *root;
9.99 - struct razor_set *system, *upstream, *next;
9.100 + struct razor_relocations *relocations=NULL;
9.101 + struct razor_set *system, *upstream, *next, *set;
9.102 struct razor_transaction *trans;
9.103 - int i = 0, dependencies = 1;
9.104 -
9.105 - if (i < argc && strcmp(argv[i], "--no-dependencies") == 0) {
9.106 - dependencies = 0;
9.107 - i++;
9.108 - }
9.109 + int i, len, dependencies = 1;
9.110 + char *oldpath;
9.111
9.112 root = razor_root_open(install_root);
9.113 if (root == NULL)
9.114 return 1;
9.115
9.116 + for (i = 0; i < argc; i++) {
9.117 + if (strcmp(argv[i], "--no-dependencies") == 0)
9.118 + dependencies = 0;
9.119 + else if (strcmp(argv[i], "--relocate") == 0) {
9.120 + i++;
9.121 + if (i >= argc || strchr(argv[i], '=') == NULL) {
9.122 + fprintf(stderr,
9.123 + "Usage: razor install [OPTION...] RPM\n");
9.124 + fprintf(stderr, "Options:\n");
9.125 + fprintf(stderr, " [--no-dependencies]\n");
9.126 + fprintf(stderr,
9.127 + " [--relocate OLDPATH=NEWPATH] RPM\n");
9.128 + return -1;
9.129 + }
9.130 + len = strchr(argv[i], '=') - argv[i];
9.131 + oldpath = malloc(len + 1);
9.132 + strncpy(oldpath, argv[i], len);
9.133 + oldpath[len] = '\0';
9.134 + if (!relocations)
9.135 + relocations = razor_relocations_create();
9.136 + razor_relocations_add(relocations, oldpath,
9.137 + argv[i] + len + 1);
9.138 + free(oldpath);
9.139 + } else
9.140 + break;
9.141 + }
9.142 +
9.143 system = razor_root_get_system_set(root);
9.144 upstream = razor_set_open(rawhide_repo_filename);
9.145 if (upstream == NULL ||
9.146 @@ -818,6 +910,12 @@
9.147 return 1;
9.148 }
9.149
9.150 + if (relocations) {
9.151 + set = relocate_packages(upstream, relocations);
9.152 + razor_set_destroy(upstream);
9.153 + upstream = set;
9.154 + }
9.155 +
9.156 trans = razor_transaction_create(system, upstream);
9.157
9.158 for (; i < argc; i++) {
9.159 @@ -851,8 +949,10 @@
9.160 return 1;
9.161 }
9.162
9.163 - install_packages(system, next);
9.164 + install_packages(system, next, relocations);
9.165
9.166 + if (relocations)
9.167 + razor_relocations_destroy(relocations);
9.168 razor_set_destroy(next);
9.169 razor_set_destroy(upstream);
9.170
10.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
10.2 +++ b/test/Makefile.am Thu Jan 22 22:54:45 2009 +0000
10.3 @@ -0,0 +1,30 @@
10.4 +## Process this file with automake to produce Makefile.in
10.5 +
10.6 +check_SCRIPTS = relocate
10.7 +
10.8 +relocate: relocate.sh primary.xml.gz
10.9 + cp $(srcdir)/relocate.sh relocate
10.10 +
10.11 +primary.xml.gz: zsh.spec zip.spec zap.spec Makefile
10.12 + rm -rf rpmbuild rpms repodata
10.13 + mkdir -p rpmbuild/BUILD rpmbuild/RPMS
10.14 + rpmbuild --define "_topdir `pwd`/rpmbuild" -bb $(srcdir)/zap.spec
10.15 + rpmbuild --define "_topdir `pwd`/rpmbuild" -bb $(srcdir)/zip.spec
10.16 + rpmbuild --define "_topdir `pwd`/rpmbuild" -bb $(srcdir)/zsh.spec
10.17 + mkdir rpms
10.18 + mv rpmbuild/RPMS/noarch/*.rpm rpms
10.19 + rm -rf rpmbuild
10.20 + createrepo -o . rpms
10.21 + cp repodata/primary.xml.gz repodata/filelists.xml.gz .
10.22 +
10.23 +TESTS = $(check_SCRIPTS)
10.24 +
10.25 +EXTRA_DIST = \
10.26 + zap.spec \
10.27 + zip.spec \
10.28 + zsh.spec \
10.29 + relocate.sh
10.30 +
10.31 +clean-local :
10.32 + rm -f *~
10.33 +
11.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
11.2 +++ b/test/relocate.sh Thu Jan 22 22:54:45 2009 +0000
11.3 @@ -0,0 +1,24 @@
11.4 +#!/bin/sh
11.5 +check_file()
11.6 +{
11.7 + ../src/razor list-files | grep -x "$1" > /dev/null
11.8 + if [ $? -ne 0 ]; then
11.9 + echo $1: Not in database >&2
11.10 + exit 1
11.11 + fi
11.12 + if [ ! -e "$RAZOR_ROOT$1" ]; then
11.13 + echo $1: Not in filesystem >&2
11.14 + exit 1
11.15 + fi
11.16 +}
11.17 +export RAZOR_ROOT=`mktemp -dt` || exit 1
11.18 +../src/razor init || exit 1
11.19 +export YUM_URL="file://localhost/`pwd`"
11.20 +../src/razor import-yum || exit 1
11.21 +../src/razor install zap || exit 1
11.22 +../src/razor install --relocate /usr=/opt --relocate /etc=/opt/etc zsh || exit 1
11.23 +check_file /etc/zsh.conf
11.24 +check_file /usr/bin/zap
11.25 +check_file /opt/bin/zip
11.26 +check_file /opt/bin/zsh
11.27 +rm -rf "$RAZOR_ROOT"
12.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
12.2 +++ b/test/zap.spec Thu Jan 22 22:54:45 2009 +0000
12.3 @@ -0,0 +1,26 @@
12.4 +Name: zap
12.5 +Summary: Test package
12.6 +Group: Test
12.7 +License: GPL
12.8 +Version: 1
12.9 +Release: 1
12.10 +Source: zap.tar
12.11 +BuildArch: noarch
12.12 +BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
12.13 +Prefix: /usr
12.14 +
12.15 +%description
12.16 +Test package
12.17 +
12.18 +%prep
12.19 +
12.20 +%build
12.21 +
12.22 +%install
12.23 +mkdir -p $RPM_BUILD_ROOT/usr/bin
12.24 +touch $RPM_BUILD_ROOT/usr/bin/zap
12.25 +
12.26 +%clean
12.27 +
12.28 +%files
12.29 +/usr/bin/zap
13.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
13.2 +++ b/test/zip.spec Thu Jan 22 22:54:45 2009 +0000
13.3 @@ -0,0 +1,27 @@
13.4 +Name: zip
13.5 +Summary: Test package
13.6 +Group: Test
13.7 +License: GPL
13.8 +Version: 1
13.9 +Release: 1
13.10 +Source: zip.tar
13.11 +BuildArch: noarch
13.12 +BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
13.13 +Prefix: /usr
13.14 +Requires: zap
13.15 +
13.16 +%description
13.17 +Test package
13.18 +
13.19 +%prep
13.20 +
13.21 +%build
13.22 +
13.23 +%install
13.24 +mkdir -p $RPM_BUILD_ROOT/usr/bin
13.25 +touch $RPM_BUILD_ROOT/usr/bin/zip
13.26 +
13.27 +%clean
13.28 +
13.29 +%files
13.30 +/usr/bin/zip
14.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
14.2 +++ b/test/zsh.spec Thu Jan 22 22:54:45 2009 +0000
14.3 @@ -0,0 +1,30 @@
14.4 +Name: zsh
14.5 +Summary: Test package
14.6 +Group: Test
14.7 +License: GPL
14.8 +Version: 1
14.9 +Release: 1
14.10 +Source: zsh.tar
14.11 +BuildArch: noarch
14.12 +BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
14.13 +Prefix: /usr
14.14 +Requires: zip
14.15 +
14.16 +%description
14.17 +Test package
14.18 +
14.19 +%prep
14.20 +
14.21 +%build
14.22 +
14.23 +%install
14.24 +mkdir -p $RPM_BUILD_ROOT/usr/bin
14.25 +mkdir -p $RPM_BUILD_ROOT/etc
14.26 +touch $RPM_BUILD_ROOT/usr/bin/zsh
14.27 +touch $RPM_BUILD_ROOT/etc/zsh.conf
14.28 +
14.29 +%clean
14.30 +
14.31 +%files
14.32 +/usr/bin/zsh
14.33 +/etc/zsh.conf