On Tue, Nov 25, 2014 at 09:13:10AM +0100, Uros Bizjak wrote: > On Tue, Nov 25, 2014 at 8:40 AM, Uros Bizjak <ubiz...@gmail.com> wrote: > > On Tue, Nov 25, 2014 at 12:25 AM, Jakub Jelinek <ja...@redhat.com> wrote: > > > >> The fallback delegitimization I've added as last option mainly for > >> debug info purposes, when we don't know if the base is a PIC register > >> or say a PIC register plus some addend, unfortunately in some tests > >> broke find_base_term, which for PLUS looks only at the first operand > >> and recursion on it finds a base term, it returns it immediately. > >> So, it found base term of _GLOBAL_OFFSET_TABLE_, when the right base > >> term is actually in the second operand. > >> > >> This patch fixes it by swapping the operands, debug info doesn't care about > >> the order, it won't match in any instruction anyway, but helps alias.c. > >> > >> Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk? > >> > >> 2014-11-24 Jakub Jelinek <ja...@redhat.com> > >> > >> PR lto/64025 > >> * config/i386/i386.c (ix86_delegitimize_address): Ensure result > >> comes before (addend - _GLOBAL_OFFSET_TABLE_) term. > > > > Can you also swap operands of (%ecx - %ebx) + foo? There is no point > > digging into RTX involving registers only when we know that we are > > looking for foo. This will also be consistent with the code you > > patched below. > > Something like attached prototype patch.
Actually, thinking about it more, at least according to commutative_operand_precedence the canonical order is what we used to return (i.e. (something - _G_O_T_) + (symbol_ref) or (something - _G_O_T_) + (const (symbol_ref +- const)) So perhaps better fix is to follow find_base_value, which does something like: /* Guess which operand is the base address: If either operand is a symbol, then it is the base. If either operand is a CONST_INT, then the other is the base. */ if (CONST_INT_P (src_1) || CONSTANT_P (src_0)) return find_base_value (src_0); else if (CONST_INT_P (src_0) || CONSTANT_P (src_1)) return find_base_value (src_1); and do something similar in find_base_term too. I.e. perhaps even with higher precedence over REG_P with REG_POINTER (or lower, in these cases it doesn't really matter, neither argument is REG_P), choose first operand that is CONSTANT_P and not CONST_INT_P. Jakub