NCSA server performance patch

Russel Kipp Jones (
Sun, 26 Feb 1995 14:55:52 +0500

The past couple of months have seen our NCSA server performance degrade
considerably. The included patch should improve most servers, but
those with large yp group files and/or those experiencing multiple
hits/second should see the most gain.

The included patch gave us an order of magnitude improvement.
Technical details as well as the diff file are included below.

Please let me know if you have any questions.

Thank you,

Kipp Jones
----------------------------------------------------------------------------- <URL:>
Graduate Research Assistant, Computing and Networking Services, Georgia Tech
"Gather your courage and your list of networking information and continue"
-Greg Hankins

Technical Details:

We had been experiencing considerable delay on our server connections.
Discovered that it was the server was doing an initgroups call for
each fork'd process. As we use yp, and our group file keeps growing,
AND yp is single threaded, all of the accesses were getting queued
up waiting for ypserv.

We tweaked the code to allow us to only do the initgroups
call once, and use that information the remaining times. As the
uid/gid is always the same, this is sufficient.

The improvement for us was in the range of 2-3 seconds/connection, a
very considerable amount. The performance improvement experienced
by others will vary depending on the number of hits, the size of the
group file, and the yp activity.

diff for httpd_1.3/httpd.c
> #include "sys/param.h"
> int ngroups, groups[NGROUPS];
> /* Figure out which groups we're in for later use*/
> if (!getuid()) {
> struct passwd* pwent;
> int nsavegroups, savegroups[NGROUPS];
> if ((nsavegroups = getgroups(NGROUPS, savegroups)) == -1)
> die(SERVER_ERROR,"couldn't save current groupids", stdout);
> if ((pwent = getpwuid(user_id)) == NULL)
> die(SERVER_ERROR,"couldn't determine user name from uid", stdout);
> if (initgroups(pwent->pw_name, group_id) == -1)
> die(SERVER_ERROR,"unable to initgroups",stdout);
> if ((ngroups = getgroups(NGROUPS, groups)) == -1)
> die(SERVER_ERROR,"couldn't save new groupids", stdout);
> if (setgroups(nsavegroups, savegroups) == -1)
> die(SERVER_ERROR,"couldn't restore old groupids", stdout);
> }
< if ((pwent = getpwuid(user_id)) == NULL)
< die(SERVER_ERROR,"couldn't determine user name from uid",
< stdout);
< if (initgroups(pwent->pw_name, group_id) == -1)

>                 if (setgroups(ngroups, groups) == -1)