1
0
Fork 0

Adding upstream version 2.12.

Signed-off-by: Daniel Baumann <daniel@debian.org>
This commit is contained in:
Daniel Baumann 2025-03-20 08:10:40 +01:00
parent 65508f0a28
commit c0fbec1eb4
Signed by: daniel
GPG key ID: FBB4F0E80A80222F
571 changed files with 10718 additions and 2738 deletions

View file

@ -3,10 +3,15 @@
#include <assert.h>
#include <errno.h>
#include <time.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <ccan/ccan/compiler/compiler.h>
#include "nvme-print.h"
#include "util/json.h"
#include "util/logging.h"
#include "nvme.h"
#include "common.h"
@ -28,6 +33,13 @@
#define obj_add_uint json_object_add_value_uint
#define obj_add_uint128 json_object_add_value_uint128
#define obj_add_uint64 json_object_add_value_uint64
#define obj_add_str json_object_add_value_string
#define obj_add_uint_02x json_object_add_uint_02x
#define obj_add_uint_0x json_object_add_uint_0x
#define obj_add_byte_array json_object_add_byte_array
#define obj_add_nprix64 json_object_add_nprix64
#define obj_add_uint_0nx json_object_add_uint_0nx
#define obj_add_0nprix64 json_object_add_0nprix64
static const uint8_t zero_uuid[16] = { 0 };
static struct print_ops json_print_ops;
@ -74,27 +86,6 @@ static void obj_add_uint_x(struct json_object *o, const char *k, __u32 v)
obj_add_str(o, k, str);
}
void obj_add_uint_0x(struct json_object *o, const char *k, __u32 v)
{
char str[STR_LEN];
sprintf(str, "0x%x", v);
obj_add_str(o, k, str);
}
void obj_add_uint_0nx(struct json_object *o, const char *k, __u32 v, int width)
{
char str[STR_LEN];
sprintf(str, "0x%0*x", width, v);
obj_add_str(o, k, str);
}
void obj_add_uint_02x(struct json_object *o, const char *k, __u32 v)
{
obj_add_uint_0nx(o, k, v, 2);
}
static void obj_add_uint_nx(struct json_object *o, const char *k, __u32 v)
{
char str[STR_LEN];
@ -103,14 +94,6 @@ static void obj_add_uint_nx(struct json_object *o, const char *k, __u32 v)
obj_add_str(o, k, str);
}
void obj_add_nprix64(struct json_object *o, const char *k, uint64_t v)
{
char str[STR_LEN];
sprintf(str, "%#"PRIx64"", v);
obj_add_str(o, k, str);
}
static void obj_add_prix64(struct json_object *o, const char *k, uint64_t v)
{
char str[STR_LEN];
@ -203,9 +186,27 @@ static void obj_print(struct json_object *o)
json_print(o);
}
static void json_id_iocs_iocsc(struct json_object *obj_iocsc, __u64 iocsc)
{
__u8 cpncs = NVME_GET(iocsc, IOCS_IOCSC_CPNCS);
__u8 slmcs = NVME_GET(iocsc, IOCS_IOCSC_SLMCS);
__u8 znscs = NVME_GET(iocsc, IOCS_IOCSC_ZNSCS);
__u8 kvcs = NVME_GET(iocsc, IOCS_IOCSC_KVCS);
__u8 nvmcs = NVME_GET(iocsc, IOCS_IOCSC_NVMCS);
obj_add_str(obj_iocsc, "Computational Programs Namespace Command Set", cpncs ?
"Selected" : "Not selected");
obj_add_str(obj_iocsc, "Subsystem Local Memory Command Set", slmcs ?
"Selected" : "Not selected");
obj_add_str(obj_iocsc, "Zoned Namespace Command Set", znscs ? "Selected" : "Not selected");
obj_add_str(obj_iocsc, "Key Value Command Set", kvcs ? "Selected" : "Not selected");
obj_add_str(obj_iocsc, "NVM Command Set", nvmcs ? "Selected" : "Not selected");
}
static void json_id_iocs(struct nvme_id_iocs *iocs)
{
struct json_object *r = json_create_object();
struct json_object *obj_iocsc;
char json_str[STR_LEN];
__u16 i;
@ -213,6 +214,11 @@ static void json_id_iocs(struct nvme_id_iocs *iocs)
if (iocs->iocsc[i]) {
sprintf(json_str, "I/O Command Set Combination[%u]", i);
obj_add_uint64(r, json_str, le64_to_cpu(iocs->iocsc[i]));
obj_iocsc = json_create_object();
sprintf(json_str, "IOCSC%u", i);
json_id_iocs_iocsc(obj_iocsc, le64_to_cpu(iocs->iocsc[i]));
obj_add_obj(r, json_str, obj_iocsc);
}
}
@ -260,8 +266,6 @@ static void json_nvme_id_ns(struct nvme_id_ns *ns, unsigned int nsid,
obj_add_int(r, "nabspf", le16_to_cpu(ns->nabspf));
obj_add_int(r, "noiob", le16_to_cpu(ns->noiob));
obj_add_uint128(r, "nvmcap", nvmcap);
obj_add_int(r, "nsattr", ns->nsattr);
obj_add_int(r, "nvmsetid", le16_to_cpu(ns->nvmsetid));
if (ns->nsfeat & 0x30) {
obj_add_int(r, "npwg", le16_to_cpu(ns->npwg));
@ -275,12 +279,16 @@ static void json_nvme_id_ns(struct nvme_id_ns *ns, unsigned int nsid,
obj_add_int(r, "mssrl", le16_to_cpu(ns->mssrl));
obj_add_uint(r, "mcl", le32_to_cpu(ns->mcl));
obj_add_int(r, "msrc", ns->msrc);
obj_add_uint(r, "kpios", ns->kpios);
}
obj_add_int(r, "nulbaf", ns->nulbaf);
if (!cap_only) {
obj_add_uint(r, "kpiodaag", le32_to_cpu(ns->kpiodaag));
obj_add_uint(r, "anagrpid", le32_to_cpu(ns->anagrpid));
obj_add_int(r, "nsattr", ns->nsattr);
obj_add_int(r, "nvmsetid", le16_to_cpu(ns->nvmsetid));
obj_add_int(r, "endgid", le16_to_cpu(ns->endgid));
memset(eui64, 0, sizeof(eui64_buf));
@ -293,8 +301,8 @@ static void json_nvme_id_ns(struct nvme_id_ns *ns, unsigned int nsid,
for (i = 0; i < sizeof(ns->nguid); i++)
nguid += sprintf(nguid, "%02x", ns->nguid[i]);
obj_add_str(r, "eui64", eui64_buf);
obj_add_str(r, "nguid", nguid_buf);
obj_add_str(r, "eui64", eui64_buf);
}
obj_add_array(r, "lbafs", lbafs);
@ -350,11 +358,15 @@ void json_nvme_id_ctrl(struct nvme_id_ctrl *ctrl,
obj_add_uint(r, "oaes", le32_to_cpu(ctrl->oaes));
obj_add_uint(r, "ctratt", le32_to_cpu(ctrl->ctratt));
obj_add_int(r, "rrls", le16_to_cpu(ctrl->rrls));
obj_add_int(r, "bpcap", ctrl->bpcap);
obj_add_uint(r, "nssl", le32_to_cpu(ctrl->nssl));
obj_add_int(r, "plsi", ctrl->plsi);
obj_add_int(r, "cntrltype", ctrl->cntrltype);
obj_add_str(r, "fguid", util_uuid_to_string(ctrl->fguid));
obj_add_int(r, "crdt1", le16_to_cpu(ctrl->crdt1));
obj_add_int(r, "crdt2", le16_to_cpu(ctrl->crdt2));
obj_add_int(r, "crdt3", le16_to_cpu(ctrl->crdt3));
obj_add_int(r, "crcap", ctrl->crcap);
obj_add_int(r, "nvmsr", ctrl->nvmsr);
obj_add_int(r, "vwci", ctrl->vwci);
obj_add_int(r, "mec", ctrl->mec);
@ -393,8 +405,11 @@ void json_nvme_id_ctrl(struct nvme_id_ctrl *ctrl,
obj_add_uint(r, "nanagrpid", le32_to_cpu(ctrl->nanagrpid));
obj_add_uint(r, "pels", le32_to_cpu(ctrl->pels));
obj_add_int(r, "domainid", le16_to_cpu(ctrl->domainid));
obj_add_int(r, "kpioc", ctrl->kpioc);
obj_add_int(r, "mptfawr", le16_to_cpu(ctrl->mptfawr));
obj_add_uint128(r, "megcap", megcap);
obj_add_int(r, "tmpthha", ctrl->tmpthha);
obj_add_int(r, "cqt", le16_to_cpu(ctrl->cqt));
obj_add_int(r, "sqes", ctrl->sqes);
obj_add_int(r, "cqes", ctrl->cqes);
obj_add_int(r, "maxcmd", le16_to_cpu(ctrl->maxcmd));
@ -414,6 +429,18 @@ void json_nvme_id_ctrl(struct nvme_id_ctrl *ctrl,
obj_add_uint128(r, "maxdna", maxdna);
obj_add_uint(r, "maxcna", le32_to_cpu(ctrl->maxcna));
obj_add_uint(r, "oaqd", le32_to_cpu(ctrl->oaqd));
obj_add_int(r, "rhiri", ctrl->rhiri);
obj_add_int(r, "hirt", ctrl->hirt);
obj_add_int(r, "cmmrtd", le16_to_cpu(ctrl->cmmrtd));
obj_add_int(r, "nmmrtd", le16_to_cpu(ctrl->nmmrtd));
obj_add_int(r, "minmrtg", ctrl->minmrtg);
obj_add_int(r, "maxmrtg", ctrl->maxmrtg);
obj_add_int(r, "trattr", ctrl->trattr);
obj_add_int(r, "mcudmq", le16_to_cpu(ctrl->mcudmq));
obj_add_int(r, "mnsudmq", le16_to_cpu(ctrl->mnsudmq));
obj_add_int(r, "mcmr", le16_to_cpu(ctrl->mcmr));
obj_add_int(r, "nmcmr", le16_to_cpu(ctrl->nmcmr));
obj_add_int(r, "mcdqpc", le16_to_cpu(ctrl->mcdqpc));
if (strlen(subnqn))
obj_add_str(r, "subnqn", subnqn);
@ -431,8 +458,9 @@ void json_nvme_id_ctrl(struct nvme_id_ctrl *ctrl,
struct json_object *psd = json_create_object();
obj_add_int(psd, "max_power", le16_to_cpu(ctrl->psd[i].mp));
obj_add_int(psd, "max_power_scale", ctrl->psd[i].flags & 0x1);
obj_add_int(psd, "non-operational_state", (ctrl->psd[i].flags & 2) >> 1);
obj_add_int(psd, "max_power_scale", ctrl->psd[i].flags & NVME_PSD_FLAGS_MXPS);
obj_add_int(psd, "non-operational_state",
!!(ctrl->psd[i].flags & NVME_PSD_FLAGS_NOPS));
obj_add_uint(psd, "entry_lat", le32_to_cpu(ctrl->psd[i].enlat));
obj_add_uint(psd, "exit_lat", le32_to_cpu(ctrl->psd[i].exlat));
obj_add_int(psd, "read_tput", ctrl->psd[i].rrt);
@ -444,6 +472,12 @@ void json_nvme_id_ctrl(struct nvme_id_ctrl *ctrl,
obj_add_int(psd, "active_power", le16_to_cpu(ctrl->psd[i].actp));
obj_add_int(psd, "active_power_work", ctrl->psd[i].apws & 7);
obj_add_int(psd, "active_scale", nvme_psd_power_scale(ctrl->psd[i].apws));
obj_add_int(psd, "emerg_power_fail_recover_time", ctrl->psd[i].epfrt);
obj_add_int(psd, "emerg_power_fail_recover_scale", ctrl->psd[i].epfr_fqv_ts & 0xf);
obj_add_int(psd, "force_quiesce_vault_time", ctrl->psd[i].fqvt);
obj_add_int(psd, "force_quiesce_vault_scale", ctrl->psd[i].epfr_fqv_ts >> 4);
obj_add_int(psd, "emerg_power_fail_vault_time", ctrl->psd[i].epfvt);
obj_add_int(psd, "emerg_power_fail_vault_scale", ctrl->psd[i].epfvts & 0xf);
array_add_obj(psds, psd);
}
@ -577,8 +611,7 @@ void json_fw_log(struct nvme_firmware_slot *fw_log, const char *devname)
json_print(r);
}
void json_changed_ns_list_log(struct nvme_ns_list *log,
const char *devname)
void json_changed_ns_list_log(struct nvme_ns_list *log, const char *devname, bool alloc)
{
struct json_object *r = json_create_object();
struct json_object *nsi = json_create_object();
@ -587,10 +620,13 @@ void json_changed_ns_list_log(struct nvme_ns_list *log,
__u32 nsid;
int i;
_cleanup_free_ char *k = NULL;
if (log->ns[0] == cpu_to_le32(0xffffffff))
return;
obj_add_str(r, "Changed Namespace List Log", devname);
if (asprintf(&k, "Changed %s Namespace List Log", alloc ? "Allocated" : "Attached") > 0)
obj_add_str(r, k, devname);
for (i = 0; i < NVME_ID_NS_LIST_MAX; i++) {
nsid = le32_to_cpu(log->ns[i]);
@ -1137,42 +1173,43 @@ static void json_registers_bpinfo(uint32_t bpinfo, struct json_object *r)
{
obj_add_uint_x(r, "bpinfo", bpinfo);
obj_add_uint(r, "Active Boot Partition ID (ABPID)", (bpinfo & 0x80000000) >> 31);
json_registers_bpinfo_brs((bpinfo & 0x3000000) >> 24, r);
obj_add_uint(r, "Boot Partition Size (BPSZ)", bpinfo & 0x7fff);
obj_add_uint(r, "Active Boot Partition ID (ABPID)", NVME_BPINFO_ABPID(bpinfo));
json_registers_bpinfo_brs(NVME_BPINFO_BRS(bpinfo), r);
obj_add_uint(r, "Boot Partition Size (BPSZ)", NVME_BPINFO_BPSZ(bpinfo));
}
static void json_registers_bprsel(uint32_t bprsel, struct json_object *r)
{
obj_add_uint_x(r, "bprsel", bprsel);
obj_add_uint(r, "Boot Partition Identifier (BPID)", (bprsel & 0x80000000) >> 31);
obj_add_uint_x(r, "Boot Partition Read Offset (BPROF)", (bprsel & 0x3ffffc00) >> 10);
obj_add_uint_x(r, "Boot Partition Read Size (BPRSZ)", bprsel & 0x3ff);
obj_add_uint(r, "Boot Partition Identifier (BPID)", NVME_BPRSEL_BPID(bprsel));
obj_add_uint_x(r, "Boot Partition Read Offset (BPROF)", NVME_BPRSEL_BPROF(bprsel));
obj_add_uint_x(r, "Boot Partition Read Size (BPRSZ)", NVME_BPRSEL_BPRSZ(bprsel));
}
static void json_registers_bpmbl(uint64_t bpmbl, struct json_object *r)
{
obj_add_prix64(r, "bpmbl", bpmbl);
obj_add_prix64(r, "Boot Partition Memory Buffer Base Address (BMBBA)", bpmbl);
obj_add_prix64(r, "Boot Partition Memory Buffer Base Address (BMBBA)",
(uint64_t)NVME_BPMBL_BMBBA(bpmbl));
}
static void json_registers_cmbmsc(uint64_t cmbmsc, struct json_object *r)
{
obj_add_prix64(r, "cmbmsc", cmbmsc);
obj_add_prix64(r, "Controller Base Address (CBA)", (cmbmsc & 0xfffffffffffff000) >> 12);
obj_add_prix64(r, "Controller Memory Space Enable (CMSE)", (cmbmsc & 2) >> 1);
obj_add_prix64(r, "Controller Base Address (CBA)", (uint64_t)NVME_CMBMSC_CBA(cmbmsc));
obj_add_prix64(r, "Controller Memory Space Enable (CMSE)", NVME_CMBMSC_CMSE(cmbmsc));
obj_add_str(r, "Capabilities Registers Enabled (CRE)",
cmbmsc & 1 ? "Enabled" : "Not enabled");
NVME_CMBMSC_CRE(cmbmsc) ? "Enabled" : "Not enabled");
}
static void json_registers_cmbsts(uint32_t cmbsts, struct json_object *r)
{
obj_add_uint_x(r, "cmbsts", cmbsts);
obj_add_uint_x(r, "Controller Base Address Invalid (CBAI)", cmbsts & 1);
obj_add_uint_x(r, "Controller Base Address Invalid (CBAI)", NVME_CMBSTS_CBAI(cmbsts));
}
static void json_registers_cmbebs(uint32_t cmbebs, struct json_object *r)
@ -1181,11 +1218,11 @@ static void json_registers_cmbebs(uint32_t cmbebs, struct json_object *r)
obj_add_uint_nx(r, "cmbebs", cmbebs);
obj_add_uint_nx(r, "CMB Elasticity Buffer Size Base (CMBWBZ)", cmbebs >> 8);
sprintf(buffer, "%s", cmbebs & 0x10 ? "shall" : "may");
obj_add_uint_nx(r, "CMB Elasticity Buffer Size Base (CMBWBZ)", NVME_CMBEBS_CMBWBZ(cmbebs));
sprintf(buffer, "%s", NVME_CMBEBS_RBB(cmbebs) ? "shall" : "may");
obj_add_str(r, "CMB Read Bypass Behavior (CMBRBB)", buffer);
obj_add_str(r, "CMB Elasticity Buffer Size Units (CMBSZU)",
nvme_register_unit_to_string(cmbebs & 0xf));
nvme_register_unit_to_string(NVME_CMBEBS_CMBSZU(cmbebs)));
}
static void json_registers_cmbswtp(uint32_t cmbswtp, struct json_object *r)
@ -1194,8 +1231,9 @@ static void json_registers_cmbswtp(uint32_t cmbswtp, struct json_object *r)
obj_add_uint_nx(r, "cmbswtp", cmbswtp);
obj_add_uint_nx(r, "CMB Sustained Write Throughput (CMBSWTV)", cmbswtp >> 8);
sprintf(str, "%s/second", nvme_register_unit_to_string(cmbswtp & 0xf));
obj_add_uint_nx(r, "CMB Sustained Write Throughput (CMBSWTV)",
NVME_CMBSWTP_CMBSWTV(cmbswtp));
sprintf(str, "%s/second", nvme_register_unit_to_string(NVME_CMBSWTP_CMBSWTU(cmbswtp)));
obj_add_str(r, "CMB Sustained Write Throughput Units (CMBSWTU)", str);
}
@ -1375,19 +1413,22 @@ static void json_sanitize_log(struct nvme_sanitize_log_page *sanitize_log,
struct json_object *r = json_create_object();
struct json_object *dev = json_create_object();
struct json_object *sstat = json_create_object();
struct json_object *ssi = json_create_object();
const char *status_str;
__u16 status, sos;
__u8 fails, sans;
char str[128];
__u16 status = le16_to_cpu(sanitize_log->sstat);
status = le16_to_cpu(sanitize_log->sstat);
obj_add_int(dev, "sprog", le16_to_cpu(sanitize_log->sprog));
obj_add_int(sstat, "global_erased", (status & NVME_SANITIZE_SSTAT_GLOBAL_DATA_ERASED) >> 8);
obj_add_int(sstat, "no_cmplted_passes",
(status >> NVME_SANITIZE_SSTAT_COMPLETED_PASSES_SHIFT) &
NVME_SANITIZE_SSTAT_COMPLETED_PASSES_MASK);
obj_add_int(sstat, "media_verification_canceled", NVME_GET(status, SANITIZE_SSTAT_MVCNCLD));
obj_add_int(sstat, "global_erased", NVME_GET(status, SANITIZE_SSTAT_GLOBAL_DATA_ERASED));
obj_add_int(sstat, "no_cmplted_passes", NVME_GET(status, SANITIZE_SSTAT_COMPLETED_PASSES));
sos = NVME_GET(status, SANITIZE_SSTAT_STATUS);
status_str = nvme_sstat_status_to_string(status);
sprintf(str, "(%d) %s", status & NVME_SANITIZE_SSTAT_STATUS_MASK,
status_str);
sprintf(str, "(%d) %s", sos, status_str);
obj_add_str(sstat, "status", str);
obj_add_obj(dev, "sstat", sstat);
@ -1398,7 +1439,21 @@ static void json_sanitize_log(struct nvme_sanitize_log_page *sanitize_log,
obj_add_uint(dev, "time_over_write_no_dealloc", le32_to_cpu(sanitize_log->etond));
obj_add_uint(dev, "time_block_erase_no_dealloc", le32_to_cpu(sanitize_log->etbend));
obj_add_uint(dev, "time_crypto_erase_no_dealloc", le32_to_cpu(sanitize_log->etcend));
obj_add_uint(dev, "time_post_verification_dealloc", le32_to_cpu(sanitize_log->etpvds));
sans = NVME_GET(sanitize_log->ssi, SANITIZE_SSI_SANS);
status_str = nvme_ssi_state_to_string(sans);
sprintf(str, "(%d) %s", sans, status_str);
obj_add_str(ssi, "sanitize_state", str);
if (sos == NVME_SANITIZE_SSTAT_STATUS_COMPLETED_FAILED) {
fails = NVME_GET(sanitize_log->ssi, SANITIZE_SSI_FAILS);
status_str = nvme_ssi_state_to_string(fails);
sprintf(str, "(%d) %s", fails, status_str);
obj_add_str(ssi, "failure_state", str);
}
obj_add_obj(dev, "sanitize_state_information", ssi);
obj_add_obj(r, devname, dev);
json_print(r);
@ -2944,6 +2999,8 @@ static void json_nvme_id_ns_descs(void *data, unsigned int nsid)
static void json_nvme_id_ctrl_nvm(struct nvme_id_ctrl_nvm *ctrl_nvm)
{
struct json_object *r = json_create_object();
__u16 rsvd = (ctrl_nvm->aocs & 0xfffe) >> 1;
__u8 ralbas = ctrl_nvm->aocs & 0x1;
obj_add_uint(r, "vsl", ctrl_nvm->vsl);
obj_add_uint(r, "wzsl", ctrl_nvm->wzsl);
@ -2951,15 +3008,17 @@ static void json_nvme_id_ctrl_nvm(struct nvme_id_ctrl_nvm *ctrl_nvm)
obj_add_uint(r, "dmrl", ctrl_nvm->dmrl);
obj_add_uint(r, "dmrsl", le32_to_cpu(ctrl_nvm->dmrsl));
obj_add_uint64(r, "dmsl", le64_to_cpu(ctrl_nvm->dmsl));
obj_add_uint(r, "kpiocap", ctrl_nvm->kpiocap);
obj_add_uint(r, "wzdsl", ctrl_nvm->wzdsl);
obj_add_uint(r, "aocs", le16_to_cpu(ctrl_nvm->aocs));
__u16 rsvd = (ctrl_nvm->aocs & 0xfffe) >> 1;
__u8 ralbas = ctrl_nvm->aocs & 0x1;
if (rsvd)
obj_add_uint(r, "[15:1]: Reserved", rsvd);
obj_add_uint(r, "[0:0]: Reporting Allocated LBA Supported", ralbas);
obj_add_uint(r, "ver", le32_to_cpu(ctrl_nvm->ver));
obj_add_uint(r, "lbamqf", ctrl_nvm->lbamqf);
json_print(r);
}
@ -3294,24 +3353,36 @@ static void json_feature_show_fields_write_atomic(struct json_object *r, unsigne
static void json_feature_show_fields_async_event(struct json_object *r, unsigned int result)
{
obj_add_str(r, "Discovery Log Page Change Notices", (result & 0x80000000) >> 31 ?
"Send async event" : "Do not send async event");
obj_add_str(r, "Endurance Group Event Aggregate Log Change Notices", (result & 0x4000) >> 14 ?
"Send async event" : "Do not send async event");
obj_add_str(r, "LBA Status Information Notices", (result & 0x2000) >> 13 ?
"Send async event" : "Do not send async event");
const char *async = "Send async event";
const char *no_async = "Do not send async event";
obj_add_str(r, "Discovery Log Page Change Notices", NVME_FEAT_AE_DLPCN(result) ?
async : no_async);
obj_add_str(r, "Host Discovery Log Page Change Notification", NVME_FEAT_AE_HDLPCN(result) ?
async : no_async);
obj_add_str(r, "AVE Discovery Log Page Change Notification", NVME_FEAT_AE_ADLPCN(result) ?
async : no_async);
obj_add_str(r, "Pull Model DDC Request Log Page Change Notification",
NVME_FEAT_AE_PMDRLPCN(result) ? async : no_async);
obj_add_str(r, "Zone Descriptor Changed Notices", NVME_FEAT_AE_ZDCN(result) ?
async : no_async);
obj_add_str(r, "Reachability Group", NVME_FEAT_AE_RGRP0(result) ? async : no_async);
obj_add_str(r, "Reachability Association", NVME_FEAT_AE_RASSN(result) ? async : no_async);
obj_add_str(r, "Normal NVM Subsystem Shutdown", NVME_FEAT_AE_NNSSHDN(result) ?
async : no_async);
obj_add_str(r, "Endurance Group Event Aggregate Log Change Notices",
NVME_FEAT_AE_EGA(result) ? async : no_async);
obj_add_str(r, "LBA Status Information Notices", NVME_FEAT_AE_LBAS(result) ?
async : no_async);
obj_add_str(r, "Predictable Latency Event Aggregate Log Change Notices",
(result & 0x1000) >> 12 ? "Send async event" : "Do not send async event");
obj_add_str(r, "Asymmetric Namespace Access Change Notices", (result & 0x800) >> 11 ?
"Send async event" : "Do not send async event");
obj_add_str(r, "Telemetry Log Notices", (result & 0x400) >> 10 ? "Send async event" :
"Do not send async event");
obj_add_str(r, "Firmware Activation Notices", (result & 0x200) >> 9 ? "Send async event" :
"Do not send async event");
obj_add_str(r, "Namespace Attribute Notices", (result & 0x100) >> 8 ? "Send async event" :
"Do not send async event");
obj_add_str(r, "SMART / Health Critical Warnings", result & 0xff ? "Send async event" :
"Do not send async event");
NVME_FEAT_AE_PLA(result) ? async : no_async);
obj_add_str(r, "Asymmetric Namespace Access Change Notices", NVME_FEAT_AE_ANA(result) ?
async : no_async);
obj_add_str(r, "Telemetry Log Notices", NVME_FEAT_AE_TELEM(result) ? async : no_async);
obj_add_str(r, "Firmware Activation Notices", NVME_FEAT_AE_FW(result) ? async : no_async);
obj_add_str(r, "Namespace Attribute Notices", NVME_FEAT_AE_NAN(result) ? async : no_async);
obj_add_str(r, "SMART / Health Critical Warnings", NVME_FEAT_AE_SMART(result) ?
async : no_async);
}
static void json_auto_pst(struct nvme_feat_auto_pst *apst, struct json_object *r)
@ -3470,8 +3541,25 @@ static void json_feature_show_fields_lba_sts_interval(struct json_object *r, uns
static void json_feature_show_fields_host_behavior(struct json_object *r, unsigned char *buf)
{
if (buf)
if (buf) {
struct nvme_feat_host_behavior *host = (struct nvme_feat_host_behavior *)buf;
obj_add_str(r, "Host Behavior Support", buf[0] & 0x1 ? "True" : "False");
obj_add_str(r, "Advanced Command Retry Enable (ACRE)", host->acre ?
"True" : "False");
obj_add_str(r, "Extended Telemetry Data Area 4 Supported (ETDAS)", host->etdas ?
"True" : "False");
obj_add_str(r, "LBA Format Extension Enable (LBAFEE)", host->lbafee ?
"True" : "False");
obj_add_str(r, "Host Dispersed Namespace Support (HDISNS)", host->hdisns ?
"Enabled" : "Disabled");
obj_add_str(r, "Copy Descriptor Format 2h Enable (CDF2E)", host->cdfe & (1 << 2) ?
"True" : "False");
obj_add_str(r, "Copy Descriptor Format 3h Enable (CDF3E)", host->cdfe & (1 << 3) ?
"True" : "False");
obj_add_str(r, "Copy Descriptor Format 4h Enable (CDF4E)", host->cdfe & (1 << 4) ?
"True" : "False");
}
}
static void json_feature_show_fields_sanitize(struct json_object *r, unsigned int result)
@ -3495,6 +3583,12 @@ static void json_feature_show_fields_spinup_control(struct json_object *r, unsig
obj_add_str(r, "Spinup control feature Enabled", result & 1 ? "True" : "False");
}
static void json_feature_show_fields_power_loss_signal(struct json_object *r, unsigned int result)
{
obj_add_str(r, "Power Loss Signaling Mode (PLSM)",
nvme_pls_mode_to_string(NVME_GET(result, FEAT_PLS_MODE)));
}
static void json_host_metadata(struct json_object *r, enum nvme_features_id fid,
struct nvme_host_metadata *data)
{
@ -3705,6 +3799,9 @@ static void json_feature_show_fields(enum nvme_features_id fid, unsigned int res
case NVME_FEAT_FID_SPINUP_CONTROL:
json_feature_show_fields_spinup_control(r, result);
break;
case NVME_FEAT_FID_POWER_LOSS_SIGNAL:
json_feature_show_fields_power_loss_signal(r, result);
break;
case NVME_FEAT_FID_ENH_CTRL_METADATA:
case NVME_FEAT_FID_CTRL_METADATA:
case NVME_FEAT_FID_NS_METADATA:
@ -4568,6 +4665,268 @@ void json_show_finish(void)
json_r = NULL;
}
static void json_mgmt_addr_list_log(struct nvme_mgmt_addr_list_log *ma_list)
{
int i;
bool reserved = true;
struct json_object *r = json_create_object();
struct json_object *mad;
struct json_object *mat;
char json_str[STR_LEN];
for (i = 0; i < ARRAY_SIZE(ma_list->mad); i++) {
switch (ma_list->mad[i].mat) {
case 1:
case 2:
mad = json_create_object();
mat = json_create_object();
obj_add_str(mat, "definition", ma_list->mad[i].mat == 1 ?
"NVM subsystem management agent" : "fabric interface manager");
snprintf(json_str, sizeof(json_str), "type: %d", ma_list->mad[i].mat);
obj_add_obj(mad, json_str, mat);
obj_add_str(mad, "address", (const char *)ma_list->mad[i].madrs);
snprintf(json_str, sizeof(json_str), "descriptor: %d", i);
obj_add_obj(r, json_str, mad);
reserved = false;
break;
case 0xff:
goto out;
default:
break;
}
}
out:
if (reserved)
obj_add_str(r, "list", "All management address descriptors reserved");
json_print(r);
}
static void json_rotational_media_info_log(struct nvme_rotational_media_info_log *info)
{
struct json_object *r = json_create_object();
obj_add_uint(r, "endgid", le16_to_cpu(info->endgid));
obj_add_uint(r, "numa", le16_to_cpu(info->numa));
obj_add_uint(r, "nrs", le16_to_cpu(info->nrs));
obj_add_uint(r, "spinc", le32_to_cpu(info->spinc));
obj_add_uint(r, "fspinc", le32_to_cpu(info->fspinc));
obj_add_uint(r, "ldc", le32_to_cpu(info->ldc));
obj_add_uint(r, "fldc", le32_to_cpu(info->fldc));
json_print(r);
}
static void json_dispersed_ns_psub_log(struct nvme_dispersed_ns_participating_nss_log *log)
{
struct json_object *r = json_create_object();
__u64 numpsub = le64_to_cpu(log->numpsub);
__u64 i;
char json_str[STR_LEN];
char psub[NVME_NQN_LENGTH + 1];
obj_add_uint64(r, "genctr", le64_to_cpu(log->genctr));
obj_add_uint64(r, "numpsub", numpsub);
for (i = 0; i < numpsub; i++) {
snprintf(json_str, sizeof(json_str), "participating_nss %"PRIu64"", (uint64_t)i);
snprintf(psub, sizeof(psub), "%-.*s", NVME_NQN_LENGTH,
&log->participating_nss[i * NVME_NQN_LENGTH]);
obj_add_str(r, json_str, psub);
}
json_print(r);
}
static void json_reachability_groups_log(struct nvme_reachability_groups_log *log, __u64 len UNUSED)
{
struct json_object *r = json_create_object();
__u16 i;
__u32 j;
char json_str[STR_LEN];
struct json_object *rgd;
obj_add_uint64(r, "chngc", le64_to_cpu(log->chngc));
obj_add_uint(r, "nrgd", le16_to_cpu(log->nrgd));
for (i = 0; i < le16_to_cpu(log->nrgd); i++) {
snprintf(json_str, sizeof(json_str), "rgid: %u", le32_to_cpu(log->rgd[i].rgid));
rgd = json_create_object();
obj_add_uint(rgd, "nnid", le32_to_cpu(log->rgd[i].nnid));
obj_add_uint64(rgd, "chngc", le64_to_cpu(log->rgd[i].chngc));
for (j = 0; j < le32_to_cpu(log->rgd[i].nnid); j++)
obj_add_uint(rgd, "nnid", le32_to_cpu(log->rgd[i].nsid[j]));
obj_add_obj(r, json_str, rgd);
}
json_print(r);
}
static void json_reachability_associations_log(struct nvme_reachability_associations_log *log,
__u64 len UNUSED)
{
struct json_object *r = json_create_object();
__u16 i;
__u32 j;
char json_str[STR_LEN];
struct json_object *rad;
obj_add_uint64(r, "chngc", le64_to_cpu(log->chngc));
obj_add_uint(r, "nrad", le16_to_cpu(log->nrad));
for (i = 0; i < le16_to_cpu(log->nrad); i++) {
snprintf(json_str, sizeof(json_str), "rasid: %u", le32_to_cpu(log->rad[i].rasid));
rad = json_create_object();
obj_add_uint(rad, "nrid", le32_to_cpu(log->rad[i].nrid));
obj_add_uint64(rad, "chngc", le64_to_cpu(log->rad[i].chngc));
obj_add_uint(rad, "rac", log->rad[i].rac);
for (j = 0; j < le32_to_cpu(log->rad[i].nrid); j++)
obj_add_uint(rad, "rgid", le32_to_cpu(log->rad[i].rgid[j]));
obj_add_obj(r, json_str, rad);
}
json_print(r);
}
static void json_host_discovery_log(struct nvme_host_discover_log *log)
{
struct json_object *r = json_create_object();
__u32 i;
__u16 j;
struct nvme_host_ext_discover_log *hedlpe;
struct nvmf_ext_attr *exat;
__u32 thdlpl = le32_to_cpu(log->thdlpl);
__u32 tel;
__u16 numexat;
char json_str[STR_LEN];
struct json_object *hedlpe_o;
struct json_object *tsas_o;
struct json_object *exat_o;
int n = 0;
obj_add_uint64(r, "genctr", le64_to_cpu(log->genctr));
obj_add_uint64(r, "numrec", le64_to_cpu(log->numrec));
obj_add_uint(r, "recfmt", le16_to_cpu(log->recfmt));
obj_add_uint_02x(r, "hdlpf", log->hdlpf);
obj_add_uint(r, "thdlpl", thdlpl);
for (i = sizeof(*log); i < le32_to_cpu(log->thdlpl); i += tel) {
hedlpe_o = json_create_object();
hedlpe = (void *)log + i;
tel = le32_to_cpu(hedlpe->tel);
numexat = le16_to_cpu(hedlpe->numexat);
obj_add_str(hedlpe_o, "trtype", nvmf_trtype_str(hedlpe->trtype));
obj_add_str(hedlpe_o, "adrfam",
strlen(hedlpe->traddr) ? nvmf_adrfam_str(hedlpe->adrfam) : "");
obj_add_str(hedlpe_o, "eflags", nvmf_eflags_str(le16_to_cpu(hedlpe->eflags)));
obj_add_str(hedlpe_o, "hostnqn", hedlpe->hostnqn);
obj_add_str(hedlpe_o, "traddr", hedlpe->traddr);
tsas_o = json_create_object();
switch (hedlpe->trtype) {
case NVMF_TRTYPE_RDMA:
obj_add_str(tsas_o, "prtype", nvmf_prtype_str(hedlpe->tsas.rdma.prtype));
obj_add_str(tsas_o, "qptype", nvmf_qptype_str(hedlpe->tsas.rdma.qptype));
obj_add_str(tsas_o, "cms", nvmf_cms_str(hedlpe->tsas.rdma.cms));
obj_add_uint_0nx(tsas_o, "pkey", le16_to_cpu(hedlpe->tsas.rdma.pkey), 4);
break;
case NVMF_TRTYPE_TCP:
obj_add_str(tsas_o, "sectype", nvmf_sectype_str(hedlpe->tsas.tcp.sectype));
break;
default:
obj_d(tsas_o, "common", (unsigned char *)hedlpe->tsas.common,
sizeof(hedlpe->tsas.common), 16, 1);
break;
}
obj_add_obj(hedlpe_o, "tsas", tsas_o);
obj_add_uint(hedlpe_o, "tel", tel);
obj_add_uint(hedlpe_o, "numexat", numexat);
exat = hedlpe->exat;
for (j = 0; j < numexat; j++) {
exat_o = json_create_object();
snprintf(json_str, sizeof(json_str), "exat: %d", j);
obj_add_uint(exat_o, "exattype", le16_to_cpu(exat->exattype));
obj_add_uint(exat_o, "exatlen", le16_to_cpu(exat->exatlen));
obj_d(exat_o, "exatval", (unsigned char *)exat->exatval,
le16_to_cpu(exat->exatlen), 16, 1);
obj_add_obj(hedlpe_o, json_str, exat_o);
exat = nvmf_exat_ptr_next(exat);
}
snprintf(json_str, sizeof(json_str), "hedlpe: %d", n++);
obj_add_obj(r, json_str, hedlpe_o);
}
}
static void obj_add_traddr(struct json_object *o, const char *k, __u8 adrfam, __u8 *traddr)
{
int af = AF_INET;
socklen_t size = INET_ADDRSTRLEN;
char dst[INET6_ADDRSTRLEN];
if (adrfam == NVMF_ADDR_FAMILY_IP6) {
af = AF_INET6;
size = INET6_ADDRSTRLEN;
}
if (inet_ntop(af, nvmf_adrfam_str(adrfam), dst, size))
obj_add_str(o, k, dst);
}
static void json_ave_discovery_log(struct nvme_ave_discover_log *log)
{
struct json_object *r = json_create_object();
__u32 i;
__u8 j;
struct nvme_ave_discover_log_entry *adlpe;
struct nvme_ave_tr_record *atr;
__u32 tadlpl = le32_to_cpu(log->tadlpl);
__u32 tel;
__u8 numatr;
int n = 0;
char json_str[STR_LEN];
struct json_object *adlpe_o;
struct json_object *atr_o;
obj_add_uint64(r, "genctr", le64_to_cpu(log->genctr));
obj_add_uint64(r, "numrec", le64_to_cpu(log->numrec));
obj_add_uint(r, "recfmt", le16_to_cpu(log->recfmt));
obj_add_uint(r, "thdlpl", tadlpl);
for (i = sizeof(*log); i < le32_to_cpu(log->tadlpl); i += tel) {
adlpe_o = json_create_object();
adlpe = (void *)log + i;
tel = le32_to_cpu(adlpe->tel);
numatr = adlpe->numatr;
obj_add_uint(adlpe_o, "tel", tel);
obj_add_str(adlpe_o, "avenqn", adlpe->avenqn);
obj_add_uint(adlpe_o, "numatr", numatr);
atr = adlpe->atr;
for (j = 0; j < numatr; j++) {
atr_o = json_create_object();
snprintf(json_str, sizeof(json_str), "atr: %d", j);
obj_add_str(atr_o, "aveadrfam", nvmf_adrfam_str(atr->aveadrfam));
obj_add_uint(atr_o, "avetrsvcid", le16_to_cpu(atr->avetrsvcid));
obj_add_traddr(atr_o, "avetraddr", atr->aveadrfam, atr->avetraddr);
obj_add_obj(adlpe_o, json_str, atr_o);
atr++;
}
snprintf(json_str, sizeof(json_str), "adlpe: %d", n++);
obj_add_obj(r, json_str, adlpe_o);
}
}
static void json_pull_model_ddc_req_log(struct nvme_pull_model_ddc_req_log *log)
{
struct json_object *r = json_create_object();
__u32 tpdrpl = le32_to_cpu(log->tpdrpl);
__u32 osp_len = tpdrpl - offsetof(struct nvme_pull_model_ddc_req_log, osp);
obj_add_uint(r, "ori", log->ori);
printf("tpdrpl: %u\n", tpdrpl);
obj_d(r, "osp", (unsigned char *)log->osp, osp_len, 16, 1);
}
static struct print_ops json_print_ops = {
/* libnvme types.h print functions */
.ana_log = json_ana_log,
@ -4635,6 +4994,14 @@ static struct print_ops json_print_ops = {
.d = json_d,
.show_init = json_show_init,
.show_finish = json_show_finish,
.mgmt_addr_list_log = json_mgmt_addr_list_log,
.rotational_media_info_log = json_rotational_media_info_log,
.dispersed_ns_psub_log = json_dispersed_ns_psub_log,
.reachability_groups_log = json_reachability_groups_log,
.reachability_associations_log = json_reachability_associations_log,
.host_discovery_log = json_host_discovery_log,
.ave_discovery_log = json_ave_discovery_log,
.pull_model_ddc_req_log = json_pull_model_ddc_req_log,
/* libnvme tree print functions */
.list_item = json_list_item,
@ -4656,36 +5023,3 @@ struct print_ops *nvme_get_json_print_ops(nvme_print_flags_t flags)
json_print_ops.flags = flags;
return &json_print_ops;
}
void obj_add_byte_array(struct json_object *o, const char *k, unsigned char *buf, int len)
{
int i;
_cleanup_free_ char *value = NULL;
if (!buf || !len) {
obj_add_str(o, k, "No information provided");
return;
}
value = calloc(1, (len + 1) * 2 + 1);
if (!value) {
obj_add_str(o, k, "Could not allocate string");
return;
}
sprintf(value, "0x");
for (i = 1; i <= len; i++)
sprintf(&value[i * 2], "%02x", buf[len - i]);
obj_add_str(o, k, value);
}
void obj_add_0nprix64(struct json_object *o, const char *k, uint64_t v, int width)
{
char str[STR_LEN];
sprintf(str, "0x%0*"PRIx64"", width, v);
obj_add_str(o, k, str);
}