Ver código fonte

Support implicit conversion from specific node IDs to node ID categories (#3799)

Co-authored-by: Josh L <josh11b@users.noreply.github.com>
josh11b 2 anos atrás
pai
commit
f97a543395
2 arquivos alterados com 10 adições e 10 exclusões
  1. 4 9
      toolchain/check/handle_operator.cpp
  2. 6 1
      toolchain/parse/node_ids.h

+ 4 - 9
toolchain/check/handle_operator.cpp

@@ -11,11 +11,8 @@
 namespace Carbon::Check {
 
 // Common logic for unary operator handlers.
-static auto HandleUnaryOperator(Context& context, Parse::NodeId node_id,
+static auto HandleUnaryOperator(Context& context, Parse::AnyExprId expr_node_id,
                                 Operator op) -> bool {
-  // TODO: Support implicit conversion from specific node IDs to node ID
-  // categories and change this function to take an `AnyExprId` directly.
-  auto expr_node_id = static_cast<Parse::AnyExprId>(node_id);
   auto operand_id = context.node_stack().PopExpr();
   auto result_id = BuildUnaryOperator(context, expr_node_id, op, operand_id);
   context.node_stack().Push(expr_node_id, result_id);
@@ -23,11 +20,9 @@ static auto HandleUnaryOperator(Context& context, Parse::NodeId node_id,
 }
 
 // Common logic for binary operator handlers.
-static auto HandleBinaryOperator(Context& context, Parse::NodeId node_id,
-                                 Operator op) -> bool {
-  // TODO: Support implicit conversion from specific node IDs to node ID
-  // categories and change this function to take an `AnyExprId` directly.
-  auto expr_node_id = static_cast<Parse::AnyExprId>(node_id);
+static auto HandleBinaryOperator(Context& context,
+                                 Parse::AnyExprId expr_node_id, Operator op)
+    -> bool {
   auto rhs_id = context.node_stack().PopExpr();
   auto lhs_id = context.node_stack().PopExpr();
   auto result_id =

+ 6 - 1
toolchain/parse/node_ids.h

@@ -52,8 +52,13 @@ const NodeKind& NodeIdForKind<K>::Kind = K;
 // NodeId that matches any NodeKind whose `category()` overlaps with `Category`.
 template <NodeCategory Category>
 struct NodeIdInCategory : public NodeId {
-  // TODO: Support conversion from `NodeIdForKind<Kind>` if `Kind::category()`
+  // Support conversion from `NodeIdForKind<Kind>` if Kind's category
   // overlaps with `Category`.
+  template <const NodeKind& Kind>
+  // NOLINTNEXTLINE(google-explicit-constructor)
+  NodeIdInCategory(NodeIdForKind<Kind> node_id) : NodeId(node_id) {
+    CARBON_CHECK(!!(Kind.category() & Category));
+  }
 
   constexpr explicit NodeIdInCategory(NodeId node_id) : NodeId(node_id) {}
   // NOLINTNEXTLINE(google-explicit-constructor)