[ARM] Fix cmse_nonsecure_entry return insn size
authorThomas Preud'homme <thomas.preudhomme@arm.com>
Thu, 9 Nov 2017 16:34:43 +0000 (16:34 +0000)
committerThomas Preud'homme <thopre01@gcc.gnu.org>
Thu, 9 Nov 2017 16:34:43 +0000 (16:34 +0000)
A number of instructions are output in assembler form by
output_return_instruction () when compiling a function with the
cmse_nonsecure_entry attribute for Armv8-M Mainline with hardfloat float
ABI. However, the corresponding thumb2_cmse_entry_return insn pattern
does not account for all these instructions in its computing of the
length of the instruction.

This may lead GCC to use the wrong branching instruction due to
incorrect computation of the offset between the branch instruction's
address and the target address.

This commit fixes the mismatch between what output_return_instruction ()
does and what the pattern think it does and adds a note warning about
mismatch in the affected functions' heading comments to ensure code does
not get out of sync again.

Note: no test is provided because the C testcase is fragile (only works
on GCC 6) and the extracted RTL test fails to compile due to bugs in the
RTL frontend (PR82815 and PR82817)

2017-11-09  Thomas Preud'homme  <thomas.preudhomme@arm.com>

    gcc/
    * config/arm/arm.c (output_return_instruction): Add comments to
    indicate requirement for cmse_nonsecure_entry return to account
    for the size of clearing instruction output here.
    (thumb_exit): Likewise.
    * config/arm/thumb2.md (thumb2_cmse_entry_return): Fix length for
    return in hardfloat mode.

From-SVN: r254601

gcc/ChangeLog
gcc/config/arm/arm.c
gcc/config/arm/thumb2.md

index b223f61b0d7bbf08f74927a503013ee222ddf120..67d925c0014b7f16eb1b36268927ef9a112c8c1a 100644 (file)
@@ -1,3 +1,12 @@
+2017-11-09  Thomas Preud'homme  <thomas.preudhomme@arm.com>
+
+       * config/arm/arm.c (output_return_instruction): Add comments to
+       indicate requirement for cmse_nonsecure_entry return to account
+       for the size of clearing instruction output here.
+       (thumb_exit): Likewise.
+       * config/arm/thumb2.md (thumb2_cmse_entry_return): Fix length for
+       return in hardfloat mode.
+
 2017-11-09  Segher Boessenkool  <segher@kernel.crashing.org>
 
        * config/rs6000/rs6000.c (machine_function): Add a bool,
index c2a3e9ccbbfa46c31712cd6d0312a515ac127561..f1ac70ff0895b79df6f14811fc9095b73ff8ee26 100644 (file)
@@ -19417,7 +19417,12 @@ arm_get_vfp_saved_size (void)
 
 /* Generate a function exit sequence.  If REALLY_RETURN is false, then do
    everything bar the final return instruction.  If simple_return is true,
-   then do not output epilogue, because it has already been emitted in RTL.  */
+   then do not output epilogue, because it has already been emitted in RTL.
+
+   Note: do not forget to update length attribute of corresponding insn pattern
+   when changing assembly output (eg. length attribute of
+   thumb2_cmse_entry_return when updating Armv8-M Mainline Security Extensions
+   register clearing sequences).  */
 const char *
 output_return_instruction (rtx operand, bool really_return, bool reverse,
                            bool simple_return)
@@ -23950,7 +23955,12 @@ thumb_pop (FILE *f, unsigned long mask)
 
 /* Generate code to return from a thumb function.
    If 'reg_containing_return_addr' is -1, then the return address is
-   actually on the stack, at the stack pointer.  */
+   actually on the stack, at the stack pointer.
+
+   Note: do not forget to update length attribute of corresponding insn pattern
+   when changing assembly output (eg. length attribute of epilogue_insns when
+   updating Armv8-M Baseline Security Extensions register clearing
+   sequences).  */
 static void
 thumb_exit (FILE *f, int reg_containing_return_addr)
 {
index c2dcc8fddc00707673870f50474f41dd5bcbcfd4..abe90d4f4e4509f643a2cfcd6e0d225b3b4186a9 100644 (file)
    ; we adapt the length accordingly.
    (set (attr "length")
      (if_then_else (match_test "TARGET_HARD_FLOAT")
-      (const_int 12)
+      (const_int 34)
       (const_int 8)))
    ; We do not support predicate execution of returns from cmse_nonsecure_entry
    ; functions because we need to clear the APSR.  Since predicable has to be