|
|
9219d1 |
From 536d6aa32497ab17e12767446f294fc8467cfc7c Mon Sep 17 00:00:00 2001
|
|
|
9219d1 |
From: Dumitru Ceara <dceara@redhat.com>
|
|
|
9219d1 |
Date: Thu, 3 Sep 2020 17:03:45 +0200
|
|
|
9219d1 |
Subject: [PATCH 1/2] chassis: Fix the way encaps are updated for a chassis
|
|
|
9219d1 |
record.
|
|
|
9219d1 |
|
|
|
9219d1 |
ovn-controller always stores the last configured system-id/chassis-id in
|
|
|
9219d1 |
memory regardless if the connection to the SB is up or down. This is OK
|
|
|
9219d1 |
as long as the change can be committed successfully when the SB DB
|
|
|
9219d1 |
connection comes back up.
|
|
|
9219d1 |
|
|
|
9219d1 |
Without this change, if the chassis-id changes while the SB connection is
|
|
|
9219d1 |
down, ovn-controller will fail to create the new record but nevertheless
|
|
|
9219d1 |
update its in-memory chassis-id. When the SB connection is restored
|
|
|
9219d1 |
ovn-controller tries to find the record corresponding to the chassis-id
|
|
|
9219d1 |
it stored in memory. This fails causing ovn-controller to try to insert
|
|
|
9219d1 |
a new record. But at this point a constraint violation is hit in the SB
|
|
|
9219d1 |
because the Encap records of the "stale" chassis still exist in the DB,
|
|
|
9219d1 |
along with the old chassis record.
|
|
|
9219d1 |
|
|
|
9219d1 |
This commit changes the way we search for a "stale" chassis record in the
|
|
|
9219d1 |
SB to cover the above mentioned case. Also, in such cases there's no need
|
|
|
9219d1 |
to recreate the Encaps, it's sufficient to update the chassis_name field.
|
|
|
9219d1 |
|
|
|
9219d1 |
Fixes: 5344f24ecb1a ("ovn-controller: Refactor chassis.c to abstract the string parsing")
|
|
|
9219d1 |
Signed-off-by: Dumitru Ceara <dceara@redhat.com>
|
|
|
9219d1 |
Signed-off-by: Numan Siddique <numans@ovn.org>
|
|
|
9219d1 |
|
|
|
9219d1 |
(cherry-picked from master commit 94a32fca2d2b825fece0ef5b1873459bd9857dd3)
|
|
|
9219d1 |
|
|
|
9219d1 |
(cherry picked from upstream commit 0716c4f4cf2d97f03c1f2e5099fece92f3183d43)
|
|
|
9219d1 |
|
|
|
9219d1 |
Change-Id: I20f0c61fddffba599b16f43d15b110414a6a6e6b
|
|
|
9219d1 |
---
|
|
|
9219d1 |
controller/chassis.c | 60 +++++++++++++++++++++++++++++++------------------
|
|
|
9219d1 |
tests/ovn-controller.at | 17 ++++++++++++++
|
|
|
9219d1 |
2 files changed, 55 insertions(+), 22 deletions(-)
|
|
|
9219d1 |
|
|
|
9219d1 |
diff --git a/controller/chassis.c b/controller/chassis.c
|
|
|
9219d1 |
index 6ac591e..773d966 100644
|
|
|
9219d1 |
--- a/controller/chassis.c
|
|
|
9219d1 |
+++ b/controller/chassis.c
|
|
|
9219d1 |
@@ -397,10 +397,7 @@ chassis_tunnels_changed(const struct sset *encap_type_set,
|
|
|
9219d1 |
{
|
|
|
9219d1 |
size_t encap_type_count = 0;
|
|
|
9219d1 |
|
|
|
9219d1 |
- for (int i = 0; i < chassis_rec->n_encaps; i++) {
|
|
|
9219d1 |
- if (strcmp(chassis_rec->name, chassis_rec->encaps[i]->chassis_name)) {
|
|
|
9219d1 |
- return true;
|
|
|
9219d1 |
- }
|
|
|
9219d1 |
+ for (size_t i = 0; i < chassis_rec->n_encaps; i++) {
|
|
|
9219d1 |
|
|
|
9219d1 |
if (!sset_contains(encap_type_set, chassis_rec->encaps[i]->type)) {
|
|
|
9219d1 |
return true;
|
|
|
9219d1 |
@@ -473,6 +470,19 @@ chassis_build_encaps(struct ovsdb_idl_txn *ovnsb_idl_txn,
|
|
|
9219d1 |
}
|
|
|
9219d1 |
|
|
|
9219d1 |
/*
|
|
|
9219d1 |
+ * Updates encaps for a given chassis. This can happen when the chassis
|
|
|
9219d1 |
+ * name has changed. Also, the only thing we support updating is the
|
|
|
9219d1 |
+ * chassis_name. For other changes the encaps will be recreated.
|
|
|
9219d1 |
+ */
|
|
|
9219d1 |
+static void
|
|
|
9219d1 |
+chassis_update_encaps(const struct sbrec_chassis *chassis)
|
|
|
9219d1 |
+{
|
|
|
9219d1 |
+ for (size_t i = 0; i < chassis->n_encaps; i++) {
|
|
|
9219d1 |
+ sbrec_encap_set_chassis_name(chassis->encaps[i], chassis->name);
|
|
|
9219d1 |
+ }
|
|
|
9219d1 |
+}
|
|
|
9219d1 |
+
|
|
|
9219d1 |
+/*
|
|
|
9219d1 |
* Returns a pointer to a chassis record from 'chassis_table' that
|
|
|
9219d1 |
* matches at least one tunnel config.
|
|
|
9219d1 |
*/
|
|
|
9219d1 |
@@ -503,9 +513,10 @@ chassis_get_stale_record(const struct sbrec_chassis_table *chassis_table,
|
|
|
9219d1 |
/* If this is a chassis config update after we initialized the record once
|
|
|
9219d1 |
* then we should always be able to find it with the ID we saved in
|
|
|
9219d1 |
* chassis_state.
|
|
|
9219d1 |
- * Otherwise (i.e., first time we create the record) then we check if there's
|
|
|
9219d1 |
- * a stale record from a previous controller run that didn't end gracefully
|
|
|
9219d1 |
- * and reuse it. If not then we create a new record.
|
|
|
9219d1 |
+ * Otherwise (i.e., first time we create the record or if the system-id
|
|
|
9219d1 |
+ * changed) then we check if there's a stale record from a previous
|
|
|
9219d1 |
+ * controller run that didn't end gracefully and reuse it. If not then we
|
|
|
9219d1 |
+ * create a new record.
|
|
|
9219d1 |
*
|
|
|
9219d1 |
* Sets '*chassis_rec' to point to the local chassis record.
|
|
|
9219d1 |
* Returns true if this record was already in the database, false if it was
|
|
|
9219d1 |
@@ -519,28 +530,32 @@ chassis_get_record(struct ovsdb_idl_txn *ovnsb_idl_txn,
|
|
|
9219d1 |
const char *chassis_id,
|
|
|
9219d1 |
const struct sbrec_chassis **chassis_rec)
|
|
|
9219d1 |
{
|
|
|
9219d1 |
+ const struct sbrec_chassis *chassis = NULL;
|
|
|
9219d1 |
+
|
|
|
9219d1 |
if (chassis_info_id_inited(&chassis_state)) {
|
|
|
9219d1 |
- *chassis_rec = chassis_lookup_by_name(sbrec_chassis_by_name,
|
|
|
9219d1 |
- chassis_info_id(&chassis_state));
|
|
|
9219d1 |
- if (!(*chassis_rec)) {
|
|
|
9219d1 |
- VLOG_DBG("Could not find Chassis, will create it"
|
|
|
9219d1 |
- ": stored (%s) ovs (%s)",
|
|
|
9219d1 |
+ chassis = chassis_lookup_by_name(sbrec_chassis_by_name,
|
|
|
9219d1 |
+ chassis_info_id(&chassis_state));
|
|
|
9219d1 |
+ if (!chassis) {
|
|
|
9219d1 |
+ VLOG_DBG("Could not find Chassis, will check if the id changed: "
|
|
|
9219d1 |
+ "stored (%s) ovs (%s)",
|
|
|
9219d1 |
chassis_info_id(&chassis_state), chassis_id);
|
|
|
9219d1 |
- if (ovnsb_idl_txn) {
|
|
|
9219d1 |
- /* Recreate the chassis record. */
|
|
|
9219d1 |
- *chassis_rec = sbrec_chassis_insert(ovnsb_idl_txn);
|
|
|
9219d1 |
- return false;
|
|
|
9219d1 |
- }
|
|
|
9219d1 |
}
|
|
|
9219d1 |
- } else {
|
|
|
9219d1 |
- *chassis_rec =
|
|
|
9219d1 |
- chassis_get_stale_record(chassis_table, ovs_cfg, chassis_id);
|
|
|
9219d1 |
+ }
|
|
|
9219d1 |
|
|
|
9219d1 |
- if (!(*chassis_rec) && ovnsb_idl_txn) {
|
|
|
9219d1 |
+ if (!chassis) {
|
|
|
9219d1 |
+ chassis = chassis_get_stale_record(chassis_table, ovs_cfg, chassis_id);
|
|
|
9219d1 |
+ }
|
|
|
9219d1 |
+
|
|
|
9219d1 |
+ if (!chassis) {
|
|
|
9219d1 |
+ /* Recreate the chassis record. */
|
|
|
9219d1 |
+ VLOG_DBG("Could not find Chassis, will create it: %s", chassis_id);
|
|
|
9219d1 |
+ if (ovnsb_idl_txn) {
|
|
|
9219d1 |
*chassis_rec = sbrec_chassis_insert(ovnsb_idl_txn);
|
|
|
9219d1 |
- return false;
|
|
|
9219d1 |
}
|
|
|
9219d1 |
+ return false;
|
|
|
9219d1 |
}
|
|
|
9219d1 |
+
|
|
|
9219d1 |
+ *chassis_rec = chassis;
|
|
|
9219d1 |
return true;
|
|
|
9219d1 |
}
|
|
|
9219d1 |
|
|
|
9219d1 |
@@ -602,6 +617,7 @@ chassis_update(const struct sbrec_chassis *chassis_rec,
|
|
|
9219d1 |
&ovs_cfg->encap_ip_set, ovs_cfg->encap_csum,
|
|
|
9219d1 |
chassis_rec);
|
|
|
9219d1 |
if (!tunnels_changed) {
|
|
|
9219d1 |
+ chassis_update_encaps(chassis_rec);
|
|
|
9219d1 |
return updated;
|
|
|
9219d1 |
}
|
|
|
9219d1 |
|
|
|
9219d1 |
diff --git a/tests/ovn-controller.at b/tests/ovn-controller.at
|
|
|
9219d1 |
index 1b96934..f2faf1f 100644
|
|
|
9219d1 |
--- a/tests/ovn-controller.at
|
|
|
9219d1 |
+++ b/tests/ovn-controller.at
|
|
|
9219d1 |
@@ -196,6 +196,23 @@ OVS_WAIT_UNTIL([
|
|
|
9219d1 |
test "${sysid}" = "${chassis_id}"
|
|
|
9219d1 |
])
|
|
|
9219d1 |
|
|
|
9219d1 |
+# Simulate system-id changing while ovn-controller is disconnected from the
|
|
|
9219d1 |
+# SB.
|
|
|
9219d1 |
+valid_remote=$(ovs-vsctl get Open_vSwitch . external_ids:ovn-remote)
|
|
|
9219d1 |
+invalid_remote=tcp:0.0.0.0:4242
|
|
|
9219d1 |
+ovs-vsctl set Open_vSwitch . external_ids:ovn-remote=${invalid_remote}
|
|
|
9219d1 |
+expected_state="not connected"
|
|
|
9219d1 |
+OVS_WAIT_UNTIL([
|
|
|
9219d1 |
+ test "${expected_state}" = "$(ovn-appctl -t ovn-controller connection-status)"
|
|
|
9219d1 |
+])
|
|
|
9219d1 |
+sysid=${sysid}-bar
|
|
|
9219d1 |
+ovs-vsctl set Open_vSwitch . external-ids:system-id="${sysid}"
|
|
|
9219d1 |
+ovs-vsctl set Open_vSwitch . external_ids:ovn-remote=${valid_remote}
|
|
|
9219d1 |
+OVS_WAIT_UNTIL([
|
|
|
9219d1 |
+ chassis_id=$(ovn-sbctl get Chassis "${sysid}" name)
|
|
|
9219d1 |
+ test "${sysid}" = "${chassis_id}"
|
|
|
9219d1 |
+])
|
|
|
9219d1 |
+
|
|
|
9219d1 |
# Gracefully terminate daemons
|
|
|
9219d1 |
OVN_CLEANUP_SBOX([hv])
|
|
|
9219d1 |
OVN_CLEANUP_VSWITCH([main])
|
|
|
9219d1 |
--
|
|
|
9219d1 |
1.8.3.1
|
|
|
9219d1 |
|