]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
gccrs: derive(Ord): Handle unit structs properly
authorArthur Cohen <arthur.cohen@embecosm.com>
Tue, 27 May 2025 12:23:39 +0000 (14:23 +0200)
committerArthur Cohen <arthur.cohen@embecosm.com>
Tue, 5 Aug 2025 14:36:48 +0000 (16:36 +0200)
gcc/rust/ChangeLog:

* expand/rust-derive-ord.cc (DeriveOrd::make_cmp_arms): Use new make_equal function.
(DeriveOrd::make_equal): New function.
(DeriveOrd::recursive_match): Handle the unit struct/tuple case.
* expand/rust-derive-ord.h: Declare make_equal.

gcc/rust/expand/rust-derive-ord.cc
gcc/rust/expand/rust-derive-ord.h

index 1623495b8b60948d3a751155c3bef3f4554a2fdb..dfc014446fa20bc371bf1e10d9d6db8bbb1a4a71 100644 (file)
@@ -109,12 +109,9 @@ DeriveOrd::cmp_fn (std::unique_ptr<BlockExpr> &&block, Identifier type_name)
                           ptrify (return_type), std::move (block));
 }
 
-std::pair<MatchArm, MatchArm>
-DeriveOrd::make_cmp_arms ()
+std::unique_ptr<Pattern>
+DeriveOrd::make_equal ()
 {
-  // All comparison results other than Ordering::Equal
-  auto non_equal = builder.identifier_pattern (DeriveOrd::not_equal);
-
   std::unique_ptr<Pattern> equal = ptrify (
     builder.path_in_expression ({"core", "cmp", "Ordering", "Equal"}, true));
 
@@ -131,6 +128,16 @@ DeriveOrd::make_cmp_arms ()
                                                std::move (pattern_items));
     }
 
+  return equal;
+}
+
+std::pair<MatchArm, MatchArm>
+DeriveOrd::make_cmp_arms ()
+{
+  // All comparison results other than Ordering::Equal
+  auto non_equal = builder.identifier_pattern (DeriveOrd::not_equal);
+  auto equal = make_equal ();
+
   return {builder.match_arm (std::move (equal)),
          builder.match_arm (std::move (non_equal))};
 }
@@ -138,6 +145,20 @@ DeriveOrd::make_cmp_arms ()
 std::unique_ptr<Expr>
 DeriveOrd::recursive_match (std::vector<SelfOther> &&members)
 {
+  if (members.empty ())
+    {
+      std::unique_ptr<Expr> value = ptrify (
+       builder.path_in_expression ({"core", "cmp", "Ordering", "Equal"},
+                                   true));
+
+      if (ordering == Ordering::Partial)
+       value = builder.call (ptrify (builder.path_in_expression (
+                               LangItem::Kind::OPTION_SOME)),
+                             std::move (value));
+
+      return value;
+    }
+
   std::unique_ptr<Expr> final_expr = nullptr;
 
   for (auto it = members.rbegin (); it != members.rend (); it++)
index 20086afe9b7f1d790bec4f06e73e34244fded03d..90ce9c8ca6f18c6b18ef02ba2a11363ce05d208e 100644 (file)
@@ -79,6 +79,12 @@ private:
    */
   std::unique_ptr<Expr> recursive_match (std::vector<SelfOther> &&members);
 
+  /**
+   * Create a pattern for the `Ordering::Equal` case. In the case of partial
+   * ordering, `Option::Some(Ordering::Equal)`.
+   */
+  std::unique_ptr<Pattern> make_equal ();
+
   /**
    * Make the match arms for one inner match in a comparison function block.
    * This returns the "equal" match arm and the "rest" match arm, so something