Replace user- and groupname + file lang caches with a global stringpool

- With the string pool we dont have to worry about overflowing the
  indexes so we can lump all this relatively static data into one pool.
  Because rpmsid's are larger than the previous cache indexes, we'll
  loose some of the memory savings, but then the pool is faster on
  insertion, and we'll only need one of them so...
- The misc. pool is never freed, flushed or frozen so it'll "waste" memory
  throughout the lifetime of a process (similarly to the previous caches)
  but its not huge so .. ignoring that for now.
This commit is contained in:
Panu Matilainen 2012-09-07 11:31:12 +03:00
parent 4606460e54
commit 8909eed1a8
2 changed files with 34 additions and 14 deletions

View File

@ -18,6 +18,9 @@
#include "debug.h"
/* pool for widely common, "static" stuff like langs and user/group names */
static rpmstrPool miscpool = NULL;
/*
* Simple and stupid string "cache."
* Store each unique string just once, retrieve by index value.
@ -30,11 +33,6 @@ struct strcache_s {
scidx_t num;
};
static struct strcache_s _ugcache = { NULL, 0 };
static strcache ugcache = &_ugcache;
static struct strcache_s _langcache = { NULL, 0 };
static strcache langcache = &_langcache;
static scidx_t strcachePut(strcache cache, const char *str)
{
int found = 0;
@ -412,7 +410,7 @@ const char * rpmfiFUserIndex(rpmfi fi, int ix)
if (fi != NULL && ix >= 0 && ix < fi->fc) {
if (fi->fuser != NULL)
fuser = strcacheGet(ugcache, fi->fuser[ix]);
fuser = rpmstrPoolStr(miscpool, fi->fuser[ix]);
}
return fuser;
}
@ -423,7 +421,7 @@ const char * rpmfiFGroupIndex(rpmfi fi, int ix)
if (fi != NULL && ix >= 0 && ix < fi->fc) {
if (fi->fgroup != NULL)
fgroup = strcacheGet(ugcache, fi->fgroup[ix]);
fgroup = rpmstrPoolStr(miscpool, fi->fgroup[ix]);
}
return fgroup;
}
@ -441,7 +439,7 @@ const char * rpmfiFLangsIndex(rpmfi fi, int ix)
{
const char *flangs = NULL;
if (fi != NULL && fi->flangs != NULL && ix >= 0 && ix < fi->fc) {
flangs = strcacheGet(langcache, fi->flangs[ix]);
flangs = rpmstrPoolStr(miscpool, fi->flangs[ix]);
}
return flangs;
}
@ -1143,6 +1141,23 @@ static scidx_t *cacheTag(strcache cache, Header h, rpmTag tag)
return idx;
}
static rpmsid * tag2pool(rpmstrPool pool, Header h, rpmTag tag)
{
rpmsid *sids = NULL;
struct rpmtd_s td;
if (headerGet(h, tag, &td, HEADERGET_MINMEM)) {
int i = 0;
const char *str;
sids = xmalloc(sizeof(*sids) * rpmtdCount(&td));
while ((str = rpmtdNextString(&td))) {
sids[i++] = rpmstrPoolId(pool, str, 1);
}
rpmtdFreeData(&td);
}
return sids;
}
#define _hgfi(_h, _tag, _td, _flags, _data) \
if (headerGet((_h), (_tag), (_td), (_flags))) \
_data = (td.data)
@ -1181,6 +1196,10 @@ rpmfi rpmfiNew(const rpmts ts, Header h, rpmTagVal tagN, rpmfiFlags flags)
goto errxit;
}
/* XXX: ensure the global misc. pool exists */
if (miscpool == NULL)
miscpool = rpmstrPoolCreate();
/* XXX TODO: all these should be sanity checked, ugh... */
if (!(flags & RPMFI_NOFILEMODES))
_hgfi(h, RPMTAG_FILEMODES, &td, scareFlags, fi->fmodes);
@ -1218,7 +1237,7 @@ rpmfi rpmfiNew(const rpmts ts, Header h, rpmTagVal tagN, rpmfiFlags flags)
}
/* FILELANGS are only interesting when installing */
if ((headerGetInstance(h) == 0) && !(flags & RPMFI_NOFILELANGS))
fi->flangs = cacheTag(langcache, h, RPMTAG_FILELANGS);
fi->flangs = tag2pool(miscpool, h, RPMTAG_FILELANGS);
/* See if the package has non-md5 file digests */
fi->digestalgo = PGPHASHALGO_MD5;
@ -1259,9 +1278,9 @@ rpmfi rpmfiNew(const rpmts ts, Header h, rpmTagVal tagN, rpmfiFlags flags)
_hgfi(h, RPMTAG_FILEINODES, &td, scareFlags, fi->finodes);
if (!(flags & RPMFI_NOFILEUSER))
fi->fuser = cacheTag(ugcache, h, RPMTAG_FILEUSERNAME);
fi->fuser = tag2pool(miscpool, h, RPMTAG_FILEUSERNAME);
if (!(flags & RPMFI_NOFILEGROUP))
fi->fgroup = cacheTag(ugcache, h, RPMTAG_FILEGROUPNAME);
fi->fgroup = tag2pool(miscpool, h, RPMTAG_FILEGROUPNAME);
/* lazily alloced from rpmfiFN() */
fi->fn = NULL;

View File

@ -3,6 +3,7 @@
#include <rpm/header.h>
#include <rpm/rpmfi.h>
#include <rpm/rpmstrpool.h>
#include "lib/fprint.h"
/*
@ -28,7 +29,6 @@ struct rpmfi_s {
strcache flinkcache; /*!< File link cache */
scidx_t * flinks; /*!< Index to file link(s) cache */
scidx_t * flangs; /*!< Index to file lang(s) cache */
uint32_t * dil; /*!< Directory indice(s) (from header) */
rpm_flag_t * fflags; /*!< File flag(s) (from header) */
@ -38,8 +38,9 @@ struct rpmfi_s {
rpm_rdev_t * frdevs; /*!< File rdev(s) (from header) */
rpm_ino_t * finodes; /*!< File inodes(s) (from header) */
scidx_t *fuser; /*!< Index to file owner(s) cache */
scidx_t *fgroup; /*!< Index to file group(s) cache */
rpmsid * fuser; /*!< Index to file owner(s) (misc pool) */
rpmsid * fgroup; /*!< Index to file group(s) (misc pool) */
rpmsid * flangs; /*!< Index to file lang(s) (misc pool) */
char * fstates; /*!< File state(s) (from header) */