@@ -1080,12 +1080,14 @@ remap_contract (tree src, tree dst, tree contract, bool duplicate_p)
1080
1080
bool do_remap = false ;
1081
1081
1082
1082
/* Insert parameter remappings. */
1083
- if (TREE_CODE (src) == FUNCTION_DECL)
1084
- src = DECL_ARGUMENTS (src);
1085
- if (TREE_CODE (dst) == FUNCTION_DECL)
1086
- dst = DECL_ARGUMENTS (dst);
1083
+ gcc_assert (TREE_CODE (src) == FUNCTION_DECL);
1084
+ gcc_assert (TREE_CODE (dst) == FUNCTION_DECL);
1087
1085
1088
- for (tree sp = src, dp = dst;
1086
+ int src_num_artificial_args = num_artificial_parms_for (src);
1087
+ int dst_num_artificial_args = num_artificial_parms_for (dst);
1088
+
1089
+
1090
+ for (tree sp = DECL_ARGUMENTS (src), dp = DECL_ARGUMENTS (dst);
1089
1091
sp || dp;
1090
1092
sp = DECL_CHAIN (sp), dp = DECL_CHAIN (dp))
1091
1093
{
@@ -1109,6 +1111,20 @@ remap_contract (tree src, tree dst, tree contract, bool duplicate_p)
1109
1111
1110
1112
insert_decl_map (&id, sp, dp);
1111
1113
do_remap = true ;
1114
+
1115
+ /* First artificial arg is *this. We want to remap that. However, we
1116
+ want to skip _in_charge param and __vtt_parm. Do so now. */
1117
+ if (src_num_artificial_args > 0 )
1118
+ {
1119
+ while (--src_num_artificial_args,src_num_artificial_args > 0 )
1120
+ sp = DECL_CHAIN (sp);
1121
+ }
1122
+ if (dst_num_artificial_args > 0 )
1123
+ {
1124
+ while (--dst_num_artificial_args,dst_num_artificial_args > 0 )
1125
+ dp = DECL_CHAIN (dp);
1126
+ }
1127
+
1112
1128
}
1113
1129
if (!do_remap)
1114
1130
return ;
@@ -3065,17 +3081,17 @@ maybe_apply_function_contracts (tree fndecl)
3065
3081
/* The DECL_SAVED_TREE stmt list will be popped by our caller. */
3066
3082
}
3067
3083
3068
- /* Replace any contract attributes on SOURCE with a copy where any
3069
- references to SOURCE's PARM_DECLs have been rewritten to the corresponding
3070
- PARM_DECL in DEST. If remap_result is true, result identifier is
3071
- also re-mapped. C++20 version used this function to remap contracts on
3072
- virtual functions from base class to derived class. In such a case
3073
- postcondition identified wasn't remapped. Caller side wrapper functions
3074
- need to remap the result identifier.
3075
- I remap_post is false, postconditions are dropped from the destination. */
3084
+ /* Returns a copy of SOURCE contracts where any references to SOURCE's
3085
+ PARM_DECLs have been rewritten to the corresponding PARM_DECL in DEST. If
3086
+ remap_result is true, result identifier is also re-mapped.
3087
+ C++20 version used this function to remap contracts on virtual functions
3088
+ from base class to derived class. In such a case postcondition identifier
3089
+ wasn't remapped. Caller side wrapper functions need to remap the result
3090
+ identifier.
3091
+ If remap_post is false, postconditions are dropped from the destination. */
3076
3092
3077
- void
3078
- copy_and_remap_contracts (tree dest, tree source, bool remap_result = true ,
3093
+ tree
3094
+ remap_contracts (tree dest, tree source, bool remap_result = true ,
3079
3095
bool remap_post = true )
3080
3096
{
3081
3097
tree last = NULL_TREE, contract_attrs = NULL_TREE;
@@ -3111,7 +3127,7 @@ copy_and_remap_contracts (tree dest, tree source, bool remap_result = true,
3111
3127
contract_attrs = c;
3112
3128
}
3113
3129
3114
- set_decl_contracts (dest, contract_attrs) ;
3130
+ return contract_attrs;
3115
3131
}
3116
3132
3117
3133
/* Finish up the pre & post function definitions for a guarded FNDECL,
@@ -3407,7 +3423,10 @@ should_contract_wrap_call (bool do_pre, bool do_post, bool is_virt)
3407
3423
3408
3424
/* We always wrap virtual function calls, and non-virtual calls when
3409
3425
client-side checking is enabled for all contracts. */
3410
- if (is_virt || (flag_contract_nonattr_client_check > 1 ))
3426
+ if ((is_virt
3427
+ && (flag_contract_nonattr_inheritance_mode
3428
+ == CONTRACT_INHERITANCE_P2900R13))
3429
+ || (flag_contract_nonattr_client_check > 1 ))
3411
3430
return true ;
3412
3431
3413
3432
/* Otherwise, any function with pre-conditions when selected. */
@@ -3482,11 +3501,16 @@ define_contract_wrapper_func (const tree& fndecl, const tree& wrapdecl, void*)
3482
3501
/* We check postconditions on virtual function calls or if postcondition
3483
3502
checks are enabled for all clients. We should not get here unless there
3484
3503
are some checks to make. */
3485
- bool check_post = (flag_contract_nonattr_client_check > 1 ) || is_virtual;
3504
+ bool check_post
3505
+ = (flag_contract_nonattr_client_check > 1 )
3506
+ || (is_virtual
3507
+ && (flag_contract_nonattr_inheritance_mode
3508
+ == CONTRACT_INHERITANCE_P2900R13));
3486
3509
/* For wrappers on CDTORs we need to refer to the original contracts,
3487
3510
when the wrapper is around a clone. */
3488
- copy_and_remap_contracts (wrapdecl, DECL_ORIGIN (fndecl),
3489
- /* remap_result*/ true , check_post);
3511
+ set_decl_contracts ( wrapdecl,
3512
+ remap_contracts (wrapdecl, DECL_ORIGIN (fndecl),
3513
+ /* remap_result*/ true , check_post));
3490
3514
3491
3515
start_preparsed_function (wrapdecl, /* DECL_ATTRIBUTES*/ NULL_TREE,
3492
3516
SF_DEFAULT | SF_PRE_PARSED);
0 commit comments