00001
00006 #include "system.h"
00007
00008 #include "buildio.h"
00009 #include "debug.h"
00010
00011
00012 extern int specedit;
00013
00014
00015 #define SKIPWHITE(_x) {while(*(_x) && (xisspace(*_x) || *(_x) == ',')) (_x)++;}
00016 #define SKIPNONWHITE(_x){while(*(_x) &&!(xisspace(*_x) || *(_x) == ',')) (_x)++;}
00017
00018
00019
00024 static inline
00025 struct TriggerFileEntry * freeTriggerFiles( struct TriggerFileEntry * p)
00026
00027 {
00028 struct TriggerFileEntry *o, *q = p;
00029
00030 while (q != NULL) {
00031 o = q;
00032 q = q->next;
00033 o->fileName = _free(o->fileName);
00034 o->script = _free(o->script);
00035 o->prog = _free(o->prog);
00036 o = _free(o);
00037 }
00038 return NULL;
00039 }
00040
00046 static inline
00047 struct Source * freeSources( struct Source * s)
00048
00049 {
00050 struct Source *r, *t = s;
00051
00052 while (t != NULL) {
00053 r = t;
00054 t = t->next;
00055 r->fullSource = _free(r->fullSource);
00056 r = _free(r);
00057 }
00058 return NULL;
00059 }
00060
00061 int lookupPackage(Spec spec, const char *name, int flag, Package *pkg)
00062 {
00063 const char *pname;
00064 const char *fullName;
00065 Package p;
00066
00067
00068 if (name == NULL) {
00069 if (pkg)
00070 *pkg = spec->packages;
00071 return 0;
00072 }
00073
00074
00075 { char *n;
00076 if (flag == PART_SUBNAME) {
00077 (void) headerNVR(spec->packages->header, &pname, NULL, NULL);
00078 fullName = n = alloca(strlen(pname) + 1 + strlen(name) + 1);
00079 while (*pname != '\0') *n++ = *pname++;
00080 *n++ = '-';
00081 } else {
00082 fullName = n = alloca(strlen(name)+1);
00083 }
00084
00085 strcpy(n, name);
00086
00087 }
00088
00089
00090 for (p = spec->packages; p != NULL; p = p->next) {
00091 (void) headerNVR(p->header, &pname, NULL, NULL);
00092 if (pname && (! strcmp(fullName, pname))) {
00093 break;
00094 }
00095 }
00096
00097 if (pkg)
00098 *pkg = p;
00099 return ((p == NULL) ? 1 : 0);
00100 }
00101
00102 Package newPackage(Spec spec)
00103 {
00104 Package p;
00105 Package pp;
00106
00107 p = xcalloc(1, sizeof(*p));
00108
00109 p->header = headerNew();
00110 p->icon = NULL;
00111
00112 p->autoProv = 1;
00113 p->autoReq = 1;
00114
00115 #if 0
00116 p->reqProv = NULL;
00117 p->triggers = NULL;
00118 p->triggerScripts = NULL;
00119 #endif
00120
00121 p->triggerFiles = NULL;
00122
00123 p->fileFile = NULL;
00124 p->fileList = NULL;
00125
00126 p->cpioList = NULL;
00127
00128 p->preInFile = NULL;
00129 p->postInFile = NULL;
00130 p->preUnFile = NULL;
00131 p->postUnFile = NULL;
00132 p->verifyFile = NULL;
00133
00134 p->specialDoc = NULL;
00135
00136 if (spec->packages == NULL) {
00137 spec->packages = p;
00138 } else {
00139
00140 for (pp = spec->packages; pp->next != NULL; pp = pp->next)
00141 {};
00142 pp->next = p;
00143 }
00144 p->next = NULL;
00145
00146 return p;
00147 }
00148
00149 Package freePackage(Package pkg)
00150 {
00151 if (pkg == NULL) return NULL;
00152
00153 pkg->preInFile = _free(pkg->preInFile);
00154 pkg->postInFile = _free(pkg->postInFile);
00155 pkg->preUnFile = _free(pkg->preUnFile);
00156 pkg->postUnFile = _free(pkg->postUnFile);
00157 pkg->verifyFile = _free(pkg->verifyFile);
00158
00159 pkg->header = headerFree(pkg->header);
00160 pkg->fileList = freeStringBuf(pkg->fileList);
00161 pkg->fileFile = _free(pkg->fileFile);
00162 if (pkg->cpioList) {
00163 TFI_t fi = pkg->cpioList;
00164 pkg->cpioList = NULL;
00165 freeFi(fi);
00166 fi = _free(fi);
00167 }
00168
00169 pkg->specialDoc = freeStringBuf(pkg->specialDoc);
00170 pkg->icon = freeSources(pkg->icon);
00171 pkg->triggerFiles = freeTriggerFiles(pkg->triggerFiles);
00172
00173 pkg = _free(pkg);
00174 return NULL;
00175 }
00176
00177 Package freePackages(Package packages)
00178 {
00179 Package p;
00180
00181 while ((p = packages) != NULL) {
00182 packages = p->next;
00183 p->next = NULL;
00184 p = freePackage(p);
00185 }
00186 return NULL;
00187 }
00188
00191 static inline struct Source *findSource(Spec spec, int num, int flag)
00192
00193 {
00194 struct Source *p;
00195
00196 for (p = spec->sources; p != NULL; p = p->next)
00197 if ((num == p->num) && (p->flags & flag)) return p;
00198
00199 return NULL;
00200 }
00201
00202 int parseNoSource(Spec spec, const char * field, int tag)
00203 {
00204 const char *f, *fe;
00205 const char *name;
00206 int num, flag;
00207
00208 if (tag == RPMTAG_NOSOURCE) {
00209 flag = RPMBUILD_ISSOURCE;
00210 name = "source";
00211 } else {
00212 flag = RPMBUILD_ISPATCH;
00213 name = "patch";
00214 }
00215
00216 fe = field;
00217 for (f = fe; *f != '\0'; f = fe) {
00218 struct Source *p;
00219
00220 SKIPWHITE(f);
00221 if (*f == '\0')
00222 break;
00223 fe = f;
00224 SKIPNONWHITE(fe);
00225 if (*fe != '\0') fe++;
00226
00227 if (parseNum(f, &num)) {
00228 rpmError(RPMERR_BADSPEC, _("line %d: Bad number: %s\n"),
00229 spec->lineNum, f);
00230 return RPMERR_BADSPEC;
00231 }
00232
00233 if (! (p = findSource(spec, num, flag))) {
00234 rpmError(RPMERR_BADSPEC, _("line %d: Bad no%s number: %d\n"),
00235 spec->lineNum, name, num);
00236 return RPMERR_BADSPEC;
00237 }
00238
00239 p->flags |= RPMBUILD_ISNO;
00240
00241 }
00242
00243 return 0;
00244 }
00245
00246 int addSource(Spec spec, Package pkg, const char *field, int tag)
00247 {
00248 struct Source *p;
00249 int flag = 0;
00250 char *name = NULL;
00251 char *nump;
00252 const char *fieldp = NULL;
00253 char buf[BUFSIZ];
00254 int num = 0;
00255
00256 buf[0] = '\0';
00257
00258 switch (tag) {
00259 case RPMTAG_SOURCE:
00260 flag = RPMBUILD_ISSOURCE;
00261 name = "source";
00262 fieldp = spec->line + 6;
00263 break;
00264 case RPMTAG_PATCH:
00265 flag = RPMBUILD_ISPATCH;
00266 name = "patch";
00267 fieldp = spec->line + 5;
00268 break;
00269 case RPMTAG_ICON:
00270 flag = RPMBUILD_ISICON;
00271 fieldp = NULL;
00272 break;
00273 }
00274
00275
00276
00277 if (tag != RPMTAG_ICON) {
00278
00279
00280
00281
00282
00283 nump = buf;
00284 while ((*fieldp != ':') && (*fieldp != ' ') && (*fieldp != '\t')) {
00285 *nump++ = *fieldp++;
00286 }
00287 *nump = '\0';
00288
00289 nump = buf;
00290 SKIPSPACE(nump);
00291 if (nump == NULL || *nump == '\0') {
00292 num = 0;
00293 } else {
00294 if (parseNum(buf, &num)) {
00295 rpmError(RPMERR_BADSPEC, _("line %d: Bad %s number: %s\n"),
00296 spec->lineNum, name, spec->line);
00297 return RPMERR_BADSPEC;
00298 }
00299 }
00300 }
00301
00302
00303 p = xmalloc(sizeof(*p));
00304 p->num = num;
00305 p->fullSource = xstrdup(field);
00306 p->flags = flag;
00307 p->source = strrchr(p->fullSource, '/');
00308 if (p->source) {
00309 p->source++;
00310 } else {
00311 p->source = p->fullSource;
00312 }
00313
00314 if (tag != RPMTAG_ICON) {
00315 p->next = spec->sources;
00316 spec->sources = p;
00317 } else {
00318 p->next = pkg->icon;
00319 pkg->icon = p;
00320 }
00321
00322 spec->numSources++;
00323
00324 if (tag != RPMTAG_ICON) {
00325
00326 const char *body = rpmGetPath("%{_sourcedir}/", p->source, NULL);
00327
00328
00329 sprintf(buf, "%s%d",
00330 (flag & RPMBUILD_ISPATCH) ? "PATCH" : "SOURCE", num);
00331 addMacro(spec->macros, buf, NULL, body, RMIL_SPEC);
00332 sprintf(buf, "%sURL%d",
00333 (flag & RPMBUILD_ISPATCH) ? "PATCH" : "SOURCE", num);
00334 addMacro(spec->macros, buf, NULL, p->fullSource, RMIL_SPEC);
00335 body = _free(body);
00336 }
00337
00338 return 0;
00339 }
00340
00343 static inline speclines newSl(void)
00344
00345 {
00346 speclines sl = NULL;
00347
00348 if (specedit) {
00349 sl = xmalloc(sizeof(*sl));
00350 sl->sl_lines = NULL;
00351 sl->sl_nalloc = 0;
00352 sl->sl_nlines = 0;
00353 }
00354
00355 return sl;
00356 }
00357
00360 static inline speclines freeSl( speclines sl)
00361
00362 {
00363 int i;
00364 if (sl == NULL) return NULL;
00365 for (i = 0; i < sl->sl_nlines; i++)
00366
00367 sl->sl_lines[i] = _free(sl->sl_lines[i]);
00368
00369 sl->sl_lines = _free(sl->sl_lines);
00370 return _free(sl);
00371 }
00372
00375 static inline spectags newSt(void)
00376
00377 {
00378 spectags st = NULL;
00379
00380 if (specedit) {
00381 st = xmalloc(sizeof(*st));
00382 st->st_t = NULL;
00383 st->st_nalloc = 0;
00384 st->st_ntags = 0;
00385 }
00386
00387 return st;
00388 }
00389
00392 static inline spectags freeSt( spectags st)
00393
00394 {
00395 int i;
00396 if (st == NULL) return NULL;
00397 for (i = 0; i < st->st_ntags; i++) {
00398 spectag t = st->st_t + i;
00399 t->t_lang = _free(t->t_lang);
00400 t->t_msgid = _free(t->t_msgid);
00401 }
00402 st->st_t = _free(st->st_t);
00403 return _free(st);
00404 }
00405
00406 Spec newSpec(void)
00407 {
00408 Spec spec = xcalloc(1, sizeof(*spec));
00409
00410 spec->specFile = NULL;
00411 spec->sourceRpmName = NULL;
00412
00413 spec->sl = newSl();
00414 spec->st = newSt();
00415
00416 spec->fileStack = NULL;
00417 spec->lbuf[0] = '\0';
00418 spec->line = spec->lbuf;
00419 spec->nextline = NULL;
00420 spec->nextpeekc = '\0';
00421 spec->lineNum = 0;
00422 spec->readStack = xcalloc(1, sizeof(*spec->readStack));
00423 spec->readStack->next = NULL;
00424 spec->readStack->reading = 1;
00425
00426 spec->rootURL = NULL;
00427 spec->prep = NULL;
00428 spec->build = NULL;
00429 spec->install = NULL;
00430 spec->clean = NULL;
00431
00432 spec->sources = NULL;
00433 spec->packages = NULL;
00434 spec->noSource = 0;
00435 spec->numSources = 0;
00436
00437 spec->sourceHeader = NULL;
00438
00439 spec->sourceCpioList = NULL;
00440
00441 spec->gotBuildRootURL = 0;
00442 spec->buildRootURL = NULL;
00443 spec->buildSubdir = NULL;
00444
00445 spec->passPhrase = NULL;
00446 spec->timeCheck = 0;
00447 spec->cookie = NULL;
00448
00449 spec->buildRestrictions = headerNew();
00450 spec->BANames = NULL;
00451 spec->BACount = 0;
00452 spec->recursing = 0;
00453 spec->BASpecs = NULL;
00454
00455 spec->force = 0;
00456 spec->anyarch = 0;
00457
00458 spec->macros = rpmGlobalMacroContext;
00459
00460 return spec;
00461 }
00462
00463 Spec freeSpec(Spec spec)
00464 {
00465 struct ReadLevelEntry *rl;
00466
00467 if (spec == NULL) return NULL;
00468
00469 spec->sl = freeSl(spec->sl);
00470 spec->st = freeSt(spec->st);
00471
00472 spec->prep = freeStringBuf(spec->prep);
00473 spec->build = freeStringBuf(spec->build);
00474 spec->install = freeStringBuf(spec->install);
00475 spec->clean = freeStringBuf(spec->clean);
00476
00477 spec->buildRootURL = _free(spec->buildRootURL);
00478 spec->buildSubdir = _free(spec->buildSubdir);
00479 spec->rootURL = _free(spec->rootURL);
00480 spec->specFile = _free(spec->specFile);
00481 spec->sourceRpmName = _free(spec->sourceRpmName);
00482
00483 #ifdef DEAD
00484 { struct OpenFileInfo *ofi;
00485 while (spec->fileStack) {
00486 ofi = spec->fileStack;
00487 spec->fileStack = ofi->next;
00488 ofi->next = NULL;
00489 ofi->fileName = _free(ofi->fileName);
00490 ofi = _free(ofi);
00491 }
00492 }
00493 #else
00494 closeSpec(spec);
00495 #endif
00496
00497 while (spec->readStack) {
00498 rl = spec->readStack;
00499
00500 spec->readStack = rl->next;
00501
00502 rl->next = NULL;
00503 rl = _free(rl);
00504 }
00505
00506 spec->sourceHeader = headerFree(spec->sourceHeader);
00507
00508 if (spec->sourceCpioList) {
00509 TFI_t fi = spec->sourceCpioList;
00510 spec->sourceCpioList = NULL;
00511 freeFi(fi);
00512 fi = _free(fi);
00513 }
00514
00515 spec->buildRestrictions = headerFree(spec->buildRestrictions);
00516
00517 if (!spec->recursing) {
00518 if (spec->BASpecs != NULL)
00519 while (spec->BACount--) {
00520
00521 spec->BASpecs[spec->BACount] =
00522 freeSpec(spec->BASpecs[spec->BACount]);
00523
00524 }
00525
00526 spec->BASpecs = _free(spec->BASpecs);
00527
00528 }
00529 spec->BANames = _free(spec->BANames);
00530
00531 spec->passPhrase = _free(spec->passPhrase);
00532 spec->cookie = _free(spec->cookie);
00533
00534 spec->sources = freeSources(spec->sources);
00535 spec->packages = freePackages(spec->packages);
00536
00537 spec = _free(spec);
00538
00539 return spec;
00540 }
00541
00542 struct OpenFileInfo * newOpenFileInfo(void)
00543 {
00544 struct OpenFileInfo *ofi;
00545
00546 ofi = xmalloc(sizeof(*ofi));
00547 ofi->fd = NULL;
00548 ofi->fileName = NULL;
00549 ofi->lineNum = 0;
00550 ofi->readBuf[0] = '\0';
00551 ofi->readPtr = NULL;
00552 ofi->next = NULL;
00553
00554 return ofi;
00555 }