LOGIN   :::   RECOVER PASS   :::   GET ACCOUNT    
Browse
  • Projects
  • Code (CVS)
  • Forums
  • News
  • Articles
  • Polls
  •  
    OpenCores
  • FAQ
  • CVS HowTo
  • Mission
  • Media
  • Tools
  • Advertise
  • Mirrors
  • Logos
  • Contact us
  • Find Resources
  • Job Opportunity
  •  
    Tools
  • Search
      
  • Download Cores (CVSGet)
  •  
    More
  • Wishbone
  • Perlilog
  • EDA tools
  • OpenTech CD
  •  
    Navigation: All forums > Openrisc > Message List > Message Post

    Message

    Reply | Reply all
    Date Prev | Date Next | Thread Prev | Thread Next Date Index | Thread Index

    From: pablo.huerta@a...
    Date: Thu, 13 Nov 2003 10:33:41 +0100
    Subject: Re: [openrisc] Optimization Problems
    Top

    If you don't define both "movdi" and "movdf" instructions, GCC will
    use his owns ones from floating point library, I suppose. But we have
    tested that when using that functions from floating point library they
    work ok almost always, but when compiling with optimizations they
    crash sometimes. I think that is better to include this functions
    regardless the FPU will be added soon, because some people perhaps
    will not want to use that unit and will need to have software support
    for floating point opperations.
    
    Regards,
    
    Pablo Huerta
    
    ----- Original Message ----- 
    From: "Damjan Lampret" <lampret@o... > 
    To: <openrisc@o... > 
    Date: Wed, 12 Nov 2003 19:10:57 +0100 
    Subject: Re: [openrisc] Optimization Problems 
    
    > 
    > 
    > Pablo, 
    > 
    > this is the floating point stuff. Properly is to use soft floating 
    > point 
    > library. The FPU is just being added to or1ksim and OR1200. So 
    > nobody is 
    > taking seriously gcc with regard to proper FP support (that's why 
    > it says 
    > "fake insns") 
    > 
    > regards, 
    > Damjan 
    > 
    > ----- Original Message ----- 
    > From: <pablo.huerta@a... > 
    > To: <openrisc@o... > 
    > Sent: Wednesday, November 12, 2003 4:11 PM 
    > Subject: Re: [openrisc] Optimization Problems 
    > 
    > 
    > > Hi again: 
    > > 
    > > The bugs I have found and the way to solve them are the 
    > following: 
    > > 
    > > In File or32.md: 
    > > 
    > >      (define_insn "movdf"  [(set (match_operand:DF 0 
    > "general_operand" 
    > > "=r,r,m") 
    > >              (match_operand:DF 1 "general_operand" "r,m,r"))] 
    > >        "" 
    > >        "* 
    > >        switch(which_alternative) 
    > >         { 
    > >           case 0: 
    > >             return \"l.addi  \\t%0,%1,0\\t # fake insn for 
    > handling DF\"; 
    > >           case 1: 
    > >             return \"l.lwz    \\t%0,%1\\t # fake insn for 
    > handling DF\"; 
    > >           case 2: 
    > >             return \"l.sw    \\t%0,%1\\t # fake insn for 
    > handling DF\"; 
    > >           default: 
    > >             return \"invalid alternative\"; 
    > >         }" 
    > >      [(set_attr "type" "move,load,store") 
    > >         (set_attr "length" "1,1,1")]) 
    > > 
    > > Should be replaced with: 
    > > 
    > >      (define_insn "movdf" 
    > >              [(set (match_operand:DF 0 "nonimmediate_operand" 
    > "=r, r, 
    > > m, r") 
    > >                    (match_operand:DF 1 "general_operand"      
    > " r, m, 
    > > r, i"))] 
    > >              "" 
    > >              "* 
    > >               return or1k_output_move_double (operands); 
    > >              " 
    > >              [(set_attr "length" "2,2,2,3")]) 
    > > 
    > > And function or1k_output_move_double(operands) must be placed 
    > in 
    > > or1k.c. The definition for that function is as follows: 
    > > 
    > > char * 
    > > or1k_output_move_double(rtx *operands) 
    > > 
    > > { 
    > > rtx xoperands[3]; 
    > > switch (GET_CODE (operands[0])) { 
    > > case REG: 
    > > if (GET_CODE (operands[1]) == REG) 
    > > { 
    > > if (REGNO (operands[0]) == REGNO (operands[1]) + 1) 
    > > { 
    > > output_asm_insn ("\tl.or    \t%H0, %H1, r0", operands); 
    > > output_asm_insn ("\tl.or    \t%0, %1, r0", operands); 
    > > return ""; 
    > > } 
    > > else 
    > > { 
    > > output_asm_insn ("\tl.or    \t%0, %1, r0", operands); 
    > > output_asm_insn ("\tl.or    \t%H0, %H1, r0", operands); 
    > > return ""; 
    > > } 
    > > } 
    > > else if (GET_CODE (operands[1]) == MEM) 
    > > { 
    > > xoperands[1] = XEXP (operands[1], 0); 
    > > if (GET_CODE (xoperands[1]) == REG) 
    > > { 
    > > xoperands[0] = operands[0]; 
    > > if (REGNO (xoperands[0]) == REGNO (xoperands[1])) 
    > > { 
    > > output_asm_insn ("\tl.lwz   \t%H0, 4(%1)", xoperands); 
    > > output_asm_insn ("\tl.lwz   \t%0, 0(%1)", xoperands); 
    > > return ""; 
    > > } 
    > > else 
    > > { 
    > > output_asm_insn ("\tl.lwz   \t%0, 0(%1)", xoperands); 
    > > output_asm_insn ("\tl.lwz   \t%H0, 4(%1)", xoperands); 
    > > return ""; 
    > > } 
    > > } 
    > > else if (GET_CODE (xoperands[1]) == PLUS) 
    > > { 
    > > if (GET_CODE (xoperands[2] = XEXP (xoperands[1], 1)) == REG) 
    > > { 
    > > xoperands[0] = operands[0]; 
    > > xoperands[1] = XEXP (xoperands[1], 0); 
    > > if (REGNO (xoperands[0]) == REGNO (xoperands[2])) 
    > > { 
    > > output_asm_insn ("\tl.lwz   \t%H0, %1+4(%2)", xoperands); 
    > > output_asm_insn ("\tl.lwz   \t%0, %1(%2)", xoperands); 
    > > return ""; 
    > > } 
    > > else 
    > > { 
    > > output_asm_insn ("\tl.lwz   \t%0, %1(%2)", xoperands); 
    > > output_asm_insn ("\tl.lwz   \t%H0, %1+4(%2)", xoperands); 
    > > return ""; 
    > > } 
    > > } 
    > > else if (GET_CODE (xoperands[2] = XEXP (xoperands[1], 0)) == 
    > REG) 
    > > { 
    > > xoperands[0] = operands[0]; 
    > > xoperands[1] = XEXP (xoperands[1], 1); 
    > > if (REGNO (xoperands[0]) == REGNO (xoperands[2])) 
    > >                                                 { 
    > > 
    > > output_asm_insn ("\tl.lwz   \t%H0, %1+4(%2)", xoperands); 
    > > 
    > > output_asm_insn ("\tl.lwz   \t%0, %1(%2)", xoperands); 
    > >                                                         return 
    > ""; 
    > >                                                 } 
    > > else 
    > >                                                 { 
    > > 
    > > output_asm_insn ("\tl.lwz   \t%0, %1(%2)", xoperands); 
    > > 
    > > output_asm_insn ("\tl.lwz   \t%H0, %1+4(%2)", xoperands); 
    > >                                                         return 
    > ""; 
    > >                                                 } 
    > > } 
    > > else abort (); 
    > > } 
    > > else abort (); 
    > > } 
    > > else if (GET_CODE (operands[1]) == CONST_INT) 
    > > { 
    > > if (INTVAL (operands[1]) < 0) 
    > > output_asm_insn ("\tl.addi  \t%0, r0, -1", operands); 
    > > else 
    > > output_asm_insn ("\tl.or    \t%0, r0, r0", operands); 
    > > output_asm_insn ("\tl.movhi \t%H0, hi(%1)", operands); 
    > > output_asm_insn ("\tl.ori   \t%H0, %H0, lo(%1)", operands); 
    > > return ""; 
    > > } 
    > > else abort (); 
    > > case MEM: 
    > > xoperands[0] = XEXP (operands[0], 0); 
    > > if (GET_CODE (xoperands[0]) == REG) 
    > > { 
    > > xoperands[1] = operands[1]; 
    > > output_asm_insn ("\tl.sw    \t0(%0), %1", xoperands); 
    > > output_asm_insn ("\tl.sw    \t4(%0), %H1", xoperands); 
    > > return ""; 
    > > } 
    > > else if (GET_CODE (xoperands[0]) == PLUS) 
    > > { 
    > > if (GET_CODE (xoperands[1] = XEXP (xoperands[0], 1)) == REG) 
    > > { 
    > > xoperands[0] = XEXP (xoperands[0], 0); 
    > > xoperands[2] = operands[1]; 
    > > output_asm_insn ("\tl.sw    \t%0(%1), %2", xoperands); 
    > > output_asm_insn ("\tl.sw    \t%0+4(%1), %H2", xoperands); 
    > > return ""; 
    > > } 
    > > else if (GET_CODE (xoperands[1] = XEXP (xoperands[0], 0)) == 
    > REG) 
    > > { 
    > > xoperands[0] = XEXP (xoperands[0], 1); 
    > > xoperands[2] = operands[1]; 
    > > output_asm_insn ("\tl.sw    \t%0(%1), %2", xoperands); 
    > > output_asm_insn ("\tl.sw    \t%0+4(%1), %H2", xoperands); 
    > > return ""; 
    > > } 
    > > else abort (); 
    > > } 
    > > else abort (); 
    > > default: 
    > > abort (); 
    > > } 
    > > } 
    > > 
    > > 
    > > Following with or32.md, I think that "movdi" should be 
    > defined. The 
    > > definition is similar to "movdf" : 
    > > 
    > >      (define_insn "movdi" 
    > >              [(set (match_operand:DI 0 "nonimmediate_operand" 
    > "=r, r, 
    > > m, r") 
    > >                    (match_operand:DI 1 "general_operand"      
    > " r, m, 
    > > r, i"))] 
    > >              "" 
    > >              "* 
    > >               return or1k_output_move_double (operands); 
    > >              " 
    > >              [(set_attr "length" "2,2,2,3")]) 
    > > 
    > > Also in or32.md I think you should define "addi3". The 
    > definition 
    > > should be: 
    > > 
    > >      (define_insn "adddi3" 
    > >              [(set (match_operand:DI 0 "register_operand" 
    > "=&r") 
    > >                    (plus:DI (match_operand:DI 1 
    > "register_operand" "%r") 
    > >                              (match_operand:DI 2 
    > "register_operand" " 
    > > r")))] 
    > >              "" 
    > >              "* 
    > >               return or1k_output_add_double (operands); 
    > >              " 
    > >              [(set_attr "length" "2")]) 
    > > 
    > > The definition of or1k_output_add_double(operands) must be put 
    > in or1k.c: 
    > > 
    > > char * 
    > > or1k_output_add_double (rtx *operands) 
    > > 
    > > { 
    > > if (REGNO (operands[0]) + 1 == REGNO (operands[1])) 
    > > { 
    > > output_asm_insn ("\tl.add   \t%0, %H1, %H2", operands); 
    > > output_asm_insn ("\tl.addc  \t%0, %1, %2", operands); 
    > > output_asm_insn ("\tl.add   \t%H0, %H1, %H2", operands); 
    > > } 
    > > else 
    > > { 
    > > output_asm_insn ("\tl.add   \t%H0, %H1, %H2", operands); 
    > > output_asm_insn ("\tl.addc  \t%0, %1, %2", operands); 
    > > } 
    > > return ""; 
    > > } 
    > > 
    > > That's all the changes that must be done in or32.md. I think 
    > that this 
    > > changes will solve most of the optimization problems. I don't 
    > have 
    > > tested it with GCC 3.2.3, but in 3.4 they work fine. 
    > > 
    > > Now, changes I think that must be made in or32.S: 
    > > 
    > > If the ABI has not changed since the last time, Calle-Saved 
    > Registers 
    > > are: r10, r13, r15, r17, r19, r21, r23, r25, r27, r29 and r31, 
    > so if 
    > > you use them inside a function call, you should save them at 
    > function 
    > > entry and restore them at function exit, so in file or32.S you 
    > should do: 
    > > 
    > >    in function ___udivsi3, the instruction "l.addi          
    > r13,r0,32" 
    > >  should use another register (r12 for example) instead of r13, 
    > or you 
    > > should save r13 in function entry for restoring it in function 
    > exit. 
    > > The same happens with registers r15 and r17 in manay 
    > instructions. I 
    > > think that the easiest way to solve that problem is to replace 
    > every 
    > > usage of r13 for r12, r15 for r14, and r17 for r16. 
    > > 
    > > Anything else at the moment. 
    > > 
    > > Bestb regards, 
    > > 
    > > Pablo Huerta 
    > > 
    > > ----- Original Message ----- 
    > > From: Matjaz Breskvar <phoenix@f... > 
    > > To: openrisc@o... 
    > > Date: Wed, 12 Nov 2003 13:22:48 +0100 
    > > Subject: Re: [openrisc] Optimization Problems 
    > > 
    > > > 
    > > > 
    > > > * pablo.huerta@a...  (pablo.huerta@a... ) 
    > > > wrote: 
    > > > > Hi all! 
    > > > > 
    > > > > I have read some messages about optimization 
    > problems when 
    > > > using GCC 
    > > > > 3.2.3. In 
    > > > > 
    > > > 
    > > 
    > 
    >
    http://www.teisa.unican.es/~csanchez/guides/double_modes_bug_explanation.shtml
    
    > > 
    > > > > there is an explanation on how we solved a bug with 
    > > > optimization 
    > > > > problems in GCC 2.9.5 that is not solved yet in GCC 
    > 3.2.3, 
    > > > reading 
    > > > > this may help OpenCores GCC maintainers to solve 
    > this 
    > > > problems. 
    > > > 
    > > > i'll look into this and fix it. 
    > > > 
    > > > > If any GCC maintainer needs help to solve that 
    > problem, I can 
    > > > help 
    > > > > him. I have also found   some problems in file 
    > or32.S, in the 
    > > > > __udivsi3 function. I think that functions in or32.S 
    > file 
    > > > should be 
    > > > > revised. I don't have write acces to CVS so if any 
    > maintainer 
    > > > could 
    > > > > help me to solve that bugs please contact me. 
    > > > 
    > > > i'm defenetly interested in fixing any/all bugs in 
    > OpenRISC 
    > > > toolchain. 
    > > > please do post any bugs you've found with proposed 
    > bugfixes. 
    > > > 
    > > > > Also we have already developed the port of GCC 3.4 
    > and will be 
    > > > ready 
    > > > > for downloading in that web page soon: 
    > > > > http://www.teisa.unican.es/~csanchez/download1.shtml 
    > A port of 
    > > > eCos 2.0 
    > > > > is also ready to be published. I will post a message 
    > in the 
    > > > forum when 
    > > > > everythingh is ready to download. 
    > > > 
    > > > please make sure that your gcc-3.4 port uses the same ABI 
    > > > than ours. one quick test would be to compile uclinux 
    > from 
    > > > opencores 
    > > > cvs. i think it's in all ours best interest to have one 
    > unified 
    > > > toolchain 
    > > > to avoid duplicating efforts. 
    > > > 
    > > > regards, 
    > > > p. 
    > > > 
    > > 
    > 
    
    
    
     
    Copyright (c) 1999 OPENCORES.ORG. All rights reserved.