From patchwork Thu Nov 12 16:10:12 2020 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Lorenzo Bianconi X-Patchwork-Id: 1399083 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=openvswitch.org (client-ip=140.211.166.136; helo=silver.osuosl.org; envelope-from=ovs-dev-bounces@openvswitch.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=redhat.com Authentication-Results: ozlabs.org; dkim=fail reason="signature verification failed" (1024-bit key; unprotected) header.d=redhat.com header.i=@redhat.com header.a=rsa-sha256 header.s=mimecast20190719 header.b=EmLuyxJT; dkim-atps=neutral Received: from silver.osuosl.org (smtp3.osuosl.org [140.211.166.136]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 4CX65x66l7z9sRR for ; Fri, 13 Nov 2020 03:11:01 +1100 (AEDT) Received: from localhost (localhost [127.0.0.1]) by silver.osuosl.org (Postfix) with ESMTP id 5CAA22E217; Thu, 12 Nov 2020 16:11:00 +0000 (UTC) X-Virus-Scanned: amavisd-new at osuosl.org Received: from silver.osuosl.org ([127.0.0.1]) by localhost (.osuosl.org [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id JYfm4wGN7sUj; Thu, 12 Nov 2020 16:10:45 +0000 (UTC) Received: from lists.linuxfoundation.org (lf-lists.osuosl.org [140.211.9.56]) by silver.osuosl.org (Postfix) with ESMTP id C11872E20A; Thu, 12 Nov 2020 16:10:45 +0000 (UTC) Received: from lf-lists.osuosl.org (localhost [127.0.0.1]) by lists.linuxfoundation.org (Postfix) with ESMTP id A27F5C1AD5; Thu, 12 Nov 2020 16:10:45 +0000 (UTC) X-Original-To: dev@openvswitch.org Delivered-To: ovs-dev@lists.linuxfoundation.org Received: from hemlock.osuosl.org (smtp2.osuosl.org [140.211.166.133]) by lists.linuxfoundation.org (Postfix) with ESMTP id F369FC016F for ; Thu, 12 Nov 2020 16:10:43 +0000 (UTC) Received: from localhost (localhost [127.0.0.1]) by hemlock.osuosl.org (Postfix) with ESMTP id EFB468780B for ; Thu, 12 Nov 2020 16:10:43 +0000 (UTC) X-Virus-Scanned: amavisd-new at osuosl.org Received: from hemlock.osuosl.org ([127.0.0.1]) by localhost (.osuosl.org [127.0.0.1]) (amavisd-new, port 10024) with ESMTP id sLvfb7MInqQZ for ; Thu, 12 Nov 2020 16:10:42 +0000 (UTC) X-Greylist: domain auto-whitelisted by SQLgrey-1.7.6 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [63.128.21.124]) by hemlock.osuosl.org (Postfix) with ESMTPS id 7211887802 for ; Thu, 12 Nov 2020 16:10:42 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1605197441; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=E1UKZPf+JbiNQvE8XW2nOS5hDXu2C+VrvGY9vlixvOI=; b=EmLuyxJTgoPitBJbihbqLb1i1pZx+POYslSJ/IYTh5+wTx9c7guwzCU36YJLbpClzSE0UO zoiwvLstTI88aSkRjlFd45PnFPaJytJ3xy/Xg1zwDo8Kw5btU2fZCYYssXgRWh6ZsI2v9D hDfmYNepde8mhS0UmN/mwBMpfwqWOW0= Received: from mail-wr1-f69.google.com (mail-wr1-f69.google.com [209.85.221.69]) (Using TLS) by relay.mimecast.com with ESMTP id us-mta-424-L6-ZlgHcOfGOQ2tZ9-Kp6Q-1; Thu, 12 Nov 2020 11:10:27 -0500 X-MC-Unique: L6-ZlgHcOfGOQ2tZ9-Kp6Q-1 Received: by mail-wr1-f69.google.com with SMTP id z7so767284wrl.14 for ; Thu, 12 Nov 2020 08:10:27 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=E1UKZPf+JbiNQvE8XW2nOS5hDXu2C+VrvGY9vlixvOI=; b=Nr32bsfqDlANCUU4UGcezioQcMtqs2iqIdRRfN6801wlbMc0vVplhJcf2hQZkrhghw 0ooOdfYOVauaWxVt/X2Wd2piZptAAHSqShGVMXV5kPHdtbIfzKswbMo+K2Ch9YfrlngB V3AfXHYLvAdsDO7Wzsx7tqK8wWZPYTagOTVoB66h2DhB7uJ9vZ/5AZBv3VzkTKi2v0Hu lSnc2Jn5cwq43PejYIs/4p15rE0ZKIAbOhiGfEE/FA9zoXal2ZG9bfqF3eJCJq8CrVod DnAf61UxbuEWdeUc/FFgn2ROsigCKKx8NEYj0kSzufP69sxoBP6iJZbfECsS/9wbiPC0 49Ag== X-Gm-Message-State: AOAM532Q0Ax/yjj8jmwzXODYPiJwzuuCbsmzXCUI9/+BniE0PEjOR9FE itsD2gxzFdiiZZyrXo95PmyXDmUqlGcYRWTZPLz2oReXDPjcV2hQCGKDSKTApKU9+gJzil+BeiU 3VQpTSLhy7paeAVX3yovPXuY2dn/GdLeGkwvBLfDnfUi5WW8YQM403pPs2YtfYukFlmTxaJWARu Q= X-Received: by 2002:a05:600c:21d5:: with SMTP id x21mr375870wmj.133.1605197426163; Thu, 12 Nov 2020 08:10:26 -0800 (PST) X-Google-Smtp-Source: ABdhPJzz8GPQmNVAYc/9/AvhxUe3NjGmvGNU+TswKlX2YUip3+q1uHa1mGTJ602ELMZutcjriwYlYQ== X-Received: by 2002:a05:600c:21d5:: with SMTP id x21mr375842wmj.133.1605197425932; Thu, 12 Nov 2020 08:10:25 -0800 (PST) Received: from lore-desk.redhat.com ([151.66.8.153]) by smtp.gmail.com with ESMTPSA id h4sm7084997wrq.3.2020.11.12.08.10.25 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 12 Nov 2020 08:10:25 -0800 (PST) From: Lorenzo Bianconi To: dev@openvswitch.org Date: Thu, 12 Nov 2020 17:10:12 +0100 Message-Id: <0d6d52452333ebdfd601a799c60e63d47b18f4f7.1605196277.git.lorenzo.bianconi@redhat.com> X-Mailer: git-send-email 2.26.2 In-Reply-To: References: MIME-Version: 1.0 Authentication-Results: relay.mimecast.com; auth=pass smtp.auth=CUSA124A263 smtp.mailfrom=lorenzo.bianconi@redhat.com X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com Subject: [ovs-dev] [RFC ovn 3/3] controller: bfd: introduce BFD state machine X-BeenThere: ovs-dev@openvswitch.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: ovs-dev-bounces@openvswitch.org Sender: "dev" Introduce BFD state machine according to RFC880 https://tools.ietf.org/html/rfc5880 Signed-off-by: Lorenzo Bianconi --- controller/pinctrl.c | 103 ++++++++++++++++++++++++++++++++++++++++++- northd/ovn-northd.c | 9 ++++ 2 files changed, 111 insertions(+), 1 deletion(-) diff --git a/controller/pinctrl.c b/controller/pinctrl.c index b6d68e2a5..e88193d77 100644 --- a/controller/pinctrl.c +++ b/controller/pinctrl.c @@ -6317,6 +6317,28 @@ sync_svc_monitors(struct ovsdb_idl_txn *ovnsb_idl_txn, } +enum bfd_state { + BFD_STATE_ADMIN_DOWN, + BFD_STATE_DOWN, + BFD_STATE_INIT, + BFD_STATE_UP, +}; + +static char * +bfd_get_status(enum bfd_state state) +{ + switch (state) { + case BFD_STATE_ADMIN_DOWN: + return "admin_down"; + case BFD_STATE_DOWN: + return "down"; + case BFD_STATE_INIT: + return "init"; + case BFD_STATE_UP: + return "up"; + } +} + static struct hmap bfd_monitor_map; struct bfd_entry { @@ -6341,7 +6363,12 @@ struct bfd_entry { int64_t port_key; int64_t metadata; + enum bfd_state state; + bool change_state; + + uint32_t detection_timeout; long long int last_update; + long long int last_rx; long long int next_tx; }; @@ -6369,6 +6396,18 @@ pinctrl_find_bfd_monitor_entry_by_port(uint16_t port) return NULL; } +static struct bfd_entry * +pinctrl_find_bfd_monitor_entry_by_disc(ovs_be32 disc) +{ + struct bfd_entry *entry; + HMAP_FOR_EACH (entry, node, &bfd_monitor_map) { + if (entry->disc == disc) { + return entry; + } + } + return NULL; +} + static bool bfd_monitor_should_inject(void) { @@ -6419,9 +6458,11 @@ bfd_monitor_put_bfd_msg(struct bfd_entry *entry, struct dp_packet *packet) udp->udp_dst = htons(BFD_DEST_PORT); udp->udp_len = htons(sizeof *udp + sizeof *msg); - msg = dp_packet_put_uninit(packet, sizeof *msg); + msg = dp_packet_put_zeros(packet, sizeof *msg); msg->vers_diag = (BFD_VERSION << 5); msg->length = BFD_PACKET_LEN; + msg->flags = entry->state << 6; + msg->my_disc = entry->disc; } static void @@ -6432,6 +6473,10 @@ bfd_monitor_send_msg(struct rconn *swconn, long long int *bfd_time) struct bfd_entry *entry; HMAP_FOR_EACH (entry, node, &bfd_monitor_map) { + if (cur_time > entry->last_rx + entry->detection_timeout) { + entry->state = BFD_STATE_DOWN; + } + if (cur_time < entry->next_tx) { goto next; } @@ -6483,6 +6528,56 @@ pinctrl_handle_bfd_msg(struct rconn *swconn, const struct flow *ip_flow, struct dp_packet *pkt_in, const struct match *md) OVS_REQUIRES(pinctrl_mutex) { + /* XXX add sanity checks here */ + const struct bfd_msg *msg = dp_packet_get_udp_payload(pkt_in); + struct bfd_entry *entry = pinctrl_find_bfd_monitor_entry_by_disc( + msg->your_disc); + if (!entry) { + return; + } + + enum bfd_state peer_state = msg->flags >> 6; + /* bfd state machine */ + switch (entry->state) { + case BFD_STATE_DOWN: + if (peer_state == BFD_STATE_DOWN) { + entry->state = BFD_STATE_INIT; + entry->change_state = true; + } + if (peer_state == BFD_STATE_INIT) { + entry->state = BFD_STATE_UP; + entry->change_state = true; + } + entry->last_rx = time_msec(); + break; + case BFD_STATE_INIT: + if (peer_state == BFD_STATE_INIT || + peer_state == BFD_STATE_UP) { + entry->state = BFD_STATE_UP; + entry->change_state = true; + } + if (peer_state == BFD_STATE_ADMIN_DOWN) { + entry->state = BFD_STATE_DOWN; + entry->change_state = true; + } + entry->last_rx = time_msec(); + break; + case BFD_STATE_UP: + if (peer_state == BFD_STATE_ADMIN_DOWN || + peer_state == BFD_STATE_DOWN) { + entry->state = BFD_STATE_DOWN; + entry->change_state = true; + } + entry->last_rx = time_msec(); + break; + case BFD_STATE_ADMIN_DOWN: + default: + break; + } + + if (entry->change_state) { + notify_pinctrl_main(); + } } #define BFD_MONITOR_STALE_TIMEOUT 180000LL @@ -6564,12 +6659,18 @@ bfd_monitor_run(const struct sbrec_bfd_table *bfd_table, entry->udp_src = bt->src_port; entry->disc = htonl(bt->disc); entry->next_tx = cur_time; + entry->last_rx = cur_time; + entry->detection_timeout = 30000; /* XXX */ entry->metadata = pb->datapath->tunnel_key; entry->port_key = pb->tunnel_key; + entry->state = BFD_STATE_DOWN; uint32_t hash = hash_string(bt->dst_ip, 0); hmap_insert(&bfd_monitor_map, &entry->node, hash); changed = true; + } else if (entry->change_state) { + sbrec_bfd_set_status(bt, bfd_get_status(entry->state)); + entry->change_state = false; } entry->last_update = cur_time; } diff --git a/northd/ovn-northd.c b/northd/ovn-northd.c index 6470d1670..91dff5979 100644 --- a/northd/ovn-northd.c +++ b/northd/ovn-northd.c @@ -91,6 +91,8 @@ static bool controller_event_en; static bool check_lsp_is_up; +static bool bfd_en; + /* MAC allocated for service monitor usage. Just one mac is allocated * for this purpose and ovn-controller's on each chassis will make use * of this mac when sending out the packets to monitor the services @@ -9267,6 +9269,12 @@ build_lrouter_flows(struct hmap *datapaths, struct hmap *ports, continue; } + /* BFD msg handling */ + if (bfd_en) { + ovn_lflow_add(lflows, od, S_ROUTER_IN_IP_INPUT, 100, + "udp.dst == 3784", "handle_bfd_msg;"); + } + /* Packets are allowed by default. */ ovn_lflow_add(lflows, od, S_ROUTER_IN_DEFRAG, 0, "1", "next;"); ovn_lflow_add(lflows, od, S_ROUTER_IN_UNSNAT, 0, "1", "next;"); @@ -12330,6 +12338,7 @@ ovnnb_db_run(struct northd_context *ctx, controller_event_en = smap_get_bool(&nb->options, "controller_event", false); + bfd_en = smap_get_bool(&nb->options, "bfd", false); check_lsp_is_up = !smap_get_bool(&nb->options, "ignore_lsp_down", false);