rpm 5.2.1

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

- File List
- Globals

lib/rpmte.c
Go to the documentation of this file.

    00001
    00005 #include "system.h"
    00006
    00007 #include <rpmio.h>
    00008 #include <rpmiotypes.h>         /* XXX fnpyKey */
    00009
    00010 #include <rpmtypes.h>
    00011 #include <rpmtag.h>
    00012
    00013 #include "rpmds.h"
    00014 #include "rpmfi.h"
    00015
    00016 #define _RPMTE_INTERNAL
    00017 #include "rpmte.h"
    00018 #include "rpmts.h"
    00019
    00020 #include "debug.h"
    00021
    00022 /*@unchecked@*/
    00023 int _rpmte_debug = 0;
    00024
    00025 /*@access alKey @*/
    00026 /*@access rpmts @*/     /* XXX cast */
    00027 /*@access rpmtsi @*/
    00028
    00029 void rpmteCleanDS(rpmte te)
    00030 {
    00031     te->PRCO = rpmdsFreePRCO(te->PRCO);
    00032 }
    00033
    00038 static void delTE(rpmte p)
    00039         /*@globals fileSystem @*/
    00040         /*@modifies p, fileSystem @*/
    00041 {
    00042     p->relocs = rpmfiFreeRelocations(p->relocs);
    00043
    00044     rpmteCleanDS(p);
    00045
    00046     p->fi = rpmfiFree(p->fi);
    00047
    00048 /*@-refcounttrans@*/    /* FIX: XfdFree annotation */
    00049     if (p->fd != NULL)
    00050         p->fd = fdFree(p->fd, "delTE");
    00051 /*@=refcounttrans@*/
    00052
    00053     p->os = _free(p->os);
    00054     p->arch = _free(p->arch);
    00055     p->epoch = _free(p->epoch);
    00056     p->name = _free(p->name);
    00057     p->version = _free(p->version);
    00058     p->release = _free(p->release);
    00059 #ifdef  RPM_VENDOR_MANDRIVA
    00060     p->distepoch = _free(p->distepoch);
    00061 #endif
    00062     p->NEVR = _free(p->NEVR);
    00063     p->NEVRA = _free(p->NEVRA);
    00064     p->pkgid = _free(p->pkgid);
    00065     p->hdrid = _free(p->hdrid);
    00066     p->sourcerpm = _free(p->sourcerpm);
    00067
    00068     p->replaced = _free(p->replaced);
    00069
    00070     p->flink.NEVRA = argvFree(p->flink.NEVRA);
    00071     p->flink.Pkgid = argvFree(p->flink.Pkgid);
    00072     p->flink.Hdrid = argvFree(p->flink.Hdrid);
    00073     p->blink.NEVRA = argvFree(p->blink.NEVRA);
    00074     p->blink.Pkgid = argvFree(p->blink.Pkgid);
    00075     p->blink.Hdrid = argvFree(p->blink.Hdrid);
    00076
    00077     (void)headerFree(p->h);
    00078     p->h = NULL;
    00079
    00080     /*@-nullstate@*/ /* FIX: p->{NEVR,name} annotations */
    00081     return;
    00082     /*@=nullstate@*/
    00083 }
    00084
    00093 static void addTE(rpmts ts, rpmte p, Header h,
    00094                 /*@dependent@*/ /*@null@*/ fnpyKey key,
    00095                 /*@null@*/ rpmRelocation relocs)
    00096         /*@globals rpmGlobalMacroContext, h_errno, fileSystem, internalState @*/
    00097         /*@modifies ts, p, h,
    00098                 rpmGlobalMacroContext, fileSystem, internalState @*/
    00099 {
    00100     int scareMem = 0;
    00101     HE_t he = memset(alloca(sizeof(*he)), 0, sizeof(*he));
    00102     int xx;
    00103
    00104     he->tag = RPMTAG_NVRA;
    00105     xx = headerGet(h, he, 0);
    00106 assert(he->p.str != NULL);
    00107     p->NEVR = (xx ? he->p.str : xstrdup("?N-?V-?R.?A"));
    00108
    00109     he->tag = RPMTAG_NAME;
    00110     xx = headerGet(h, he, 0);
    00111     p->name = (xx ? he->p.str : xstrdup("?RPMTAG_NAME?"));
    00112     he->tag = RPMTAG_VERSION;
    00113     xx = headerGet(h, he, 0);
    00114     p->version = (char *)(xx ? he->p.str : xstrdup("?RPMTAG_VERSION?"));
    00115     he->tag = RPMTAG_RELEASE;
    00116     xx = headerGet(h, he, 0);
    00117     p->release = (char *)(xx ? he->p.str : xstrdup("?RPMTAG_RELEASE?"));
    00118
    00119     p->db_instance = 0;
    00120
    00121     he->tag = RPMTAG_PKGID;
    00122     xx = headerGet(h, he, 0);
    00123     if (he->p.ui8p != NULL) {
    00124         static const char hex[] = "0123456789abcdef";
    00125         char * t;
    00126         rpmuint32_t i;
    00127
    00128         p->pkgid = t = xmalloc((2*he->c) + 1);
    00129         for (i = 0 ; i < he->c; i++) {
    00130             *t++ = hex[ (unsigned)((he->p.ui8p[i] >> 4) & 0x0f) ];
    00131             *t++ = hex[ (unsigned)((he->p.ui8p[i]     ) & 0x0f) ];
    00132         }
    00133         *t = '\0';
    00134         he->p.ptr = _free(he->p.ptr);
    00135     } else
    00136         p->pkgid = NULL;
    00137
    00138     he->tag = RPMTAG_HDRID;
    00139     xx = headerGet(h, he, 0);
    00140     p->hdrid = (xx ? he->p.str : xstrdup("?RPMTAG_HDRID?"));
    00141
    00142     he->tag = RPMTAG_SOURCERPM;
    00143     xx = headerGet(h, he, 0);
    00144     p->sourcerpm = (xx ? he->p.str : NULL);
    00145
    00146     he->tag = RPMTAG_ARCH;
    00147     xx = headerGet(h, he, 0);
    00148     p->arch = (xx ? he->p.str : xstrdup("?RPMTAG_ARCH?"));
    00149
    00150     he->tag = RPMTAG_OS;
    00151     xx = headerGet(h, he, 0);
    00152     p->os = (xx ? he->p.str : xstrdup("?RPMTAG_OS?"));
    00153
    00154     p->isSource =
    00155         (headerIsEntry(h, RPMTAG_SOURCERPM) == 0 &&
    00156          headerIsEntry(h, RPMTAG_ARCH) != 0);
    00157
    00158     p->NEVRA = xstrdup(p->NEVR);
    00159
    00160     he->tag = RPMTAG_EPOCH;
    00161     xx = headerGet(h, he, 0);
    00162     if (he->p.ui32p != NULL) {
    00163         p->epoch = xmalloc(20);
    00164         sprintf(p->epoch, "%u", he->p.ui32p[0]);
    00165         he->p.ptr = _free(he->p.ptr);
    00166     } else
    00167         p->epoch = NULL;
    00168
    00169 #ifdef  RPM_VENDOR_MANDRIVA
    00170     he->tag = RPMTAG_DISTEPOCH;
    00171     xx = headerGet(h, he, 0);
    00172     if (he->p.str != NULL) {
    00173         p->distepoch = (char*)(xx ? he->p.str : xstrdup("?RPMTAG_DISTEPOCH?"));
    00174     } else
    00175         p->distepoch = NULL;
    00176 #endif
    00177
    00178     p->installed = 0;
    00179
    00180     p->relocs = rpmfiDupeRelocations(relocs, &p->nrelocs);
    00181     p->autorelocatex = -1;
    00182
    00183     p->key = key;
    00184     p->fd = NULL;
    00185
    00186     p->replaced = NULL;
    00187
    00188     p->pkgFileSize = 0;
    00189     memset(p->originTid, 0, sizeof(p->originTid));
    00190     memset(p->originTime, 0, sizeof(p->originTime));
    00191
    00192     p->PRCO = rpmdsNewPRCO(h);
    00193
    00194     {   rpmte savep = rpmtsSetRelocateElement(ts, p);
    00195         p->fi = rpmfiNew(ts, h, RPMTAG_BASENAMES, scareMem);
    00196         (void) rpmtsSetRelocateElement(ts, savep);
    00197     }
    00198
    00199     rpmteColorDS(p, RPMTAG_PROVIDENAME);
    00200     rpmteColorDS(p, RPMTAG_REQUIRENAME);
    00201 /*@-compdef@*/
    00202     return;
    00203 /*@=compdef@*/
    00204 }
    00205
    00206 static void rpmteFini(void * _te)
    00207         /*@modifies _te @*/
    00208 {
    00209     rpmte te = _te;
    00210
    00211     delTE(te);
    00212 }
    00213
    00214 /*@unchecked@*/ /*@only@*/ /*@null@*/
    00215 rpmioPool _rpmtePool;
    00216
    00217 static rpmte rpmteGetPool(/*@null@*/ rpmioPool pool)
    00218         /*@globals _rpmtePool, fileSystem, internalState @*/
    00219         /*@modifies pool, _rpmtePool, fileSystem, internalState @*/
    00220 {
    00221     rpmte te;
    00222
    00223     if (_rpmtePool == NULL) {
    00224         _rpmtePool = rpmioNewPool("te", sizeof(*te), -1, _rpmte_debug,
    00225                         NULL, NULL, rpmteFini);
    00226         pool = _rpmtePool;
    00227     }
    00228     return (rpmte) rpmioGetPool(pool, sizeof(*te));
    00229 }
    00230
    00231 rpmte rpmteNew(const rpmts ts, Header h,
    00232                 rpmElementType type,
    00233                 fnpyKey key,
    00234                 rpmRelocation relocs,
    00235                 int dboffset,
    00236                 alKey pkgKey)
    00237 {
    00238     HE_t he = memset(alloca(sizeof(*he)), 0, sizeof(*he));
    00239     rpmte p = rpmteGetPool(_rpmtePool);
    00240     int xx;
    00241
    00242     p->type = type;
    00243
    00244     addTE(ts, p, h, key, relocs);
    00245     switch (type) {
    00246     case TR_ADDED:
    00247         p->u.addedKey = pkgKey;
    00248         /* XXX 256 is only an estimate of signature header. */
    00249         p->pkgFileSize = 96 + 256;
    00250         he->tag = RPMTAG_SIGSIZE;
    00251         xx = headerGet(h, he, 0);
    00252         if (xx && he->p.ui32p)
    00253             p->pkgFileSize += *he->p.ui32p;
    00254         he->p.ptr = _free(he->p.ptr);
    00255         break;
    00256     case TR_REMOVED:
    00257         p->u.addedKey = pkgKey;
    00258         p->u.removed.dboffset = dboffset;
    00259         break;
    00260     }
    00261     return p;
    00262 }
    00263
    00264 /* Get the DB Instance value */
    00265 unsigned int rpmteDBInstance(rpmte te)
    00266 {
    00267     return (te != NULL ? te->db_instance : 0);
    00268 }
    00269
    00270 /* Set the DB Instance value */
    00271 void rpmteSetDBInstance(rpmte te, unsigned int instance)
    00272 {
    00273     if (te != NULL)
    00274         te->db_instance = instance;
    00275 }
    00276
    00277 Header rpmteHeader(rpmte te)
    00278 {
    00279 /*@-castexpose -retalias -retexpose @*/
    00280     return (te != NULL && te->h != NULL ? headerLink(te->h) : NULL);
    00281 /*@=castexpose =retalias =retexpose @*/
    00282 }
    00283
    00284 Header rpmteSetHeader(rpmte te, Header h)
    00285 {
    00286     if (te != NULL)  {
    00287         (void)headerFree(te->h);
    00288         te->h = NULL;
    00289 /*@-assignexpose -castexpose @*/
    00290         if (h != NULL)
    00291             te->h = headerLink(h);
    00292 /*@=assignexpose =castexpose @*/
    00293     }
    00294     return NULL;
    00295 }
    00296
    00297 rpmElementType rpmteType(rpmte te)
    00298 {
    00299     return (te != NULL ? te->type : (rpmElementType)-1);
    00300 }
    00301
    00302 const char * rpmteN(rpmte te)
    00303 {
    00304     return (te != NULL ? te->name : NULL);
    00305 }
    00306
    00307 const char * rpmteE(rpmte te)
    00308 {
    00309     return (te != NULL ? te->epoch : NULL);
    00310 }
    00311
    00312 const char * rpmteV(rpmte te)
    00313 {
    00314     return (te != NULL ? te->version : NULL);
    00315 }
    00316
    00317 const char * rpmteR(rpmte te)
    00318 {
    00319     return (te != NULL ? te->release : NULL);
    00320 }
    00321
    00322 #ifdef  RPM_VENDOR_MANDRIVA
    00323 const char * rpmteD(rpmte te)
    00324 {
    00325     return (te != NULL ? te->distepoch : NULL);
    00326 }
    00327 #endif
    00328
    00329 const char * rpmteA(rpmte te)
    00330 {
    00331     return (te != NULL ? te->arch : NULL);
    00332 }
    00333
    00334 const char * rpmteO(rpmte te)
    00335 {
    00336     return (te != NULL ? te->os : NULL);
    00337 }
    00338
    00339 int rpmteIsSource(rpmte te)
    00340 {
    00341     return (te != NULL ? te->isSource : 0);
    00342 }
    00343
    00344 rpmuint32_t rpmteColor(rpmte te)
    00345 {
    00346     return (te != NULL ? te->color : 0);
    00347 }
    00348
    00349 rpmuint32_t rpmteSetColor(rpmte te, rpmuint32_t color)
    00350 {
    00351     int ocolor = 0;
    00352     if (te != NULL) {
    00353         ocolor = te->color;
    00354         te->color = color;
    00355     }
    00356     return ocolor;
    00357 }
    00358
    00359 rpmuint32_t rpmtePkgFileSize(rpmte te)
    00360 {
    00361     return (te != NULL ? te->pkgFileSize : 0);
    00362 }
    00363
    00364 rpmuint32_t * rpmteOriginTid(rpmte te)
    00365 {
    00366     return te->originTid;
    00367 }
    00368
    00369 rpmuint32_t * rpmteOriginTime(rpmte te)
    00370 {
    00371     return te->originTime;
    00372 }
    00373
    00374 int rpmteDepth(rpmte te)
    00375 {
    00376     return (te != NULL ? te->depth : 0);
    00377 }
    00378
    00379 int rpmteSetDepth(rpmte te, int ndepth)
    00380 {
    00381     int odepth = 0;
    00382     if (te != NULL) {
    00383         odepth = te->depth;
    00384         te->depth = ndepth;
    00385     }
    00386     return odepth;
    00387 }
    00388
    00389 int rpmteBreadth(rpmte te)
    00390 {
    00391     return (te != NULL ? te->depth : 0);
    00392 }
    00393
    00394 int rpmteSetBreadth(rpmte te, int nbreadth)
    00395 {
    00396     int obreadth = 0;
    00397     if (te != NULL) {
    00398         obreadth = te->breadth;
    00399         te->breadth = nbreadth;
    00400     }
    00401     return obreadth;
    00402 }
    00403
    00404 int rpmteNpreds(rpmte te)
    00405 {
    00406     return (te != NULL ? te->npreds : 0);
    00407 }
    00408
    00409 int rpmteSetNpreds(rpmte te, int npreds)
    00410 {
    00411     int opreds = 0;
    00412     if (te != NULL) {
    00413         opreds = te->npreds;
    00414         te->npreds = npreds;
    00415     }
    00416     return opreds;
    00417 }
    00418
    00419 int rpmteTree(rpmte te)
    00420 {
    00421     return (te != NULL ? te->tree : 0);
    00422 }
    00423
    00424 int rpmteSetTree(rpmte te, int ntree)
    00425 {
    00426     int otree = 0;
    00427     if (te != NULL) {
    00428         otree = te->tree;
    00429         te->tree = ntree;
    00430     }
    00431     return otree;
    00432 }
    00433
    00434 rpmte rpmteParent(rpmte te)
    00435 {
    00436     return (te != NULL ? te->parent : NULL);
    00437 }
    00438
    00439 rpmte rpmteSetParent(rpmte te, rpmte pte)
    00440 {
    00441     rpmte opte = NULL;
    00442     if (te != NULL) {
    00443         opte = te->parent;
    00444         /*@-assignexpose -temptrans@*/
    00445         te->parent = pte;
    00446         /*@=assignexpose =temptrans@*/
    00447     }
    00448     return opte;
    00449 }
    00450
    00451 int rpmteDegree(rpmte te)
    00452 {
    00453     return (te != NULL ? te->degree : 0);
    00454 }
    00455
    00456 int rpmteSetDegree(rpmte te, int ndegree)
    00457 {
    00458     int odegree = 0;
    00459     if (te != NULL) {
    00460         odegree = te->degree;
    00461         te->degree = ndegree;
    00462     }
    00463     return odegree;
    00464 }
    00465
    00466 tsortInfo rpmteTSI(rpmte te)
    00467 {
    00468     /*@-compdef -retalias -retexpose -usereleased @*/
    00469     return te->tsi;
    00470     /*@=compdef =retalias =retexpose =usereleased @*/
    00471 }
    00472
    00473 void rpmteFreeTSI(rpmte te)
    00474 {
    00475     if (te != NULL && rpmteTSI(te) != NULL) {
    00476         tsortInfo tsi;
    00477
    00478         /* Clean up tsort remnants (if any). */
    00479         while ((tsi = rpmteTSI(te)->tsi_next) != NULL) {
    00480             rpmteTSI(te)->tsi_next = tsi->tsi_next;
    00481             tsi->tsi_next = NULL;
    00482             tsi = _free(tsi);
    00483         }
    00484         te->tsi = _free(te->tsi);
    00485     }
    00486     /*@-nullstate@*/ /* FIX: te->tsi is NULL */
    00487     return;
    00488     /*@=nullstate@*/
    00489 }
    00490
    00491 void rpmteNewTSI(rpmte te)
    00492 {
    00493     if (te != NULL) {
    00494         rpmteFreeTSI(te);
    00495         te->tsi = xcalloc(1, sizeof(*te->tsi));
    00496     }
    00497 }
    00498
    00499 alKey rpmteAddedKey(rpmte te)
    00500 {
    00501     return (te != NULL ? te->u.addedKey : RPMAL_NOMATCH);
    00502 }
    00503
    00504 alKey rpmteSetAddedKey(rpmte te, alKey npkgKey)
    00505 {
    00506     alKey opkgKey = RPMAL_NOMATCH;
    00507     if (te != NULL) {
    00508         opkgKey = te->u.addedKey;
    00509         te->u.addedKey = npkgKey;
    00510     }
    00511     return opkgKey;
    00512 }
    00513
    00514
    00515 int rpmteDBOffset(rpmte te)
    00516 {
    00517     return (te != NULL ? te->u.removed.dboffset : 0);
    00518 }
    00519
    00520 const char * rpmteNEVR(rpmte te)
    00521 {
    00522     return (te != NULL ? te->NEVR : NULL);
    00523 }
    00524
    00525 const char * rpmteNEVRA(rpmte te)
    00526 {
    00527     return (te != NULL ? te->NEVRA : NULL);
    00528 }
    00529
    00530 const char * rpmtePkgid(rpmte te)
    00531 {
    00532     return (te != NULL ? te->pkgid : NULL);
    00533 }
    00534
    00535 const char * rpmteHdrid(rpmte te)
    00536 {
    00537     return (te != NULL ? te->hdrid : NULL);
    00538 }
    00539
    00540 const char * rpmteSourcerpm(rpmte te)
    00541 {
    00542     return (te != NULL ? te->sourcerpm : NULL);
    00543 }
    00544
    00545 FD_t rpmteFd(rpmte te)
    00546 {
    00547     /*@-compdef -refcounttrans -retalias -retexpose -usereleased @*/
    00548     return (te != NULL ? te->fd : NULL);
    00549     /*@=compdef =refcounttrans =retalias =retexpose =usereleased @*/
    00550 }
    00551
    00552 fnpyKey rpmteKey(rpmte te)
    00553 {
    00554     return (te != NULL ? te->key : NULL);
    00555 }
    00556
    00557 rpmds rpmteDS(rpmte te, rpmTag tag)
    00558 {
    00559     return (te != NULL ? rpmdsFromPRCO(te->PRCO, tag) : NULL);
    00560 }
    00561
    00562 rpmfi rpmteFI(rpmte te, rpmTag tag)
    00563 {
    00564     /*@-compdef -refcounttrans -retalias -retexpose -usereleased @*/
    00565     if (te == NULL)
    00566         return NULL;
    00567
    00568     if (tag == RPMTAG_BASENAMES)
    00569         return te->fi;
    00570     else
    00571         return NULL;
    00572     /*@=compdef =refcounttrans =retalias =retexpose =usereleased @*/
    00573 }
    00574
    00575 void rpmteColorDS(rpmte te, rpmTag tag)
    00576 {
    00577     rpmfi fi = rpmteFI(te, RPMTAG_BASENAMES);
    00578     rpmds ds = rpmteDS(te, tag);
    00579     char deptype = 'R';
    00580     char mydt;
    00581     const rpmuint32_t * ddict;
    00582     rpmuint32_t * colors;
    00583     rpmuint32_t * refs;
    00584     rpmuint32_t val;
    00585     int Count;
    00586     size_t nb;
    00587     unsigned ix;
    00588     int ndx, i;
    00589
    00590     if (!(te && (Count = rpmdsCount(ds)) > 0 && rpmfiFC(fi) > 0))
    00591         return;
    00592
    00593     switch (tag) {
    00594     default:
    00595         return;
    00596         /*@notreached@*/ break;
    00597     case RPMTAG_PROVIDENAME:
    00598         deptype = 'P';
    00599         break;
    00600     case RPMTAG_REQUIRENAME:
    00601         deptype = 'R';
    00602         break;
    00603     }
    00604
    00605     nb = Count * sizeof(*colors);
    00606     colors = memset(alloca(nb), 0, nb);
    00607     nb = Count * sizeof(*refs);
    00608     refs = memset(alloca(nb), -1, nb);
    00609
    00610     /* Calculate dependency color and reference count. */
    00611     fi = rpmfiInit(fi, 0);
    00612     if (fi != NULL)
    00613     while (rpmfiNext(fi) >= 0) {
    00614         val = rpmfiFColor(fi);
    00615         ddict = NULL;
    00616         ndx = rpmfiFDepends(fi, &ddict);
    00617         if (ddict != NULL)
    00618         while (ndx-- > 0) {
    00619             ix = *ddict++;
    00620             mydt = (char)((ix >> 24) & 0xff);
    00621             if (mydt != deptype)
    00622                 /*@innercontinue@*/ continue;
    00623             ix &= 0x00ffffff;
    00624 assert ((int)ix < Count);
    00625             colors[ix] |= val;
    00626             refs[ix]++;
    00627         }
    00628     }
    00629
    00630     /* Set color/refs values in dependency set. */
    00631     ds = rpmdsInit(ds);
    00632     while ((i = rpmdsNext(ds)) >= 0) {
    00633         val = colors[i];
    00634         te->color |= val;
    00635         (void) rpmdsSetColor(ds, val);
    00636         val = refs[i];
    00637         (void) rpmdsSetRefs(ds, val);
    00638     }
    00639 }
    00640
    00641 /*@unchecked@*/
    00642 static int __mydebug = 0;
    00643
    00644 int rpmteChain(rpmte p, rpmte q, Header oh, const char * msg)
    00645 {
    00646     HE_t he = memset(alloca(sizeof(*he)), 0, sizeof(*he));
    00647     const char * blinkNEVRA = NULL;
    00648     const char * blinkPkgid = NULL;
    00649     const char * blinkHdrid = NULL;
    00650     int xx;
    00651
    00652     if (msg == NULL)
    00653         msg = "";
    00654     he->tag = RPMTAG_NVRA;
    00655     xx = headerGet(oh, he, 0);
    00656 assert(he->p.str != NULL);
    00657     blinkNEVRA = he->p.str;
    00658
    00659     /*
    00660      * Convert binary pkgid to a string.
    00661      * XXX Yum's borken conception of a "header" doesn't have signature
    00662      * tags appended.
    00663      */
    00664     he->tag = RPMTAG_PKGID;
    00665     xx = headerGet(oh, he, 0);
    00666     if (xx && he->p.ui8p != NULL) {
    00667         static const char hex[] = "0123456789abcdef";
    00668         char * t;
    00669         rpmuint32_t i;
    00670
    00671         blinkPkgid = t = xmalloc((2*he->c) + 1);
    00672         for (i = 0 ; i < he->c; i++) {
    00673             *t++ = hex[ ((he->p.ui8p[i] >> 4) & 0x0f) ];
    00674             *t++ = hex[ ((he->p.ui8p[i]     ) & 0x0f) ];
    00675         }
    00676         *t = '\0';
    00677         he->p.ptr = _free(he->p.ptr);
    00678     } else
    00679         blinkPkgid = NULL;
    00680
    00681     he->tag = RPMTAG_HDRID;
    00682     xx = headerGet(oh, he, 0);
    00683     blinkHdrid = he->p.str;
    00684
    00685 /*@-modfilesys@*/
    00686 if (__mydebug)
    00687 fprintf(stderr, "%s argvAdd(&q->flink.NEVRA, \"%s\")\n", msg, p->NEVRA);
    00688         xx = argvAdd(&q->flink.NEVRA, p->NEVRA);
    00689 if (__mydebug)
    00690 fprintf(stderr, "%s argvAdd(&p->blink.NEVRA, \"%s\")\n", msg, blinkNEVRA);
    00691         xx = argvAdd(&p->blink.NEVRA, blinkNEVRA);
    00692 if (__mydebug)
    00693 fprintf(stderr, "%s argvAdd(&q->flink.Pkgid, \"%s\")\n", msg, p->pkgid);
    00694     if (p->pkgid != NULL)
    00695         xx = argvAdd(&q->flink.Pkgid, p->pkgid);
    00696 if (__mydebug)
    00697 fprintf(stderr, "%s argvAdd(&p->blink.Pkgid, \"%s\")\n", msg, blinkPkgid);
    00698     if (blinkPkgid != NULL)
    00699         xx = argvAdd(&p->blink.Pkgid, blinkPkgid);
    00700 if (__mydebug)
    00701 fprintf(stderr, "%s argvAdd(&q->flink.Hdrid, \"%s\")\n", msg, p->hdrid);
    00702     if (p->hdrid != NULL)
    00703         xx = argvAdd(&q->flink.Hdrid, p->hdrid);
    00704 if (__mydebug)
    00705 fprintf(stderr, "%s argvAdd(&p->blink.Hdrid, \"%s\")\n", msg, blinkHdrid);
    00706     if (blinkHdrid != NULL)
    00707         xx = argvAdd(&p->blink.Hdrid, blinkHdrid);
    00708 /*@=modfilesys@*/
    00709
    00710     blinkNEVRA = _free(blinkNEVRA);
    00711     blinkPkgid = _free(blinkPkgid);
    00712     blinkHdrid = _free(blinkHdrid);
    00713
    00714     return 0;
    00715 }
    00716
    00717 int rpmtsiOc(rpmtsi tsi)
    00718 {
    00719     return tsi->ocsave;
    00720 }
    00721
    00722 /*@-mustmod@*/
    00723 static void rpmtsiFini(void * _tsi)
    00724         /*@modifies _tsi @*/
    00725 {
    00726     rpmtsi tsi = _tsi;
    00727 /*@-internalglobs@*/
    00728     (void)rpmtsFree(tsi->ts);
    00729     tsi->ts = NULL;
    00730 /*@=internalglobs@*/
    00731 }
    00732 /*@=mustmod@*/
    00733
    00734 /*@unchecked@*/ /*@only@*/ /*@null@*/
    00735 rpmioPool _rpmtsiPool;
    00736
    00737 static rpmtsi rpmtsiGetPool(/*@null@*/ rpmioPool pool)
    00738         /*@globals _rpmtsiPool, fileSystem, internalState @*/
    00739         /*@modifies pool, _rpmtsiPool, fileSystem, internalState @*/
    00740 {
    00741     rpmtsi tsi;
    00742
    00743     if (_rpmtsiPool == NULL) {
    00744         _rpmtsiPool = rpmioNewPool("tsi", sizeof(*tsi), -1, _rpmte_debug,
    00745                         NULL, NULL, rpmtsiFini);/* XXX _rpmtsi_debug? */
    00746         pool = _rpmtsiPool;
    00747     }
    00748     return (rpmtsi) rpmioGetPool(pool, sizeof(*tsi));
    00749 }
    00750
    00751 rpmtsi XrpmtsiInit(rpmts ts, const char * fn, unsigned int ln)
    00752 {
    00753     rpmtsi tsi = rpmtsiGetPool(_rpmtsiPool);
    00754
    00755 /*@-assignexpose -castexpose @*/
    00756     tsi->ts = rpmtsLink(ts, "rpmtsi");
    00757 /*@=assignexpose =castexpose @*/
    00758     tsi->reverse = 0;
    00759     tsi->oc = (tsi->reverse ? (rpmtsNElements(ts) - 1) : 0);
    00760     tsi->ocsave = tsi->oc;
    00761
    00762     return (rpmtsi) rpmioLinkPoolItem((rpmioItem)tsi, "rpmtsiInit", fn, ln);
    00763 }
    00764
    00770 static /*@null@*/ /*@dependent@*/
    00771 rpmte rpmtsiNextElement(rpmtsi tsi)
    00772         /*@modifies tsi @*/
    00773 {
    00774     rpmte te = NULL;
    00775     int oc = -1;
    00776
    00777     if (tsi == NULL || tsi->ts == NULL || rpmtsNElements(tsi->ts) <= 0)
    00778         return te;
    00779
    00780     if (tsi->reverse) {
    00781         if (tsi->oc >= 0)               oc = tsi->oc--;
    00782     } else {
    00783         if (tsi->oc < rpmtsNElements(tsi->ts))  oc = tsi->oc++;
    00784     }
    00785     tsi->ocsave = oc;
    00786     if (oc != -1)
    00787         te = rpmtsElement(tsi->ts, oc);
    00788     return te;
    00789 }
    00790
    00791 rpmte rpmtsiNext(rpmtsi tsi, rpmElementType type)
    00792 {
    00793     rpmte te;
    00794
    00795     while ((te = rpmtsiNextElement(tsi)) != NULL) {
    00796         if (type == 0 || (te->type & type) != 0)
    00797             break;
    00798     }
    00799     return te;
    00800 }