[ovs-dev] [PATCH] db-ctl-base: Allow print rows that weak reference to table in 'cmd_show_table'.

Alex Wang alexw at nicira.com
Thu Aug 13 04:49:08 UTC 2015


Sometimes, it is desirable to print the table with weak reference to
the table specified in 'struct cmd_show_table'.  For example the
Port_Binding table rows in OVN_Southbound database that refer to the
same Chassis table row can be printed under the same chassis entry
in 'ovn-sbctl show' output.

To achieve it, this commit adds a new struct in 'struct cmd_show_table'
that allows users to print a table with weak reference to 'table'
specified in 'struct cmd_show_table'.  The 'ovn-sbctl' which now prints
the Port_Binding entries with Chassis table, is the first user of this
new feature.

Requested-by: Justin Pettit <jpettit at nicira.com>
Signed-off-by: Alex Wang <alexw at nicira.com>
---
 lib/db-ctl-base.c         |   45 +++++++++++++++++++++++++++++++++++++++++++++
 lib/db-ctl-base.h         |   16 ++++++++++++++++
 ovn/utilities/ovn-sbctl.c |   10 +++++++---
 tests/ovn-sbctl.at        |   27 +++++++++++++++++++++++++++
 utilities/ovs-vsctl.c     |   20 +++++++++++++-------
 vtep/vtep-ctl.c           |   17 +++++++++++------
 6 files changed, 119 insertions(+), 16 deletions(-)

diff --git a/lib/db-ctl-base.c b/lib/db-ctl-base.c
index 3028c09..cbafff1 100644
--- a/lib/db-ctl-base.c
+++ b/lib/db-ctl-base.c
@@ -1620,6 +1620,12 @@ pre_cmd_show(struct ctl_context *ctx)
                 ovsdb_idl_add_column(ctx->idl, column);
             }
         }
+        if (show->wref_table.name_column) {
+            ovsdb_idl_add_column(ctx->idl, show->wref_table.name_column);
+        }
+        if (show->wref_table.wref_column) {
+            ovsdb_idl_add_column(ctx->idl, show->wref_table.wref_column);
+        }
     }
 }
 
@@ -1649,6 +1655,44 @@ cmd_show_find_table_by_name(const char *name)
     return NULL;
 }
 
+/*  Prints table entries that weak reference the 'cur_row'. */
+static void
+cmd_show_weak_ref(struct ctl_context *ctx, const struct cmd_show_table *show,
+                  const struct ovsdb_idl_row *cur_row, int level)
+{
+    const struct ovsdb_idl_row *row_wref;
+    const struct ovsdb_idl_table_class *table = show->wref_table.table;
+    const struct ovsdb_idl_column *name_column
+        = show->wref_table.name_column;
+    const struct ovsdb_idl_column *wref_column
+        = show->wref_table.wref_column;
+
+    if (!table || !name_column || !wref_column) {
+        return;
+    }
+
+    ds_put_char_multiple(&ctx->output, ' ', (level + 1) * 4);
+    ds_put_format(&ctx->output, "%s", table->name);
+    ds_put_char(&ctx->output, '\n');
+
+    for (row_wref = ovsdb_idl_first_row(ctx->idl, table); row_wref;
+         row_wref = ovsdb_idl_next_row(row_wref)) {
+        const struct ovsdb_datum *wref_datum
+            = ovsdb_idl_read(row_wref, wref_column);
+        /* If weak reference refers to the 'cur_row', prints it. */
+        if (wref_datum->n
+            && uuid_equals(&cur_row->uuid, &wref_datum->keys[0].uuid)) {
+            const struct ovsdb_datum *name_datum
+                = ovsdb_idl_read(row_wref, name_column);
+
+            ds_put_char_multiple(&ctx->output, ' ', (level + 2) * 4);
+            ds_put_format(&ctx->output, "%s: ", name_column->name);
+            ovsdb_datum_to_string(name_datum, &name_column->type, &ctx->output);
+            ds_put_char(&ctx->output, '\n');
+        }
+    }
+}
+
 /* 'shown' records the tables that has been displayed by the current
  * command to avoid duplicated prints.
  */
@@ -1753,6 +1797,7 @@ cmd_show_row(struct ctl_context *ctx, const struct ovsdb_idl_row *row,
             ds_put_char(&ctx->output, '\n');
         }
     }
+    cmd_show_weak_ref(ctx, show, row, level);
     sset_find_and_delete_assert(shown, show->table->name);
 }
 
diff --git a/lib/db-ctl-base.h b/lib/db-ctl-base.h
index 00e86f8..209419a 100644
--- a/lib/db-ctl-base.h
+++ b/lib/db-ctl-base.h
@@ -148,6 +148,17 @@ struct ctl_command *ctl_parse_commands(int argc, char *argv[],
                                        struct shash *local_options,
                                        size_t *n_commandsp);
 
+/* Sometimes, it is desirable to print the table with weak reference to
+ * rows in a 'cmd_show_table' table.  In that case, the 'weak_ref_table'
+ * should be used and user must define all variables. */
+struct weak_ref_table {
+    const struct ovsdb_idl_table_class *table;
+    const struct ovsdb_idl_column *name_column;
+    /* This colum must be a weak reference to the owning
+     * 'struct cmd_show_table''s table row. */
+    const struct ovsdb_idl_column *wref_column;
+};
+
 /* This struct is for organizing the 'show' command output where:
  *
  * - 'table' is the table to show.
@@ -157,11 +168,16 @@ struct ctl_command *ctl_parse_commands(int argc, char *argv[],
  *
  * - 'columns[]' allows user to specify the print of additional columns
  *   in 'table'.
+ *
+ * - if 'wref_table' is filled, print the 'wref_table.table' rows that refer
+ *   to the 'table'.
+ *
  * */
 struct cmd_show_table {
     const struct ovsdb_idl_table_class *table;
     const struct ovsdb_idl_column *name_column;
     const struct ovsdb_idl_column *columns[3]; /* Seems like a good number. */
+    const struct weak_ref_table wref_table;
 };
 
 
diff --git a/ovn/utilities/ovn-sbctl.c b/ovn/utilities/ovn-sbctl.c
index 9976215..3c3cd5b 100644
--- a/ovn/utilities/ovn-sbctl.c
+++ b/ovn/utilities/ovn-sbctl.c
@@ -488,15 +488,19 @@ static struct cmd_show_table cmd_show_tables[] = {
      &sbrec_chassis_col_name,
      {&sbrec_chassis_col_encaps,
       NULL,
-      NULL}},
+      NULL},
+     {&sbrec_table_port_binding,
+      &sbrec_port_binding_col_logical_port,
+      &sbrec_port_binding_col_chassis}},
 
     {&sbrec_table_encap,
      &sbrec_encap_col_type,
      {&sbrec_encap_col_ip,
       &sbrec_encap_col_options,
-      NULL}},
+      NULL},
+     {NULL, NULL, NULL}},
 
-    {NULL, NULL, {NULL, NULL, NULL}},
+    {NULL, NULL, {NULL, NULL, NULL}, {NULL, NULL, NULL}},
 };
 
 static void
diff --git a/tests/ovn-sbctl.at b/tests/ovn-sbctl.at
index 6bda181..9d1f375 100644
--- a/tests/ovn-sbctl.at
+++ b/tests/ovn-sbctl.at
@@ -48,6 +48,33 @@ AT_CHECK([ovn-sbctl show], [0], [dnl
 Chassis "ch0"
     Encap stt
         ip: "1.2.3.5"
+    Port_Binding
+        logical_port: "vif0"
+])
+
+# adds another 'vif1'
+AT_CHECK([ovn-nbctl lport-add br-test vif1])
+AT_CHECK([ovn-nbctl lport-set-macs vif1 f0:ab:cd:ef:01:03])
+AT_CHECK([ovn-sbctl lport-bind vif1 ch0])
+
+AT_CHECK([ovn-sbctl show | sed 's/vif[[0-9]]/vif/'], [0], [dnl
+Chassis "ch0"
+    Encap stt
+        ip: "1.2.3.5"
+    Port_Binding
+        logical_port: "vif"
+        logical_port: "vif"
+])
+
+# deletes 'vif1'
+AT_CHECK([ovn-nbctl lport-del vif1])
+
+AT_CHECK([ovn-sbctl show], [0], [dnl
+Chassis "ch0"
+    Encap stt
+        ip: "1.2.3.5"
+    Port_Binding
+        logical_port: "vif0"
 ])
 
 uuid=$(ovn-sbctl --columns=_uuid list Chassis ch0 | cut -d ':' -f2 | tr -d ' ')
diff --git a/utilities/ovs-vsctl.c b/utilities/ovs-vsctl.c
index c3b8a38..e28634a 100644
--- a/utilities/ovs-vsctl.c
+++ b/utilities/ovs-vsctl.c
@@ -980,45 +980,51 @@ static struct cmd_show_table cmd_show_tables[] = {
      NULL,
      {&ovsrec_open_vswitch_col_manager_options,
       &ovsrec_open_vswitch_col_bridges,
-      &ovsrec_open_vswitch_col_ovs_version}
+      &ovsrec_open_vswitch_col_ovs_version},
+     {NULL, NULL, NULL}
     },
 
     {&ovsrec_table_bridge,
      &ovsrec_bridge_col_name,
      {&ovsrec_bridge_col_controller,
       &ovsrec_bridge_col_fail_mode,
-      &ovsrec_bridge_col_ports}
+      &ovsrec_bridge_col_ports},
+     {NULL, NULL, NULL}
     },
 
     {&ovsrec_table_port,
      &ovsrec_port_col_name,
      {&ovsrec_port_col_tag,
       &ovsrec_port_col_trunks,
-      &ovsrec_port_col_interfaces}
+      &ovsrec_port_col_interfaces},
+     {NULL, NULL, NULL}
     },
 
     {&ovsrec_table_interface,
      &ovsrec_interface_col_name,
      {&ovsrec_interface_col_type,
       &ovsrec_interface_col_options,
-      &ovsrec_interface_col_error}
+      &ovsrec_interface_col_error},
+     {NULL, NULL, NULL}
     },
 
     {&ovsrec_table_controller,
      &ovsrec_controller_col_target,
      {&ovsrec_controller_col_is_connected,
       NULL,
-      NULL}
+      NULL},
+     {NULL, NULL, NULL}
     },
 
     {&ovsrec_table_manager,
      &ovsrec_manager_col_target,
      {&ovsrec_manager_col_is_connected,
       NULL,
-      NULL}
+      NULL},
+     {NULL, NULL, NULL}
     },
 
-    {NULL, NULL, {NULL, NULL, NULL}}
+    {NULL, NULL, {NULL, NULL, NULL}, {NULL, NULL, NULL}}
 };
 
 static void
diff --git a/vtep/vtep-ctl.c b/vtep/vtep-ctl.c
index 37a78a1..82b87f4 100644
--- a/vtep/vtep-ctl.c
+++ b/vtep/vtep-ctl.c
@@ -369,38 +369,43 @@ static struct cmd_show_table cmd_show_tables[] = {
      NULL,
      {&vteprec_global_col_managers,
       &vteprec_global_col_switches,
-      NULL}
+      NULL},
+     {NULL, NULL, NULL}
     },
 
     {&vteprec_table_manager,
      &vteprec_manager_col_target,
      {&vteprec_manager_col_is_connected,
       NULL,
-      NULL}
+      NULL},
+     {NULL, NULL, NULL}
     },
 
     {&vteprec_table_physical_switch,
      &vteprec_physical_switch_col_name,
      {&vteprec_physical_switch_col_management_ips,
       &vteprec_physical_switch_col_tunnel_ips,
-      &vteprec_physical_switch_col_ports}
+      &vteprec_physical_switch_col_ports},
+     {NULL, NULL, NULL}
     },
 
     {&vteprec_table_physical_port,
      &vteprec_physical_port_col_name,
      {&vteprec_physical_port_col_vlan_bindings,
       NULL,
-      NULL}
+      NULL},
+     {NULL, NULL, NULL}
     },
 
     {&vteprec_table_logical_switch,
      &vteprec_logical_switch_col_name,
      {NULL,
       NULL,
-      NULL}
+      NULL},
+     {NULL, NULL, NULL}
     },
 
-    {NULL, NULL, {NULL, NULL, NULL}}
+    {NULL, NULL, {NULL, NULL, NULL}, {NULL, NULL, NULL}}
 };
 
 /* vtep-ctl specific context.  Inherits the 'struct ctl_context' as base. */
-- 
1.7.9.5




More information about the dev mailing list