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]

C++ PATCH for c++/37932


This is another place where we need to handle lowered bitfield types. As it turns out, even though this PR deals with C++0x initializer list semantics, the testcase in the PR shows a 4.2/4.3/4.4 regression, which I have added as bitfield11.C.

Tested x86_64-pc-linux-gnu, applied to trunk. I'll apply the relevant changes to 4.2 and 4.3 after testing.

2008-11-13  Jason Merrill  <jason@redhat.com>

	PR c++/37932
	* typeck2.c (process_init_constructor_record): Update bitfield
	handling.
	(check_narrowing): Update bitfield handling, print source type.
	
Index: cp/typeck2.c
===================================================================
*** cp/typeck2.c	(revision 141769)
--- cp/typeck2.c	(working copy)
*************** store_init_value (tree decl, tree init)
*** 650,656 ****
  void
  check_narrowing (tree type, tree init)
  {
!   tree ftype = TREE_TYPE (init);
    bool ok = true;
    REAL_VALUE_TYPE d;
    bool was_decl = false;
--- 650,656 ----
  void
  check_narrowing (tree type, tree init)
  {
!   tree ftype = unlowered_expr_type (init);
    bool ok = true;
    REAL_VALUE_TYPE d;
    bool was_decl = false;
*************** check_narrowing (tree type, tree init)
*** 704,711 ****
      }
  
    if (!ok)
!     permerror (input_location, "narrowing conversion of %qE to %qT inside { }",
! 	       init, type);
  }
  
  /* Process the initializer INIT for a variable of type TYPE, emitting
--- 704,711 ----
      }
  
    if (!ok)
!     permerror (input_location, "narrowing conversion of %qE from %qT to %qT inside { }",
! 	       init, ftype, type);
  }
  
  /* Process the initializer INIT for a variable of type TYPE, emitting
*************** process_init_constructor_record (tree ty
*** 993,998 ****
--- 993,999 ----
    for (field = TYPE_FIELDS (type); field; field = TREE_CHAIN (field))
      {
        tree next;
+       tree type;
  
        if (!DECL_NAME (field) && DECL_C_BIT_FIELD (field))
  	{
*************** process_init_constructor_record (tree ty
*** 1004,1009 ****
--- 1005,1015 ----
        if (TREE_CODE (field) != FIELD_DECL || DECL_ARTIFICIAL (field))
  	continue;
  
+       /* If this is a bitfield, first convert to the declared type.  */
+       type = TREE_TYPE (field);
+       if (DECL_BIT_FIELD_TYPE (field))
+ 	type = DECL_BIT_FIELD_TYPE (field);
+ 
        if (idx < VEC_length (constructor_elt, CONSTRUCTOR_ELTS (init)))
  	{
  	  constructor_elt *ce = VEC_index (constructor_elt,
*************** process_init_constructor_record (tree ty
*** 1024,1030 ****
  	    }
  
  	  gcc_assert (ce->value);
! 	  next = digest_init_r (TREE_TYPE (field), ce->value, true);
  	  ++idx;
  	}
        else if (TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (field)))
--- 1030,1036 ----
  	    }
  
  	  gcc_assert (ce->value);
! 	  next = digest_init_r (type, ce->value, true);
  	  ++idx;
  	}
        else if (TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (field)))
*************** process_init_constructor_record (tree ty
*** 1068,1073 ****
--- 1074,1082 ----
  	    continue;
  	}
  
+       /* If this is a bitfield, now convert to the lowered type.  */
+       if (type != TREE_TYPE (field))
+ 	next = cp_convert_and_check (TREE_TYPE (field), next);
        flags |= picflag_from_initializer (next);
        CONSTRUCTOR_APPEND_ELT (v, field, next);
      }
Index: testsuite/g++.dg/conversion/bitfield11.C
===================================================================
*** testsuite/g++.dg/conversion/bitfield11.C	(revision 0)
--- testsuite/g++.dg/conversion/bitfield11.C	(revision 0)
***************
*** 0 ****
--- 1,8 ----
+ // Make sure that digest_init converts to the declared type of the
+ // bitfield, not just the lowered type.
+ 
+ enum E { EA, EB };
+ 
+ struct A { E e: 8; };
+ 
+ A a = { 0 };			// { dg-error "invalid conversion" }
Index: testsuite/g++.dg/cpp0x/initlist7.C
===================================================================
*** testsuite/g++.dg/cpp0x/initlist7.C	(revision 0)
--- testsuite/g++.dg/cpp0x/initlist7.C	(revision 0)
***************
*** 0 ****
--- 1,12 ----
+ // PR c++/37932
+ // { dg-options "-std=c++0x" }
+ 
+ typedef enum { AA=1, BB=2 } my_enum;
+ 
+ typedef struct { my_enum a:4 ; unsigned b:28; } stru;
+ 
+ void foo (char c, my_enum x, int i)
+ {
+   char arr[2] = {c+'0', 0};	// { dg-error "narrowing" }
+   stru s = {x,0};
+ }

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