This is the mail archive of the gcc-patches@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] |
Hello! This patch is based on observations by Steven Bosscher in PR tartet/23524 (comment #11), where he found that the length of displacement only move to AX reg is wrong: A100000000 movl x, %eax # 11 *movsi_1/1 [length = 6] The problem is in the calculation on "modrm" attribute, that misses a couple of special cases. In the case above, A0, A1, A2 and A3 opcodes do _not_ need a modrm byte. This patch fixes the calculations, and the testcase: int x, y; int z; int foo(void) { z = y; x = z; return x + y; } returns correct lengths (-O0): foo: pushl %ebp # 35 *pushsi2 [length = 1] movl %esp, %ebp # 36 *movsi_1/1 [length = 2] movl y, %eax # 8 *movsi_1/1 [length = 5] movl %eax, z # 9 *movsi_1/2 [length = 5] movl z, %eax # 11 *movsi_1/1 [length = 5] movl %eax, x # 12 *movsi_1/2 [length = 5] movl x, %edx # 14 *movsi_1/1 [length = 6] movl y, %eax # 15 *movsi_1/1 [length = 5] leal (%edx,%eax), %eax # 34 *lea_1 [length = 3] popl %ebp # 39 popsi1 [length = 1] ret # 40 return_internal [length = 1] these can be verified by objdump: 00000000 <foo>: 0: 55 push %ebp 1: 89 e5 mov %esp,%ebp 3: a1 00 00 00 00 mov 0x0,%eax 8: a3 00 00 00 00 mov %eax,0x0 d: a1 00 00 00 00 mov 0x0,%eax 12: a3 00 00 00 00 mov %eax,0x0 17: 8b 15 00 00 00 00 mov 0x0,%edx 1d: a1 00 00 00 00 mov 0x0,%eax 22: 8d 04 02 lea (%edx,%eax,1),%eax 25: 5d pop %ebp 26: c3 ret The patch was regtested on i686-pc-linux-gnu. 2005-11-05 Uros Bizjak <uros@kss-loka.si> * config/i386/predicates.md (ax_reg_operand): New predicate. (memory_displacement_only_operand): New predicate. * config/i386/i386.md ("modrm" attribute): Return 0 if one operand is AX register and the other operand is memory operand with displacement only. OK for mainline? BTW: The calculation of "modrm" attribute does not consider other special cases involving AX register. For example, adding immediate to ax is calculated as: addl $132, %eax # 17 *addsi_1/1 [length = 6] where in fact, the correct length is 5: 18: 05 84 00 00 00 add $0x84,%eax This can be checked in Intel's documnetation, where addition (and other operations) of immediate to AX reg is special-cased with opcode 04 and 05, without additional modrm bytes. I plan to fix these by adding a check to "modrm" attribute for operations with immediate and AX reg in following patch(es). Uros.
Attachment:
modrm.diff
Description: Binary data
Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
---|---|---|
Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |