aboutsummaryrefslogtreecommitdiff
path: root/gdb/amd64-tdep.c
diff options
context:
space:
mode:
Diffstat (limited to 'gdb/amd64-tdep.c')
-rw-r--r--gdb/amd64-tdep.c61
1 files changed, 36 insertions, 25 deletions
diff --git a/gdb/amd64-tdep.c b/gdb/amd64-tdep.c
index 14be776..8f686d1 100644
--- a/gdb/amd64-tdep.c
+++ b/gdb/amd64-tdep.c
@@ -1910,43 +1910,37 @@ amd64_analyze_prologue (struct gdbarch *gdbarch,
return pc;
}
-/* Return PC of first real instruction. */
+/* Work around false termination of prologue - GCC PR debug/48827.
+
+ START_PC is the first instruction of a function, PC is its minimal already
+ determined advanced address. Function returns PC if it has nothing to do.
+
+ 84 c0 test %al,%al
+ 74 23 je after
+ <-- here is 0 lines advance - the false prologue end marker.
+ 0f 29 85 70 ff ff ff movaps %xmm0,-0x90(%rbp)
+ 0f 29 4d 80 movaps %xmm1,-0x80(%rbp)
+ 0f 29 55 90 movaps %xmm2,-0x70(%rbp)
+ 0f 29 5d a0 movaps %xmm3,-0x60(%rbp)
+ 0f 29 65 b0 movaps %xmm4,-0x50(%rbp)
+ 0f 29 6d c0 movaps %xmm5,-0x40(%rbp)
+ 0f 29 75 d0 movaps %xmm6,-0x30(%rbp)
+ 0f 29 7d e0 movaps %xmm7,-0x20(%rbp)
+ after: */
static CORE_ADDR
-amd64_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR start_pc)
+amd64_skip_xmm_prologue (CORE_ADDR pc, CORE_ADDR start_pc)
{
- struct amd64_frame_cache cache;
- CORE_ADDR pc;
struct symtab_and_line start_pc_sal, next_sal;
gdb_byte buf[4 + 8 * 7];
int offset, xmmreg;
- amd64_init_frame_cache (&cache);
- pc = amd64_analyze_prologue (gdbarch, start_pc, 0xffffffffffffffffLL,
- &cache);
- if (cache.frameless_p)
- return start_pc;
-
- /* GCC PR debug/48827 produced false prologue end:
- 84 c0 test %al,%al
- 74 23 je after
- <-- here is 0 lines advance - the false prologue end marker.
- 0f 29 85 70 ff ff ff movaps %xmm0,-0x90(%rbp)
- 0f 29 4d 80 movaps %xmm1,-0x80(%rbp)
- 0f 29 55 90 movaps %xmm2,-0x70(%rbp)
- 0f 29 5d a0 movaps %xmm3,-0x60(%rbp)
- 0f 29 65 b0 movaps %xmm4,-0x50(%rbp)
- 0f 29 6d c0 movaps %xmm5,-0x40(%rbp)
- 0f 29 75 d0 movaps %xmm6,-0x30(%rbp)
- 0f 29 7d e0 movaps %xmm7,-0x20(%rbp)
- after: */
-
if (pc == start_pc)
return pc;
start_pc_sal = find_pc_sect_line (start_pc, NULL, 0);
if (start_pc_sal.symtab == NULL
- || !start_pc_sal.symtab->amd64_prologue_line_bug
+ || producer_is_gcc_ge_4 (start_pc_sal.symtab->producer) < 6
|| start_pc_sal.pc != start_pc || pc >= start_pc_sal.end)
return pc;
@@ -1993,6 +1987,23 @@ amd64_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR start_pc)
return next_sal.end;
}
+
+/* Return PC of first real instruction. */
+
+static CORE_ADDR
+amd64_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR start_pc)
+{
+ struct amd64_frame_cache cache;
+ CORE_ADDR pc;
+
+ amd64_init_frame_cache (&cache);
+ pc = amd64_analyze_prologue (gdbarch, start_pc, 0xffffffffffffffffLL,
+ &cache);
+ if (cache.frameless_p)
+ return start_pc;
+
+ return amd64_skip_xmm_prologue (pc, start_pc);
+}
/* Normal frames. */