summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEric Botcazou <ebotcazou@adacore.com>2021-02-12 00:16:49 +0100
committerEric Botcazou <ebotcazou@adacore.com>2021-02-12 00:19:21 +0100
commit85cefe22564c4b7c1159a544fa692a24e0c71870 (patch)
tree819cf044158af0146dcd6170c2a01c53816386ec
parent5e40542f878127a1dd0421831c03cda1b977f2a0 (diff)
downloadgcc-85cefe22564c4b7c1159a544fa692a24e0c71870.tar.gz
Fix -freorder-blocks-and-partition glitch with Windows SEH
Since GCC 8, the -freorder-blocks-and-partition pass can split a function into hot and cold parts, thus generating 2 CIEs for a single function in DWARF for exception purposes and doing an equivalent trick for Windows SEH. Now the Windows system unwinder is picky when it comes to the boundary between an active EH region and the end of the function and, therefore, a nop may need to be added in specific cases. gcc/ * config/i386/winnt.c (i386_pe_seh_unwind_emit): When switching to the cold section, emit a nop before the directive if the previous active instruction can throw.
-rw-r--r--gcc/config/i386/winnt.c4
1 files changed, 4 insertions, 0 deletions
diff --git a/gcc/config/i386/winnt.c b/gcc/config/i386/winnt.c
index 962c88e3c1b..adc3f36f13b 100644
--- a/gcc/config/i386/winnt.c
+++ b/gcc/config/i386/winnt.c
@@ -1231,6 +1231,10 @@ i386_pe_seh_unwind_emit (FILE *asm_out_file, rtx_insn *insn)
seh = cfun->machine->seh;
if (NOTE_P (insn) && NOTE_KIND (insn) == NOTE_INSN_SWITCH_TEXT_SECTIONS)
{
+ /* See ix86_seh_fixup_eh_fallthru for the rationale. */
+ rtx_insn *prev = prev_active_insn (insn);
+ if (prev && !insn_nothrow_p (prev))
+ fputs ("\tnop\n", asm_out_file);
fputs ("\t.seh_endproc\n", asm_out_file);
seh->in_cold_section = true;
return;