Bug Summary

File:.build-ci/../plugins/seagate/seagate-nvme.c
Warning:line 1507, column 3
Value stored to 'err' is never read

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-pc-linux-gnu -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name seagate-nvme.c -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -pic-is-pie -mframe-pointer=none -fmath-errno -ffp-contract=on -fno-rounding-math -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fdebug-compilation-dir=/__w/nvme-cli/nvme-cli/.build-ci -fcoverage-compilation-dir=/__w/nvme-cli/nvme-cli/.build-ci -resource-dir /usr/lib/llvm-19/lib/clang/19 -include /__w/nvme-cli/nvme-cli/.build-ci/nvme-config.h -I nvme.p -I . -I .. -I ccan -I ../ccan -I libnvme/src -I ../libnvme/src -I /usr/include/json-c -D _FILE_OFFSET_BITS=64 -D _GNU_SOURCE -U NDEBUG -internal-isystem /usr/lib/llvm-19/lib/clang/19/include -internal-isystem /usr/local/include -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/14/../../../../x86_64-linux-gnu/include -internal-externc-isystem /usr/include/x86_64-linux-gnu -internal-externc-isystem /include -internal-externc-isystem /usr/include -O3 -std=gnu99 -ferror-limit 19 -fgnuc-version=4.2.1 -fskip-odr-check-in-gmf -fcolor-diagnostics -vectorize-loops -vectorize-slp -analyzer-opt-analyze-headers -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /__w/nvme-cli/nvme-cli/.build-ci/scan-results/2026-06-24-175442-590-1 -x c ../plugins/seagate/seagate-nvme.c
1// SPDX-License-Identifier: GPL-2.0-or-later
2/*
3 * Do NOT modify or remove this copyright and license
4 *
5 * Copyright (c) 2017-2018 Seagate Technology LLC and/or its Affiliates, All Rights Reserved
6 *
7 * ******************************************************************************************
8 *
9 * This program is free software; you can redistribute it and/or
10 * modify it under the terms of the GNU General Public License
11 * as published by the Free Software Foundation; either version 2
12 * of the License, or (at your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * \file seagate-nvme.c
20 * \brief This file defines the functions and macros to make building a nvme-cli seagate plug-in.
21 *
22 * Author: Debabrata Bardhan <debabrata.bardhan@seagate.com>
23 */
24
25
26#include <ctype.h>
27#include <errno(*__errno_location ()).h>
28#include <fcntl.h>
29#include <inttypes.h>
30#include <stdio.h>
31#include <stdlib.h>
32#include <string.h>
33#include <time.h>
34#include <unistd.h>
35
36#include <sys/stat.h>
37
38#include <libnvme.h>
39
40#include "common.h"
41#include "nvme-cmds.h"
42#include "nvme-print.h"
43#include "nvme.h"
44#include "plugin.h"
45
46#define CREATE_CMD
47
48#include "seagate-nvme.h"
49#include "seagate-diag.h"
50
51
52/***************************************
53 * Command for "log-pages-supp"
54 ***************************************/
55static char *log_pages_supp_print(__u32 pageID)
56{
57 switch (pageID) {
58 case 0x01:
59 return "ERROR_INFORMATION";
60 case 0x02:
61 return "SMART_INFORMATION";
62 case 0x03:
63 return "FW_SLOT_INFORMATION";
64 case 0x04:
65 return "CHANGED_NAMESPACE_LIST";
66 case 0x05:
67 return "COMMANDS_SUPPORTED_AND_EFFECTS";
68 case 0x06:
69 return "DEVICE_SELF_TEST";
70 case 0x07:
71 return "TELEMETRY_HOST_INITIATED";
72 case 0x08:
73 return "TELEMETRY_CONTROLLER_INITIATED";
74 case 0xC0:
75 return "VS_MEDIA_SMART_LOG";
76 case 0xC1:
77 return "VS_DEBUG_LOG1";
78 case 0xC2:
79 return "VS_SEC_ERROR_LOG_PAGE";
80 case 0xC3:
81 return "VS_LIFE_TIME_DRIVE_HISTORY";
82 case 0xC4:
83 return "VS_EXTENDED_SMART_INFO";
84 case 0xC5:
85 return "VS_LIST_SUPPORTED_LOG_PAGE";
86 case 0xC6:
87 return "VS_POWER_MONITOR_LOG_PAGE";
88 case 0xC7:
89 return "VS_CRITICAL_EVENT_LOG_PAGE";
90 case 0xC8:
91 return "VS_RECENT_DRIVE_HISTORY";
92 case 0xC9:
93 return "VS_SEC_ERROR_LOG_PAGE";
94 case 0xCA:
95 return "VS_LIFE_TIME_DRIVE_HISTORY";
96 case 0xCB:
97 return "VS_PCIE_ERROR_LOG_PAGE";
98 case 0xCF:
99 return "DRAM Supercap SMART Attributes";
100 case 0xD6:
101 return "VS_OEM2_WORK_LOAD";
102 case 0xD7:
103 return "VS_OEM2_FW_SECURITY";
104 case 0xD8:
105 return "VS_OEM2_REVISION";
106 default:
107 return "UNKNOWN";
108 }
109}
110
111static int stx_is_jag_pan(char *devMN)
112{
113 int match_found = 1; /* found = 0, not_found = 1 */
114
115 for (int i = 0; i < STX_NUM_LEGACY_DRV(123); i++) {
116 match_found = strncmp(devMN, stx_jag_pan_mn[i], strlen(stx_jag_pan_mn[i]));
117 if (!match_found)
118 break;
119 }
120
121 return match_found;
122}
123
124
125static void json_log_pages_supp(log_page_map *logPageMap)
126{
127 struct json_object *root;
128 struct json_object *logPages;
129 __u32 i = 0;
130
131 root = json_create_object()json_object_new_object();
132 logPages = json_create_array()json_object_new_array();
133 json_object_add_value_array(root, "supported_log_pages", logPages)json_object_object_add(root, "supported_log_pages", logPages);
134
135 for (i = 0; i < le32_to_cpu(logPageMap->NumLogPages); i++) {
136 struct json_object *lbaf = json_create_object()json_object_new_object();
137
138 json_object_add_value_int(lbaf, "logpage_id",json_object_object_add(lbaf, "logpage_id", json_object_new_int
(le32_to_cpu(logPageMap->LogPageEntry[i].LogPageID)))
139 le32_to_cpu(logPageMap->LogPageEntry[i].LogPageID))json_object_object_add(lbaf, "logpage_id", json_object_new_int
(le32_to_cpu(logPageMap->LogPageEntry[i].LogPageID)))
;
140 json_object_add_value_string(lbaf, "logpage_name",
141 log_pages_supp_print(le32_to_cpu(logPageMap->LogPageEntry[i].LogPageID)));
142
143 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
144 }
145 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
146 json_free_object(root)json_object_put(root);
147}
148
149static int log_pages_supp(int argc, char **argv, struct command *acmd,
150 struct plugin *plugin)
151{
152 int err = 0;
153 __u32 i = 0;
154 log_page_map logPageMap;
155 const char *desc = "Retrieve Seagate Supported Log-Page information for the given device ";
156 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
157 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
158 nvme_print_flags_t flags;
159 int fmt;
160
161 NVME_ARGS(opts)struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
162
163 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
164 if (err)
165 return err;
166
167 err = validate_output_format(nvme_args.output_format, &flags);
168 if (err < 0) {
169 nvme_show_error("Invalid output format")nvme_show_message(1, "Invalid output format");
170 return err;
171 }
172
173 err = nvme_get_log_simple(hdl, 0xc5, &logPageMap, sizeof(logPageMap));
174 if (!err) {
175 if (flags & NORMAL) {
176 printf("Seagate Supported Log-pages count :%d\n",
177 le32_to_cpu(logPageMap.NumLogPages));
178 printf("%-15s %-30s\n", "LogPage-Id", "LogPage-Name");
179
180 for (fmt = 0; fmt < 45; fmt++)
181 printf("-");
182 printf("\n");
183 } else if (flags & JSON)
184 json_log_pages_supp(&logPageMap);
185
186 for (i = 0; i < le32_to_cpu(logPageMap.NumLogPages); i++) {
187 if (flags & NORMAL) {
188 printf("0x%-15X",
189 le32_to_cpu(logPageMap.LogPageEntry[i].LogPageID));
190 printf("%-30s\n",
191 log_pages_supp_print(le32_to_cpu(logPageMap.LogPageEntry[i].LogPageID)));
192 }
193 }
194 }
195
196 if (err > 0)
197 nvme_show_status(err);
198
199 return err;
200}
201
202/* EOF Command for "log-pages-supp" */
203
204/***************************************
205 * Extended-SMART Information
206 ***************************************/
207static char *print_ext_smart_id(__u8 attrId)
208{
209 switch (attrId) {
210 case VS_ATTR_ID_SOFT_READ_ERROR_RATE:
211 return "Soft ECC error count";
212 case VS_ATTR_ID_REALLOCATED_SECTOR_COUNT:
213 return "Bad NAND block count";
214 case VS_ATTR_ID_POWER_ON_HOURS:
215 return "Power On Hours";
216 case VS_ATTR_ID_POWER_FAIL_EVENT_COUNT:
217 return "Power Fail Event Count";
218 case VS_ATTR_ID_DEVICE_POWER_CYCLE_COUNT:
219 return "Device Power Cycle Count";
220 case VS_ATTR_ID_RAW_READ_ERROR_RATE:
221 return "Raw Read Error Count";
222 case VS_ATTR_ID_GROWN_BAD_BLOCK_COUNT:
223 return "Bad NAND block count";
224 case VS_ATTR_ID_END_2_END_CORRECTION_COUNT:
225 return "SSD End to end correction counts";
226 case VS_ATTR_ID_MIN_MAX_WEAR_RANGE_COUNT:
227 return "User data erase counts";
228 case VS_ATTR_ID_REFRESH_COUNT:
229 return "Refresh count";
230 case VS_ATTR_ID_BAD_BLOCK_COUNT_USER:
231 return "User data erase fail count";
232 case VS_ATTR_ID_BAD_BLOCK_COUNT_SYSTEM:
233 return "System area erase fail count";
234 case VS_ATTR_ID_THERMAL_THROTTLING_STATUS:
235 return "Thermal throttling status and count";
236 case VS_ATTR_ID_ALL_PCIE_CORRECTABLE_ERROR_COUNT:
237 return "PCIe Correctable Error count";
238 case VS_ATTR_ID_ALL_PCIE_UNCORRECTABLE_ERROR_COUNT:
239 return "PCIe Uncorrectable Error count";
240 case VS_ATTR_ID_INCOMPLETE_SHUTDOWN_COUNT:
241 return "Incomplete shutdowns";
242 case VS_ATTR_ID_GB_ERASED_LSB:
243 return "LSB of Flash GB erased";
244 case VS_ATTR_ID_GB_ERASED_MSB:
245 return "MSB of Flash GB erased";
246 case VS_ATTR_ID_LIFETIME_DEVSLEEP_EXIT_COUNT:
247 return "LIFETIME_DEV_SLEEP_EXIT_COUNT";
248 case VS_ATTR_ID_LIFETIME_ENTERING_PS4_COUNT:
249 return "LIFETIME_ENTERING_PS4_COUNT";
250 case VS_ATTR_ID_LIFETIME_ENTERING_PS3_COUNT:
251 return "LIFETIME_ENTERING_PS3_COUNT";
252 case VS_ATTR_ID_RETIRED_BLOCK_COUNT:
253 return "Retired block count";
254 case VS_ATTR_ID_PROGRAM_FAILURE_COUNT:
255 return "Program fail count";
256 case VS_ATTR_ID_ERASE_FAIL_COUNT:
257 return "Erase Fail Count";
258 case VS_ATTR_ID_AVG_ERASE_COUNT:
259 return "System data % used";
260 case VS_ATTR_ID_UNEXPECTED_POWER_LOSS_COUNT:
261 return "Unexpected power loss count";
262 case VS_ATTR_ID_WEAR_RANGE_DELTA:
263 return "Wear range delta";
264 case VS_ATTR_ID_SATA_INTERFACE_DOWNSHIFT_COUNT:
265 return "PCIE_INTF_DOWNSHIFT_COUNT";
266 case VS_ATTR_ID_END_TO_END_CRC_ERROR_COUNT:
267 return "E2E_CRC_ERROR_COUNT";
268 case VS_ATTR_ID_UNCORRECTABLE_READ_ERRORS:
269 return "Uncorrectable Read Error Count";
270 case VS_ATTR_ID_MAX_LIFE_TEMPERATURE:
271 return "Max lifetime temperature";
272 case VS_ATTR_ID_RAISE_ECC_CORRECTABLE_ERROR_COUNT:
273 return "RAIS_ECC_CORRECT_ERR_COUNT";
274 case VS_ATTR_ID_UNCORRECTABLE_RAISE_ERRORS:
275 return "Uncorrectable RAISE error count";
276 case VS_ATTR_ID_DRIVE_LIFE_PROTECTION_STATUS:
277 return "DRIVE_LIFE_PROTECTION_STATUS";
278 case VS_ATTR_ID_REMAINING_SSD_LIFE:
279 return "Remaining SSD life";
280 case VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB:
281 return "LSB of Physical (NAND) bytes written";
282 case VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_MSB:
283 return "MSB of Physical (NAND) bytes written";
284 case VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB:
285 return "LSB of Physical (HOST) bytes written";
286 case VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_MSB:
287 return "MSB of Physical (HOST) bytes written";
288 case VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB:
289 return "LSB of Physical (NAND) bytes read";
290 case VS_ATTR_ID_LIFETIME_READS_TO_HOST_MSB:
291 return "MSB of Physical (NAND) bytes read";
292 case VS_ATTR_ID_FREE_SPACE:
293 return "Free Space";
294 case VS_ATTR_ID_TRIM_COUNT_LSB:
295 return "LSB of Trim count";
296 case VS_ATTR_ID_TRIM_COUNT_MSB:
297 return "MSB of Trim count";
298 case VS_ATTR_ID_OP_PERCENTAGE:
299 return "OP percentage";
300 case VS_ATTR_ID_MAX_SOC_LIFE_TEMPERATURE:
301 return "Max lifetime SOC temperature";
302 default:
303 return "Un-Known";
304 }
305}
306
307static __u64 smart_attribute_vs(__u16 verNo, SmartVendorSpecific attr)
308{
309 __u64 val = 0;
310 vendor_smart_attribute_data *attrVendor;
311
312 /**
313 * These are all Vendor A specific attributes.
314 */
315 if (verNo >= EXTENDED_SMART_VERSION_VENDOR1) {
316 attrVendor = (vendor_smart_attribute_data *)&attr;
317 memcpy(&val, &(attrVendor->LSDword), sizeof(val));
318 return val;
319 } else
320 return le32_to_cpu(attr.Raw0_3);
321}
322
323static void print_smart_log(__u16 verNo, SmartVendorSpecific attr, int lastAttr)
324{
325 static __u64 lsbGbErased = 0, msbGbErased = 0, lsbLifWrtToFlash = 0, msbLifWrtToFlash = 0,
326 lsbLifWrtFrmHost = 0, msbLifWrtFrmHost = 0, lsbLifRdToHost = 0, msbLifRdToHost = 0, lsbTrimCnt = 0, msbTrimCnt = 0;
327 char buf[40] = {0};
328 char strBuf[35] = {0};
329 int hideAttr = 0;
330
331 if (attr.AttributeNumber == VS_ATTR_ID_GB_ERASED_LSB) {
332 lsbGbErased = smart_attribute_vs(verNo, attr);
333 hideAttr = 1;
334 }
335
336 if (attr.AttributeNumber == VS_ATTR_ID_GB_ERASED_MSB) {
337 msbGbErased = smart_attribute_vs(verNo, attr);
338 hideAttr = 1;
339 }
340
341 if (attr.AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB) {
342 lsbLifWrtToFlash = smart_attribute_vs(verNo, attr);
343 hideAttr = 1;
344 }
345
346 if (attr.AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_MSB) {
347 msbLifWrtToFlash = smart_attribute_vs(verNo, attr);
348 hideAttr = 1;
349 }
350
351 if (attr.AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB) {
352 lsbLifWrtFrmHost = smart_attribute_vs(verNo, attr);
353 hideAttr = 1;
354 }
355
356 if (attr.AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_MSB) {
357 msbLifWrtFrmHost = smart_attribute_vs(verNo, attr);
358 hideAttr = 1;
359 }
360
361 if (attr.AttributeNumber == VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB) {
362 lsbLifRdToHost = smart_attribute_vs(verNo, attr);
363 hideAttr = 1;
364 }
365
366 if (attr.AttributeNumber == VS_ATTR_ID_LIFETIME_READS_TO_HOST_MSB) {
367 msbLifRdToHost = smart_attribute_vs(verNo, attr);
368 hideAttr = 1;
369 }
370
371 if (attr.AttributeNumber == VS_ATTR_ID_TRIM_COUNT_LSB) {
372 lsbTrimCnt = smart_attribute_vs(verNo, attr);
373 hideAttr = 1;
374 }
375
376 if (attr.AttributeNumber == VS_ATTR_ID_TRIM_COUNT_MSB) {
377 msbTrimCnt = smart_attribute_vs(verNo, attr);
378 hideAttr = 1;
379 }
380
381 if ((attr.AttributeNumber) && (hideAttr != 1)) {
382 printf("%-40s", print_ext_smart_id(attr.AttributeNumber));
383 printf("%-15d", attr.AttributeNumber);
384 printf(" 0x%016"PRIx64"l" "x""\n", (uint64_t)smart_attribute_vs(verNo, attr));
385 }
386
387 if (lastAttr == 1) {
388 sprintf(strBuf, "%s", (print_ext_smart_id(VS_ATTR_ID_GB_ERASED_LSB) + 7));
389 printf("%-40s", strBuf);
390
391 printf("%-15d", VS_ATTR_ID_GB_ERASED_MSB << 8 | VS_ATTR_ID_GB_ERASED_LSB);
392
393 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbGbErased, (uint64_t)lsbGbErased);
394 printf(" %s\n", buf);
395
396 sprintf(strBuf, "%s", (print_ext_smart_id(VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB) + 7));
397 printf("%-40s", strBuf);
398
399 printf("%-15d", VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_MSB << 8 | VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB);
400
401 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbLifWrtToFlash, (uint64_t)lsbLifWrtToFlash);
402 printf(" %s\n", buf);
403
404 sprintf(strBuf, "%s", (print_ext_smart_id(VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB) + 7));
405 printf("%-40s", strBuf);
406
407 printf("%-15d", VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_MSB << 8 | VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB);
408
409 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbLifWrtFrmHost, (uint64_t)lsbLifWrtFrmHost);
410 printf(" %s\n", buf);
411
412 sprintf(strBuf, "%s", (print_ext_smart_id(VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB) + 7));
413 printf("%-40s", strBuf);
414
415 printf("%-15d", VS_ATTR_ID_LIFETIME_READS_TO_HOST_MSB << 8 | VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB);
416
417 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbLifRdToHost, (uint64_t)lsbLifRdToHost);
418 printf(" %s\n", buf);
419
420 sprintf(strBuf, "%s", (print_ext_smart_id(VS_ATTR_ID_TRIM_COUNT_LSB) + 7));
421 printf("%-40s", strBuf);
422
423 printf("%-15d", VS_ATTR_ID_TRIM_COUNT_MSB << 8 | VS_ATTR_ID_TRIM_COUNT_LSB);
424
425 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbTrimCnt, (uint64_t)lsbTrimCnt);
426 printf(" %s\n", buf);
427
428 }
429}
430
431static void json_print_smart_log(struct json_object *root, EXTENDED_SMART_INFO_T *ExtdSMARTInfo)
432{
433 struct json_object *lbafs;
434 int index = 0;
435
436 static __u64 lsbGbErased = 0, msbGbErased = 0, lsbLifWrtToFlash = 0, msbLifWrtToFlash = 0,
437 lsbLifWrtFrmHost = 0, msbLifWrtFrmHost = 0, lsbLifRdToHost = 0, msbLifRdToHost = 0, lsbTrimCnt = 0, msbTrimCnt = 0;
438 char buf[40] = {0};
439
440 lbafs = json_create_array()json_object_new_array();
441 json_object_add_value_array(root, "Extended-SMART-Attributes", lbafs)json_object_object_add(root, "Extended-SMART-Attributes", lbafs
)
;
442
443 for (index = 0; index < NUMBER_EXTENDED_SMART_ATTRIBUTES42; index++) {
444 struct json_object *lbaf = json_create_object()json_object_new_object();
445
446 if (ExtdSMARTInfo->vendorData[index].AttributeNumber) {
447 json_object_add_value_string(lbaf, "attribute_name", print_ext_smart_id(ExtdSMARTInfo->vendorData[index].AttributeNumber));
448 json_object_add_value_int(lbaf, "attribute_id", ExtdSMARTInfo->vendorData[index].AttributeNumber)json_object_object_add(lbaf, "attribute_id", json_object_new_int
(ExtdSMARTInfo->vendorData[index].AttributeNumber))
;
449 json_object_add_value_int(lbaf, "attribute_value", smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->
vendorData[index])))
;
450 json_array_add_value_object(lbafs, lbaf)json_object_array_add(lbafs, lbaf);
451
452 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_GB_ERASED_LSB)
453 lsbGbErased = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
454
455 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_GB_ERASED_MSB)
456 msbGbErased = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
457
458 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB)
459 lsbLifWrtToFlash = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
460
461 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_MSB)
462 msbLifWrtToFlash = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
463
464 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB)
465 lsbLifWrtFrmHost = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
466
467 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_MSB)
468 msbLifWrtFrmHost = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
469
470 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB)
471 lsbLifRdToHost = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
472
473 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_LIFETIME_READS_TO_HOST_MSB)
474 msbLifRdToHost = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
475
476 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_TRIM_COUNT_LSB)
477 lsbTrimCnt = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
478
479 if (ExtdSMARTInfo->vendorData[index].AttributeNumber == VS_ATTR_ID_TRIM_COUNT_MSB)
480 msbTrimCnt = smart_attribute_vs(ExtdSMARTInfo->Version, ExtdSMARTInfo->vendorData[index]);
481 }
482 }
483
484 struct json_object *lbaf = json_create_object()json_object_new_object();
485
486 json_object_add_value_string(lbaf, "attribute_name", (print_ext_smart_id(VS_ATTR_ID_GB_ERASED_LSB) + 7));
487
488 json_object_add_value_int(lbaf, "attribute_id", VS_ATTR_ID_GB_ERASED_MSB << 8 | VS_ATTR_ID_GB_ERASED_LSB)json_object_object_add(lbaf, "attribute_id", json_object_new_int
(VS_ATTR_ID_GB_ERASED_MSB << 8 | VS_ATTR_ID_GB_ERASED_LSB
))
;
489
490 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbGbErased, (uint64_t)lsbGbErased);
491 json_object_add_value_string(lbaf, "attribute_value", buf);
492 json_array_add_value_object(lbafs, lbaf)json_object_array_add(lbafs, lbaf);
493
494
495 lbaf = json_create_object()json_object_new_object();
496
497 json_object_add_value_string(lbaf, "attribute_name", (print_ext_smart_id(VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB) + 7));
498
499 json_object_add_value_int(lbaf, "attribute_id", VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_MSB << 8 | VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB)json_object_object_add(lbaf, "attribute_id", json_object_new_int
(VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_MSB << 8 | VS_ATTR_ID_LIFETIME_WRITES_TO_FLASH_LSB
))
;
500
501 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbLifWrtToFlash, (uint64_t)lsbLifWrtToFlash);
502 json_object_add_value_string(lbaf, "attribute_value", buf);
503 json_array_add_value_object(lbafs, lbaf)json_object_array_add(lbafs, lbaf);
504
505
506 lbaf = json_create_object()json_object_new_object();
507
508 json_object_add_value_string(lbaf, "attribute_name", (print_ext_smart_id(VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB) + 7));
509
510 json_object_add_value_int(lbaf, "attribute_id", VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_MSB << 8 | VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB)json_object_object_add(lbaf, "attribute_id", json_object_new_int
(VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_MSB << 8 | VS_ATTR_ID_LIFETIME_WRITES_FROM_HOST_LSB
))
;
511
512 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbLifWrtFrmHost, (uint64_t)lsbLifWrtFrmHost);
513 json_object_add_value_string(lbaf, "attribute_value", buf);
514 json_array_add_value_object(lbafs, lbaf)json_object_array_add(lbafs, lbaf);
515
516
517 lbaf = json_create_object()json_object_new_object();
518
519 json_object_add_value_string(lbaf, "attribute_name", (print_ext_smart_id(VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB) + 7));
520
521 json_object_add_value_int(lbaf, "attribute_id", VS_ATTR_ID_LIFETIME_READS_TO_HOST_MSB << 8 | VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB)json_object_object_add(lbaf, "attribute_id", json_object_new_int
(VS_ATTR_ID_LIFETIME_READS_TO_HOST_MSB << 8 | VS_ATTR_ID_LIFETIME_READS_TO_HOST_LSB
))
;
522
523 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbLifRdToHost, (uint64_t)lsbLifRdToHost);
524 json_object_add_value_string(lbaf, "attribute_value", buf);
525 json_array_add_value_object(lbafs, lbaf)json_object_array_add(lbafs, lbaf);
526
527
528 lbaf = json_create_object()json_object_new_object();
529
530 json_object_add_value_string(lbaf, "attribute_name", (print_ext_smart_id(VS_ATTR_ID_TRIM_COUNT_LSB) + 7));
531
532 json_object_add_value_int(lbaf, "attribute_id", VS_ATTR_ID_TRIM_COUNT_MSB << 8 | VS_ATTR_ID_TRIM_COUNT_LSB)json_object_object_add(lbaf, "attribute_id", json_object_new_int
(VS_ATTR_ID_TRIM_COUNT_MSB << 8 | VS_ATTR_ID_TRIM_COUNT_LSB
))
;
533
534 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", (uint64_t)msbTrimCnt, (uint64_t)lsbTrimCnt);
535 json_object_add_value_string(lbaf, "attribute_value", buf);
536 json_array_add_value_object(lbafs, lbaf)json_object_array_add(lbafs, lbaf);
537}
538
539static void print_smart_log_CF(vendor_log_page_CF *pLogPageCF)
540{
541 __u64 currentTemp, maxTemp;
542
543 printf("\n\nSeagate DRAM Supercap SMART Attributes :\n");
544 printf("%-39s %-19s\n", "Description", "Supercap Attributes");
545
546 printf("%-40s", "Super-cap current temperature");
547 currentTemp = pLogPageCF->AttrCF.SuperCapCurrentTemperature;
548 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(currentTemp));
549
550 maxTemp = pLogPageCF->AttrCF.SuperCapMaximumTemperature;
551 printf("%-40s", "Super-cap maximum temperature");
552 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(maxTemp));
553
554 printf("%-40s", "Super-cap status");
555 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageCF->AttrCF.SuperCapStatus));
556
557 printf("%-40s", "Data units read to DRAM namespace");
558 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageCF->AttrCF.DataUnitsReadToDramNamespace.MS__u64),
559 le64_to_cpu(pLogPageCF->AttrCF.DataUnitsReadToDramNamespace.LS__u64));
560
561 printf("%-40s", "Data units written to DRAM namespace");
562 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageCF->AttrCF.DataUnitsWrittenToDramNamespace.MS__u64),
563 le64_to_cpu(pLogPageCF->AttrCF.DataUnitsWrittenToDramNamespace.LS__u64));
564
565 printf("%-40s", "DRAM correctable error count");
566 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageCF->AttrCF.DramCorrectableErrorCount));
567
568 printf("%-40s", "DRAM uncorrectable error count");
569 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageCF->AttrCF.DramUncorrectableErrorCount));
570}
571
572static void json_print_smart_log_CF(struct json_object *root, vendor_log_page_CF *pLogPageCF)
573{
574 struct json_object *logPages;
575 unsigned int currentTemp, maxTemp;
576 char buf[40];
577
578 logPages = json_create_array()json_object_new_array();
579 json_object_add_value_array(root, "DRAM Supercap SMART Attributes", logPages)json_object_object_add(root, "DRAM Supercap SMART Attributes"
, logPages)
;
580 struct json_object *lbaf = json_create_object()json_object_new_object();
581
582 currentTemp = pLogPageCF->AttrCF.SuperCapCurrentTemperature;
583 json_object_add_value_string(lbaf, "attribute_name", "Super-cap current temperature");
584 json_object_add_value_int(lbaf, "attribute_value", currentTemp)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(currentTemp))
;
585 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
586
587 lbaf = json_create_object()json_object_new_object();
588 maxTemp = pLogPageCF->AttrCF.SuperCapMaximumTemperature;
589 json_object_add_value_string(lbaf, "attribute_name", "Super-cap maximum temperature");
590 json_object_add_value_int(lbaf, "attribute_value", maxTemp)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(maxTemp))
;
591 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
592
593 lbaf = json_create_object()json_object_new_object();
594 json_object_add_value_string(lbaf, "attribute_name", "Super-cap status");
595 json_object_add_value_int(lbaf, "attribute_value", pLogPageCF->AttrCF.SuperCapStatus)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(pLogPageCF->AttrCF.SuperCapStatus))
;
596 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
597
598 lbaf = json_create_object()json_object_new_object();
599 json_object_add_value_string(lbaf, "attribute_name", "Data units read to DRAM namespace");
600 memset(buf, 0, sizeof(buf));
601 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageCF->AttrCF.DataUnitsReadToDramNamespace.MS__u64),
602 le64_to_cpu(pLogPageCF->AttrCF.DataUnitsReadToDramNamespace.LS__u64));
603 json_object_add_value_string(lbaf, "attribute_value", buf);
604 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
605
606 lbaf = json_create_object()json_object_new_object();
607 json_object_add_value_string(lbaf, "attribute_name", "Data units written to DRAM namespace");
608 memset(buf, 0, sizeof(buf));
609 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageCF->AttrCF.DataUnitsWrittenToDramNamespace.MS__u64),
610 le64_to_cpu(pLogPageCF->AttrCF.DataUnitsWrittenToDramNamespace.LS__u64));
611 json_object_add_value_string(lbaf, "attribute_value", buf);
612 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
613
614 lbaf = json_create_object()json_object_new_object();
615 json_object_add_value_string(lbaf, "attribute_name", "DRAM correctable error count");
616 json_object_add_value_int(lbaf, "attribute_value", pLogPageCF->AttrCF.DramCorrectableErrorCount)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(pLogPageCF->AttrCF.DramCorrectableErrorCount))
;
617 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
618
619 lbaf = json_create_object()json_object_new_object();
620 json_object_add_value_string(lbaf, "attribute_name", "DRAM uncorrectable error count");
621 json_object_add_value_int(lbaf, "attribute_value", pLogPageCF->AttrCF.DramUncorrectableErrorCount)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(pLogPageCF->AttrCF.DramUncorrectableErrorCount))
;
622 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
623}
624
625
626static void print_stx_smart_log_C0(STX_EXT_SMART_LOG_PAGE_C0 *pLogPageC0)
627{
628 printf("\n\nSeagate SMART Health Attributes :\n");
629 printf("%-39s %-19s\n", "Description", "Health Attributes");
630
631 printf("%-40s", "Physical Media Units Written");
632 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->phyMediaUnitsWrt.MS__u64),
633 le64_to_cpu(pLogPageC0->phyMediaUnitsWrt.LS__u64));
634
635 printf("%-40s", "Physical Media Units Read");
636 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->phyMediaUnitsRd.MS__u64),
637 le64_to_cpu(pLogPageC0->phyMediaUnitsRd.LS__u64));
638
639 printf("%-40s", "Bad User NAND Blocks");
640 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->badUsrNandBlocks));
641
642 printf("%-40s", "Bad System NAND Blocks");
643 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->badSysNandBlocks));
644
645 printf("%-40s", "XOR Recovery Count");
646 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->xorRecoveryCnt));
647
648 printf("%-40s", "Uncorrectable Read Error Count");
649 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->ucRdEc));
650
651 printf("%-40s", "Soft ECC Error Count");
652 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->softEccEc));
653
654 printf("%-40s", "End to End Correction Counts");
655 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->etoeCrrCnt));
656
657 printf("%-40s", "System Data Used in Parcent");
658 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->sysDataUsed));
659
660 printf("%-40s", "Refresh Counts");
661 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->refreshCount));
662
663 printf("%-40s", "User Data Erase Counts");
664 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->usrDataEraseCnt));
665
666 printf("%-40s", "Thermal Throttling Status and Count");
667 printf(" 0x%04x\n", le16_to_cpu(pLogPageC0->thermalThrottling));
668
669 printf("%-40s", "DSSD Specification Version");
670 printf(" %d.%d.%d.%d\n", pLogPageC0->dssdSpecVerMajor,
671 le16_to_cpu(pLogPageC0->dssdSpecVerMinor),
672 le16_to_cpu(pLogPageC0->dssdSpecVerPoint),
673 pLogPageC0->dssdSpecVerErrata);
674
675 printf("%-40s", "PCIe Correctable Error Count");
676 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->pcieCorrEc));
677
678 printf("%-40s", "Incomplete Shutdowns");
679 printf(" 0x%08x\n", le32_to_cpu(pLogPageC0->incompleteShutdowns));
680
681 printf("%-40s", "Free Blocks in Percent");
682 printf(" %d\n", pLogPageC0->freeBlocks);
683
684 printf("%-40s", "Capacitor Health");
685 printf(" 0x%04x\n", le16_to_cpu(pLogPageC0->capHealth));
686
687 printf("%-40s", "NVMe Errata Version");
688 printf(" %c\n", pLogPageC0->nvmeErrataVer);
689
690 printf("%-40s", "Unaligned IO");
691 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->unalignedIO));
692
693 printf("%-40s", "Security Version Number");
694 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->secVerNum));
695
696 printf("%-40s", "Total Namespace Utilization");
697 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->totalNUSE));
698
699 printf("%-40s", "PLP Start Count");
700 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->plpStartCnt.MS__u64),
701 le64_to_cpu(pLogPageC0->plpStartCnt.LS__u64));
702
703 printf("%-40s", "Endurance Estimate");
704 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->enduranceEstimate.MS__u64),
705 le64_to_cpu(pLogPageC0->enduranceEstimate.LS__u64));
706
707 printf("%-40s", "PCIe Link Retraining Count");
708 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->pcieLinkRetCnt));
709
710 printf("%-40s", "Power State Change Count");
711 printf(" 0x%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->powStateChangeCnt));
712
713 printf("%-40s", "Log Page Version");
714 printf(" 0x%04x\n", le16_to_cpu(pLogPageC0->logPageVer));
715
716 printf("%-40s", "Log Page GUID");
717 printf(" 0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""\n", le64_to_cpu(pLogPageC0->logPageGUID.MS__u64),
718 le64_to_cpu(pLogPageC0->logPageGUID.LS__u64));
719}
720
721static void json_print_stx_smart_log_C0(struct json_object *root, STX_EXT_SMART_LOG_PAGE_C0 *pLogPageC0)
722{
723 struct json_object *logPages;
724 char buf[40];
725
726 logPages = json_create_array()json_object_new_array();
727 json_object_add_value_array(root, "Seagate SMART Health Attributes", logPages)json_object_object_add(root, "Seagate SMART Health Attributes"
, logPages)
;
728
729 struct json_object *lbaf = json_create_object()json_object_new_object();
730
731 json_object_add_value_string(lbaf, "attribute_name", "Physical Media Units Written");
732 memset(buf, 0, sizeof(buf));
733 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageC0->phyMediaUnitsWrt.MS__u64),
734 le64_to_cpu(pLogPageC0->phyMediaUnitsWrt.LS__u64));
735 json_object_add_value_string(lbaf, "attribute_value", buf);
736 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
737
738
739 lbaf = json_create_object()json_object_new_object();
740 json_object_add_value_string(lbaf, "attribute_name", "Physical Media Units Read");
741 memset(buf, 0, sizeof(buf));
742 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageC0->phyMediaUnitsRd.MS__u64),
743 le64_to_cpu(pLogPageC0->phyMediaUnitsRd.LS__u64));
744 json_object_add_value_string(lbaf, "attribute_value", buf);
745 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
746
747 lbaf = json_create_object()json_object_new_object();
748 json_object_add_value_string(lbaf, "attribute_name", "Bad User NAND Blocks");
749 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->badUsrNandBlocks))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->badUsrNandBlocks)))
;
750 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
751
752 lbaf = json_create_object()json_object_new_object();
753 json_object_add_value_string(lbaf, "attribute_name", "Bad System NAND Blocks");
754 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->badSysNandBlocks))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->badSysNandBlocks)))
;
755 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
756
757 lbaf = json_create_object()json_object_new_object();
758 json_object_add_value_string(lbaf, "attribute_name", "XOR Recovery Count");
759 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->xorRecoveryCnt))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->xorRecoveryCnt)))
;
760 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
761
762 lbaf = json_create_object()json_object_new_object();
763 json_object_add_value_string(lbaf, "attribute_name", "Uncorrectable Read Error Count");
764 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->ucRdEc))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->ucRdEc)))
;
765 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
766
767 lbaf = json_create_object()json_object_new_object();
768 json_object_add_value_string(lbaf, "attribute_name", "Soft ECC Error Count");
769 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->softEccEc))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->softEccEc)))
;
770 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
771
772 lbaf = json_create_object()json_object_new_object();
773 json_object_add_value_string(lbaf, "attribute_name", "End to End Correction Counts");
774 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->etoeCrrCnt))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->etoeCrrCnt)))
;
775 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
776
777 lbaf = json_create_object()json_object_new_object();
778 json_object_add_value_string(lbaf, "attribute_name", "System Data Used in Parcent");
779 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->sysDataUsed))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->sysDataUsed)))
;
780 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
781
782 lbaf = json_create_object()json_object_new_object();
783 json_object_add_value_string(lbaf, "attribute_name", "Refresh Counts");
784 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->refreshCount))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->refreshCount)))
;
785 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
786
787 lbaf = json_create_object()json_object_new_object();
788 json_object_add_value_string(lbaf, "attribute_name", "User Data Erase Counts");
789 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->usrDataEraseCnt))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->usrDataEraseCnt)))
;
790 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
791
792 lbaf = json_create_object()json_object_new_object();
793 json_object_add_value_string(lbaf, "attribute_name", "Thermal Throttling Status and Count");
794 json_object_add_value_int(lbaf, "attribute_value", le16_to_cpu(pLogPageC0->thermalThrottling))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le16_to_cpu(pLogPageC0->thermalThrottling)))
;
795 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
796
797 lbaf = json_create_object()json_object_new_object();
798 json_object_add_value_string(lbaf, "attribute_name", "DSSD Specification Version");
799 memset(buf, 0, sizeof(buf));
800 sprintf(buf, "%d.%d.%d.%d", pLogPageC0->dssdSpecVerMajor,
801 le16_to_cpu(pLogPageC0->dssdSpecVerMinor),
802 le16_to_cpu(pLogPageC0->dssdSpecVerPoint),
803 pLogPageC0->dssdSpecVerErrata);
804 json_object_add_value_string(lbaf, "attribute_value", buf);
805 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
806
807 lbaf = json_create_object()json_object_new_object();
808 json_object_add_value_string(lbaf, "attribute_name", "PCIe Correctable Error Count");
809 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->pcieCorrEc))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->pcieCorrEc)))
;
810 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
811
812 lbaf = json_create_object()json_object_new_object();
813 json_object_add_value_string(lbaf, "attribute_name", "Incomplete Shutdowns");
814 json_object_add_value_int(lbaf, "attribute_value", le32_to_cpu(pLogPageC0->incompleteShutdowns))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le32_to_cpu(pLogPageC0->incompleteShutdowns)))
;
815 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
816
817 lbaf = json_create_object()json_object_new_object();
818 json_object_add_value_string(lbaf, "attribute_name", "Free Blocks in Percent");
819 json_object_add_value_int(lbaf, "attribute_value", pLogPageC0->freeBlocks)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(pLogPageC0->freeBlocks))
;
820 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
821
822 lbaf = json_create_object()json_object_new_object();
823 json_object_add_value_string(lbaf, "attribute_name", "Capacitor Health");
824 json_object_add_value_int(lbaf, "attribute_value", le16_to_cpu(pLogPageC0->capHealth))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le16_to_cpu(pLogPageC0->capHealth)))
;
825 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
826
827 lbaf = json_create_object()json_object_new_object();
828 json_object_add_value_string(lbaf, "attribute_name", "NVMe Errata Version");
829 json_object_add_value_int(lbaf, "attribute_value", pLogPageC0->nvmeErrataVer)json_object_object_add(lbaf, "attribute_value", json_object_new_int
(pLogPageC0->nvmeErrataVer))
;
830 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
831
832 lbaf = json_create_object()json_object_new_object();
833 json_object_add_value_string(lbaf, "attribute_name", "Unaligned IO");
834 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->unalignedIO))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->unalignedIO)))
;
835 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
836
837 lbaf = json_create_object()json_object_new_object();
838 json_object_add_value_string(lbaf, "attribute_name", "Security Version Number");
839 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->secVerNum))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->secVerNum)))
;
840 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
841
842 lbaf = json_create_object()json_object_new_object();
843 json_object_add_value_string(lbaf, "attribute_name", "Total Namespace Utilization");
844 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->totalNUSE))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->totalNUSE)))
;
845 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
846
847 lbaf = json_create_object()json_object_new_object();
848 json_object_add_value_string(lbaf, "attribute_name", "PLP Start Count");
849 memset(buf, 0, sizeof(buf));
850 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageC0->plpStartCnt.MS__u64),
851 le64_to_cpu(pLogPageC0->plpStartCnt.LS__u64));
852 json_object_add_value_string(lbaf, "attribute_value", buf);
853 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
854
855 lbaf = json_create_object()json_object_new_object();
856 json_object_add_value_string(lbaf, "attribute_name", "Endurance Estimate");
857 memset(buf, 0, sizeof(buf));
858 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageC0->enduranceEstimate.MS__u64),
859 le64_to_cpu(pLogPageC0->enduranceEstimate.LS__u64));
860 json_object_add_value_string(lbaf, "attribute_value", buf);
861 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
862
863 lbaf = json_create_object()json_object_new_object();
864 json_object_add_value_string(lbaf, "attribute_name", "PCIe Link Retraining Count");
865 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->pcieLinkRetCnt))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->pcieLinkRetCnt)))
;
866 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
867
868 lbaf = json_create_object()json_object_new_object();
869 json_object_add_value_string(lbaf, "attribute_name", "Power State Change Count");
870 json_object_add_value_int(lbaf, "attribute_value", le64_to_cpu(pLogPageC0->powStateChangeCnt))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le64_to_cpu(pLogPageC0->powStateChangeCnt)))
;
871 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
872
873 lbaf = json_create_object()json_object_new_object();
874 json_object_add_value_string(lbaf, "attribute_name", "Log Page Version");
875 json_object_add_value_int(lbaf, "attribute_value", le16_to_cpu(pLogPageC0->logPageVer))json_object_object_add(lbaf, "attribute_value", json_object_new_int
(le16_to_cpu(pLogPageC0->logPageVer)))
;
876 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
877
878 lbaf = json_create_object()json_object_new_object();
879 json_object_add_value_string(lbaf, "attribute_name", "Log Page GUID");
880 memset(buf, 0, sizeof(buf));
881 sprintf(buf, "0x%016"PRIx64"l" "x""%016"PRIx64"l" "x""", le64_to_cpu(pLogPageC0->logPageGUID.MS__u64),
882 le64_to_cpu(pLogPageC0->logPageGUID.LS__u64));
883 json_object_add_value_string(lbaf, "attribute_value", buf);
884 json_array_add_value_object(logPages, lbaf)json_object_array_add(logPages, lbaf);
885}
886
887static int vs_smart_log(int argc, char **argv, struct command *acmd, struct plugin *plugin)
888{
889 struct nvme_id_ctrl ctrl;
890 char modelNo[40];
891 STX_EXT_SMART_LOG_PAGE_C0 ehExtSmart;
892 EXTENDED_SMART_INFO_T ExtdSMARTInfo;
893 vendor_log_page_CF logPageCF;
894 struct json_object *root = json_create_object()json_object_new_object();
895 struct json_object *lbafs = json_create_array()json_object_new_array();
896 struct json_object *lbafs_ExtSmart, *lbafs_DramSmart;
897
898 const char *desc = "Retrieve the Firmware Activation History for Seagate NVMe drives";
899 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
900 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
901 nvme_print_flags_t flags;
902 int err, index = 0;
903
904 NVME_ARGS(opts)struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
905
906 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
907 if (err) {
908 printf("\nDevice not found\n");
909 return -1;
910 }
911
912 err = validate_output_format(nvme_args.output_format, &flags);
913 if (err < 0) {
914 nvme_show_error("Invalid output format")nvme_show_message(1, "Invalid output format");
915 return err;
916 }
917
918 if (flags & JSON)
919 printf("Seagate Extended SMART Information :\n");
920
921
922 /**
923 * Here we should identify if the drive is a Panthor or Jaguar.
924 * Here we need to extract the model no from ctrl-id abd use it
925 * to determine drive family.
926 */
927
928 err = nvme_identify_ctrl(hdl, &ctrl);
929 if (!err) {
930 memcpy(modelNo, ctrl.mn, sizeof(modelNo));
931 } else {
932 nvme_show_status(err);
933 return err;
934 }
935
936 if (!stx_is_jag_pan(modelNo)) {
937 err = nvme_get_log_simple(hdl, 0xC4, &ExtdSMARTInfo, sizeof(ExtdSMARTInfo));
938 if (!err) {
939 if (flags & NORMAL) {
940 printf("%-39s %-15s %-19s\n", "Description", "Ext-Smart-Id", "Ext-Smart-Value");
941 for (index = 0; index < 80; index++)
942 printf("-");
943 printf("\n");
944 for (index = 0; index < NUMBER_EXTENDED_SMART_ATTRIBUTES42; index++)
945 print_smart_log(ExtdSMARTInfo.Version, ExtdSMARTInfo.vendorData[index], index == (NUMBER_EXTENDED_SMART_ATTRIBUTES42 - 1));
946
947 } else if (flags & JSON){
948 lbafs_ExtSmart = json_create_object()json_object_new_object();
949 json_print_smart_log(lbafs_ExtSmart, &ExtdSMARTInfo);
950
951 json_object_add_value_array(root, "SMART-Attributes", lbafs)json_object_object_add(root, "SMART-Attributes", lbafs);
952 json_array_add_value_object(lbafs, lbafs_ExtSmart)json_object_array_add(lbafs, lbafs_ExtSmart);
953 }
954
955 /**
956 * Next get Log Page 0xCF
957 */
958
959 err = nvme_get_log_simple(hdl, 0xCF, &logPageCF, sizeof(logPageCF));
960 if (!err) {
961 if (flags & NORMAL) {
962 print_smart_log_CF(&logPageCF);
963 } else if (flags & JSON) {
964 lbafs_DramSmart = json_create_object()json_object_new_object();
965 json_print_smart_log_CF(lbafs_DramSmart, &logPageCF);
966 json_array_add_value_object(lbafs, lbafs_DramSmart)json_object_array_add(lbafs, lbafs_DramSmart);
967 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
968 }
969 } else if (flags & JSON) {
970 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
971 json_free_object(root)json_object_put(root);
972 }
973 } else if (err > 0) {
974 nvme_show_status(err);
975 }
976 } else {
977 err = nvme_get_log_simple(hdl, 0xC0, &ehExtSmart, sizeof(ehExtSmart));
978
979 if (!err) {
980 if (flags & NORMAL) {
981 print_stx_smart_log_C0(&ehExtSmart);
982 } else if (flags & JSON){
983 lbafs_ExtSmart = json_create_object()json_object_new_object();
984 json_print_stx_smart_log_C0(lbafs_ExtSmart, &ehExtSmart);
985
986 json_object_add_value_array(root, "SMART-Attributes", lbafs)json_object_object_add(root, "SMART-Attributes", lbafs);
987 json_array_add_value_object(lbafs, lbafs_ExtSmart)json_object_array_add(lbafs, lbafs_ExtSmart);
988
989 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
990 json_free_object(root)json_object_put(root);
991 }
992 }
993
994 if (err > 0)
995 nvme_show_status(err);
996 }
997
998 err = nvme_get_log_simple(hdl, 0xC4,
999 &ExtdSMARTInfo, sizeof(ExtdSMARTInfo));
1000 if (!err) {
1001 if (flags & NORMAL) {
1002 printf("%-39s %-15s %-19s\n", "Description", "Ext-Smart-Id", "Ext-Smart-Value");
1003 for (index = 0; index < 80; index++)
1004 printf("-");
1005 printf("\n");
1006 for (index = 0; index < NUMBER_EXTENDED_SMART_ATTRIBUTES42; index++)
1007 print_smart_log(ExtdSMARTInfo.Version, ExtdSMARTInfo.vendorData[index], index == (NUMBER_EXTENDED_SMART_ATTRIBUTES42 - 1));
1008
1009 } else if (flags & JSON) {
1010 lbafs_ExtSmart = json_create_object()json_object_new_object();
1011 json_print_smart_log(lbafs_ExtSmart, &ExtdSMARTInfo);
1012
1013 json_object_add_value_array(root, "SMART-Attributes", lbafs)json_object_object_add(root, "SMART-Attributes", lbafs);
1014 json_array_add_value_object(lbafs, lbafs_ExtSmart)json_object_array_add(lbafs, lbafs_ExtSmart);
1015 }
1016
1017 /**
1018 * Next get Log Page 0xCF
1019 */
1020
1021 err = nvme_get_log_simple(hdl, 0xCF,
1022 &logPageCF, sizeof(logPageCF));
1023 if (!err) {
1024 if (flags & NORMAL) {
1025 print_smart_log_CF(&logPageCF);
1026 } else if (flags & JSON) {
1027 lbafs_DramSmart = json_create_object()json_object_new_object();
1028 json_print_smart_log_CF(lbafs_DramSmart, &logPageCF);
1029 json_array_add_value_object(lbafs, lbafs_DramSmart)json_object_array_add(lbafs, lbafs_DramSmart);
1030 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
1031 }
1032 } else if (flags & JSON) {
1033 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
1034 }
1035 } else if (err > 0) {
1036 nvme_show_status(err);
1037 }
1038
1039 return err;
1040}
1041
1042/*EOF Extended-SMART Information */
1043
1044/***************************************
1045 * Temperature-Stats information
1046 ***************************************/
1047static void json_temp_stats(__u32 temperature, __u32 PcbTemp, __u32 SocTemp,
1048 __u32 maxTemperature, __u32 MaxSocTemp,
1049 __u32 cf_err, __u32 scCurrentTemp, __u32 scMaxTem)
1050{
1051 struct json_object *root = json_create_object()json_object_new_object();
1052
1053 json_object_add_value_int(root, "Current temperature", temperature)json_object_object_add(root, "Current temperature", json_object_new_int
(temperature))
;
1054 json_object_add_value_int(root, "Current PCB temperature", PcbTemp)json_object_object_add(root, "Current PCB temperature", json_object_new_int
(PcbTemp))
;
1055 json_object_add_value_int(root, "Current SOC temperature", SocTemp)json_object_object_add(root, "Current SOC temperature", json_object_new_int
(SocTemp))
;
1056 json_object_add_value_int(root, "Highest temperature", maxTemperature)json_object_object_add(root, "Highest temperature", json_object_new_int
(maxTemperature))
;
1057 json_object_add_value_int(root, "Max SOC temperature", MaxSocTemp)json_object_object_add(root, "Max SOC temperature", json_object_new_int
(MaxSocTemp))
;
1058 if (!cf_err) {
1059 json_object_add_value_int(root, "SuperCap Current temperature", scCurrentTemp)json_object_object_add(root, "SuperCap Current temperature", json_object_new_int
(scCurrentTemp))
;
1060 json_object_add_value_int(root, "SuperCap Max temperature", scMaxTem)json_object_object_add(root, "SuperCap Max temperature", json_object_new_int
(scMaxTem))
;
1061 }
1062
1063 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
1064}
1065
1066static int temp_stats(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1067{
1068 struct nvme_smart_log smart_log;
1069 EXTENDED_SMART_INFO_T ExtdSMARTInfo;
1070 vendor_log_page_CF logPageCF;
1071
1072 int err, cf_err;
1073 int index;
1074 const char *desc = "Retrieve Seagate Temperature Stats information for the given device ";
1075 nvme_print_flags_t flags;
1076 unsigned int temperature = 0, PcbTemp = 0, SocTemp = 0, scCurrentTemp = 0, scMaxTemp = 0;
1077 unsigned long long maxTemperature = 0, MaxSocTemp = 0;
1078 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1079 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1080
1081 NVME_ARGS(opts)struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
1082
1083 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1084 if (err) {
1085 printf("\nDevice not found\n");
1086 return -1;
1087 }
1088
1089 err = validate_output_format(nvme_args.output_format, &flags);
1090 if (err < 0) {
1091 nvme_show_error("Invalid output format")nvme_show_message(1, "Invalid output format");
1092 return err;
1093 }
1094
1095 if (flags & NORMAL)
1096 printf("Seagate Temperature Stats Information :\n");
1097 /*STEP-1 : Get Current Temperature from SMART */
1098 err = nvme_get_log_smart(hdl, NVME_NSID_ALL, &smart_log);
1099 if (!err) {
1100 temperature = ((smart_log.temperature[1] << 8) | smart_log.temperature[0]);
1101 temperature = temperature ? temperature - 273 : 0;
1102 PcbTemp = le16_to_cpu(smart_log.temp_sensor[0]);
1103 PcbTemp = PcbTemp ? PcbTemp - 273 : 0;
1104 SocTemp = le16_to_cpu(smart_log.temp_sensor[1]);
1105 SocTemp = SocTemp ? SocTemp - 273 : 0;
1106 if (flags & NORMAL) {
1107 printf("%-20s : %u C\n", "Current Temperature", temperature);
1108 printf("%-20s : %u C\n", "Current PCB Temperature", PcbTemp);
1109 printf("%-20s : %u C\n", "Current SOC Temperature", SocTemp);
1110 }
1111 }
1112
1113 /* STEP-2 : Get Max temperature form Ext SMART-id 194 */
1114 err = nvme_get_log_simple(hdl, 0xC4,
1115 &ExtdSMARTInfo, sizeof(ExtdSMARTInfo));
1116 if (!err) {
1117 for (index = 0; index < NUMBER_EXTENDED_SMART_ATTRIBUTES42; index++) {
1118 if (ExtdSMARTInfo.vendorData[index].AttributeNumber == VS_ATTR_ID_MAX_LIFE_TEMPERATURE) {
1119 maxTemperature = smart_attribute_vs(ExtdSMARTInfo.Version, ExtdSMARTInfo.vendorData[index]);
1120 maxTemperature = maxTemperature ? maxTemperature - 273 : 0;
1121 if (flags & NORMAL)
1122 printf("%-20s : %d C\n", "Highest Temperature", (unsigned int)maxTemperature);
1123 }
1124
1125 if (ExtdSMARTInfo.vendorData[index].AttributeNumber == VS_ATTR_ID_MAX_SOC_LIFE_TEMPERATURE) {
1126 MaxSocTemp = smart_attribute_vs(ExtdSMARTInfo.Version, ExtdSMARTInfo.vendorData[index]);
1127 MaxSocTemp = MaxSocTemp ? MaxSocTemp - 273 : 0;
1128 if (flags & NORMAL)
1129 printf("%-20s : %d C\n", "Max SOC Temperature", (unsigned int)MaxSocTemp);
1130 }
1131 }
1132 } else {
1133 if (err > 0)
1134 nvme_show_status(err);
1135 }
1136
1137 cf_err = nvme_get_log_simple(hdl, 0xCF,
1138 &logPageCF, sizeof(ExtdSMARTInfo));
1139
1140 if (!cf_err) {
1141 scCurrentTemp = logPageCF.AttrCF.SuperCapCurrentTemperature;
1142 scCurrentTemp = scCurrentTemp ? scCurrentTemp - 273 : 0;
1143 printf("%-20s : %d C\n", "Super-cap Current Temperature", scCurrentTemp);
1144
1145 scMaxTemp = logPageCF.AttrCF.SuperCapMaximumTemperature;
1146 scMaxTemp = scMaxTemp ? scMaxTemp - 273 : 0;
1147 printf("%-20s : %d C\n", "Super-cap Max Temperature", scMaxTemp);
1148 }
1149
1150 if (flags & JSON)
1151 json_temp_stats(temperature, PcbTemp, SocTemp, maxTemperature, MaxSocTemp, cf_err, scCurrentTemp, scMaxTemp);
1152
1153 return err;
1154}
1155/* EOF Temperature Stats information */
1156
1157/***************************************
1158 * PCIe error-log information
1159 ***************************************/
1160static void print_vs_pcie_error_log(pcie_error_log_page pcieErrorLog)
1161{
1162 __u32 correctPcieEc = pcieErrorLog.BadDllpErrCnt + pcieErrorLog.BadTlpErrCnt +
1163 pcieErrorLog.RcvrErrCnt + pcieErrorLog.ReplayTOErrCnt +
1164 pcieErrorLog.ReplayNumRolloverErrCnt;
1165 __u32 uncorrectPcieEc = pcieErrorLog.FCProtocolErrCnt + pcieErrorLog.DllpProtocolErrCnt +
1166 pcieErrorLog.CmpltnTOErrCnt + pcieErrorLog.RcvrQOverflowErrCnt +
1167 pcieErrorLog.UnexpectedCplTlpErrCnt + pcieErrorLog.CplTlpURErrCnt +
1168 pcieErrorLog.CplTlpCAErrCnt + pcieErrorLog.ReqCAErrCnt +
1169 pcieErrorLog.ReqURErrCnt + pcieErrorLog.EcrcErrCnt +
1170 pcieErrorLog.MalformedTlpErrCnt + pcieErrorLog.CplTlpPoisonedErrCnt +
1171 pcieErrorLog.MemRdTlpPoisonedErrCnt;
1172
1173 printf("%-45s : %u\n", "PCIe Correctable Error Count", correctPcieEc);
1174 printf("%-45s : %u\n", "PCIe Un-Correctable Error Count", uncorrectPcieEc);
1175 printf("%-45s : %u\n", "Unsupported Request Error Status (URES)", pcieErrorLog.ReqURErrCnt);
1176 printf("%-45s : %u\n", "ECRC Error Status (ECRCES)", pcieErrorLog.EcrcErrCnt);
1177 printf("%-45s : %u\n", "Malformed TLP Status (MTS)", pcieErrorLog.MalformedTlpErrCnt);
1178 printf("%-45s : %u\n", "Receiver Overflow Status (ROS)", pcieErrorLog.RcvrQOverflowErrCnt);
1179 printf("%-45s : %u\n", "Unexpected Completion Status(UCS)", pcieErrorLog.UnexpectedCplTlpErrCnt);
1180 printf("%-45s : %u\n", "Completion Timeout Status (CTS)", pcieErrorLog.CmpltnTOErrCnt);
1181 printf("%-45s : %u\n", "Flow Control Protocol Error Status (FCPES)", pcieErrorLog.FCProtocolErrCnt);
1182 printf("%-45s : %u\n", "Poisoned TLP Status (PTS)", pcieErrorLog.MemRdTlpPoisonedErrCnt);
1183 printf("%-45s : %u\n", "Data Link Protocol Error Status(DLPES)", pcieErrorLog.DllpProtocolErrCnt);
1184 printf("%-45s : %u\n", "Replay Timer Timeout Status(RTS)", pcieErrorLog.ReplayTOErrCnt);
1185 printf("%-45s : %u\n", "Replay_NUM Rollover Status(RRS)", pcieErrorLog.ReplayNumRolloverErrCnt);
1186 printf("%-45s : %u\n", "Bad DLLP Status (BDS)", pcieErrorLog.BadDllpErrCnt);
1187 printf("%-45s : %u\n", "Bad TLP Status (BTS)", pcieErrorLog.BadTlpErrCnt);
1188 printf("%-45s : %u\n", "Receiver Error Status (RES)", pcieErrorLog.RcvrErrCnt);
1189 printf("%-45s : %u\n", "Cpl TLP Unsupported Request Error Count", pcieErrorLog.CplTlpURErrCnt);
1190 printf("%-45s : %u\n", "Cpl TLP Completion Abort Error Count", pcieErrorLog.CplTlpCAErrCnt);
1191 printf("%-45s : %u\n", "Cpl TLP Poisoned Error Count", pcieErrorLog.CplTlpPoisonedErrCnt);
1192 printf("%-45s : %u\n", "Request Completion Abort Error Count", pcieErrorLog.ReqCAErrCnt);
1193 printf("%-45s : %s\n", "Advisory Non-Fatal Error Status(ANFES)", "Not Supported");
1194 printf("%-45s : %s\n", "Completer Abort Status (CAS)", "Not Supported");
1195}
1196
1197static void json_vs_pcie_error_log(pcie_error_log_page pcieErrorLog)
1198{
1199 struct json_object *root = json_create_object()json_object_new_object();
1200 __u32 correctPcieEc = pcieErrorLog.BadDllpErrCnt + pcieErrorLog.BadTlpErrCnt +
1201 pcieErrorLog.RcvrErrCnt + pcieErrorLog.ReplayTOErrCnt +
1202 pcieErrorLog.ReplayNumRolloverErrCnt;
1203 __u32 uncorrectPcieEc = pcieErrorLog.FCProtocolErrCnt + pcieErrorLog.DllpProtocolErrCnt +
1204 pcieErrorLog.CmpltnTOErrCnt + pcieErrorLog.RcvrQOverflowErrCnt +
1205 pcieErrorLog.UnexpectedCplTlpErrCnt + pcieErrorLog.CplTlpURErrCnt +
1206 pcieErrorLog.CplTlpCAErrCnt + pcieErrorLog.ReqCAErrCnt +
1207 pcieErrorLog.ReqURErrCnt + pcieErrorLog.EcrcErrCnt +
1208 pcieErrorLog.MalformedTlpErrCnt + pcieErrorLog.CplTlpPoisonedErrCnt +
1209 pcieErrorLog.MemRdTlpPoisonedErrCnt;
1210
1211 json_object_add_value_int(root, "PCIe Correctable Error Count", correctPcieEc)json_object_object_add(root, "PCIe Correctable Error Count", json_object_new_int
(correctPcieEc))
;
1212 json_object_add_value_int(root, "PCIe Un-Correctable Error Count", uncorrectPcieEc)json_object_object_add(root, "PCIe Un-Correctable Error Count"
, json_object_new_int(uncorrectPcieEc))
;
1213 json_object_add_value_int(root, "Unsupported Request Error Status (URES)", pcieErrorLog.ReqURErrCnt)json_object_object_add(root, "Unsupported Request Error Status (URES)"
, json_object_new_int(pcieErrorLog.ReqURErrCnt))
;
1214 json_object_add_value_int(root, "ECRC Error Status (ECRCES)", pcieErrorLog.EcrcErrCnt)json_object_object_add(root, "ECRC Error Status (ECRCES)", json_object_new_int
(pcieErrorLog.EcrcErrCnt))
;
1215 json_object_add_value_int(root, "Malformed TLP Status (MTS)", pcieErrorLog.MalformedTlpErrCnt)json_object_object_add(root, "Malformed TLP Status (MTS)", json_object_new_int
(pcieErrorLog.MalformedTlpErrCnt))
;
1216 json_object_add_value_int(root, "Receiver Overflow Status (ROS)", pcieErrorLog.RcvrQOverflowErrCnt)json_object_object_add(root, "Receiver Overflow Status (ROS)"
, json_object_new_int(pcieErrorLog.RcvrQOverflowErrCnt))
;
1217 json_object_add_value_int(root, "Unexpected Completion Status(UCS)", pcieErrorLog.UnexpectedCplTlpErrCnt)json_object_object_add(root, "Unexpected Completion Status(UCS)"
, json_object_new_int(pcieErrorLog.UnexpectedCplTlpErrCnt))
;
1218 json_object_add_value_int(root, "Completion Timeout Status (CTS)", pcieErrorLog.CmpltnTOErrCnt)json_object_object_add(root, "Completion Timeout Status (CTS)"
, json_object_new_int(pcieErrorLog.CmpltnTOErrCnt))
;
1219 json_object_add_value_int(root, "Flow Control Protocol Error Status (FCPES)", pcieErrorLog.FCProtocolErrCnt)json_object_object_add(root, "Flow Control Protocol Error Status (FCPES)"
, json_object_new_int(pcieErrorLog.FCProtocolErrCnt))
;
1220 json_object_add_value_int(root, "Poisoned TLP Status (PTS)", pcieErrorLog.MemRdTlpPoisonedErrCnt)json_object_object_add(root, "Poisoned TLP Status (PTS)", json_object_new_int
(pcieErrorLog.MemRdTlpPoisonedErrCnt))
;
1221 json_object_add_value_int(root, "Data Link Protocol Error Status(DLPES)", pcieErrorLog.DllpProtocolErrCnt)json_object_object_add(root, "Data Link Protocol Error Status(DLPES)"
, json_object_new_int(pcieErrorLog.DllpProtocolErrCnt))
;
1222 json_object_add_value_int(root, "Replay Timer Timeout Status(RTS)", pcieErrorLog.ReplayTOErrCnt)json_object_object_add(root, "Replay Timer Timeout Status(RTS)"
, json_object_new_int(pcieErrorLog.ReplayTOErrCnt))
;
1223 json_object_add_value_int(root, "Replay_NUM Rollover Status(RRS)", pcieErrorLog.ReplayNumRolloverErrCnt)json_object_object_add(root, "Replay_NUM Rollover Status(RRS)"
, json_object_new_int(pcieErrorLog.ReplayNumRolloverErrCnt))
;
1224 json_object_add_value_int(root, "Bad DLLP Status (BDS)", pcieErrorLog.BadDllpErrCnt)json_object_object_add(root, "Bad DLLP Status (BDS)", json_object_new_int
(pcieErrorLog.BadDllpErrCnt))
;
1225 json_object_add_value_int(root, "Bad TLP Status (BTS)", pcieErrorLog.BadTlpErrCnt)json_object_object_add(root, "Bad TLP Status (BTS)", json_object_new_int
(pcieErrorLog.BadTlpErrCnt))
;
1226 json_object_add_value_int(root, "Receiver Error Status (RES)", pcieErrorLog.RcvrErrCnt)json_object_object_add(root, "Receiver Error Status (RES)", json_object_new_int
(pcieErrorLog.RcvrErrCnt))
;
1227 json_object_add_value_int(root, "Cpl TLP Unsupported Request Error Count", pcieErrorLog.CplTlpURErrCnt)json_object_object_add(root, "Cpl TLP Unsupported Request Error Count"
, json_object_new_int(pcieErrorLog.CplTlpURErrCnt))
;
1228 json_object_add_value_int(root, "Cpl TLP Completion Abort Error Count", pcieErrorLog.CplTlpCAErrCnt)json_object_object_add(root, "Cpl TLP Completion Abort Error Count"
, json_object_new_int(pcieErrorLog.CplTlpCAErrCnt))
;
1229 json_object_add_value_int(root, "Cpl TLP Poisoned Error Count", pcieErrorLog.CplTlpPoisonedErrCnt)json_object_object_add(root, "Cpl TLP Poisoned Error Count", json_object_new_int
(pcieErrorLog.CplTlpPoisonedErrCnt))
;
1230 json_object_add_value_int(root, "Request Completion Abort Error Count", pcieErrorLog.ReqCAErrCnt)json_object_object_add(root, "Request Completion Abort Error Count"
, json_object_new_int(pcieErrorLog.ReqCAErrCnt))
;
1231 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
1232}
1233
1234static int vs_pcie_error_log(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1235{
1236 pcie_error_log_page pcieErrorLog;
1237 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1238 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1239
1240 const char *desc = "Retrieve Seagate PCIe error counters for the given device ";
1241 int err;
1242 nvme_print_flags_t flags;
1243
1244 NVME_ARGS(opts)struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
1245
1246 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1247 if (err) {
1248 printf("\nDevice not found\n");
1249 return -1;
1250 }
1251
1252 err = validate_output_format(nvme_args.output_format, &flags);
1253 if (err < 0) {
1254 nvme_show_error("Invalid output format")nvme_show_message(1, "Invalid output format");
1255 return err;
1256 }
1257
1258 if (flags & NORMAL)
1259 printf("Seagate PCIe error counters Information :\n");
1260
1261 err = nvme_get_log_simple(hdl, 0xCB,
1262 &pcieErrorLog, sizeof(pcieErrorLog));
1263 if (!err) {
1264 if (flags & NORMAL)
1265 print_vs_pcie_error_log(pcieErrorLog);
1266 else
1267 json_vs_pcie_error_log(pcieErrorLog);
1268
1269 } else if (err > 0) {
1270 nvme_show_status(err);
1271 }
1272
1273
1274 return err;
1275}
1276/* EOF PCIE error-log information */
1277
1278
1279/***************************************
1280 * FW Activation History log
1281 ***************************************/
1282static void print_stx_vs_fw_activate_history(stx_fw_activ_history_log_page fwActivHis)
1283{
1284 __u32 i;
1285 char prev_fw[9] = {0};
1286 char new_fw[9] = {0};
1287 char buf[80];
1288
1289 if (fwActivHis.numValidFwActHisEnt > 0) {
1290 printf("\n\nSeagate FW Activation History :\n");
1291 printf("%-9s %-21s %-7s %-13s %-9s %-5s %-15s %-9s\n", "Counter ", " Timestamp ", " PCC ", "Previous FW ", "New FW ", "Slot", "Commit Action", "Result");
1292
1293 for (i = 0; i < fwActivHis.numValidFwActHisEnt; i++) {
1294
1295 printf(" %-4d ", fwActivHis.fwActHisEnt[i].fwActivCnt);
1296
1297 time_t t = fwActivHis.fwActHisEnt[i].timeStamp / 1000;
1298 struct tm ts = *localtime(&t);
1299
1300 strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", &ts);
1301 printf(" %-20s ", buf);
1302 printf("%-5" PRId64"l" "d" " ",
1303 (uint64_t)fwActivHis.fwActHisEnt[i].powCycleCnt);
1304
1305 memset(prev_fw, 0, sizeof(prev_fw));
1306 memcpy(prev_fw, fwActivHis.fwActHisEnt[i].previousFW, sizeof(fwActivHis.fwActHisEnt[i].previousFW));
1307 printf("%-8s ", prev_fw);
1308
1309 memset(new_fw, 0, sizeof(new_fw));
1310 memcpy(new_fw, fwActivHis.fwActHisEnt[i].newFW, sizeof(fwActivHis.fwActHisEnt[i].newFW));
1311 printf("%-8s ", new_fw);
1312
1313 printf(" %-2d ", fwActivHis.fwActHisEnt[i].slotNum);
1314 printf(" 0x%02x ", fwActivHis.fwActHisEnt[i].commitActionType);
1315 printf(" 0x%02x\n", fwActivHis.fwActHisEnt[i].result);
1316 }
1317 } else {
1318 printf("%s\n", "Do not have valid FW Activation History");
1319 }
1320}
1321
1322static void json_stx_vs_fw_activate_history(stx_fw_activ_history_log_page fwActivHis)
1323{
1324 struct json_object *root = json_create_object()json_object_new_object();
1325 __u32 i;
1326
1327 char buf[80];
1328
1329 struct json_object *historyLogPage = json_create_array()json_object_new_array();
1330
1331 json_object_add_value_array(root, "Seagate FW Activation History", historyLogPage)json_object_object_add(root, "Seagate FW Activation History",
historyLogPage)
;
1332
1333 if (fwActivHis.numValidFwActHisEnt > 0) {
1334 for (i = 0; i < fwActivHis.numValidFwActHisEnt; i++) {
1335 struct json_object *lbaf = json_create_object()json_object_new_object();
1336 char prev_fw[8] = { 0 };
1337 char new_fw[8] = { 0 };
1338
1339 json_object_add_value_int(lbaf, "Counter", fwActivHis.fwActHisEnt[i].fwActivCnt)json_object_object_add(lbaf, "Counter", json_object_new_int(fwActivHis
.fwActHisEnt[i].fwActivCnt))
;
1340
1341 time_t t = fwActivHis.fwActHisEnt[i].timeStamp / 1000;
1342 struct tm ts = *localtime(&t);
1343
1344 strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", &ts);
1345 printf(" %-20s ", buf);
1346 json_object_add_value_string(lbaf, "Timestamp", buf);
1347
1348 json_object_add_value_int(lbaf, "PCC", fwActivHis.fwActHisEnt[i].powCycleCnt)json_object_object_add(lbaf, "PCC", json_object_new_int(fwActivHis
.fwActHisEnt[i].powCycleCnt))
;
1349 sprintf(prev_fw, "%s", fwActivHis.fwActHisEnt[i].previousFW);
1350 json_object_add_value_string(lbaf, "Previous_FW", prev_fw);
1351
1352 sprintf(new_fw, "%s", fwActivHis.fwActHisEnt[i].newFW);
1353 json_object_add_value_string(lbaf, "New_FW", new_fw);
1354
1355 json_object_add_value_int(lbaf, "Slot", fwActivHis.fwActHisEnt[i].slotNum)json_object_object_add(lbaf, "Slot", json_object_new_int(fwActivHis
.fwActHisEnt[i].slotNum))
;
1356 json_object_add_value_int(lbaf, "Commit_Action", fwActivHis.fwActHisEnt[i].commitActionType)json_object_object_add(lbaf, "Commit_Action", json_object_new_int
(fwActivHis.fwActHisEnt[i].commitActionType))
;
1357 json_object_add_value_int(lbaf, "Result", fwActivHis.fwActHisEnt[i].result)json_object_object_add(lbaf, "Result", json_object_new_int(fwActivHis
.fwActHisEnt[i].result))
;
1358
1359 json_array_add_value_object(historyLogPage, lbaf)json_object_array_add(historyLogPage, lbaf);
1360 }
1361 } else {
1362 printf("%s\n", "Do not have valid FW Activation History");
1363 }
1364
1365 json_print_object(root, NULL)printf("%s", json_object_to_json_string_ext(root, (1 <<
1) | (1 << 4)))
;
1366 json_free_object(root)json_object_put(root);
1367}
1368
1369static int stx_vs_fw_activate_history(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1370{
1371 stx_fw_activ_history_log_page fwActivHis;
1372 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1373 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1374
1375 const char *desc = "Retrieve FW Activate History for Seagate device ";
1376 int err;
1377 nvme_print_flags_t flags;
1378
1379 NVME_ARGS(opts)struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
1380
1381 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1382 if (err < 0) {
1383 printf("\nDevice not found\n");
1384 return -1;
1385 }
1386
1387 err = validate_output_format(nvme_args.output_format, &flags);
1388 if (err < 0) {
1389 nvme_show_error("Invalid output format")nvme_show_message(1, "Invalid output format");
1390 return err;
1391 }
1392
1393 if (flags & NORMAL)
1394 printf("Seagate FW Activation History Information :\n");
1395
1396 err = nvme_get_log_simple(hdl, 0xC2, &fwActivHis, sizeof(fwActivHis));
1397 if (!err) {
1398 if (flags & NORMAL)
1399 print_stx_vs_fw_activate_history(fwActivHis);
1400 else
1401 json_stx_vs_fw_activate_history(fwActivHis);
1402 } else if (err > 0) {
1403 nvme_show_status(err);
1404 }
1405
1406 return err;
1407}
1408/* EOF FW Activation History log information */
1409
1410
1411static int clear_fw_activate_history(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1412{
1413 const char *desc = "Clear FW Activation History for the given Seagate device ";
1414 const char *save = "specifies that the controller shall save the attribute";
1415 int err;
1416 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1417 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1418 struct nvme_id_ctrl ctrl;
1419 char modelNo[40];
1420 __u64 result;
1421
1422 struct config {
1423 bool_Bool save;
1424 };
1425
1426 struct config cfg = {
1427 .save = 0,
1428 };
1429
1430 NVME_ARGS(opts,struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"save", 's', ((void*)0), CFG_FLAG, &cfg.save, 0, save
, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
1431 OPT_FLAG("save", 's', &cfg.save, save))struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"save", 's', ((void*)0), CFG_FLAG, &cfg.save, 0, save
, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
1432
1433 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1434 if (err < 0) {
1435 printf("\nDevice not found\n");
1436 return -1;
1437 }
1438
1439 err = nvme_identify_ctrl(hdl, &ctrl);
1440 if (!err) {
1441 memcpy(modelNo, ctrl.mn, sizeof(modelNo));
1442 } else {
1443 nvme_show_status(err);
1444 return err;
1445 }
1446
1447 if (!stx_is_jag_pan(modelNo)) {
1448 printf("\nDevice does not support Clear FW Activation History\n");
1449 } else {
1450 err = nvme_set_features(hdl, 0, 0xC1, 0, 0x80000000, 0, 0, 0, 0, NULL((void*)0),
1451 0, &result);
1452 if (err)
1453 fprintf(stderrstderr, "%s: couldn't clear PCIe correctable errors\n",
1454 __func__);
1455 }
1456
1457 if (err < 0) {
1458 perror("set-feature");
1459 return errno(*__errno_location ());
1460 }
1461
1462 return err;
1463}
1464
1465
1466static int vs_clr_pcie_correctable_errs(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1467{
1468 const char *desc = "Clear Seagate PCIe Correctable counters for the given device ";
1469 const char *save = "specifies that the controller shall save the attribute";
1470
1471 struct nvme_id_ctrl ctrl;
1472 char modelNo[40];
1473
1474 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1475 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1476
1477 __u64 result;
1478 int err;
1479
1480 struct config {
1481 bool_Bool save;
1482 };
1483
1484 struct config cfg = {
1485 .save = 0,
1486 };
1487
1488 NVME_ARGS(opts,struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"save", 's', ((void*)0), CFG_FLAG, &cfg.save, 0, save
, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
1489 OPT_FLAG("save", 's', &cfg.save, save))struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"save", 's', ((void*)0), CFG_FLAG, &cfg.save, 0, save
, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0
, "Global options", 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT
, &nvme_args.verbose, 0, "Increase output verbosity", 0, }
, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args.output_format
, 1, "Output format: normal|json|binary|tabular", 0, }, {"timeout"
, 0, "NUM", CFG_POSITIVE, &nvme_args.timeout, 1, "timeout value, in milliseconds"
, 0, }, {"dry-run", 0, ((void*)0), CFG_FLAG, &nvme_args.dry_run
, 0, "show command instead of executing", 0, }, {"no-retries"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_retries, 0, "disable retry logic on errors"
, 0, }, {"no-ioctl-probing", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_ioctl_probing, 0, "disable 64-bit IOCTL support probing",
0, }, {"output-format-version", 0, "NUM", CFG_POSITIVE, &
nvme_args.output_format_ver, 1, "output format version: 1|2",
0, }, {"human-readable", 'H', ((void*)0), CFG_FLAG, &nvme_args
.verbose, 0, ((void*)0), 0, ((void*)0), 1}, { ((void*)0) } }
;
1490
1491 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1492 if (err) {
1493 printf("\nDevice not found\n");
1494 return -1;
1495 }
1496
1497
1498 err = nvme_identify_ctrl(hdl, &ctrl);
1499 if (!err) {
1500 memcpy(modelNo, ctrl.mn, sizeof(modelNo));
1501 } else {
1502 nvme_show_status(err);
1503 return err;
1504 }
1505
1506 if (!stx_is_jag_pan(modelNo)) {
1507 err = nvme_set_features_simple(hdl, 0, 0xE1, cfg.save, 0xCB, &result);
Value stored to 'err' is never read
1508 } else {
1509 err = nvme_set_features(hdl, 0, 0xC3, 0, 0x80000000, 0, 0, 0, 0, NULL((void*)0),
1510 0, &result);
1511 if (err)
1512 fprintf(stderrstderr, "%s: couldn't clear PCIe correctable errors\n", __func__);
1513 }
1514
1515 err = nvme_set_features_simple(hdl, 0, 0xE1, cfg.save, 0xCB, &result);
1516
1517 if (err < 0) {
1518 perror("set-feature");
1519 return errno(*__errno_location ());
1520 }
1521
1522 return err;
1523}
1524
1525static int get_host_tele(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1526{
1527 const char *desc =
1528 "Capture the Telemetry Host-Initiated Data in either hex-dump (default) or binary format";
1529 const char *namespace_id = "desired namespace";
1530 const char *log_specific = "1 - controller shall capture Data representing the internal\n"
1531 "state of the controller at the time the command is processed.\n"
1532 "0 - controller shall not update the Telemetry Host Initiated Data.";
1533 const char *raw = "output in raw format";
1534 struct nvme_temetry_log_hdr tele_log;
1535 int blkCnt, maxBlk = 0, blksToGet;
1536 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1537 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1538 struct libnvme_passthru_cmd cmd;
1539 unsigned char *log;
1540 __le64 offset = 0;
1541 int err, dump_fd;
1542
1543 struct config {
1544 __u32 namespace_id;
1545 __u32 log_id;
1546 bool_Bool raw_binary;
1547 };
1548
1549 struct config cfg = {
1550 .namespace_id = 0xffffffff,
1551 .log_id = 0,
1552 };
1553
1554 NVME_ARGS(opts,struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"log_specific", 'i', "NUM", CFG_POSITIVE
, &cfg.log_id, 1, log_specific, 0, }, {"raw-binary", 'b',
((void*)0), CFG_FLAG, &cfg.raw_binary, 0, raw, 0, }, {""
, 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Global options"
, 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT, &
nvme_args.verbose, 0, "Increase output verbosity", 0, }, {"output-format"
, 'o', "FMT", CFG_STRING, &nvme_args.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1555 OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id),struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"log_specific", 'i', "NUM", CFG_POSITIVE
, &cfg.log_id, 1, log_specific, 0, }, {"raw-binary", 'b',
((void*)0), CFG_FLAG, &cfg.raw_binary, 0, raw, 0, }, {""
, 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Global options"
, 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT, &
nvme_args.verbose, 0, "Increase output verbosity", 0, }, {"output-format"
, 'o', "FMT", CFG_STRING, &nvme_args.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1556 OPT_UINT("log_specific", 'i', &cfg.log_id, log_specific),struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"log_specific", 'i', "NUM", CFG_POSITIVE
, &cfg.log_id, 1, log_specific, 0, }, {"raw-binary", 'b',
((void*)0), CFG_FLAG, &cfg.raw_binary, 0, raw, 0, }, {""
, 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Global options"
, 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT, &
nvme_args.verbose, 0, "Increase output verbosity", 0, }, {"output-format"
, 'o', "FMT", CFG_STRING, &nvme_args.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1557 OPT_FLAG("raw-binary", 'b', &cfg.raw_binary, raw))struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"log_specific", 'i', "NUM", CFG_POSITIVE
, &cfg.log_id, 1, log_specific, 0, }, {"raw-binary", 'b',
((void*)0), CFG_FLAG, &cfg.raw_binary, 0, raw, 0, }, {""
, 0, ((void*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Global options"
, 0, ((void*)0)}, {"verbose", 'v', "NUM", CFG_INCREMENT, &
nvme_args.verbose, 0, "Increase output verbosity", 0, }, {"output-format"
, 'o', "FMT", CFG_STRING, &nvme_args.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
;
1558
1559 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1560 if (err)
1561 return err;
1562
1563 dump_fd = STDOUT_FILENO1;
1564 cfg.log_id = (cfg.log_id << 8) | 0x07;
1565 err = nvme_get_nsid_log(hdl, cfg.namespace_id, false0, cfg.log_id,
1566 (void *)(&tele_log), sizeof(tele_log));
1567 if (!err) {
1568 maxBlk = tele_log.tele_data_area3;
1569 offset += 512;
1570
1571 if (!cfg.raw_binary) {
1572 printf("Device:%s log-id:%d namespace-id:%#x\n",
1573 libnvme_transport_handle_get_name(hdl), cfg.log_id,
1574 cfg.namespace_id);
1575 printf("Data Block 1 Last Block:%d Data Block 2 Last Block:%d Data Block 3 Last Block:%d\n",
1576 tele_log.tele_data_area1, tele_log.tele_data_area2, tele_log.tele_data_area3);
1577
1578 d((unsigned char *)(&tele_log), sizeof(tele_log), 16, 1);
1579 } else
1580 seaget_d_raw((unsigned char *)(&tele_log), sizeof(tele_log), dump_fd);
1581 } else if (err > 0) {
1582 nvme_show_status(err);
1583 } else {
1584 perror("log page");
1585 }
1586
1587 blkCnt = 0;
1588
1589 while (blkCnt < maxBlk) {
1590 unsigned long long bytesToGet;
1591
1592 blksToGet = ((maxBlk - blkCnt) >= TELEMETRY_BLOCKS_TO_READ8) ? TELEMETRY_BLOCKS_TO_READ8 : (maxBlk - blkCnt);
1593
1594 if (!blksToGet) {
1595
1596 return err;
1597 }
1598
1599 bytesToGet = (unsigned long long)blksToGet * 512;
1600 log = malloc(bytesToGet);
1601
1602 if (!log) {
1603 fprintf(stderrstderr, "could not alloc buffer for log\n");
1604
1605 return -EINVAL22;
1606 }
1607
1608 memset(log, 0, bytesToGet);
1609
1610 nvme_init_get_log(&cmd, cfg.namespace_id, cfg.log_id,
1611 NVME_CSI_NVM, log, bytesToGet);
1612 nvme_init_get_log_lpo(&cmd, offset);
1613 err = libnvme_get_log(hdl, &cmd, true1, NVME_LOG_PAGE_PDU_SIZE4096);
1614 if (!err) {
1615 offset += (__le64)bytesToGet;
1616
1617 if (!cfg.raw_binary) {
1618 printf("\nBlock # :%d to %d\n", blkCnt + 1, blkCnt + blksToGet);
1619
1620 d((unsigned char *)log, bytesToGet, 16, 1);
1621 } else
1622 seaget_d_raw((unsigned char *)log, bytesToGet, dump_fd);
1623 } else if (err > 0) {
1624 nvme_show_status(err);
1625 } else {
1626 perror("log page");
1627 }
1628
1629 blkCnt += blksToGet;
1630
1631 free(log);
1632 }
1633
1634 return err;
1635}
1636
1637static int get_ctrl_tele(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1638{
1639 const char *desc =
1640 "Capture the Telemetry Controller-Initiated Data in either hex-dump (default) or binary format";
1641 const char *namespace_id = "desired namespace";
1642 const char *raw = "output in raw format";
1643 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1644 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1645 struct libnvme_passthru_cmd cmd;
1646 int err, dump_fd;
1647 struct nvme_temetry_log_hdr tele_log;
1648 __le64 offset = 0;
1649 __u16 log_id;
1650 int blkCnt, maxBlk = 0, blksToGet;
1651 unsigned char *log;
1652
1653 struct config {
1654 __u32 namespace_id;
1655 bool_Bool raw_binary;
1656 };
1657
1658 struct config cfg = {
1659 .namespace_id = 0xffffffff,
1660 };
1661
1662 NVME_ARGS(opts,struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"raw-binary", 'b', ((void*)0), CFG_FLAG
, &cfg.raw_binary, 0, raw, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR
, ((void*)0), 0, "Global options", 0, ((void*)0)}, {"verbose"
, 'v', "NUM", CFG_INCREMENT, &nvme_args.verbose, 0, "Increase output verbosity"
, 0, }, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args
.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1663 OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id),struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"raw-binary", 'b', ((void*)0), CFG_FLAG
, &cfg.raw_binary, 0, raw, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR
, ((void*)0), 0, "Global options", 0, ((void*)0)}, {"verbose"
, 'v', "NUM", CFG_INCREMENT, &nvme_args.verbose, 0, "Increase output verbosity"
, 0, }, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args
.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1664 OPT_FLAG("raw-binary", 'b', &cfg.raw_binary, raw))struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"raw-binary", 'b', ((void*)0), CFG_FLAG
, &cfg.raw_binary, 0, raw, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR
, ((void*)0), 0, "Global options", 0, ((void*)0)}, {"verbose"
, 'v', "NUM", CFG_INCREMENT, &nvme_args.verbose, 0, "Increase output verbosity"
, 0, }, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args
.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
;
1665
1666 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1667 if (err)
1668 return err;
1669
1670 dump_fd = STDOUT_FILENO1;
1671
1672 log_id = 0x08;
1673 err = nvme_get_nsid_log(hdl, cfg.namespace_id, false0, log_id,
1674 (void *)(&tele_log), sizeof(tele_log));
1675 if (!err) {
1676 maxBlk = tele_log.tele_data_area3;
1677 offset += 512;
1678
1679 if (!cfg.raw_binary) {
1680 printf("Device:%s namespace-id:%#x\n",
1681 libnvme_transport_handle_get_name(hdl), cfg.namespace_id);
1682 printf("Data Block 1 Last Block:%d Data Block 2 Last Block:%d Data Block 3 Last Block:%d\n",
1683 tele_log.tele_data_area1, tele_log.tele_data_area2, tele_log.tele_data_area3);
1684
1685 d((unsigned char *)(&tele_log), sizeof(tele_log), 16, 1);
1686 } else
1687 seaget_d_raw((unsigned char *)(&tele_log), sizeof(tele_log), dump_fd);
1688 } else if (err > 0) {
1689 nvme_show_status(err);
1690 } else {
1691 perror("log page");
1692 }
1693
1694 blkCnt = 0;
1695
1696 while (blkCnt < maxBlk) {
1697 unsigned long long bytesToGet;
1698
1699 blksToGet = ((maxBlk - blkCnt) >= TELEMETRY_BLOCKS_TO_READ8) ? TELEMETRY_BLOCKS_TO_READ8 : (maxBlk - blkCnt);
1700
1701 if (!blksToGet)
1702 return err;
1703
1704 bytesToGet = (unsigned long long)blksToGet * 512;
1705 log = malloc(bytesToGet);
1706
1707 if (!log) {
1708 fprintf(stderrstderr, "could not alloc buffer for log\n");
1709 return -EINVAL22;
1710 }
1711
1712 memset(log, 0, bytesToGet);
1713
1714 nvme_init_get_log(&cmd, cfg.namespace_id, log_id,
1715 NVME_CSI_NVM, log, bytesToGet);
1716 nvme_init_get_log_lpo(&cmd, offset);
1717 err = libnvme_get_log(hdl, &cmd, true1, NVME_LOG_PAGE_PDU_SIZE4096);
1718 if (!err) {
1719 offset += (__le64)bytesToGet;
1720
1721 if (!cfg.raw_binary) {
1722 printf("\nBlock # :%d to %d\n", blkCnt + 1, blkCnt + blksToGet);
1723
1724 d((unsigned char *)log, bytesToGet, 16, 1);
1725 } else
1726 seaget_d_raw((unsigned char *)log, bytesToGet, dump_fd);
1727 } else if (err > 0) {
1728 nvme_show_status(err);
1729 } else {
1730 perror("log page");
1731 }
1732
1733 blkCnt += blksToGet;
1734
1735 free(log);
1736 }
1737
1738
1739 return err;
1740}
1741
1742void
1743seaget_d_raw(unsigned char *buf, int len, int fd)
1744{
1745 if (write(fd, (void *)buf, len) <= 0)
1746 printf("%s: Write Failed\n", __func__);
1747}
1748
1749
1750static int vs_internal_log(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1751{
1752 const char *desc = "Capture the Telemetry Controller-Initiated Data in binary format";
1753 const char *namespace_id = "desired namespace";
1754
1755 const char *file = "dump file";
1756 __cleanup_nvme_global_ctx__attribute__((cleanup(cleanup_nvme_global_ctx))) struct libnvme_global_ctx *ctx = NULL((void*)0);
1757 __cleanup_nvme_transport_handle__attribute__((cleanup(cleanup_nvme_transport_handle))) struct libnvme_transport_handle *hdl = NULL((void*)0);
1758 struct libnvme_passthru_cmd cmd;
1759 int err, dump_fd;
1760 int flags = O_WRONLY01 | O_CREAT0100;
1761 int mode = 0664;
1762 struct nvme_temetry_log_hdr tele_log;
1763 __le64 offset = 0;
1764 __u16 log_id;
1765 int blkCnt, maxBlk = 0, blksToGet;
1766 unsigned char *log;
1767
1768 struct config {
1769 __u32 namespace_id;
1770 char *file;
1771 };
1772
1773 struct config cfg = {
1774 .namespace_id = 0xffffffff,
1775 .file = "",
1776 };
1777
1778 NVME_ARGS(opts,struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"dump-file", 'f', "FILE", CFG_STRING
, &cfg.file, 1, file, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR
, ((void*)0), 0, "Global options", 0, ((void*)0)}, {"verbose"
, 'v', "NUM", CFG_INCREMENT, &nvme_args.verbose, 0, "Increase output verbosity"
, 0, }, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args
.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1779 OPT_UINT("namespace-id", 'n', &cfg.namespace_id, namespace_id),struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"dump-file", 'f', "FILE", CFG_STRING
, &cfg.file, 1, file, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR
, ((void*)0), 0, "Global options", 0, ((void*)0)}, {"verbose"
, 'v', "NUM", CFG_INCREMENT, &nvme_args.verbose, 0, "Increase output verbosity"
, 0, }, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args
.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
1780 OPT_FILE("dump-file", 'f', &cfg.file, file))struct argconfig_commandline_options opts[] = { {"", 0, ((void
*)0), CFG_GROUP_SEPARATOR, ((void*)0), 0, "Options", 0, ((void
*)0)}, {"namespace-id", 'n', "NUM", CFG_POSITIVE, &cfg.namespace_id
, 1, namespace_id, 0, }, {"dump-file", 'f', "FILE", CFG_STRING
, &cfg.file, 1, file, 0, }, {"", 0, ((void*)0), CFG_GROUP_SEPARATOR
, ((void*)0), 0, "Global options", 0, ((void*)0)}, {"verbose"
, 'v', "NUM", CFG_INCREMENT, &nvme_args.verbose, 0, "Increase output verbosity"
, 0, }, {"output-format", 'o', "FMT", CFG_STRING, &nvme_args
.output_format, 1, "Output format: normal|json|binary|tabular"
, 0, }, {"timeout", 0, "NUM", CFG_POSITIVE, &nvme_args.timeout
, 1, "timeout value, in milliseconds", 0, }, {"dry-run", 0, (
(void*)0), CFG_FLAG, &nvme_args.dry_run, 0, "show command instead of executing"
, 0, }, {"no-retries", 0, ((void*)0), CFG_FLAG, &nvme_args
.no_retries, 0, "disable retry logic on errors", 0, }, {"no-ioctl-probing"
, 0, ((void*)0), CFG_FLAG, &nvme_args.no_ioctl_probing, 0
, "disable 64-bit IOCTL support probing", 0, }, {"output-format-version"
, 0, "NUM", CFG_POSITIVE, &nvme_args.output_format_ver, 1
, "output format version: 1|2", 0, }, {"human-readable", 'H',
((void*)0), CFG_FLAG, &nvme_args.verbose, 0, ((void*)0),
0, ((void*)0), 1}, { ((void*)0) } }
;
1781
1782 err = parse_and_open(&ctx, &hdl, argc, argv, desc, opts);
1783 if (err)
1784 return err;
1785
1786 dump_fd = STDOUT_FILENO1;
1787 if (strlen(cfg.file)) {
1788 dump_fd = nvme_open_rawdata(cfg.file, flags, mode)open((cfg.file), (flags), mode);
1789 if (dump_fd < 0) {
1790 perror(cfg.file);
1791 return -EINVAL22;
1792 }
1793 }
1794
1795 log_id = 0x08;
1796 err = nvme_get_nsid_log(hdl, cfg.namespace_id, false0, log_id,
1797 (void *)(&tele_log), sizeof(tele_log));
1798 if (!err) {
1799 maxBlk = tele_log.tele_data_area3;
1800 offset += 512;
1801
1802 seaget_d_raw((unsigned char *)(&tele_log), sizeof(tele_log), dump_fd);
1803 } else if (err > 0) {
1804 nvme_show_status(err);
1805 } else {
1806 perror("log page");
1807 }
1808
1809 blkCnt = 0;
1810
1811 while (blkCnt < maxBlk) {
1812 unsigned long long bytesToGet;
1813
1814 blksToGet = ((maxBlk - blkCnt) >= TELEMETRY_BLOCKS_TO_READ8) ? TELEMETRY_BLOCKS_TO_READ8 : (maxBlk - blkCnt);
1815
1816 if (!blksToGet)
1817 goto out;
1818
1819 bytesToGet = (unsigned long long)blksToGet * 512;
1820 log = malloc(bytesToGet);
1821
1822 if (!log) {
1823 fprintf(stderrstderr, "could not alloc buffer for log\n");
1824 err = EINVAL22;
1825 goto out;
1826 }
1827
1828 memset(log, 0, bytesToGet);
1829
1830 nvme_init_get_log_lpo(&cmd, offset);
1831 nvme_init_get_log(&cmd, cfg.namespace_id, log_id,
1832 NVME_CSI_NVM, log, bytesToGet);
1833 nvme_init_get_log_lpo(&cmd, offset);
1834 err = libnvme_get_log(hdl, &cmd, true1, NVME_LOG_PAGE_PDU_SIZE4096);
1835 if (!err) {
1836 offset += (__le64)bytesToGet;
1837
1838 seaget_d_raw((unsigned char *)log, bytesToGet, dump_fd);
1839
1840 } else if (err > 0) {
1841 nvme_show_status(err);
1842 } else {
1843 perror("log page");
1844 }
1845
1846 blkCnt += blksToGet;
1847
1848 free(log);
1849 }
1850out:
1851 if (strlen(cfg.file))
1852 close(dump_fd);
1853
1854 return err;
1855}
1856
1857/*SEAGATE-PLUGIN Version */
1858static int seagate_plugin_version(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1859{
1860 printf("Seagate-Plugin version : %d.%d\n",
1861 SEAGATE_PLUGIN_VERSION_MAJOR1,
1862 SEAGATE_PLUGIN_VERSION_MINOR2);
1863 return 0;
1864}
1865/*EOF SEAGATE-PLUGIN Version */
1866
1867/*OCP SEAGATE-PLUGIN Version */
1868static int stx_ocp_plugin_version(int argc, char **argv, struct command *acmd, struct plugin *plugin)
1869{
1870 printf("Seagate-OCP-Plugin version : %d.%d\n",
1871 SEAGATE_OCP_PLUGIN_VERSION_MAJOR1,
1872 SEAGATE_OCP_PLUGIN_VERSION_MINOR0);
1873 return 0;
1874}
1875/*EOF OCP SEAGATE-PLUGIN Version */