diff options
author | Kugan Vivekanandarajah <kuganv@linaro.org> | 2015-11-22 23:07:58 +0000 |
---|---|---|
committer | Kugan Vivekanandarajah <kugan@gcc.gnu.org> | 2015-11-22 23:07:58 +0000 |
commit | c6392c416d5d794fff4f8b3d51e5f9248a5a5bf2 (patch) | |
tree | 55f2f883214379511399e4b40061339fb37d2209 /gcc | |
parent | cfba61d25c4acaa74c352c492150e197a4cafcba (diff) | |
download | gcc-c6392c416d5d794fff4f8b3d51e5f9248a5a5bf2.zip gcc-c6392c416d5d794fff4f8b3d51e5f9248a5a5bf2.tar.gz gcc-c6392c416d5d794fff4f8b3d51e5f9248a5a5bf2.tar.bz2 |
re PR target/68390 (Incorrect code due to indirect tail call of varargs function with hard float ABI)
gcc/ChangeLog:
2015-11-23 Kugan Vivekanandarajah <kuganv@linaro.org>
PR target/68390
* config/arm/arm.c (arm_function_ok_for_sibcall): Get function type
for indirect function call.
gcc/testsuite/ChangeLog:
2015-11-23 Kugan Vivekanandarajah <kuganv@linaro.org>
PR target/68390
* gcc/testsuite/gcc.c-torture/execute/pr68390.c: New test.
From-SVN: r230730
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/ChangeLog | 6 | ||||
-rw-r--r-- | gcc/config/arm/arm.c | 7 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | gcc/testsuite/gcc.c-torture/execute/pr68390.c | 27 |
4 files changed, 44 insertions, 1 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 51e0707..c584fd9 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,9 @@ +2015-11-23 Kugan Vivekanandarajah <kuganv@linaro.org> + + PR target/68390 + * config/arm/arm.c (arm_function_ok_for_sibcall): Get function type + for indirect function call. + 2015-11-22 Bilyan Borisov <bilyan.borisov@arm.com> * config/aarch64/aarch64-simd.md diff --git a/gcc/config/arm/arm.c b/gcc/config/arm/arm.c index 290b537..e0cdc20 100644 --- a/gcc/config/arm/arm.c +++ b/gcc/config/arm/arm.c @@ -6686,8 +6686,13 @@ arm_function_ok_for_sibcall (tree decl, tree exp) a VFP register but then need to transfer it to a core register. */ rtx a, b; + tree decl_or_type = decl; - a = arm_function_value (TREE_TYPE (exp), decl, false); + /* If it is an indirect function pointer, get the function type. */ + if (!decl) + decl_or_type = TREE_TYPE (TREE_TYPE (CALL_EXPR_FN (exp))); + + a = arm_function_value (TREE_TYPE (exp), decl_or_type, false); b = arm_function_value (TREE_TYPE (DECL_RESULT (cfun->decl)), cfun->decl, false); if (!rtx_equal_p (a, b)) diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 7163326..3074642 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2015-11-23 Kugan Vivekanandarajah <kuganv@linaro.org> + + PR target/68390 + * gcc/testsuite/gcc.c-torture/execute/pr68390.c: New test. + 2015-11-22 Jerry DeLisle <jvdelisle@gcc.gnu.org> * gfortran.dg/fmt_g0_1.f08: Update test. Leading zero. diff --git a/gcc/testsuite/gcc.c-torture/execute/pr68390.c b/gcc/testsuite/gcc.c-torture/execute/pr68390.c new file mode 100644 index 0000000..86f07fe --- /dev/null +++ b/gcc/testsuite/gcc.c-torture/execute/pr68390.c @@ -0,0 +1,27 @@ +/* { dg-do run } */ +/* { dg-options "-O2" } */ + +__attribute__ ((noinline)) +double direct(int x, ...) +{ + return x*x; +} + +__attribute__ ((noinline)) +double broken(double (*indirect)(int x, ...), int v) +{ + return indirect(v); +} + +int main () +{ + double d1, d2; + int i = 2; + d1 = broken (direct, i); + if (d1 != i*i) + { + __builtin_abort (); + } + return 0; +} + |