web/2281: Bug in the "Suboptimal code for complex conditionals" proposal
cbouchon@hotmail.com
cbouchon@hotmail.com
Sun Apr 1 00:00:00 GMT 2001
>Number: 2281
>Category: web
>Synopsis: Bug in the "Suboptimal code for complex conditionals" proposal
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: gerald
>State: open
>Class: doc-bug
>Submitter-Id: net
>Arrival-Date: Tue Mar 13 13:36:01 PST 2001
>Closed-Date:
>Last-Modified:
>Originator: Christophe Bouchon
>Release: unknown-1.0
>Organization:
>Environment:
>Description:
On the http://gcc.gnu.org/projects/optimize.html page (Deficiencies of GCC's optimizer), the "Suboptimal code for complex conditionals" section contains faulty code proposals (the 2 code samples at the bottom of the section). It assumes that for any given a and b integers, (a & b) == (a && b) is always true, and that's wrong: (1 & 2) == 0 but (1 && 2) == 1 !
The proposed translation for a && b is:
movl 4(%esp), %edx
movl 8(%esp), %ecx
xorl %eax, %eax
testl %ecx, %edx
setne %al
ret
Then the proposed translation for a || b using the boolean equivalence (!((!a) && (!b))) == (a || b) is worse because it also assume that (!a) == (~a) and that's also wrong:
!1 == 0 but ~1 != 0 (the two notl instructions in the "or" sample are like the ~ C operator).
Just assembly the samples and test them with some integers not having 1 bits at the same position (like 1 and 2) and you can verify this.
>How-To-Repeat:
>Fix:
This tranlation for (a || b) is correct:
movl 4(%esp), %edx
xorl %eax, %eax
movl 8(%esp), %ecx
orl %ecx, %edx
setne %al
ret
this destroys the edx register content but the result is always correct. By the way, I tried to interleave register writes for speed.
For "and", I can still optimize the GCC generated code (with -mbranch-cost=2 option):
and:
movl 4(%esp), %edx
xorl %eax, %eax
testl %edx, %edx
movl 8(%esp), %edx
setne %al
testl %edx, %edx
setne %dl
andl %dl, %al
ret
>Release-Note:
>Audit-Trail:
>Unformatted:
More information about the Gcc-prs
mailing list