x86: Restore the frame pointer in word_mode
authorH.J. Lu <hjl.tools@gmail.com>
Mon, 13 Apr 2020 11:23:05 +0000 (04:23 -0700)
committerH.J. Lu <hjl.tools@gmail.com>
Mon, 13 Apr 2020 11:23:17 +0000 (04:23 -0700)
We must restore the frame pointer in word_mode for eh_return epilogues
since the upper 32 bits of RBP register can have any values.

Tested on Linux/x32 and Linux/x86-64.

PR target/94556
* config/i386/i386.c (ix86_expand_epilogue): Restore the frame
pointer in word_mode for eh_return epilogues.

gcc/ChangeLog
gcc/config/i386/i386.c

index 8bfc2127989bd01447523c6004b8b8ce193bd86e..b4229419bc21e8d9c50b434034a190ccd472ff7a 100644 (file)
@@ -1,3 +1,9 @@
+2020-04-13  H.J. Lu  <hongjiu.lu@intel.com>
+
+       PR target/94556
+       * config/i386/i386.c (ix86_expand_epilogue): Restore the frame
+       pointer in word_mode for eh_return epilogues.
+
 2020-04-13  Jozef Lawrynowicz  <jozef.l@mittosystems.com>
 
        * config/msp430/msp430.c (msp430_print_operand): Don't add offsets to
index ca3b7dc06c233214b8a7ef4b2942333fe5019586..5e87cd463d058240ceba9129cc3ba88d7ff92f31 100644 (file)
@@ -9052,8 +9052,13 @@ ix86_expand_epilogue (int style)
              t = plus_constant (Pmode, t, m->fs.fp_offset - UNITS_PER_WORD);
              emit_insn (gen_rtx_SET (sa, t));
 
-             t = gen_frame_mem (Pmode, hard_frame_pointer_rtx);
-             insn = emit_move_insn (hard_frame_pointer_rtx, t);
+             /* NB: eh_return epilogues must restore the frame pointer
+                in word_mode since the upper 32 bits of RBP register
+                can have any values.  */
+             t = gen_frame_mem (word_mode, hard_frame_pointer_rtx);
+             rtx frame_reg = gen_rtx_REG (word_mode,
+                                          HARD_FRAME_POINTER_REGNUM);
+             insn = emit_move_insn (frame_reg, t);
 
              /* Note that we use SA as a temporary CFA, as the return
                 address is at the proper place relative to it.  We
@@ -9068,7 +9073,7 @@ ix86_expand_epilogue (int style)
              add_reg_note (insn, REG_CFA_DEF_CFA,
                            plus_constant (Pmode, sa, UNITS_PER_WORD));
              ix86_add_queued_cfa_restore_notes (insn);
-             add_reg_note (insn, REG_CFA_RESTORE, hard_frame_pointer_rtx);
+             add_reg_note (insn, REG_CFA_RESTORE, frame_reg);
              RTX_FRAME_RELATED_P (insn) = 1;
 
              m->fs.cfa_reg = sa;