A common error scenario with OVN is to attempt to use ovn-nbctl when the OVN databases have not been created in ovsdb-server: 1. ovn-nbctl sends a "get_schema" request for the OVN db to ovsdb-server. 2. ovsdb-server fails to find requested db, sends error response to ovn-nbctl. 3. ovn-nbctl receives the error response in ovsdb_idl_run(), but takes no specific action. 4. ovn-nbctl hangs forever in IDL_S_SCHEMA_REQUESTED state (assuming a timeout wasn't requested on the command line).
This commit adds a new IDL state, IDL_S_NO_SCHEMA, which is entered when a negative response to a schema request is received. When in this state, ovsdb_idl_is_alive() now returns 'false', allowing clients (currently ovn-nbctl, ovn-sbctl, vtep-ctl, and ovs-vsctl) to detect this condition and exit with an appropriate error message. Signed-off-by: Lance Richardson <lrich...@redhat.com> --- v2: changed ovsdb_idl_get_last_error() to better preserve the original semantics (per comments from Ben Pfaff). lib/ovsdb-idl.c | 29 +++++++++++++++++++++++------ 1 file changed, 23 insertions(+), 6 deletions(-) diff --git a/lib/ovsdb-idl.c b/lib/ovsdb-idl.c index 4cb1c81..2a109a9 100644 --- a/lib/ovsdb-idl.c +++ b/lib/ovsdb-idl.c @@ -80,7 +80,8 @@ enum ovsdb_idl_state { IDL_S_MONITOR_REQUESTED, IDL_S_MONITORING, IDL_S_MONITOR2_REQUESTED, - IDL_S_MONITORING2 + IDL_S_MONITORING2, + IDL_S_NO_SCHEMA }; struct ovsdb_idl { @@ -417,6 +418,7 @@ ovsdb_idl_run(struct ovsdb_idl *idl) case IDL_S_MONITORING: case IDL_S_MONITORING2: + case IDL_S_NO_SCHEMA: default: OVS_NOT_REACHED(); } @@ -461,6 +463,7 @@ ovsdb_idl_run(struct ovsdb_idl *idl) idl->request_id = NULL; VLOG_ERR("%s: requested schema not found", jsonrpc_session_get_name(idl->session)); + idl->state = IDL_S_NO_SCHEMA; } else if ((msg->type == JSONRPC_ERROR || msg->type == JSONRPC_REPLY) && ovsdb_idl_txn_process_reply(idl, msg)) { @@ -550,20 +553,34 @@ ovsdb_idl_verify_write_only(struct ovsdb_idl *idl) idl->verify_write_only = true; } -/* Returns true if 'idl' is currently connected or trying to connect. */ +/* Returns true if 'idl' is currently connected or trying to connect + * and a negative response to a schema request has not been received */ bool ovsdb_idl_is_alive(const struct ovsdb_idl *idl) { - return jsonrpc_session_is_alive(idl->session); + return jsonrpc_session_is_alive(idl->session) && + idl->state != IDL_S_NO_SCHEMA; } /* Returns the last error reported on a connection by 'idl'. The return value - * is 0 only if no connection made by 'idl' has ever encountered an error. See - * jsonrpc_get_status() for return value interpretation. */ + * is 0 only if no connection made by 'idl' has ever encountered an error and + * a negative response to a schema request has never been received. See + * jsonrpc_get_status() for jsonrpc_session_get_last_error() return value + * interpretation. */ int ovsdb_idl_get_last_error(const struct ovsdb_idl *idl) { - return jsonrpc_session_get_last_error(idl->session); + int err; + + err = jsonrpc_session_get_last_error(idl->session); + + if (err) { + return err; + } else if (idl->state == IDL_S_NO_SCHEMA) { + return ENOENT; + } else { + return 0; + } } static unsigned char * -- 2.5.0 _______________________________________________ dev mailing list dev@openvswitch.org http://openvswitch.org/mailman/listinfo/dev