From fbc4c20a80a81ef6bc624a219ef5f2c746efe563 Mon Sep 17 00:00:00 2001 From: Andrew Stubbs Date: Thu, 22 Oct 2009 19:35:53 +0000 Subject: [PATCH] Fix register conflicts and avoid deprecated instructions in ARM EABI setjmp/longjmp. * setjmp and longjmp were using the obsolete fstmiax and fldmiax instructions. * Because of a confusion with two different sets of names for the same registers (r0...r3 and a1...a4), if VFP was present then the subsequent check for iWMMXt support would use a register that had been clobbered by saving/restoring the VFP registers. (The bit being checked was clobbered by a reserved bit of FPSCR that it always 0 on present hardware, and no present hardware has both VFP and iWMMXt, so this did not cause visible problems.) 2009-10-22 Andrew Stubbs Julian Brown * sysdeps/arm/eabi/setjmp.S (__sigsetjmp): Replace deprecated instruction fstmiax with vstmia. Correct register conflict and comment. * sysdeps/arm/eabi/__longjmp.S (__longjmp): Use vldmia not fldmiax. Don't clobber r1/a2 register before testing IWMMXT hwcap. --- ChangeLog.arm | 9 +++++++++ sysdeps/arm/eabi/__longjmp.S | 10 +++++----- sysdeps/arm/eabi/setjmp.S | 14 ++++++++------ 3 files changed, 22 insertions(+), 11 deletions(-) diff --git a/ChangeLog.arm b/ChangeLog.arm index 643a071c4e..f098f3c9a6 100644 --- a/ChangeLog.arm +++ b/ChangeLog.arm @@ -1,3 +1,12 @@ +2009-10-22 Andrew Stubbs + Julian Brown + + * sysdeps/arm/eabi/setjmp.S (__sigsetjmp): Replace deprecated + instruction fstmiax with vstmia. + Correct register conflict and comment. + * sysdeps/arm/eabi/__longjmp.S (__longjmp): Use vldmia not fldmiax. + Don't clobber r1/a2 register before testing IWMMXT hwcap. + 2009-10-22 Julian Brown * sysdeps/arm/elf/start.S (_start): Avoid dependency on PC pipeline diff --git a/sysdeps/arm/eabi/__longjmp.S b/sysdeps/arm/eabi/__longjmp.S index f283297089..305919393d 100644 --- a/sysdeps/arm/eabi/__longjmp.S +++ b/sysdeps/arm/eabi/__longjmp.S @@ -59,12 +59,12 @@ ENTRY (__longjmp) beq Lno_vfp /* Restore the VFP registers. */ - /* Following instruction is fldmiax ip!, {d8-d15}. */ - ldc p11, cr8, [r12], #68 + /* Following instruction is vldmia ip!, {d8-d15}. */ + ldc p11, cr8, [r12], #64 /* Restore the floating-point status register. */ - ldr r1, [ip], #4 - /* Following instruction is fmxr fpscr, r1. */ - mcr p10, 7, r1, cr1, cr0, 0 + ldr a3, [ip], #4 + /* Following instruction is fmxr fpscr, a3. */ + mcr p10, 7, a3, cr1, cr0, 0 Lno_vfp: tst a2, #HWCAP_ARM_IWMMXT diff --git a/sysdeps/arm/eabi/setjmp.S b/sysdeps/arm/eabi/setjmp.S index 835db714a6..92f83af3f8 100644 --- a/sysdeps/arm/eabi/setjmp.S +++ b/sysdeps/arm/eabi/setjmp.S @@ -52,13 +52,15 @@ ENTRY (__sigsetjmp) tst a3, #HWCAP_ARM_VFP beq Lno_vfp - /* Store the VFP registers. */ - /* Following instruction is fstmiax ip!, {d8-d15}. */ - stc p11, cr8, [r12], #68 + /* Store the VFP registers. + Don't use VFP instructions directly because this code + is used in non-VFP multilibs. */ + /* Following instruction is vstmia ip!, {d8-d15}. */ + stc p11, cr8, [ip], #64 /* Store the floating-point status register. */ - /* Following instruction is fmrx r2, fpscr. */ - mrc p10, 7, r2, cr1, cr0, 0 - str r2, [ip], #4 + /* Following instruction is vmrs a4, fpscr. */ + mrc p10, 7, a4, cr1, cr0, 0 + str a4, [ip], #4 Lno_vfp: tst a3, #HWCAP_ARM_IWMMXT