@@ -2960,6 +2960,9 @@ static tree cp_parser_function_contract_specifier_seq
29602960static void cp_parser_late_contract_condition
29612961 (cp_parser *, tree, tree);
29622962
2963+ static bool cp_parser_should_constify_contract
2964+ (const contract_modifier&);
2965+
29632966enum pragma_context {
29642967 pragma_external,
29652968 pragma_member,
@@ -13220,12 +13223,8 @@ cp_parser_statement (cp_parser* parser, tree in_statement_expr,
1322013223 0);
1322113224
1322213225 /* Do we have an override for const-ification? */
13223- bool should_constify = !flag_contracts_nonattr_noconst;
13224- if (!modifier.error_p
13225- && (modifier.mutable_p
13226- || (flag_contracts_nonattr_const_keyword
13227- && !modifier.const_p)))
13228- should_constify = false;
13226+ bool should_constify
13227+ = cp_parser_should_constify_contract (modifier);
1322913228
1323013229 /* If we have a current class object, see if we need to consider
1323113230 it const when processing the contract condition. */
@@ -31745,6 +31744,41 @@ cp_parser_function_contract_modifier_opt (cp_parser * parser)
3174531744 return mod;
3174631745}
3174731746
31747+ /* Decide on whether this contract is const-ified, which depends on both
31748+ the global choice (flag_contracts_nonattr_noconst) and local MODIFIER
31749+ settings.
31750+
31751+ Precedence:
31752+ 'const' keyword
31753+ 'mutable' keyword
31754+ -fcontracts-nonattr-noconst. */
31755+
31756+ static bool
31757+ cp_parser_should_constify_contract (const contract_modifier& modifier)
31758+ {
31759+ /* Start with the user's base choice. */
31760+ bool should_constify = !flag_contracts_nonattr_noconst;
31761+
31762+ /* We do not need to check for mutable/const conflicts that was done when
31763+ parsing the modifier. */
31764+
31765+ /* Do we have an override that makes this mutable? */
31766+ if (!modifier.error_p
31767+ && (modifier.mutable_p
31768+ || (flag_contracts_nonattr_const_keyword && !modifier.const_p)))
31769+ should_constify = false;
31770+
31771+ /* Do we have an override that makes this const?
31772+ This would apply when the base choice is 'no' but we have the const
31773+ keyword applied to this specific contract. */
31774+ if (!modifier.error_p
31775+ && flag_contracts_nonattr_const_keyword
31776+ && modifier.const_p)
31777+ should_constify = true;
31778+
31779+ return should_constify;
31780+ }
31781+
3174831782/* Parse a natural syntax contract specifier seq.
3174931783
3175031784 function-contract-specifier :
@@ -31759,8 +31793,8 @@ cp_parser_function_contract_modifier_opt (cp_parser * parser)
3175931793
3176031794 Return void_list_node if the current token doesn't start a
3176131795 contract specifier.
31762-
3176331796*/
31797+
3176431798static tree
3176531799cp_parser_function_contract_specifier (cp_parser *parser)
3176631800{
@@ -31810,11 +31844,7 @@ cp_parser_function_contract_specifier (cp_parser *parser)
3181031844 cp_parser_require (parser, CPP_COLON, RT_COLON);
3181131845
3181231846 /* Do we have an override for const-ification? */
31813- bool should_constify = !flag_contracts_nonattr_noconst;
31814- if (!modifier.error_p
31815- && (modifier.mutable_p
31816- || (flag_contracts_nonattr_const_keyword && !modifier.const_p)))
31817- should_constify = false;
31847+ bool should_constify = cp_parser_should_constify_contract (modifier);
3181831848
3181931849 tree contract;
3182031850 if (current_class_type &&
@@ -31899,7 +31929,7 @@ cp_parser_function_contract_specifier (cp_parser *parser)
3189931929 if (!flag_contracts || !flag_contracts_nonattr)
3190031930 {
3190131931 error_at (loc, "P2900 contracts are only available with %<-fcontracts%>"
31902- " and %<-fcontracts-nonattr%>");
31932+ " and %<-fcontracts-nonattr%>");
3190331933 return error_mark_node;
3190431934 }
3190531935
0 commit comments