re PR middle-end/37908 (atomic NAND op generate wrong code; __sync_nand_and_fetch...
authorUros Bizjak <uros@gcc.gnu.org>
Mon, 17 Nov 2008 11:19:06 +0000 (12:19 +0100)
committerUros Bizjak <uros@gcc.gnu.org>
Mon, 17 Nov 2008 11:19:06 +0000 (12:19 +0100)
PR middle-end/37908
* optabs.c (expand_sync_operation): Properly handle NAND case
by calculating ~(t1 & val) instead of (~t1 & val).
* builtins.c (expand_builtin_sync_operation): Warn for changed
semantics in NAND builtins.
* c.opt (Wsync-nand): New warning option.  Describe -Wsync-nand.

* doc/invoke.texi (Warning options): Add Wsync-nand.
* doc/extend.texi (Atomic Builtins) [__sync_fetch_and_nand]: Correct
__sync_fetch_and_nand builtin operation in the example.  Add a note
about changed semantics in GCC 4.4.
[__sync_nand_and_fetch]: Correct __sync_nand_and_fetch builtin
operation in the example.  Add a note about changed semantics in
GCC 4.4.

testsuite/ChangeLog:

PR middle-end/37908
* gcc.dg/pr37908.c: New test.
* gcc.dg/ia64-sync-1.c: Correct __sync_fetch_and_nand and
__sync_nand_and_fetch results.  Add dg-message to look for the warning
about changed semantics of NAND builtin.
(init_si, init_di): Change init value for __sync_fetch_and_nand to -1.
(test_si, test_di): Change expected result of
__sync_nand_and_fetch to ~7.
* gcc.dg/ia64-sync-2.c: Correct __sync_fetch_and_nand and
__sync_nand_and_fetch results.  Add dg-message to look for the warning
about changed semantics of NAND builtin.
(init_noret_si, init_noret_di): Change init value for
__sync_fetch_and_nand to -1.
(init_noret_si, init_noret_di): Change expected result of
__sync_nand_and_fetch to ~7.
* gcc.dg/sync-2.c: Correct __sync_fetch_and_nand and
__sync_nand_and_fetch results.  Add dg-message to look for the warning
about changed semantics of NAND builtin.
(init_qi, init_qi): Change init value for __sync_fetch_and_nand to -1.
(init_hi, init_hi): Change expected result of
__sync_nand_and_fetch to ~7.
* gcc.dg/sync-3.c: Copy from sync-2.c instead of including
the c source file.
* gcc.c-torture/compile/sync-1.c: Add dg-message to look for the
warning about changed semantics of NAND builtin.
* gcc.c-torture/compile/sync-2.c: Ditto.
* gcc.c-torture/compile/sync-3.c: Ditto.

From-SVN: r141942

15 files changed:
gcc/ChangeLog
gcc/builtins.c
gcc/c.opt
gcc/doc/extend.texi
gcc/doc/invoke.texi
gcc/optabs.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.c-torture/compile/sync-1.c
gcc/testsuite/gcc.c-torture/compile/sync-2.c
gcc/testsuite/gcc.c-torture/compile/sync-3.c
gcc/testsuite/gcc.dg/ia64-sync-1.c
gcc/testsuite/gcc.dg/ia64-sync-2.c
gcc/testsuite/gcc.dg/pr37908.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/sync-2.c
gcc/testsuite/gcc.dg/sync-3.c

index 1c8085e0ba45dd0c7f4c5d1c9cec2b193820713e..a916993a7997f101b52f17d7f46c6f78e8c87b4b 100644 (file)
@@ -1,3 +1,20 @@
+2008-11-17  Uros Bizjak  <ubizjak@gmail.com>
+
+       PR middle-end/37908
+       * optabs.c (expand_sync_operation): Properly handle NAND case
+       by calculating ~(t1 & val) instead of (~t1 & val).
+       * builtins.c (expand_builtin_sync_operation): Warn for changed
+       semantics in NAND builtins.
+       * c.opt (Wsync-nand): New warning option.  Describe -Wsync-nand.
+       
+       * doc/invoke.texi (Warning options): Add Wsync-nand.
+       * doc/extend.texi (Atomic Builtins) [__sync_fetch_and_nand]: Correct
+       __sync_fetch_and_nand builtin operation in the example.  Add a note
+       about changed semantics in GCC 4.4.
+       [__sync_nand_and_fetch]: Correct __sync_nand_and_fetch builtin
+       operation in the example.  Add a note about changed semantics in
+       GCC 4.4.
+
 2008-11-16  Jan Hubicka  <jh@suse.cz>
 
        * cgraph.c (cgraph_function_body_availability): Fix test of externally
 
        * configure.ac (gcc_cv_libc_provides_ssp): Also consider GNU/Hurd
        systems, which are assumend to always provide SSP-support in glibc.
-       * configure: Regenerate.
-
-       * configure.ac (gcc_cv_libc_provides_ssp): Also consider GNU/kFreeBSD,
-       GNU/kNetBSD systems in the `*-*-linux*' case.
+       Also consider GNU/kFreeBSD, GNU/kNetBSD systems in the `*-*-linux*'
+       case.
        * configure: Regenerate.
 
 2008-11-14  Jakub Jelinek  <jakub@redhat.com>
 2008-11-13  Thomas Schwinge  <tschwinge@gnu.org>
 
        PR target/28102
-       * config.gcc (*-*-gnu*): Move Alpha parts into the `alpha*-*-gnu*', x86
-       parts into the `i[34567]86-*-linux*' and parts that are independent of
-       the processor architecture into the `*-*-linux*' cases.
+       * config.gcc (*-*-gnu*): Move Alpha parts into the `alpha*-*-gnu*',
+       x86 parts into the `i[34567]86-*-linux*' and parts that are
+       independent of the processor architecture into the `*-*-linux*' cases.
        (*-*-linux*): Consider `linux.opt' only for Linux-based configurations.
        * config/i386/gnu.h (GLIBC_DYNAMIC_LINKER): Redefine.
        (TARGET_OS_CPP_BUILTINS, LINK_SPEC): Don't redefine.
 2008-11-11  Richard Sandiford  <rdsandiford@googlemail.com>
 
        PR rtl-optimization/37363
-       * simplify-rtx.c (simplify_plus_minus): Don't create (const (minus ...))
-       expresisons.
+       * simplify-rtx.c (simplify_plus_minus): Don't create
+       (const (minus ...)) expresisons.
 
 2008-11-11  Eric Botcazou  <ebotcazou@adacore.com>
 
index a1bba0d716081d232b6028303aa397fcc918b065..fd6d0b859e00a85f05cd04b51b3d6e56a196816a 100644 (file)
@@ -5988,6 +5988,50 @@ expand_builtin_sync_operation (enum machine_mode mode, tree exp,
   rtx val, mem;
   enum machine_mode old_mode;
 
+  if (code == NOT && warn_sync_nand)
+    {
+      tree fndecl = get_callee_fndecl (exp);
+      enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
+
+      static bool warned_f_a_n, warned_n_a_f;
+
+      switch (fcode)
+       {
+       case BUILT_IN_FETCH_AND_NAND_1:
+       case BUILT_IN_FETCH_AND_NAND_2:
+       case BUILT_IN_FETCH_AND_NAND_4:
+       case BUILT_IN_FETCH_AND_NAND_8:
+       case BUILT_IN_FETCH_AND_NAND_16:
+
+         if (warned_f_a_n)
+           break;
+
+         fndecl = implicit_built_in_decls[BUILT_IN_FETCH_AND_NAND_N];
+         inform (input_location,
+                 "%qD changed semantics in GCC 4.4", fndecl);
+         warned_f_a_n = true;
+         break;
+
+       case BUILT_IN_NAND_AND_FETCH_1:
+       case BUILT_IN_NAND_AND_FETCH_2:
+       case BUILT_IN_NAND_AND_FETCH_4:
+       case BUILT_IN_NAND_AND_FETCH_8:
+       case BUILT_IN_NAND_AND_FETCH_16:
+
+         if (warned_n_a_f)
+           break;
+
+         fndecl = implicit_built_in_decls[BUILT_IN_NAND_AND_FETCH_N];
+         inform (input_location,
+                 "%qD changed semantics in GCC 4.4", fndecl);
+         warned_n_a_f = true;
+         break;
+
+       default:
+         gcc_unreachable ();
+       }
+    }
+
   /* Expand the operands.  */
   mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
 
index 94d6047a5a399082f10d50f0673aa58850175f46..1888ecde63c5cd2cfdde3a46cfacce275d6016c5 100644 (file)
--- a/gcc/c.opt
+++ b/gcc/c.opt
@@ -428,6 +428,10 @@ Wstrict-selector-match
 ObjC ObjC++ Var(warn_strict_selector_match) Warning
 Warn if type signatures of candidate methods do not match exactly
 
+Wsync-nand
+C C++ Var(warn_sync_nand) Init(1) Warning
+Warn when __sync_fetch_and_nand and __sync_nand_and_fetch built-in functions are used
+
 Wsynth
 C++ ObjC++ Var(warn_synth) Warning
 Deprecated.  This switch has no effect
index e03eaf9faad81a4cc6fa1faf76382d41900c703c..43e91afe8b42587c438bf476351c0ab96fb28706 100644 (file)
@@ -5774,9 +5774,12 @@ returns the value that had previously been in memory.  That is,
 
 @smallexample
 @{ tmp = *ptr; *ptr @var{op}= value; return tmp; @}
-@{ tmp = *ptr; *ptr = ~tmp & value; return tmp; @}   // nand
+@{ tmp = *ptr; *ptr = ~(tmp & value); return tmp; @}   // nand
 @end smallexample
 
+@emph{Note:} GCC 4.4 and later implement @code{__sync_fetch_and_nand}
+builtin as @code{*ptr = ~(tmp & value)} instead of @code{*ptr = ~tmp & value}.
+
 @item @var{type} __sync_add_and_fetch (@var{type} *ptr, @var{type} value, ...)
 @itemx @var{type} __sync_sub_and_fetch (@var{type} *ptr, @var{type} value, ...)
 @itemx @var{type} __sync_or_and_fetch (@var{type} *ptr, @var{type} value, ...)
@@ -5794,9 +5797,13 @@ return the new value.  That is,
 
 @smallexample
 @{ *ptr @var{op}= value; return *ptr; @}
-@{ *ptr = ~*ptr & value; return *ptr; @}   // nand
+@{ *ptr = ~(*ptr & value); return *ptr; @}   // nand
 @end smallexample
 
+@emph{Note:} GCC 4.4 and later implement @code{__sync_nand_and_fetch}
+builtin as @code{*ptr = ~(*ptr & value)} instead of
+@code{*ptr = ~*ptr & value}.
+
 @item bool __sync_bool_compare_and_swap (@var{type} *ptr, @var{type} oldval @var{type} newval, ...)
 @itemx @var{type} __sync_val_compare_and_swap (@var{type} *ptr, @var{type} oldval @var{type} newval, ...)
 @findex __sync_bool_compare_and_swap
index cc66b45c14bed7097637ba0db2add2cb62e18b34..476ab8cf92a39690d047997520096d31eeeb5635 100644 (file)
@@ -257,7 +257,7 @@ Objective-C and Objective-C++ Dialects}.
 -Wsign-compare  -Wsign-conversion  -Wstack-protector @gol
 -Wstrict-aliasing -Wstrict-aliasing=n @gol
 -Wstrict-overflow -Wstrict-overflow=@var{n} @gol
--Wswitch  -Wswitch-default  -Wswitch-enum @gol
+-Wswitch  -Wswitch-default  -Wswitch-enum -Wsync-nand @gol
 -Wsystem-headers  -Wtrigraphs  -Wtype-limits  -Wundef  -Wuninitialized @gol
 -Wunknown-pragmas  -Wno-pragmas -Wunreachable-code @gol
 -Wunused  -Wunused-function  -Wunused-label  -Wunused-parameter @gol
@@ -3127,6 +3127,12 @@ and lacks a @code{case} for one or more of the named codes of that
 enumeration.  @code{case} labels outside the enumeration range also
 provoke warnings when this option is used.
 
+@item -Wsync-nand
+@opindex Wsync-nand
+@opindex Wno-sync-nand
+Warn when @code{__sync_fetch_and_nand} and @code{__sync_nand_and_fetch}
+built-in functions are used.  These functions changed semantics in GCC 4.4.
+
 @item -Wtrigraphs
 @opindex Wtrigraphs
 @opindex Wno-trigraphs
index 127310390919babb6fb4a49368a1107d50a81633..ed59f5e1e7f17560c392d366df8209c6a4f88c22 100644 (file)
@@ -7182,12 +7182,13 @@ expand_sync_operation (rtx mem, rtx val, enum rtx_code code)
       t1 = t0;
       if (code == NOT)
        {
-         t1 = expand_simple_unop (mode, NOT, t1, NULL_RTX, true);
-         code = AND;
+         t1 = expand_simple_binop (mode, AND, t1, val, NULL_RTX,
+                                   true, OPTAB_LIB_WIDEN);
+         t1 = expand_simple_unop (mode, code, t1, NULL_RTX, true);
        }
-      t1 = expand_simple_binop (mode, code, t1, val, NULL_RTX,
-                               true, OPTAB_LIB_WIDEN);
-
+      else
+       t1 = expand_simple_binop (mode, code, t1, val, NULL_RTX,
+                                 true, OPTAB_LIB_WIDEN);
       insn = get_insns ();
       end_sequence ();
 
@@ -7315,9 +7316,17 @@ expand_sync_fetch_operation (rtx mem, rtx val, enum rtx_code code,
                }
 
              if (code == NOT)
-               target = expand_simple_unop (mode, NOT, target, NULL_RTX, true);
-             target = expand_simple_binop (mode, code, target, val, NULL_RTX,
-                                           true, OPTAB_LIB_WIDEN);
+               {
+                 target = expand_simple_binop (mode, AND, target, val,
+                                               NULL_RTX, true,
+                                               OPTAB_LIB_WIDEN);
+                 target = expand_simple_unop (mode, code, target,
+                                              NULL_RTX, true);
+               }
+             else
+               target = expand_simple_binop (mode, code, target, val,
+                                             NULL_RTX, true,
+                                             OPTAB_LIB_WIDEN);
            }
 
          return target;
@@ -7340,11 +7349,13 @@ expand_sync_fetch_operation (rtx mem, rtx val, enum rtx_code code,
       t1 = t0;
       if (code == NOT)
        {
-         t1 = expand_simple_unop (mode, NOT, t1, NULL_RTX, true);
-         code = AND;
+         t1 = expand_simple_binop (mode, AND, t1, val, NULL_RTX,
+                                   true, OPTAB_LIB_WIDEN);
+         t1 = expand_simple_unop (mode, code, t1, NULL_RTX, true);
        }
-      t1 = expand_simple_binop (mode, code, t1, val, NULL_RTX,
-                               true, OPTAB_LIB_WIDEN);
+      else
+       t1 = expand_simple_binop (mode, code, t1, val, NULL_RTX,
+                                 true, OPTAB_LIB_WIDEN);
       if (after)
        emit_move_insn (target, t1);
 
index 4520da370211daa186b59ea13d691481271368f1..16c4e05e23fed054e8e2d009e4fb33d4a49f401d 100644 (file)
@@ -1,3 +1,33 @@
+2008-11-17  Uros Bizjak  <ubizjak@gmail.com>
+
+       PR middle-end/37908
+       * gcc.dg/pr37908.c: New test.
+       * gcc.dg/ia64-sync-1.c: Correct __sync_fetch_and_nand and
+       __sync_nand_and_fetch results.  Add dg-message to look for the warning
+       about changed semantics of NAND builtin.
+       (init_si, init_di): Change init value for __sync_fetch_and_nand to -1.
+       (test_si, test_di): Change expected result of
+       __sync_nand_and_fetch to ~7.
+       * gcc.dg/ia64-sync-2.c: Correct __sync_fetch_and_nand and
+       __sync_nand_and_fetch results.  Add dg-message to look for the warning
+       about changed semantics of NAND builtin.
+       (init_noret_si, init_noret_di): Change init value for
+       __sync_fetch_and_nand to -1.
+       (init_noret_si, init_noret_di): Change expected result of
+       __sync_nand_and_fetch to ~7.
+       * gcc.dg/sync-2.c: Correct __sync_fetch_and_nand and
+       __sync_nand_and_fetch results.  Add dg-message to look for the warning
+       about changed semantics of NAND builtin.
+       (init_qi, init_qi): Change init value for __sync_fetch_and_nand to -1.
+       (init_hi, init_hi): Change expected result of
+       __sync_nand_and_fetch to ~7.
+       * gcc.dg/sync-3.c: Copy from sync-2.c instead of including
+       the c source file.
+       * gcc.c-torture/compile/sync-1.c: Add dg-message to look for the
+       warning about changed semantics of NAND builtin.
+       * gcc.c-torture/compile/sync-2.c: Ditto.
+       * gcc.c-torture/compile/sync-3.c: Ditto.
+
 2008-11-17  Jakub Jelinek  <jakub@redhat.com>
 
        PR c++/36089
index 1703aaf267f214814685f43922f0b57180e59f56..0354923d2dd15ba8d1592d047a841b9fa96c72e5 100644 (file)
@@ -1,3 +1,6 @@
+/* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+/* { dg-message "note: '__sync_nand_and_fetch' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+
 /* Validate that each of the __sync builtins compiles.  This won't 
    necessarily link, since the target might not support the builtin,
    so this may result in external library calls.  */
index 299aa09741d5e4d7532404d4cae4d6294058c905..bdc84ef0ae6a4ecf5f4fd55f217188bb1511a5a5 100644 (file)
@@ -1,3 +1,5 @@
+/* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+
 /* Validate that each of the __sync builtins compiles.  This won't 
    necessarily link, since the target might not support the builtin,
    so this may result in external library calls.  */
index a31c9260d96f089c7382c8c4f9864ffe18be961f..9689eea5bb05385e6a9d271b9680c94a8e658a7b 100644 (file)
@@ -1,3 +1,5 @@
+/* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+
 /* Validate that each of the __sync builtins compiles.  This won't 
    necessarily link, since the target might not support the builtin,
    so this may result in external library calls.  */
index efca5d7a0495683f77ee427d6b178f5ad6f56d40..83c995a624f94b02e869f4d7ac653f932d072e32 100644 (file)
@@ -4,6 +4,8 @@
 /* { dg-options "-march=i486" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-mcpu=v9" { target sparc*-*-* } } */
 
+/* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+
 /* Test basic functionality of the intrinsics.  The operations should
    not be optimized away if no one checks the return values.  */
 
@@ -13,8 +15,8 @@ extern void abort (void);
 extern void *memcpy (void *, const void *, size_t);
 
 static int AI[12];
-static int init_noret_si[12] = { 0, 0, 0, 1, 0, 0, 0, 0, -1, 0, 0, 0 };
-static int test_noret_si[12] = { 1, 1, 1, 0, 1, 4, 22, -12, 7, 8, 9, 7 };
+static int init_noret_si[12] = { 0, 0, 0, 1, 0, 0, 0 , 0  , -1, 0, 0, -1 };
+static int test_noret_si[12] = { 1, 1, 1, 0, 1, 4, 22, -12, 7 , 8, 9, ~7 };
 
 static void
 do_noret_si (void)
@@ -35,8 +37,8 @@ do_noret_si (void)
 }
 
 static long AL[12];
-static long init_noret_di[12] = { 0, 0, 0, 1, 0, 0, 0, 0, -1, 0, 0, 0 };
-static long test_noret_di[12] = { 1, 1, 1, 0, 1, 4, 22, -12, 7, 8, 9, 7 };
+static long init_noret_di[12] = { 0, 0, 0, 1, 0, 0, 0 , 0  , -1, 0, 0, -1 };
+static long test_noret_di[12] = { 1, 1, 1, 0, 1, 4, 22, -12, 7 , 8, 9, ~7 };
 
 static void
 do_noret_di (void)
index b3ff127d9a3d8e4302d5f7c2ba108a1c85af78b2..69fb9b7c26e808f5c5538a56b7844f637c1f9330 100644 (file)
@@ -4,6 +4,9 @@
 /* { dg-options "-march=i486" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-mcpu=v9" { target sparc*-*-* } } */
 
+/* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+/* { dg-message "note: '__sync_nand_and_fetch' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+
 /* Test basic functionality of the intrinsics.  */
 
 __extension__ typedef __SIZE_TYPE__ size_t;
@@ -12,8 +15,8 @@ extern void abort (void);
 extern void *memcpy (void *, const void *, size_t);
 
 static int AI[18];
-static int init_si[18] = { 0,0,0,1,0,0,0,0,-1,0,0,0,0,0,-1,0,0,0 };
-static int test_si[18] = { 1,1,1,1,1,4,22,-12,7,8,9,7,1,-12,7,8,9,7 };
+static int init_si[18] = { 0,0,0,1,0,0, 0,0  ,-1,0,0,-1,0,0  ,-1,0,0,-1 };
+static int test_si[18] = { 1,1,1,1,1,4,22,-12,7 ,8,9,~7,1,-12,7 ,8,9,~7 };
 
 static void
 do_si (void)
@@ -44,7 +47,7 @@ do_si (void)
     abort ();
   if (__sync_fetch_and_xor(AI+10, 9) != 0)
     abort ();
-  if (__sync_fetch_and_nand(AI+11, 7) != 0)
+  if (__sync_fetch_and_nand(AI+11, 7) != -1)
     abort ();
 
   if (__sync_add_and_fetch(AI+12, 1) != 1)
@@ -57,13 +60,13 @@ do_si (void)
     abort ();
   if (__sync_xor_and_fetch(AI+16, 9) != 9)
     abort ();
-  if (__sync_nand_and_fetch(AI+17, 7) != 7)
+  if (__sync_nand_and_fetch(AI+17, 7) != ~7)
     abort ();
 }
 
 static long AL[18];
-static long init_di[18] = { 0,0,0,1,0,0,0,0,-1,0,0,0,0,0,-1,0,0,0 };
-static long test_di[18] = { 1,1,1,1,1,4,22,-12,7,8,9,7,1,-12,7,8,9,7 };
+static long init_di[18] = { 0,0,0,1,0,0, 0,0  ,-1,0,0,-1,0,0  ,-1,0,0,-1 };
+static long test_di[18] = { 1,1,1,1,1,4,22,-12,7 ,8,9,~7,1,-12,7 ,8,9,~7 };
 
 static void
 do_di (void)
@@ -94,7 +97,7 @@ do_di (void)
     abort ();
   if (__sync_fetch_and_xor(AL+10, 9) != 0)
     abort ();
-  if (__sync_fetch_and_nand(AL+11, 7) != 0)
+  if (__sync_fetch_and_nand(AL+11, 7) != -1)
     abort ();
 
   if (__sync_add_and_fetch(AL+12, 1) != 1)
@@ -107,7 +110,7 @@ do_di (void)
     abort ();
   if (__sync_xor_and_fetch(AL+16, 9) != 9)
     abort ();
-  if (__sync_nand_and_fetch(AL+17, 7) != 7)
+  if (__sync_nand_and_fetch(AL+17, 7) != ~7)
     abort ();
 }
 
diff --git a/gcc/testsuite/gcc.dg/pr37908.c b/gcc/testsuite/gcc.dg/pr37908.c
new file mode 100644 (file)
index 0000000..d927807
--- /dev/null
@@ -0,0 +1,25 @@
+/* { dg-do run } */
+/* { dg-require-effective-target sync_char_short } */
+/* { dg-options "-Wsync-nand" } */
+/* { dg-options "-Wsync-nand -march=i486" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
+/* { dg-options "-Wsync-nand -mcpu=v9" { target sparc*-*-* } } */
+
+
+extern void abort (void);
+
+int main (void)
+{
+
+  short xLoc;
+  short xIn, xOut, xExpect, i = 1;
+
+  xLoc = xIn = ~ (1 << i);
+  xExpect = ~ (xIn & 0x7F);
+
+  xOut = __sync_nand_and_fetch (&xLoc, 0x7F); /* { dg-message "note: '__sync_nand_and_fetch' changed semantics in GCC 4.4" "" } */
+
+  if (xOut != xExpect)
+    abort ();
+
+  return 0;
+}
index d0e3f2cbe776228072025f52c5a84a53ed9b49c3..7fea8f8fd03bcc896ff394b63e2233ec24f402ef 100644 (file)
@@ -4,18 +4,17 @@
 /* { dg-options "-march=i486" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
 /* { dg-options "-mcpu=v9" { target sparc*-*-* } } */
 
+/* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+/* { dg-message "note: '__sync_nand_and_fetch' changed semantics in GCC 4.4" "" { target *-*-* } 0 } */
+
 /* Test functionality of the intrinsics for 'short' and 'char'.  */
 
 extern void abort (void);
 extern void *memcpy (void *, const void *, __SIZE_TYPE__);
 
-#ifndef AI_ALIGN
-#define AI_ALIGN
-#endif
-
-static char AI[18] AI_ALIGN;
-static char init_qi[18] = { 3,5,7,9,0,0,0,0,-1,0,0,0,0,0,-1,0,0,0 };
-static char test_qi[18] = { 3,5,7,9,1,4,22,-12,7,8,9,7,1,-12,7,8,9,7 };
+static char AI[18];
+static char init_qi[18] = { 3,5,7,9,0,0,0 ,0  ,-1,0,0,-1,0,0  ,-1,0,0,-1 };
+static char test_qi[18] = { 3,5,7,9,1,4,22,-12,7 ,8,9,~7,1,-12,7 ,8,9,~7 };
 
 static void
 do_qi (void)
@@ -34,7 +33,7 @@ do_qi (void)
     abort ();
   if (__sync_fetch_and_xor(AI+10, 9) != 0)
     abort ();
-  if (__sync_fetch_and_nand(AI+11, 7) != 0)
+  if (__sync_fetch_and_nand(AI+11, 7) != (char)-1)
     abort ();
 
   if (__sync_add_and_fetch(AI+12, 1) != 1)
@@ -47,13 +46,13 @@ do_qi (void)
     abort ();
   if (__sync_xor_and_fetch(AI+16, 9) != 9)
     abort ();
-  if (__sync_nand_and_fetch(AI+17, 7) != 7)
+  if (__sync_nand_and_fetch(AI+17, 7) != ~7)
     abort ();
 }
 
 static short AL[18];
-static short init_hi[18] = { 3,5,7,9,0,0,0,0,-1,0,0,0,0,0,-1,0,0,0 };
-static short test_hi[18] = { 3,5,7,9,1,4,22,-12,7,8,9,7,1,-12,7,8,9,7 };
+static short init_hi[18] = { 3,5,7,9,0,0,0 ,0  ,-1,0,0,-1,0,0  ,-1,0,0,-1 };
+static short test_hi[18] = { 3,5,7,9,1,4,22,-12,7 ,8,9,~7,1,-12,7 ,8,9,~7 };
 
 static void
 do_hi (void)
@@ -72,7 +71,7 @@ do_hi (void)
     abort ();
   if (__sync_fetch_and_xor(AL+10, 9) != 0)
     abort ();
-  if (__sync_fetch_and_nand(AL+11, 7) != 0)
+  if (__sync_fetch_and_nand(AL+11, 7) != -1)
     abort ();
 
   if (__sync_add_and_fetch(AL+12, 1) != 1)
@@ -85,7 +84,7 @@ do_hi (void)
     abort ();
   if (__sync_xor_and_fetch(AL+16, 9) != 9)
     abort ();
-  if (__sync_nand_and_fetch(AL+17, 7) != 7)
+  if (__sync_nand_and_fetch(AL+17, 7) != ~7)
     abort ();
 }
 
index bf8abb785de1f937c20036ca3dc630118779b453..a359d162fee3cb67d7ed29947148b840663a4521 100644 (file)
 /* { dg-do run } */
 /* { dg-require-effective-target sync_char_short } */
-/* { dg-options "-O2" } */
-/* { dg-options "-march=i486 -O2" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
-/* { dg-options "-mcpu=v9 -O2" { target sparc*-*-* } } */
+/* { dg-options "-ansi" } */
+/* { dg-options "-march=i486" { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */
+/* { dg-options "-mcpu=v9" { target sparc*-*-* } } */
 
 /* Test functionality of the intrinsics for 'short' and 'char'.  */
 
-#define AI_ALIGN __attribute__((__aligned__ (4)))
-#include "sync-2.c"
+extern void abort (void);
+extern void *memcpy (void *, const void *, __SIZE_TYPE__);
+
+static char AI[18] __attribute__((__aligned__ (4)));
+static char init_qi[18] = { 3,5,7,9,0,0,0 ,0  ,-1,0,0,-1,0,0  ,-1,0,0,-1 };
+static char test_qi[18] = { 3,5,7,9,1,4,22,-12,7 ,8,9,~7,1,-12,7 ,8,9,~7 };
+
+static void
+do_qi (void)
+{
+  if (__sync_fetch_and_add(AI+4, 1) != 0)
+    abort ();
+  if (__sync_fetch_and_add(AI+5, 4) != 0)
+    abort ();
+  if (__sync_fetch_and_add(AI+6, 22) != 0)
+    abort ();
+  if (__sync_fetch_and_sub(AI+7, 12) != 0)
+    abort ();
+  if (__sync_fetch_and_and(AI+8, 7) != (char)-1)
+    abort ();
+  if (__sync_fetch_and_or(AI+9, 8) != 0)
+    abort ();
+  if (__sync_fetch_and_xor(AI+10, 9) != 0)
+    abort ();
+  if (__sync_fetch_and_nand(AI+11, 7) != (char)-1) /* { dg-message "note: '__sync_fetch_and_nand' changed semantics in GCC 4.4" "" } */
+    abort ();
+
+  if (__sync_add_and_fetch(AI+12, 1) != 1)
+    abort ();
+  if (__sync_sub_and_fetch(AI+13, 12) != (char)-12)
+    abort ();
+  if (__sync_and_and_fetch(AI+14, 7) != 7)
+    abort ();
+  if (__sync_or_and_fetch(AI+15, 8) != 8)
+    abort ();
+  if (__sync_xor_and_fetch(AI+16, 9) != 9)
+    abort ();
+  if (__sync_nand_and_fetch(AI+17, 7) != ~7) /* { dg-message "note: '__sync_nand_and_fetch' changed semantics in GCC 4.4" "" } */
+    abort ();
+}
+
+static short AL[18];
+static short init_hi[18] = { 3,5,7,9,0,0,0 ,0  ,-1,0,0,-1,0,0  ,-1,0,0,-1 };
+static short test_hi[18] = { 3,5,7,9,1,4,22,-12,7 ,8,9,~7,1,-12,7 ,8,9,~7 };
+
+static void
+do_hi (void)
+{
+  if (__sync_fetch_and_add(AL+4, 1) != 0)
+    abort ();
+  if (__sync_fetch_and_add(AL+5, 4) != 0)
+    abort ();
+  if (__sync_fetch_and_add(AL+6, 22) != 0)
+    abort ();
+  if (__sync_fetch_and_sub(AL+7, 12) != 0)
+    abort ();
+  if (__sync_fetch_and_and(AL+8, 7) != -1)
+    abort ();
+  if (__sync_fetch_and_or(AL+9, 8) != 0)
+    abort ();
+  if (__sync_fetch_and_xor(AL+10, 9) != 0)
+    abort ();
+  if (__sync_fetch_and_nand(AL+11, 7) != -1)
+    abort ();
+
+  if (__sync_add_and_fetch(AL+12, 1) != 1)
+    abort ();
+  if (__sync_sub_and_fetch(AL+13, 12) != -12)
+    abort ();
+  if (__sync_and_and_fetch(AL+14, 7) != 7)
+    abort ();
+  if (__sync_or_and_fetch(AL+15, 8) != 8)
+    abort ();
+  if (__sync_xor_and_fetch(AL+16, 9) != 9)
+    abort ();
+  if (__sync_nand_and_fetch(AL+17, 7) != ~7)
+    abort ();
+}
+
+int main()
+{
+  memcpy(AI, init_qi, sizeof(init_qi));
+  memcpy(AL, init_hi, sizeof(init_hi));
+
+  do_qi ();
+  do_hi ();
+
+  if (memcmp (AI, test_qi, sizeof(test_qi)))
+    abort ();
+  if (memcmp (AL, test_hi, sizeof(test_hi)))
+    abort ();
+
+  return 0;
+}