On Mon, Jan 13, 2025 at 9:46 PM Frode Nordahl <[email protected]> wrote:
>
> Along with dependent data structures these functions are useful
> for programs that build against OVS private library sources,
> allowing them to make use of functionality provided by the
> route-table module.
>
> A test program to be run as part of the system tests that
> exercise the exported interfaces will be added in a subsequent
> patch.
>
> Signed-off-by: Frode Nordahl <[email protected]>
> ---
Test failure due to what appears to be GitHub infrastructure issues
(Internal server error on Git checkout).
Recheck-request: github-robot
> lib/route-table.c | 60 ++-------------------
> lib/route-table.h | 134 ++++++++++++++++++++++++++++++++++++++++++++++
> 2 files changed, 137 insertions(+), 57 deletions(-)
>
> diff --git a/lib/route-table.c b/lib/route-table.c
> index 7086fd2bd..56f7dd167 100644
> --- a/lib/route-table.c
> +++ b/lib/route-table.c
> @@ -48,56 +48,6 @@ VLOG_DEFINE_THIS_MODULE(route_table);
>
> COVERAGE_DEFINE(route_table_dump);
>
> -struct route_data_nexthop {
> - struct ovs_list nexthop_node;
> -
> - sa_family_t family;
> - struct in6_addr addr;
> - char ifname[IFNAMSIZ]; /* Interface name. */
> -};
> -
> -struct route_data {
> - /* Routes can have multiple next hops per destination.
> - *
> - * Each next hop has its own set of attributes such as address family,
> - * interface and IP address.
> - *
> - * When retrieving information about a route from the kernel, in the case
> - * of multiple next hops, information is provided as nested attributes.
> - *
> - * A linked list with struct route_data_nexthop entries is used to store
> - * this information as we parse each attribute.
> - *
> - * For the common case of one next hop, the nexthops list will contain a
> - * single entry pointing to the struct route_data _primary_next_hop
> - * element.
> - *
> - * Any dynamically allocated list elements MUST be freed with a call to
> the
> - * route_data_destroy function. */
> - struct ovs_list nexthops;
> - struct route_data_nexthop _primary_next_hop;
> -
> - /* Copied from struct rtmsg. */
> - unsigned char rtm_dst_len;
> - unsigned char rtm_protocol;
> - bool rtn_local;
> -
> - /* Extracted from Netlink attributes. */
> - struct in6_addr rta_dst; /* 0 if missing. */
> - struct in6_addr rta_prefsrc; /* 0 if missing. */
> - uint32_t rta_mark; /* 0 if missing. */
> - uint32_t rta_table_id; /* 0 if missing. */
> - uint32_t rta_priority; /* 0 if missing. */
> -};
> -
> -/* A digested version of a route message sent down by the kernel to indicate
> - * that a route has changed. */
> -struct route_table_msg {
> - bool relevant; /* Should this message be processed? */
> - uint16_t nlmsg_type; /* e.g. RTM_NEWROUTE, RTM_DELROUTE. */
> - struct route_data rd; /* Data parsed from this message. */
> -};
> -
> static struct ovs_mutex route_table_mutex = OVS_MUTEX_INITIALIZER;
> static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(5, 20);
>
> @@ -115,14 +65,13 @@ static bool route_table_valid = false;
>
> static void route_table_reset(void);
> static void route_table_handle_msg(const struct route_table_msg *, void
> *aux);
> -static int route_table_parse(struct ofpbuf *, void *change);
> static void route_table_change(struct route_table_msg *, void *aux);
> static void route_map_clear(void);
>
> static void name_table_init(void);
> static void name_table_change(const struct rtnetlink_change *, void *);
>
> -static void
> +void
> route_data_destroy(struct route_data *rd)
> {
> struct route_data_nexthop *rdnh;
> @@ -197,10 +146,7 @@ route_table_wait(void)
> ovs_mutex_unlock(&route_table_mutex);
> }
>
> -typedef void route_table_handle_msg_callback(const struct route_table_msg *,
> - void *aux);
> -
> -static bool
> +bool
> route_table_dump_one_table(uint32_t id,
> route_table_handle_msg_callback *handle_msg_cb,
> void *aux)
> @@ -466,7 +412,7 @@ error_out:
> * responsibility to free it with a call to route_data_destroy().
> *
> * In case of error, any allocated memory will be freed before returning. */
> -static int
> +int
> route_table_parse(struct ofpbuf *buf, void *change)
> {
> struct nlmsghdr *nlmsg;
> diff --git a/lib/route-table.h b/lib/route-table.h
> index 3a02d737a..ae28b6af1 100644
> --- a/lib/route-table.h
> +++ b/lib/route-table.h
> @@ -24,8 +24,133 @@
> #include <stdbool.h>
> #include <stdint.h>
>
> +#include "openvswitch/list.h"
> +#include "openvswitch/ofpbuf.h"
> #include "openvswitch/types.h"
>
> +/*
> + * route-table, system route table synchronization for Open vSwitch.
> + *
> + * Overview
> + * ========
> + *
> + * The route-table module has two use cases:
> + *
> + * 1) Internal use by Open vSwitch which together with the ovs-router module
> + * implement route lookup for features such as flow based tunneling,
> + * userspace tunneling, and sFlow.
> + *
> + * 2) External use by projects such as Open Virtual Network (OVN), that use
> + * Open vSwitch as a compile time library.
> + *
> + * Typical External Usage
> + * ======================
> + *
> + * static void
> + * my_handle_msg(const struct route_table_msg *change, void *data)
> + * {
> + * struct my_data *aux = data;
> + *
> + * if (data) {
> + * aux->rta_dst = change->rd.rta_dst;
> + * }
> + * }
> + *
> + * static void
> + * my_route_table_dump(void)
> + * {
> + * struct my_data *aux;
> + *
> + * route_table_dump_one_table(RT_TABLE_MAIN, my_handle_msg, aux);
> + * }
> + *
> + * static void
> + * my_route_table_change(struct route_table_msg *change, void *aux
> OVS_UNUSED);
> + * {
> + * my_handle_msg(change, NULL);
> + * route_data_destroy(&change->rd);
> + * }
> + *
> + * static void
> + * my_init(void)
> + * {
> + * static struct nln_notifier *route6_notifier = NULL;
> + * static struct nln_notifier *route_notifier = NULL;
> + * static struct route_table_msg nln_change;
> + * static struct nln *nln = NULL;
> + *
> + * nln = nln_create(NETLINK_ROUTE, route_table_parse, NULL);
> + *
> + * route6_notifier =
> + * nln_notifier_create(nln, RTNLGRP_IPV6_ROUTE,
> + * (nln_notify_func *)
> test_lib_route_table_change,
> + * NULL);
> + *
> + * route_notifier =
> + * nln_notifier_create(nln, RTNLGRP_IPV4_ROUTE,
> + * (nln_notify_func *)
> test_lib_route_table_change,
> + * NULL);
> + * }
> + *
> + * Thread-safety
> + * =============
> + *
> + * Assuming thread safe initialization of dependencies such as netlink
> socket,
> + * netlink notifier and so on, the functions in this module are thread safe.
> + */
> +
> +/* Information about a next hop stored in a linked list with base in struct
> + * route_data. Please refer to comment in struct route_data for details. */
> +struct route_data_nexthop {
> + struct ovs_list nexthop_node;
> +
> + sa_family_t family;
> + struct in6_addr addr;
> + char ifname[IFNAMSIZ]; /* Interface name. */
> +};
> +
> +struct route_data {
> + /* Routes can have multiple next hops per destination.
> + *
> + * Each next hop has its own set of attributes such as address family,
> + * interface and IP address.
> + *
> + * When retrieving information about a route from the kernel, in the case
> + * of multiple next hops, information is provided as nested attributes.
> + *
> + * A linked list with struct route_data_nexthop entries is used to store
> + * this information as we parse each attribute.
> + *
> + * For the common case of one next hop, the nexthops list will contain a
> + * single entry pointing to the struct route_data _primary_next_hop
> + * element.
> + *
> + * Any dynamically allocated list elements MUST be freed with a call to
> the
> + * route_data_destroy function. */
> + struct ovs_list nexthops;
> + struct route_data_nexthop _primary_next_hop;
> +
> + /* Copied from struct rtmsg. */
> + unsigned char rtm_dst_len;
> + unsigned char rtm_protocol;
> + bool rtn_local;
> +
> + /* Extracted from Netlink attributes. */
> + struct in6_addr rta_dst; /* 0 if missing. */
> + struct in6_addr rta_prefsrc; /* 0 if missing. */
> + uint32_t rta_mark; /* 0 if missing. */
> + uint32_t rta_table_id; /* 0 if missing. */
> + uint32_t rta_priority; /* 0 if missing. */
> +};
> +
> +/* A digested version of a route message sent down by the kernel to indicate
> + * that a route has changed. */
> +struct route_table_msg {
> + bool relevant; /* Should this message be processed? */
> + uint16_t nlmsg_type; /* e.g. RTM_NEWROUTE, RTM_DELROUTE. */
> + struct route_data rd; /* Data parsed from this message. */
> +};
> +
> uint64_t route_table_get_change_seq(void);
> void route_table_init(void);
> void route_table_run(void);
> @@ -33,4 +158,13 @@ void route_table_wait(void);
> bool route_table_fallback_lookup(const struct in6_addr *ip6_dst,
> char name[],
> struct in6_addr *gw6);
> +
> +typedef void route_table_handle_msg_callback(const struct route_table_msg *,
> + void *aux);
> +
> +bool route_table_dump_one_table(uint32_t id,
> + route_table_handle_msg_callback *,
> + void *aux);
> +int route_table_parse(struct ofpbuf *buf, void *change);
> +void route_data_destroy(struct route_data *rd);
> #endif /* route-table.h */
> --
> 2.47.1
>
_______________________________________________
dev mailing list
[email protected]
https://mail.openvswitch.org/mailman/listinfo/ovs-dev