Hi,
I ran into a case and found conditional (const) propagation is
mishandled in cprop pass.
With following insn sequence after cprop1 pass:
----------------------------------------------------
(note 878 877 880 96 [bb 96] NOTE_INSN_BASIC_BLOCK)

(insn 882 881 883 96 (set (reg:CC 24 cc)
        (compare:CC (reg:SI 684 [ default_num_contexts ])
            (const_int 0 [0]))) core_main.c:265 211 {*arm_cmpsi_insn}
     (nil))

(jump_insn 883 882 886 96 (set (pc)
        (if_then_else (ne (reg:CC 24 cc)
                (const_int 0 [0]))
            (label_ref:SI 905)
            (pc))) core_main.c:265 223 {*arm_cond_branch}
     (expr_list:REG_DEAD (reg:CC 24 cc)
        (expr_list:REG_BR_PROB (const_int 9100 [0x238c])
            (nil)))
 -> 905)

(note 886 883 49 97 [bb 97] NOTE_INSN_BASIC_BLOCK)

(insn 49 886 0 97 (set (reg/v:SI 291 [ total_errors ])
        (reg:SI 684 [ default_num_contexts ])) core_main.c:265 709
{*thumb2_movsi_insn}
     (expr_list:REG_DEAD (reg:SI 684 [ default_num_contexts ])
        (expr_list:REG_EQUAL (const_int 0 [0])
            (nil))))
......

(code_label 905 54 904 47 54 "" [1 uses])

(note 904 905 46 47 [bb 47] NOTE_INSN_BASIC_BLOCK)

(insn 46 904 47 47 (set (reg/v:SI 291 [ total_errors ])
        (const_int 0 [0])) core_main.c:265 709 {*thumb2_movsi_insn}
     (nil))
----------------------------------------------------

The insn49 should be propagated with conditional const from insn882
and jump_insn883, optimized into "r291<-0" as following code, then let
pre do redundancy elimination work.
----------------------------------------------------
(note 878 877 880 96 [bb 96] NOTE_INSN_BASIC_BLOCK)

(insn 882 881 883 96 (set (reg:CC 24 cc)
        (compare:CC (reg:SI 684 [ default_num_contexts ])
            (const_int 0 [0]))) core_main.c:265 211 {*arm_cmpsi_insn}
     (nil))

(jump_insn 883 882 886 96 (set (pc)
        (if_then_else (ne (reg:CC 24 cc)
                (const_int 0 [0]))
            (label_ref:SI 905)
            (pc))) core_main.c:265 223 {*arm_cond_branch}
     (expr_list:REG_DEAD (reg:CC 24 cc)
        (expr_list:REG_BR_PROB (const_int 9100 [0x238c])
            (nil)))
 -> 905)

(note 886 883 49 97 [bb 97] NOTE_INSN_BASIC_BLOCK)

(insn 49 886 0 97 (set (reg/v:SI 291 [ total_errors ])
        (const_int 0 [0])) core_main.c:265 709 {*thumb2_movsi_insn}
     (expr_list:REG_DEAD (reg:SI 684 [ default_num_contexts ])
        (expr_list:REG_EQUAL (const_int 0 [0])
            (nil))))
......

(code_label 905 54 904 47 54 "" [1 uses])

(note 904 905 46 47 [bb 47] NOTE_INSN_BASIC_BLOCK)

(insn 46 904 47 47 (set (reg/v:SI 291 [ total_errors ])
        (const_int 0 [0])) core_main.c:265 709 {*thumb2_movsi_insn}
     (nil))
----------------------------------------------------

The problem is function one_cprop_pass does local const/copy
propagation pass first, then the global pass, which only handles
global opportunities.
Though conditional const information "r684 <- 0" is collected by
find_implicit_sets, the conditional information is recorded as local
information of bb 97, and it is not recorded in avout of bb 96, so not
in avin of bb 97 either.

Unfortunately, the global pass only considers potential opportunities
from avin of each basic block in function cprop_insn and
find_avail_set.

That's why the conditional propagation opportunity in bb 97 is missed.

I worked a patch to fix this, and wanna hear more suggestions on this topic.
Is it a bug or I missed something important?

Thanks

BTW, I'm using gcc mainline which configured for arm-none-eabi target.

Reply via email to