Date: Thu, 18 Jan 2001 21:03:45 +1100 (EST) From: Bruce Evans <bde@zeta.org.au> To: Garrett Wollman <wollman@khavrinen.lcs.mit.edu> Cc: Alfred Perlstein <bright@wintelcom.net>, current@FreeBSD.ORG Subject: Re: Atomic breakage? Message-ID: <Pine.BSF.4.21.0101181957230.1115-100000@besplex.bde.org> In-Reply-To: <200101171614.LAA18224@khavrinen.lcs.mit.edu>
next in thread | previous in thread | raw e-mail | index | archive | help
On Wed, 17 Jan 2001, Garrett Wollman wrote: > <<On Tue, 16 Jan 2001 19:10:10 -0800, Alfred Perlstein <bright@wintelcom.net> said: > > > Just wondering, can't you use 'LOCK addl' and then use 'LOCK addc'? > > add longword, add longword with carry? I know it would be pretty > > ugly, but it should work, no? > > The two bus cycles are independent, so there is a race condition. > > OTOH, it's a fairly *unlikely* race condition, and the worst thing > that can happen is statistics that are obviously off by four billion. > (The race only occurs when there is a carry out of the low-order > longword, which is to say, once in every 2**32 operations.) If they are obviously off by precisely four billion, then they can be corrected :-). I have thought of using special overflow handling methods to reduce the cost of keeping statistics. E.g.: --- uint32_t counter[2]; /* Low-level code increments only the lower 32 bits of counters. */ atomic_add_32(&counter[0]), 1); /* * Counter daemon adjusts counters before they get anywhere near * overflowing. It must run often enough to prevent overflow * (not very often). This also make the race in the adjustment * code harmless. */ KASSERT(counter[0] < 0xC0000000, "counter got near overflowing"); if (counter[0] & 0x80000000) { atomic_subtract_32(&counter[0], 0x80000000); ++counter[1]; } /* * Clients must use code like the following to convert counters * to values. More locking is required to load counter[0] and * counter[1] atomically, but this is not a new problem (e.g., * atomicity is mostly accidental for accesses via kmem). */ counter_value = ((uint64_t)counter[1] << 31) | counter[0]; --- Bruce To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-current" in the body of the message
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?Pine.BSF.4.21.0101181957230.1115-100000>