[Patch] Use __GCC_HAVE_SYNC_COMPARE_AND_SWAP_*
Peter Dimov
pdimov@mmltd.net
Mon May 28 16:02:00 GMT 2007
Paolo Carlini wrote:
> Peter Dimov wrote:
>
>>> I see. In fact, as you may remember, I have been asking for an
>>> infrastructure providing an emulation layer transparent to the users
>>> for *years*...
>>
>> I understand, but isn't the infrastructure now almost in place? The
>> compiler support is present; is it not just the library support that
>> is missing?
>
> I wish I could share your optimism :-) These issues are nasty, very
> nasty, given all the requirements. Please have a look to the past
> exchanges on the lists: people came to the conclusion that the only
> satisfactory and complete solution are multilibs. And that would not
> solve the statically linked case. Well, if you have a complete
> solution ready fullfilling all those requirements, just post it ;)
OK, here's what I have in mind. The basic assumption is that all targets
support a spinlock using __sync_lock_* or equivalent. I'll concentrate on
the 386 case here and fetch_and_add but the others are similar.
Assume a spinlock pool:
spinlock_t spinlocks[ 41 ];
spinlock_t spinlock_for( void * p )
{
return spinlocks[ (unsigned)p % 41 ];
}
void lock_spinlock_for( void * p );
void unlock_spinlock_for( void * p ); // omitted for brevity
// set by runtime at startup before any other code is executed
extern bool __is_486;
// emulation layer
int __sync_fetch_and_add_4( int * ptr, int value )
{
if( __is_486 )
{
asm { xadd [ptr], value } // pseudocode
}
else
{
lock_spinlock_for( ptr );
int r = *ptr; *ptr += value;
unlock_spinlock_for( ptr );
return r;
}
}
This seems to work as intended for all cases that come to mind. If a module
compiled with -m486 is linked with a module compiled with -m386, the result
will work when run on 486 or better since the emulation will have the same
effect as the inlined intrinsic.
I may of course be missing something; apologies if so.
More information about the Libstdc++
mailing list