178 lines
3.6 KiB
C
178 lines
3.6 KiB
C
#include "system.h"
|
|
|
|
#include "rpmbuild.h"
|
|
#include "buildio.h"
|
|
|
|
#include "depends.h"
|
|
#include "header.h"
|
|
|
|
extern int _depends_debug;
|
|
|
|
static int
|
|
do_tsort(const char *fileArgv[])
|
|
{
|
|
const char * rootdir = "/";
|
|
const char ** fileURL;
|
|
int numPkgs;
|
|
int numFailed = 0;
|
|
rpmdb rpmdb = NULL;
|
|
rpmTransactionSet ts = NULL;
|
|
Header h;
|
|
int rc;
|
|
|
|
if (fileArgv == NULL)
|
|
return 0;
|
|
|
|
if (rpmdbOpen(rootdir, &rpmdb, O_RDONLY, 0644)) {
|
|
rpmMessage(RPMMESS_ERROR, _("cannot open Packages database\n"));
|
|
rc = -1;
|
|
goto exit;
|
|
}
|
|
|
|
ts = rpmtransCreateSet(rpmdb, rootdir);
|
|
|
|
for (fileURL = fileArgv, numPkgs = 0; *fileURL; fileURL++, numPkgs++)
|
|
;
|
|
|
|
for (fileURL = fileArgv; *fileURL; fileURL++) {
|
|
const char * fileName;
|
|
FD_t fd;
|
|
|
|
(void) urlPath(*fileURL, &fileName);
|
|
fd = Fopen(*fileURL, "r.ufdio");
|
|
if (fd == NULL || Ferror(fd)) {
|
|
rpmMessage(RPMMESS_ERROR, _("cannot open file %s: %s\n"), *fileURL,
|
|
Fstrerror(fd));
|
|
if (fd) Fclose(fd);
|
|
numFailed++;
|
|
continue;
|
|
}
|
|
|
|
rc = rpmReadPackageHeader(fd, &h, NULL, NULL, NULL);
|
|
|
|
rc = rpmtransAddPackage(ts, h, NULL, fileName, 0, NULL);
|
|
|
|
headerFree(h); /* XXX reference held by transaction set */
|
|
Fclose(fd);
|
|
|
|
}
|
|
|
|
{ struct rpmDependencyConflict * conflicts = NULL;
|
|
int numConflicts = 0;
|
|
|
|
rc = rpmdepCheck(ts, &conflicts, &numConflicts);
|
|
|
|
if (conflicts) {
|
|
rpmMessage(RPMMESS_ERROR, _("failed dependencies:\n"));
|
|
printDepProblems(stderr, conflicts, numConflicts);
|
|
rpmdepFreeConflicts(conflicts, numConflicts);
|
|
rc = -1;
|
|
goto exit;
|
|
}
|
|
}
|
|
|
|
rc = rpmdepOrder(ts);
|
|
if (rc)
|
|
goto exit;
|
|
|
|
{ int oc;
|
|
for (oc = 0; oc < ts->orderCount; oc++) {
|
|
struct availablePackage *alp;
|
|
rpmdbMatchIterator mi;
|
|
const char * str;
|
|
int i;
|
|
|
|
str = "???";
|
|
switch (ts->order[oc].type) {
|
|
case TR_ADDED:
|
|
i = ts->order[oc].u.addedIndex;
|
|
alp = ts->addedPackages.list + ts->order[oc].u.addedIndex;
|
|
h = headerLink(alp->h);
|
|
str = "+++";
|
|
break;
|
|
case TR_REMOVED:
|
|
i = ts->order[oc].u.removed.dboffset;
|
|
mi = rpmdbInitIterator(ts->rpmdb, RPMDBI_PACKAGES, &i, sizeof(i));
|
|
h = rpmdbNextIterator(mi);
|
|
if (h)
|
|
h = headerLink(h);
|
|
rpmdbFreeIterator(mi);
|
|
str = "---";
|
|
break;
|
|
}
|
|
|
|
if (h) {
|
|
const char *n, *v, *r;
|
|
headerNVR(h, &n, &v, &r);
|
|
fprintf(stdout, "%s %s-%s-%s\n", str, n, v, r);
|
|
headerFree(h);
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
rc = 0;
|
|
|
|
exit:
|
|
if (ts) {
|
|
rpmtransFree(ts);
|
|
ts = NULL;
|
|
}
|
|
if (rpmdb) {
|
|
rpmdbClose(rpmdb);
|
|
rpmdb = NULL;
|
|
}
|
|
return rc;
|
|
}
|
|
|
|
static struct poptOption optionsTable[] = {
|
|
{ "verbose", 'v', 0, 0, 'v', NULL, NULL},
|
|
{ NULL, 0, 0, 0, 0, NULL, NULL}
|
|
};
|
|
|
|
int
|
|
main(int argc, const char *argv[])
|
|
{
|
|
poptContext optCon;
|
|
const char * optArg;
|
|
int arg;
|
|
int ec = 0;
|
|
|
|
#if HAVE_MCHECK_H && HAVE_MTRACE
|
|
mtrace(); /* Trace malloc only if MALLOC_TRACE=mtrace-output-file. */
|
|
#endif
|
|
setprogname(argv[0]); /* Retrofit glibc __progname */
|
|
(void)setlocale(LC_ALL, "" );
|
|
|
|
#ifdef __LCLINT__
|
|
#define LOCALEDIR "/usr/share/locale"
|
|
#endif
|
|
(void)bindtextdomain(PACKAGE, LOCALEDIR);
|
|
(void)textdomain(PACKAGE);
|
|
|
|
_depends_debug = 1;
|
|
|
|
optCon = poptGetContext("rpmsort", argc, argv, optionsTable, 0);
|
|
poptReadDefaultConfig(optCon, 1);
|
|
|
|
while ((arg = poptGetNextOpt(optCon)) > 0) {
|
|
optArg = poptGetOptArg(optCon);
|
|
switch (arg) {
|
|
case 'v':
|
|
rpmIncreaseVerbosity();
|
|
break;
|
|
default:
|
|
errx(EXIT_FAILURE, _("unknown popt return (%d)"), arg);
|
|
/*@notreached@*/ break;
|
|
}
|
|
}
|
|
|
|
rpmReadConfigFiles(NULL, NULL);
|
|
|
|
ec = do_tsort(poptGetArgs(optCon));
|
|
|
|
poptFreeContext(optCon);
|
|
|
|
return ec;
|
|
}
|