Skip to content

Commit 1c9817a

Browse files
wxiong66igaw
authored andcommitted
plugins/ibm: show persist events log
Add two IBM specific persistent events log: DE-01: Change Definition DE-02: Reported Error Signed-off-by: Wen Xiong <[email protected]>
1 parent f5694b2 commit 1c9817a

File tree

4 files changed

+214
-2
lines changed

4 files changed

+214
-2
lines changed

nvme-print-stdout.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -277,7 +277,7 @@ static void stdout_persistent_event_log_fdp_events(unsigned int cdw11, unsigned
277277
}
278278
}
279279

280-
static void pel_header(struct nvme_persistent_event_log *pevent_log_head, int human)
280+
void nvme_show_pel_header(struct nvme_persistent_event_log *pevent_log_head, int human)
281281
{
282282
printf("Log Identifier: %u\n", pevent_log_head->lid);
283283
printf("Total Number of Events: %u\n", le32_to_cpu(pevent_log_head->tnev));
@@ -513,7 +513,7 @@ static void stdout_persistent_event_log(void *pevent_log_info, __u8 action, __u3
513513

514514
pevent_log_head = pevent_log_info;
515515

516-
pel_header(pevent_log_head, human);
516+
nvme_show_pel_header(pevent_log_head, human);
517517

518518
printf("\n");
519519
printf("\nPersistent Event Entries:\n");

nvme-print.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -366,6 +366,7 @@ void nvme_show_ave_discovery_log(struct nvme_ave_discover_log *log, nvme_print_f
366366
void nvme_show_pull_model_ddc_req_log(struct nvme_pull_model_ddc_req_log *log,
367367
nvme_print_flags_t flags);
368368
void nvme_show_log(const char *devname, struct nvme_get_log_args *args, nvme_print_flags_t flags);
369+
void nvme_show_pel_header(struct nvme_persistent_event_log *pevent_log_head, int human);
369370

370371
extern char *alloc_error;
371372
#endif /* NVME_PRINT_H */

plugins/ibm/ibm-nvme.c

Lines changed: 209 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -391,3 +391,212 @@ static int get_ibm_vpd_log(int argc, char **argv, struct command *cmd, struct pl
391391
dev_close(dev);
392392
return err;
393393
}
394+
395+
#define NVME_VENDOR_SPECIFIC_EVENT 0xde
396+
#define NVME_IBM_CHG_DEF 0x1
397+
#define NVME_IBM_RPT_ERR 0x2
398+
399+
struct ibm_change_def_event {
400+
__le64 pom;
401+
__u8 vs1;
402+
__u8 vs2;
403+
__u8 dp;
404+
};
405+
406+
struct ibm_reported_err_event {
407+
__le64 pom;
408+
__u8 temp;
409+
__u8 retry_cnt;
410+
__u8 sc;
411+
__u8 sct;
412+
__le64 cmd_specific_info;
413+
__u8 *cmd;
414+
415+
};
416+
417+
/* persistent event type deh */
418+
struct nvme_pel_ibm_specific_event {
419+
__le16 vsecode;
420+
__u8 vsetype;
421+
__u8 uuid;
422+
__le16 vsedl;
423+
__u8 *vse_data;
424+
};
425+
426+
static const char *raw_use = "use binary output";
427+
428+
void nvme_show_ibm_persistent_event_log(void *pevent_log_info,
429+
__u8 action, __u32 size, const char *devname,
430+
enum nvme_print_flags flags)
431+
{
432+
__u32 offset;
433+
struct nvme_pel_ibm_specific_event *vendor_speci_event;
434+
struct nvme_persistent_event_log *pevent_log_head;
435+
struct nvme_persistent_event_entry *pevent_entry_head;
436+
int human = flags & VERBOSE;
437+
bool ibm_event = false;
438+
int i = 0;
439+
440+
if (flags & BINARY)
441+
return d_raw((unsigned char *)pevent_log_info, size);
442+
443+
offset = sizeof(*pevent_log_head);
444+
445+
printf("Persistent Event Log for device: %s\n", devname);
446+
printf("Action for Persistent Event Log: %u\n", action);
447+
448+
if (size >= offset) {
449+
pevent_log_head = pevent_log_info;
450+
nvme_show_pel_header(pevent_log_head, human);
451+
} else {
452+
printf("No log data can be shown with this log length\n");
453+
return;
454+
}
455+
456+
printf("\n");
457+
printf(" i=%d tnev=%d\n", i, le32_to_cpu(pevent_log_head->tnev));
458+
for (i = 0; i < le32_to_cpu(pevent_log_head->tnev); i++) {
459+
if (offset + sizeof(*pevent_entry_head) >= size)
460+
break;
461+
462+
pevent_entry_head = pevent_log_info + offset;
463+
if ((offset + pevent_entry_head->ehl + 3 +
464+
le16_to_cpu(pevent_entry_head->el)) >= size)
465+
break;
466+
467+
offset += pevent_entry_head->ehl + 3;
468+
469+
switch (pevent_entry_head->etype) {
470+
case NVME_VENDOR_SPECIFIC_EVENT:
471+
printf("\nPersistent Event Entries:\n");
472+
printf("Event Number: %u\n", i);
473+
printf("Event Type Field: 0x%X\n", pevent_entry_head->etype);
474+
printf("Event Type Revision: 0x%X\n", pevent_entry_head->etype_rev);
475+
476+
vendor_speci_event = pevent_log_info + offset;
477+
478+
printf("Vendor Specific Event Code: 0x%X\n",
479+
le16_to_cpu(vendor_speci_event->vsecode));
480+
printf("Vendor Specific Event Data Type: 0x%X\n",
481+
vendor_speci_event->vsetype);
482+
printf("UUID Index: %u\n", vendor_speci_event->uuid);
483+
printf("VSEDL: %u\n", le16_to_cpu(vendor_speci_event->vsedl));
484+
485+
if (le16_to_cpu(vendor_speci_event->vsecode) == NVME_IBM_CHG_DEF) {
486+
struct ibm_change_def_event *change_def;
487+
488+
change_def = pevent_log_info + offset + 6;
489+
printf("POM: %"PRIu64"\n", le64_to_cpu(change_def->pom));
490+
printf("VS1: %u\n", change_def->vs1);
491+
printf("VS2: %u\n", change_def->vs2);
492+
printf("DP : %u\n", change_def->dp);
493+
}
494+
495+
if (le16_to_cpu(vendor_speci_event->vsecode) == NVME_IBM_RPT_ERR) {
496+
struct ibm_reported_err_event *report_err;
497+
498+
report_err = pevent_log_info + offset + 6;
499+
printf("POM: %"PRIu64"\n", le64_to_cpu(report_err->pom));
500+
printf("TEMP: %u\n", report_err->temp);
501+
printf("Retry Count: %u\n", report_err->retry_cnt);
502+
printf("SC : %u\n", report_err->sc);
503+
printf("SCT : %u\n", report_err->sct);
504+
printf("CMD Specific Info: %"PRIu64"\n",
505+
le64_to_cpu(report_err->cmd_specific_info));
506+
}
507+
ibm_event = true;
508+
printf("\n");
509+
break;
510+
default:
511+
break;
512+
}
513+
offset += le16_to_cpu(pevent_entry_head->el);
514+
}
515+
516+
if (!ibm_event)
517+
printf("NO IBM specific persistent events found!\n");
518+
}
519+
520+
static int get_ibm_persistent_event_log(int argc, char **argv,
521+
struct command *cmd, struct plugin *plugin)
522+
{
523+
const char *desc = "Retrieve Persistent Event log info for "
524+
"the given device in either decoded format(default), json or binary.";
525+
const char *action = "action the controller shall take during "
526+
"processing this persistent log page command.";
527+
const char *log_len = "number of bytes to retrieve";
528+
struct nvme_persistent_event_log pevent_log;
529+
void *pevent_log_info = NULL;
530+
enum nvme_print_flags flags;
531+
struct nvme_dev *dev;
532+
__u32 log_length = 0;
533+
int err = 0;
534+
535+
struct config {
536+
__u8 action;
537+
__u32 log_len;
538+
char *output_format;
539+
bool raw_binary;
540+
};
541+
542+
struct config cfg = {
543+
.action = 0xff,
544+
.log_len = 0,
545+
.output_format = "normal",
546+
.raw_binary = false,
547+
};
548+
549+
OPT_ARGS(opts) = {
550+
OPT_BYTE("action", 'a', &cfg.action, action),
551+
OPT_UINT("log_len", 'l', &cfg.log_len, log_len),
552+
OPT_FMT("output-format", 'o', &cfg.output_format, output_format),
553+
OPT_FLAG("raw-binary", 'b', &cfg.raw_binary, raw_use),
554+
OPT_END()
555+
};
556+
557+
err = parse_and_open(&dev, argc, argv, desc, opts);
558+
if (err)
559+
goto ret;
560+
561+
err = flags = validate_output_format(cfg.output_format, &flags);
562+
if (flags < 0)
563+
goto close_dev;
564+
565+
if (cfg.raw_binary)
566+
flags = BINARY;
567+
568+
/* get persistent event log */
569+
err = nvme_get_log_persistent_event(dev_fd(dev), NVME_PEVENT_LOG_RELEASE_CTX,
570+
sizeof(pevent_log), &pevent_log);
571+
572+
if (err)
573+
return err;
574+
575+
memset(&pevent_log, 0, sizeof(pevent_log));
576+
577+
err = nvme_get_log_persistent_event(dev_fd(dev), NVME_PEVENT_LOG_EST_CTX_AND_READ,
578+
sizeof(pevent_log), &pevent_log);
579+
if (err) {
580+
fprintf(stderr, "Setting persistent event log read ctx failed (ignored)!\n");
581+
return err;
582+
}
583+
584+
log_length = le64_to_cpu(pevent_log.tll);
585+
pevent_log_info = nvme_alloc(log_length);
586+
if (!pevent_log_info) {
587+
perror("could not alloc buffer for persistent event log page (ignored)!\n");
588+
return err;
589+
}
590+
591+
err = nvme_get_log_persistent_event(dev_fd(dev), NVME_PEVENT_LOG_READ,
592+
log_length, pevent_log_info);
593+
if (!err) {
594+
nvme_show_ibm_persistent_event_log(pevent_log_info, cfg.action,
595+
log_length, dev->name, flags);
596+
}
597+
598+
close_dev:
599+
dev_close(dev);
600+
ret:
601+
return err;
602+
}

plugins/ibm/ibm-nvme.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@ PLUGIN(NAME("ibm", "IBM vendor specific extensions", NVME_VERSION),
1313
COMMAND_LIST(
1414
ENTRY("crit-log", "Display IBM Smart Log Information", get_ibm_addi_smart_log)
1515
ENTRY("vpd", "Display IBM VPD Information", get_ibm_vpd_log)
16+
ENTRY("persist-event-log", "IBM specific Persistent Event Log",
17+
get_ibm_persistent_event_log)
1618
)
1719
);
1820
#endif

0 commit comments

Comments
 (0)