@@ -1845,6 +1845,17 @@ set_contract_wrapper_function (tree fndecl, tree wrapper)
18451845 decl_wrapper_fn->put (fndecl, wrapper);
18461846}
18471847
1848+ static tree
1849+ contracts_fixup_cdtorname (tree idin)
1850+ {
1851+ const char *n = IDENTIFIER_POINTER (idin);
1852+ size_t l = strlen (n);
1853+ char *nn = xasprintf (" %.*s_" , (int )l-1 , n);
1854+ tree nid = get_identifier (nn);
1855+ free (nn);
1856+ return nid;
1857+ }
1858+
18481859/* Build a declaration for the contract wrapper of a caller FNDECL.
18491860 If is_cvh is true, we're wrapping a contract violation handler
18501861 in a noexcept wrapper. Otherwise, we're making a caller side
@@ -1863,6 +1874,8 @@ build_contract_wrapper_function (tree fndecl, bool is_cvh)
18631874 tree fnname;
18641875 if (is_cvh)
18651876 fnname = get_identifier (" handle_contract_violation.noexcept_wrapper" );
1877+ else if (DECL_NAME (fndecl) && IDENTIFIER_CDTOR_P (DECL_NAME (fndecl)))
1878+ fnname = contracts_fixup_cdtorname (DECL_NAME (fndecl));
18661879 else
18671880 fnname = copy_node (DECL_NAME (fndecl));
18681881 location_t loc = DECL_SOURCE_LOCATION (fndecl);
@@ -3469,7 +3482,10 @@ define_contract_wrapper_func (const tree& fndecl, const tree& wrapdecl, void*)
34693482 checks are enabled for all clients. We should not get here unless there
34703483 are some checks to make. */
34713484 bool check_post = (flag_contract_nonattr_client_check > 1 ) || is_virtual;
3472- copy_and_remap_contracts (wrapdecl, fndecl, /* remap_result*/ true , check_post);
3485+ /* For wrappers on CDTORs we need to refer to the original contracts,
3486+ when the wrapper is around a clone. */
3487+ copy_and_remap_contracts (wrapdecl, DECL_ORIGIN (fndecl),
3488+ /* remap_result*/ true , check_post);
34733489
34743490 start_preparsed_function (wrapdecl, /* DECL_ATTRIBUTES*/ NULL_TREE,
34753491 SF_DEFAULT | SF_PRE_PARSED);
0 commit comments