From c65019affca0988705ea4b8b9b38adbeca6ac98f Mon Sep 17 00:00:00 2001 From: Florian Festi Date: Tue, 21 Oct 2008 15:45:09 +0200 Subject: [PATCH] Change both hashes to a typed version --- lib/fprint.c | 43 +++++++++++++++++++---------------- lib/fprint.h | 53 +++++++++++++++++++++++++++++++------------- lib/rpmts_internal.h | 4 +++- lib/transaction.c | 26 +++++++++++++--------- 4 files changed, 81 insertions(+), 45 deletions(-) diff --git a/lib/fprint.c b/lib/fprint.c index d31a6943a..4f449c606 100644 --- a/lib/fprint.c +++ b/lib/fprint.c @@ -7,22 +7,36 @@ #include /* for rpmCleanPath */ #include "lib/rpmdb_internal.h" +#include "lib/rpmfi_internal.h" #include "lib/fprint.h" #include "debug.h" +#include + +/* Create new hash table type rpmFpEntryHash */ +#include "lib/rpmhash.C" + +#undef HASHTYPE +#undef HTKEYTYPE +#undef HTDATATYPE +#define HASHTYPE rpmFpEntryHash +#define HTKEYTYPE const char * +#define HTDATATYPE const struct fprintCacheEntry_s * +#include "lib/rpmhash.C" fingerPrintCache fpCacheCreate(int sizeHint) { fingerPrintCache fpc; fpc = xmalloc(sizeof(*fpc)); - fpc->ht = htCreate(sizeHint * 2, 0, 1, hashFunctionString, - hashEqualityString); + fpc->ht = rpmFpEntryHashCreate(sizeHint * 2, hashFunctionString, strcmp, + (rpmFpEntryHashFreeKey)free, + (rpmFpEntryHashFreeData)free); return fpc; } fingerPrintCache fpCacheFree(fingerPrintCache cache) { - cache->ht = htFree(cache->ht); + cache->ht = rpmFpEntryHashFree(cache->ht); free(cache); return NULL; } @@ -37,9 +51,9 @@ static const struct fprintCacheEntry_s * cacheContainsDirectory( fingerPrintCache cache, const char * dirName) { - const void ** data; + const struct fprintCacheEntry_s ** data; - if (htGetEntry(cache->ht, dirName, &data, NULL, NULL)) + if (rpmFpEntryHashGetEntry(cache->ht, dirName, &data, NULL, NULL)) return NULL; return data[0]; } @@ -124,19 +138,14 @@ static fingerPrint doLookup(fingerPrintCache cache, if (cacheHit != NULL) { fp.entry = cacheHit; } else if (!stat((*buf != '\0' ? buf : "/"), &sb)) { - size_t nb = sizeof(*fp.entry) + (*buf != '\0' ? (end-buf) : 1) + 1; - char * dn = xmalloc(nb); - struct fprintCacheEntry_s * newEntry = (void *)dn; + struct fprintCacheEntry_s * newEntry = xmalloc(sizeof(* newEntry)); - /* LCL: contiguous malloc confusion */ - dn += sizeof(*newEntry); - strcpy(dn, (*buf != '\0' ? buf : "/")); newEntry->ino = sb.st_ino; newEntry->dev = sb.st_dev; - newEntry->dirName = dn; + newEntry->dirName = xstrdup((*buf != '\0' ? buf : "/")); fp.entry = newEntry; - htAddEntry(cache->ht, dn, fp.entry); + rpmFpEntryHashAddEntry(cache->ht, newEntry->dirName, fp.entry); } if (fp.entry) { @@ -179,9 +188,8 @@ fingerPrint fpLookup(fingerPrintCache cache, const char * dirName, return doLookup(cache, dirName, baseName, scareMemory); } -unsigned int fpHashFunction(const void * key) +unsigned int fpHashFunction(const fingerPrint * fp) { - const fingerPrint * fp = key; unsigned int hash = 0; char ch; const char * chptr; @@ -197,11 +205,8 @@ unsigned int fpHashFunction(const void * key) return hash; } -int fpEqual(const void * key1, const void * key2) +int fpEqual(const fingerPrint * k1, const fingerPrint * k2) { - const fingerPrint *k1 = key1; - const fingerPrint *k2 = key2; - /* If the addresses are the same, so are the values. */ if (k1 == k2) return 0; diff --git a/lib/fprint.h b/lib/fprint.h index ff4dbfeaa..4771b399d 100644 --- a/lib/fprint.h +++ b/lib/fprint.h @@ -7,9 +7,7 @@ */ #include -#include "lib/rpmhash.h" #include "lib/rpmdb_internal.h" -#include "lib/rpmts_internal.h" /** */ @@ -20,6 +18,24 @@ typedef struct fprintCache_s * fingerPrintCache; */ typedef struct fingerPrint_s fingerPrint; +/** + * Associates a trailing sub-directory and final base name with an existing + * directory finger print. + */ +struct fingerPrint_s { +/*! directory finger print entry (the directory path is stat(2)-able */ + const struct fprintCacheEntry_s * entry; +/*! trailing sub-directory path (directories that are not stat(2)-able */ +const char * subDir; +const char * baseName; /*!< file base name */ +}; + +/* Create new hash table data type */ +#define HASHTYPE rpmFpEntryHash +#define HTKEYTYPE const char * +#define HTDATATYPE const struct fprintCacheEntry_s * +#include "lib/rpmhash.H" + /** * Finger print cache entry. * This is really a directory and symlink cache. We don't differentiate between @@ -36,21 +52,28 @@ struct fprintCacheEntry_s { * Finger print cache. */ struct fprintCache_s { - hashTable ht; /*!< hashed by dirName */ + rpmFpEntryHash ht; /*!< hashed by dirName */ }; -/** - * Associates a trailing sub-directory and final base name with an existing - * directory finger print. - */ -struct fingerPrint_s { -/*! directory finger print entry (the directory path is stat(2)-able */ - const struct fprintCacheEntry_s * entry; -/*! trailing sub-directory path (directories that are not stat(2)-able */ -const char * subDir; -const char * baseName; /*!< file base name */ +/* Create new hash table data type */ + +struct rpmffi_s { + rpmfi fi; + int fileno; }; +#undef HASHTYPE +#undef HTKEYTYPE +#undef HTDATATYPE + +#define HASHTYPE rpmFpHash +#define HTKEYTYPE const fingerPrint * +#define HTDATATYPE struct rpmffi_s +#include "lib/rpmhash.H" + +/* avoid include cycle problem by including after rpmFpHash definition */ +#include "lib/rpmts_internal.h" + /** */ #define FP_ENTRY_EQUAL(a, b) (((a)->dev == (b)->dev) && ((a)->ino == (b)->ino)) @@ -116,7 +139,7 @@ fingerPrint fpLookup(fingerPrintCache cache, const char * dirName, * @return hash value */ RPM_GNUC_INTERNAL -unsigned int fpHashFunction(const void * key); +unsigned int fpHashFunction(const fingerPrint * key); /** * Compare two finger print entries. @@ -126,7 +149,7 @@ unsigned int fpHashFunction(const void * key); * @return result of comparing key1 and key2 */ RPM_GNUC_INTERNAL -int fpEqual(const void * key1, const void * key2); +int fpEqual(const fingerPrint * key1, const fingerPrint * key2); /** * Return finger prints of an array of file paths. diff --git a/lib/rpmts_internal.h b/lib/rpmts_internal.h index 249ea63b0..fc1309e86 100644 --- a/lib/rpmts_internal.h +++ b/lib/rpmts_internal.h @@ -5,6 +5,7 @@ #include /* XXX availablePackage/relocateFileList ,*/ #include "lib/rpmhash.h" /* XXX hashTable */ +#include "lib/fprint.h" /** \ingroup rpmts */ @@ -30,6 +31,7 @@ struct diskspaceInfo_s { probably right :-( */ #define BLOCK_ROUND(size, block) (((size) + (block) - 1) / (block)) + /** \ingroup rpmts * The set of packages to be installed/removed atomically. */ @@ -53,7 +55,7 @@ struct rpmts_s { rpmdb rdb; /*!< Install database handle. */ int dbmode; /*!< Install database open mode. */ - hashTable ht; /*!< Fingerprint hash table. */ + rpmFpHash ht; /*!< Fingerprint hash table. */ int * removedPackages; /*!< Set of packages being removed. */ int numRemovedPackages; /*!< No. removed package instances. */ diff --git a/lib/transaction.c b/lib/transaction.c index f075c9bb5..cf60d0be4 100644 --- a/lib/transaction.c +++ b/lib/transaction.c @@ -392,7 +392,7 @@ static void handleOverlappedFiles(const rpmts ts, rpmfi otherFi; rpmfileAttrs FFlags; rpm_mode_t FMode; - const rpmfi * recs; + struct rpmffi_s * recs; int numRecs; if (XFA_SKIPPING(fi->actions[i])) @@ -413,8 +413,7 @@ static void handleOverlappedFiles(const rpmts ts, * will be installed and removed so the records for an overlapped * files will be sorted in exactly the same order. */ - (void) htGetEntry(ts->ht, fiFps, - (const void ***) &recs, &numRecs, NULL); + (void) rpmFpHashGetEntry(ts->ht, fiFps, &recs, &numRecs, NULL); /* * If this package is being added, look only at other packages @@ -438,17 +437,19 @@ static void handleOverlappedFiles(const rpmts ts, */ /* Locate this overlapped file in the set of added/removed packages. */ - for (j = 0; j < numRecs && recs[j] != fi; j++) + for (j = 0; j < numRecs && recs[j].fi != fi; j++) {}; /* Find what the previous disposition of this file was. */ otherFileNum = -1; /* keep gcc quiet */ otherFi = NULL; + for (otherPkgNum = j - 1; otherPkgNum >= 0; otherPkgNum--) { struct fingerPrint_s * otherFps; int otherFc; - otherFi = recs[otherPkgNum]; + otherFi = recs[otherPkgNum].fi; + otherFileNum = recs[otherPkgNum].fileno; /* Added packages need only look at other added packages. */ if (rpmteType(p) == TR_ADDED && rpmteType(otherFi->te) != TR_ADDED) @@ -457,7 +458,6 @@ static void handleOverlappedFiles(const rpmts ts, otherFps = otherFi->fps; otherFc = rpmfiFC(otherFi); - otherFileNum = findFps(fiFps, otherFps, otherFc); (void) rpmfiSetFX(otherFi, otherFileNum); /* XXX Happens iff fingerprint for incomplete package install. */ @@ -517,7 +517,6 @@ assert(otherFi != NULL); } done = 1; } - if (rConflicts) { rpmpsAppend(ps, RPMPROB_NEW_FILE_CONFLICT, rpmteNEVRA(p), rpmteKey(p), @@ -1191,7 +1190,8 @@ int rpmtsRun(rpmts ts, rpmps okProbs, rpmprobFilterFlags ignoreSet) (void) rpmtsSetChrootDone(ts, 1); } - ts->ht = htCreate(totalFileCount * 2, 0, 0, fpHashFunction, fpEqual); + ts->ht = rpmFpHashCreate(totalFileCount * 2, fpHashFunction, fpEqual, + NULL, NULL); fpc = fpCacheCreate(totalFileCount); /* =============================================== @@ -1212,15 +1212,21 @@ int rpmtsRun(rpmts ts, rpmps okProbs, rpmprobFilterFlags ignoreSet) fi = rpmfiInit(fi, 0); if (fi != NULL) /* XXX lclint */ while ((i = rpmfiNext(fi)) >= 0) { + struct rpmffi_s ffi; + ffi.fi = fi; + ffi.fileno = i; if (XFA_SKIPPING(fi->actions[i])) continue; - htAddEntry(ts->ht, fi->fps + i, (void *) fi); + rpmFpHashAddEntry(ts->ht, fi->fps + i, ffi); } (void) rpmswExit(rpmtsOp(ts, RPMTS_OP_FINGERPRINT), fc); } pi = rpmtsiFree(pi); + rpmFpHashFree(ts->ht); + ts->ht = newht; + rpmtsNotify(ts, NULL, RPMCALLBACK_TRANS_START, 6, ts->orderCount); /* =============================================== @@ -1389,7 +1395,7 @@ int rpmtsRun(rpmts ts, rpmps okProbs, rpmprobFilterFlags ignoreSet) pi = rpmtsiFree(pi); fpc = fpCacheFree(fpc); - ts->ht = htFree(ts->ht); + ts->ht = rpmFpHashFree(ts->ht); /* =============================================== * If unfiltered problems exist, free memory and return.