648 lines
17 KiB
C
648 lines
17 KiB
C
#include "config.h"
|
|
|
|
#if HAVE_ALLOCA_H
|
|
# include <alloca.h>
|
|
#endif
|
|
|
|
#include <fcntl.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
#include <sys/file.h>
|
|
#include <signal.h>
|
|
#include <sys/signal.h>
|
|
#include <unistd.h>
|
|
|
|
#include "dbindex.h"
|
|
#include "falloc.h"
|
|
#include "header.h"
|
|
#include "misc.h"
|
|
#include "rpmdb.h"
|
|
#include "rpmlib.h"
|
|
#include "messages.h"
|
|
|
|
/* XXX the signal handling in here is not thread safe */
|
|
|
|
/* the requiredbyIndex isn't stricly necessary. In a perfect world, we could
|
|
have each header keep a list of packages that need it. However, we
|
|
can't reserve space in the header for extra information so all of the
|
|
required packages would move in the database every time a package was
|
|
added or removed. Instead, each package (or virtual package) name
|
|
keeps a list of package offsets of packages that might depend on this
|
|
one. Version numbers still need verification, but it gets us in the
|
|
right area w/o a linear search through the database. */
|
|
|
|
struct rpmdb {
|
|
faFile pkgs;
|
|
dbiIndex * nameIndex, * fileIndex, * groupIndex, * providesIndex;
|
|
dbiIndex * requiredbyIndex, * conflictsIndex;
|
|
};
|
|
|
|
static void removeIndexEntry(dbiIndex * dbi, char * name, dbiIndexRecord rec,
|
|
int tolerant, char * idxName);
|
|
static int addIndexEntry(dbiIndex * idx, char * index, unsigned int offset,
|
|
unsigned int fileNumber);
|
|
static void blockSignals(void);
|
|
static void unblockSignals(void);
|
|
|
|
static sigset_t signalMask;
|
|
|
|
int rpmdbOpen (char * prefix, rpmdb *rpmdbp, int mode, int perms) {
|
|
char * dbpath;
|
|
|
|
dbpath = rpmGetVar(RPMVAR_DBPATH);
|
|
if (!dbpath) {
|
|
rpmMessage(RPMMESS_DEBUG, "no dbpath has been set");
|
|
return 1;
|
|
}
|
|
|
|
return openDatabase(prefix, dbpath, rpmdbp, mode, perms, 0);
|
|
}
|
|
|
|
int rpmdbInit (char * prefix, int perms) {
|
|
rpmdb db;
|
|
char * dbpath;
|
|
|
|
dbpath = rpmGetVar(RPMVAR_DBPATH);
|
|
if (!dbpath) {
|
|
rpmMessage(RPMMESS_DEBUG, "no dbpath has been set");
|
|
return 1;
|
|
}
|
|
|
|
return openDatabase(prefix, dbpath, &db, O_CREAT | O_RDWR, perms, 1);
|
|
}
|
|
|
|
int openDatabase(char * prefix, char * dbpath, rpmdb *rpmdbp, int mode,
|
|
int perms, int justcheck) {
|
|
char * filename;
|
|
struct rpmdb db;
|
|
int i;
|
|
struct flock lockinfo;
|
|
|
|
i = strlen(dbpath);
|
|
if (dbpath[i - 1] != '/') {
|
|
filename = alloca(i + 2);
|
|
strcpy(filename, dbpath);
|
|
filename[i] = '/';
|
|
filename[i + 1] = '\0';
|
|
dbpath = filename;
|
|
}
|
|
|
|
filename = alloca(strlen(prefix) + strlen(dbpath) + 40);
|
|
|
|
if (mode & O_WRONLY)
|
|
return 1;
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
|
|
rpmMessage(RPMMESS_DEBUG, "opening database in %s\n", filename);
|
|
|
|
strcat(filename, "packages.rpm");
|
|
|
|
memset(&db, 0, sizeof(db));
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.pkgs = faOpen(filename, mode, 0644);
|
|
if (!db.pkgs) {
|
|
rpmError(RPMERR_DBOPEN, "failed to open %s\n", filename);
|
|
return 1;
|
|
}
|
|
|
|
/* try and get a lock - this is released by the kernel when we close
|
|
the file */
|
|
lockinfo.l_whence = 0;
|
|
lockinfo.l_start = 0;
|
|
lockinfo.l_len = 0;
|
|
|
|
if (mode & O_RDWR) {
|
|
lockinfo.l_type = F_WRLCK;
|
|
if (fcntl(db.pkgs->fd, F_SETLK, (void *) &lockinfo)) {
|
|
rpmError(RPMERR_FLOCK, "cannot get %s lock on database",
|
|
"exclusive");
|
|
return 1;
|
|
}
|
|
} else {
|
|
lockinfo.l_type = F_RDLCK;
|
|
if (fcntl(db.pkgs->fd, F_SETLK, (void *) &lockinfo)) {
|
|
rpmError(RPMERR_FLOCK, "cannot get %s lock on database", "shared");
|
|
return 1;
|
|
}
|
|
}
|
|
}
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
strcat(filename, "nameindex.rpm");
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.nameIndex = dbiOpenIndex(filename, mode, 0644);
|
|
if (!db.nameIndex) {
|
|
faClose(db.pkgs);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
strcat(filename, "fileindex.rpm");
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.fileIndex = dbiOpenIndex(filename, mode, 0644);
|
|
if (!db.fileIndex) {
|
|
faClose(db.pkgs);
|
|
dbiCloseIndex(db.nameIndex);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
strcat(filename, "groupindex.rpm");
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.groupIndex = dbiOpenIndex(filename, mode, 0644);
|
|
if (!db.groupIndex) {
|
|
faClose(db.pkgs);
|
|
dbiCloseIndex(db.nameIndex);
|
|
dbiCloseIndex(db.fileIndex);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
strcat(filename, "providesindex.rpm");
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.providesIndex = dbiOpenIndex(filename, mode, 0644);
|
|
if (!db.providesIndex) {
|
|
faClose(db.pkgs);
|
|
dbiCloseIndex(db.fileIndex);
|
|
dbiCloseIndex(db.nameIndex);
|
|
dbiCloseIndex(db.groupIndex);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
strcat(filename, "requiredby.rpm");
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.requiredbyIndex = dbiOpenIndex(filename, mode, 0644);
|
|
if (!db.requiredbyIndex) {
|
|
faClose(db.pkgs);
|
|
dbiCloseIndex(db.fileIndex);
|
|
dbiCloseIndex(db.nameIndex);
|
|
dbiCloseIndex(db.groupIndex);
|
|
dbiCloseIndex(db.providesIndex);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
strcpy(filename, prefix);
|
|
strcat(filename, dbpath);
|
|
strcat(filename, "conflictsindex.rpm");
|
|
|
|
if (!justcheck || !exists(filename)) {
|
|
db.conflictsIndex = dbiOpenIndex(filename, mode, 0644);
|
|
if (!db.conflictsIndex) {
|
|
faClose(db.pkgs);
|
|
dbiCloseIndex(db.fileIndex);
|
|
dbiCloseIndex(db.nameIndex);
|
|
dbiCloseIndex(db.groupIndex);
|
|
dbiCloseIndex(db.providesIndex);
|
|
dbiCloseIndex(db.requiredbyIndex);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
*rpmdbp = malloc(sizeof(struct rpmdb));
|
|
**rpmdbp = db;
|
|
|
|
if (justcheck) {
|
|
rpmdbClose(*rpmdbp);
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
void rpmdbClose (rpmdb db) {
|
|
if (db->pkgs) faClose(db->pkgs);
|
|
if (db->fileIndex) dbiCloseIndex(db->fileIndex);
|
|
if (db->groupIndex) dbiCloseIndex(db->groupIndex);
|
|
if (db->nameIndex) dbiCloseIndex(db->nameIndex);
|
|
if (db->providesIndex) dbiCloseIndex(db->providesIndex);
|
|
if (db->requiredbyIndex) dbiCloseIndex(db->requiredbyIndex);
|
|
if (db->conflictsIndex) dbiCloseIndex(db->conflictsIndex);
|
|
free(db);
|
|
}
|
|
|
|
int rpmdbFirstRecNum(rpmdb db) {
|
|
return faFirstOffset(db->pkgs);
|
|
}
|
|
|
|
int rpmdbNextRecNum(rpmdb db, unsigned int lastOffset) {
|
|
/* 0 at end */
|
|
return faNextOffset(db->pkgs, lastOffset);
|
|
}
|
|
|
|
Header rpmdbGetRecord(rpmdb db, unsigned int offset) {
|
|
lseek(db->pkgs->fd, offset, SEEK_SET);
|
|
|
|
return headerRead(db->pkgs->fd, HEADER_MAGIC_NO);
|
|
}
|
|
|
|
int rpmdbFindByFile(rpmdb db, char * filespec, dbiIndexSet * matches) {
|
|
return dbiSearchIndex(db->fileIndex, filespec, matches);
|
|
}
|
|
|
|
int rpmdbFindByProvides(rpmdb db, char * filespec, dbiIndexSet * matches) {
|
|
return dbiSearchIndex(db->providesIndex, filespec, matches);
|
|
}
|
|
|
|
int rpmdbFindByRequiredBy(rpmdb db, char * filespec, dbiIndexSet * matches) {
|
|
return dbiSearchIndex(db->requiredbyIndex, filespec, matches);
|
|
}
|
|
|
|
int rpmdbFindByConflicts(rpmdb db, char * filespec, dbiIndexSet * matches) {
|
|
return dbiSearchIndex(db->conflictsIndex, filespec, matches);
|
|
}
|
|
|
|
int rpmdbFindByGroup(rpmdb db, char * group, dbiIndexSet * matches) {
|
|
return dbiSearchIndex(db->groupIndex, group, matches);
|
|
}
|
|
|
|
int rpmdbFindPackage(rpmdb db, char * name, dbiIndexSet * matches) {
|
|
return dbiSearchIndex(db->nameIndex, name, matches);
|
|
}
|
|
|
|
static void removeIndexEntry(dbiIndex * dbi, char * key, dbiIndexRecord rec,
|
|
int tolerant, char * idxName) {
|
|
int rc;
|
|
dbiIndexSet matches;
|
|
|
|
rc = dbiSearchIndex(dbi, key, &matches);
|
|
switch (rc) {
|
|
case 0:
|
|
if (dbiRemoveIndexRecord(&matches, rec) && !tolerant) {
|
|
rpmError(RPMERR_DBCORRUPT, "package %s not listed in %s",
|
|
key, idxName);
|
|
} else {
|
|
dbiUpdateIndex(dbi, key, &matches);
|
|
/* errors from above will be reported from dbindex.c */
|
|
}
|
|
break;
|
|
case 1:
|
|
if (!tolerant)
|
|
rpmError(RPMERR_DBCORRUPT, "package %s not found in %s", key, idxName);
|
|
break;
|
|
case 2:
|
|
break; /* error message already generated from dbindex.c */
|
|
}
|
|
|
|
dbiFreeIndexRecord(matches);
|
|
}
|
|
|
|
int rpmdbRemove(rpmdb db, unsigned int offset, int tolerant) {
|
|
Header h;
|
|
char * name, * group;
|
|
int type;
|
|
unsigned int count;
|
|
dbiIndexRecord rec;
|
|
char ** fileList, ** providesList, ** requiredbyList;
|
|
char ** conflictList;
|
|
int i;
|
|
|
|
rec.recOffset = offset;
|
|
rec.fileNumber = 0;
|
|
|
|
h = rpmdbGetRecord(db, offset);
|
|
if (!h) {
|
|
rpmError(RPMERR_DBCORRUPT, "cannot read header at %d for uninstall",
|
|
offset);
|
|
return 1;
|
|
}
|
|
|
|
blockSignals();
|
|
|
|
if (!headerGetEntry(h, RPMTAG_NAME, &type, (void **) &name, &count)) {
|
|
rpmError(RPMERR_DBCORRUPT, "package has no name");
|
|
} else {
|
|
rpmMessage(RPMMESS_DEBUG, "removing name index\n");
|
|
removeIndexEntry(db->nameIndex, name, rec, tolerant, "name index");
|
|
}
|
|
|
|
if (!headerGetEntry(h, RPMTAG_GROUP, &type, (void **) &group, &count)) {
|
|
rpmMessage(RPMMESS_DEBUG, "package has no group\n");
|
|
} else {
|
|
rpmMessage(RPMMESS_DEBUG, "removing group index\n");
|
|
removeIndexEntry(db->groupIndex, group, rec, tolerant, "group index");
|
|
}
|
|
|
|
if (headerGetEntry(h, RPMTAG_PROVIDES, &type, (void **) &providesList,
|
|
&count)) {
|
|
for (i = 0; i < count; i++) {
|
|
rpmMessage(RPMMESS_DEBUG, "removing provides index for %s\n",
|
|
providesList[i]);
|
|
removeIndexEntry(db->providesIndex, providesList[i], rec, tolerant,
|
|
"providesfile index");
|
|
}
|
|
free(providesList);
|
|
}
|
|
|
|
if (headerGetEntry(h, RPMTAG_REQUIRENAME, &type, (void **) &requiredbyList,
|
|
&count)) {
|
|
for (i = 0; i < count; i++) {
|
|
rpmMessage(RPMMESS_DEBUG, "removing requiredby index for %s\n",
|
|
requiredbyList[i]);
|
|
removeIndexEntry(db->requiredbyIndex, requiredbyList[i], rec,
|
|
tolerant, "requiredby index");
|
|
}
|
|
free(requiredbyList);
|
|
}
|
|
|
|
if (headerGetEntry(h, RPMTAG_CONFLICTNAME, &type, (void **) &conflictList,
|
|
&count)) {
|
|
for (i = 0; i < count; i++) {
|
|
rpmMessage(RPMMESS_DEBUG, "removing conflict index for %s\n",
|
|
conflictList[i]);
|
|
removeIndexEntry(db->conflictsIndex, conflictList[i], rec,
|
|
tolerant, "conflict index");
|
|
}
|
|
free(conflictList);
|
|
}
|
|
|
|
if (headerGetEntry(h, RPMTAG_FILENAMES, &type, (void **) &fileList,
|
|
&count)) {
|
|
for (i = 0; i < count; i++) {
|
|
rpmMessage(RPMMESS_DEBUG, "removing file index for %s\n", fileList[i]);
|
|
rec.fileNumber = i;
|
|
removeIndexEntry(db->fileIndex, fileList[i], rec, tolerant,
|
|
"file index");
|
|
}
|
|
free(fileList);
|
|
} else {
|
|
rpmMessage(RPMMESS_DEBUG, "package has no files\n");
|
|
}
|
|
|
|
faFree(db->pkgs, offset);
|
|
|
|
dbiSyncIndex(db->nameIndex);
|
|
dbiSyncIndex(db->groupIndex);
|
|
dbiSyncIndex(db->fileIndex);
|
|
|
|
unblockSignals();
|
|
|
|
headerFree(h);
|
|
|
|
return 0;
|
|
}
|
|
|
|
static int addIndexEntry(dbiIndex * idx, char * index, unsigned int offset,
|
|
unsigned int fileNumber) {
|
|
dbiIndexSet set;
|
|
dbiIndexRecord irec;
|
|
int rc;
|
|
|
|
irec.recOffset = offset;
|
|
irec.fileNumber = fileNumber;
|
|
|
|
rc = dbiSearchIndex(idx, index, &set);
|
|
if (rc == -1) /* error */
|
|
return 1;
|
|
|
|
if (rc == 1) /* new item */
|
|
set = dbiCreateIndexRecord();
|
|
dbiAppendIndexRecord(&set, irec);
|
|
if (dbiUpdateIndex(idx, index, &set))
|
|
exit(1);
|
|
dbiFreeIndexRecord(set);
|
|
return 0;
|
|
}
|
|
|
|
int rpmdbAdd(rpmdb db, Header dbentry) {
|
|
unsigned int dboffset;
|
|
unsigned int i;
|
|
char ** fileList;
|
|
char ** providesList;
|
|
char ** requiredbyList;
|
|
char ** conflictList;
|
|
char * name, * group;
|
|
int count, providesCount, requiredbyCount, conflictCount;
|
|
int type;
|
|
int rc = 0;
|
|
|
|
headerGetEntry(dbentry, RPMTAG_NAME, &type, (void **) &name, &count);
|
|
headerGetEntry(dbentry, RPMTAG_GROUP, &type, (void **) &group, &count);
|
|
|
|
if (!group) group = "Unknown";
|
|
|
|
if (!headerGetEntry(dbentry, RPMTAG_FILENAMES, &type, (void **) &fileList,
|
|
&count)) {
|
|
count = 0;
|
|
}
|
|
|
|
if (!headerGetEntry(dbentry, RPMTAG_PROVIDES, &type, (void **) &providesList,
|
|
&providesCount)) {
|
|
providesCount = 0;
|
|
}
|
|
|
|
if (!headerGetEntry(dbentry, RPMTAG_REQUIRENAME, &type,
|
|
(void **) &requiredbyList, &requiredbyCount)) {
|
|
requiredbyCount = 0;
|
|
}
|
|
|
|
if (!headerGetEntry(dbentry, RPMTAG_CONFLICTNAME, &type,
|
|
(void **) &conflictList, &conflictCount)) {
|
|
conflictCount = 0;
|
|
}
|
|
|
|
blockSignals();
|
|
|
|
dboffset = faAlloc(db->pkgs, headerSizeof(dbentry, HEADER_MAGIC_NO));
|
|
if (!dboffset) {
|
|
rpmError(RPMERR_DBCORRUPT, "cannot allocate space for database");
|
|
unblockSignals();
|
|
if (providesCount) free(providesList);
|
|
if (requiredbyCount) free(requiredbyList);
|
|
if (count) free(fileList);
|
|
return 1;
|
|
}
|
|
lseek(db->pkgs->fd, dboffset, SEEK_SET);
|
|
|
|
headerWrite(db->pkgs->fd, dbentry, HEADER_MAGIC_NO);
|
|
|
|
/* Now update the appropriate indexes */
|
|
if (addIndexEntry(db->nameIndex, name, dboffset, 0))
|
|
rc = 1;
|
|
if (addIndexEntry(db->groupIndex, group, dboffset, 0))
|
|
rc = 1;
|
|
|
|
for (i = 0; i < conflictCount; i++) {
|
|
if (addIndexEntry(db->conflictsIndex, conflictList[i], dboffset, 0))
|
|
rc = 1;
|
|
}
|
|
|
|
for (i = 0; i < requiredbyCount; i++) {
|
|
if (addIndexEntry(db->requiredbyIndex, requiredbyList[i], dboffset, 0))
|
|
rc = 1;
|
|
}
|
|
|
|
for (i = 0; i < providesCount; i++) {
|
|
if (addIndexEntry(db->providesIndex, providesList[i], dboffset, 0))
|
|
rc = 1;
|
|
}
|
|
|
|
for (i = 0; i < count; i++) {
|
|
if (addIndexEntry(db->fileIndex, fileList[i], dboffset, i))
|
|
rc = 1;
|
|
}
|
|
|
|
dbiSyncIndex(db->nameIndex);
|
|
dbiSyncIndex(db->groupIndex);
|
|
dbiSyncIndex(db->fileIndex);
|
|
dbiSyncIndex(db->providesIndex);
|
|
dbiSyncIndex(db->requiredbyIndex);
|
|
|
|
unblockSignals();
|
|
|
|
if (requiredbyCount) free(requiredbyList);
|
|
if (providesCount) free(providesList);
|
|
if (count) free(fileList);
|
|
|
|
return rc;
|
|
}
|
|
|
|
int rpmdbUpdateRecord(rpmdb db, int offset, Header newHeader) {
|
|
Header oldHeader;
|
|
int oldSize;
|
|
|
|
oldHeader = rpmdbGetRecord(db, offset);
|
|
if (!oldHeader) {
|
|
rpmError(RPMERR_DBCORRUPT, "cannot read header at %d for update",
|
|
offset);
|
|
return 1;
|
|
}
|
|
|
|
oldSize = headerSizeof(oldHeader, HEADER_MAGIC_NO);
|
|
headerFree(oldHeader);
|
|
|
|
if (oldSize != headerSizeof(newHeader, HEADER_MAGIC_NO)) {
|
|
rpmMessage(RPMMESS_DEBUG, "header changed size!");
|
|
if (rpmdbRemove(db, offset, 1))
|
|
return 1;
|
|
|
|
if (rpmdbAdd(db, newHeader))
|
|
return 1;
|
|
} else {
|
|
blockSignals();
|
|
|
|
lseek(db->pkgs->fd, offset, SEEK_SET);
|
|
|
|
headerWrite(db->pkgs->fd, newHeader, HEADER_MAGIC_NO);
|
|
|
|
unblockSignals();
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
static void blockSignals(void) {
|
|
sigset_t newMask;
|
|
|
|
sigfillset(&newMask); /* block all signals */
|
|
sigprocmask(SIG_BLOCK, &newMask, &signalMask);
|
|
}
|
|
|
|
static void unblockSignals(void) {
|
|
sigprocmask(SIG_SETMASK, &signalMask, NULL);
|
|
}
|
|
|
|
void rpmdbRemoveDatabase(char * rootdir, char * dbpath) {
|
|
int i;
|
|
char * filename;
|
|
|
|
i = strlen(dbpath);
|
|
if (dbpath[i - 1] != '/') {
|
|
filename = alloca(i);
|
|
strcpy(filename, dbpath);
|
|
filename[i] = '/';
|
|
filename[i + 1] = '\0';
|
|
dbpath = filename;
|
|
}
|
|
|
|
filename = alloca(strlen(rootdir) + strlen(dbpath) + 40);
|
|
|
|
sprintf(filename, "%s/%s/packages.rpm", rootdir, dbpath);
|
|
unlink(filename);
|
|
|
|
sprintf(filename, "%s/%s/nameindex.rpm", rootdir, dbpath);
|
|
unlink(filename);
|
|
|
|
sprintf(filename, "%s/%s/fileindex.rpm", rootdir, dbpath);
|
|
unlink(filename);
|
|
|
|
sprintf(filename, "%s/%s/groupindex.rpm", rootdir, dbpath);
|
|
unlink(filename);
|
|
|
|
sprintf(filename, "%s/%s/requiredby.rpm", rootdir, dbpath);
|
|
unlink(filename);
|
|
|
|
sprintf(filename, "%s/%s/providesindex.rpm", rootdir, dbpath);
|
|
unlink(filename);
|
|
}
|
|
|
|
int rpmdbMoveDatabase(char * rootdir, char * olddbpath, char * newdbpath) {
|
|
int i;
|
|
char * ofilename, * nfilename;
|
|
int rc = 0;
|
|
|
|
i = strlen(olddbpath);
|
|
if (olddbpath[i - 1] != '/') {
|
|
ofilename = alloca(i + 2);
|
|
strcpy(ofilename, olddbpath);
|
|
ofilename[i] = '/';
|
|
ofilename[i + 1] = '\0';
|
|
olddbpath = ofilename;
|
|
}
|
|
|
|
i = strlen(newdbpath);
|
|
if (newdbpath[i - 1] != '/') {
|
|
nfilename = alloca(i + 2);
|
|
strcpy(nfilename, newdbpath);
|
|
nfilename[i] = '/';
|
|
nfilename[i + 1] = '\0';
|
|
newdbpath = nfilename;
|
|
}
|
|
|
|
ofilename = alloca(strlen(rootdir) + strlen(olddbpath) + 40);
|
|
nfilename = alloca(strlen(rootdir) + strlen(newdbpath) + 40);
|
|
|
|
sprintf(ofilename, "%s/%s/packages.rpm", rootdir, olddbpath);
|
|
sprintf(nfilename, "%s/%s/packages.rpm", rootdir, newdbpath);
|
|
if (rename(ofilename, nfilename)) rc = 1;
|
|
|
|
sprintf(ofilename, "%s/%s/nameindex.rpm", rootdir, olddbpath);
|
|
sprintf(nfilename, "%s/%s/nameindex.rpm", rootdir, newdbpath);
|
|
if (rename(ofilename, nfilename)) rc = 1;
|
|
|
|
sprintf(ofilename, "%s/%s/fileindex.rpm", rootdir, olddbpath);
|
|
sprintf(nfilename, "%s/%s/fileindex.rpm", rootdir, newdbpath);
|
|
if (rename(ofilename, nfilename)) rc = 1;
|
|
|
|
sprintf(ofilename, "%s/%s/groupindex.rpm", rootdir, olddbpath);
|
|
sprintf(nfilename, "%s/%s/groupindex.rpm", rootdir, newdbpath);
|
|
if (rename(ofilename, nfilename)) rc = 1;
|
|
|
|
sprintf(ofilename, "%s/%s/requiredby.rpm", rootdir, olddbpath);
|
|
sprintf(nfilename, "%s/%s/requiredby.rpm", rootdir, newdbpath);
|
|
if (rename(ofilename, nfilename)) rc = 1;
|
|
|
|
sprintf(ofilename, "%s/%s/providesindex.rpm", rootdir, olddbpath);
|
|
sprintf(nfilename, "%s/%s/providesindex.rpm", rootdir, newdbpath);
|
|
if (rename(ofilename, nfilename)) rc = 1;
|
|
|
|
return rc;
|
|
}
|