wineport: Add support for ctz().
Adam Martinson
amartinson at codeweavers.com
Thu Mar 17 12:20:53 CDT 2011
On 03/17/2011 03:23 AM, David Laight wrote:
> On Wed, Mar 16, 2011 at 01:26:31PM -0500, Adam Martinson wrote:
>> __builtin_ctz() compiles to:
>> mov 0x8(%ebp),%eax
>> bsf %eax,%eax
>>
>> (ffs()-1) compiles to:
>> mov $0xffffffff,%edx
>> bsf 0x8(%ebp),%eax
>> cmove %edx,%eax
> ...
>> So yes, there is a reason, ctz() is at least 50% faster.
> I'm not where you get 50% from!
>
> I've read both the intel and amd x86 instruction performance manuals
> (but can't clain to remember all of it!).
> The 'bsf' will be a slow instruction (with constraints on where it
> exectutes, and what can execute in parallel).
> The 'cmove' has even worse constraints since it can't execute until
> the 'flags' from the previous instruction are known.
> cmove is only slightly better than a mis-predicted branch!
> In this case there will be complete pipeline stall between the 'bsf'
> and the 'cmove'.
>
> ffs would probably execute faster with a forwards conditional branch
> (predicted not taken) in the 'return -1' path.
>
> David
>
For my purposes the 'return -1' path will never be taken, so it's not
needed. I want to be able to do:
while (bitmap)
{
i = ctz(bitmap); /* get the LSB index */
bitmap ^= 1 << i; /* zero LSB */
/* for each set bit i... */
}
If there's a faster way to do this I'm all ears.
More information about the wine-devel
mailing list