rpm
4.10.0
|
00001 #include "system.h" 00002 const char *__progname; 00003 00004 #include <rpm/rpmcli.h> 00005 #include <rpm/rpmlib.h> /* RPMSIGTAG, rpmReadPackageFile .. */ 00006 #include <rpm/rpmlog.h> 00007 #include <rpm/rpmps.h> 00008 #include <rpm/rpmts.h> 00009 00010 #include "cliutils.h" 00011 00012 #include "debug.h" 00013 00014 #if defined(IAM_RPMQ) || defined(IAM_RPMV) 00015 #define IAM_RPMQV 00016 #endif 00017 00018 enum modes { 00019 00020 MODE_QUERY = (1 << 0), 00021 MODE_VERIFY = (1 << 3), 00022 #define MODES_QV (MODE_QUERY | MODE_VERIFY) 00023 00024 MODE_INSTALL = (1 << 1), 00025 MODE_ERASE = (1 << 2), 00026 #define MODES_IE (MODE_INSTALL | MODE_ERASE) 00027 00028 MODE_UNKNOWN = 0 00029 }; 00030 00031 #define MODES_FOR_NODEPS (MODES_IE | MODE_VERIFY) 00032 #define MODES_FOR_TEST (MODES_IE) 00033 00034 static int quiet; 00035 00036 /* the structure describing the options we take and the defaults */ 00037 static struct poptOption optionsTable[] = { 00038 00039 #ifdef IAM_RPMQV 00040 { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmQVSourcePoptTable, 0, 00041 N_("Query/Verify package selection options:"), 00042 NULL }, 00043 #endif 00044 #ifdef IAM_RPMQ 00045 { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmQueryPoptTable, 0, 00046 N_("Query options (with -q or --query):"), 00047 NULL }, 00048 #endif 00049 #ifdef IAM_RPMV 00050 { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmVerifyPoptTable, 0, 00051 N_("Verify options (with -V or --verify):"), 00052 NULL }, 00053 #endif 00054 00055 #ifdef IAM_RPMEIU 00056 { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmInstallPoptTable, 0, 00057 N_("Install/Upgrade/Erase options:"), 00058 NULL }, 00059 #endif /* IAM_RPMEIU */ 00060 00061 { "quiet", '\0', POPT_ARGFLAG_DOC_HIDDEN, &quiet, 0, NULL, NULL}, 00062 00063 { NULL, '\0', POPT_ARG_INCLUDE_TABLE, rpmcliAllPoptTable, 0, 00064 N_("Common options for all rpm modes and executables:"), 00065 NULL }, 00066 00067 POPT_AUTOALIAS 00068 POPT_AUTOHELP 00069 POPT_TABLEEND 00070 }; 00071 00072 int main(int argc, char *argv[]) 00073 { 00074 rpmts ts = NULL; 00075 enum modes bigMode = MODE_UNKNOWN; 00076 00077 #if defined(IAM_RPMQV) 00078 QVA_t qva = &rpmQVKArgs; 00079 #endif 00080 00081 #ifdef IAM_RPMEIU 00082 struct rpmInstallArguments_s * ia = &rpmIArgs; 00083 #endif 00084 00085 poptContext optCon; 00086 int ec = 0; 00087 #ifdef IAM_RPMEIU 00088 int i; 00089 #endif 00090 00091 optCon = rpmcliInit(argc, argv, optionsTable); 00092 00093 /* Set the major mode based on argv[0] */ 00094 #ifdef IAM_RPMQV 00095 if (rstreq(__progname, "rpmquery")) bigMode = MODE_QUERY; 00096 if (rstreq(__progname, "rpmverify")) bigMode = MODE_VERIFY; 00097 #endif 00098 00099 #if defined(IAM_RPMQV) 00100 /* Jumpstart option from argv[0] if necessary. */ 00101 switch (bigMode) { 00102 case MODE_QUERY: qva->qva_mode = 'q'; break; 00103 case MODE_VERIFY: qva->qva_mode = 'V'; break; 00104 case MODE_INSTALL: 00105 case MODE_ERASE: 00106 case MODE_UNKNOWN: 00107 default: 00108 break; 00109 } 00110 #endif 00111 00112 #ifdef IAM_RPMQV 00113 if (bigMode == MODE_UNKNOWN || (bigMode & MODES_QV)) { 00114 switch (qva->qva_mode) { 00115 case 'q': bigMode = MODE_QUERY; break; 00116 case 'V': bigMode = MODE_VERIFY; break; 00117 } 00118 00119 if (qva->qva_sourceCount) { 00120 if (qva->qva_sourceCount > 1) 00121 argerror(_("one type of query/verify may be performed at a " 00122 "time")); 00123 } 00124 if (qva->qva_flags && (bigMode & ~MODES_QV)) 00125 argerror(_("unexpected query flags")); 00126 00127 if (qva->qva_queryFormat && (bigMode & ~MODES_QV)) 00128 argerror(_("unexpected query format")); 00129 00130 if (qva->qva_source != RPMQV_PACKAGE && (bigMode & ~MODES_QV)) 00131 argerror(_("unexpected query source")); 00132 } 00133 #endif /* IAM_RPMQV */ 00134 00135 #ifdef IAM_RPMEIU 00136 if (bigMode == MODE_UNKNOWN || (bigMode & MODES_IE)) 00137 { int iflags = (ia->installInterfaceFlags & 00138 (INSTALL_UPGRADE|INSTALL_FRESHEN|INSTALL_INSTALL)); 00139 int eflags = (ia->installInterfaceFlags & INSTALL_ERASE); 00140 00141 if (iflags & eflags) 00142 argerror(_("only one major mode may be specified")); 00143 else if (iflags) 00144 bigMode = MODE_INSTALL; 00145 else if (eflags) 00146 bigMode = MODE_ERASE; 00147 } 00148 #endif /* IAM_RPMEIU */ 00149 00150 #if defined(IAM_RPMEIU) 00151 if (!( bigMode == MODE_INSTALL ) && 00152 (ia->probFilter & (RPMPROB_FILTER_REPLACEPKG | RPMPROB_FILTER_OLDPACKAGE))) 00153 argerror(_("only installation and upgrading may be forced")); 00154 if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_FORCERELOCATE)) 00155 argerror(_("files may only be relocated during package installation")); 00156 00157 if (ia->relocations && ia->prefix) 00158 argerror(_("cannot use --prefix with --relocate or --excludepath")); 00159 00160 if (bigMode != MODE_INSTALL && ia->relocations) 00161 argerror(_("--relocate and --excludepath may only be used when installing new packages")); 00162 00163 if (bigMode != MODE_INSTALL && ia->prefix) 00164 argerror(_("--prefix may only be used when installing new packages")); 00165 00166 if (ia->prefix && ia->prefix[0] != '/') 00167 argerror(_("arguments to --prefix must begin with a /")); 00168 00169 if (!(bigMode & MODES_IE) && (ia->installInterfaceFlags & INSTALL_HASH)) 00170 argerror(_("--hash (-h) may only be specified during package " 00171 "installation and erasure")); 00172 00173 if (!(bigMode & MODES_IE) && (ia->installInterfaceFlags & INSTALL_PERCENT)) 00174 argerror(_("--percent may only be specified during package " 00175 "installation and erasure")); 00176 00177 if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_REPLACEPKG)) 00178 argerror(_("--replacepkgs may only be specified during package " 00179 "installation")); 00180 00181 if (bigMode != MODE_INSTALL && (ia->transFlags & RPMTRANS_FLAG_NODOCS)) 00182 argerror(_("--excludedocs may only be specified during package " 00183 "installation")); 00184 00185 if (bigMode != MODE_INSTALL && ia->incldocs) 00186 argerror(_("--includedocs may only be specified during package " 00187 "installation")); 00188 00189 if (ia->incldocs && (ia->transFlags & RPMTRANS_FLAG_NODOCS)) 00190 argerror(_("only one of --excludedocs and --includedocs may be " 00191 "specified")); 00192 00193 if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_IGNOREARCH)) 00194 argerror(_("--ignorearch may only be specified during package " 00195 "installation")); 00196 00197 if (bigMode != MODE_INSTALL && (ia->probFilter & RPMPROB_FILTER_IGNOREOS)) 00198 argerror(_("--ignoreos may only be specified during package " 00199 "installation")); 00200 00201 if (bigMode != MODE_INSTALL && bigMode != MODE_ERASE && 00202 (ia->probFilter & (RPMPROB_FILTER_DISKSPACE|RPMPROB_FILTER_DISKNODES))) 00203 argerror(_("--ignoresize may only be specified during package " 00204 "installation")); 00205 00206 if ((ia->installInterfaceFlags & UNINSTALL_ALLMATCHES) && bigMode != MODE_ERASE) 00207 argerror(_("--allmatches may only be specified during package " 00208 "erasure")); 00209 00210 if ((ia->transFlags & RPMTRANS_FLAG_ALLFILES) && bigMode != MODE_INSTALL) 00211 argerror(_("--allfiles may only be specified during package " 00212 "installation")); 00213 00214 if ((ia->transFlags & RPMTRANS_FLAG_JUSTDB) && 00215 bigMode != MODE_INSTALL && bigMode != MODE_ERASE) 00216 argerror(_("--justdb may only be specified during package " 00217 "installation and erasure")); 00218 00219 if (bigMode != MODE_INSTALL && bigMode != MODE_ERASE && bigMode != MODE_VERIFY && 00220 (ia->transFlags & (RPMTRANS_FLAG_NOSCRIPTS | _noTransScripts | _noTransTriggers))) 00221 argerror(_("script disabling options may only be specified during " 00222 "package installation and erasure")); 00223 00224 if (bigMode != MODE_INSTALL && bigMode != MODE_ERASE && bigMode != MODE_VERIFY && 00225 (ia->transFlags & (RPMTRANS_FLAG_NOTRIGGERS | _noTransTriggers))) 00226 argerror(_("trigger disabling options may only be specified during " 00227 "package installation and erasure")); 00228 00229 if (ia->noDeps & (bigMode & ~MODES_FOR_NODEPS)) 00230 argerror(_("--nodeps may only be specified during package " 00231 "installation, erasure, and verification")); 00232 00233 if ((ia->transFlags & RPMTRANS_FLAG_TEST) && (bigMode & ~MODES_FOR_TEST)) 00234 argerror(_("--test may only be specified during package installation " 00235 "and erasure")); 00236 #endif /* IAM_RPMEIU */ 00237 00238 if (rpmcliRootDir && rpmcliRootDir[0] != '/') { 00239 argerror(_("arguments to --root (-r) must begin with a /")); 00240 } 00241 00242 if (quiet) 00243 rpmSetVerbosity(RPMLOG_WARNING); 00244 00245 if (rpmcliPipeOutput && initPipe()) 00246 exit(EXIT_FAILURE); 00247 00248 ts = rpmtsCreate(); 00249 (void) rpmtsSetRootDir(ts, rpmcliRootDir); 00250 switch (bigMode) { 00251 #ifdef IAM_RPMEIU 00252 case MODE_ERASE: 00253 if (ia->noDeps) ia->installInterfaceFlags |= UNINSTALL_NODEPS; 00254 00255 if (!poptPeekArg(optCon)) { 00256 argerror(_("no packages given for erase")); 00257 } else { 00258 ec += rpmErase(ts, ia, (ARGV_const_t) poptGetArgs(optCon)); 00259 } 00260 break; 00261 00262 case MODE_INSTALL: 00263 00264 /* RPMTRANS_FLAG_KEEPOBSOLETE */ 00265 00266 if (!ia->incldocs) { 00267 if (ia->transFlags & RPMTRANS_FLAG_NODOCS) { 00268 ; 00269 } else if (rpmExpandNumeric("%{_excludedocs}")) 00270 ia->transFlags |= RPMTRANS_FLAG_NODOCS; 00271 } 00272 00273 if (ia->noDeps) ia->installInterfaceFlags |= INSTALL_NODEPS; 00274 00275 /* we've already ensured !(!ia->prefix && !ia->relocations) */ 00276 if (ia->prefix) { 00277 ia->relocations = xmalloc(2 * sizeof(*ia->relocations)); 00278 ia->relocations[0].oldPath = NULL; /* special case magic */ 00279 ia->relocations[0].newPath = ia->prefix; 00280 ia->relocations[1].oldPath = NULL; 00281 ia->relocations[1].newPath = NULL; 00282 } else if (ia->relocations) { 00283 ia->relocations = xrealloc(ia->relocations, 00284 sizeof(*ia->relocations) * (ia->numRelocations + 1)); 00285 ia->relocations[ia->numRelocations].oldPath = NULL; 00286 ia->relocations[ia->numRelocations].newPath = NULL; 00287 } 00288 00289 if (!poptPeekArg(optCon)) { 00290 argerror(_("no packages given for install")); 00291 } else { 00292 /* FIX: ia->relocations[0].newPath undefined */ 00293 ec += rpmInstall(ts, ia, (ARGV_t) poptGetArgs(optCon)); 00294 } 00295 break; 00296 00297 #endif /* IAM_RPMEIU */ 00298 00299 #ifdef IAM_RPMQV 00300 case MODE_QUERY: 00301 if (!poptPeekArg(optCon) && !(qva->qva_source == RPMQV_ALL)) 00302 argerror(_("no arguments given for query")); 00303 00304 ec = rpmcliQuery(ts, qva, (ARGV_const_t) poptGetArgs(optCon)); 00305 break; 00306 00307 case MODE_VERIFY: 00308 { rpmVerifyFlags verifyFlags = VERIFY_ALL; 00309 00310 verifyFlags &= ~qva->qva_flags; 00311 qva->qva_flags = (rpmQueryFlags) verifyFlags; 00312 00313 if (!poptPeekArg(optCon) && !(qva->qva_source == RPMQV_ALL)) 00314 argerror(_("no arguments given for verify")); 00315 ec = rpmcliVerify(ts, qva, (ARGV_const_t) poptGetArgs(optCon)); 00316 } break; 00317 #endif /* IAM_RPMQV */ 00318 00319 #if !defined(IAM_RPMQV) 00320 case MODE_QUERY: 00321 case MODE_VERIFY: 00322 #endif 00323 #if !defined(IAM_RPMEIU) 00324 case MODE_INSTALL: 00325 case MODE_ERASE: 00326 #endif 00327 case MODE_UNKNOWN: 00328 if (poptPeekArg(optCon) != NULL || argc <= 1 || rpmIsVerbose()) { 00329 printUsage(optCon, stderr, 0); 00330 ec = argc; 00331 } 00332 break; 00333 } 00334 00335 rpmtsFree(ts); 00336 if (finishPipe()) 00337 ec = EXIT_FAILURE; 00338 00339 #ifdef IAM_RPMQV 00340 free(qva->qva_queryFormat); 00341 #endif 00342 00343 #ifdef IAM_RPMEIU 00344 if (ia->relocations != NULL) { 00345 for (i = 0; i < ia->numRelocations; i++) 00346 free(ia->relocations[i].oldPath); 00347 free(ia->relocations); 00348 } 00349 #endif 00350 00351 rpmcliFini(optCon); 00352 00353 return RETVAL(ec); 00354 }