2 * Licensed under the Apache License, Version 2.0 (the "License");
3 * you may not use this file except in compliance with the License.
4 * You may obtain a copy of the License at:
6 * http://www.apache.org/licenses/LICENSE-2.0
8 * Unless required by applicable law or agreed to in writing, software
9 * distributed under the License is distributed on an "AS IS" BASIS,
10 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
11 * See the License for the specific language governing permissions and
12 * limitations under the License.
22 #include "command-line.h"
24 #include "fatal-signal.h"
25 #include "ovn/lib/ovn-nb-idl.h"
26 #include "poll-loop.h"
29 #include "stream-ssl.h"
31 #include "openvswitch/vlog.h"
33 VLOG_DEFINE_THIS_MODULE(ovn_nbctl);
35 struct nbctl_context {
36 struct ovsdb_idl *idl;
37 struct ovsdb_idl_txn *txn;
40 static const char *db;
42 static const char *default_db(void);
48 %s: OVN northbound DB management utility\n\
49 usage: %s [OPTIONS] COMMAND [ARG...]\n\
52 show print overview of database contents\n\
53 show LSWITCH print overview of database contents for LSWITCH\n\
55 Logical switch commands:\n\
56 lswitch-add [LSWITCH] create a logical switch named LSWITCH\n\
57 lswitch-del LSWITCH delete LSWITCH and all its ports\n\
58 lswitch-list print the names of all logical switches\n\
59 lswitch-set-external-id LSWITCH KEY [VALUE]\n\
60 set or delete an external-id on LSWITCH\n\
61 lswitch-get-external-id LSWITCH [KEY]\n\
62 list one or all external-ids on LSWITCH\n\
64 Logical port commands:\n\
65 lport-add LSWITCH LPORT add logical port LPORT on LSWITCH\n\
66 lport-add LSWITCH LPORT PARENT TAG\n\
67 add logical port LPORT on LSWITCH with PARENT\n\
69 lport-del LPORT delete LPORT from its attached switch\n\
70 lport-list LSWITCH print the names of all logical ports on LSWITCH\n\
71 lport-get-parent LPORT get the parent of LPORT if set\n\
72 lport-get-tag LPORT get the LPORT's tag if set\n\
73 lport-set-external-id LPORT KEY [VALUE]\n\
74 set or delete an external-id on LPORT\n\
75 lport-get-external-id LPORT [KEY]\n\
76 list one or all external-ids on LPORT\n\
77 lport-set-macs LPORT [MAC]...\n\
78 set MAC addresses for LPORT.\n\
79 lport-get-macs LPORT get a list of MAC addresses on LPORT\n\
80 lport-set-port-security LPORT [ADDRS]...\n\
81 set port security addresses for LPORT.\n\
82 lport-get-port-security LPORT get LPORT's port security addresses\n\
83 lport-get-up LPORT get state of LPORT ('up' or 'down')\n\
84 lport-set-enabled LPORT STATE\n\
85 set administrative state LPORT\n\
86 ('enabled' or 'disabled')\n\
87 lport-get-enabled LPORT get administrative state LPORT\n\
88 ('enabled' or 'disabled')\n\
89 lport-set-type LPORT TYPE Set the type for LPORT\n\
90 lport-get-type LPORT Get the type for LPORT\n\
91 lport-set-options LPORT KEY=VALUE [KEY=VALUE]...\n\
92 Set options related to the type of LPORT\n\
93 lport-get-options LPORT Get the type specific options for LPORT\n\
96 --db=DATABASE connect to DATABASE\n\
98 -h, --help display this help message\n\
99 -o, --options list available options\n\
100 -V, --version display version information\n\
101 ", program_name, program_name, default_db());
103 stream_usage("database", true, true, false);
106 static const struct nbrec_logical_switch *
107 lswitch_by_name_or_uuid(struct nbctl_context *nb_ctx, const char *id)
109 const struct nbrec_logical_switch *lswitch = NULL;
110 bool is_uuid = false;
111 bool duplicate = false;
112 struct uuid lswitch_uuid;
114 if (uuid_from_string(&lswitch_uuid, id)) {
116 lswitch = nbrec_logical_switch_get_for_uuid(nb_ctx->idl,
121 const struct nbrec_logical_switch *iter;
123 NBREC_LOGICAL_SWITCH_FOR_EACH(iter, nb_ctx->idl) {
124 if (strcmp(iter->name, id)) {
128 VLOG_WARN("There is more than one logical switch named '%s'. "
138 if (!lswitch && !duplicate) {
139 VLOG_WARN("lswitch not found for %s: '%s'",
140 is_uuid ? "UUID" : "name", id);
147 print_lswitch(const struct nbrec_logical_switch *lswitch)
149 printf(" lswitch "UUID_FMT" (%s)\n",
150 UUID_ARGS(&lswitch->header_.uuid), lswitch->name);
152 for (size_t i = 0; i < lswitch->n_ports; i++) {
153 const struct nbrec_logical_port *lport = lswitch->ports[i];
155 printf(" lport %s\n", lport->name);
156 if (lport->parent_name && lport->n_tag) {
157 printf(" parent: %s, tag:%"PRIu64"\n",
158 lport->parent_name, lport->tag[0]);
162 for (size_t j = 0; j < lport->n_macs; j++) {
163 printf(" %s", lport->macs[j]);
171 do_show(struct ovs_cmdl_context *ctx)
173 struct nbctl_context *nb_ctx = ctx->pvt;
174 const struct nbrec_logical_switch *lswitch;
176 if (ctx->argc == 2) {
177 lswitch = lswitch_by_name_or_uuid(nb_ctx, ctx->argv[1]);
179 print_lswitch(lswitch);
182 NBREC_LOGICAL_SWITCH_FOR_EACH(lswitch, nb_ctx->idl) {
183 print_lswitch(lswitch);
189 do_lswitch_add(struct ovs_cmdl_context *ctx)
191 struct nbctl_context *nb_ctx = ctx->pvt;
192 struct nbrec_logical_switch *lswitch;
194 lswitch = nbrec_logical_switch_insert(nb_ctx->txn);
195 if (ctx->argc == 2) {
196 nbrec_logical_switch_set_name(lswitch, ctx->argv[1]);
201 do_lswitch_del(struct ovs_cmdl_context *ctx)
203 struct nbctl_context *nb_ctx = ctx->pvt;
204 const char *id = ctx->argv[1];
205 const struct nbrec_logical_switch *lswitch;
207 lswitch = lswitch_by_name_or_uuid(nb_ctx, id);
212 nbrec_logical_switch_delete(lswitch);
216 do_lswitch_list(struct ovs_cmdl_context *ctx)
218 struct nbctl_context *nb_ctx = ctx->pvt;
219 const struct nbrec_logical_switch *lswitch;
221 NBREC_LOGICAL_SWITCH_FOR_EACH(lswitch, nb_ctx->idl) {
222 printf(UUID_FMT " (%s)\n",
223 UUID_ARGS(&lswitch->header_.uuid), lswitch->name);
228 do_lswitch_set_external_id(struct ovs_cmdl_context *ctx)
230 struct nbctl_context *nb_ctx = ctx->pvt;
231 const char *id = ctx->argv[1];
232 const struct nbrec_logical_switch *lswitch;
233 struct smap new_external_ids;
235 lswitch = lswitch_by_name_or_uuid(nb_ctx, id);
240 smap_init(&new_external_ids);
241 smap_clone(&new_external_ids, &lswitch->external_ids);
242 if (ctx->argc == 4) {
243 smap_replace(&new_external_ids, ctx->argv[2], ctx->argv[3]);
245 smap_remove(&new_external_ids, ctx->argv[2]);
247 nbrec_logical_switch_set_external_ids(lswitch, &new_external_ids);
248 smap_destroy(&new_external_ids);
252 do_lswitch_get_external_id(struct ovs_cmdl_context *ctx)
254 struct nbctl_context *nb_ctx = ctx->pvt;
255 const char *id = ctx->argv[1];
256 const struct nbrec_logical_switch *lswitch;
258 lswitch = lswitch_by_name_or_uuid(nb_ctx, id);
263 if (ctx->argc == 3) {
264 const char *key = ctx->argv[2];
267 /* List one external ID */
269 value = smap_get(&lswitch->external_ids, key);
271 printf("%s\n", value);
274 struct smap_node *node;
276 /* List all external IDs */
278 SMAP_FOR_EACH(node, &lswitch->external_ids) {
279 printf("%s=%s\n", node->key, node->value);
284 static const struct nbrec_logical_port *
285 lport_by_name_or_uuid(struct nbctl_context *nb_ctx, const char *id)
287 const struct nbrec_logical_port *lport = NULL;
288 bool is_uuid = false;
289 struct uuid lport_uuid;
291 if (uuid_from_string(&lport_uuid, id)) {
293 lport = nbrec_logical_port_get_for_uuid(nb_ctx->idl, &lport_uuid);
297 NBREC_LOGICAL_PORT_FOR_EACH(lport, nb_ctx->idl) {
298 if (!strcmp(lport->name, id)) {
305 VLOG_WARN("lport not found for %s: '%s'",
306 is_uuid ? "UUID" : "name", id);
313 do_lport_add(struct ovs_cmdl_context *ctx)
315 struct nbctl_context *nb_ctx = ctx->pvt;
316 struct nbrec_logical_port *lport;
317 const struct nbrec_logical_switch *lswitch;
320 lswitch = lswitch_by_name_or_uuid(nb_ctx, ctx->argv[1]);
325 if (ctx->argc != 3 && ctx->argc != 5) {
326 /* If a parent_name is specified, a tag must be specified as well. */
327 VLOG_WARN("Invalid arguments to lport-add.");
331 if (ctx->argc == 5) {
333 if (!ovs_scan(ctx->argv[4], "%"SCNd64, &tag) || tag < 0 || tag > 4095) {
334 VLOG_WARN("Invalid tag '%s'", ctx->argv[4]);
339 /* Create the logical port. */
340 lport = nbrec_logical_port_insert(nb_ctx->txn);
341 nbrec_logical_port_set_name(lport, ctx->argv[2]);
342 if (ctx->argc == 5) {
343 nbrec_logical_port_set_parent_name(lport, ctx->argv[3]);
344 nbrec_logical_port_set_tag(lport, &tag, 1);
347 /* Insert the logical port into the logical switch. */
348 nbrec_logical_switch_verify_ports(lswitch);
349 struct nbrec_logical_port **new_ports = xmalloc(sizeof *new_ports *
350 (lswitch->n_ports + 1));
351 memcpy(new_ports, lswitch->ports, sizeof *new_ports * lswitch->n_ports);
352 new_ports[lswitch->n_ports] = lport;
353 nbrec_logical_switch_set_ports(lswitch, new_ports, lswitch->n_ports + 1);
357 /* Removes lport 'lswitch->ports[idx]'. */
359 remove_lport(const struct nbrec_logical_switch *lswitch, size_t idx)
361 const struct nbrec_logical_port *lport = lswitch->ports[idx];
363 /* First remove 'lport' from the array of ports. This is what will
364 * actually cause the logical port to be deleted when the transaction is
365 * sent to the database server (due to garbage collection). */
366 struct nbrec_logical_port **new_ports
367 = xmemdup(lswitch->ports, sizeof *new_ports * lswitch->n_ports);
368 new_ports[idx] = new_ports[lswitch->n_ports - 1];
369 nbrec_logical_switch_verify_ports(lswitch);
370 nbrec_logical_switch_set_ports(lswitch, new_ports, lswitch->n_ports - 1);
373 /* Delete 'lport' from the IDL. This won't have a real effect on the
374 * database server (the IDL will suppress it in fact) but it means that it
375 * won't show up when we iterate with NBREC_LOGICAL_PORT_FOR_EACH later. */
376 nbrec_logical_port_delete(lport);
380 do_lport_del(struct ovs_cmdl_context *ctx)
382 struct nbctl_context *nb_ctx = ctx->pvt;
383 const struct nbrec_logical_port *lport;
385 lport = lport_by_name_or_uuid(nb_ctx, ctx->argv[1]);
390 /* Find the switch that contains 'lport', then delete it. */
391 const struct nbrec_logical_switch *lswitch;
392 NBREC_LOGICAL_SWITCH_FOR_EACH (lswitch, nb_ctx->idl) {
393 for (size_t i = 0; i < lswitch->n_ports; i++) {
394 if (lswitch->ports[i] == lport) {
395 remove_lport(lswitch, i);
401 VLOG_WARN("logical port %s is not part of any logical switch",
406 do_lport_list(struct ovs_cmdl_context *ctx)
408 struct nbctl_context *nb_ctx = ctx->pvt;
409 const char *id = ctx->argv[1];
410 const struct nbrec_logical_switch *lswitch;
412 lswitch = lswitch_by_name_or_uuid(nb_ctx, id);
417 for (size_t i = 0; i < lswitch->n_ports; i++) {
418 const struct nbrec_logical_port *lport = lswitch->ports[i];
419 printf(UUID_FMT " (%s)\n",
420 UUID_ARGS(&lport->header_.uuid), lport->name);
425 do_lport_get_parent(struct ovs_cmdl_context *ctx)
427 struct nbctl_context *nb_ctx = ctx->pvt;
428 const struct nbrec_logical_port *lport;
430 lport = lport_by_name_or_uuid(nb_ctx, ctx->argv[1]);
435 if (lport->parent_name) {
436 printf("%s\n", lport->parent_name);
441 do_lport_get_tag(struct ovs_cmdl_context *ctx)
443 struct nbctl_context *nb_ctx = ctx->pvt;
444 const struct nbrec_logical_port *lport;
446 lport = lport_by_name_or_uuid(nb_ctx, ctx->argv[1]);
451 if (lport->n_tag > 0) {
452 printf("%"PRId64"\n", lport->tag[0]);
457 do_lport_set_external_id(struct ovs_cmdl_context *ctx)
459 struct nbctl_context *nb_ctx = ctx->pvt;
460 const char *id = ctx->argv[1];
461 const struct nbrec_logical_port *lport;
462 struct smap new_external_ids;
464 lport = lport_by_name_or_uuid(nb_ctx, id);
469 smap_init(&new_external_ids);
470 smap_clone(&new_external_ids, &lport->external_ids);
471 if (ctx->argc == 4) {
472 smap_replace(&new_external_ids, ctx->argv[2], ctx->argv[3]);
474 smap_remove(&new_external_ids, ctx->argv[2]);
476 nbrec_logical_port_set_external_ids(lport, &new_external_ids);
477 smap_destroy(&new_external_ids);
481 do_lport_get_external_id(struct ovs_cmdl_context *ctx)
483 struct nbctl_context *nb_ctx = ctx->pvt;
484 const char *id = ctx->argv[1];
485 const struct nbrec_logical_port *lport;
487 lport = lport_by_name_or_uuid(nb_ctx, id);
492 if (ctx->argc == 3) {
493 const char *key = ctx->argv[2];
496 /* List one external ID */
498 value = smap_get(&lport->external_ids, key);
500 printf("%s\n", value);
503 struct smap_node *node;
505 /* List all external IDs */
507 SMAP_FOR_EACH(node, &lport->external_ids) {
508 printf("%s=%s\n", node->key, node->value);
514 do_lport_set_macs(struct ovs_cmdl_context *ctx)
516 struct nbctl_context *nb_ctx = ctx->pvt;
517 const char *id = ctx->argv[1];
518 const struct nbrec_logical_port *lport;
520 lport = lport_by_name_or_uuid(nb_ctx, id);
525 nbrec_logical_port_set_macs(lport,
526 (const char **) ctx->argv + 2, ctx->argc - 2);
530 do_lport_get_macs(struct ovs_cmdl_context *ctx)
532 struct nbctl_context *nb_ctx = ctx->pvt;
533 const char *id = ctx->argv[1];
534 const struct nbrec_logical_port *lport;
537 lport = lport_by_name_or_uuid(nb_ctx, id);
542 for (i = 0; i < lport->n_macs; i++) {
543 printf("%s\n", lport->macs[i]);
548 do_lport_set_port_security(struct ovs_cmdl_context *ctx)
550 struct nbctl_context *nb_ctx = ctx->pvt;
551 const char *id = ctx->argv[1];
552 const struct nbrec_logical_port *lport;
554 lport = lport_by_name_or_uuid(nb_ctx, id);
559 nbrec_logical_port_set_port_security(lport,
560 (const char **) ctx->argv + 2, ctx->argc - 2);
564 do_lport_get_port_security(struct ovs_cmdl_context *ctx)
566 struct nbctl_context *nb_ctx = ctx->pvt;
567 const char *id = ctx->argv[1];
568 const struct nbrec_logical_port *lport;
571 lport = lport_by_name_or_uuid(nb_ctx, id);
576 for (i = 0; i < lport->n_port_security; i++) {
577 printf("%s\n", lport->port_security[i]);
582 do_lport_get_up(struct ovs_cmdl_context *ctx)
584 struct nbctl_context *nb_ctx = ctx->pvt;
585 const char *id = ctx->argv[1];
586 const struct nbrec_logical_port *lport;
588 lport = lport_by_name_or_uuid(nb_ctx, id);
593 printf("%s\n", (lport->up && *lport->up) ? "up" : "down");
597 do_lport_set_enabled(struct ovs_cmdl_context *ctx)
599 struct nbctl_context *nb_ctx = ctx->pvt;
600 const char *id = ctx->argv[1];
601 const char *state = ctx->argv[2];
602 const struct nbrec_logical_port *lport;
604 lport = lport_by_name_or_uuid(nb_ctx, id);
609 if (!strcasecmp(state, "enabled")) {
611 nbrec_logical_port_set_enabled(lport, &enabled, 1);
612 } else if (!strcasecmp(state, "disabled")) {
613 bool enabled = false;
614 nbrec_logical_port_set_enabled(lport, &enabled, 1);
616 VLOG_ERR("Invalid state '%s' provided to lport-set-enabled", state);
621 do_lport_get_enabled(struct ovs_cmdl_context *ctx)
623 struct nbctl_context *nb_ctx = ctx->pvt;
624 const char *id = ctx->argv[1];
625 const struct nbrec_logical_port *lport;
627 lport = lport_by_name_or_uuid(nb_ctx, id);
633 (!lport->enabled || *lport->enabled) ? "enabled" : "disabled");
637 do_lport_set_type(struct ovs_cmdl_context *ctx)
639 struct nbctl_context *nb_ctx = ctx->pvt;
640 const char *id = ctx->argv[1];
641 const char *type = ctx->argv[2];
642 const struct nbrec_logical_port *lport;
644 lport = lport_by_name_or_uuid(nb_ctx, id);
649 nbrec_logical_port_set_type(lport, type);
653 do_lport_get_type(struct ovs_cmdl_context *ctx)
655 struct nbctl_context *nb_ctx = ctx->pvt;
656 const char *id = ctx->argv[1];
657 const struct nbrec_logical_port *lport;
659 lport = lport_by_name_or_uuid(nb_ctx, id);
664 printf("%s\n", lport->type);
668 do_lport_set_options(struct ovs_cmdl_context *ctx)
670 struct nbctl_context *nb_ctx = ctx->pvt;
671 const char *id = ctx->argv[1];
672 const struct nbrec_logical_port *lport;
674 struct smap options = SMAP_INITIALIZER(&options);
676 lport = lport_by_name_or_uuid(nb_ctx, id);
681 for (i = 2; i < ctx->argc; i++) {
683 value = xstrdup(ctx->argv[i]);
684 key = strsep(&value, "=");
686 smap_add(&options, key, value);
691 nbrec_logical_port_set_options(lport, &options);
693 smap_destroy(&options);
697 do_lport_get_options(struct ovs_cmdl_context *ctx)
699 struct nbctl_context *nb_ctx = ctx->pvt;
700 const char *id = ctx->argv[1];
701 const struct nbrec_logical_port *lport;
702 struct smap_node *node;
704 lport = lport_by_name_or_uuid(nb_ctx, id);
709 SMAP_FOR_EACH(node, &lport->options) {
710 printf("%s=%s\n", node->key, node->value);
715 parse_options(int argc, char *argv[])
720 static const struct option long_options[] = {
721 {"db", required_argument, NULL, 'd'},
722 {"help", no_argument, NULL, 'h'},
723 {"options", no_argument, NULL, 'o'},
724 {"version", no_argument, NULL, 'V'},
726 STREAM_SSL_LONG_OPTIONS,
729 char *short_options = ovs_cmdl_long_options_to_short_options(long_options);
734 c = getopt_long(argc, argv, short_options, long_options, NULL);
740 VLOG_OPTION_HANDLERS;
741 STREAM_SSL_OPTION_HANDLERS;
752 ovs_cmdl_print_options(long_options);
756 ovs_print_version(0, 0);
771 static const struct ovs_cmdl_command all_commands[] = {
774 .usage = "[LSWITCH]",
780 .name = "lswitch-add",
781 .usage = "[LSWITCH]",
784 .handler = do_lswitch_add,
787 .name = "lswitch-del",
791 .handler = do_lswitch_del,
794 .name = "lswitch-list",
798 .handler = do_lswitch_list,
801 .name = "lswitch-set-external-id",
802 .usage = "LSWITCH KEY [VALUE]",
805 .handler = do_lswitch_set_external_id,
808 .name = "lswitch-get-external-id",
809 .usage = "LSWITCH [KEY]",
812 .handler = do_lswitch_get_external_id,
816 .usage = "LSWITCH LPORT [PARENT] [TAG]",
819 .handler = do_lport_add,
826 .handler = do_lport_del,
829 .name = "lport-list",
833 .handler = do_lport_list,
836 .name = "lport-get-parent",
840 .handler = do_lport_get_parent,
843 .name = "lport-get-tag",
847 .handler = do_lport_get_tag,
850 .name = "lport-set-external-id",
851 .usage = "LPORT KEY [VALUE]",
854 .handler = do_lport_set_external_id,
857 .name = "lport-get-external-id",
858 .usage = "LPORT [KEY]",
861 .handler = do_lport_get_external_id,
864 .name = "lport-set-macs",
865 .usage = "LPORT [MAC]...",
867 /* Accept however many arguments the system will allow. */
869 .handler = do_lport_set_macs,
872 .name = "lport-get-macs",
876 .handler = do_lport_get_macs,
879 .name = "lport-set-port-security",
880 .usage = "LPORT [ADDRS]...",
882 /* Accept however many arguments the system will allow. */
884 .handler = do_lport_set_port_security,
887 .name = "lport-get-port-security",
891 .handler = do_lport_get_port_security,
894 .name = "lport-get-up",
898 .handler = do_lport_get_up,
901 .name = "lport-set-enabled",
902 .usage = "LPORT STATE",
905 .handler = do_lport_set_enabled,
908 .name = "lport-get-enabled",
912 .handler = do_lport_get_enabled,
915 .name = "lport-set-type",
916 .usage = "LPORT TYPE",
919 .handler = do_lport_set_type,
922 .name = "lport-get-type",
926 .handler = do_lport_get_type,
929 .name = "lport-set-options",
930 .usage = "LPORT KEY=VALUE [KEY=VALUE]...",
933 .handler = do_lport_set_options
936 .name = "lport-get-options",
940 .handler = do_lport_get_options,
949 static const struct ovs_cmdl_command *
950 get_all_commands(void)
960 def = getenv("OVN_NB_DB");
962 def = xasprintf("unix:%s/db.sock", ovs_rundir());
969 main(int argc, char *argv[])
971 extern struct vlog_module VLM_reconnect;
972 struct ovs_cmdl_context ctx;
973 struct nbctl_context nb_ctx = { .idl = NULL, };
974 enum ovsdb_idl_txn_status txn_status;
979 fatal_ignore_sigpipe();
980 set_program_name(argv[0]);
981 vlog_set_levels(NULL, VLF_CONSOLE, VLL_WARN);
982 vlog_set_levels(&VLM_reconnect, VLF_ANY_DESTINATION, VLL_WARN);
983 parse_options(argc, argv);
986 args = process_escape_args(argv);
988 nb_ctx.idl = ovsdb_idl_create(db, &nbrec_idl_class, true, false);
990 ctx.argc = argc - optind;
991 ctx.argv = argv + optind;
993 seqno = ovsdb_idl_get_seqno(nb_ctx.idl);
995 ovsdb_idl_run(nb_ctx.idl);
997 if (!ovsdb_idl_is_alive(nb_ctx.idl)) {
998 int retval = ovsdb_idl_get_last_error(nb_ctx.idl);
999 VLOG_ERR("%s: database connection failed (%s)",
1000 db, ovs_retval_to_string(retval));
1005 if (seqno != ovsdb_idl_get_seqno(nb_ctx.idl)) {
1006 nb_ctx.txn = ovsdb_idl_txn_create(nb_ctx.idl);
1007 ovsdb_idl_txn_add_comment(nb_ctx.txn, "ovn-nbctl: %s", args);
1008 ovs_cmdl_run_command(&ctx, get_all_commands());
1009 txn_status = ovsdb_idl_txn_commit_block(nb_ctx.txn);
1010 if (txn_status == TXN_TRY_AGAIN) {
1011 ovsdb_idl_txn_destroy(nb_ctx.txn);
1019 if (seqno == ovsdb_idl_get_seqno(nb_ctx.idl)) {
1020 ovsdb_idl_wait(nb_ctx.idl);
1026 ovsdb_idl_txn_destroy(nb_ctx.txn);
1028 ovsdb_idl_destroy(nb_ctx.idl);