From: Numan Siddique <[email protected]> This patch moves the 'struct put_mac_binding' from controller/pinctrl.c to controller/mac-learn.c as a 'struct mac_binding' and adds the relevant functions to access it.
Signed-off-by: Numan Siddique <[email protected]> --- controller/automake.mk | 5 +- controller/mac-learn.c | 101 ++++++++++++++++++++++++++++++++++++++++ controller/mac-learn.h | 46 +++++++++++++++++++ controller/pinctrl.c | 102 ++++++++++++----------------------------- 4 files changed, 181 insertions(+), 73 deletions(-) create mode 100644 controller/mac-learn.c create mode 100644 controller/mac-learn.h diff --git a/controller/automake.mk b/controller/automake.mk index 480578eda3..9b8debd2ff 100644 --- a/controller/automake.mk +++ b/controller/automake.mk @@ -27,7 +27,10 @@ controller_ovn_controller_SOURCES = \ controller/ovn-controller.c \ controller/ovn-controller.h \ controller/physical.c \ - controller/physical.h + controller/physical.h \ + controller/mac-learn.c \ + controller/mac-learn.h + controller_ovn_controller_LDADD = lib/libovn.la $(OVS_LIBDIR)/libopenvswitch.la man_MANS += controller/ovn-controller.8 EXTRA_DIST += controller/ovn-controller.8.xml diff --git a/controller/mac-learn.c b/controller/mac-learn.c new file mode 100644 index 0000000000..36a6d6e589 --- /dev/null +++ b/controller/mac-learn.c @@ -0,0 +1,101 @@ +/* Copyright (c) 2020, Red Hat, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include <config.h> + +#include "mac-learn.h" + +/* OpenvSwitch lib includes. */ +#include "openvswitch/vlog.h" +#include "lib/smap.h" + +VLOG_DEFINE_THIS_MODULE(mac_learn); + +#define MAX_MAC_BINDINGS 1000 + +static size_t mac_binding_hash(uint32_t dp_key, uint32_t port_key, + struct in6_addr *); +static struct mac_binding *mac_binding_find(struct hmap *mac_bindings, + uint32_t dp_key, + uint32_t port_key, + struct in6_addr *ip, size_t hash); + +void +ovn_mac_bindings_init(struct hmap *mac_bindings) +{ + hmap_init(mac_bindings); +} + +void +ovn_mac_bindings_flush(struct hmap *mac_bindings) +{ + struct mac_binding *mb; + HMAP_FOR_EACH_POP (mb, hmap_node, mac_bindings) { + free(mb); + } +} + +void +ovn_mac_bindings_destroy(struct hmap *mac_bindings) +{ + ovn_mac_bindings_flush(mac_bindings); + hmap_destroy(mac_bindings); +} + +struct mac_binding * +ovn_mac_binding_add(struct hmap *mac_bindings, uint32_t dp_key, + uint32_t port_key, struct in6_addr *ip, + struct eth_addr mac) +{ + uint32_t hash = mac_binding_hash(dp_key, port_key, ip); + + struct mac_binding *mb = + mac_binding_find(mac_bindings, dp_key, port_key, ip, hash); + if (!mb) { + if (hmap_count(mac_bindings) >= MAX_MAC_BINDINGS) { + return NULL; + } + + mb = xmalloc(sizeof *mb); + mb->dp_key = dp_key; + mb->port_key = port_key; + mb->ip = *ip; + hmap_insert(mac_bindings, &mb->hmap_node, hash); + } + mb->mac = mac; + + return mb; +} + +static size_t +mac_binding_hash(uint32_t dp_key, uint32_t port_key, struct in6_addr *ip) +{ + return hash_bytes(ip, sizeof *ip, hash_2words(dp_key, port_key)); +} + +static struct mac_binding * +mac_binding_find(struct hmap *mac_bindings, uint32_t dp_key, + uint32_t port_key, struct in6_addr *ip, size_t hash) +{ + struct mac_binding *mb; + HMAP_FOR_EACH_WITH_HASH (mb, hmap_node, hash, mac_bindings) { + if (mb->dp_key == dp_key && mb->port_key == port_key && + IN6_ARE_ADDR_EQUAL(&mb->ip, ip)) { + return mb; + } + } + + return NULL; +} diff --git a/controller/mac-learn.h b/controller/mac-learn.h new file mode 100644 index 0000000000..3a8520c360 --- /dev/null +++ b/controller/mac-learn.h @@ -0,0 +1,46 @@ +/* + * Copyright (c) 2020 Red Hat, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef OVN_MAC_LEARN_H +#define OVN_MAC_LEARN_H 1 + +#include <sys/types.h> +#include <netinet/in.h> +#include "openvswitch/hmap.h" + +struct mac_binding { + struct hmap_node hmap_node; /* In a hmap. */ + + /* Key. */ + uint32_t dp_key; + uint32_t port_key; /* Port from where this mac_binding is learnt. */ + struct in6_addr ip; + + /* Value. */ + struct eth_addr mac; +}; + +void ovn_mac_bindings_init(struct hmap *mac_bindings); +void ovn_mac_bindings_flush(struct hmap *mac_bindings); +void ovn_mac_bindings_destroy(struct hmap *mac_bindings); + +struct mac_binding *ovn_mac_binding_add(struct hmap *mac_bindings, + uint32_t dp_key, uint32_t port_key, + struct in6_addr *ip, + struct eth_addr mac); + + +#endif /* OVN_MAC_LEARN_H */ \ No newline at end of file diff --git a/controller/pinctrl.c b/controller/pinctrl.c index dcf6b4af5c..723d2a6522 100644 --- a/controller/pinctrl.c +++ b/controller/pinctrl.c @@ -26,6 +26,7 @@ #include "flow.h" #include "ha-chassis.h" #include "lport.h" +#include "mac-learn.h" #include "nx-match.h" #include "latch.h" #include "lib/packets.h" @@ -193,7 +194,6 @@ static void run_put_mac_bindings( struct ovsdb_idl_index *sbrec_mac_binding_by_lport_ip) OVS_REQUIRES(pinctrl_mutex); static void wait_put_mac_bindings(struct ovsdb_idl_txn *ovnsb_idl_txn); -static void flush_put_mac_bindings(void); static void send_mac_binding_buffered_pkts(struct rconn *swconn) OVS_REQUIRES(pinctrl_mutex); @@ -3893,47 +3893,20 @@ pinctrl_destroy(void) * available. */ /* Buffered "put_mac_binding" operation. */ -struct put_mac_binding { - struct hmap_node hmap_node; /* In 'put_mac_bindings'. */ - /* Key. */ - uint32_t dp_key; - uint32_t port_key; - struct in6_addr ip_key; - - /* Value. */ - struct eth_addr mac; -}; - -/* Contains "struct put_mac_binding"s. */ +/* Contains "struct mac_binding"s. */ static struct hmap put_mac_bindings; static void init_put_mac_bindings(void) { - hmap_init(&put_mac_bindings); + ovn_mac_bindings_init(&put_mac_bindings); } static void destroy_put_mac_bindings(void) { - flush_put_mac_bindings(); - hmap_destroy(&put_mac_bindings); -} - -static struct put_mac_binding * -pinctrl_find_put_mac_binding(uint32_t dp_key, uint32_t port_key, - const struct in6_addr *ip_key, uint32_t hash) -{ - struct put_mac_binding *pa; - HMAP_FOR_EACH_WITH_HASH (pa, hmap_node, hash, &put_mac_bindings) { - if (pa->dp_key == dp_key - && pa->port_key == port_key - && IN6_ARE_ADDR_EQUAL(&pa->ip_key, ip_key)) { - return pa; - } - } - return NULL; + ovn_mac_bindings_destroy(&put_mac_bindings); } /* Called with in the pinctrl_handler thread context. */ @@ -3953,23 +3926,16 @@ pinctrl_handle_put_mac_binding(const struct flow *md, ovs_be128 ip6 = hton128(flow_get_xxreg(md, 0)); memcpy(&ip_key, &ip6, sizeof ip_key); } - uint32_t hash = hash_bytes(&ip_key, sizeof ip_key, - hash_2words(dp_key, port_key)); - struct put_mac_binding *pmb - = pinctrl_find_put_mac_binding(dp_key, port_key, &ip_key, hash); - if (!pmb) { + + struct mac_binding *mb = ovn_mac_binding_add(&put_mac_bindings, dp_key, + port_key, &ip_key, + headers->dl_src); + if (!mb) { if (hmap_count(&put_mac_bindings) >= 1000) { COVERAGE_INC(pinctrl_drop_put_mac_binding); return; } - - pmb = xmalloc(sizeof *pmb); - hmap_insert(&put_mac_bindings, &pmb->hmap_node, hash); - pmb->dp_key = dp_key; - pmb->port_key = port_key; - pmb->ip_key = ip_key; } - pmb->mac = headers->dl_src; /* We can send the buffered packet once the main ovn-controller * thread calls pinctrl_run() and it writes the mac_bindings stored @@ -4012,12 +3978,12 @@ mac_binding_lookup(struct ovsdb_idl_index *sbrec_mac_binding_by_lport_ip, /* Update or add an IP-MAC binding for 'logical_port'. * Caller should make sure that 'ovnsb_idl_txn' is valid. */ static void -mac_binding_add(struct ovsdb_idl_txn *ovnsb_idl_txn, - struct ovsdb_idl_index *sbrec_mac_binding_by_lport_ip, - const char *logical_port, - const struct sbrec_datapath_binding *dp, - struct eth_addr ea, const char *ip, - bool update_only) +mac_binding_add_to_sb(struct ovsdb_idl_txn *ovnsb_idl_txn, + struct ovsdb_idl_index *sbrec_mac_binding_by_lport_ip, + const char *logical_port, + const struct sbrec_datapath_binding *dp, + struct eth_addr ea, const char *ip, + bool update_only) { /* Convert ethernet argument to string form for database. */ char mac_string[ETH_ADDR_STRLEN + 1]; @@ -4073,9 +4039,9 @@ send_garp_locally(struct ovsdb_idl_txn *ovnsb_idl_txn, struct ds ip_s = DS_EMPTY_INITIALIZER; ip_format_masked(ip, OVS_BE32_MAX, &ip_s); - mac_binding_add(ovnsb_idl_txn, sbrec_mac_binding_by_lport_ip, - remote->logical_port, remote->datapath, - ea, ds_cstr(&ip_s), update_only); + mac_binding_add_to_sb(ovnsb_idl_txn, sbrec_mac_binding_by_lport_ip, + remote->logical_port, remote->datapath, + ea, ds_cstr(&ip_s), update_only); ds_destroy(&ip_s); } } @@ -4085,30 +4051,30 @@ run_put_mac_binding(struct ovsdb_idl_txn *ovnsb_idl_txn, struct ovsdb_idl_index *sbrec_datapath_binding_by_key, struct ovsdb_idl_index *sbrec_port_binding_by_key, struct ovsdb_idl_index *sbrec_mac_binding_by_lport_ip, - const struct put_mac_binding *pmb) + const struct mac_binding *mb) { /* Convert logical datapath and logical port key into lport. */ const struct sbrec_port_binding *pb = lport_lookup_by_key( sbrec_datapath_binding_by_key, sbrec_port_binding_by_key, - pmb->dp_key, pmb->port_key); + mb->dp_key, mb->port_key); if (!pb) { static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 5); VLOG_WARN_RL(&rl, "unknown logical port with datapath %"PRIu32" " - "and port %"PRIu32, pmb->dp_key, pmb->port_key); + "and port %"PRIu32, mb->dp_key, mb->port_key); return; } /* Convert ethernet argument to string form for database. */ char mac_string[ETH_ADDR_STRLEN + 1]; snprintf(mac_string, sizeof mac_string, - ETH_ADDR_FMT, ETH_ADDR_ARGS(pmb->mac)); + ETH_ADDR_FMT, ETH_ADDR_ARGS(mb->mac)); struct ds ip_s = DS_EMPTY_INITIALIZER; - ipv6_format_mapped(&pmb->ip_key, &ip_s); - mac_binding_add(ovnsb_idl_txn, sbrec_mac_binding_by_lport_ip, - pb->logical_port, pb->datapath, pmb->mac, ds_cstr(&ip_s), - false); + ipv6_format_mapped(&mb->ip, &ip_s); + mac_binding_add_to_sb(ovnsb_idl_txn, sbrec_mac_binding_by_lport_ip, + pb->logical_port, pb->datapath, mb->mac, + ds_cstr(&ip_s), false); ds_destroy(&ip_s); } @@ -4125,14 +4091,14 @@ run_put_mac_bindings(struct ovsdb_idl_txn *ovnsb_idl_txn, return; } - const struct put_mac_binding *pmb; - HMAP_FOR_EACH (pmb, hmap_node, &put_mac_bindings) { + const struct mac_binding *mb; + HMAP_FOR_EACH (mb, hmap_node, &put_mac_bindings) { run_put_mac_binding(ovnsb_idl_txn, sbrec_datapath_binding_by_key, sbrec_port_binding_by_key, sbrec_mac_binding_by_lport_ip, - pmb); + mb); } - flush_put_mac_bindings(); + ovn_mac_bindings_flush(&put_mac_bindings); } static void @@ -4188,14 +4154,6 @@ wait_put_mac_bindings(struct ovsdb_idl_txn *ovnsb_idl_txn) } } -static void -flush_put_mac_bindings(void) -{ - struct put_mac_binding *pmb; - HMAP_FOR_EACH_POP (pmb, hmap_node, &put_mac_bindings) { - free(pmb); - } -} /* * Send gratuitous/reverse ARP for vif on localnet. -- 2.29.2 _______________________________________________ dev mailing list [email protected] https://mail.openvswitch.org/mailman/listinfo/ovs-dev
