- Main Page
- Related Pages
- Modules
- Data Structures
- Files

# rpmqv.c

Go to the documentation of this file.

    00001 #include "system.h"
    00002 const char *__progname;
    00003
    00004 #define _AUTOHELP
    00005
    00006 #if defined(IAM_RPM)
    00007 #define IAM_RPMBT
    00008 #define IAM_RPMDB
    00009 #define IAM_RPMEIU
    00010 #define IAM_RPMQV
    00011 #define IAM_RPMK
    00012 #endif
    00013
    00014 #include <rpm/rpmcli.h>
    00015 #include <rpm/rpmlib.h>                 /* RPMSIGTAG, rpmReadPackageFile .. */
    00016 #include <rpm/rpmbuild.h>
    00017 #include <rpm/rpmlog.h>
    00018
    00019 #include <rpm/rpmdb.h>
    00020 #include <rpm/rpmps.h>
    00021 #include <rpm/rpmts.h>
    00022
    00023 #ifdef  IAM_RPMBT
    00024 #include "build.h"
    00025 #define GETOPT_REBUILD          1003
    00026 #define GETOPT_RECOMPILE        1004
    00027 #endif
    00028
    00029 #if defined(IAM_RPMBT) || defined(IAM_RPMK)
    00030 #include "lib/signature.h"
    00031 #endif
    00032
    00033 #include "debug.h"
    00034
    00035 enum modes {
    00036
    00037     MODE_QUERY          = (1 <<  0),
    00038     MODE_VERIFY         = (1 <<  3),
    00039 #define MODES_QV (MODE_QUERY | MODE_VERIFY)
    00040
    00041     MODE_INSTALL        = (1 <<  1),
    00042     MODE_ERASE          = (1 <<  2),
    00043 #define MODES_IE (MODE_INSTALL | MODE_ERASE)
    00044
    00045     MODE_BUILD          = (1 <<  4),
    00046     MODE_REBUILD        = (1 <<  5),
    00047     MODE_RECOMPILE      = (1 <<  8),
    00048     MODE_TARBUILD       = (1 << 11),
    00049 #define MODES_BT (MODE_BUILD | MODE_TARBUILD | MODE_REBUILD | MODE_RECOMPILE)
    00050
    00051     MODE_CHECKSIG       = (1 <<  6),
    00052     MODE_RESIGN         = (1 <<  7),
    00053 #define MODES_K  (MODE_CHECKSIG | MODE_RESIGN)
    00054
    00055     MODE_INITDB         = (1 << 10),
    00056     MODE_REBUILDDB      = (1 << 12),
    00057     MODE_VERIFYDB       = (1 << 13),
    00058 #define MODES_DB (MODE_INITDB | MODE_REBUILDDB | MODE_VERIFYDB)
    00059
    00060
    00061     MODE_UNKNOWN        = 0
    00062 };
    00063
    00064 #define MODES_FOR_DBPATH        (MODES_BT | MODES_IE | MODES_QV | MODES_DB)
    00065 #define MODES_FOR_NODEPS        (MODES_BT | MODES_IE | MODE_VERIFY)
    00066 #define MODES_FOR_TEST          (MODES_BT | MODES_IE)
    00067 #define MODES_FOR_ROOT          (MODES_BT | MODES_IE | MODES_QV | MODES_DB | MODES_K)
    00068
    00069 static int quiet;
    00070
    00071 /* the structure describing the options we take and the defaults */
    00072 static struct poptOption optionsTable[] = {
    00073
    00074 #ifdef  IAM_RPMQV
    00075  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmQueryPoptTable, 0,
    00076         N_("Query options (with -q or --query):"),
    00077         NULL },
    00078  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmVerifyPoptTable, 0,
    00079         N_("Verify options (with -V or --verify):"),
    00080         NULL },
    00081 #ifdef  NOTYET
    00082  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmcliQVSourcePoptTable, 0,
    00083         N_("Source options (with --query or --verify):"),
    00084         NULL },
    00085 #endif
    00086  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmcliFtsPoptTable, 0,
    00087         N_("File tree walk options (with --ftswalk):"),
    00088         NULL },
    00089 #endif  /* IAM_RPMQV */
    00090
    00091 #ifdef  IAM_RPMK
    00092  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmSignPoptTable, 0,
    00093         N_("Signature options:"),
    00094         NULL },
    00095 #endif  /* IAM_RPMK */
    00096
    00097 #ifdef  IAM_RPMDB
    00098  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmDatabasePoptTable, 0,
    00099         N_("Database options:"),
    00100         NULL },
    00101 #endif  /* IAM_RPMDB */
    00102
    00103 #ifdef  IAM_RPMBT
    00104  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmBuildPoptTable, 0,
    00105         N_("Build options with [ <specfile> | <tarball> | <source package> ]:"),
    00106         NULL },
    00107 #endif  /* IAM_RPMBT */
    00108
    00109 #ifdef  IAM_RPMEIU
    00110  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmInstallPoptTable, 0,
    00111         N_("Install/Upgrade/Erase options:"),
    00112         NULL },
    00113 #endif  /* IAM_RPMEIU */
    00114
    00115  { "quiet", '\0', 0, &quiet, 0,                 NULL, NULL},
    00116
    00117  { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmcliAllPoptTable, 0,
    00118         N_("Common options for all rpm modes and executables:"),
    00119         NULL },
    00120
    00121    POPT_AUTOALIAS
    00122    POPT_AUTOHELP
    00123    POPT_TABLEEND
    00124 };
    00125
    00126 #ifdef __MINT__
    00127 /* MiNT cannot dynamically increase the stack.  */
    00128 long _stksize = 64 * 1024L;
    00129 #endif
    00130
    00131 static void argerror(const char * desc)
    00132 {
    00133     fprintf(stderr, _("%s: %s\n"), __progname, desc);
    00134     exit(EXIT_FAILURE);
    00135 }
    00136
    00137 static void printVersion(FILE * fp)
    00138 {
    00139     fprintf(fp, _("RPM version %s\n"), rpmEVR);
    00140 }
    00141
    00142 static void printBanner(FILE * fp)
    00143 {
    00144     fprintf(fp, _("Copyright (C) 1998-2002 - Red Hat, Inc.\n"));
    00145     fprintf(fp, _("This program may be freely redistributed under the terms of the GNU GPL\n"));
    00146 }
    00147
    00148 static void printUsage(poptContext con, FILE * fp, int flags)
    00149 {
    00150     printVersion(fp);
    00151     printBanner(fp);
    00152     fprintf(fp, "\n");
    00153
    00154     if (rpmIsVerbose())
    00155         poptPrintHelp(con, fp, flags);
    00156     else
    00157         poptPrintUsage(con, fp, flags);
    00158 }
    00159
    00160 int main(int argc, char *argv[])
    00161 {
    00162     rpmts ts = NULL;
    00163     enum modes bigMode = MODE_UNKNOWN;
    00164
    00165 #if defined(IAM_RPMQV)
    00166     QVA_t qva = &rpmQVKArgs;
    00167 #endif
    00168
    00169 #ifdef  IAM_RPMBT
    00170     BTA_t ba = &rpmBTArgs;
    00171 #endif
    00172
    00173 #ifdef  IAM_RPMEIU
    00174    struct rpmInstallArguments_s * ia = &rpmIArgs;
    00175 #endif
    00176
    00177 #if defined(IAM_RPMDB)
    00178    struct rpmDatabaseArguments_s * da = &rpmDBArgs;
    00179 #endif
    00180
    00181 #if defined(IAM_RPMK)
    00182    QVA_t ka = &rpmQVKArgs;
    00183 #endif
    00184
    00185 #if defined(IAM_RPMBT) || defined(IAM_RPMK)
    00186     char * passPhrase = "";
    00187 #endif
    00188
    00189     int arg;
    00190
    00191     const char *optArg, *poptCtx;
    00192     pid_t pipeChild = 0;
    00193     poptContext optCon;
    00194     int ec = 0;
    00195     int status;
    00196     int p[2];
    00197 #ifdef  IAM_RPMEIU
    00198     int i;
    00199 #endif
    00200
    00201 #if HAVE_MCHECK_H && HAVE_MTRACE
    00202     mtrace();   /* Trace malloc only if MALLOC_TRACE=mtrace-output-file. */
    00203 #endif
    00204     setprogname(argv[0]);       /* Retrofit glibc __progname */
    00205
    00206     /* XXX glibc churn sanity */
    00207     if (__progname == NULL) {
    00208         if ((__progname = strrchr(argv[0], '/')) != NULL) __progname++;
    00209         else __progname = argv[0];
    00210     }
    00211
    00212     /* Set the major mode based on argv[0] */
    00213 #ifdef  IAM_RPMBT
    00214     if (!strcmp(__progname, "rpmbuild"))        bigMode = MODE_BUILD;
    00215 #endif
    00216 #ifdef  IAM_RPMQV
    00217     if (!strcmp(__progname, "rpmquery"))        bigMode = MODE_QUERY;
    00218     if (!strcmp(__progname, "rpmverify"))       bigMode = MODE_VERIFY;
    00219 #endif
    00220
    00221 #if defined(IAM_RPMQV)
    00222     /* Jumpstart option from argv[0] if necessary. */
    00223     switch (bigMode) {
    00224     case MODE_QUERY:    qva->qva_mode = 'q';    break;
    00225     case MODE_VERIFY:   qva->qva_mode = 'V';    break;
    00226     case MODE_CHECKSIG: qva->qva_mode = 'K';    break;
    00227     case MODE_RESIGN:   qva->qva_mode = 'R';    break;
    00228     case MODE_INSTALL:
    00229     case MODE_ERASE:
    00230     case MODE_BUILD:
    00231     case MODE_REBUILD:
    00232     case MODE_RECOMPILE:
    00233     case MODE_TARBUILD:
    00234     case MODE_INITDB:
    00235     case MODE_REBUILDDB:
    00236     case MODE_VERIFYDB:
    00237     case MODE_UNKNOWN:
    00238     default:
    00239         break;
    00240     }
    00241 #endif
    00242
    00243 #if defined(ENABLE_NLS)
    00244     /* set up the correct locale */
    00245     (void) setlocale(LC_ALL, "" );
    00246
    00247     bindtextdomain(PACKAGE, LOCALEDIR);
    00248     textdomain(PACKAGE);
    00249 #endif
    00250
    00251     rpmSetVerbosity(RPMLOG_NOTICE);     /* XXX silly use by showrc */
    00252
    00253     /* Only build has it's own set of aliases, everything else uses rpm */
    00254 #ifdef  IAM_RPMBT
    00255     poptCtx = "rpmbuild";
    00256 #else
    00257     poptCtx = "rpm";
    00258 #endif
    00259
    00260     /* Make a first pass through the arguments, looking for --rcfile */
    00261     /* We need to handle that before dealing with the rest of the arguments. */
    00262     /* XXX popt argv definition should be fixed instead of casting... */
    00263     optCon = poptGetContext(poptCtx, argc, (const char **)argv, optionsTable, 0);
    00264     (void) poptReadConfigFile(optCon, LIBRPMALIAS_FILENAME);
    00265 #if RPM_USES_POPTREADDEFAULTCONFIG
    00266     (void) poptReadDefaultConfig(optCon, 1);
    00267 #endif
    00268     poptSetExecPath(optCon, RPMCONFIGDIR, 1);
    00269
    00270     while ((arg = poptGetNextOpt(optCon)) > 0) {
    00271         optArg = poptGetOptArg(optCon);
    00272
    00273         switch (arg) {
    00274         default:
    00275             fprintf(stderr, _("Internal error in argument processing (%d) :-(\n"), arg);
    00276             exit(EXIT_FAILURE);
    00277         }
    00278     }
    00279
    00280     if (arg < -1) {
    00281         fprintf(stderr, "%s: %s\n",
    00282                 poptBadOption(optCon, POPT_BADOPTION_NOALIAS),
    00283                 poptStrerror(arg));
    00284         exit(EXIT_FAILURE);
    00285     }
    00286
    00287     rpmcliConfigured();
    00288
    00289 #ifdef  IAM_RPMBT
    00290     switch (ba->buildMode) {
    00291     case 'b':   bigMode = MODE_BUILD;           break;
    00292     case 't':   bigMode = MODE_TARBUILD;        break;
    00293     case 'B':   bigMode = MODE_REBUILD;         break;
    00294     case 'C':   bigMode = MODE_RECOMPILE;       break;
    00295     }
    00296
    00297     if ((ba->buildAmount & RPMBUILD_RMSOURCE) && bigMode == MODE_UNKNOWN)
    00298         bigMode = MODE_BUILD;
    00299
    00300     if ((ba->buildAmount & RPMBUILD_RMSPEC) && bigMode == MODE_UNKNOWN)
    00301         bigMode = MODE_BUILD;
    00302
    00303     if (ba->buildRootOverride && bigMode != MODE_BUILD &&
    00304         bigMode != MODE_REBUILD && bigMode != MODE_TARBUILD) {
    00305         argerror("--buildroot may only be used during package builds");
    00306     }
    00307 #endif  /* IAM_RPMBT */
    00308
    00309 #ifdef  IAM_RPMDB
    00310   if (bigMode == MODE_UNKNOWN || (bigMode & MODES_DB)) {
    00311     if (da->init) {
    00312         if (bigMode != MODE_UNKNOWN)
    00313             argerror(_("only one major mode may be specified"));
    00314         else
    00315             bigMode = MODE_INITDB;
    00316     } else
    00317     if (da->rebuild) {
    00318         if (bigMode != MODE_UNKNOWN)
    00319             argerror(_("only one major mode may be specified"));
    00320         else
    00321             bigMode = MODE_REBUILDDB;
    00322     } else
    00323     if (da->verify) {
    00324         if (bigMode != MODE_UNKNOWN)
    00325             argerror(_("only one major mode may be specified"));
    00326         else
    00327             bigMode = MODE_VERIFYDB;
    00328     }
    00329   }
    00330 #endif  /* IAM_RPMDB */
    00331
    00332 #ifdef  IAM_RPMQV
    00333   if (bigMode == MODE_UNKNOWN || (bigMode & MODES_QV)) {
    00334     switch (qva->qva_mode) {
    00335     case 'q':   bigMode = MODE_QUERY;           break;
    00336     case 'V':   bigMode = MODE_VERIFY;          break;
    00337     }
    00338
    00339     if (qva->qva_sourceCount) {
    00340         if (qva->qva_sourceCount > 2)
    00341             argerror(_("one type of query/verify may be performed at a "
    00342                         "time"));
    00343     }
    00344     if (qva->qva_flags && (bigMode & ~MODES_QV))
    00345         argerror(_("unexpected query flags"));
    00346
    00347     if (qva->qva_queryFormat && (bigMode & ~MODES_QV))
    00348         argerror(_("unexpected query format"));
    00349
    00350     if (qva->qva_source != RPMQV_PACKAGE && (bigMode & ~MODES_QV))
    00351         argerror(_("unexpected query source"));
    00352   }
    00353 #endif  /* IAM_RPMQV */
    00354
    00355 #ifdef  IAM_RPMEIU
    00356   if (bigMode == MODE_UNKNOWN || (bigMode & MODES_IE))
    00357     {   int iflags = (ia->installInterfaceFlags &
    00358                 (INSTALL_UPGRADE|INSTALL_FRESHEN|INSTALL_INSTALL));
    00359         int eflags = (ia->installInterfaceFlags & INSTALL_ERASE);
    00360
    00361         if (iflags & eflags)
    00362             argerror(_("only one major mode may be specified"));
    00363         else if (iflags)
    00364             bigMode = MODE_INSTALL;
    00365         else if (eflags)
    00366             bigMode = MODE_ERASE;
    00367     }
    00368 #endif  /* IAM_RPMEIU */
    00369
    00370 #ifdef  IAM_RPMK
    00371   if (bigMode == MODE_UNKNOWN || (bigMode & MODES_K)) {
    00372         switch (ka->qva_mode) {
    00373         case RPMSIGN_NONE:
    00374             ka->sign = 0;
    00375             break;
    00376         case RPMSIGN_IMPORT_PUBKEY:
    00377         case RPMSIGN_CHK_SIGNATURE:
    00378             bigMode = MODE_CHECKSIG;
    00379             ka->sign = 0;
    00380             break;
    00381         case RPMSIGN_ADD_SIGNATURE:
    00382         case RPMSIGN_NEW_SIGNATURE:
    00383         case RPMSIGN_DEL_SIGNATURE:
    00384             bigMode = MODE_RESIGN;
    00385             ka->sign = (ka->qva_mode != RPMSIGN_DEL_SIGNATURE);
    00386             break;
    00387         }
    00388   }
    00389 #endif  /* IAM_RPMK */
    00390
    00391 #if defined(IAM_RPMEIU)
    00392     if (!( bigMode == MODE_INSTALL ) &&
    00393 (ia->probFilter & (RPMPROB_FILTER_REPLACEPKG | RPMPROB_FILTER_OLDPACKAGE)))
    00394         argerror(_("only installation, upgrading, rmsource and rmspec may be forced"));
    00395     if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_FORCERELOCATE))
    00396         argerror(_("files may only be relocated during package installation"));
    00397
    00398     if (ia->relocations && ia->prefix)
    00399         argerror(_("cannot use --prefix with --relocate or --excludepath"));
    00400
    00401     if (bigMode != MODE_INSTALL && ia->relocations)
    00402         argerror(_("--relocate and --excludepath may only be used when installing new packages"));
    00403
    00404     if (bigMode != MODE_INSTALL && ia->prefix)
    00405         argerror(_("--prefix may only be used when installing new packages"));
    00406
    00407     if (ia->prefix && ia->prefix[0] != '/')
    00408         argerror(_("arguments to --prefix must begin with a /"));
    00409
    00410     if (bigMode != MODE_INSTALL && (ia->installInterfaceFlags & INSTALL_HASH))
    00411         argerror(_("--hash (-h) may only be specified during package "
    00412                         "installation"));
    00413
    00414     if (bigMode != MODE_INSTALL && (ia->installInterfaceFlags & INSTALL_PERCENT))
    00415         argerror(_("--percent may only be specified during package "
    00416                         "installation"));
    00417
    00418     if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_REPLACEPKG))
    00419         argerror(_("--replacepkgs may only be specified during package "
    00420                         "installation"));
    00421
    00422     if (bigMode != MODE_INSTALL && (ia->transFlags & RPMTRANS_FLAG_NODOCS))
    00423         argerror(_("--excludedocs may only be specified during package "
    00424                    "installation"));
    00425
    00426     if (bigMode != MODE_INSTALL && ia->incldocs)
    00427         argerror(_("--includedocs may only be specified during package "
    00428                    "installation"));
    00429
    00430     if (ia->incldocs && (ia->transFlags & RPMTRANS_FLAG_NODOCS))
    00431         argerror(_("only one of --excludedocs and --includedocs may be "
    00432                  "specified"));
    00433
    00434     if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_IGNOREARCH))
    00435         argerror(_("--ignorearch may only be specified during package "
    00436                    "installation"));
    00437
    00438     if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_IGNOREOS))
    00439         argerror(_("--ignoreos may only be specified during package "
    00440                    "installation"));
    00441
    00442     if (bigMode != MODE_INSTALL && bigMode != MODE_ERASE &&
    00443         (ia->probFilter & (RPMPROB_FILTER_DISKSPACE|RPMPROB_FILTER_DISKNODES)))
    00444         argerror(_("--ignoresize may only be specified during package "
    00445                    "installation"));
    00446
    00447     if ((ia->eraseInterfaceFlags & UNINSTALL_ALLMATCHES) && bigMode != MODE_ERASE)
    00448         argerror(_("--allmatches may only be specified during package "
    00449                    "erasure"));
    00450
    00451     if ((ia->transFlags & RPMTRANS_FLAG_ALLFILES) && bigMode != MODE_INSTALL)
    00452         argerror(_("--allfiles may only be specified during package "
    00453                    "installation"));
    00454
    00455     if ((ia->transFlags & RPMTRANS_FLAG_JUSTDB) &&
    00456         bigMode != MODE_INSTALL && bigMode != MODE_ERASE)
    00457         argerror(_("--justdb may only be specified during package "
    00458                    "installation and erasure"));
    00459
    00460     if (bigMode != MODE_INSTALL && bigMode != MODE_ERASE &&
    00461         (ia->transFlags & (RPMTRANS_FLAG_NOSCRIPTS | _noTransScripts | _noTransTriggers)))
    00462         argerror(_("script disabling options may only be specified during "
    00463                    "package installation and erasure"));
    00464
    00465     if (bigMode != MODE_INSTALL && bigMode != MODE_ERASE &&
    00466         (ia->transFlags & (RPMTRANS_FLAG_NOTRIGGERS | _noTransTriggers)))
    00467         argerror(_("trigger disabling options may only be specified during "
    00468                    "package installation and erasure"));
    00469
    00470     if (ia->noDeps & (bigMode & ~MODES_FOR_NODEPS))
    00471         argerror(_("--nodeps may only be specified during package "
    00472                    "building, rebuilding, recompilation, installation,"
    00473                    "erasure, and verification"));
    00474
    00475     if ((ia->transFlags & RPMTRANS_FLAG_TEST) && (bigMode & ~MODES_FOR_TEST))
    00476         argerror(_("--test may only be specified during package installation, "
    00477                  "erasure, and building"));
    00478 #endif  /* IAM_RPMEIU */
    00479
    00480     if (rpmcliRootDir && rpmcliRootDir[1] && (bigMode & ~MODES_FOR_ROOT))
    00481         argerror(_("--root (-r) may only be specified during "
    00482                  "installation, erasure, querying, and "
    00483                  "database rebuilds"));
    00484
    00485     if (rpmcliRootDir) {
    00486         switch (urlIsURL(rpmcliRootDir)) {
    00487         default:
    00488             if (bigMode & MODES_FOR_ROOT)
    00489                 break;
    00490         case URL_IS_UNKNOWN:
    00491             if (rpmcliRootDir[0] != '/')
    00492                 argerror(_("arguments to --root (-r) must begin with a /"));
    00493             break;
    00494         }
    00495     }
    00496
    00497     if (quiet)
    00498         rpmSetVerbosity(RPMLOG_WARNING);
    00499
    00500 #if defined(IAM_RPMBT) || defined(IAM_RPMK)
    00501     if (0
    00502 #if defined(IAM_RPMBT)
    00503     || ba->sign
    00504 #endif
    00505 #if defined(IAM_RPMK)
    00506     || ka->sign
    00507 #endif
    00508     )
    00509     {
    00510         if (bigMode == MODE_REBUILD || bigMode == MODE_BUILD ||
    00511             bigMode == MODE_RESIGN || bigMode == MODE_TARBUILD)
    00512         {
    00513             const char ** av;
    00514             struct stat sb;
    00515             int errors = 0;
    00516
    00517             if ((av = poptGetArgs(optCon)) == NULL) {
    00518                 fprintf(stderr, _("no files to sign\n"));
    00519                 errors++;
    00520             } else
    00521             while (*av) {
    00522                 if (stat(*av, &sb)) {
    00523                     fprintf(stderr, _("cannot access file %s\n"), *av);
    00524                     errors++;
    00525                 }
    00526                 av++;
    00527             }
    00528
    00529             if (errors) {
    00530                 ec = errors;
    00531                 goto exit;
    00532             }
    00533
    00534             if (poptPeekArg(optCon)) {
    00535                 int sigTag = rpmLookupSignatureType(RPMLOOKUPSIG_QUERY);
    00536                 switch (sigTag) {
    00537                   case 0:
    00538                     break;
    00539                   case RPMSIGTAG_PGP:
    00540 #ifdef  DYING   /* XXX gpg can now be used for RSA signatures. */
    00541                     if ((sigTag == RPMSIGTAG_PGP || sigTag == RPMSIGTAG_PGP5) &&
    00542                         !rpmDetectPGPVersion(NULL)) {
    00543                         fprintf(stderr, _("pgp not found: "));
    00544                         ec = EXIT_FAILURE;
    00545                         goto exit;
    00546                     }
    00547 #endif
    00548                   case RPMSIGTAG_GPG:
    00549                   case RPMSIGTAG_DSA:
    00550                   case RPMSIGTAG_RSA:
    00551                     passPhrase = rpmGetPassPhrase(_("Enter pass phrase: "), sigTag);
    00552                     if (passPhrase == NULL) {
    00553                         fprintf(stderr, _("Pass phrase check failed\n"));
    00554                         ec = EXIT_FAILURE;
    00555                         goto exit;
    00556                     }
    00557                     fprintf(stderr, _("Pass phrase is good.\n"));
    00558                     passPhrase = xstrdup(passPhrase);
    00559                     break;
    00560                   default:
    00561                     fprintf(stderr,
    00562                             _("Invalid %%_signature spec in macro file.\n"));
    00563                     ec = EXIT_FAILURE;
    00564                     goto exit;
    00565                     break;
    00566                 }
    00567             }
    00568         } else {
    00569             argerror(_("--sign may only be used during package building"));
    00570         }
    00571     } else {
    00572         /* Make rpmLookupSignatureType() return 0 ("none") from now on */
    00573         (void) rpmLookupSignatureType(RPMLOOKUPSIG_DISABLE);
    00574     }
    00575 #endif  /* IAM_RPMBT || IAM_RPMK */
    00576
    00577     if (rpmcliPipeOutput) {
    00578         if (pipe(p) < 0) {
    00579             fprintf(stderr, _("creating a pipe for --pipe failed: %m\n"));
    00580             goto exit;
    00581         }
    00582
    00583         if (!(pipeChild = fork())) {
    00584             (void) signal(SIGPIPE, SIG_DFL);
    00585             (void) close(p[1]);
    00586             (void) dup2(p[0], STDIN_FILENO);
    00587             (void) close(p[0]);
    00588             (void) execl("/bin/sh", "/bin/sh", "-c", rpmcliPipeOutput, NULL);
    00589             fprintf(stderr, _("exec failed\n"));
    00590         }
    00591
    00592         (void) close(p[0]);
    00593         (void) dup2(p[1], STDOUT_FILENO);
    00594         (void) close(p[1]);
    00595     }
    00596
    00597     ts = rpmtsCreate();
    00598     (void) rpmtsSetRootDir(ts, rpmcliRootDir);
    00599     switch (bigMode) {
    00600 #ifdef  IAM_RPMDB
    00601     case MODE_INITDB:
    00602         ec = rpmtsInitDB(ts, 0644);
    00603         break;
    00604
    00605     case MODE_REBUILDDB:
    00606     {   rpmVSFlags vsflags = rpmExpandNumeric("%{_vsflags_rebuilddb}");
    00607         rpmVSFlags ovsflags = rpmtsSetVSFlags(ts, vsflags);
    00608         ec = rpmtsRebuildDB(ts);
    00609         vsflags = rpmtsSetVSFlags(ts, ovsflags);
    00610     }   break;
    00611     case MODE_VERIFYDB:
    00612         ec = rpmtsVerifyDB(ts);
    00613         break;
    00614 #endif  /* IAM_RPMDB */
    00615
    00616 #ifdef  IAM_RPMBT
    00617     case MODE_REBUILD:
    00618     case MODE_RECOMPILE:
    00619     {   const char * pkg;
    00620
    00621         while (!rpmIsVerbose())
    00622             rpmIncreaseVerbosity();
    00623
    00624         if (!poptPeekArg(optCon))
    00625             argerror(_("no packages files given for rebuild"));
    00626
    00627         ba->buildAmount =
    00628             RPMBUILD_PREP | RPMBUILD_BUILD | RPMBUILD_INSTALL | RPMBUILD_CHECK;
    00629         if (bigMode == MODE_REBUILD) {
    00630             ba->buildAmount |= RPMBUILD_PACKAGEBINARY;
    00631             ba->buildAmount |= RPMBUILD_RMSOURCE;
    00632             ba->buildAmount |= RPMBUILD_RMSPEC;
    00633             ba->buildAmount |= RPMBUILD_CLEAN;
    00634             ba->buildAmount |= RPMBUILD_RMBUILD;
    00635         }
    00636
    00637         while ((pkg = poptGetArg(optCon))) {
    00638             char * specFile = NULL;
    00639
    00640             ba->cookie = NULL;
    00641             ec = rpmInstallSource(ts, pkg, &specFile, &ba->cookie);
    00642             if (ec == 0) {
    00643                 ba->rootdir = rpmcliRootDir;
    00644                 ba->passPhrase = passPhrase;
    00645                 ec = build(ts, specFile, ba, rpmcliRcfile);
    00646             }
    00647             ba->cookie = _free(ba->cookie);
    00648             specFile = _free(specFile);
    00649
    00650             if (ec)
    00651                 break;
    00652         }
    00653
    00654     }   break;
    00655
    00656     case MODE_BUILD:
    00657     case MODE_TARBUILD:
    00658     {   const char * pkg;
    00659         if (!quiet) while (!rpmIsVerbose())
    00660             rpmIncreaseVerbosity();
    00661
    00662         switch (ba->buildChar) {
    00663         case 'a':
    00664             ba->buildAmount |= RPMBUILD_PACKAGESOURCE;
    00665         case 'b':
    00666             ba->buildAmount |= RPMBUILD_PACKAGEBINARY;
    00667             ba->buildAmount |= RPMBUILD_CLEAN;
    00668         case 'i':
    00669             ba->buildAmount |= RPMBUILD_INSTALL;
    00670             ba->buildAmount |= RPMBUILD_CHECK;
    00671             if ((ba->buildChar == 'i') && ba->shortCircuit)
    00672                 break;
    00673         case 'c':
    00674             ba->buildAmount |= RPMBUILD_BUILD;
    00675             if ((ba->buildChar == 'c') && ba->shortCircuit)
    00676                 break;
    00677         case 'p':
    00678             ba->buildAmount |= RPMBUILD_PREP;
    00679             break;
    00680
    00681         case 'l':
    00682             ba->buildAmount |= RPMBUILD_FILECHECK;
    00683             break;
    00684         case 's':
    00685             ba->buildAmount |= RPMBUILD_PACKAGESOURCE;
    00686             break;
    00687         }
    00688
    00689         if (!poptPeekArg(optCon)) {
    00690             if (bigMode == MODE_BUILD)
    00691                 argerror(_("no spec files given for build"));
    00692             else
    00693                 argerror(_("no tar files given for build"));
    00694         }
    00695
    00696         while ((pkg = poptGetArg(optCon))) {
    00697             ba->rootdir = rpmcliRootDir;
    00698             ba->passPhrase = passPhrase;
    00699             ba->cookie = NULL;
    00700             ec = build(ts, pkg, ba, rpmcliRcfile);
    00701             if (ec)
    00702                 break;
    00703             rpmFreeMacros(NULL);
    00704             (void) rpmReadConfigFiles(rpmcliRcfile, NULL);
    00705         }
    00706     }   break;
    00707 #endif  /* IAM_RPMBT */
    00708
    00709 #ifdef  IAM_RPMEIU
    00710     case MODE_ERASE:
    00711         if (ia->noDeps) ia->eraseInterfaceFlags |= UNINSTALL_NODEPS;
    00712
    00713         if (!poptPeekArg(optCon)) {
    00714             argerror(_("no packages given for erase"));
    00715         } else {
    00716             ec += rpmErase(ts, ia, (ARGV_const_t) poptGetArgs(optCon));
    00717         }
    00718         break;
    00719
    00720     case MODE_INSTALL:
    00721
    00722         /* RPMTRANS_FLAG_KEEPOBSOLETE */
    00723
    00724         if (!ia->incldocs) {
    00725             if (ia->transFlags & RPMTRANS_FLAG_NODOCS) {
    00726                 ;
    00727             } else if (rpmExpandNumeric("%{_excludedocs}"))
    00728                 ia->transFlags |= RPMTRANS_FLAG_NODOCS;
    00729         }
    00730
    00731         if (ia->noDeps) ia->installInterfaceFlags |= INSTALL_NODEPS;
    00732
    00733         /* we've already ensured !(!ia->prefix && !ia->relocations) */
    00734         if (ia->prefix) {
    00735             ia->relocations = xmalloc(2 * sizeof(*ia->relocations));
    00736             ia->relocations[0].oldPath = NULL;   /* special case magic */
    00737             ia->relocations[0].newPath = ia->prefix;
    00738             ia->relocations[1].oldPath = NULL;
    00739             ia->relocations[1].newPath = NULL;
    00740         } else if (ia->relocations) {
    00741             ia->relocations = xrealloc(ia->relocations,
    00742                         sizeof(*ia->relocations) * (ia->numRelocations + 1));
    00743             ia->relocations[ia->numRelocations].oldPath = NULL;
    00744             ia->relocations[ia->numRelocations].newPath = NULL;
    00745         }
    00746
    00747         if (!poptPeekArg(optCon)) {
    00748             argerror(_("no packages given for install"));
    00749         } else {
    00750             /* FIX: ia->relocations[0].newPath undefined */
    00751             ec += rpmInstall(ts, ia, (ARGV_t) poptGetArgs(optCon));
    00752         }
    00753         break;
    00754
    00755 #endif  /* IAM_RPMEIU */
    00756
    00757 #ifdef  IAM_RPMQV
    00758     case MODE_QUERY:
    00759         if (!poptPeekArg(optCon)
    00760          && !(qva->qva_source == RPMQV_ALL || qva->qva_source == RPMQV_HDLIST))
    00761             argerror(_("no arguments given for query"));
    00762
    00763         qva->qva_specQuery = rpmspecQuery;
    00764         ec = rpmcliQuery(ts, qva, (ARGV_const_t) poptGetArgs(optCon));
    00765         qva->qva_specQuery = NULL;
    00766         break;
    00767
    00768     case MODE_VERIFY:
    00769     {   rpmVerifyFlags verifyFlags = VERIFY_ALL;
    00770
    00771         verifyFlags &= ~qva->qva_flags;
    00772         qva->qva_flags = (rpmQueryFlags) verifyFlags;
    00773
    00774         if (!poptPeekArg(optCon)
    00775          && !(qva->qva_source == RPMQV_ALL || qva->qva_source == RPMQV_HDLIST))
    00776             argerror(_("no arguments given for verify"));
    00777         ec = rpmcliVerify(ts, qva, (ARGV_const_t) poptGetArgs(optCon));
    00778     }   break;
    00779 #endif  /* IAM_RPMQV */
    00780
    00781 #ifdef IAM_RPMK
    00782     case MODE_CHECKSIG:
    00783     {   rpmVerifyFlags verifyFlags =
    00784                 (VERIFY_MD5|VERIFY_DIGEST|VERIFY_SIGNATURE);
    00785
    00786         verifyFlags &= ~ka->qva_flags;
    00787         ka->qva_flags = (rpmQueryFlags) verifyFlags;
    00788     }
    00789     case MODE_RESIGN:
    00790         if (!poptPeekArg(optCon))
    00791             argerror(_("no arguments given"));
    00792         ka->passPhrase = passPhrase;
    00793         ec = rpmcliSign(ts, ka, (ARGV_const_t) poptGetArgs(optCon));
    00794         break;
    00795 #endif  /* IAM_RPMK */
    00796
    00797 #if !defined(IAM_RPMQV)
    00798     case MODE_QUERY:
    00799     case MODE_VERIFY:
    00800 #endif
    00801 #if !defined(IAM_RPMK)
    00802     case MODE_CHECKSIG:
    00803     case MODE_RESIGN:
    00804 #endif
    00805 #if !defined(IAM_RPMDB)
    00806     case MODE_INITDB:
    00807     case MODE_REBUILDDB:
    00808     case MODE_VERIFYDB:
    00809 #endif
    00810 #if !defined(IAM_RPMBT)
    00811     case MODE_BUILD:
    00812     case MODE_REBUILD:
    00813     case MODE_RECOMPILE:
    00814     case MODE_TARBUILD:
    00815 #endif
    00816 #if !defined(IAM_RPMEIU)
    00817     case MODE_INSTALL:
    00818     case MODE_ERASE:
    00819 #endif
    00820     case MODE_UNKNOWN:
    00821         if (poptPeekArg(optCon) != NULL || argc <= 1 || rpmIsVerbose()) {
    00822             printUsage(optCon, stderr, 0);
    00823             ec = argc;
    00824         }
    00825         break;
    00826     }
    00827
    00828 exit:
    00829
    00830     ts = rpmtsFree(ts);
    00831
    00832     optCon = poptFreeContext(optCon);
    00833     rpmFreeMacros(NULL);
    00834         rpmFreeMacros(rpmCLIMacroContext);
    00835     rpmFreeRpmrc();
    00836
    00837     if (pipeChild) {
    00838         (void) fclose(stdout);
    00839         (void) waitpid(pipeChild, &status, 0);
    00840     }
    00841
    00842     /* keeps memory leak checkers quiet */
    00843     rpmFreeFilesystems();
    00844     rpmlogClose();
    00845
    00846 #ifdef  IAM_RPMQV
    00847     qva->qva_queryFormat = _free(qva->qva_queryFormat);
    00848 #endif
    00849
    00850 #ifdef  IAM_RPMBT
    00851     freeNames();
    00852     ba->buildRootOverride = _free(ba->buildRootOverride);
    00853     ba->targets = _free(ba->targets);
    00854 #endif
    00855
    00856 #ifdef  IAM_RPMEIU
    00857     if (ia->relocations != NULL)
    00858     for (i = 0; i < ia->numRelocations; i++)
    00859         ia->relocations[i].oldPath = _free(ia->relocations[i].oldPath);
    00860     ia->relocations = _free(ia->relocations);
    00861 #endif
    00862
    00863 #if HAVE_MCHECK_H && HAVE_MTRACE
    00864     muntrace();   /* Trace malloc only if MALLOC_TRACE=mtrace-output-file. */
    00865 #endif
    00866
    00867     /* XXX Avoid exit status overflow. Status 255 is special to xargs(1) */
    00868     if (ec > 254) ec = 254;
    00869
    00870     return ec;
    00871 }