push_access_scope (fn);
push_deferring_access_checks (dk_no_deferred);
input_location = DECL_SOURCE_LOCATION (fn);
- noex = tsubst_copy_and_build (DEFERRED_NOEXCEPT_PATTERN (noex),
- DEFERRED_NOEXCEPT_ARGS (noex),
- tf_warning_or_error, fn,
- /*function_p=*/false,
- /*integral_constant_expression_p=*/true);
- spec = build_noexcept_spec (noex, tf_warning_or_error);
+
+ /* A new stack interferes with pop_access_scope. */
+ {
+ /* Set up the list of local specializations. */
+ local_specialization_stack lss (lss_copy);
+
+ tree save_ccp = current_class_ptr;
+ tree save_ccr = current_class_ref;
+ /* If needed, set current_class_ptr for the benefit of
+ tsubst_copy/PARM_DECL. */
+ tree tdecl = DECL_TEMPLATE_RESULT (DECL_TI_TEMPLATE (fn));
+ if (DECL_NONSTATIC_MEMBER_FUNCTION_P (tdecl))
+ {
+ tree this_parm = DECL_ARGUMENTS (tdecl);
+ current_class_ptr = NULL_TREE;
+ current_class_ref = cp_build_fold_indirect_ref (this_parm);
+ current_class_ptr = this_parm;
+ }
+
+ /* Create substitution entries for the parameters. */
+ register_parameter_specializations (tdecl, fn);
+
+ /* Do deferred instantiation of the noexcept-specifier. */
+ noex = tsubst_copy_and_build (DEFERRED_NOEXCEPT_PATTERN (noex),
+ DEFERRED_NOEXCEPT_ARGS (noex),
+ tf_warning_or_error, fn,
+ /*function_p=*/false,
+ /*i_c_e_p=*/true);
+ current_class_ptr = save_ccp;
+ current_class_ref = save_ccr;
+ spec = build_noexcept_spec (noex, tf_warning_or_error);
+ }
+
pop_deferring_access_checks ();
pop_access_scope (fn);
pop_tinst_level ();
--- /dev/null
+// PR c++/88294
+// { dg-do compile { target c++11 } }
+
+constexpr int foo (bool b) { return b; }
+
+template<typename> struct A
+{
+ constexpr int f () { return 0; }
+ bool b = true;
+ void g () noexcept (f()) { } // { dg-error "use of parameter" }
+ void g2 () noexcept (this->f()) { } // { dg-error "use of parameter" }
+ void g3 () noexcept (b) { } // { dg-error "use of .this. in a constant expression|use of parameter" }
+ void g4 (int i) noexcept (i) { } // { dg-error "use of parameter" }
+ void g5 () noexcept (A::f()) { } // { dg-error "use of parameter" }
+ void g6 () noexcept (foo(b)) { } // { dg-error "use of .this. in a constant expression|use of parameter" }
+ void g7 () noexcept (int{f()}) { } // { dg-error "use of parameter" }
+};
+
+int main ()
+{
+ A<int> a;
+ a.g ();
+ a.g2 ();
+ a.g3 ();
+ a.g4 (1);
+ a.g5 ();
+ a.g6 ();
+ a.g7 ();
+}
--- /dev/null
+// { dg-do compile { target c++11 } }
+
+template <typename _Tp, _Tp __v> struct A { static constexpr _Tp value = __v; };
+typedef A<bool, false> false_type;
+struct is_same : false_type {};
+template <bool> struct enable_if;
+template <typename> using __remove_cvref_t = int;
+template <typename _Tp> class reference_wrapper {
+ static _Tp _S_fun();
+ template <typename _Up, typename = __remove_cvref_t<_Up>>
+ using __not_same = enable_if<is_same::value>;
+
+public:
+ template <typename _Up, typename = __not_same<_Up>>
+ reference_wrapper(_Up) noexcept(noexcept(reference_wrapper::_S_fun));
+};
+
+reference_wrapper<int> fn1() {
+ int __t = 10;
+ return __t;
+}