From 4da1ad28b64d69bbc706b21ee486e94b9c8f2152 Mon Sep 17 00:00:00 2001 From: Daniel Wagner Date: Mon, 5 Jan 2026 11:33:23 +0100 Subject: [PATCH 1/5] build: merge all symbols into 2.0 sections Move all symbols into the 2.0 section. Signed-off-by: Daniel Wagner --- libnvme/src/libnvme.map | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/libnvme/src/libnvme.map b/libnvme/src/libnvme.map index 4054de184f..60dc9b3d00 100644 --- a/libnvme/src/libnvme.map +++ b/libnvme/src/libnvme.map @@ -2,17 +2,9 @@ LIBNVME_UNRELEASED { }; -LIBNVME_1_16 { - global: - nvme_get_uuid_list; - nvme_set_etdas; - nvme_clear_etdas; - nvme_insert_tls_key_compat; - nvme_generate_tls_key_identity_compat; -}; - LIBNVME_2_0 { global: + nvme_clear_etdas; nvme_close; nvme_create_ctrl; nvme_create_global_ctx; @@ -83,6 +75,7 @@ LIBNVME_2_0 { nvme_fw_download_seq; nvme_gen_dhchap_key; nvme_generate_tls_key_identity; + nvme_generate_tls_key_identity_compat; nvme_get_ana_log_atomic; nvme_get_ana_log_len; nvme_get_ana_log_len_from_id_ctrl; @@ -105,6 +98,7 @@ LIBNVME_2_0 { nvme_get_subsys_attr; nvme_get_telemetry_log; nvme_get_telemetry_max; + nvme_get_uuid_list; nvme_get_version; nvme_host_get_dhchap_key; nvme_host_get_global_ctx; @@ -129,6 +123,7 @@ LIBNVME_2_0 { nvme_init_dsm_range; nvme_init_logging; nvme_insert_tls_key; + nvme_insert_tls_key_compat; nvme_insert_tls_key_versioned; nvme_ipaddrs_eq; nvme_lookup_ctrl; @@ -241,6 +236,7 @@ LIBNVME_2_0 { nvme_set_application; nvme_set_debug; nvme_set_dry_run; + nvme_set_etdas; nvme_set_keyring; nvme_set_property; nvme_set_root; From 72a2140be7c2f7de66e12f983a419a5ae884d65e Mon Sep 17 00:00:00 2001 From: Daniel Wagner Date: Mon, 5 Jan 2026 11:39:03 +0100 Subject: [PATCH 2/5] build: change linker script to use the .ld extension The commom name for linker scripts uses the .ld extension, thus rename the libnvme.map to libnvme.ld Signed-off-by: Daniel Wagner --- libnvme/scripts/release.sh | 20 ++++++++++---------- libnvme/src/{libnvme.map => libnvme.ld} | 0 libnvme/src/meson.build | 4 ++-- 3 files changed, 12 insertions(+), 12 deletions(-) rename libnvme/src/{libnvme.map => libnvme.ld} (100%) diff --git a/libnvme/scripts/release.sh b/libnvme/scripts/release.sh index 0323ee536d..20b33720b3 100755 --- a/libnvme/scripts/release.sh +++ b/libnvme/scripts/release.sh @@ -132,18 +132,18 @@ if [ "$build_doc" = true ]; then git commit -s -m "doc: Regenerate all docs for $VERSION" fi -declare -A maps -maps=( - [src/libnvme.map]=LIBNVME +declare -A ldscripts +ldscripts=( + [src/libnvme.ld]=LIBNVME ) lib_ver="${ver//./_}" -for map_file in "${!maps[@]}" +for ld_file in "${!ldscripts[@]}" do - lib_name=${maps[$map_file]} + lib_name=${ldscripts[$ld_file]} - if [ ! -f "${map_file}" ]; then + if [ ! -f "${ld_file}" ]; then continue fi @@ -155,16 +155,16 @@ do in_section && $0 ~ /\}/ { exit } in_section && $0 !~ /^[[:space:]]*($|\/|\/\*|\*|#)/ { found = 1; exit } END { exit !found } - ' "${map_file}"; then + ' "${ld_file}"; then continue fi sed -i \ -e "s/^${lib_unreleased}\s*{/&\n};\n\n${lib_name}_${lib_ver} {/" \ - "$map_file" + "$ld_file" - git add "${map_file}" - echo "${map_file} updated." + git add "${ld_file}" + echo "${ld_file} updated." done # update meson.build diff --git a/libnvme/src/libnvme.map b/libnvme/src/libnvme.ld similarity index 100% rename from libnvme/src/libnvme.map rename to libnvme/src/libnvme.ld diff --git a/libnvme/src/meson.build b/libnvme/src/meson.build index 2ea2e62012..40798e15ce 100644 --- a/libnvme/src/meson.build +++ b/libnvme/src/meson.build @@ -41,14 +41,14 @@ deps = [ accessors_dep, ] -mapfile = 'libnvme.map' +ldfile = 'libnvme.ld' libnvme = library( 'nvme', # produces libnvme.so sources, version: libnvme_so_version, link_args: [ - '-Wl,--version-script=@0@'.format(meson.current_source_dir() / mapfile), + '-Wl,--version-script=@0@'.format(meson.current_source_dir() / ldfile), '-Wl,--version-script=@0@'.format(accessors_ld_full_path), ], dependencies: deps, From 2f060ebd1c105148ab097e58384413e041340c18 Mon Sep 17 00:00:00 2001 From: Daniel Wagner Date: Thu, 8 Jan 2026 14:31:35 +0100 Subject: [PATCH 3/5] test: print command string When debugging it's useful to get the exact command line which is used. This string can then be directly given to 'gdb --args'. Signed-off-by: Daniel Wagner --- libnvme/test/config/config-diff.sh | 22 ++++++++++++++++++---- libnvme/test/sysfs/meson.build | 2 +- libnvme/test/sysfs/tree-diff.sh | 21 +++++++++++++++++---- 3 files changed, 36 insertions(+), 9 deletions(-) diff --git a/libnvme/test/config/config-diff.sh b/libnvme/test/config/config-diff.sh index abec20e15a..920ffb3aad 100755 --- a/libnvme/test/config/config-diff.sh +++ b/libnvme/test/config/config-diff.sh @@ -40,9 +40,23 @@ fi output="${build_dir}"/$(basename "${expected_output}") -LIBNVME_SYSFS_PATH="${sysfs_path}" \ -LIBNVME_HOSTNQN=nqn.2014-08.org.nvmexpress:uuid:ce4fee3e-c02c-11ee-8442-830d068a36c6 \ -LIBNVME_HOSTID=ce4fee3e-c02c-11ee-8442-830d068a36c6 \ -"${test_binary}" "${config_json}" > "${output}" || echo "test failed" +cmd=( + env + LIBNVME_SYSFS_PATH="$sysfs_path" + LIBNVME_HOSTNQN="nqn.2014-08.org.nvmexpress:uuid:ce4fee3e-c02c-11ee-8442-830d068a36c6" + LIBNVME_HOSTID="ce4fee3e-c02c-11ee-8442-830d068a36c6" + "$test_binary" + "$config_json" +) + +echo "Running command:" +printf '%q ' "${cmd[@]}" +printf '> %q\n' "$output" + +if ! "${cmd[@]}" > "$output"; then + rc=$? + echo "test failed (exit code $rc)" + exit $rc +fi diff -u "${expected_output}" "${output}" diff --git a/libnvme/test/sysfs/meson.build b/libnvme/test/sysfs/meson.build index 91cfb5cce9..933f8a2ee9 100644 --- a/libnvme/test/sysfs/meson.build +++ b/libnvme/test/sysfs/meson.build @@ -8,7 +8,7 @@ diff = find_program('diff', required : false) if diff.found() tree_dump = executable( - 'libnvme - test-tree-dump', + 'test-tree-dump', ['tree-dump.c'], dependencies: libnvme_dep, ) diff --git a/libnvme/test/sysfs/tree-diff.sh b/libnvme/test/sysfs/tree-diff.sh index 39b8d0d405..6ee7bc7420 100644 --- a/libnvme/test/sysfs/tree-diff.sh +++ b/libnvme/test/sysfs/tree-diff.sh @@ -14,9 +14,22 @@ rm -rf "${TEST_DIR}" mkdir "${TEST_DIR}" tar -x -f "${SYSFS_INPUT}" -C "${TEST_DIR}" -LIBNVME_SYSFS_PATH="${TEST_DIR}" \ -LIBNVME_HOSTNQN=nqn.2014-08.org.nvmexpress:uuid:ce4fee3e-c02c-11ee-8442-830d068a36c6 \ -LIBNVME_HOSTID=ce4fee3e-c02c-11ee-8442-830d068a36c6 \ -"${TREE_DUMP}" > "${ACTUAL_OUTPUT}" || echo "test failed" +cmd=( + env + LIBNVME_SYSFS_PATH="$TEST_DIR" + LIBNVME_HOSTNQN="nqn.2014-08.org.nvmexpress:uuid:ce4fee3e-c02c-11ee-8442-830d068a36c6" + LIBNVME_HOSTID="ce4fee3e-c02c-11ee-8442-830d068a36c6" + "$TREE_DUMP" +) + +echo "Running command:" +printf '%q ' "${cmd[@]}" +printf '> %q\n' "$ACTUAL_OUTPUT" + +if ! "${cmd[@]}" > "$ACTUAL_OUTPUT"; then + rc=$? + echo "test failed (exit code $rc)" + exit $rc +fi diff -u "${EXPECTED_OUTPUT}" "${ACTUAL_OUTPUT}" From bc95f55a420d8070c20c9fe7c99141d80e503cc1 Mon Sep 17 00:00:00 2001 From: Daniel Wagner Date: Thu, 8 Jan 2026 10:41:10 +0100 Subject: [PATCH 4/5] tree: remove nvme_update_config nvme_update_config is used to dump the current configuration to the either stdout or a config file. There is also nvme_dump_config which does almost the same thing. The only difference is that nvme_update_config is testing if the something has been modified. The modified tracking happens on a global level and almost all operations on the tree will set the modified flag. This is actually not really needed. nvme-cli uses for the 'config' command which expects that the config is updated. One could argue that the config should not be written when nothing changes. But this could be done in a different way, e.g. create a temp config and compare it to the original and only overwrite the original if something changes. But no one complained that the config is overwritten all the time so far (remember the modified flag is almost certainly always set). Signed-off-by: Daniel Wagner --- fabrics.c | 8 ++++---- libnvme/libnvme/nvme.i | 5 +---- libnvme/src/libnvme.ld | 1 - libnvme/src/nvme/private.h | 1 - libnvme/src/nvme/tree.c | 16 ++-------------- libnvme/src/nvme/tree.h | 16 ++++------------ libnvme/test/config/config-dump.c | 2 +- libnvme/test/config/psk-json.c | 2 +- 8 files changed, 13 insertions(+), 38 deletions(-) diff --git a/fabrics.c b/fabrics.c index 6c846e7a14..e6f8ea1641 100644 --- a/fabrics.c +++ b/fabrics.c @@ -579,7 +579,7 @@ int fabrics_discovery(const char *desc, int argc, char **argv, bool connect) out_free: if (dump_config) - nvme_dump_config(ctx); + nvme_dump_config(ctx, NULL); return ret; } @@ -714,7 +714,7 @@ int fabrics_connect(const char *desc, int argc, char **argv) } if (dump_config) - nvme_dump_config(ctx); + nvme_dump_config(ctx, NULL); return 0; } @@ -1029,10 +1029,10 @@ int fabrics_config(const char *desc, int argc, char **argv) } if (update_config) - nvme_update_config(ctx); + nvme_dump_config(ctx, config_file); if (dump_config) - nvme_dump_config(ctx); + nvme_dump_config(ctx, NULL); return 0; } diff --git a/libnvme/libnvme/nvme.i b/libnvme/libnvme/nvme.i index 2cca7d6565..a6fc37a76b 100644 --- a/libnvme/libnvme/nvme.i +++ b/libnvme/libnvme/nvme.i @@ -528,11 +528,8 @@ struct nvme_ns { void refresh_topology() { nvme_refresh_topology($self); } - void update_config() { - nvme_update_config($self); - } void dump_config() { - nvme_dump_config($self); + nvme_dump_config($self, NULL); } } diff --git a/libnvme/src/libnvme.ld b/libnvme/src/libnvme.ld index 60dc9b3d00..6a0be1e27e 100644 --- a/libnvme/src/libnvme.ld +++ b/libnvme/src/libnvme.ld @@ -275,7 +275,6 @@ LIBNVME_2_0 { nvme_transport_handle_set_submit_entry; nvme_transport_handle_set_submit_exit; nvme_unlink_ctrl; - nvme_update_config; nvme_update_key; nvme_uuid_find; nvme_uuid_from_string; diff --git a/libnvme/src/nvme/private.h b/libnvme/src/nvme/private.h index 6b2a864805..e11dae4083 100644 --- a/libnvme/src/nvme/private.h +++ b/libnvme/src/nvme/private.h @@ -267,7 +267,6 @@ struct nvme_global_ctx { struct list_head endpoints; /* MI endpoints */ struct list_head hosts; struct nvme_log log; - bool modified; bool mi_probe_enabled; bool create_only; bool dry_run; diff --git a/libnvme/src/nvme/tree.c b/libnvme/src/nvme/tree.c index 2fdde49ee2..67835f1ffb 100644 --- a/libnvme/src/nvme/tree.c +++ b/libnvme/src/nvme/tree.c @@ -404,17 +404,9 @@ int nvme_scan(const char *config_file, struct nvme_global_ctx **ctxp) return ret; } -int nvme_update_config(struct nvme_global_ctx *ctx) +int nvme_dump_config(struct nvme_global_ctx *ctx, const char *config_file) { - if (!ctx->modified || !ctx->config_file) - return 0; - - return json_update_config(ctx, ctx->config_file); -} - -int nvme_dump_config(struct nvme_global_ctx *ctx) -{ - return json_update_config(ctx, NULL); + return json_update_config(ctx, config_file); } int nvme_dump_tree(struct nvme_global_ctx *ctx) @@ -717,7 +709,6 @@ struct nvme_subsystem *nvme_alloc_subsystem(struct nvme_host *h, list_head_init(&s->namespaces); list_node_init(&s->entry); list_add_tail(&h->subsystems, &s->entry); - h->ctx->modified = true; return s; } @@ -756,7 +747,6 @@ static void __nvme_free_host(struct nvme_host *h) free(h->hostid); free(h->dhchap_key); nvme_host_set_hostsymname(h, NULL); - h->ctx->modified = true; free(h); } @@ -799,7 +789,6 @@ struct nvme_host *nvme_lookup_host(struct nvme_global_ctx *ctx, const char *host list_node_init(&h->entry); h->ctx = ctx; list_add_tail(&ctx->hosts, &h->entry); - ctx->modified = true; return h; } @@ -1870,7 +1859,6 @@ nvme_ctrl_t nvme_lookup_ctrl(nvme_subsystem_t s, const char *transport, c->s = s; list_add_tail(&s->ctrls, &c->entry); - s->h->ctx->modified = true; return c; } diff --git a/libnvme/src/nvme/tree.h b/libnvme/src/nvme/tree.h index 541f1c5601..469dc29495 100644 --- a/libnvme/src/nvme/tree.h +++ b/libnvme/src/nvme/tree.h @@ -1453,26 +1453,18 @@ int nvme_read_config(struct nvme_global_ctx *ctx, const char *config_file); */ void nvme_refresh_topology(struct nvme_global_ctx *ctx); -/** - * nvme_update_config() - Update JSON configuration - * @ctx: &struct nvme_global_ctx object - * - * Updates the JSON configuration file with the contents of @r. - * - * Return: 0 on success, -1 on failure. - */ -int nvme_update_config(struct nvme_global_ctx *ctx); - /** * nvme_dump_config() - Print the JSON configuration * @ctx: &struct nvme_global_ctx object + * @config_file: JSON configuration file. * * Prints the current contents of the JSON configuration - * file to stdout. + * file to the config_file. If connfig_file is not provided it prints + * to stdout. * * Return: 0 on success, or negative error code otherwise. */ -int nvme_dump_config(struct nvme_global_ctx *ctx); +int nvme_dump_config(struct nvme_global_ctx *ctx, const char *config_file); /** * nvme_dump_tree() - Dump internal object tree diff --git a/libnvme/test/config/config-dump.c b/libnvme/test/config/config-dump.c index bf8318ee77..d9e8d27032 100644 --- a/libnvme/test/config/config-dump.c +++ b/libnvme/test/config/config-dump.c @@ -29,7 +29,7 @@ static bool config_dump(const char *file) if (err) goto out; - err = nvme_dump_config(ctx); + err = nvme_dump_config(ctx, NULL); if (err) goto out; diff --git a/libnvme/test/config/psk-json.c b/libnvme/test/config/psk-json.c index 1469dac520..678130982b 100644 --- a/libnvme/test/config/psk-json.c +++ b/libnvme/test/config/psk-json.c @@ -69,7 +69,7 @@ static bool psk_json_test(char *file) if (!import_export_key(c)) goto out; - err = nvme_dump_config(ctx); + err = nvme_dump_config(ctx, NULL); if (err) goto out; From 860b3bcb87ee30eda0bfa9ab735052995ee12052 Mon Sep 17 00:00:00 2001 From: Daniel Wagner Date: Wed, 7 Jan 2026 19:23:39 +0100 Subject: [PATCH 5/5] fabrics: reorder and align fabric_args assigments Follow the same order for describing the fabrics configuration. This will make is simpler to replace fabrics_args with nvmf_context. While at it also fix the assignments alignment. Signed-off-by: Daniel Wagner --- libnvme/src/nvme/fabrics.c | 54 +++++++++++++++++++------------------- libnvme/src/nvme/private.h | 2 +- 2 files changed, 28 insertions(+), 28 deletions(-) diff --git a/libnvme/src/nvme/fabrics.c b/libnvme/src/nvme/fabrics.c index 89cdbed9bc..6917e66141 100644 --- a/libnvme/src/nvme/fabrics.c +++ b/libnvme/src/nvme/fabrics.c @@ -2141,9 +2141,9 @@ static int _nvmf_discovery(struct nvme_global_ctx *ctx, .subsysnqn = e->subnqn, .transport = nvmf_trtype_str(e->trtype), .traddr = e->traddr, + .trsvcid = e->trsvcid, .host_traddr = fctx->host_traddr, .host_iface = fctx->host_iface, - .trsvcid = e->trsvcid, }; /* Already connected ? */ @@ -2400,12 +2400,12 @@ int _discovery_config_json(struct nvme_global_ctx *ctx, memcpy(&cfg, fctx->cfg, sizeof(cfg)); struct fabric_args trcfg = { - .subsysnqn = subsysnqn, - .transport = transport, - .traddr = traddr, - .host_traddr = host_traddr, - .host_iface = host_iface, - .trsvcid = trsvcid, + .subsysnqn = subsysnqn, + .transport = transport, + .traddr = traddr, + .trsvcid = trsvcid, + .host_traddr = host_traddr, + .host_iface = host_iface, }; if (!force) { @@ -2561,12 +2561,12 @@ int nvmf_discovery_config_file(struct nvme_global_ctx *ctx, break; struct fabric_args trcfg = { - .transport = fctx->transport, - .traddr = fctx->traddr, - .trsvcid = fctx->trsvcid, - .subsysnqn = fctx->subsysnqn, - .host_traddr = fctx->host_traddr, - .host_iface = fctx->host_iface, + .subsysnqn = fctx->subsysnqn, + .transport = fctx->transport, + .traddr = fctx->traddr, + .trsvcid = fctx->trsvcid, + .host_traddr = fctx->host_traddr, + .host_iface = fctx->host_iface, }; if (!force) { @@ -2929,9 +2929,9 @@ int nvmf_discovery_nbft(struct nvme_global_ctx *ctx, .subsysnqn = (*ss)->subsys_nqn, .transport = (*ss)->transport, .traddr = (*ss)->traddr, + .trsvcid = (*ss)->trsvcid, .host_traddr = host_traddr, .host_iface = NULL, - .trsvcid = (*ss)->trsvcid, }; rr = nbft_connect(ctx, fctx, h, NULL, @@ -3019,9 +3019,9 @@ int nvmf_discovery_nbft(struct nvme_global_ctx *ctx, .subsysnqn = NVME_DISC_SUBSYS_NAME, .transport = uri->protocol, .traddr = uri->host, + .trsvcid = trsvcid, .host_traddr = host_traddr, .host_iface = NULL, - .trsvcid = trsvcid, }; /* Lookup existing discovery controller */ @@ -3224,12 +3224,12 @@ int nvmf_discovery(struct nvme_global_ctx *ctx, struct nvmf_context *fctx, } struct fabric_args trcfg = { - .subsysnqn = fctx->subsysnqn, - .transport = fctx->transport, - .traddr = fctx->traddr, - .host_traddr = fctx->host_traddr, - .host_iface = fctx->host_iface, - .trsvcid = fctx->trsvcid, + .subsysnqn = fctx->subsysnqn, + .transport = fctx->transport, + .traddr = fctx->traddr, + .trsvcid = fctx->trsvcid, + .host_traddr = fctx->host_traddr, + .host_iface = fctx->host_iface, }; if (!c && !force) { @@ -3301,12 +3301,12 @@ int nvmf_connect(struct nvme_global_ctx *ctx, struct nvmf_context *fctx) return err; struct fabric_args trcfg = { - .subsysnqn = fctx->subsysnqn, - .transport = fctx->transport, - .traddr = fctx->traddr, - .host_traddr = fctx->host_traddr, - .host_iface = fctx->host_iface, - .trsvcid = fctx->trsvcid, + .subsysnqn = fctx->subsysnqn, + .transport = fctx->transport, + .traddr = fctx->traddr, + .trsvcid = fctx->trsvcid, + .host_traddr = fctx->host_traddr, + .host_iface = fctx->host_iface, }; c = lookup_ctrl(h, &trcfg); diff --git a/libnvme/src/nvme/private.h b/libnvme/src/nvme/private.h index e11dae4083..db7cebbe9f 100644 --- a/libnvme/src/nvme/private.h +++ b/libnvme/src/nvme/private.h @@ -376,9 +376,9 @@ struct fabric_args { const char *subsysnqn; const char *transport; const char *traddr; + const char *trsvcid; const char *host_traddr; const char *host_iface; - const char *trsvcid; }; int nvme_set_attr(const char *dir, const char *attr, const char *value);