Re: Help-The possible places where insn is splitted in greg pass

2010-02-01 Thread fanqifei
2010/1/27 fanqifei fanqi...@gmail.com:
 2010/1/25 Ulrich Weigand uweig...@de.ibm.com:
 Qifei Fan wrote:

  But insn#479 is not recognized by recog() in insn-recog.c and the
  compilation failed. (recog only recognizes RTL defined in md, right?)
  Here the backtrace is
  reload---cleanup_subreg_operands---extract_insn_cached---extract_insn-=
 --recog_memoized---recog.
  There is no machine instruction(r3=3Dr1*4+r2) match the pattern of
  insn#479. Though there is pattern r3=3Dmem(r1*4+r2).
  I don=92t quite understand the generation of reload information.

 There's two issues here.  The first issue is that reload makes the
 fundamental assumption that everything that is a valid address, can
 be loaded into a register as well, if necessary.  On many platforms
 this is true, either because there is some sort of load address
 instruction, or because the form of valid addresses matches standard
 arithmetic instruction patterns.  Reload will simply emit a naked
 set of some register to the address -- if the back-end doesn't
 support that, you'll get the failure you saw.

 If this doesn't work on your particular platform, you could either
 try to set things up so that reload never thinks it needs to reload
 an address (but this may be difficult to achieve).  The safe option
 would be to tell reload how to achieve computing an address by
 providing a secondary reload pattern.  See e.g. s390_secondary_reload
 (in config/s390/s390.c) and the associated reloadmode_plus pattern.

 The second issue is as you notice here:

 Actually the second reload is not needed if there is already the first relo=
 ad.
 If (plus:SI (reg/f:SI 16 SP)  (const_int 96 [0x60]) is replaced by
 (reg:SI 12 a12), then (plus:SI (mult:SI (reg:SI 9 a9 [204])
 (const_int 4 [0x4])) (reg:SI 12 a12) ) is a valid memory address.
 But in function find_reloads, I can=92t find the related code that
 deciding whether the second reload should be generated by regarding
 the previous reload.  The function is too complex. :-(

 The first reload, loading sp + 96 into a register, is generated from
 within find_reloads_address.  After this is done, it is assumed that
 the address is now valid.

 However, something else later in find_reloads apparently assumes there
 is still some problem with the operand, and decides to reload the
 whole address.  It is hard to say exactly what the problem is, without
 seeing the insn constraints, but the most likely cause seems to be that
 this instruction pattern does not have a general m constraint, but
 a more restricted memory constraint.

 If this is the case, the back-end procedure called to verify the
 constraint probably rejects it.  This runs into another fundamental
 assumption reload makes: it assumes such procedures take other
 actions done by reload into account implicitly.  This means the
 constraint checker ought to *accept* addresses of the form
   reg*const + (sp + const)
 because it ought to know that reload will already load the (sp + const)
 into a register anyway.

 If this is *not* the case, please send me the instruction pattern
 and constraints for the insn pattern that matched insn 320 before
 reload so I can investigate in more detail.

 (Please note that I'm currently travelling with restricted access
 to email, so it might be a couple of days before I'm able to reply;
 sorry ...)

 Bye,
 Ulrich

 --
  Dr. Ulrich Weigand
  GNU Toolchain for Linux on System z and Cell BE
  ulrich.weig...@de.ibm.com


 For the second issue, there is indeed a strict constraint(back-end
 procedure) that rejects the pattern.
 The back-end procedure is composed of macros like
 EXTRA_MEMORY_CONSTRAINT/EXTRA_CONSTRAINT. These macros are defined in
 config/cpu.c and used in around Line3376 of reload.c(gcc4.3.2).
 So it's the constraint checker's job to know whether reload will load
 the (sp+const) into a register and use such information to decide
 whether to accept the pattern or not, right?
 Is there any other architecture which checks address by using previous
 determined reload info?
 I think this may be the proper way to resolve this problem. It may be
 easy to implement too.

 I will dig into all the issues and possible options, and provide more
 information later.
 As I am not familiar with it, it may take some time.

 Thanks very much!!
 -Qifei Fan

I have modified the constraint checker in which previous generated
reloads are considered.
Now the error is gone, from the result of reload I can see that the
reload is correct.
However the instruction is not in the final assembly code. It may be
optimized away.
So I am not sure this change is really correct.

-Qifei Fan


Re: Help-The possible places where insn is splitted in greg pass

2010-01-26 Thread fanqifei
2010/1/25 Ulrich Weigand uweig...@de.ibm.com:
 Qifei Fan wrote:

  But insn#479 is not recognized by recog() in insn-recog.c and the
  compilation failed. (recog only recognizes RTL defined in md, right?)
  Here the backtrace is
  reload---cleanup_subreg_operands---extract_insn_cached---extract_insn-=
 --recog_memoized---recog.
  There is no machine instruction(r3=3Dr1*4+r2) match the pattern of
  insn#479. Though there is pattern r3=3Dmem(r1*4+r2).
  I don=92t quite understand the generation of reload information.

 There's two issues here.  The first issue is that reload makes the
 fundamental assumption that everything that is a valid address, can
 be loaded into a register as well, if necessary.  On many platforms
 this is true, either because there is some sort of load address
 instruction, or because the form of valid addresses matches standard
 arithmetic instruction patterns.  Reload will simply emit a naked
 set of some register to the address -- if the back-end doesn't
 support that, you'll get the failure you saw.

 If this doesn't work on your particular platform, you could either
 try to set things up so that reload never thinks it needs to reload
 an address (but this may be difficult to achieve).  The safe option
 would be to tell reload how to achieve computing an address by
 providing a secondary reload pattern.  See e.g. s390_secondary_reload
 (in config/s390/s390.c) and the associated reloadmode_plus pattern.

 The second issue is as you notice here:

 Actually the second reload is not needed if there is already the first relo=
 ad.
 If (plus:SI (reg/f:SI 16 SP)  (const_int 96 [0x60]) is replaced by
 (reg:SI 12 a12), then (plus:SI (mult:SI (reg:SI 9 a9 [204])
 (const_int 4 [0x4])) (reg:SI 12 a12) ) is a valid memory address.
 But in function find_reloads, I can=92t find the related code that
 deciding whether the second reload should be generated by regarding
 the previous reload.  The function is too complex. :-(

 The first reload, loading sp + 96 into a register, is generated from
 within find_reloads_address.  After this is done, it is assumed that
 the address is now valid.

 However, something else later in find_reloads apparently assumes there
 is still some problem with the operand, and decides to reload the
 whole address.  It is hard to say exactly what the problem is, without
 seeing the insn constraints, but the most likely cause seems to be that
 this instruction pattern does not have a general m constraint, but
 a more restricted memory constraint.

 If this is the case, the back-end procedure called to verify the
 constraint probably rejects it.  This runs into another fundamental
 assumption reload makes: it assumes such procedures take other
 actions done by reload into account implicitly.  This means the
 constraint checker ought to *accept* addresses of the form
   reg*const + (sp + const)
 because it ought to know that reload will already load the (sp + const)
 into a register anyway.

 If this is *not* the case, please send me the instruction pattern
 and constraints for the insn pattern that matched insn 320 before
 reload so I can investigate in more detail.

 (Please note that I'm currently travelling with restricted access
 to email, so it might be a couple of days before I'm able to reply;
 sorry ...)

 Bye,
 Ulrich

 --
  Dr. Ulrich Weigand
  GNU Toolchain for Linux on System z and Cell BE
  ulrich.weig...@de.ibm.com


For the second issue, there is indeed a strict constraint(back-end
procedure) that rejects the pattern.
The back-end procedure is composed of macros like
EXTRA_MEMORY_CONSTRAINT/EXTRA_CONSTRAINT. These macros are defined in
config/cpu.c and used in around Line3376 of reload.c(gcc4.3.2).
So it's the constraint checker's job to know whether reload will load
the (sp+const) into a register and use such information to decide
whether to accept the pattern or not, right?
Is there any other architecture which checks address by using previous
determined reload info?
I think this may be the proper way to resolve this problem. It may be
easy to implement too.

I will dig into all the issues and possible options, and provide more
information later.
As I am not familiar with it, it may take some time.

Thanks very much!!
-Qifei Fan


Re: Help-The possible places where insn is splitted in greg pass

2010-01-25 Thread Ulrich Weigand
Qifei Fan wrote:

  But insn#479 is not recognized by recog() in insn-recog.c and the
  compilation failed. (recog only recognizes RTL defined in md, right?)
  Here the backtrace is
  reload---cleanup_subreg_operands---extract_insn_cached---extract_insn-=
 --recog_memoized---recog.
  There is no machine instruction(r3=3Dr1*4+r2) match the pattern of
  insn#479. Though there is pattern r3=3Dmem(r1*4+r2).
  I don=92t quite understand the generation of reload information.

There's two issues here.  The first issue is that reload makes the
fundamental assumption that everything that is a valid address, can
be loaded into a register as well, if necessary.  On many platforms
this is true, either because there is some sort of load address
instruction, or because the form of valid addresses matches standard
arithmetic instruction patterns.  Reload will simply emit a naked
set of some register to the address -- if the back-end doesn't
support that, you'll get the failure you saw.

If this doesn't work on your particular platform, you could either
try to set things up so that reload never thinks it needs to reload
an address (but this may be difficult to achieve).  The safe option
would be to tell reload how to achieve computing an address by
providing a secondary reload pattern.  See e.g. s390_secondary_reload
(in config/s390/s390.c) and the associated reloadmode_plus pattern.

The second issue is as you notice here:

 Actually the second reload is not needed if there is already the first relo=
 ad.
 If (plus:SI (reg/f:SI 16 SP)  (const_int 96 [0x60]) is replaced by
 (reg:SI 12 a12), then (plus:SI (mult:SI (reg:SI 9 a9 [204])
 (const_int 4 [0x4])) (reg:SI 12 a12) ) is a valid memory address.
 But in function find_reloads, I can=92t find the related code that
 deciding whether the second reload should be generated by regarding
 the previous reload.  The function is too complex. :-(

The first reload, loading sp + 96 into a register, is generated from
within find_reloads_address.  After this is done, it is assumed that
the address is now valid.

However, something else later in find_reloads apparently assumes there
is still some problem with the operand, and decides to reload the
whole address.  It is hard to say exactly what the problem is, without
seeing the insn constraints, but the most likely cause seems to be that 
this instruction pattern does not have a general m constraint, but
a more restricted memory constraint.

If this is the case, the back-end procedure called to verify the 
constraint probably rejects it.  This runs into another fundamental
assumption reload makes: it assumes such procedures take other
actions done by reload into account implicitly.  This means the
constraint checker ought to *accept* addresses of the form
   reg*const + (sp + const)
because it ought to know that reload will already load the (sp + const)
into a register anyway.

If this is *not* the case, please send me the instruction pattern
and constraints for the insn pattern that matched insn 320 before
reload so I can investigate in more detail.

(Please note that I'm currently travelling with restricted access
to email, so it might be a couple of days before I'm able to reply;
sorry ...)

Bye,
Ulrich

-- 
  Dr. Ulrich Weigand
  GNU Toolchain for Linux on System z and Cell BE
  ulrich.weig...@de.ibm.com


Re: Help-The possible places where insn is splitted in greg pass

2010-01-19 Thread fanqifei
2010/1/16 fanqifei fanqi...@gmail.com:
 2010/1/15 Ian Lance Taylor i...@google.com:
 There are many places where that insn could be generated, so it's
 pretty hard to answer your question as asked.

 I recommend setting a breakpoint on make_insn_raw if
 cfun-emit-x_cur_insn_uid == 479.  Then a backtrace will show you
 what is creating the insn.

 Ian

 That insn was generated in subst_reloads() called by reload_as_needed
 in reload1.c.

 In greg pass, the instruction#320 needs to be splitted. The cpu
 supports the memory address mode mem(r1*4+r2).
 (insn 320 308 309 19 a.c:381 (set (reg:SI 207 [ variable.wrData ])
        (mem/s:SI (plus:SI (mult:SI (reg:SI 204)
                    (const_int 4 [0x4]))
                (reg/f:SI 234)) [5 variable.wrData+0 S4 A32])) 3
 {movsi} (expr_list:REG_DEAD (reg:SI 204)
        (nil)))

 In find_reloads() (called by reload_as_needed()), following reload
 information was generated.
 (insn 320 308 309 19 a.c:381 (set (reg:SI 14 a14 [orig:207
 variable.wrData ] [207])
        (mem/s:SI (plus:SI (mult:SI (reg:SI 9 a9 [204])
                    (const_int 4 [0x4]))
                (plus:SI (reg/f:SI 16 SP)
                    (const_int 96 [0x60]))) [5 variable.wrData+0 S4
 A32])) 3 {movsi} (expr_list:REG_DEAD (reg:SI 9 a9 [204])
        (nil)))
 Reload 0: reload_in (SI) = (plus:SI (reg/f:SI 16 SP)
                                                    (const_int 96 [0x60]))
    GENERAL_REGS, RELOAD_FOR_INPUT_ADDRESS (opnum = 1)
    reload_in_reg: (plus:SI (reg/f:SI 16 SP)
                                                    (const_int 96 [0x60]))
    reload_reg_rtx: (reg:SI 12 a12)
 Reload 1: reload_in (SI) = (plus:SI (mult:SI (reg:SI 9 a9 [204])
                                                        (const_int 4 [0x4]))
                                                    (plus:SI (reg/f:SI 16 SP)
                                                        (const_int 96 [0x60])))
    GENERAL_REGS, RELOAD_FOR_INPUT (opnum = 1), inc by 4
    reload_in_reg: (plus:SI (mult:SI (reg:SI 9 a9 [204])
                                                        (const_int 4 [0x4]))
                                                    (plus:SI (reg/f:SI 16 SP)
                                                        (const_int 96 [0x60])))
    reload_reg_rtx: (reg:SI 12 a12)

 After find_reloads() called, emit_reload_insns() generated insns to
 reload operands. Then subst_reloads() substituted the reload regs
 using the replacement information.

 The insn list after subst_reloads():
 (insn 475 308 477 19 a.c:381 (set (reg:SI 12 a12)
        (const_int 96 [0x60])) -1 (nil))

 (insn 477 475 478 19 a.c:381 (set (reg:SI 12 a12)
        (reg/f:SI 16 SP)) -1 (nil))

 (insn 478 477 479 19 a.c:381 (set (reg:SI 12 a12)
        (plus:SI (reg:SI 12 a12)
            (const_int 96 [0x60]))) -1 (expr_list:REG_EQUIV (plus:SI
 (reg/f:SI 16 SP)
            (const_int 96 [0x60]))
        (nil)))

 (insn 479 478 320 19 a.c:381 (set (reg:SI 12 a12)
        (plus:SI (mult:SI (reg:SI 9 a9 [204])
                (const_int 4 [0x4]))
            (reg:SI 12 a12))) -1 (nil))

 (insn 320 479 481 19 a.c:381 (set (reg:SI 14 a14 [orig:207
 variable.wrData ] [207])
        (mem/s:SI (reg:SI 12 a12) [5 variable.wrData+0 S4 A32])) 3
 {movsi} (expr_list:REG_DEAD (reg:SI 9 a9 [204])
        (nil)))

 But insn#479 is not recognized by recog() in insn-recog.c and the
 compilation failed. (recog only recognizes RTL defined in md, right?)
 Here the backtrace is
 reload---cleanup_subreg_operands---extract_insn_cached---extract_insn---recog_memoized---recog.
 There is no machine instruction(r3=r1*4+r2) match the pattern of
 insn#479. Though there is pattern r3=mem(r1*4+r2).
 I don’t quite understand the generation of reload information.
 What can I do next?
 Thanks!

 Qifei Fan

Actually the second reload is not needed if there is already the first reload.
If (plus:SI (reg/f:SI 16 SP)  (const_int 96 [0x60]) is replaced by
(reg:SI 12 a12), then (plus:SI (mult:SI (reg:SI 9 a9 [204])
(const_int 4 [0x4])) (reg:SI 12 a12) ) is a valid memory address.
But in function find_reloads, I can’t find the related code that
deciding whether the second reload should be generated by regarding
the previous reload.  The function is too complex. :-(

  Qifei Fan


Re: Help-The possible places where insn is splitted in greg pass

2010-01-15 Thread fanqifei
2010/1/15 Ian Lance Taylor i...@google.com:
 There are many places where that insn could be generated, so it's
 pretty hard to answer your question as asked.

 I recommend setting a breakpoint on make_insn_raw if
 cfun-emit-x_cur_insn_uid == 479.  Then a backtrace will show you
 what is creating the insn.

 Ian

That insn was generated in subst_reloads() called by reload_as_needed
in reload1.c.

In greg pass, the instruction#320 needs to be splitted. The cpu
supports the memory address mode mem(r1*4+r2).
(insn 320 308 309 19 a.c:381 (set (reg:SI 207 [ variable.wrData ])
(mem/s:SI (plus:SI (mult:SI (reg:SI 204)
(const_int 4 [0x4]))
(reg/f:SI 234)) [5 variable.wrData+0 S4 A32])) 3
{movsi} (expr_list:REG_DEAD (reg:SI 204)
(nil)))

In find_reloads() (called by reload_as_needed()), following reload
information was generated.
(insn 320 308 309 19 a.c:381 (set (reg:SI 14 a14 [orig:207
variable.wrData ] [207])
(mem/s:SI (plus:SI (mult:SI (reg:SI 9 a9 [204])
(const_int 4 [0x4]))
(plus:SI (reg/f:SI 16 SP)
(const_int 96 [0x60]))) [5 variable.wrData+0 S4
A32])) 3 {movsi} (expr_list:REG_DEAD (reg:SI 9 a9 [204])
(nil)))
Reload 0: reload_in (SI) = (plus:SI (reg/f:SI 16 SP)
(const_int 96 [0x60]))
GENERAL_REGS, RELOAD_FOR_INPUT_ADDRESS (opnum = 1)
reload_in_reg: (plus:SI (reg/f:SI 16 SP)
(const_int 96 [0x60]))
reload_reg_rtx: (reg:SI 12 a12)
Reload 1: reload_in (SI) = (plus:SI (mult:SI (reg:SI 9 a9 [204])
(const_int 4 [0x4]))
(plus:SI (reg/f:SI 16 SP)
(const_int 96 [0x60])))
GENERAL_REGS, RELOAD_FOR_INPUT (opnum = 1), inc by 4
reload_in_reg: (plus:SI (mult:SI (reg:SI 9 a9 [204])
(const_int 4 [0x4]))
(plus:SI (reg/f:SI 16 SP)
(const_int 96 [0x60])))
reload_reg_rtx: (reg:SI 12 a12)

After find_reloads() called, emit_reload_insns() generated insns to
reload operands. Then subst_reloads() substituted the reload regs
using the replacement information.

The insn list after subst_reloads():
(insn 475 308 477 19 a.c:381 (set (reg:SI 12 a12)
(const_int 96 [0x60])) -1 (nil))

(insn 477 475 478 19 a.c:381 (set (reg:SI 12 a12)
(reg/f:SI 16 SP)) -1 (nil))

(insn 478 477 479 19 a.c:381 (set (reg:SI 12 a12)
(plus:SI (reg:SI 12 a12)
(const_int 96 [0x60]))) -1 (expr_list:REG_EQUIV (plus:SI
(reg/f:SI 16 SP)
(const_int 96 [0x60]))
(nil)))

(insn 479 478 320 19 a.c:381 (set (reg:SI 12 a12)
(plus:SI (mult:SI (reg:SI 9 a9 [204])
(const_int 4 [0x4]))
(reg:SI 12 a12))) -1 (nil))

(insn 320 479 481 19 a.c:381 (set (reg:SI 14 a14 [orig:207
variable.wrData ] [207])
(mem/s:SI (reg:SI 12 a12) [5 variable.wrData+0 S4 A32])) 3
{movsi} (expr_list:REG_DEAD (reg:SI 9 a9 [204])
(nil)))

But insn#479 is not recognized by recog() in insn-recog.c and the
compilation failed. (recog only recognizes RTL defined in md, right?)
Here the backtrace is
reload---cleanup_subreg_operands---extract_insn_cached---extract_insn---recog_memoized---recog.
There is no machine instruction(r3=r1*4+r2) match the pattern of
insn#479. Though there is pattern r3=mem(r1*4+r2).
I don’t quite understand the generation of reload information.
What can I do next?
Thanks!

Qifei Fan


Re: Help-The possible places where insn is splitted in greg pass

2010-01-14 Thread Ian Lance Taylor
fanqifei fanqi...@gmail.com writes:

 2010/1/13 fanqifei fanqi...@gmail.com:
 Hi,
 I am working on a micro controller and trying to port gcc(4.3.2) for it.
 Not the compiling process runs into the following error:
 a.c: In function 'task':
 a.c:150: error: unrecognizable insn:
 (insn 479 478 320 19 a:381 (set (reg:SI 12 a12)
         (plus:SI (mult:SI (reg:SI 9 a9 [204])
                 (const_int 4 [0x4]))
             (reg:SI 12 a12))) -1 (nil))
 a.c:150: internal compiler error: in extract_insn, at recog.c:1990
 Please submit a full bug report, ...

 This insn is generated in greg pass from another insn:
 (insn 320 308 309 19 a.c:381 (set (reg:SI 207 [ variable.wrData ])
 (mem/s:SI (plus:SI (mult:SI (reg:SI 204)
 (const_int 4 [0x4]))
 (reg/f:SI 234)) [5 variable.wrData+0 S4 A32])) 3 {movsi}
 (expr_list:REG_DEAD (reg:SI 204)
 (nil)))
 I surfed the web a bit and found similar gcc bug report 37436
 http://gcc.gnu.org/bugzilla/show_bug.cgi?id=37436.
 But basically they are not same.

 Can someone show me the possible places where insn#479 is generated in
 reload.c or reload1.c?
 Thanks!

 Qifei Fan

 Is there anyone can help?

There are many places where that insn could be generated, so it's
pretty hard to answer your question as asked.

I recommend setting a breakpoint on make_insn_raw if
cfun-emit-x_cur_insn_uid == 479.  Then a backtrace will show you
what is creating the insn.

Ian


Help-The possible places where insn is splitted in greg pass

2010-01-13 Thread fanqifei
Hi,
I am working on a micro controller and trying to port gcc(4.3.2) for it.
Not the compiling process runs into the following error:
a.c: In function 'task':
a.c:150: error: unrecognizable insn:
(insn 479 478 320 19 a:381 (set (reg:SI 12 a12)
        (plus:SI (mult:SI (reg:SI 9 a9 [204])
                (const_int 4 [0x4]))
            (reg:SI 12 a12))) -1 (nil))
a.c:150: internal compiler error: in extract_insn, at recog.c:1990
Please submit a full bug report, ...

This insn is generated in greg pass from another insn:
(insn 320 308 309 19 a.c:381 (set (reg:SI 207 [ variable.wrData ])
(mem/s:SI (plus:SI (mult:SI (reg:SI 204)
(const_int 4 [0x4]))
(reg/f:SI 234)) [5 variable.wrData+0 S4 A32])) 3 {movsi}
(expr_list:REG_DEAD (reg:SI 204)
(nil)))
I surfed the web a bit and found similar gcc bug report 37436
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=37436.
But basically they are not same.

Can someone show me the possible places where insn#479 is generated in
reload.c or reload1.c?
Thanks!

Qifei Fan