bitlock: hand-code assembly version for x86
authorRyan Lortie <desrt@desrt.ca>
Fri, 3 Jun 2011 18:29:41 +0000 (20:29 +0200)
committerMatthias Clasen <mclasen@redhat.com>
Fri, 3 Jun 2011 21:33:39 +0000 (17:33 -0400)
commit1a80405a36eae6777cf8dc809da5883ba666f41c
tree37b2fc69e0c6336a5db1003b93928e164da253c1
parentf2bd54d0c5e3093ad141de6142277a27b82147e1
bitlock: hand-code assembly version for x86

The __sync_fetch_and_or() operation on x86 is a bit suboptimal when the
result isn't ignored.  Normally we could use the 'lock or' assembly
instruction to accomplish this, but this instruction discards the
previous value.

In order to work around this issue, GCC is forced to emit a
compare-and-exchange loop.

We can easily use the 'lock bts' instruction, though.  It can't be used
in the general case for __sync_fetch_and_or() but it works great for our
case (test and set a single bit).

I filed a bug against GCC[1] to get this exposed as a new intrinsic (or
have the optimiser detect the case) but until then we'll hand-code it on
x86 and amd64.

The uncontended case sees a 31% improvement on my test machine.

 [1] http://gcc.gnu.org/bugzilla/show_bug.cgi?id=49244

https://bugzilla.gnome.org/show_bug.cgi?id=651467
glib/gbitlock.c