bridge: Make bridge_pick_local_hw_addr() easier to reason.
[openvswitch] / lib / classifier.c
index e89a6c8fb4659fa8d71f409506da662503fa580b..d1f9d5ddc0336a549786804226bbbe5b97237719 100644 (file)
@@ -406,6 +406,16 @@ cls_rule_equal(const struct cls_rule *a, const struct cls_rule *b)
             && flow_equal(&a->flow, &b->flow));
 }
 
+/* Returns a hash value for the flow, wildcards, and priority in 'rule',
+ * starting from 'basis'. */
+uint32_t
+cls_rule_hash(const struct cls_rule *rule, uint32_t basis)
+{
+    uint32_t h0 = flow_hash(&rule->flow, basis);
+    uint32_t h1 = flow_wildcards_hash(&rule->wc, h0);
+    return hash_int(rule->priority, h1);
+}
+
 static void
 format_ip_netmask(struct ds *s, const char *name, ovs_be32 ip,
                   ovs_be32 netmask)
@@ -457,6 +467,8 @@ cls_rule_format(const struct cls_rule *rule, struct ds *s)
 
     int i;
 
+    BUILD_ASSERT_DECL(FLOW_WC_SEQ == 1);
+
     if (rule->priority != OFP_DEFAULT_PRIORITY) {
         ds_put_format(s, "priority=%d,", rule->priority);
     }
@@ -582,7 +594,7 @@ cls_rule_format(const struct cls_rule *rule, struct ds *s)
     }
     if (!skip_proto && !(w & FWW_NW_PROTO)) {
         if (f->dl_type == htons(ETH_TYPE_ARP)) {
-            ds_put_format(s, "opcode=%"PRIu8",", f->nw_proto);
+            ds_put_format(s, "arp_op=%"PRIu8",", f->nw_proto);
         } else {
             ds_put_format(s, "nw_proto=%"PRIu8",", f->nw_proto);
         }
@@ -620,11 +632,11 @@ cls_rule_format(const struct cls_rule *rule, struct ds *s)
             ds_put_char(s, ',');
         }
         if (!(w & FWW_ARP_SHA)) {
-            ds_put_format(s, "nd_sll="ETH_ADDR_FMT",", 
+            ds_put_format(s, "nd_sll="ETH_ADDR_FMT",",
                     ETH_ADDR_ARGS(f->arp_sha));
         }
         if (!(w & FWW_ARP_THA)) {
-            ds_put_format(s, "nd_tll="ETH_ADDR_FMT",", 
+            ds_put_format(s, "nd_tll="ETH_ADDR_FMT",",
                     ETH_ADDR_ARGS(f->arp_tha));
         }
    } else {
@@ -969,7 +981,7 @@ find_table(const struct classifier *cls, const struct flow_wildcards *wc)
 {
     struct cls_table *table;
 
-    HMAP_FOR_EACH_IN_BUCKET (table, hmap_node, flow_wildcards_hash(wc),
+    HMAP_FOR_EACH_IN_BUCKET (table, hmap_node, flow_wildcards_hash(wc, 0),
                              &cls->tables) {
         if (flow_wildcards_equal(wc, &table->wc)) {
             return table;
@@ -986,7 +998,7 @@ insert_table(struct classifier *cls, const struct flow_wildcards *wc)
     table = xzalloc(sizeof *table);
     hmap_init(&table->rules);
     table->wc = *wc;
-    hmap_insert(&cls->tables, &table->hmap_node, flow_wildcards_hash(wc));
+    hmap_insert(&cls->tables, &table->hmap_node, flow_wildcards_hash(wc, 0));
 
     return table;
 }
@@ -1128,7 +1140,7 @@ flow_equal_except(const struct flow *a, const struct flow *b,
     const flow_wildcards_t wc = wildcards->wildcards;
     int i;
 
-    BUILD_ASSERT_DECL(FLOW_SIG_SIZE == 100 + FLOW_N_REGS * 4);
+    BUILD_ASSERT_DECL(FLOW_WC_SEQ == 1);
 
     for (i = 0; i < FLOW_N_REGS; i++) {
         if ((a->regs[i] ^ b->regs[i]) & wildcards->reg_masks[i]) {
@@ -1162,7 +1174,7 @@ flow_equal_except(const struct flow *a, const struct flow *b,
                     &wildcards->ipv6_src_mask)
             && ipv6_equal_except(&a->ipv6_dst, &b->ipv6_dst,
                     &wildcards->ipv6_dst_mask)
-            && (wc & FWW_ND_TARGET 
+            && (wc & FWW_ND_TARGET
                 || ipv6_addr_equals(&a->nd_target, &b->nd_target)));
 }
 
@@ -1172,7 +1184,7 @@ zero_wildcards(struct flow *flow, const struct flow_wildcards *wildcards)
     const flow_wildcards_t wc = wildcards->wildcards;
     int i;
 
-    BUILD_ASSERT_DECL(FLOW_SIG_SIZE == 100 + 4 * FLOW_N_REGS);
+    BUILD_ASSERT_DECL(FLOW_WC_SEQ == 1);
 
     for (i = 0; i < FLOW_N_REGS; i++) {
         flow->regs[i] &= wildcards->reg_masks[i];