8 #include <rpm/rpmcli.h>     9 #include <rpm/rpmlib.h>                     10 #include <rpm/rpmbuild.h>    11 #include <rpm/rpmlog.h>    12 #include <rpm/rpmfileutil.h>    13 #include <rpm/rpmdb.h>    14 #include <rpm/rpmps.h>    15 #include <rpm/rpmts.h>    16 #include "lib/signature.h"    23 #define POPT_NOLANG             -1012    24 #define POPT_RMSOURCE           -1013    25 #define POPT_RMBUILD            -1014    26 #define POPT_BUILDROOT          -1015    27 #define POPT_TARGETPLATFORM     -1016    28 #define POPT_NOBUILD            -1017    29 #define POPT_RMSPEC             -1019    30 #define POPT_NODIRTOKENS        -1020    32 #define POPT_REBUILD            0x4220    33 #define POPT_RECOMPILE          0x4320    34 #define POPT_BA                 0x6261    35 #define POPT_BB                 0x6262    36 #define POPT_BC                 0x6263    37 #define POPT_BI                 0x6269    38 #define POPT_BL                 0x626c    39 #define POPT_BP                 0x6270    40 #define POPT_BS                 0x6273    41 #define POPT_TA                 0x7461    42 #define POPT_TB                 0x7462    43 #define POPT_TC                 0x7463    44 #define POPT_TI                 0x7469    45 #define POPT_TL                 0x746c    46 #define POPT_TP                 0x7470    47 #define POPT_TS                 0x7473    60         enum poptCallbackReason reason,
    61         const struct poptOption * opt, 
const char * arg,
    86             buildMode = (((unsigned)opt->val) >> 8) & 0xff;
   116  { NULL, 
'\0', POPT_ARG_CALLBACK | POPT_CBFLAG_INC_DATA | POPT_CBFLAG_CONTINUE,
   119  { 
"bp", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BP,
   120         N_(
"build through %prep (unpack sources and apply patches) from <specfile>"),
   122  { 
"bc", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BC,
   123         N_(
"build through %build (%prep, then compile) from <specfile>"),
   125  { 
"bi", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BI,
   126         N_(
"build through %install (%prep, %build, then install) from <specfile>"),
   128  { 
"bl", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BL,
   129         N_(
"verify %files section from <specfile>"),
   131  { 
"ba", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BA,
   132         N_(
"build source and binary packages from <specfile>"),
   134  { 
"bb", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BB,
   135         N_(
"build binary package only from <specfile>"),
   137  { 
"bs", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_BS,
   138         N_(
"build source package only from <specfile>"),
   141  { 
"tp", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_TP,
   142         N_(
"build through %prep (unpack sources and apply patches) from <tarball>"),
   144  { 
"tc", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_TC,
   145         N_(
"build through %build (%prep, then compile) from <tarball>"),
   147  { 
"ti", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_TI,
   148         N_(
"build through %install (%prep, %build, then install) from <tarball>"),
   150  { 
"tl", 0, POPT_ARGFLAG_ONEDASH|POPT_ARGFLAG_DOC_HIDDEN, 0, 
POPT_TL,
   151         N_(
"verify %files section from <tarball>"),
   153  { 
"ta", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_TA,
   154         N_(
"build source and binary packages from <tarball>"),
   156  { 
"tb", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_TB,
   157         N_(
"build binary package only from <tarball>"),
   159  { 
"ts", 0, POPT_ARGFLAG_ONEDASH, 0, 
POPT_TS,
   160         N_(
"build source package only from <tarball>"),
   164         N_(
"build binary package from <source package>"),
   165         N_(
"<source package>") },
   167         N_(
"build through %install (%prep, %build, then install) from <source package>"),
   168         N_(
"<source package>") },
   171         N_(
"override build root"), 
"DIRECTORY" },
   173         N_(
"remove build tree when done"), NULL},
   175         N_(
"ignore ExcludeArch: directives from spec file"), NULL},
   176  { 
"fsmdebug", 
'\0', (POPT_ARG_VAL|POPT_ARGFLAG_DOC_HIDDEN), &
_fsm_debug, -1,
   177         N_(
"debug file state machine"), NULL},
   179         N_(
"do not execute any stages of the build"), NULL },
   180  { 
"nodeps", 
'\0', POPT_ARG_VAL, &
noDeps, 1,
   181         N_(
"do not verify build dependencies"), NULL },
   183         N_(
"generate package header(s) compatible with (legacy) rpm v3 packaging"),
   187         N_(
"do not execute %clean stage of the build"), NULL },
   189         N_(
"do not execute %check stage of the build"), NULL },
   191  { 
"nolang", 
'\0', POPT_ARGFLAG_DOC_HIDDEN, 0, 
POPT_NOLANG,
   192         N_(
"do not accept i18N msgstr's from specfile"), NULL},
   194         N_(
"remove sources when done"), NULL},
   196         N_(
"remove specfile when done"), NULL},
   197  { 
"short-circuit", 
'\0', POPT_ARG_VAL, &
shortCircuit,  1,
   198         N_(
"skip straight to specified stage (only for c,i)"), NULL },
   200         N_(
"override target platform"), 
"CPU-VENDOR-OS" },
   217         N_(
"Build options with [ <specfile> | <tarball> | <source package> ]:"),
   220  { 
"quiet", 
'\0', POPT_ARGFLAG_DOC_HIDDEN, &
quiet, 0, NULL, NULL},
   223         N_(
"Common options for all rpm modes and executables:"),
   253     f = fopen(specfile, 
"r");
   256                 specfile, strerror(errno));
   259     count = fread(buf, 
sizeof(buf[0]), 
sizeof(buf), f);
   266     for (s = buf; count--; s++) {
   277             if (checking && !(isprint(*s) || isspace(*s))) 
return 0;
   280             if (checking && !(isprint(*s) || isspace(*s)) && *(
unsigned char *)s < 32) 
return 0;
   294     char *specFile = NULL;
   300     int gotspec = 0, res;
   301     static const char *tryspec[] = { 
"Specfile", 
"\\*.spec", NULL };
   304     tmpSpecFile = 
rpmGetPath(
"%{_specdir}/", 
"rpm-spec.XXXXXX", NULL);
   306     (void) close(mkstemp(tmpSpecFile));
   308     for (spec = tryspec; *spec != NULL; spec++) {
   312         cmd = 
rpmExpand(
"%{uncompress: ", arg, 
"} | ",
   313                         "%{__tar} xOvf - --wildcards ", *spec,
   314                         " 2>&1 > ", tmpSpecFile, NULL);
   316         if (!(fp = popen(cmd, 
"r"))) {
   321                 fok = fgets(tarbuf, 
sizeof(tarbuf) - 1, fp);
   323                 if (!fok || strncmp(fok, 
"tar: ", 5) != 0)
   327             gotspec = (fok != NULL) && 
isSpecFile(tmpSpecFile);
   340     specBase = basename(tarbuf);
   342     specBase[strlen(specBase)-1] = 
'\0';
   344     rasprintf(&specFile, 
"%s/%s", specDir, specBase);
   345     res = rename(tmpSpecFile, specFile);
   349                 tmpSpecFile, specFile);
   355         umask(mask = umask(0));
   356         (void) chmod(specFile, 0666 & ~mask);
   360     (void) unlink(tmpSpecFile);
   369     char * buildRootURL = NULL;
   370     char * specFile = NULL;
   380     const char * buildtree = 
"%{_topdir}:%{_specdir}:%{_sourcedir}:%{_builddir}:%{_rpmdir}:%{_srcrpmdir}:%{_buildrootdir}";
   387         char *srcdir = NULL, *dir;
   401         srcdir = dirname(dir);
   408     if (*specFile != 
'/') {
   418     if (stat(specFile, &st) < 0) {
   422     if (! S_ISREG(st.st_mode)) {
   430                 _(
"File %s does not appear to be a specfile.\n"), specFile);
   436         rc = unlink(specFile);
   441 #define _anyarch(_f)    \   442 (((_f)&(RPMBUILD_PREP|RPMBUILD_BUILD|RPMBUILD_INSTALL|RPMBUILD_PACKAGEBINARY)) == 0)   462         (void) unlink(specFile);
   476 #define buildCleanMask  (RPMBUILD_RMSOURCE|RPMBUILD_RMSPEC)   496     printf(
_(
"Building target platforms: %s\n"), targets);
   501         if (*(target + 1) == NULL)
   504         printf(
_(
"Building for target %s\n"), *target);
   526 int main(
int argc, 
char *argv[])
   532     const char *pkg = NULL;
   534     poptContext optCon = 
rpmcliInit(argc, argv, optionsTable);
   537     if (ba->
buildAmount && poptPeekArg(optCon) == NULL) {
   550         argerror(
_(
"arguments to --root (-r) must begin with a /"));
   575         while ((pkg = poptGetArg(optCon))) {
   576             char * specFile = NULL;
   585             specFile = 
_free(specFile);
   623         while ((pkg = poptGetArg(optCon))) {
 static struct poptOption rpmBuildPoptTable[]
static rpmBuildFlags nobuildAmount
const char * rpmcliRcfile
int rpmtsSetRootDir(rpmts ts, const char *rootDir)
Set transaction rootDir, i.e. 
rpmQueryFlags rpmcliQueryFlags
Bit(s) from common command line options. 
void printUsage(poptContext con, FILE *fp, int flags)
rpmps rpmSpecCheckDeps(rpmts ts, rpmSpec spec)
Verify build depencies of a spec against. 
static int buildForTarget(rpmts ts, const char *arg, BTA_t ba)
static rpmSpecFlags spec_flags
static int build(rpmts ts, const char *arg, BTA_t ba, const char *rcfile)
static struct rpmBuildArguments_s rpmBTArgs
char * rstrscat(char **dest, const char *arg,...) RPM_GNUC_NULL_TERMINATED
Concatenate multiple strings with dynamically (re)allocated memory. 
static int isSpecFile(const char *specfile)
poptContext rpmcliInit(int argc, char *const argv[], struct poptOption *optionsTable)
Initialize most everything needed by an rpm CLI executable context. 
poptContext rpmcliFini(poptContext optCon)
Destroy most everything needed by an rpm CLI executable context. 
rpmSpec rpmSpecFree(rpmSpec spec)
Destroy Spec structure. 
static ARGV_t build_targets
rpmBuildPkgFlags pkgFlags
const char * rpmtsRootDir(rpmts ts)
Get transaction rootDir, i.e. 
rpmRC rpmSpecBuild(rpmSpec spec, BTA_t buildArgs)
Spec build stages state machine driver. 
int rpmReadConfigFiles(const char *file, const char *target)
Read macro configuration file(s) for a target. 
static void buildArgCallback(poptContext con, enum poptCallbackReason reason, const struct poptOption *opt, const char *arg, const void *data)
#define POPT_TARGETPLATFORM
int argvSplit(ARGV_t *argvp, const char *str, const char *seps)
Split a string into an argv array. 
const char * rpmcliPipeOutput
void argerror(const char *desc)
rpmBuildFlags buildAmount
static int rstreq(const char *s1, const char *s2)
Test for string equality. 
static char * getTarSpec(const char *arg)
int rpmExpandNumeric(const char *arg)
Return macro expansion as a numeric value. 
int rpmInstallSource(rpmts ts, const char *arg, char **specFilePtr, char **cookie)
Install source rpm package. 
static struct poptOption optionsTable[]
int rpmMkdirs(const char *root, const char *pathstr)
Create several directories (including parents if needed) in one go. 
const char * rpmcliRootDir
rpmps rpmpsFree(rpmps ps)
Destroy a problem set. 
char * rpmGetPath(const char *path,...) RPM_GNUC_NULL_TERMINATED
Return (malloc'ed) expanded, canonicalized, file path. 
#define RPMCLI_POPT_FORCE
void addMacro(rpmMacroContext mc, const char *n, const char *o, const char *b, int level)
Add macro to context. 
ARGV_t argvFree(ARGV_t argv)
Destroy an argv array. 
char *const * ARGV_const_t
#define _RPMVSF_NOSIGNATURES
rpmts rpmtsFree(rpmts ts)
Destroy transaction set, closing the database as well. 
static int checkSpec(rpmts ts, rpmSpec spec)
void rpmFreeMacros(rpmMacroContext mc)
Destroy macro context. 
rpmSpec rpmSpecParse(const char *specFile, rpmSpecFlags flags, const char *buildRoot)
Parse spec file into spec control structure. 
rpmVSFlags rpmtsSetVSFlags(rpmts ts, rpmVSFlags vsflags)
Set verify signatures flag(s). 
char * rpmExpand(const char *arg,...) RPM_GNUC_NULL_TERMINATED
Return (malloc'ed) concatenated macro expansion(s). 
struct rpmts_s * rpmts
The main types involved in transaction manipulation. 
int rasprintf(char **strp, const char *fmt,...) RPM_GNUC_PRINTF(2
asprintf() clone 
void rpmFreeRpmrc(void)
Destroy rpmrc arch/os compatibility tables. 
#define _RPMVSF_NODIGESTS
#define rpmSetVerbosity(_lvl)
void rpmpsPrint(FILE *fp, rpmps ps)
Print problems to file handle. 
rpmts rpmtsCreate(void)
Create an empty transaction set. 
char * rpmGenPath(const char *urlroot, const char *urlmdir, const char *urlfile)
Merge 3 args into path, any or all of which may be a url. 
char * rpmGetCwd(void)
Like getcwd() but the result is malloced. 
struct poptOption rpmcliAllPoptTable[]
Popt option table for options shared by all modes and executables. 
char * argvJoin(ARGV_const_t argv, const char *sep)
Join an argv array into a string. 
int main(int argc, char *argv[])
void rpmlog(int code, const char *fmt,...) RPM_GNUC_PRINTF(2
Generate a log message using FMT string and option arguments. 
struct rpmSpec_s * rpmSpec