diff options
| author | Dan Williams <dan.j.williams@intel.com> | 2017-11-17 19:23:08 -0500 |
|---|---|---|
| committer | Dan Williams <dan.j.williams@intel.com> | 2017-12-04 13:19:20 -0500 |
| commit | cdd77d3e193031cc67426cd671d8aa370f7dfee4 (patch) | |
| tree | 593f495eb83145d25e848a4a5c88bfb6f5509440 | |
| parent | ae64f9bd1d3621b5e60d7363bc20afb46aede215 (diff) | |
nfit, libnvdimm: deprecate the generic SMART ioctl
The kernel's ND_IOCTL_SMART_THRESHOLD command is based on a payload
definition that has become broken / out-of-sync with recent versions of
the NVDIMM_FAMILY_INTEL definition. Deprecate the use of the
ND_IOCTL_SMART_THRESHOLD command in favor of the ND_CMD_CALL approach
taken by NVDIMM_FAMILY_{HPE,MSFT}, where we can manage the per-vendor
variance in userspace.
In a couple years, when the new scheme is widely deployed in userspace
packages, the ND_IOCTL_SMART_THRESHOLD support can be removed. For now
we prevent new binaries from compiling against the kernel header
definitions, but kernel still compatible with old binaries. The
libndctl.h [1] header is now the authoritative interface definition for
NVDIMM SMART.
[1]: https://github.com/pmem/ndctl
Signed-off-by: Dan Williams <dan.j.williams@intel.com>
| -rw-r--r-- | drivers/nvdimm/bus.c | 3 | ||||
| -rw-r--r-- | include/uapi/linux/ndctl.h | 54 | ||||
| -rw-r--r-- | tools/testing/nvdimm/test/nfit.c | 39 | ||||
| -rw-r--r-- | tools/testing/nvdimm/test/nfit_test.h | 59 |
4 files changed, 84 insertions, 71 deletions
diff --git a/drivers/nvdimm/bus.c b/drivers/nvdimm/bus.c index 0a5e6cd758fe..78eabc3a1ab1 100644 --- a/drivers/nvdimm/bus.c +++ b/drivers/nvdimm/bus.c | |||
| @@ -1142,9 +1142,6 @@ int __init nvdimm_bus_init(void) | |||
| 1142 | { | 1142 | { |
| 1143 | int rc; | 1143 | int rc; |
| 1144 | 1144 | ||
| 1145 | BUILD_BUG_ON(sizeof(struct nd_smart_payload) != 128); | ||
| 1146 | BUILD_BUG_ON(sizeof(struct nd_smart_threshold_payload) != 8); | ||
| 1147 | |||
| 1148 | rc = bus_register(&nvdimm_bus_type); | 1145 | rc = bus_register(&nvdimm_bus_type); |
| 1149 | if (rc) | 1146 | if (rc) |
| 1150 | return rc; | 1147 | return rc; |
diff --git a/include/uapi/linux/ndctl.h b/include/uapi/linux/ndctl.h index 3f03567631cb..30ef1236aafa 100644 --- a/include/uapi/linux/ndctl.h +++ b/include/uapi/linux/ndctl.h | |||
| @@ -15,54 +15,6 @@ | |||
| 15 | 15 | ||
| 16 | #include <linux/types.h> | 16 | #include <linux/types.h> |
| 17 | 17 | ||
| 18 | struct nd_cmd_smart { | ||
| 19 | __u32 status; | ||
| 20 | __u8 data[128]; | ||
| 21 | } __packed; | ||
| 22 | |||
| 23 | #define ND_SMART_HEALTH_VALID (1 << 0) | ||
| 24 | #define ND_SMART_SPARES_VALID (1 << 1) | ||
| 25 | #define ND_SMART_USED_VALID (1 << 2) | ||
| 26 | #define ND_SMART_TEMP_VALID (1 << 3) | ||
| 27 | #define ND_SMART_CTEMP_VALID (1 << 4) | ||
| 28 | #define ND_SMART_ALARM_VALID (1 << 9) | ||
| 29 | #define ND_SMART_SHUTDOWN_VALID (1 << 10) | ||
| 30 | #define ND_SMART_VENDOR_VALID (1 << 11) | ||
| 31 | #define ND_SMART_SPARE_TRIP (1 << 0) | ||
| 32 | #define ND_SMART_TEMP_TRIP (1 << 1) | ||
| 33 | #define ND_SMART_CTEMP_TRIP (1 << 2) | ||
| 34 | #define ND_SMART_NON_CRITICAL_HEALTH (1 << 0) | ||
| 35 | #define ND_SMART_CRITICAL_HEALTH (1 << 1) | ||
| 36 | #define ND_SMART_FATAL_HEALTH (1 << 2) | ||
| 37 | |||
| 38 | struct nd_smart_payload { | ||
| 39 | __u32 flags; | ||
| 40 | __u8 reserved0[4]; | ||
| 41 | __u8 health; | ||
| 42 | __u8 spares; | ||
| 43 | __u8 life_used; | ||
| 44 | __u8 alarm_flags; | ||
| 45 | __u16 temperature; | ||
| 46 | __u16 ctrl_temperature; | ||
| 47 | __u8 reserved1[15]; | ||
| 48 | __u8 shutdown_state; | ||
| 49 | __u32 vendor_size; | ||
| 50 | __u8 vendor_data[92]; | ||
| 51 | } __packed; | ||
| 52 | |||
| 53 | struct nd_cmd_smart_threshold { | ||
| 54 | __u32 status; | ||
| 55 | __u8 data[8]; | ||
| 56 | } __packed; | ||
| 57 | |||
| 58 | struct nd_smart_threshold_payload { | ||
| 59 | __u8 alarm_control; | ||
| 60 | __u8 reserved0; | ||
| 61 | __u16 temperature; | ||
| 62 | __u8 spares; | ||
| 63 | __u8 reserved[3]; | ||
| 64 | } __packed; | ||
| 65 | |||
| 66 | struct nd_cmd_dimm_flags { | 18 | struct nd_cmd_dimm_flags { |
| 67 | __u32 status; | 19 | __u32 status; |
| 68 | __u32 flags; | 20 | __u32 flags; |
| @@ -211,12 +163,6 @@ static inline const char *nvdimm_cmd_name(unsigned cmd) | |||
| 211 | 163 | ||
| 212 | #define ND_IOCTL 'N' | 164 | #define ND_IOCTL 'N' |
| 213 | 165 | ||
| 214 | #define ND_IOCTL_SMART _IOWR(ND_IOCTL, ND_CMD_SMART,\ | ||
| 215 | struct nd_cmd_smart) | ||
| 216 | |||
| 217 | #define ND_IOCTL_SMART_THRESHOLD _IOWR(ND_IOCTL, ND_CMD_SMART_THRESHOLD,\ | ||
| 218 | struct nd_cmd_smart_threshold) | ||
| 219 | |||
| 220 | #define ND_IOCTL_DIMM_FLAGS _IOWR(ND_IOCTL, ND_CMD_DIMM_FLAGS,\ | 166 | #define ND_IOCTL_DIMM_FLAGS _IOWR(ND_IOCTL, ND_CMD_DIMM_FLAGS,\ |
| 221 | struct nd_cmd_dimm_flags) | 167 | struct nd_cmd_dimm_flags) |
| 222 | 168 | ||
diff --git a/tools/testing/nvdimm/test/nfit.c b/tools/testing/nvdimm/test/nfit.c index 7217b2b953b5..640c02b08a50 100644 --- a/tools/testing/nvdimm/test/nfit.c +++ b/tools/testing/nvdimm/test/nfit.c | |||
| @@ -440,39 +440,50 @@ static int nfit_test_cmd_translate_spa(struct nvdimm_bus *bus, | |||
| 440 | return 0; | 440 | return 0; |
| 441 | } | 441 | } |
| 442 | 442 | ||
| 443 | static int nfit_test_cmd_smart(struct nd_cmd_smart *smart, unsigned int buf_len) | 443 | static int nfit_test_cmd_smart(struct nd_intel_smart *smart, unsigned int buf_len) |
| 444 | { | 444 | { |
| 445 | static const struct nd_smart_payload smart_data = { | 445 | static const struct nd_intel_smart smart_data = { |
| 446 | .flags = ND_SMART_HEALTH_VALID | ND_SMART_TEMP_VALID | 446 | .flags = ND_INTEL_SMART_HEALTH_VALID |
| 447 | | ND_SMART_SPARES_VALID | ND_SMART_ALARM_VALID | 447 | | ND_INTEL_SMART_SPARES_VALID |
| 448 | | ND_SMART_USED_VALID | ND_SMART_SHUTDOWN_VALID, | 448 | | ND_INTEL_SMART_ALARM_VALID |
| 449 | .health = ND_SMART_NON_CRITICAL_HEALTH, | 449 | | ND_INTEL_SMART_USED_VALID |
| 450 | .temperature = 23 * 16, | 450 | | ND_INTEL_SMART_SHUTDOWN_VALID |
| 451 | | ND_INTEL_SMART_MTEMP_VALID, | ||
| 452 | .health = ND_INTEL_SMART_NON_CRITICAL_HEALTH, | ||
| 453 | .media_temperature = 23 * 16, | ||
| 454 | .ctrl_temperature = 30 * 16, | ||
| 455 | .pmic_temperature = 40 * 16, | ||
| 451 | .spares = 75, | 456 | .spares = 75, |
| 452 | .alarm_flags = ND_SMART_SPARE_TRIP | ND_SMART_TEMP_TRIP, | 457 | .alarm_flags = ND_INTEL_SMART_SPARE_TRIP |
| 458 | | ND_INTEL_SMART_TEMP_TRIP, | ||
| 459 | .ait_status = 1, | ||
| 453 | .life_used = 5, | 460 | .life_used = 5, |
| 454 | .shutdown_state = 0, | 461 | .shutdown_state = 0, |
| 455 | .vendor_size = 0, | 462 | .vendor_size = 0, |
| 463 | .shutdown_count = 100, | ||
| 456 | }; | 464 | }; |
| 457 | 465 | ||
| 458 | if (buf_len < sizeof(*smart)) | 466 | if (buf_len < sizeof(*smart)) |
| 459 | return -EINVAL; | 467 | return -EINVAL; |
| 460 | memcpy(smart->data, &smart_data, sizeof(smart_data)); | 468 | memcpy(smart, &smart_data, sizeof(smart_data)); |
| 461 | return 0; | 469 | return 0; |
| 462 | } | 470 | } |
| 463 | 471 | ||
| 464 | static int nfit_test_cmd_smart_threshold(struct nd_cmd_smart_threshold *smart_t, | 472 | static int nfit_test_cmd_smart_threshold( |
| 473 | struct nd_intel_smart_threshold *smart_t, | ||
| 465 | unsigned int buf_len) | 474 | unsigned int buf_len) |
| 466 | { | 475 | { |
| 467 | static const struct nd_smart_threshold_payload smart_t_data = { | 476 | static const struct nd_intel_smart_threshold smart_t_data = { |
| 468 | .alarm_control = ND_SMART_SPARE_TRIP | ND_SMART_TEMP_TRIP, | 477 | .alarm_control = ND_INTEL_SMART_SPARE_TRIP |
| 469 | .temperature = 40 * 16, | 478 | | ND_INTEL_SMART_TEMP_TRIP, |
| 479 | .media_temperature = 40 * 16, | ||
| 480 | .ctrl_temperature = 30 * 16, | ||
| 470 | .spares = 5, | 481 | .spares = 5, |
| 471 | }; | 482 | }; |
| 472 | 483 | ||
| 473 | if (buf_len < sizeof(*smart_t)) | 484 | if (buf_len < sizeof(*smart_t)) |
| 474 | return -EINVAL; | 485 | return -EINVAL; |
| 475 | memcpy(smart_t->data, &smart_t_data, sizeof(smart_t_data)); | 486 | memcpy(smart_t, &smart_t_data, sizeof(smart_t_data)); |
| 476 | return 0; | 487 | return 0; |
| 477 | } | 488 | } |
| 478 | 489 | ||
diff --git a/tools/testing/nvdimm/test/nfit_test.h b/tools/testing/nvdimm/test/nfit_test.h index 113b44675a71..b85fba2856c7 100644 --- a/tools/testing/nvdimm/test/nfit_test.h +++ b/tools/testing/nvdimm/test/nfit_test.h | |||
| @@ -84,6 +84,65 @@ struct nd_cmd_ars_err_inj_stat { | |||
| 84 | } __packed record[0]; | 84 | } __packed record[0]; |
| 85 | } __packed; | 85 | } __packed; |
| 86 | 86 | ||
| 87 | #define ND_INTEL_SMART 1 | ||
| 88 | #define ND_INTEL_SMART_THRESHOLD 2 | ||
| 89 | |||
| 90 | #define ND_INTEL_SMART_HEALTH_VALID (1 << 0) | ||
| 91 | #define ND_INTEL_SMART_SPARES_VALID (1 << 1) | ||
| 92 | #define ND_INTEL_SMART_USED_VALID (1 << 2) | ||
| 93 | #define ND_INTEL_SMART_MTEMP_VALID (1 << 3) | ||
| 94 | #define ND_INTEL_SMART_CTEMP_VALID (1 << 4) | ||
| 95 | #define ND_INTEL_SMART_SHUTDOWN_COUNT_VALID (1 << 5) | ||
| 96 | #define ND_INTEL_SMART_AIT_STATUS_VALID (1 << 6) | ||
| 97 | #define ND_INTEL_SMART_PTEMP_VALID (1 << 7) | ||
| 98 | #define ND_INTEL_SMART_ALARM_VALID (1 << 9) | ||
| 99 | #define ND_INTEL_SMART_SHUTDOWN_VALID (1 << 10) | ||
| 100 | #define ND_INTEL_SMART_VENDOR_VALID (1 << 11) | ||
| 101 | #define ND_INTEL_SMART_SPARE_TRIP (1 << 0) | ||
| 102 | #define ND_INTEL_SMART_TEMP_TRIP (1 << 1) | ||
| 103 | #define ND_INTEL_SMART_CTEMP_TRIP (1 << 2) | ||
| 104 | #define ND_INTEL_SMART_NON_CRITICAL_HEALTH (1 << 0) | ||
| 105 | #define ND_INTEL_SMART_CRITICAL_HEALTH (1 << 1) | ||
| 106 | #define ND_INTEL_SMART_FATAL_HEALTH (1 << 2) | ||
| 107 | |||
| 108 | struct nd_intel_smart { | ||
| 109 | __u32 status; | ||
| 110 | union { | ||
| 111 | struct { | ||
| 112 | __u32 flags; | ||
| 113 | __u8 reserved0[4]; | ||
| 114 | __u8 health; | ||
| 115 | __u8 spares; | ||
| 116 | __u8 life_used; | ||
| 117 | __u8 alarm_flags; | ||
| 118 | __u16 media_temperature; | ||
| 119 | __u16 ctrl_temperature; | ||
| 120 | __u32 shutdown_count; | ||
| 121 | __u8 ait_status; | ||
| 122 | __u16 pmic_temperature; | ||
| 123 | __u8 reserved1[8]; | ||
| 124 | __u8 shutdown_state; | ||
| 125 | __u32 vendor_size; | ||
| 126 | __u8 vendor_data[92]; | ||
| 127 | } __packed; | ||
| 128 | __u8 data[128]; | ||
| 129 | }; | ||
| 130 | } __packed; | ||
| 131 | |||
| 132 | struct nd_intel_smart_threshold { | ||
| 133 | __u32 status; | ||
| 134 | union { | ||
| 135 | struct { | ||
| 136 | __u16 alarm_control; | ||
| 137 | __u8 spares; | ||
| 138 | __u16 media_temperature; | ||
| 139 | __u16 ctrl_temperature; | ||
| 140 | __u8 reserved[1]; | ||
| 141 | } __packed; | ||
| 142 | __u8 data[8]; | ||
| 143 | }; | ||
| 144 | } __packed; | ||
| 145 | |||
| 87 | union acpi_object; | 146 | union acpi_object; |
| 88 | typedef void *acpi_handle; | 147 | typedef void *acpi_handle; |
| 89 | 148 | ||
