struct vconn *);
struct rconn *rconn_create(int txq_limit, int inactivity_probe_interval,
int max_backoff);
-void rconn_connect(struct rconn *, const char *name);
+int rconn_connect(struct rconn *, const char *name);
void rconn_connect_unreliably(struct rconn *,
const char *name, struct vconn *vconn);
void rconn_disconnect(struct rconn *);
static bool timeout(struct rconn *, unsigned int secs);
static void state_transition(struct rconn *, enum state);
static int try_send(struct rconn *);
-static void reconnect(struct rconn *);
+static int reconnect(struct rconn *);
static void disconnect(struct rconn *, int error);
static void question_connectivity(struct rconn *);
return rc;
}
-void
+int
rconn_connect(struct rconn *rc, const char *name)
{
rconn_disconnect(rc);
free(rc->name);
rc->name = xstrdup(name);
rc->reliable = true;
- reconnect(rc);
+ return reconnect(rc);
}
void
/* Nothing to do. */
}
-static void
+static int
reconnect(struct rconn *rc)
{
int retval;
VLOG_WARN("%s: connection failed (%s)", rc->name, strerror(retval));
disconnect(rc, 0);
}
+ return retval;
}
static void
static void
run_CONNECTING(struct rconn *rc)
{
- int error = vconn_connect(rc->vconn);
- if (!error) {
+ int retval = vconn_connect(rc->vconn);
+ if (!retval) {
VLOG_WARN("%s: connected", rc->name);
if (vconn_is_passive(rc->vconn)) {
- fatal(0, "%s: passive vconn not supported in switch",
- rc->name);
+ error(0, "%s: passive vconn not supported", rc->name);
+ state_transition(rc, S_VOID);
+ } else {
+ state_transition(rc, S_ACTIVE);
+ rc->last_connected = rc->state_entered;
}
- state_transition(rc, S_ACTIVE);
- rc->last_connected = rc->state_entered;
- } else if (error != EAGAIN) {
- VLOG_WARN("%s: connection failed (%s)", rc->name, strerror(error));
- disconnect(rc, error);
+ } else if (retval != EAGAIN) {
+ VLOG_WARN("%s: connection failed (%s)", rc->name, strerror(retval));
+ disconnect(rc, retval);
} else if (timeout(rc, MAX(1, rc->backoff))) {
VLOG_WARN("%s: connection timed out", rc->name);
rc->backoff_deadline = TIME_MAX; /* Prevent resetting backoff. */
subscribe = 1;
if (sscanf(suffix, "%d:%d", &dp_idx, &subscribe) < 1) {
- fatal(0, "%s: syntax error", name);
+ error(0, "%s: syntax error", name);
+ return EAFNOSUPPORT;
}
netlink = xmalloc(sizeof *netlink);
host_name = strtok_r(suffix, "::", &save_ptr);
port_string = strtok_r(NULL, "::", &save_ptr);
if (!host_name) {
- fatal(0, "%s: bad peer name format", name);
+ error(0, "%s: bad peer name format", name);
+ return EAFNOSUPPORT;
}
memset(&sin, 0, sizeof sin);
host_name = strtok_r(suffix, "::", &save_ptr);
port_string = strtok_r(NULL, "::", &save_ptr);
if (!host_name) {
- fatal(0, "%s: bad peer name format", name);
+ error(0, "%s: bad peer name format", name);
+ return EAFNOSUPPORT;
}
memset(&sin, 0, sizeof sin);
prefix_len = strcspn(name, ":");
if (prefix_len == strlen(name)) {
- fatal(0, "`%s' not correct format for peer name", name);
+ error(0, "`%s' not correct format for peer name", name);
+ return EAFNOSUPPORT;
}
for (i = 0; i < ARRAY_SIZE(vconn_classes); i++) {
struct vconn_class *class = vconn_classes[i];
return retval;
}
}
- fatal(0, "unknown peer type `%.*s'", (int) prefix_len, name);
- abort();
+ error(0, "unknown peer type `%.*s'", (int) prefix_len, name);
+ return EAFNOSUPPORT;
}
int
int
main(int argc, char *argv[])
{
+ struct rconn *local_rconn, *remote_rconn;
struct vconn *listen_vconn;
struct relay *controller_relay;
const char *nl_name;
daemonize();
- controller_relay = relay_create(rconn_new(argv[optind], 1, 0, max_backoff),
- rconn_new(argv[optind + 1], 1,
- probe_interval, max_backoff),
- false);
+ local_rconn = rconn_create(1, 0, max_backoff);
+ retval = rconn_connect(local_rconn, nl_name);
+ if (retval == EAFNOSUPPORT) {
+ fatal(0, "No support for %s vconn", nl_name);
+ }
+
+ remote_rconn = rconn_create(1, probe_interval, max_backoff);
+ retval = rconn_connect(remote_rconn, argv[optind + 1]);
+ if (retval == EAFNOSUPPORT) {
+ fatal(0, "No support for %s vconn", argv[optind + 1]);
+ }
+ controller_relay = relay_create(local_rconn, remote_rconn, false);
for (;;) {
struct relay *r, *n;
int
main(int argc, char *argv[])
{
+ struct rconn *rconn;
int error;
set_program_name(argv[0]);
fatal(0, "missing controller argument; use --help for usage");
}
- error = dp_new(&dp, dpid, rconn_new(argv[optind], 128, 60, max_backoff));
+ rconn = rconn_create(128, 60, max_backoff);
+ error = rconn_connect(rconn, argv[optind]);
+ if (error == EAFNOSUPPORT) {
+ fatal(0, "no support for %s vconn", argv[optind]);
+ }
+ error = dp_new(&dp, dpid, rconn);
if (listen_vconn_name) {
struct vconn *listen_vconn;
int retval;