Hi,
I am working on gcc 4.1.1 and Itanium architecture. I want to modify
the machine description of ia64.md to add some checks before each ld
instruction. the
following is the original define_insn:

        (define_insn "*movqi_internal"
         [(set (match_operand:QI 0 "destination_operand" "=r,r,r, m, r,*f,*f")
         (match_operand:QI 1 "move_operand"        "rO,J,m,rO,*f,rO,*f"))]
         "ia64_move_ok (operands[0], operands[1])"
         "@
          mov %0 = %r1
          addl %0 = %1, r0
          ld1%O1 %0 = %1%P1
          st1%Q0 %0 = %r1%P0
          getf.sig %0 = %1
          setf.sig %0 = %r1
          mov %0 = %1"
          [(set_attr "itanium_class" "ialu,ialu,ld,st,frfr,tofr,fmisc")])

I observe that there is a ld instruction in 3rd alternative, so I add
a new define_insn before it in the hope that it will be matched
firstly.

        (define_insn "*ld_movqi_internal"
         [(set (match_operand:QI 0 "destination_operand" "=r")
         (match_operand:QI 1 "move_operand" "m"))]
         "ia64_move_ok (operands[0], operands[1])
          && flag_check_ld"
          {
                printf("define_insn ld_movqi_internal\n");
                return "ld1%O1 %0 = %1%P1";
          }
          [(set_attr "itanium_class" "ld")]

I keep every thing the same as 3rd alternative in original define_insn
except using C statement to return the desired output template.
However, when I use the newly builded gcc to compile the following
program, it crashes.
        
        #include <stdio.h>

        char characters[8192]={'a',};

        int main()
        {
        char c = characters[0];
        printf("Hello World! c:%c\n", c);
        }

the error reported is:
hi.c:9: error: unable to generate reloads for:
(insn 10 9 12 1 (set (mem/c/i:QI (reg/f:DI 111 loc79) [0 c+0 S1 A128])
       (reg:QI 14 r14 [orig:342 characters ] [342])) 3
{*gift_movqi_internal_ld} (nil)
   (expr_list:REG_DEAD (reg:QI 14 r14 [orig:342 characters ] [342])
       (nil)))
hi.c:9: internal compiler error: in find_reloads, at reload.c:3738

In IA64, the first pesudo register number is 334, thus register 111
and register 14 are both hardware registers.

I looked at find_reloads at reload.c and find the following code
fragement and comment:

 /* The operands don't meet the constraints.
    goal_alternative describes the alternative
    that we could reach by reloading the fewest operands.
    Reload so as to fit it.  */

 if (best == MAX_RECOG_OPERANDS * 2 + 600)
   {
     /* No alternative works with reloads??  */
     if (insn_code_number >= 0)
       fatal_insn ("unable to generate reloads for:", insn);
     ...

So, what is going on here? Especially, what is find_reloads going to
finish and why it is going wrong here...

I would appreciate any help on this question, thx!

Best Regards

--andy.wu

Reply via email to