ovs-vsctl: Add --dry-run option.
[sliver-openvswitch.git] / utilities / ovs-vsctl.c
1 /*
2  * Copyright (c) 2009 Nicira Networks.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at:
7  *
8  *     http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include <config.h>
18
19 #include <assert.h>
20 #include <errno.h>
21 #include <getopt.h>
22 #include <inttypes.h>
23 #include <signal.h>
24 #include <stdarg.h>
25 #include <stdlib.h>
26 #include <string.h>
27
28 #include "command-line.h"
29 #include "compiler.h"
30 #include "dirs.h"
31 #include "dynamic-string.h"
32 #include "ovsdb-idl.h"
33 #include "poll-loop.h"
34 #include "svec.h"
35 #include "vswitchd/vswitch-idl.h"
36 #include "timeval.h"
37 #include "util.h"
38
39 #include "vlog.h"
40 #define THIS_MODULE VLM_vsctl
41
42 /* --db: The database server to contact. */
43 static const char *db;
44
45 /* --oneline: Write each command's output as a single line? */
46 static bool oneline;
47
48 /* --dry-run: Do not commit any changes. */
49 static bool dry_run;
50
51 static void vsctl_fatal(const char *, ...) PRINTF_FORMAT(1, 2) NO_RETURN;
52 static char *default_db(void);
53 static void usage(void) NO_RETURN;
54 static void parse_options(int argc, char *argv[]);
55
56 static void check_vsctl_command(int argc, char *argv[]);
57 static void do_vsctl(int argc, char *argv[], struct ovsdb_idl *idl);
58
59 int
60 main(int argc, char *argv[])
61 {
62     struct ovsdb_idl *idl;
63     unsigned int seqno;
64     struct ds args;
65     int start, n_commands;
66     int trials;
67     int i;
68
69     set_program_name(argv[0]);
70     signal(SIGPIPE, SIG_IGN);
71     time_init();
72     vlog_init();
73     vlog_set_levels(VLM_ANY_MODULE, VLF_CONSOLE, VLL_WARN);
74     vlog_set_levels(VLM_reconnect, VLF_ANY_FACILITY, VLL_WARN);
75     parse_options(argc, argv);
76
77     /* Log our arguments.  This is often valuable for debugging systems. */
78     ds_init(&args);
79     for (i = 1; i < argc; i++) {
80         ds_put_format(&args, " %s", argv[i]);
81     }
82     VLOG_INFO("Called as%s", ds_cstr(&args));
83     ds_destroy(&args);
84
85     /* Do basic command syntax checking. */
86     n_commands = 0;
87     for (start = i = optind; i <= argc; i++) {
88         if (i == argc || !strcmp(argv[i], "--")) {
89             if (i > start) {
90                 check_vsctl_command(i - start, &argv[start]);
91                 n_commands++;
92             }
93             start = i + 1;
94         }
95     }
96     if (!n_commands) {
97         vsctl_fatal("missing command name (use --help for help)");
98     }
99
100     /* Now execute the commands. */
101     idl = ovsdb_idl_create(db, &ovsrec_idl_class);
102     seqno = ovsdb_idl_get_seqno(idl);
103     trials = 0;
104     for (;;) {
105         unsigned int new_seqno;
106
107         ovsdb_idl_run(idl);
108         new_seqno = ovsdb_idl_get_seqno(idl);
109         if (new_seqno != seqno) {
110             if (++trials > 5) {
111                 vsctl_fatal("too many database inconsistency failures");
112             }
113             do_vsctl(argc - optind, argv + optind, idl);
114             seqno = new_seqno;
115         }
116
117         ovsdb_idl_wait(idl);
118         poll_block();
119     }
120 }
121
122 static void
123 vsctl_fatal(const char *format, ...)
124 {
125     char *message;
126     va_list args;
127
128     va_start(args, format);
129     message = xvasprintf(format, args);
130     va_end(args);
131
132     vlog_set_levels(VLM_vsctl, VLF_CONSOLE, VLL_EMER);
133     VLOG_ERR("%s", message);
134     ovs_fatal(0, "%s", message);
135 }
136
137 static void
138 parse_options(int argc, char *argv[])
139 {
140     enum {
141         OPT_DB = UCHAR_MAX + 1,
142         OPT_ONELINE,
143         OPT_NO_SYSLOG,
144         OPT_NO_WAIT,
145         OPT_DRY_RUN
146     };
147     static struct option long_options[] = {
148         {"db", required_argument, 0, OPT_DB},
149         {"no-syslog", no_argument, 0, OPT_NO_SYSLOG},
150         {"no-wait", no_argument, 0, OPT_NO_WAIT},
151         {"dry-run", no_argument, 0, OPT_DRY_RUN},
152         {"oneline", no_argument, 0, OPT_ONELINE},
153         {"verbose", optional_argument, 0, 'v'},
154         {"help", no_argument, 0, 'h'},
155         {"version", no_argument, 0, 'V'},
156         {0, 0, 0, 0},
157     };
158
159     for (;;) {
160         int c;
161
162         c = getopt_long(argc, argv, "+v::hV", long_options, NULL);
163         if (c == -1) {
164             break;
165         }
166
167         switch (c) {
168         case OPT_DB:
169             db = optarg;
170             break;
171
172         case OPT_ONELINE:
173             oneline = true;
174             break;
175
176         case OPT_NO_SYSLOG:
177             vlog_set_levels(VLM_vsctl, VLF_SYSLOG, VLL_WARN);
178             break;
179
180         case OPT_NO_WAIT:
181             /* XXX not yet implemented */
182             break;
183
184         case OPT_DRY_RUN:
185             dry_run = true;
186             break;
187
188         case 'h':
189             usage();
190
191         case 'V':
192             OVS_PRINT_VERSION(0, 0);
193             exit(EXIT_SUCCESS);
194
195         case 'v':
196             vlog_set_verbosity(optarg);
197             break;
198
199         case '?':
200             exit(EXIT_FAILURE);
201
202         default:
203             abort();
204         }
205     }
206
207     if (!db) {
208         db = default_db();
209     }
210 }
211
212 static void
213 usage(void)
214 {
215     printf("%s: ovs-vswitchd management utility\n"
216            "usage: %s [OPTIONS] COMMAND [ARG...]\n",
217            program_name, program_name);
218     printf("\nBridge commands:\n"
219            "  add-br BRIDGE               "
220            "create a new bridge named BRIDGE\n"
221            "  add-br BRIDGE PARENT VLAN   "
222            "create new fake bridge BRIDGE in PARENT on VLAN\n"
223            "  del-br BRIDGE               "
224            "delete BRIDGE and all of its ports\n"
225            "  list-br                     "
226            "print the names of all the bridges\n"
227            "  br-exists BRIDGE            "
228            "test whether BRIDGE exists\n"
229            "  br-to-vlan BRIDGE           "
230            "print the VLAN which BRIDGE is on\n"
231            "  br-to-parent BRIDGE         "
232            "print the parent of BRIDGE\n"
233            "  br-set-external-id BRIDGE KEY VALUE"
234            "  set KEY on BRIDGE to VALUE\n"
235            "  br-set-external-id BRIDGE KEY"
236            "  unset KEY on BRIDGE\n"
237            "  br-get-external-id BRIDGE KEY"
238            "  print value of KEY on BRIDGE\n"
239            "  br-get-external-id BRIDGE"
240            "  list key-value pairs on BRIDGE\n"
241         );
242     printf("\nPort commands:\n"
243            "  list-ports BRIDGE           "
244            "print the names of all the ports on BRIDGE\n"
245            "  add-port BRIDGE PORT        "
246            "add network device PORT to BRIDGE\n"
247            "  add-bond BRIDGE PORT IFACE...  "
248            "add new bonded port PORT in BRIDGE from IFACES\n"
249            "  del-port [BRIDGE] PORT      "
250            "delete PORT (which may be bonded) from BRIDGE\n"
251            "  port-to-br PORT             "
252            "print name of bridge that contains PORT\n"
253            "  port-set-external-id PORT KEY VALUE"
254            "  set KEY on PORT to VALUE\n"
255            "  port-set-external-id PORT KEY"
256            "  unset KEY on PORT\n"
257            "  port-get-external-id PORT KEY"
258            "  print value of KEY on PORT\n"
259            "  port-get-external-id PORT"
260            "  list key-value pairs on PORT\n"
261            "A bond is considered to be a single port.\n"
262         );
263     printf("\nInterface commands (a bond consists of multiple interfaces):\n"
264            "  list-ifaces BRIDGE          "
265            "print the names of all the interfaces on BRIDGE\n"
266            "  iface-to-br IFACE           "
267            "print name of bridge that contains IFACE\n"
268            "  iface-set-external-id IFACE KEY VALUE"
269            "  set KEY on IFACE to VALUE\n"
270            "  iface-set-external-id IFACE KEY"
271            "  unset KEY on IFACE\n"
272            "  iface-get-external-id IFACE KEY"
273            "  print value of KEY on IFACE\n"
274            "  iface-get-external-id IFACE"
275            "  list key-value pairs on IFACE\n"
276         );
277     printf("\nOptions:\n"
278            "  --db=DATABASE               "
279            "connect to DATABASE\n"
280            "                              "
281            "(default: %s)\n"
282            "  --oneline                   "
283            "print exactly one line of output per command\n",
284            default_db());
285     vlog_usage();
286     printf("\nOther options:\n"
287            "  -h, --help                  "
288            "display this help message\n"
289            "  -V, --version               "
290            "display version information\n");
291     exit(EXIT_SUCCESS);
292 }
293
294 static char *
295 default_db(void)
296 {
297     static char *def;
298     if (!def) {
299         def = xasprintf("unix:%s/ovsdb-server", ovs_rundir);
300     }
301     return def;
302 }
303 \f
304 struct vsctl_context {
305     int argc;
306     char **argv;
307     const struct ovsrec_open_vswitch *ovs;
308     struct ds output;
309     struct shash options;
310 };
311
312 struct vsctl_bridge {
313     struct ovsrec_bridge *br_cfg;
314     char *name;
315     struct vsctl_bridge *parent;
316     int vlan;
317 };
318
319 struct vsctl_port {
320     struct ovsrec_port *port_cfg;
321     struct vsctl_bridge *bridge;
322 };
323
324 struct vsctl_iface {
325     struct ovsrec_interface *iface_cfg;
326     struct vsctl_port *port;
327 };
328
329 struct vsctl_info {
330     struct shash bridges;
331     struct shash ports;
332     struct shash ifaces;
333 };
334
335 static struct ovsdb_idl_txn *
336 txn_from_openvswitch(const struct ovsrec_open_vswitch *ovs)
337 {
338     return ovsdb_idl_txn_get(&ovs->header_);
339 }
340
341 static struct vsctl_bridge *
342 add_bridge(struct vsctl_info *b,
343            struct ovsrec_bridge *br_cfg, const char *name,
344            struct vsctl_bridge *parent, int vlan)
345 {
346     struct vsctl_bridge *br = xmalloc(sizeof *br);
347     br->br_cfg = br_cfg;
348     br->name = xstrdup(name);
349     br->parent = parent;
350     br->vlan = vlan;
351     shash_add(&b->bridges, br->name, br);
352     return br;
353 }
354
355 static bool
356 port_is_fake_bridge(const struct ovsrec_port *port_cfg)
357 {
358     return (port_cfg->fake_bridge
359             && port_cfg->tag
360             && *port_cfg->tag >= 1 && *port_cfg->tag <= 4095);
361 }
362
363 static struct vsctl_bridge *
364 find_vlan_bridge(struct vsctl_info *info,
365                  struct vsctl_bridge *parent, int vlan)
366 {
367     struct shash_node *node;
368
369     SHASH_FOR_EACH (node, &info->bridges) {
370         struct vsctl_bridge *br = node->data;
371         if (br->parent == parent && br->vlan == vlan) {
372             return br;
373         }
374     }
375
376     return NULL;
377 }
378
379 static void
380 free_info(struct vsctl_info *info)
381 {
382     struct shash_node *node;
383
384     SHASH_FOR_EACH (node, &info->bridges) {
385         struct vsctl_bridge *bridge = node->data;
386         free(bridge->name);
387         free(bridge);
388     }
389     shash_destroy(&info->bridges);
390
391     SHASH_FOR_EACH (node, &info->ports) {
392         struct vsctl_port *port = node->data;
393         free(port);
394     }
395     shash_destroy(&info->ports);
396
397     SHASH_FOR_EACH (node, &info->ifaces) {
398         struct vsctl_iface *iface = node->data;
399         free(iface);
400     }
401     shash_destroy(&info->ifaces);
402 }
403
404 static void
405 get_info(const struct ovsrec_open_vswitch *ovs, struct vsctl_info *info)
406 {
407     struct shash bridges, ports;
408     size_t i;
409
410     shash_init(&info->bridges);
411     shash_init(&info->ports);
412     shash_init(&info->ifaces);
413
414     shash_init(&bridges);
415     shash_init(&ports);
416     for (i = 0; i < ovs->n_bridges; i++) {
417         struct ovsrec_bridge *br_cfg = ovs->bridges[i];
418         struct vsctl_bridge *br;
419         size_t j;
420
421         if (!shash_add_once(&bridges, br_cfg->name, NULL)) {
422             VLOG_WARN("%s: database contains duplicate bridge name",
423                       br_cfg->name);
424             continue;
425         }
426         br = add_bridge(info, br_cfg, br_cfg->name, NULL, 0);
427         if (!br) {
428             continue;
429         }
430
431         for (j = 0; j < br_cfg->n_ports; j++) {
432             struct ovsrec_port *port_cfg = br_cfg->ports[j];
433
434             if (!shash_add_once(&ports, port_cfg->name, NULL)) {
435                 VLOG_WARN("%s: database contains duplicate port name",
436                           port_cfg->name);
437                 continue;
438             }
439
440             if (port_is_fake_bridge(port_cfg)
441                 && shash_add_once(&bridges, port_cfg->name, NULL)) {
442                 add_bridge(info, NULL, port_cfg->name, br, *port_cfg->tag);
443             }
444         }
445     }
446     shash_destroy(&bridges);
447     shash_destroy(&ports);
448
449     shash_init(&bridges);
450     shash_init(&ports);
451     for (i = 0; i < ovs->n_bridges; i++) {
452         struct ovsrec_bridge *br_cfg = ovs->bridges[i];
453         struct vsctl_bridge *br;
454         size_t j;
455
456         if (!shash_add_once(&bridges, br_cfg->name, NULL)) {
457             continue;
458         }
459         br = shash_find_data(&info->bridges, br_cfg->name);
460         for (j = 0; j < br_cfg->n_ports; j++) {
461             struct ovsrec_port *port_cfg = br_cfg->ports[j];
462             struct vsctl_port *port;
463             size_t k;
464
465             if (!shash_add_once(&ports, port_cfg->name, NULL)) {
466                 continue;
467             }
468
469             if (port_is_fake_bridge(port_cfg)
470                 && !shash_add_once(&bridges, port_cfg->name, NULL)) {
471                 continue;
472             }
473
474             port = xmalloc(sizeof *port);
475             port->port_cfg = port_cfg;
476             if (port_cfg->tag
477                 && *port_cfg->tag >= 1 && *port_cfg->tag <= 4095) {
478                 port->bridge = find_vlan_bridge(info, br, *port_cfg->tag);
479                 if (!port->bridge) {
480                     port->bridge = br;
481                 }
482             } else {
483                 port->bridge = br;
484             }
485             shash_add(&info->ports, port_cfg->name, port);
486
487             for (k = 0; k < port_cfg->n_interfaces; k++) {
488                 struct ovsrec_interface *iface_cfg = port_cfg->interfaces[k];
489                 struct vsctl_iface *iface;
490
491                 if (shash_find(&info->ifaces, iface_cfg->name)) {
492                     VLOG_WARN("%s: database contains duplicate interface name",
493                               iface_cfg->name);
494                     continue;
495                 }
496
497                 iface = xmalloc(sizeof *iface);
498                 iface->iface_cfg = iface_cfg;
499                 iface->port = port;
500                 shash_add(&info->ifaces, iface_cfg->name, iface);
501             }
502         }
503     }
504     shash_destroy(&bridges);
505     shash_destroy(&ports);
506 }
507
508 static void
509 check_conflicts(struct vsctl_info *info, const char *name,
510                 char *msg)
511 {
512     struct vsctl_iface *iface;
513     struct vsctl_port *port;
514
515     if (shash_find(&info->bridges, name)) {
516         vsctl_fatal("%s because a bridge named %s already exists",
517                     msg, name);
518     }
519
520     port = shash_find_data(&info->ports, name);
521     if (port) {
522         vsctl_fatal("%s because a port named %s already exists on "
523                     "bridge %s", msg, name, port->bridge->name);
524     }
525
526     iface = shash_find_data(&info->ifaces, name);
527     if (iface) {
528         vsctl_fatal("%s because an interface named %s already exists "
529                     "on bridge %s", msg, name, iface->port->bridge->name);
530     }
531
532     free(msg);
533 }
534
535 static struct vsctl_bridge *
536 find_bridge(struct vsctl_info *info, const char *name, bool must_exist)
537 {
538     struct vsctl_bridge *br = shash_find_data(&info->bridges, name);
539     if (must_exist && !br) {
540         vsctl_fatal("no bridge named %s", name);
541     }
542     return br;
543 }
544
545 static struct vsctl_port *
546 find_port(struct vsctl_info *info, const char *name, bool must_exist)
547 {
548     struct vsctl_port *port = shash_find_data(&info->ports, name);
549     if (port && !strcmp(name, port->bridge->name)) {
550         port = NULL;
551     }
552     if (must_exist && !port) {
553         vsctl_fatal("no port named %s", name);
554     }
555     return port;
556 }
557
558 static struct vsctl_iface *
559 find_iface(struct vsctl_info *info, const char *name, bool must_exist)
560 {
561     struct vsctl_iface *iface = shash_find_data(&info->ifaces, name);
562     if (iface && !strcmp(name, iface->port->bridge->name)) {
563         iface = NULL;
564     }
565     if (must_exist && !iface) {
566         vsctl_fatal("no interface named %s", name);
567     }
568     return iface;
569 }
570
571 static void
572 bridge_insert_port(struct ovsrec_bridge *br, struct ovsrec_port *port)
573 {
574     struct ovsrec_port **ports;
575     size_t i;
576
577     ports = xmalloc(sizeof *br->ports * (br->n_ports + 1));
578     for (i = 0; i < br->n_ports; i++) {
579         ports[i] = br->ports[i];
580     }
581     ports[br->n_ports] = port;
582     ovsrec_bridge_set_ports(br, ports, br->n_ports + 1);
583     free(ports);
584 }
585
586 static void
587 bridge_delete_port(struct ovsrec_bridge *br, struct ovsrec_port *port)
588 {
589     struct ovsrec_port **ports;
590     size_t i, n;
591
592     ports = xmalloc(sizeof *br->ports * br->n_ports);
593     for (i = n = 0; i < br->n_ports; i++) {
594         if (br->ports[i] != port) {
595             ports[n++] = br->ports[i];
596         }
597     }
598     ovsrec_bridge_set_ports(br, ports, n);
599     free(ports);
600 }
601
602 static void
603 ovs_insert_bridge(const struct ovsrec_open_vswitch *ovs,
604                   struct ovsrec_bridge *bridge)
605 {
606     struct ovsrec_bridge **bridges;
607     size_t i;
608
609     bridges = xmalloc(sizeof *ovs->bridges * (ovs->n_bridges + 1));
610     for (i = 0; i < ovs->n_bridges; i++) {
611         bridges[i] = ovs->bridges[i];
612     }
613     bridges[ovs->n_bridges] = bridge;
614     ovsrec_open_vswitch_set_bridges(ovs, bridges, ovs->n_bridges + 1);
615     free(bridges);
616 }
617
618 static void
619 ovs_delete_bridge(const struct ovsrec_open_vswitch *ovs,
620                   struct ovsrec_bridge *bridge)
621 {
622     struct ovsrec_bridge **bridges;
623     size_t i, n;
624
625     bridges = xmalloc(sizeof *ovs->bridges * ovs->n_bridges);
626     for (i = n = 0; i < ovs->n_bridges; i++) {
627         if (ovs->bridges[i] != bridge) {
628             bridges[n++] = ovs->bridges[i];
629         }
630     }
631     ovsrec_open_vswitch_set_bridges(ovs, bridges, n);
632     free(bridges);
633 }
634
635 static void
636 cmd_init(struct vsctl_context *ctx UNUSED)
637 {
638 }
639
640 static void
641 cmd_add_br(struct vsctl_context *ctx)
642 {
643     const char *br_name = ctx->argv[1];
644     struct vsctl_info info;
645
646     get_info(ctx->ovs, &info);
647     check_conflicts(&info, br_name,
648                     xasprintf("cannot create a bridge named %s", br_name));
649
650     if (ctx->argc == 2) {
651         struct ovsrec_bridge *br;
652         struct ovsrec_port *port;
653         struct ovsrec_interface *iface;
654
655         iface = ovsrec_interface_insert(txn_from_openvswitch(ctx->ovs));
656         ovsrec_interface_set_name(iface, br_name);
657
658         port = ovsrec_port_insert(txn_from_openvswitch(ctx->ovs));
659         ovsrec_port_set_name(port, br_name);
660         ovsrec_port_set_interfaces(port, &iface, 1);
661
662         br = ovsrec_bridge_insert(txn_from_openvswitch(ctx->ovs));
663         ovsrec_bridge_set_name(br, br_name);
664         ovsrec_bridge_set_ports(br, &port, 1);
665
666         ovs_insert_bridge(ctx->ovs, br);
667     } else if (ctx->argc == 3) {
668         vsctl_fatal("'%s' command takes exactly 1 or 3 arguments",
669                     ctx->argv[0]);
670     } else if (ctx->argc == 4) {
671         const char *parent_name = ctx->argv[2];
672         int vlan = atoi(ctx->argv[3]);
673         struct ovsrec_bridge *br;
674         struct vsctl_bridge *parent;
675         struct ovsrec_port *port;
676         struct ovsrec_interface *iface;
677         int64_t tag = vlan;
678
679         if (vlan < 1 || vlan > 4095) {
680             vsctl_fatal("%s: vlan must be between 1 and 4095", ctx->argv[0]);
681         }
682
683         parent = find_bridge(&info, parent_name, false);
684         if (parent && parent->vlan) {
685             vsctl_fatal("cannot create brdige with fake bridge as parent");
686         }
687         if (!parent) {
688             vsctl_fatal("parent bridge %s does not exist", parent_name);
689         }
690         br = parent->br_cfg;
691
692         iface = ovsrec_interface_insert(txn_from_openvswitch(ctx->ovs));
693         ovsrec_interface_set_name(iface, br_name);
694         ovsrec_interface_set_type(iface, "internal");
695
696         port = ovsrec_port_insert(txn_from_openvswitch(ctx->ovs));
697         ovsrec_port_set_name(port, br_name);
698         ovsrec_port_set_interfaces(port, &iface, 1);
699         ovsrec_port_set_fake_bridge(port, true);
700         ovsrec_port_set_tag(port, &tag, 1);
701
702         bridge_insert_port(br, port);
703     } else {
704         NOT_REACHED();
705     }
706
707     free_info(&info);
708 }
709
710 static void
711 del_port(struct vsctl_info *info, struct vsctl_port *port)
712 {
713     struct shash_node *node;
714
715     SHASH_FOR_EACH (node, &info->ifaces) {
716         struct vsctl_iface *iface = node->data;
717         if (iface->port == port) {
718             ovsrec_interface_delete(iface->iface_cfg);
719         }
720     }
721     ovsrec_port_delete(port->port_cfg);
722
723     bridge_delete_port((port->bridge->parent
724                         ? port->bridge->parent->br_cfg
725                         : port->bridge->br_cfg), port->port_cfg);
726 }
727
728 static void
729 cmd_del_br(struct vsctl_context *ctx)
730 {
731     bool must_exist = !shash_find(&ctx->options, "--if-exists");
732     struct vsctl_bridge *bridge;
733     struct vsctl_info info;
734
735     get_info(ctx->ovs, &info);
736     bridge = find_bridge(&info, ctx->argv[1], must_exist);
737     if (bridge) {
738         struct shash_node *node;
739
740         SHASH_FOR_EACH (node, &info.ports) {
741             struct vsctl_port *port = node->data;
742             if (port->bridge == bridge
743                 || !strcmp(port->port_cfg->name, bridge->name)) {
744                 del_port(&info, port);
745             }
746         }
747         if (bridge->br_cfg) {
748             ovsrec_bridge_delete(bridge->br_cfg);
749             ovs_delete_bridge(ctx->ovs, bridge->br_cfg);
750         }
751     }
752     free_info(&info);
753 }
754
755 static void
756 output_sorted(struct svec *svec, struct ds *output)
757 {
758     const char *name;
759     size_t i;
760
761     svec_sort(svec);
762     SVEC_FOR_EACH (i, name, svec) {
763         ds_put_format(output, "%s\n", name);
764     }
765 }
766
767 static void
768 cmd_list_br(struct vsctl_context *ctx)
769 {
770     struct shash_node *node;
771     struct vsctl_info info;
772     struct svec bridges;
773
774     get_info(ctx->ovs, &info);
775
776     svec_init(&bridges);
777     SHASH_FOR_EACH (node, &info.bridges) {
778         struct vsctl_bridge *br = node->data;
779         svec_add(&bridges, br->name);
780     }
781     output_sorted(&bridges, &ctx->output);
782     svec_destroy(&bridges);
783
784     free_info(&info);
785 }
786
787 static void
788 cmd_br_exists(struct vsctl_context *ctx)
789 {
790     struct vsctl_info info;
791
792     get_info(ctx->ovs, &info);
793     if (!find_bridge(&info, ctx->argv[1], false)) {
794         exit(2);
795     }
796     free_info(&info);
797 }
798
799 /* Returns true if 'b_prefix' (of length 'b_prefix_len') concatenated with 'b'
800  * equals 'a', false otherwise. */
801 static bool
802 key_matches(const char *a,
803             const char *b_prefix, size_t b_prefix_len, const char *b)
804 {
805     return !strncmp(a, b_prefix, b_prefix_len) && !strcmp(a + b_prefix_len, b);
806 }
807
808 static void
809 set_external_id(char **old_keys, char **old_values, size_t old_n,
810                 char *key, char *value,
811                 char ***new_keysp, char ***new_valuesp, size_t *new_np)
812 {
813     char **new_keys;
814     char **new_values;
815     size_t new_n;
816     size_t i;
817
818     new_keys = xmalloc(sizeof *new_keys * (old_n + 1));
819     new_values = xmalloc(sizeof *new_values * (old_n + 1));
820     new_n = 0;
821     for (i = 0; i < old_n; i++) {
822         if (strcmp(key, old_keys[i])) {
823             new_keys[new_n] = old_keys[i];
824             new_values[new_n] = old_values[i];
825             new_n++;
826         }
827     }
828     if (value) {
829         new_keys[new_n] = key;
830         new_values[new_n] = value;
831         new_n++;
832     }
833     *new_keysp = new_keys;
834     *new_valuesp = new_values;
835     *new_np = new_n;
836 }
837
838 static void
839 cmd_br_set_external_id(struct vsctl_context *ctx)
840 {
841     struct vsctl_info info;
842     struct vsctl_bridge *bridge;
843     char **keys, **values;
844     size_t n;
845
846     get_info(ctx->ovs, &info);
847     bridge = find_bridge(&info, ctx->argv[1], true);
848     if (bridge->br_cfg) {
849         set_external_id(bridge->br_cfg->key_external_ids,
850                         bridge->br_cfg->value_external_ids,
851                         bridge->br_cfg->n_external_ids,
852                         ctx->argv[2], ctx->argc >= 4 ? ctx->argv[3] : NULL,
853                         &keys, &values, &n);
854         ovsrec_bridge_set_external_ids(bridge->br_cfg, keys, values, n);
855     } else {
856         char *key = xasprintf("fake-bridge-%s", ctx->argv[2]);
857         struct vsctl_port *port = shash_find_data(&info.ports, ctx->argv[1]);
858         set_external_id(port->port_cfg->key_external_ids,
859                         port->port_cfg->value_external_ids,
860                         port->port_cfg->n_external_ids,
861                         key, ctx->argc >= 4 ? ctx->argv[3] : NULL,
862                         &keys, &values, &n);
863         ovsrec_port_set_external_ids(port->port_cfg, keys, values, n);
864         free(key);
865     }
866     free(keys);
867     free(values);
868
869     free_info(&info);
870 }
871
872 static void
873 get_external_id(char **keys, char **values, size_t n,
874                 const char *prefix, const char *key,
875                 struct ds *output)
876 {
877     size_t prefix_len = strlen(prefix);
878     struct svec svec;
879     size_t i;
880
881     svec_init(&svec);
882     for (i = 0; i < n; i++) {
883         if (!key && !strncmp(keys[i], prefix, prefix_len)) {
884             svec_add_nocopy(&svec, xasprintf("%s=%s",
885                                              keys[i] + prefix_len, values[i]));
886         } else if (key_matches(keys[i], prefix, prefix_len, key)) {
887             svec_add(&svec, values[i]);
888             break;
889         }
890     }
891     output_sorted(&svec, output);
892     svec_destroy(&svec);
893 }
894
895 static void
896 cmd_br_get_external_id(struct vsctl_context *ctx)
897 {
898     struct vsctl_info info;
899     struct vsctl_bridge *bridge;
900
901     get_info(ctx->ovs, &info);
902     bridge = find_bridge(&info, ctx->argv[1], true);
903     if (bridge->br_cfg) {
904         get_external_id(bridge->br_cfg->key_external_ids,
905                         bridge->br_cfg->value_external_ids,
906                         bridge->br_cfg->n_external_ids,
907                         "", ctx->argc >= 3 ? ctx->argv[2] : NULL,
908                         &ctx->output);
909     } else {
910         struct vsctl_port *port = shash_find_data(&info.ports, ctx->argv[1]);
911         get_external_id(port->port_cfg->key_external_ids,
912                         port->port_cfg->value_external_ids,
913                         port->port_cfg->n_external_ids,
914                         "fake-bridge-", ctx->argc >= 3 ? ctx->argv[2] : NULL, &ctx->output);
915     }
916     free_info(&info);
917 }
918
919
920 static void
921 cmd_list_ports(struct vsctl_context *ctx)
922 {
923     struct vsctl_bridge *br;
924     struct shash_node *node;
925     struct vsctl_info info;
926     struct svec ports;
927
928     get_info(ctx->ovs, &info);
929     br = find_bridge(&info, ctx->argv[1], true);
930
931     svec_init(&ports);
932     SHASH_FOR_EACH (node, &info.ports) {
933         struct vsctl_port *port = node->data;
934
935         if (strcmp(port->port_cfg->name, br->name) && br == port->bridge) {
936             svec_add(&ports, port->port_cfg->name);
937         }
938     }
939     output_sorted(&ports, &ctx->output);
940     svec_destroy(&ports);
941
942     free_info(&info);
943 }
944
945 static void
946 add_port(const struct ovsrec_open_vswitch *ovs,
947          const char *br_name, const char *port_name,
948          char *iface_names[], int n_ifaces)
949 {
950     struct vsctl_info info;
951     struct vsctl_bridge *bridge;
952     struct ovsrec_interface **ifaces;
953     struct ovsrec_port *port;
954     size_t i;
955
956     get_info(ovs, &info);
957     check_conflicts(&info, port_name,
958                     xasprintf("cannot create a port named %s", port_name));
959     /* XXX need to check for conflicts on interfaces too */
960     bridge = find_bridge(&info, br_name, true);
961
962     ifaces = xmalloc(n_ifaces * sizeof *ifaces);
963     for (i = 0; i < n_ifaces; i++) {
964         ifaces[i] = ovsrec_interface_insert(txn_from_openvswitch(ovs));
965         ovsrec_interface_set_name(ifaces[i], iface_names[i]);
966     }
967
968     port = ovsrec_port_insert(txn_from_openvswitch(ovs));
969     ovsrec_port_set_name(port, port_name);
970     ovsrec_port_set_interfaces(port, ifaces, n_ifaces);
971     free(ifaces);
972
973     if (bridge->vlan) {
974         int64_t tag = bridge->vlan;
975         ovsrec_port_set_tag(port, &tag, 1);
976     }
977
978     bridge_insert_port((bridge->parent ? bridge->parent->br_cfg
979                         : bridge->br_cfg), port);
980
981     free_info(&info);
982 }
983
984 static void
985 cmd_add_port(struct vsctl_context *ctx)
986 {
987     add_port(ctx->ovs, ctx->argv[1], ctx->argv[2], &ctx->argv[2], 1);
988 }
989
990 static void
991 cmd_add_bond(struct vsctl_context *ctx)
992 {
993     add_port(ctx->ovs, ctx->argv[1], ctx->argv[2], &ctx->argv[3], ctx->argc - 3);
994 }
995
996 static void
997 cmd_del_port(struct vsctl_context *ctx)
998 {
999     bool must_exist = !shash_find(&ctx->options, "--if-exists");
1000     struct vsctl_info info;
1001
1002     get_info(ctx->ovs, &info);
1003     if (ctx->argc == 2) {
1004         struct vsctl_port *port = find_port(&info, ctx->argv[1], must_exist);
1005         if (port) {
1006             del_port(&info, port);
1007         }
1008     } else if (ctx->argc == 3) {
1009         struct vsctl_bridge *bridge = find_bridge(&info, ctx->argv[1], true);
1010         struct vsctl_port *port = find_port(&info, ctx->argv[2], must_exist);
1011
1012         if (port) {
1013             if (port->bridge == bridge) {
1014                 del_port(&info, port);
1015             } else if (port->bridge->parent == bridge) {
1016                 vsctl_fatal("bridge %s does not have a port %s (although its "
1017                             "parent bridge %s does)",
1018                             ctx->argv[1], ctx->argv[2], bridge->parent->name);
1019             } else {
1020                 vsctl_fatal("bridge %s does not have a port %s",
1021                             ctx->argv[1], ctx->argv[2]);
1022             }
1023         }
1024     }
1025     free_info(&info);
1026 }
1027
1028 static void
1029 cmd_port_to_br(struct vsctl_context *ctx)
1030 {
1031     struct vsctl_port *port;
1032     struct vsctl_info info;
1033
1034     get_info(ctx->ovs, &info);
1035     port = find_port(&info, ctx->argv[1], true);
1036     ds_put_format(&ctx->output, "%s\n", port->bridge->name);
1037     free_info(&info);
1038 }
1039
1040 static void
1041 cmd_port_set_external_id(struct vsctl_context *ctx)
1042 {
1043     struct vsctl_info info;
1044     struct vsctl_port *port;
1045     char **keys, **values;
1046     size_t n;
1047
1048     get_info(ctx->ovs, &info);
1049     port = find_port(&info, ctx->argv[1], true);
1050     set_external_id(port->port_cfg->key_external_ids,
1051                     port->port_cfg->value_external_ids,
1052                     port->port_cfg->n_external_ids,
1053                     ctx->argv[2], ctx->argc >= 4 ? ctx->argv[3] : NULL,
1054                     &keys, &values, &n);
1055     ovsrec_port_set_external_ids(port->port_cfg, keys, values, n);
1056     free(keys);
1057     free(values);
1058
1059     free_info(&info);
1060 }
1061
1062 static void
1063 cmd_port_get_external_id(struct vsctl_context *ctx)
1064 {
1065     struct vsctl_info info;
1066     struct vsctl_port *port;
1067
1068     get_info(ctx->ovs, &info);
1069     port = find_port(&info, ctx->argv[1], true);
1070     get_external_id(port->port_cfg->key_external_ids,
1071                     port->port_cfg->value_external_ids,
1072                     port->port_cfg->n_external_ids,
1073                     "",  ctx->argc >= 3 ? ctx->argv[2] : NULL, &ctx->output);
1074     free_info(&info);
1075 }
1076
1077 static void
1078 cmd_br_to_vlan(struct vsctl_context *ctx)
1079 {
1080     struct vsctl_bridge *bridge;
1081     struct vsctl_info info;
1082
1083     get_info(ctx->ovs, &info);
1084     bridge = find_bridge(&info, ctx->argv[1], true);
1085     ds_put_format(&ctx->output, "%d\n", bridge->vlan);
1086     free_info(&info);
1087 }
1088
1089 static void
1090 cmd_br_to_parent(struct vsctl_context *ctx)
1091 {
1092     struct vsctl_bridge *bridge;
1093     struct vsctl_info info;
1094
1095     get_info(ctx->ovs, &info);
1096     bridge = find_bridge(&info, ctx->argv[1], true);
1097     if (bridge->parent) {
1098         bridge = bridge->parent;
1099     }
1100     ds_put_format(&ctx->output, "%s\n", bridge->name);
1101     free_info(&info);
1102 }
1103
1104 static void
1105 cmd_list_ifaces(struct vsctl_context *ctx)
1106 {
1107     struct vsctl_bridge *br;
1108     struct shash_node *node;
1109     struct vsctl_info info;
1110     struct svec ifaces;
1111
1112     get_info(ctx->ovs, &info);
1113     br = find_bridge(&info, ctx->argv[1], true);
1114
1115     svec_init(&ifaces);
1116     SHASH_FOR_EACH (node, &info.ifaces) {
1117         struct vsctl_iface *iface = node->data;
1118
1119         if (strcmp(iface->iface_cfg->name, br->name)
1120             && br == iface->port->bridge) {
1121             svec_add(&ifaces, iface->iface_cfg->name);
1122         }
1123     }
1124     output_sorted(&ifaces, &ctx->output);
1125     svec_destroy(&ifaces);
1126
1127     free_info(&info);
1128 }
1129
1130 static void
1131 cmd_iface_to_br(struct vsctl_context *ctx)
1132 {
1133     struct vsctl_iface *iface;
1134     struct vsctl_info info;
1135
1136     get_info(ctx->ovs, &info);
1137     iface = find_iface(&info, ctx->argv[1], true);
1138     ds_put_format(&ctx->output, "%s\n", iface->port->bridge->name);
1139     free_info(&info);
1140 }
1141
1142 static void
1143 cmd_iface_set_external_id(struct vsctl_context *ctx)
1144 {
1145     struct vsctl_info info;
1146     struct vsctl_iface *iface;
1147     char **keys, **values;
1148     size_t n;
1149
1150     get_info(ctx->ovs, &info);
1151     iface = find_iface(&info, ctx->argv[1], true);
1152     set_external_id(iface->iface_cfg->key_external_ids,
1153                     iface->iface_cfg->value_external_ids,
1154                     iface->iface_cfg->n_external_ids,
1155                     ctx->argv[2], ctx->argc >= 4 ? ctx->argv[3] : NULL,
1156                     &keys, &values, &n);
1157     ovsrec_interface_set_external_ids(iface->iface_cfg, keys, values, n);
1158     free(keys);
1159     free(values);
1160
1161     free_info(&info);
1162 }
1163
1164 static void
1165 cmd_iface_get_external_id(struct vsctl_context *ctx)
1166 {
1167     struct vsctl_info info;
1168     struct vsctl_iface *iface;
1169
1170     get_info(ctx->ovs, &info);
1171     iface = find_iface(&info, ctx->argv[1], true);
1172     get_external_id(iface->iface_cfg->key_external_ids,
1173                     iface->iface_cfg->value_external_ids,
1174                     iface->iface_cfg->n_external_ids,
1175                     "",  ctx->argc >= 3 ? ctx->argv[2] : NULL, &ctx->output);
1176     free_info(&info);
1177 }
1178 \f
1179 typedef void vsctl_handler_func(struct vsctl_context *);
1180
1181 struct vsctl_command {
1182     const char *name;
1183     int min_args;
1184     int max_args;
1185     vsctl_handler_func *handler;
1186     const char *options;
1187 };
1188
1189 static void run_vsctl_command(int argc, char *argv[],
1190                               const struct ovsrec_open_vswitch *ovs,
1191                               struct ds *output);
1192
1193 static void
1194 do_vsctl(int argc, char *argv[], struct ovsdb_idl *idl)
1195 {
1196     struct ovsdb_idl_txn *txn;
1197     const struct ovsrec_open_vswitch *ovs;
1198     enum ovsdb_idl_txn_status status;
1199     struct ds *output;
1200     int n_output;
1201     int i, start;
1202
1203     txn = ovsdb_idl_txn_create(idl);
1204     if (dry_run) {
1205         ovsdb_idl_txn_set_dry_run(txn);
1206     }
1207
1208     ovs = ovsrec_open_vswitch_first(idl);
1209     if (!ovs) {
1210         /* XXX add verification that table is empty */
1211         ovs = ovsrec_open_vswitch_insert(txn);
1212     }
1213
1214     output = xmalloc(argc * sizeof *output);
1215     n_output = 0;
1216     for (start = i = 0; i <= argc; i++) {
1217         if (i == argc || !strcmp(argv[i], "--")) {
1218             if (i > start) {
1219                 ds_init(&output[n_output]);
1220                 run_vsctl_command(i - start, &argv[start], ovs,
1221                                   &output[n_output++]);
1222             }
1223             start = i + 1;
1224         }
1225     }
1226
1227     while ((status = ovsdb_idl_txn_commit(txn)) == TXN_INCOMPLETE) {
1228         ovsdb_idl_run(idl);
1229         ovsdb_idl_wait(idl);
1230         ovsdb_idl_txn_wait(txn);
1231         poll_block();
1232     }
1233     ovsdb_idl_txn_destroy(txn);
1234
1235     switch (status) {
1236     case TXN_INCOMPLETE:
1237         NOT_REACHED();
1238
1239     case TXN_ABORTED:
1240         /* Should not happen--we never call ovsdb_idl_txn_abort(). */
1241         vsctl_fatal("transaction aborted");
1242
1243     case TXN_SUCCESS:
1244         break;
1245
1246     case TXN_TRY_AGAIN:
1247         for (i = 0; i < n_output; i++) {
1248             ds_destroy(&output[i]);
1249         }
1250         return;
1251
1252     case TXN_ERROR:
1253         vsctl_fatal("transaction error");
1254
1255     default:
1256         NOT_REACHED();
1257     }
1258
1259     for (i = 0; i < n_output; i++) {
1260         struct ds *ds = &output[i];
1261         if (oneline) {
1262             size_t j;
1263
1264             ds_chomp(ds, '\n');
1265             for (j = 0; j < ds->length; j++) {
1266                 int c = ds->string[j];
1267                 switch (c) {
1268                 case '\n':
1269                     fputs("\\n", stdout);
1270                     break;
1271
1272                 case '\\':
1273                     fputs("\\\\", stdout);
1274                     break;
1275
1276                 default:
1277                     putchar(c);
1278                 }
1279             }
1280             putchar('\n');
1281         } else {
1282             fputs(ds_cstr(ds), stdout);
1283         }
1284     }
1285     exit(EXIT_SUCCESS);
1286 }
1287
1288 static vsctl_handler_func *
1289 get_vsctl_handler(int argc, char *argv[], struct vsctl_context *ctx)
1290 {
1291     static const struct vsctl_command all_commands[] = {
1292         /* Open vSwitch commands. */
1293         {"init", 0, 0, cmd_init, ""},
1294
1295         /* Bridge commands. */
1296         {"add-br", 1, 3, cmd_add_br, ""},
1297         {"del-br", 1, 1, cmd_del_br, "--if-exists"},
1298         {"list-br", 0, 0, cmd_list_br, ""},
1299         {"br-exists", 1, 1, cmd_br_exists, ""},
1300         {"br-to-vlan", 1, 1, cmd_br_to_vlan, ""},
1301         {"br-to-parent", 1, 1, cmd_br_to_parent, ""},
1302         {"br-set-external-id", 2, 3, cmd_br_set_external_id, ""},
1303         {"br-get-external-id", 1, 2, cmd_br_get_external_id, ""},
1304
1305         /* Port commands. */
1306         {"list-ports", 1, 1, cmd_list_ports, ""},
1307         {"add-port", 2, 2, cmd_add_port, ""},
1308         {"add-bond", 4, INT_MAX, cmd_add_bond, ""},
1309         {"del-port", 1, 2, cmd_del_port, "--if-exists"},
1310         {"port-to-br", 1, 1, cmd_port_to_br, ""},
1311         {"port-set-external-id", 2, 3, cmd_port_set_external_id, ""},
1312         {"port-get-external-id", 1, 2, cmd_port_get_external_id, ""},
1313
1314         /* Interface commands. */
1315         {"list-ifaces", 1, 1, cmd_list_ifaces, ""},
1316         {"iface-to-br", 1, 1, cmd_iface_to_br, ""},
1317         {"iface-set-external-id", 2, 3, cmd_iface_set_external_id, ""},
1318         {"iface-get-external-id", 1, 2, cmd_iface_get_external_id, ""},
1319     };
1320
1321     const struct vsctl_command *p;
1322     int i;
1323
1324     shash_init(&ctx->options);
1325     for (i = 0; i < argc; i++) {
1326         if (argv[i][0] != '-') {
1327             break;
1328         }
1329         if (!shash_add_once(&ctx->options, argv[i], NULL)) {
1330             vsctl_fatal("'%s' option specified multiple times", argv[i]);
1331         }
1332     }
1333     if (i == argc) {
1334         vsctl_fatal("missing command name");
1335     }
1336
1337     for (p = all_commands; p < &all_commands[ARRAY_SIZE(all_commands)]; p++) {
1338         if (!strcmp(p->name, argv[i])) {
1339             struct shash_node *node;
1340             int n_arg;
1341
1342             SHASH_FOR_EACH (node, &ctx->options) {
1343                 const char *s = strstr(p->options, node->name);
1344                 int end = s ? s[strlen(node->name)] : EOF;
1345                 if (end != ',' && end != ' ' && end != '\0') {
1346                     vsctl_fatal("'%s' command has no '%s' option",
1347                                 argv[i], node->name);
1348                 }
1349             }
1350
1351             n_arg = argc - i - 1;
1352             if (n_arg < p->min_args) {
1353                 vsctl_fatal("'%s' command requires at least %d arguments",
1354                             p->name, p->min_args);
1355             } else if (n_arg > p->max_args) {
1356                 vsctl_fatal("'%s' command takes at most %d arguments",
1357                             p->name, p->max_args);
1358             } else {
1359                 ctx->argc = n_arg + 1;
1360                 ctx->argv = &argv[i];
1361                 return p->handler;
1362             }
1363         }
1364     }
1365
1366     vsctl_fatal("unknown command '%s'; use --help for help", argv[i]);
1367 }
1368
1369 static void
1370 check_vsctl_command(int argc, char *argv[])
1371 {
1372     struct vsctl_context ctx;
1373
1374     get_vsctl_handler(argc, argv, &ctx);
1375     shash_destroy(&ctx.options);
1376 }
1377
1378 static void
1379 run_vsctl_command(int argc, char *argv[],
1380                   const struct ovsrec_open_vswitch *ovs, struct ds *output)
1381 {
1382     vsctl_handler_func *function;
1383     struct vsctl_context ctx;
1384
1385     function = get_vsctl_handler(argc, argv, &ctx);
1386     ctx.ovs = ovs;
1387     ds_init(&ctx.output);
1388     function(&ctx);
1389     *output = ctx.output;
1390     shash_destroy(&ctx.options);
1391 }