httpd-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Dean Gaudet <dgau...@hotwired.com>
Subject unique hit ids
Date Sat, 17 Aug 1996 23:33:23 GMT
I'm wondering if anyone can come up with a nice function for generating
unique hit ids with very little interprocess communication.  No, with
no interprocess communication.  What I have so far isn't general enough
to work for other people's configurations.

A brief note as to why you might want this... if you're aggressive
about using this hit_id in every log you write, and passing it to CGIs
so they can log it in logs they write (or errors they generate) then you
have a powerful debugging tool.  You can keep multiple logs (a hit log,
an error log, cpu-usage log, whatever) with different archival/rotation
policies and use join(1) or grep to gather all the info on hit(s).
(There are also obvious database uses of them, but I'm not a db weenie,
so they're only incidental in my opinion.)

In my case, the ids have to be unique over multiple physical machines
serving multiple addresses, the addresses served are not tied to any
particular machine (i.e. 204.62.129.1 is served by two machines).  They
also need to have a "long life" (i.e. rolling over once every decade is
acceptable).  I also don't want anything longer than 12 bytes (uuencoded).

Anyhow, here's pseudo-code for what I'm doing:

    typedef struct {
	time_t stamp;
	unsigned count;
	/* a byte that differentiates the physical machine serving the hit
	    from every other machine that might be serving the same
	    site */
	unsigned char server_id;
    } hit_id_t;

    hit_id_t hit_id;

    /* in the parent, initialization */
    hit_id.stamp = time(0);
    hit_id.count = 0;
    hit_id.server_id = /* in my case, using the low byte of the ip of the
			server's default interface works fine -- you
			could go for statically configured ids, but I
			like all my machines to run identical config
			files */

    /* la la la, get down to that point where the parent forks
	child, the parent does this AFTER forking the child */

    if( hit_id.count + MaxRequestsPerChild < hit_id.count ) {
	/* rollover, assume it won't happen more than once per second */
	hit_id.stamp = time(0);
	hit_id.count = 0;
    } else {
	hit_id.count += MaxRequestsPerChild;
    }

    /* the child essentially has MaxRequestsPerChild hits reserved for it */

First, notice it doesn't deal with MaxRequestsPerChild == 0, which is
the shipped configuration.  The KeepAlive code also messes it up since
KeepAlive doesn't respect MaxRequestsPerChild (is this a bug?  I can't
decide...).

I've considered other things, but ultimately they run up against static
limits such as the number of machines serving, or the max number of
children.  I'd love to submit code for this, but unless we can agree on
what static limit to break I'm not sure we can do this generally.

Or we can ignore the 72-bit limitation.

Any other ideas?

Dean

Mime
View raw message