app: added --json-ignore-init-errors
If set, SPDK will continue loading the JSON config even if some commands caused an error. This can be useful when loading RPC config from spdk_tgt into e.g. bdevperf, which supports only a subset of RPC commands and would usually fail with "Method not found" message. Resolves #840 Change-Id: I070fea862fd99e5882d870e11e6a28dc9d0c8ba6 Signed-off-by: Darek Stojaczyk <dariusz.stojaczyk@intel.com> Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/620 Tested-by: SPDK CI Jenkins <sys_sgci@intel.com> Reviewed-by: Shuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com> Reviewed-by: Tomasz Zawadzki <tomasz.zawadzki@intel.com> Reviewed-by: Ben Walker <benjamin.walker@intel.com>
This commit is contained in:
parent
7745383ab2
commit
8e7d6e1b0c
@ -6,6 +6,11 @@
|
|||||||
A new function, `spdk_vmd_fini`, has been added. It releases all resources acquired by the VMD
|
A new function, `spdk_vmd_fini`, has been added. It releases all resources acquired by the VMD
|
||||||
library through the `spdk_vmd_init` call.
|
library through the `spdk_vmd_init` call.
|
||||||
|
|
||||||
|
### Miscellaneous
|
||||||
|
|
||||||
|
`--json-ignore-init-errors` command line param has been added to ignore initialization errors
|
||||||
|
on JSON config load.
|
||||||
|
|
||||||
## v20.01
|
## v20.01
|
||||||
|
|
||||||
### bdev
|
### bdev
|
||||||
|
@ -204,7 +204,7 @@ spdk_fio_bdev_init_start(void *arg)
|
|||||||
|
|
||||||
if (g_json_config_file != NULL) {
|
if (g_json_config_file != NULL) {
|
||||||
spdk_app_json_config_load(g_json_config_file, SPDK_DEFAULT_RPC_ADDR,
|
spdk_app_json_config_load(g_json_config_file, SPDK_DEFAULT_RPC_ADDR,
|
||||||
spdk_fio_bdev_init_done, done);
|
spdk_fio_bdev_init_done, done, true);
|
||||||
} else {
|
} else {
|
||||||
spdk_subsystem_init(spdk_fio_bdev_init_done, done);
|
spdk_subsystem_init(spdk_fio_bdev_init_done, done);
|
||||||
}
|
}
|
||||||
|
@ -91,6 +91,7 @@ struct spdk_app_opts {
|
|||||||
const char *name;
|
const char *name;
|
||||||
const char *config_file;
|
const char *config_file;
|
||||||
const char *json_config_file;
|
const char *json_config_file;
|
||||||
|
bool json_config_ignore_errors;
|
||||||
const char *rpc_addr; /* Can be UNIX domain socket path or IP address + TCP port */
|
const char *rpc_addr; /* Can be UNIX domain socket path or IP address + TCP port */
|
||||||
const char *reactor_mask;
|
const char *reactor_mask;
|
||||||
const char *tpoint_group_mask;
|
const char *tpoint_group_mask;
|
||||||
|
@ -144,7 +144,8 @@ void spdk_subsystem_init_next(int rc);
|
|||||||
void spdk_subsystem_fini_next(void);
|
void spdk_subsystem_fini_next(void);
|
||||||
void spdk_subsystem_config(FILE *fp);
|
void spdk_subsystem_config(FILE *fp);
|
||||||
void spdk_app_json_config_load(const char *json_config_file, const char *rpc_addr,
|
void spdk_app_json_config_load(const char *json_config_file, const char *rpc_addr,
|
||||||
spdk_subsystem_init_fn cb_fn, void *cb_arg);
|
spdk_subsystem_init_fn cb_fn, void *cb_arg,
|
||||||
|
bool stop_on_error);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Save pointed \c subsystem configuration to the JSON write context \c w. In case of
|
* Save pointed \c subsystem configuration to the JSON write context \c w. In case of
|
||||||
|
@ -59,6 +59,7 @@
|
|||||||
struct spdk_app {
|
struct spdk_app {
|
||||||
struct spdk_conf *config;
|
struct spdk_conf *config;
|
||||||
const char *json_config_file;
|
const char *json_config_file;
|
||||||
|
bool json_config_ignore_errors;
|
||||||
const char *rpc_addr;
|
const char *rpc_addr;
|
||||||
int shm_id;
|
int shm_id;
|
||||||
spdk_app_shutdown_cb shutdown_cb;
|
spdk_app_shutdown_cb shutdown_cb;
|
||||||
@ -128,6 +129,8 @@ static const struct option g_cmdline_options[] = {
|
|||||||
{"max-delay", required_argument, NULL, MAX_REACTOR_DELAY_OPT_IDX},
|
{"max-delay", required_argument, NULL, MAX_REACTOR_DELAY_OPT_IDX},
|
||||||
#define JSON_CONFIG_OPT_IDX 262
|
#define JSON_CONFIG_OPT_IDX 262
|
||||||
{"json", required_argument, NULL, JSON_CONFIG_OPT_IDX},
|
{"json", required_argument, NULL, JSON_CONFIG_OPT_IDX},
|
||||||
|
#define JSON_CONFIG_IGNORE_INIT_ERRORS_IDX 263
|
||||||
|
{"json-ignore-init-errors", no_argument, NULL, JSON_CONFIG_IGNORE_INIT_ERRORS_IDX},
|
||||||
};
|
};
|
||||||
|
|
||||||
/* Global section */
|
/* Global section */
|
||||||
@ -561,7 +564,7 @@ bootstrap_fn(void *arg1)
|
|||||||
if (g_spdk_app.json_config_file) {
|
if (g_spdk_app.json_config_file) {
|
||||||
g_delay_subsystem_init = false;
|
g_delay_subsystem_init = false;
|
||||||
spdk_app_json_config_load(g_spdk_app.json_config_file, g_spdk_app.rpc_addr, spdk_app_start_rpc,
|
spdk_app_json_config_load(g_spdk_app.json_config_file, g_spdk_app.rpc_addr, spdk_app_start_rpc,
|
||||||
NULL);
|
NULL, !g_spdk_app.json_config_ignore_errors);
|
||||||
} else {
|
} else {
|
||||||
if (!g_delay_subsystem_init) {
|
if (!g_delay_subsystem_init) {
|
||||||
spdk_subsystem_init(spdk_app_start_rpc, NULL);
|
spdk_subsystem_init(spdk_app_start_rpc, NULL);
|
||||||
@ -626,6 +629,7 @@ spdk_app_start(struct spdk_app_opts *opts, spdk_msg_fn start_fn,
|
|||||||
memset(&g_spdk_app, 0, sizeof(g_spdk_app));
|
memset(&g_spdk_app, 0, sizeof(g_spdk_app));
|
||||||
g_spdk_app.config = config;
|
g_spdk_app.config = config;
|
||||||
g_spdk_app.json_config_file = opts->json_config_file;
|
g_spdk_app.json_config_file = opts->json_config_file;
|
||||||
|
g_spdk_app.json_config_ignore_errors = opts->json_config_ignore_errors;
|
||||||
g_spdk_app.rpc_addr = opts->rpc_addr;
|
g_spdk_app.rpc_addr = opts->rpc_addr;
|
||||||
g_spdk_app.shm_id = opts->shm_id;
|
g_spdk_app.shm_id = opts->shm_id;
|
||||||
g_spdk_app.shutdown_cb = opts->shutdown_cb;
|
g_spdk_app.shutdown_cb = opts->shutdown_cb;
|
||||||
@ -728,6 +732,8 @@ usage(void (*app_usage)(void))
|
|||||||
g_default_opts.config_file != NULL ? g_default_opts.config_file : "none");
|
g_default_opts.config_file != NULL ? g_default_opts.config_file : "none");
|
||||||
printf(" --json <config> JSON config file (default %s)\n",
|
printf(" --json <config> JSON config file (default %s)\n",
|
||||||
g_default_opts.json_config_file != NULL ? g_default_opts.json_config_file : "none");
|
g_default_opts.json_config_file != NULL ? g_default_opts.json_config_file : "none");
|
||||||
|
printf(" --json-ignore-init-errors\n");
|
||||||
|
printf(" don't exit on invalid config entry\n");
|
||||||
printf(" -d, --limit-coredump do not set max coredump size to RLIM_INFINITY\n");
|
printf(" -d, --limit-coredump do not set max coredump size to RLIM_INFINITY\n");
|
||||||
printf(" -g, --single-file-segments\n");
|
printf(" -g, --single-file-segments\n");
|
||||||
printf(" force creating just one hugetlbfs file\n");
|
printf(" force creating just one hugetlbfs file\n");
|
||||||
@ -837,6 +843,9 @@ spdk_app_parse_args(int argc, char **argv, struct spdk_app_opts *opts,
|
|||||||
case JSON_CONFIG_OPT_IDX:
|
case JSON_CONFIG_OPT_IDX:
|
||||||
opts->json_config_file = optarg;
|
opts->json_config_file = optarg;
|
||||||
break;
|
break;
|
||||||
|
case JSON_CONFIG_IGNORE_INIT_ERRORS_IDX:
|
||||||
|
opts->json_config_ignore_errors = true;
|
||||||
|
break;
|
||||||
case LIMIT_COREDUMP_OPT_IDX:
|
case LIMIT_COREDUMP_OPT_IDX:
|
||||||
opts->enable_coredump = false;
|
opts->enable_coredump = false;
|
||||||
break;
|
break;
|
||||||
|
@ -88,6 +88,7 @@ struct load_json_config_ctx {
|
|||||||
struct spdk_thread *thread;
|
struct spdk_thread *thread;
|
||||||
spdk_subsystem_init_fn cb_fn;
|
spdk_subsystem_init_fn cb_fn;
|
||||||
void *cb_arg;
|
void *cb_arg;
|
||||||
|
bool stop_on_error;
|
||||||
|
|
||||||
/* Current subsystem */
|
/* Current subsystem */
|
||||||
struct spdk_json_val *subsystems; /* "subsystems" array */
|
struct spdk_json_val *subsystems; /* "subsystems" array */
|
||||||
@ -189,6 +190,9 @@ rpc_client_poller(void *arg)
|
|||||||
|
|
||||||
if (resp->error) {
|
if (resp->error) {
|
||||||
SPDK_ERRLOG("error response: %*s", (int)resp->error->len, (char *)resp->error->start);
|
SPDK_ERRLOG("error response: %*s", (int)resp->error->len, (char *)resp->error->start);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (resp->error && ctx->stop_on_error) {
|
||||||
spdk_jsonrpc_client_free_response(resp);
|
spdk_jsonrpc_client_free_response(resp);
|
||||||
spdk_app_json_config_load_done(ctx, -EINVAL);
|
spdk_app_json_config_load_done(ctx, -EINVAL);
|
||||||
} else {
|
} else {
|
||||||
@ -302,8 +306,7 @@ static void
|
|||||||
spdk_app_json_config_load_subsystem_config_entry_next(struct load_json_config_ctx *ctx,
|
spdk_app_json_config_load_subsystem_config_entry_next(struct load_json_config_ctx *ctx,
|
||||||
struct spdk_jsonrpc_client_response *resp)
|
struct spdk_jsonrpc_client_response *resp)
|
||||||
{
|
{
|
||||||
/* Don't care about the response as long it is not
|
/* Don't care about the response */
|
||||||
* an error (which is validated by poller) */
|
|
||||||
spdk_jsonrpc_client_free_response(resp);
|
spdk_jsonrpc_client_free_response(resp);
|
||||||
|
|
||||||
ctx->config_it = spdk_json_next(ctx->config_it);
|
ctx->config_it = spdk_json_next(ctx->config_it);
|
||||||
@ -530,7 +533,8 @@ err:
|
|||||||
|
|
||||||
void
|
void
|
||||||
spdk_app_json_config_load(const char *json_config_file, const char *rpc_addr,
|
spdk_app_json_config_load(const char *json_config_file, const char *rpc_addr,
|
||||||
spdk_subsystem_init_fn cb_fn, void *cb_arg)
|
spdk_subsystem_init_fn cb_fn, void *cb_arg,
|
||||||
|
bool stop_on_error)
|
||||||
{
|
{
|
||||||
struct load_json_config_ctx *ctx = calloc(1, sizeof(*ctx));
|
struct load_json_config_ctx *ctx = calloc(1, sizeof(*ctx));
|
||||||
int rc;
|
int rc;
|
||||||
@ -543,6 +547,7 @@ spdk_app_json_config_load(const char *json_config_file, const char *rpc_addr,
|
|||||||
|
|
||||||
ctx->cb_fn = cb_fn;
|
ctx->cb_fn = cb_fn;
|
||||||
ctx->cb_arg = cb_arg;
|
ctx->cb_arg = cb_arg;
|
||||||
|
ctx->stop_on_error = stop_on_error;
|
||||||
ctx->thread = spdk_get_thread();
|
ctx->thread = spdk_get_thread();
|
||||||
|
|
||||||
rc = spdk_app_json_config_read(json_config_file, ctx);
|
rc = spdk_app_json_config_read(json_config_file, ctx);
|
||||||
|
@ -49,7 +49,7 @@ DEFINE_STUB_V(spdk_rpc_register_alias_deprecated, (const char *method, const cha
|
|||||||
DEFINE_STUB_V(spdk_rpc_set_state, (uint32_t state));
|
DEFINE_STUB_V(spdk_rpc_set_state, (uint32_t state));
|
||||||
DEFINE_STUB(spdk_rpc_get_state, uint32_t, (void), SPDK_RPC_RUNTIME);
|
DEFINE_STUB(spdk_rpc_get_state, uint32_t, (void), SPDK_RPC_RUNTIME);
|
||||||
DEFINE_STUB_V(spdk_app_json_config_load, (const char *json_config_file, const char *rpc_addr,
|
DEFINE_STUB_V(spdk_app_json_config_load, (const char *json_config_file, const char *rpc_addr,
|
||||||
spdk_subsystem_init_fn cb_fn, void *cb_arg));
|
spdk_subsystem_init_fn cb_fn, void *cb_arg, bool stop_on_error));
|
||||||
|
|
||||||
static void
|
static void
|
||||||
unittest_usage(void)
|
unittest_usage(void)
|
||||||
|
Loading…
Reference in New Issue
Block a user