Fix ICE on class-template argument deduction (PR c++/88795)
authorDavid Malcolm <dmalcolm@redhat.com>
Tue, 15 Jan 2019 23:29:15 +0000 (23:29 +0000)
committerDavid Malcolm <dmalcolm@gcc.gnu.org>
Tue, 15 Jan 2019 23:29:15 +0000 (23:29 +0000)
PR c++/88795 reports an ICE building a function_type for a deduction guide
when the substitution into the function signature fails, due to an
error_mark_node being returned from tsubst_arg_types but not being checked
for.  This error_mark_node gets used as the TYPE_ARG_TYPES, leading to
ICEs in various places that assume this is a TREE_LIST.

This patch checks the result of tsubst_arg_types and propagates the failure
if it returns error_mark_node.  It also adds an assertion to
build_function_type, to fail faster if passed in error_mark_node.

gcc/cp/ChangeLog:
PR c++/88795
* pt.c (build_deduction_guide): Bail out if tsubst_arg_types
fails.

gcc/testsuite/ChangeLog:
PR c++/88795
* g++.dg/template/pr88795.C: New test.

gcc/ChangeLog:
PR c++/88795
* tree.c (build_function_type): Assert that arg_types is not
error_mark_node.

From-SVN: r267957

gcc/ChangeLog
gcc/cp/ChangeLog
gcc/cp/pt.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/template/pr88795.C [new file with mode: 0644]
gcc/tree.c

index 83d4fa4af0c61848fe8e33ca66c2593790cba650..e1ae217c03c2bc7e817e351fcd9f9ee3b4bb9b2e 100644 (file)
@@ -1,3 +1,9 @@
+2019-01-15  David Malcolm  <dmalcolm@redhat.com>
+
+       PR c++/88795
+       * tree.c (build_function_type): Assert that arg_types is not
+       error_mark_node.
+
 2019-01-15  Richard Sandiford  <richard.sandiford@arm.com>
 
        PR inline-asm/52813
index 35eec34fca5c32294a9b33bf5ae90a9bbc6c0410..7cf0ffba4928f88d94eeb9b5c9a8d503935638eb 100644 (file)
@@ -1,3 +1,9 @@
+2019-01-15  David Malcolm  <dmalcolm@redhat.com>
+
+       PR c++/88795
+       * pt.c (build_deduction_guide): Bail out if tsubst_arg_types
+       fails.
+
 2019-01-15  Paolo Carlini  <paolo.carlini@oracle.com>
 
        * decl.c (start_decl): Improve error location.
index f062a2b9707dc95667744f17746ef627f0c73fc8..c6fc1cfeffb2d77f864c29f51c30c78eff7f9637 100644 (file)
@@ -26932,6 +26932,8 @@ build_deduction_guide (tree ctor, tree outer_args, tsubst_flags_t complain)
          targs = template_parms_to_args (tparms);
          fparms = tsubst_arg_types (fparms, tsubst_args, NULL_TREE,
                                     complain, ctor);
+         if (fparms == error_mark_node)
+           ok = false;
          fargs = tsubst (fargs, tsubst_args, complain, ctor);
          if (ci)
            ci = tsubst_constraint_info (ci, tsubst_args, complain, ctor);
index ec8a0c18c70edf6b86f65b2a1ce0218577bf0593..d226aa54af6fafc80a1fb7b2312ce40af152073c 100644 (file)
@@ -1,3 +1,8 @@
+2019-01-15  David Malcolm  <dmalcolm@redhat.com>
+
+       PR c++/88795
+       * g++.dg/template/pr88795.C: New test.
+
 2019-01-15  Thomas Koenig  <tkoenig@gcc.gnu.org>
 
        PR fortran/43136
diff --git a/gcc/testsuite/g++.dg/template/pr88795.C b/gcc/testsuite/g++.dg/template/pr88795.C
new file mode 100644 (file)
index 0000000..918aa6d
--- /dev/null
@@ -0,0 +1,23 @@
+// { dg-do compile { target c++17 } }
+
+template<class, int>
+struct Array {};
+
+template<class T, int size_>
+struct Foo {
+  static constexpr int size() {
+      return size_;
+  }
+
+  template<class U>
+  Foo(U, Array<T, size()>) {}
+};
+
+template<class T, int size, class U>
+Foo(U, Array<T, size>) -> Foo<T, size>;
+
+int main() {
+  Array<int, 2> arr{};
+
+  Foo foo{2.0, arr};
+}
index 2e112ee17c6ec56e90158d030588a74780627c08..9e55499455639c0a77344ba13b6891421c23f753 100644 (file)
@@ -8455,6 +8455,8 @@ build_function_type (tree value_type, tree arg_types)
   bool any_structural_p, any_noncanonical_p;
   tree canon_argtypes;
 
+  gcc_assert (arg_types != error_mark_node);
+
   if (TREE_CODE (value_type) == FUNCTION_TYPE)
     {
       error ("function return type cannot be function");