+#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
+#include <unistd.h>
+#include "lib/package.h"
#include "rpmlib.h"
#include "query.h"
void printHeader(Header h, int queryFlags);
+char * getString(Header h, int tag, char * def);
+void showMatches(rpmdb db, dbIndexSet matches, int queryFlags);
+
+char * getString(Header h, int tag, char * def) {
+ char * str;
+ int count, type;
+
+ if (!getEntry(h, tag, &type, (void **) &str, &count)) {
+ return def;
+ }
+
+ return str;
+}
void printHeader(Header h, int queryFlags) {
char * name, * version, * release;
printf("%s-%s-%s\n", name, version, release);
} else {
if (queryFlags & QUERY_FOR_INFO) {
- getEntry(h, RPMTAG_DISTRIBUTION, &type, (void **) &distribution,
- &count);
- getEntry(h, RPMTAG_DESCRIPTION, &type, (void **) &description,
- &count);
- getEntry(h, RPMTAG_BUILDHOST, &type, (void **) &buildHost, &count);
- getEntry(h, RPMTAG_VENDOR, &type, (void **) &vendor, &count);
- getEntry(h, RPMTAG_GROUP, &type, (void **) &group, &count);
- getEntry(h, RPMTAG_SIZE, &type, (void **) &size, &count);
+ distribution = getString(h, RPMTAG_DISTRIBUTION, "");
+ description = getString(h, RPMTAG_DESCRIPTION, "");
+ buildHost = getString(h, RPMTAG_BUILDHOST, "");
+ vendor = getString(h, RPMTAG_VENDOR, "");
+ group = getString(h, RPMTAG_GROUP, "Unknown");
+ if (!getEntry(h, RPMTAG_SIZE, &type, (void **) &size, &count))
+ size = NULL;
getEntry(h, RPMTAG_BUILDTIME, &type, (void **) &pBuildDate, &count);
tstruct = localtime((time_t *) pBuildDate);
printf("Release : %-27s Build Date: %s\n", release, buildDateStr);
printf("Install date: %-27s Build Host: %s\n", "", buildHost);
printf("Group : %s\n", group);
- printf("Size : %d\n", *size);
+ if (size)
+ printf("Size : %d\n", *size);
+ else
+ printf("Size : (unknown)\n");
printf("Description : %s\n", description);
prefix = " ";
}
if (queryFlags & QUERY_FOR_LIST) {
- getEntry(h, RPMTAG_FILENAMES, &type, (void **) &fileList, &count);
- getEntry(h, RPMTAG_FILESTATES, &type,
- (void **) &fileStatesList, &count);
- getEntry(h, RPMTAG_FILEFLAGS, &type,
- (void **) &fileFlagsList, &count);
-
- for (i = 0; i < count; i++) {
- if (!((queryFlags & QUERY_FOR_DOCS) ||
- (queryFlags & QUERY_FOR_CONFIG))
- || ((queryFlags & QUERY_FOR_DOCS) &&
- (fileFlagsList[i] & RPMFILE_DOC))
- || ((queryFlags & QUERY_FOR_CONFIG) &&
- (fileFlagsList[i] & RPMFILE_CONFIG))) {
-
- prefix ? fputs(prefix, stdout) : 0;
- if (queryFlags & QUERY_FOR_STATE) {
- switch (fileStatesList[i]) {
- case RPMFILE_STATE_NORMAL:
- fputs("normal ", stdout); break;
- case RPMFILE_STATE_REPLACED:
- fputs("replaced ", stdout); break;
- default:
- fputs("unknown ", stdout);
+ if (!getEntry(h, RPMTAG_FILENAMES, &type, (void **) &fileList,
+ &count)) {
+ puts("(contains no files)");
+ } else {
+ getEntry(h, RPMTAG_FILESTATES, &type,
+ (void **) &fileStatesList, &count);
+ getEntry(h, RPMTAG_FILEFLAGS, &type,
+ (void **) &fileFlagsList, &count);
+
+ for (i = 0; i < count; i++) {
+ if (!((queryFlags & QUERY_FOR_DOCS) ||
+ (queryFlags & QUERY_FOR_CONFIG))
+ || ((queryFlags & QUERY_FOR_DOCS) &&
+ (fileFlagsList[i] & RPMFILE_DOC))
+ || ((queryFlags & QUERY_FOR_CONFIG) &&
+ (fileFlagsList[i] & RPMFILE_CONFIG))) {
+
+ prefix ? fputs(prefix, stdout) : 0;
+ if (queryFlags & QUERY_FOR_STATE) {
+ switch (fileStatesList[i]) {
+ case RPMFILE_STATE_NORMAL:
+ fputs("normal ", stdout); break;
+ case RPMFILE_STATE_REPLACED:
+ fputs("replaced ", stdout); break;
+ default:
+ fputs("unknown ", stdout);
+ }
}
+
+ puts(fileList[i]);
}
-
- puts(fileList[i]);
}
- }
- /*free(fileList);
- free(fileStatesList);
- free(fileFlagsList);*/
+ free(fileList);
+ }
}
+ }
+}
-/*
- for (i = 0; i < package.fileCount; i++) {
- if (queryFlags & QUERY_FOR_STATE)
- printf("%s%-9s%s\n", prefix,
- rpmfileStateStrs[package.files[i].state],
- package.files[i].path);
- else
- printf("%s%s\n", prefix, package.files[i].path);
- }
- }
-*/
+void showMatches(rpmdb db, dbIndexSet matches, int queryFlags) {
+ int i;
+ Header h;
+
+ for (i = 0; i < matches.count; i++) {
+ h = rpmdbGetRecord(db, matches.recs[i].recOffset);
+ if (!h) {
+ fprintf(stderr, "error: could not read database record\n");
+ } else {
+ printHeader(h, queryFlags);
+ freeHeader(h);
+ }
}
}
char * arg) {
Header h;
int offset;
- int i;
+ int fd;
+ int rc;
+ int isSource;
rpmdb db;
dbIndexSet matches;
- if (!rpmdbOpen(prefix, &db, O_RDWR, 0644)) {
+ if (!rpmdbOpen(prefix, &db, O_RDONLY, 0644)) {
fprintf(stderr, "cannot open %s/var/lib/rpm/packages.rpm\n", prefix);
exit(1);
}
switch (source) {
case QUERY_SRPM:
case QUERY_RPM:
- printf("not yet\n");
- exit(1);
+ fd = open(arg, O_RDONLY);
+ if (!fd) {
+ fprintf(stderr, "open of %s failed: %s\n", arg, strerror(errno));
+ } else {
+ rc = pkgReadHeader(fd, &h, &isSource);
+ close(fd);
+ switch (rc) {
+ case 0:
+ printHeader(h, queryFlags);
+ freeHeader(h);
+ break;
+ case 1:
+ fprintf(stderr, "%s is not an RPM\n", arg);
+ }
+ }
+
break;
case QUERY_ALL:
}
break;
+ case QUERY_SGROUP:
+ case QUERY_GROUP:
+ if (rpmdbFindByGroup(db, arg, &matches)) {
+ fprintf(stderr, "group %s does not contain any pacakges\n", arg);
+ } else {
+ showMatches(db, matches, queryFlags);
+ freeDBIndexRecord(matches);
+ }
+ break;
+
case QUERY_SPATH:
case QUERY_PATH:
if (rpmdbFindByFile(db, arg, &matches)) {
- fprintf(stderr, "file %s is not owned by and package\n", arg);
+ fprintf(stderr, "file %s is not owned by any package\n", arg);
} else {
- for (i = 0; i < matches.count; i++) {
- h = rpmdbGetRecord(db, matches.recs[i].recOffset);
- if (!h) {
- fprintf(stderr, "error: could not read database record\n");
- } else {
- printHeader(h, queryFlags);
- freeHeader(h);
- }
- }
+ showMatches(db, matches, queryFlags);
+ freeDBIndexRecord(matches);
}
break;
case QUERY_SPACKAGE:
case QUERY_PACKAGE:
- printf("not yet\n");
- exit(1);
+ if (rpmdbFindPackage(db, arg, &matches)) {
+ fprintf(stderr, "package %s is not installed\n", arg);
+ } else {
+ showMatches(db, matches, queryFlags);
+ freeDBIndexRecord(matches);
+ }
break;
}