[Bug rtl-optimization/60738] New: A missing opportunity about process_single_reg_class_operands

wmi at google dot com gcc-bugzilla@gcc.gnu.org
Wed Apr 2 05:00:00 GMT 2014


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=60738

            Bug ID: 60738
           Summary: A missing opportunity about
                    process_single_reg_class_operands
           Product: gcc
           Version: 4.9.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: rtl-optimization
          Assignee: unassigned at gcc dot gnu.org
          Reporter: wmi at google dot com

Testcase 1.c:

int a, b, c, d, e, cond;
void foo() {
  int r1, r2, r3;
  r1 = b;
  r2 = d;
  if (__builtin_expect(cond > 3, 0)) {
    e = e * 5;
    c = a << r1;
  }
  c = c << r2;
  __builtin_printf("r1 + r2 = %d\n", r1 + r2);
}

~/workarea/gcc-r208410/build/install/bin/gcc -O2 -S 1.c

foo:
.LFB0:
        .cfi_startproc
        cmpl    $3, cond(%rip)
        movl    b(%rip), %esi
        movl    d(%rip), %eax
        jg      .L2
        movl    c(%rip), %edx
.L3:
        movl    %eax, %ecx      // r2 gets assigned %eax. This is reload for
insn1.
        addl    %eax, %esi
        movl    $.LC0, %edi
        sall    %cl, %edx       // insn1. Its constraint requires r2 in %ecx
        xorl    %eax, %eax
        movl    %edx, c(%rip)
        jmp     printf
        .p2align 4,,10
        .p2align 3
.L2:
        movl    e(%rip), %edx
        movl    %esi, %ecx      // r1 gets assigned %esi. This is reload for
insn2.
        leal    (%rdx,%rdx,4), %edx
        movl    %edx, e(%rip)
        movl    a(%rip), %edx
        sall    %cl, %edx       // insn2. Its constraint requires r1 in %ecx
        jmp     .L3
        .cfi_endproc

Because the bb starting from L2 is relatively cold, it is better to generate
the code below:

foo:
.LFB0:
        .cfi_startproc
        cmpl    $3, cond(%rip)
        movl    b(%rip), %esi
        movl    d(%rip), %ecx
        jg      .L2
        movl    c(%rip), %eax
.L3:
        sall    %cl, %eax           // r2 gets assigned %ecx. no reload is
needed.
        addl    %ecx, %esi
        movl    $.LC0, %edi
        movl    %eax, c(%rip)
        xorl    %eax, %eax
        jmp     printf
        .p2align 4,,10
        .p2align 3
.L2:
        movl    e(%rip), %eax
        movl    %ecx, %edx           // r2's live range is splitted here. This
is the start of the splitted live range.
        movl    %esi, %ecx           // r1 gets assigned %esi, this is reload
for insn2. 
        leal    (%rax,%rax,4), %eax
        movl    %eax, e(%rip)
        movl    a(%rip), %eax
        sall    %cl, %eax            // insn2. constraint of insn2 requires r1
in %ecx
        movl    %edx, %ecx           // r2's live range is splitted here. This
is the end of the splitted live range.
        jmp     .L3
        .cfi_endproc

Now there is less code in the hotpath (The bb starting from .L3).

r1 and r2 used in sall insns need CX_REG class which is
single_reg_operand_class in IRA. Existing logic in
process_single_reg_class_operands in ira-lives.c doesn't allow %ecx to being
assigned to r1 or r2. May it need improvement here?



More information about the Gcc-bugs mailing list