This is the mail archive of the gcc@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

RE: add and compare combination


Well, I run combine pass in debug mode and found my mistakes. I'd like to share what I have found :)

There were 2 mistake. First my HARD_REGNO_MODE_OK returned 0 for regno=CCI_REG and mode=CCmode which lead to an early failure in combine.c.
So I added this to my macro :

if (GET_MODE_CLASS (mode) == MODE_CC)
  return (regno == CCI_REG)




Secondly, I figured out that combination was different for the 2 following code :

c = a + b;
if (c) {...} /* use c further in code */

and

if (a + b) {...} /* the addition result is a DEAD_REG */


In the first case the combiner create and try to match a parallel rtx similar to my "add_and_compare". This case was in fact working.
In the second case the combiner see the DEAD_REG and try to match a single set rtx of this form :

(define_insn "comparesi_plus"
  [(set (reg:CC CCI_REG)
        (compare:CC
          (match_operand:SI 0 "register_operand" "r")
          (neg:SI (match_operand:SI 1 "register_operand" "r"))))]  ;; the 'trick' is in the neg !!
  ""
  "cmp_plus %1,%0"
)

As I had no such insn the combination was failing, when I added one (with a clobbered result because I have no cmp_plus instruction), everything run ok. I watched in arm backend and I found a similar insn... So the solution was in front of me but I did not see it :)

	Selim


-----Message d'origine-----
De?: gcc-owner@gcc.gnu.org [mailto:gcc-owner@gcc.gnu.org] De la part de BELBACHIR Selim
Envoyé?: jeudi 15 décembre 2011 16:12
À?: gcc@gcc.gnu.org
Objet?: add and compare combination

Hi,

I'd like to know if there a way to express 'add' and 'compare' insn so that the combiner transform it in and 'add_and_compare' insn.

I watch arm backend and it seems possible when I look at 'addsi3', 'cbranchsi4' and '*addsi3_compare0'.

In my backend I have written the following insn/expand :

(define_expand "addsi3"
  [(set (match_operand:SI          0 "register_operand" "")
                (plus:SI (match_operand:SI 1 "general_operand" "")
                                (match_operand:SI 2 "off1post_general_op" "")))]
   ""
   ""
)

(define_insn "add_and_compare"
  [(set (reg:CC CCI_REG)
        (compare:CC
          (plus:SI
            (match_operand:SI 1 "register_operand" "%r")
            (match_operand:SI 2 "register_operand" "r"))
          (const_int 0)))
   (set (match_operand:SI 0 "register_operand"      "=r")
          (plus:SI
            (match_dup 1)
            (match_dup 2)))]
   ""
   "add %1,%2,%0"
)

(define_insn "add"
  [(set (match_operand:SI 0 "register_operand"      "=r")
          (plus:SI
            (match_operand:SI 1 "register_operand" "%r")
            (match_operand:SI 2 "register_operand" "r")))]
   ""
   "addk %1,%2,%0"
)

(define_expand "cbranchsi4"
  [(set (pc) 
        (if_then_else (match_operator 0 "comparison_operator"
           [(match_operand:SI 1 "register_operand" "")
            (match_operand:SI 2 "register_operand" "")])
        (label_ref (match_operand 3 "" ""))
        (pc)))]
  
  {
    emit_insn(gen_comparesi (operands[1], operands[2]));
      
    operands[1] = gen_rtx_REG (CCmode, CCI_REG);
    operands[2] = const0_rtx;
  }
)

(define_insn "comparesi"
  [(set (reg:CC CCI_REG)
        (compare:CC
          (match_operand:SI 0 "register_operand" "r")
          (match_operand:SI 1 "register_operand" "r")))]
  ""
  "cmp %1,%0"
)

(define_insn "jmpifsi"
  [(set (pc) 
        (if_then_else (match_operator 0 "comparison_operator"
          [(reg:CC CCI_REG) (const_int 0)])
        (label_ref (match_operand 1 "" ""))
        (pc)))]
  ""
  "jmp.if %c0 %1"
)

When I compile :

c = a + b;
if (c) {...}

No combination occurs between "add" and "comparesi" insn. I was expecting to see my "add_and_compare" pattern.
The resulting assembler is 
                addk
                cmp
                jmp.if
instead of
                add
                jmp.if

Do someone see why combination fails ? (gcc 4.5.2)

Thanks,

                Selim


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]