public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
* [gcc/devel/c++-contracts] c++: move duplicate_contracts to contracts.cc
@ 2022-11-01 11:43 Jason Merrill
  0 siblings, 0 replies; only message in thread
From: Jason Merrill @ 2022-11-01 11:43 UTC (permalink / raw)
  To: gcc-cvs

https://gcc.gnu.org/g:5080aec5f3f0eae334883c099f93070e6c3a5b64

commit 5080aec5f3f0eae334883c099f93070e6c3a5b64
Author: Jason Merrill <jason@redhat.com>
Date:   Fri Oct 28 11:37:23 2022 -0400

    c++: move duplicate_contracts to contracts.cc
    
    gcc/cp/ChangeLog:
    
            * cp-tree.h (duplicate_contracts): Add prototype.
            * contracts.cc (duplicate_contracts): Move from...
            * decl.cc (duplicate_contracts): ...here.
            * parser.cc (cp_parser_contract_attribute_spec): Fix typo.

Diff:
---
 gcc/cp/cp-tree.h    |   1 +
 gcc/cp/contracts.cc | 101 ++++++++++++++++++++++++++++++++++++++++++++++++++++
 gcc/cp/decl.cc      | 101 ----------------------------------------------------
 gcc/cp/parser.cc    |   2 +-
 4 files changed, 103 insertions(+), 102 deletions(-)

diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h
index 11ac082c89f..a212aa2659d 100644
--- a/gcc/cp/cp-tree.h
+++ b/gcc/cp/cp-tree.h
@@ -7788,6 +7788,7 @@ extern void maybe_update_postconditions		(tree);
 extern void start_function_contracts		(tree);
 extern void finish_function_contracts		(tree);
 extern tree apply_postcondition_to_return	(tree);
+extern void duplicate_contracts			(tree, tree);
 
 inline void
 set_decl_contracts (tree decl, tree contract_attrs)
diff --git a/gcc/cp/contracts.cc b/gcc/cp/contracts.cc
index 214be7c671f..272448d07d8 100644
--- a/gcc/cp/contracts.cc
+++ b/gcc/cp/contracts.cc
@@ -2087,4 +2087,105 @@ apply_postcondition_to_return (tree expr)
   return call;
 }
 
+/* A subroutine of duplicate_decls. Diagnose issues in the redeclaration of
+   guarded functions.  Note that attributes on new friend declarations have not
+   been processed yet, so we take those from the global above.  */
+
+void
+duplicate_contracts (tree newdecl, tree olddecl)
+{
+  /* Compare contracts to see if they match.    */
+  tree old_contracts = DECL_CONTRACTS (olddecl);
+  tree new_contracts = DECL_CONTRACTS (newdecl);
+
+  if (!old_contracts && !new_contracts)
+    return;
+
+  location_t old_loc = DECL_SOURCE_LOCATION (olddecl);
+  location_t new_loc = DECL_SOURCE_LOCATION (newdecl);
+
+  /* If both declarations specify contracts, ensure they match.
+
+     TODO: This handles a potential error a little oddly. Consider:
+
+	struct B {
+	  virtual void f(int n) [[pre: n == 0]];
+	};
+	struct D : B {
+	  void f(int n) override; // inherits contracts
+	};
+	void D::f(int n) [[pre: n == 0]] // OK
+	{ }
+
+    It's okay because we're explicitly restating the inherited contract.
+    Changing the precondition on the definition D::f causes match_contracts
+    to complain about the mismatch.
+
+    This would previously have been diagnosed as adding contracts to an
+    override, but this seems like it should be well-formed.  */
+  if (old_contracts && new_contracts)
+    {
+      if (!match_contract_conditions (old_loc, old_contracts,
+				      new_loc, new_contracts,
+				      cmc_declaration))
+	return;
+    }
+
+  /* Handle cases where contracts are omitted in one or the other
+     declaration.  */
+  if (old_contracts)
+    {
+      /* Contracts have been previously specified by are no omitted. The
+	 new declaration inherits the existing contracts. */
+      if (!new_contracts)
+	copy_contract_attributes (newdecl, olddecl);
+
+      /* In all cases, remove existing contracts from OLDDECL to prevent the
+	 attribute merging function from adding excess contracts.  */
+      remove_contract_attributes (olddecl);
+    }
+  else if (!old_contracts)
+    {
+      /* We are adding contracts to a declaration.  */
+      if (new_contracts)
+	{
+	  /* We can't add to a previously defined function.  */
+	  if (DECL_INITIAL (olddecl))
+	    {
+	      auto_diagnostic_group d;
+	      error_at (new_loc, "cannot add contracts after definition");
+	      inform (DECL_SOURCE_LOCATION (olddecl), "original definition here");
+	      return;
+	    }
+
+	  /* We can't add to an unguarded virtual function declaration.  */
+	  if (DECL_VIRTUAL_P (olddecl) && new_contracts)
+	    {
+	      auto_diagnostic_group d;
+	      error_at (new_loc, "cannot add contracts to a virtual function");
+	      inform (DECL_SOURCE_LOCATION (olddecl), "original declaration here");
+	      return;
+	    }
+
+	  /* Depending on the "first declaration" rule, we may not be able
+	     to add contracts to a function after the fact.  */
+	  if (flag_contract_strict_declarations)
+	    {
+	      warning_at (new_loc,
+			  OPT_fcontract_strict_declarations_,
+			  "declaration adds contracts to %q#D",
+			  olddecl);
+	      return;
+	    }
+
+	  /* Copy the contracts from NEWDECL to OLDDECL. We shouldn't need to
+	     remap them because NEWDECL's parameters will replace those of
+	     OLDDECL.  Remove the contracts from NEWDECL so they aren't
+	     cloned when merging.  */
+	  copy_contract_attributes (olddecl, newdecl);
+	  remove_contract_attributes (newdecl);
+	}
+    }
+}
+
 #include "gt-cp-contracts.h"
diff --git a/gcc/cp/decl.cc b/gcc/cp/decl.cc
index 9740129456b..d6eb50a260b 100644
--- a/gcc/cp/decl.cc
+++ b/gcc/cp/decl.cc
@@ -1475,107 +1475,6 @@ duplicate_function_template_decls (tree newdecl, tree olddecl)
   return false;
 }
 
-/* A subroutine of duplicate_decls. Diagnose issues in the redeclaration of
-   guarded functions.  Note that attributes on new friend declarations have not
-   been processed yet, so we take those from the global above.  */
-
-static void
-duplicate_contracts (tree newdecl, tree olddecl)
-{
-  /* Compare contracts to see if they match.    */
-  tree old_contracts = DECL_CONTRACTS (olddecl);
-  tree new_contracts = DECL_CONTRACTS (newdecl);
-
-  if (!old_contracts && !new_contracts)
-    return;
-
-  location_t old_loc = DECL_SOURCE_LOCATION (olddecl);
-  location_t new_loc = DECL_SOURCE_LOCATION (newdecl);
-
-  /* If both declarations specify contracts, ensure they match.
-
-     TODO: This handles a potential error a little oddly. Consider:
-
-	struct B {
-	  virtual void f(int n) [[pre: n == 0]];
-	};
-	struct D : B {
-	  void f(int n) override; // inherits contracts
-	};
-	void D::f(int n) [[pre: n == 0]] // OK
-	{ }
-
-    It's okay because we're explicitly restating the inherited contract.
-    Changing the precondition on the definition D::f causes match_contracts
-    to complain about the mismatch.
-
-    This would previously have been diagnosed as adding contracts to an
-    override, but this seems like it should be well-formed.  */
-  if (old_contracts && new_contracts)
-    {
-      if (!match_contract_conditions (old_loc, old_contracts,
-				      new_loc, new_contracts,
-				      cmc_declaration))
-	return;
-    }
-
-  /* Handle cases where contracts are omitted in one or the other
-     declaration.  */
-  if (old_contracts)
-    {
-      /* Contracts have been previously specified by are no omitted. The
-	 new declaration inherits the existing contracts. */
-      if (!new_contracts)
-	copy_contract_attributes (newdecl, olddecl);
-
-      /* In all cases, remove existing contracts from OLDDECL to prevent the
-	 attribute merging function from adding excess contracts.  */
-      remove_contract_attributes (olddecl);
-    }
-  else if (!old_contracts)
-    {
-      /* We are adding contracts to a declaration.  */
-      if (new_contracts)
-	{
-	  /* We can't add to a previously defined function.  */
-	  if (DECL_INITIAL (olddecl))
-	    {
-	      auto_diagnostic_group d;
-	      error_at (new_loc, "cannot add contracts after definition");
-	      inform (DECL_SOURCE_LOCATION (olddecl), "original definition here");
-	      return;
-	    }
-
-	  /* We can't add to an unguarded virtual function declaration.  */
-	  if (DECL_VIRTUAL_P (olddecl) && new_contracts)
-	    {
-	      auto_diagnostic_group d;
-	      error_at (new_loc, "cannot add contracts to a virtual function");
-	      inform (DECL_SOURCE_LOCATION (olddecl), "original declaration here");
-	      return;
-	    }
-
-	  /* Depending on the "first declaration" rule, we may not be able
-	     to add contracts to a function after the fact.  */
-	  if (flag_contract_strict_declarations)
-	    {
-	      warning_at (new_loc,
-			  OPT_fcontract_strict_declarations_,
-			  "declaration adds contracts to %q#D",
-			  olddecl);
-	      return;
-	    }
-
-	  /* Copy the contracts from NEWDECL to OLDDECL. We shouldn't need to
-	     remap them because NEWDECL's parameters will replace those of
-	     OLDDECL.  Remove the contracts from NEWDECL so they aren't
-	     cloned when merging.  */
-	  copy_contract_attributes (olddecl, newdecl);
-	  remove_contract_attributes (newdecl);
-	}
-    }
-}
-
 /* OLD_PARMS is the innermost set of template parameters for some template
    declaration, and NEW_PARMS is the corresponding set of template parameters
    for a redeclaration of that template.  Merge the default arguments within
diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc
index 7399c2f8a36..a911a660178 100644
--- a/gcc/cp/parser.cc
+++ b/gcc/cp/parser.cc
@@ -29688,7 +29688,7 @@ cp_parser_contract_attribute_spec (cp_parser *parser, tree attribute)
       DEFPARSE_TOKENS (condition) = cp_token_cache_new (first, last);
       DEFPARSE_INSTANTIATIONS (condition) = NULL;
 
-      /* And it's corresponding contract.  */
+      /* And its corresponding contract.  */
       contract = grok_contract (attribute, mode, identifier, condition, loc);
     }
   else

^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2022-11-01 11:43 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-11-01 11:43 [gcc/devel/c++-contracts] c++: move duplicate_contracts to contracts.cc Jason Merrill

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).