https://bugs.kde.org/show_bug.cgi?id=384442
--- Comment #3 from John Reiser <jrei...@bitwagon.com> --- Here is the output from "--trace-flags=10000000", condensed and commented: ===== (arm) 0x49BD90C: mov r12, r13 (arm) 0x49BD910: stmdb r13!, {0xDFF0} (arm) 0x49BD914: sub r11, r12, #0x4 (arm) 0x49BD918: ldmdb r11, {0xAFF0} ------ IMark(0x49BD918, 4, 0) ------ t8 = GET:I32(52 /*r11*/) t9 = t8 PUT(68 /*r15,pc*/) = LDle:I32(Sub32(t9,0x4:I32)) // updated pc no longer points to the 'ldmdb' PUT(60 /*r13,sp*/) = LDle:I32(Sub32(t9,0x8:I32)) // updated sp PUT(48 /*r10*/) = LDle:I32(Sub32(t9,0x10:I32)) // fetch from wrong side of *updated* sp PUT(44 /*r9*/) = LDle:I32(Sub32(t9,0x14:I32)) PUT(40 /*r8*/) = LDle:I32(Sub32(t9,0x18:I32)) PUT(36 /*r7*/) = LDle:I32(Sub32(t9,0x1C:I32)) PUT(32 /*r6*/) = LDle:I32(Sub32(t9,0x20:I32)) PUT(28 /*r5*/) = LDle:I32(Sub32(t9,0x24:I32)) PUT(24 /*r4*/) = LDle:I32(Sub32(t9,0x28:I32)) PUT(52 /*r11*/) = LDle:I32(Sub32(t9,0xC:I32)) PUT(68 /*r15,pc*/) = GET:I32(68) PUT(68 /*r15,pc*/) = GET:I32(68); exit-Boring GuestBytes 49BD90C 16 0D C0 A0 E1 F0 DF 2D E9 04 B0 4C E2 F0 AF 1B E9 0028F343 VexExpansionRatio 16 952 595 :10 ==26904== Invalid read of size 4 ==26904== at 0x40054EC: ??? (in /lib/ld-uClibc-0.9.33.2.so) ## pc should be 0x49BD918 ==26904== Address 0x7dad0654 is on thread 1's stack ==26904== 20 bytes below stack pointer ## below updated sp, but above original sp; should be no complaint ==26904== ===== (Of course the original [user] compiler code generator could do much better.) The VEX code in mk_ldm_stm() claims ===== priv/guest_arm_toIR.c near line 14138 if (bW == 0 && (regList & (1<<rN)) != 0) { /* Non-writeback, and basereg is to be transferred. Do its transfer last for a load and first for a store. Requires reordering xOff/xReg. */ ===== but I don't understand why. The earlier t8 = GET:I32(52 /*r11*/) t9 = t8 has de-coupled the original value of the base register from any interaction with subsequent code that deals with the register list. The real problem is that the new values of r15(==pc) and r13(==sp) have been written while the original values still are needed to detect fetching from the wrong side of sp (via LDle:I32() for each remaining register), and for reporting the pc of any complaint. It is the writing of pc and sp that should be re-ordered; and if both sp and pc are written then the generated code will require another temporary variable to hold the new value of pc until after there is no possibility of a complaint about this instruction. -- You are receiving this mail because: You are watching all bug changes.