re PR c++/15142 (Internal compiler error when passing a string where a char* is expec...
authorJason Merrill <jason@redhat.com>
Tue, 1 Jun 2004 20:28:38 +0000 (16:28 -0400)
committerJason Merrill <jason@gcc.gnu.org>
Tue, 1 Jun 2004 20:28:38 +0000 (16:28 -0400)
        PR c++/15142
        * call.c (call_builtin_trap): Remove type parm.
        (convert_arg_to_ellipsis): Change a non-POD argument to integer type.
        (build_x_va_arg): Dereference a null pointer for a non-POD argument.

From-SVN: r82556

gcc/cp/ChangeLog
gcc/cp/call.c
gcc/testsuite/g++.dg/overload/ellipsis1.C [new file with mode: 0644]

index 22277beadacc7d91971e6c6636a2f13ac4d5403b..c5ea71e5cd6afe44c16f2a99f703ba20d1aadaa5 100644 (file)
@@ -1,3 +1,10 @@
+2004-06-01  Jason Merrill  <jason@redhat.com>
+
+       PR c++/15142
+       * call.c (call_builtin_trap): Remove type parm.
+       (convert_arg_to_ellipsis): Change a non-POD argument to integer type.
+       (build_x_va_arg): Dereference a null pointer for a non-POD argument.
+
 2004-06-01  Kriang Lerdsuwanakij  <lerdsuwa@users.sourceforge.net>
 
        PR c++/13092
index ecace2dd78ea7dc48edd6df62a6110dc29a939e9..d1e8298164beab2102e255d5262c2326d1970e88 100644 (file)
@@ -182,7 +182,7 @@ static conversion *direct_reference_binding (tree, conversion *);
 static bool promoted_arithmetic_type_p (tree);
 static conversion *conditional_conversion (tree, tree);
 static char *name_as_c_string (tree, tree, bool *);
-static tree call_builtin_trap (tree);
+static tree call_builtin_trap (void);
 static tree prep_operand (tree);
 static void add_candidates (tree, tree, tree, bool, tree, tree,
                            int, struct z_candidate **);
@@ -4325,18 +4325,15 @@ convert_like_real (conversion *convs, tree expr, tree fn, int argnum,
                      LOOKUP_NORMAL|LOOKUP_NO_CONVERSION);
 }
 
-/* Build a call to __builtin_trap which can be used as an expression of
-   type TYPE.  */
+/* Build a call to __builtin_trap.  */
 
 static tree
-call_builtin_trap (tree type)
+call_builtin_trap (void)
 {
   tree fn = implicit_built_in_decls[BUILT_IN_TRAP];
 
   my_friendly_assert (fn != NULL, 20030927);
   fn = build_call (fn, NULL_TREE);
-  fn = build (COMPOUND_EXPR, type, fn, error_mark_node);
-  fn = force_target_expr (type, fn);
   return fn;
 }
 
@@ -4379,7 +4376,9 @@ convert_arg_to_ellipsis (tree arg)
       if (!skip_evaluation)
        warning ("cannot pass objects of non-POD type `%#T' through `...'; "
                 "call will abort at runtime", TREE_TYPE (arg));
-      arg = call_builtin_trap (TREE_TYPE (arg));
+      arg = call_builtin_trap ();
+      arg = build (COMPOUND_EXPR, integer_type_node, arg,
+                  integer_zero_node);
     }
 
   return arg;
@@ -4404,7 +4403,11 @@ build_x_va_arg (tree expr, tree type)
       warning ("cannot receive objects of non-POD type `%#T' through `...'; \
 call will abort at runtime",
               type);
-      return call_builtin_trap (type);
+      expr = convert (build_pointer_type (type), null_node);
+      expr = build (COMPOUND_EXPR, TREE_TYPE (expr),
+                   call_builtin_trap (), expr);
+      expr = build_indirect_ref (expr, NULL);
+      return expr;
     }
   
   return build_va_arg (expr, type);
diff --git a/gcc/testsuite/g++.dg/overload/ellipsis1.C b/gcc/testsuite/g++.dg/overload/ellipsis1.C
new file mode 100644 (file)
index 0000000..bdd3cd2
--- /dev/null
@@ -0,0 +1,21 @@
+// PR c++/15142
+// Bug: We were aborting after giving a warning about passing a non-POD.
+
+// Suppress the warning about undefined behavior.
+// { dg-options "-w" }
+
+struct B { 
+    B() throw() { } 
+    B(const B&) throw() { } 
+}; 
+struct X { 
+    B a; 
+    X& operator=(const X&); 
+}; 
+struct S { S(...); }; 
+void SillyFunc() { 
+  throw S(X()); 
+}