* * *

Author Topic: Boolean expressions not always reduced to simplest expression by compiler  (Read 723 times)

ccrause

  • Jr. Member
  • **
  • Posts: 82
So I check the code emitted by the compiler for various equivalent boolean expressions - it seems as if the compiler simplify the expression left to right only? AVR example:
Code: Pascal  [Select]
  1. var a: byte;
  2. ...
  3.   a := a or 1 or 2 or 4;
  4.   a2:   20 91 00 01     lds     r18, 0x0100
  5.   a6:   21 60           ori     r18, 0x01       ; 1
  6.   a8:   22 60           ori     r18, 0x02       ; 2
  7.   aa:   24 60           ori     r18, 0x04       ; 4
  8.   ac:   20 93 00 01     sts     0x0100, r18
  9.  
  10.   a := a or (1 or 2 or 4);
  11.   b0:   20 91 00 01     lds     r18, 0x0100
  12.   b4:   27 60           ori     r18, 0x07       ; 7
  13.   b6:   20 93 00 01     sts     0x0100, r18
  14.  
  15.   a := 1 or 2 or 4 or a;
  16.   ba:   20 91 00 01     lds     r18, 0x0100
  17.   be:   27 60           ori     r18, 0x07       ; 7
  18.   c0:   20 93 00 01     sts     0x0100, r18

Linux x64 example:
Code: Pascal  [Select]
  1. var a: byte;
  2. ...project1.lpr:10                           a := a or 1 or 2 or 4;
  3. 00000000004001D2 0fb605a7db2200           movzbl 0x22dba7(%rip),%eax        # 0x62dd80 <U_$P$PROJECT1_$$_A>
  4. 00000000004001D9 83c801                   or     $0x1,%eax
  5. 00000000004001DC 83c802                   or     $0x2,%eax
  6. 00000000004001DF 83c804                   or     $0x4,%eax
  7. 00000000004001E2 880598db2200             mov    %al,0x22db98(%rip)        # 0x62dd80 <U_$P$PROJECT1_$$_A>
  8.  
  9. project1.lpr:11                           a := a or (1 or 2 or 4);
  10. 00000000004001E8 0fb60591db2200           movzbl 0x22db91(%rip),%eax        # 0x62dd80 <U_$P$PROJECT1_$$_A>
  11. 00000000004001EF 83c807                   or     $0x7,%eax
  12. 00000000004001F2 880588db2200             mov    %al,0x22db88(%rip)        # 0x62dd80 <U_$P$PROJECT1_$$_A>
  13.  
  14. project1.lpr:12                           a := 1 or 2 or 4 or a;
  15. 00000000004001F8 0fb60581db2200           movzbl 0x22db81(%rip),%eax        # 0x62dd80 <U_$P$PROJECT1_$$_A>
  16. 00000000004001FF 83c807                   or     $0x7,%eax
  17. 0000000000400202 880578db2200             mov    %al,0x22db78(%rip)        # 0x62dd80 <U_$P$PROJECT1_$$_A>

Is it worth the effort to create a bug report for this?  Alternative is to remember bracketing constant expressions to help the compiler :o

Nitorami

  • Sr. Member
  • ****
  • Posts: 253
Re: Boolean expressions not always reduced to simplest expression by compiler
« Reply #1 on: November 05, 2017, 02:19:40 pm »
Confirm same behaviour on win32. Certainly a minor issue, still, the compiler should be able to optimize such simple expressions.

ASerge

  • Hero Member
  • *****
  • Posts: 530
Re: Boolean expressions not always reduced to simplest expression by compiler
« Reply #2 on: November 06, 2017, 04:35:08 pm »
If you need deep optimization, there is nothing shameful in giving a hint to the compiler (an example of brackets in your case) ;).
Another example:
Code: Pascal  [Select]
  1. function Test(A, B: Integer): Boolean;
  2. begin
  3.   Result := (A > 0) and (B < 0);
  4. end;
but this is more efficient (without jumping):
Code: Pascal  [Select]
  1. function TestFullBool(A, B: Integer): Boolean;
  2. begin
  3. {$PUSH}
  4. {$BOOLEVAL ON}
  5.   Result := (A > 0) and (B < 0);
  6. {$POP}
  7. end;
Such kinds of micro optimization is not performed, as far as I know, by all versions of Delphi.

kupferstecher

  • Full Member
  • ***
  • Posts: 150
Re: Boolean expressions not always reduced to simplest expression by compiler
« Reply #3 on: November 06, 2017, 06:54:03 pm »
boolean expressions
Why you call it boolean? Don't you speak of bitwise operations?

If you need deep optimization, there is nothing shameful in giving a hint to the compiler (an example of brackets in your case) ;).
Such expressions are very common for target embedded (AVR,ARM etc.), when bits of hardware registers are set (mostly initialization phase). So this is not a use case where one would do micro optimisations, but as its so often used, compiler support would be reasonable.

ccrause

  • Jr. Member
  • **
  • Posts: 82
Re: Boolean expressions not always reduced to simplest expression by compiler
« Reply #4 on: November 06, 2017, 08:09:16 pm »
...but this is more efficient (without jumping):
Code: Pascal  [Select]
  1. {$BOOLEVAL ON}
  2.   Result := (A > 0) and (B < 0);

I see the opposite behaviour with the AVR compiler, if $BOOLEVAL is off more compact code is generated.  I guess there are platform dependent optimizations that also play a role here.

ccrause

  • Jr. Member
  • **
  • Posts: 82
Re: Boolean expressions not always reduced to simplest expression by compiler
« Reply #5 on: November 06, 2017, 08:14:12 pm »
Why you call it boolean? Don't you speak of bitwise operations?
Correct indeed, my code perform bitwise manipulations :-[

engkin

  • Hero Member
  • *****
  • Posts: 1811
Re: Boolean expressions not always reduced to simplest expression by compiler
« Reply #6 on: November 07, 2017, 01:41:38 am »
Is it worth the effort to create a bug report for this?

This is a bug. :-|

 

Recent

Get Lazarus at SourceForge.net. Fast, secure and Free Open Source software downloads Open Hub project report for Lazarus