This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH] PR19100: truthvalue_conversion vs. TREE_CONSTANT_OVERFLOW


The following patch is a fix to PR middle-end/19100 which is a serious
wrong code bug in the C family front-ends.  The problem is that the
routine c_common_truthvalue conversion assumes that any INTEGER_CST
that isn't integer_zerop must be integer_nonzerop.  Unfortunately, this
assumption falls foul of TREE_CONSTANT_OVERFLOW, where if a constant
has previously overflowed during constant folding both integer_zerop
and integer_nonzerop return false.

The fix below preserves this function's current behaviour of ignoring
TREE_CONSTANT_OVERFLOW, but correctly returns true or false depending
on whether the integer value is zero/non-zero.

Whilst I was there I also noticed two further problems in the cases
directly before and after in c_common_truthvalue_conversion.  We
were not only also ignoring TREE_CONSTANT_OVERFLOW for REAL_CSTs,
but also return "true" for NaN.  And in the Boolean comparison
cases, we were destructively modifying the tree in-place (which in
the middle-end is generally considered a bad thing).  Finally,
whilst updating the Makefile.in dependencies for c-common.o, I
noticed that there were already several missing header file
dependencies, with are also fixed below.


Given that GCC 4.0 does considerably more constant folding at the
tree-level that any previous release, I'd like this patch to be
considered a regression fix, even though the specific testcase in
the PR has always failed.

The following patch has been tested on i686-pc-linux-gnu with a
full "make bootstrap", all default languages, and regression tested
with a top-level "make -k check" with no new failures.

Ok for mainline?



2004-12-21  Roger Sayle  <roger@eyesopen.com>

	PR middle-end/19100
	* c-common.c: Include real.h.
	(c_common_truthvalue_conversion): Avoid destructively modifying expr.
	Correctly handle TREE_CONSTANT_OVERFLOW for INTEGER_CST.
	Correctly handle TREE_CONSTANT_OVERFLOW and NaNs for REAL_CST.
	* Makefile.in (c-common.o): Update dependencies.

	* gcc.dg/conv-3.c: New test case.


Index: c-common.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/c-common.c,v
retrieving revision 1.595
diff -c -3 -p -r1.595 c-common.c
*** c-common.c	20 Dec 2004 20:11:15 -0000	1.595
--- c-common.c	21 Dec 2004 15:39:50 -0000
*************** Software Foundation, 59 Temple Place - S
*** 46,51 ****
--- 46,52 ----
  #include "hashtab.h"
  #include "tree-mudflap.h"
  #include "opts.h"
+ #include "real.h"

  cpp_reader *parse_in;		/* Declared in c-pragma.h.  */

*************** c_common_truthvalue_conversion (tree exp
*** 2326,2342 ****
      case TRUTH_OR_EXPR:
      case TRUTH_XOR_EXPR:
      case TRUTH_NOT_EXPR:
!       TREE_TYPE (expr) = truthvalue_type_node;
        return expr;

      case ERROR_MARK:
        return expr;

      case INTEGER_CST:
!       return integer_zerop (expr) ? truthvalue_false_node : truthvalue_true_node;

      case REAL_CST:
!       return real_zerop (expr) ? truthvalue_false_node : truthvalue_true_node;

      case ADDR_EXPR:
        {
--- 2327,2350 ----
      case TRUTH_OR_EXPR:
      case TRUTH_XOR_EXPR:
      case TRUTH_NOT_EXPR:
!       if (TREE_TYPE (expr) != truthvalue_type_node)
! 	return build2 (TREE_CODE (expr), truthvalue_type_node,
! 		       TREE_OPERAND (expr, 0), TREE_OPERAND (expr, 1));
        return expr;

      case ERROR_MARK:
        return expr;

      case INTEGER_CST:
!       /* Avoid integer_zerop to ignore TREE_CONSTANT_OVERFLOW.  */
!       return (TREE_INT_CST_LOW (expr) != 0 || TREE_INT_CST_HIGH (expr) != 0)
! 	     ? truthvalue_true_node
! 	     : truthvalue_false_node;

      case REAL_CST:
!       return real_compare (NE_EXPR, &TREE_REAL_CST (expr), &dconst0)
! 	     ? truthvalue_true_node
! 	     : truthvalue_false_node;

      case ADDR_EXPR:
        {
Index: Makefile.in
===================================================================
RCS file: /cvs/gcc/gcc/gcc/Makefile.in,v
retrieving revision 1.1436
diff -c -3 -p -r1.1436 Makefile.in
*** Makefile.in	20 Dec 2004 21:10:39 -0000	1.1436
--- Makefile.in	21 Dec 2004 15:39:51 -0000
*************** tlink.o: tlink.c $(DEMANGLE_H) $(HASHTAB
*** 1428,1437 ****
  # A file used by all variants of C.

  c-common.o : c-common.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) \
! 	$(OBSTACK_H) $(C_COMMON_H) $(FLAGS_H) toplev.h output.h $(C_PRAGMA_H) intl.h \
  	$(GGC_H) $(EXPR_H) $(TM_P_H) builtin-types.def builtin-attrs.def \
  	$(DIAGNOSTIC_H) gt-c-common.h langhooks.h varray.h $(RTL_H) \
! 	$(TARGET_H) $(C_TREE_H) tree-iterator.h langhooks.h tree-mudflap.h
  c-pretty-print.o : c-pretty-print.c $(C_PRETTY_PRINT_H) \
  	$(C_COMMON_H) $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) real.h \
  	$(DIAGNOSTIC_H)
--- 1428,1440 ----
  # A file used by all variants of C.

  c-common.o : c-common.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) \
! 	$(OBSTACK_H) $(C_COMMON_H) $(FLAGS_H) toplev.h output.h $(C_PRAGMA_H) \
  	$(GGC_H) $(EXPR_H) $(TM_P_H) builtin-types.def builtin-attrs.def \
  	$(DIAGNOSTIC_H) gt-c-common.h langhooks.h varray.h $(RTL_H) \
! 	$(TARGET_H) $(C_TREE_H) tree-iterator.h langhooks.h tree-mudflap.h \
! 	intl.h opts.h real.h $(CPPLIB_H) tree-inline.h $(HASHTAB_H) \
! 	builtins.def
!
  c-pretty-print.o : c-pretty-print.c $(C_PRETTY_PRINT_H) \
  	$(C_COMMON_H) $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) real.h \
  	$(DIAGNOSTIC_H)

/* PR middle-end/19100 */
/* { dg-do run } */
/* { dg-options "-O2" } */

void abort (void);

int test (int v)
{
  return ((signed char) (v ? 0x100 : 0)) ? 17 : 18;
}

int main()
{
  if (test (2) != 18)
    abort ();
  return 0;
}


Roger
--
Roger Sayle,                         E-mail: roger@eyesopen.com
OpenEye Scientific Software,         WWW: http://www.eyesopen.com/
Suite 1107, 3600 Cerrillos Road,     Tel: (+1) 505-473-7385
Santa Fe, New Mexico, 87507.         Fax: (+1) 505-473-0833


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]