[pacman-dev] Holy inefficient batman!
Nagy Gabor
ngaba at bibl.u-szeged.hu
Mon Nov 19 06:26:25 EST 2007
> On Sat, Nov 17, 2007 at 07:25:03PM +0100, Xavier wrote:
> > And I put a debug back because Aaron asked for it, and I also think it can
> be
> > very handy sometimes, to debug quicker.
> >
> > > So I did some speed test, and the results was really suprising:
> > > First of all, I kept only deps.c.diff from our patches (my typo doesn't
> matter
> > > here). And I did "pactest.py -v" on smoke001.py (empty disk cache,
> repeated
> > > many times times etc.)
> > > The result: your patch is _significantly_ slower (I got 5,4,4,4, ... sec)
> than
> > > mine (I got 4,3,3,3, ... sec). I repeated the test 4 times (patch pacman,
>
> > > compile, 5 pactest); the result is always the same!
> > > Could you test this, too?
> > >
> >
> > Hm yes, I'll do more tests.
>
> Well, I get 9.9s with your patch, and 10.8s with mine.
> I removed the logging (the 3 lines) in depcmp and I get 10.0s.
>
> But what is one second saved in the runtime of smoke001 compared to the time
> this debug log could save you when debugging? :)
>
> Maybe things can still be improved though. What is costly is apparently the
> alpm_dep_get_string call. If I remove it, but leave malloc / free and put a
> fake depstring, I still get nearly 10.0s.
> So I looked at that function for things I could change, it seems it's
> sprintf
> which is not very efficient. I replaced it by manual strncpy (so the code
> gets uglier), and I get ~10.0s again.
>
> I'm not sure this is all worth the troubles though.
>
>
> diff --git a/lib/libalpm/deps.c b/lib/libalpm/deps.c
> index 9232984..31493f7 100644
> --- a/lib/libalpm/deps.c
> +++ b/lib/libalpm/deps.c
> @@ -830,8 +830,8 @@ const char SYMEXPORT *alpm_dep_get_version(const
> pmdepend_t *dep)
> */
> char SYMEXPORT *alpm_dep_get_string(const pmdepend_t *dep)
> {
> - char *opr, *str = NULL;
> - size_t len;
> + char *opr, *str = NULL, *ptr;
> + size_t namelen, oprlen, verlen;
>
> ALPM_LOG_FUNC;
>
> @@ -858,9 +858,16 @@ char SYMEXPORT *alpm_dep_get_string(const pmdepend_t
> *dep)
>
> /* we can always compute len and print the string like this because opr
> * and ver will be empty when PM_DEP_MOD_ANY is the depend type */
> - len = strlen(dep->name) + strlen(opr) + strlen(dep->version) + 1;
> - MALLOC(str, len, RET_ERR(PM_ERR_MEMORY, NULL));
> - snprintf(str, len, "%s%s%s", dep->name, opr, dep->version);
> + namelen = strlen(dep->name);
> + oprlen = strlen(opr);
> + verlen = strlen(dep->version);
> + MALLOC(str, namelen + oprlen + verlen + 1, RET_ERR(PM_ERR_MEMORY, NULL));
> + ptr = str;
> + strncpy(ptr, dep->name, namelen);
> + ptr += namelen;
> + strncpy(ptr, opr, oprlen);
> + ptr += oprlen;
> + strncpy(ptr, dep->version, verlen + 1);
>
> return(str);
> }
1. I was curious and I tested smoke001.py with "requiredby-pacman" and as it was
expected by me (no compute-requiredby is needed here), the current version is
much faster (3 or 4 sec vs. 7 sec)
2. There is something in my mind about alpm_dep_getstring:
It shouldn't be used for debug preformat (or in libalpm at all); but that is
good for front-ends.
I would prefer the following more elegant(?) solution instead of switch():
there is a global const char *deptypestr[] = {">=", "<=", "="} in the correct
order somewhere; and from now on, you can pass deptypestr[dep->mod] parameter
easily to alpm_log for example (see alpm_depcmp). This is O(1) (<- switch is
also O(1), but that floods the code imho)
I will create a patch for this, after I can sync my git repo ;-)
Bye
----------------------------------------------------
SZTE Egyetemi Könyvtár - http://www.bibl.u-szeged.hu
This mail sent through IMP: http://horde.org/imp/
More information about the pacman-dev
mailing list