This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH] Fix regimplification of OMP_ATOMIC_LOAD (PR middle-end/35611)
- From: Jakub Jelinek <jakub at redhat dot com>
- To: gcc-patches at gcc dot gnu dot org
- Date: Tue, 18 Mar 2008 08:19:16 -0400
- Subject: [PATCH] Fix regimplification of OMP_ATOMIC_LOAD (PR middle-end/35611)
- Reply-to: Jakub Jelinek <jakub at redhat dot com>
Hi!
gimplify_expr didn't do anything with OMP_ATOMIC_LOADs, which means that
since PR middle-end/35185 if OMP_ATOMIC_LOAD address was an address of a
variable with DECL_HAS_VALUE_EXPR_P, that address wasn't regimplified.
While when using __sync_* builtins this wasn't a big deal, because
expand_omp_atomic_{fetch_op,pipeline} call force_gimple_operand_bsi
on all the statements, expand_omp_atomic_mutex does not.
The attached testcase triggered even on i?86/x86_64 (at least when not
using -march={nocona,core2,amdfam10,barcelona}).
Fixed thusly, regtested on x86_64-linux, trunk/4.3.
2008-03-18 Jakub Jelinek <jakub@redhat.com>
PR middle-end/35611
* gimplify.c (gimplify_expr): Gimplify second operand of
OMP_ATOMIC_LOAD.
* testsuite/libgomp.c/atomic-4.c: New test.
--- gcc/gimplify.c.jj 2008-03-06 18:45:59.000000000 +0100
+++ gcc/gimplify.c 2008-03-18 11:55:04.000000000 +0100
@@ -6022,12 +6022,18 @@ gimplify_expr (tree *expr_p, tree *pre_p
case OMP_RETURN:
case OMP_CONTINUE:
- case OMP_ATOMIC_LOAD:
- case OMP_ATOMIC_STORE:
-
+ case OMP_ATOMIC_STORE:
ret = GS_ALL_DONE;
break;
+ case OMP_ATOMIC_LOAD:
+ if (gimplify_expr (&TREE_OPERAND (*expr_p, 1), pre_p, NULL,
+ is_gimple_val, fb_rvalue) != GS_ALL_DONE)
+ ret = GS_ERROR;
+ else
+ ret = GS_ALL_DONE;
+ break;
+
case POINTER_PLUS_EXPR:
/* Convert ((type *)A)+offset into &A->field_of_type_and_offset.
The second is gimple immediate saving a need for extra statement.
--- libgomp/testsuite/libgomp.c/atomic-4.c.jj 2008-03-18 12:23:31.000000000 +0100
+++ libgomp/testsuite/libgomp.c/atomic-4.c 2008-03-18 12:21:26.000000000 +0100
@@ -0,0 +1,18 @@
+/* PR middle-end/35611 */
+/* { dg-options "-O2" } */
+
+extern void abort (void);
+
+int
+main (void)
+{
+ long double d = .0L;
+ int i;
+ #pragma omp parallel for shared (d)
+ for (i = 0; i < 1000; i++)
+ #pragma omp atomic
+ d += 1.0L;
+ if (d != 1000.0L)
+ abort ();
+ return 0;
+}
Jakub