[PATCH linux dev-5.8] hwmon: Ampere Computing ALTRA SMPMPRO sensor driver
Lancelot
lancelot.kao at fii-usa.com
Thu Oct 1 08:26:57 AEST 2020
From: Lancelot Kao <lancelot.kao at fii-usa.com>
Add SMPMPro-hwmon driver to monitor Ampere CPU/Memory/VR via an
i2c interface of the CPU's smpmpro management device.
Signed-off-by: Xiaopeng XP Chen <xiao-peng.chen at fii-na.com>
Signed-off-by: Lancelot Kao <lancelot.kao at fii-usa.com>
---
MAINTAINERS | 8 +
drivers/hwmon/Kconfig | 10 +
drivers/hwmon/Makefile | 1 +
drivers/hwmon/smpmpro-hwmon.c | 903 ++++++++++++++++++++++++++++++++++
4 files changed, 922 insertions(+)
create mode 100644 drivers/hwmon/smpmpro-hwmon.c
diff --git a/MAINTAINERS b/MAINTAINERS
index 5fecb388d073..c169fd9a4d7c 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -15759,6 +15759,14 @@ S: Maintained
F: Documentation/hwmon/smm665.rst
F: drivers/hwmon/smm665.c
+SMPMPRO HARDWARE MONITOR DRIVER
+M: Lancelot Kao <lancelot.kao at fii-usa.com>
+M: Xiaopeng XP Chen <xiao-peng.chen at fii-na.com>
+M: Mohaimen Alsamarai <Mohaimen.Alsamarai at fii-na.com>
+L: linux-hwmon at vger.kernel.org
+S: Maintained
+F: drivers/hwmon/smpmpro-hwmon.c
+
SMSC EMC2103 HARDWARE MONITOR DRIVER
M: Steve Glendinning <steve.glendinning at shawell.net>
L: linux-hwmon at vger.kernel.org
diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig
index 9aa89d7d4193..50881ebcb022 100644
--- a/drivers/hwmon/Kconfig
+++ b/drivers/hwmon/Kconfig
@@ -1777,6 +1777,16 @@ config SENSORS_INA3221
This driver can also be built as a module. If so, the module
will be called ina3221.
+config SENSORS_SMPMPRO
+ tristate "Ampere Computing Altra SMPMPRO sensor chip"
+ depends on I2C
+ help
+ If you say yes here you get support for Ampere Computing Altra SMPMPRO
+ sensor chip. This will enable monitoring of Ampere CPU Sensors; via hwmon.
+
+ This driver can also be built as a module. If so, the module
+ will be called smpmpro-hwmon.
+
config SENSORS_TC74
tristate "Microchip TC74"
depends on I2C
diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile
index ae41ee71a71b..49a1a8e0c73f 100644
--- a/drivers/hwmon/Makefile
+++ b/drivers/hwmon/Makefile
@@ -166,6 +166,7 @@ obj-$(CONFIG_SENSORS_SHT3x) += sht3x.o
obj-$(CONFIG_SENSORS_SHTC1) += shtc1.o
obj-$(CONFIG_SENSORS_SIS5595) += sis5595.o
obj-$(CONFIG_SENSORS_SMM665) += smm665.o
+obj-$(CONFIG_SENSORS_SMPMPRO) += smpmpro-hwmon.o
obj-$(CONFIG_SENSORS_SMSC47B397)+= smsc47b397.o
obj-$(CONFIG_SENSORS_SMSC47M1) += smsc47m1.o
obj-$(CONFIG_SENSORS_SMSC47M192)+= smsc47m192.o
diff --git a/drivers/hwmon/smpmpro-hwmon.c b/drivers/hwmon/smpmpro-hwmon.c
new file mode 100644
index 000000000000..37b48c42a372
--- /dev/null
+++ b/drivers/hwmon/smpmpro-hwmon.c
@@ -0,0 +1,903 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Ampere Computing SoC Hardware Monitoring Driver
+ *
+ * Copyright (c) 2019-2020, Ampere Computing LLC
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include <linux/err.h>
+#include <linux/hwmon.h>
+#include <linux/hwmon-sysfs.h>
+#include <linux/i2c.h>
+#include <linux/init.h>
+#include <linux/jiffies.h>
+#include <linux/module.h>
+#include <linux/slab.h>
+
+/* Identification Registers */
+#define REG_SPEC_VERSION_REG 0x00
+#define SCP_VERSION_REG 0x01
+#define MANUFACTURER_ID_REG 0x02
+#define DEVICE_ID_REG 0x03
+#define SCP_BUILD_ID_LO_REG 0x09
+#define SCP_BUILD_ID_HI_REG 0x0A
+
+/* Capability Registers */
+#define TEMP_SENSOR_SUPPORT_REG 0x05
+#define PWR_SENSOR_SUPPORT_REG 0x06
+#define VOLT_SENSOR_SUPPORT_REG 0x07
+#define OTHER_CAP_REG 0x08
+#define CORE_CLUSTER_CNT_REG 0x0B
+#define SYS_CACHE_PCIE_CNT_REG 0x0C
+#define SOCKET_INFO_REG 0x0D
+
+/* Logical Power Sensor Registers */
+#define SOC_TEMP_REG 0x10
+#define SOC_VRD_TEMP_REG 0x11
+#define DIMM_VRD_TEMP_REG 0x12
+#define CORE_VRD_TEMP_REG 0x13
+#define CH0_DIMM_TEMP_REG 0x14
+#define CH1_DIMM_TEMP_REG 0x15
+#define CH2_DIMM_TEMP_REG 0x16
+#define CH3_DIMM_TEMP_REG 0x17
+#define CH4_DIMM_TEMP_REG 0x18
+#define CH5_DIMM_TEMP_REG 0x19
+#define CH6_DIMM_TEMP_REG 0x1A
+#define CH7_DIMM_TEMP_REG 0x1B
+#define CORE_VRD_PWR_REG 0x20
+#define SOC_VRD_PWR_REG 0x21
+#define DIMM_VRD1_PWR_REG 0x22
+#define DIMM_VRD2_PWR_REG 0x23
+#define CORE_VRD_PWR_MW_REG 0x26
+#define SOC_VRD_PWR_MW_REG 0x27
+#define DIMM_VRD1_PWR_MW_REG 0x28
+#define DIMM_VRD2_PWR_MW_REG 0x29
+#define MEM_HOT_THRESHOLD_REG 0x32
+#define SOC_VR_HOT_THRESHOLD_REG 0x33
+#define CORE_VRD_VOLT_REG 0x34
+#define SOC_VRD_VOLT_REG 0x35
+#define DIMM_VRD1_VOLT_REG 0x36
+#define DIMM_VRD2_VOLT_REG 0x37
+#define DIMM_CE_THRESHOLD_REG 0x38
+
+/* GPI Control set Registers */
+#define GPI_CTRL0_REG 0x50
+#define GPI_CTRL1_REG 0x51
+#define GPI_CTRL2_REG 0x52
+#define GPI_CTRL3_REG 0x53
+#define GPI_CE_UE_MASK_REG 0x54
+
+/* GPI data set Registers */
+#define GPI_DATA_SET_REG 0x60
+#define GPI_DATA_SET0_REG 0x61
+#define GPI_DATA_SET1_REG 0x62
+#define GPI_DATA_SET2_REG 0x63
+#define GPI_DATA_SET3_REG 0x64
+
+/* GPI Status Registers */
+#define GPI_CLUSTER_ERR_SET0_REG 0x70
+#define GPI_CLUSTER_ERR_SEL_REG 0x71
+#define GPI_MCU_ERR_REG 0x72
+#define GPI_PCIE_ERR_REG 0x73
+#define GPI_SYS_CACHE_ERR_SEL_REG 0x74
+#define GPI_SYS_CACHE_ERR_REG 0x75
+#define GPI_PCIE_ERR_SEL_REG 0x76
+#define GPI_VRD_FAULT_ERR_REG 0x78
+#define GPI_VRD_HOT_ERR_REG 0x79
+#define GPI_DIMM_HOT_ERR_REG 0x7A
+#define GPI_BOOT_ERR1_REG 0x7B
+#define GPI_BOOT_ERR2_REG 0x7C
+
+/* GPI RAS Error Registers */
+#define GPI_WDT_STS_REG 0x7D
+#define GPI_RAS_ERR_REG 0x7E
+
+/* Core and L2C Error Registers */
+#define GPI_CORE_CLUSTER_SEL_REG 0x80
+#define GPI_CORE_L1_ERR_REG 0x81
+#define GPI_CORE_L2_ERR_REG 0x82
+#define GPI_SYS_CACHE_INST_SEL_REG 0x86
+#define GPI_SYS_CACHE_ERR_REG 0x87
+
+/* Memory Error Registers */
+#define GPI_MCU_DIMM_SELECT_REG 0x90
+#define GPI_MCU_DIMM_ERR_REG 0x91
+
+/* RAS Error/Warning Registers */
+#define GPI_RAS_ERR_SMPRO_TYPE_REG 0xA0
+#define GPI_RAS_ERR_PMPRO_TYPE_REG 0xA1
+#define GPI_RAS_ERR_SMPRO_INFO_LO_REG 0xA2
+#define GPI_RAS_ERR_SMPRO_INFO_HI_REG 0xA3
+#define GPI_RAS_ERR_SMPRO_DATA_LO_REG 0xA4
+#define GPI_RAS_ERR_SMPRO_DATA_HI_REG 0xA5
+#define GPI_RAS_WARN_SMPRO_INFO_LO_REG 0xAA
+#define GPI_RAS_WARN_SMPRO_INFO_HI_REG 0xAB
+#define GPI_RAS_ERR_PMPRO_INFO_LO_REG 0xA6
+#define GPI_RAS_ERR_PMPRO_INFO_HI_REG 0xA7
+#define GPI_RAS_ERR_PMPRO_DATA_LO_REG 0xA8
+#define GPI_RAS_ERR_PMPRO_DATA_HI_REG 0xA9
+#define GPI_RAS_WARN_PMPRO_INFO_LO_REG 0xAC
+#define GPI_RAS_WARN_PMPRO_INFO_HI_REG 0xAD
+
+/* Boot Stage/Progress Registers */
+#define GPI_BOOT_STAGE_SELECT_REG 0xB0
+#define GPI_BOOT_STAGE_STATUS_LO_REG 0xB1
+#define GPI_BOOT_STAGE_CUR_STAGE_REG 0xB2
+
+/* PCIE Error Registers */
+#define GPI_PCIE_ERR_SEL_REG 0xC0
+#define GPI_PCIE_ERR_TYPE_REG 0xC1
+#define GPI_PCIE_ERR_DEVICE_REG 0xC2
+
+/* Other Error Registers */
+#define OTHER_CE_ERR_CNT_REG 0xD0
+#define OTHER_CE_ERR_LEN_REG 0xD1
+#define OTHER_CE_ERR_DATA_REG 0xD2
+#define OTHER_UE_ERR_CNT_REG 0xD0
+#define OTHER_UE_ERR_LEN_REG 0xD1
+#define OTHER_UE_ERR_DATA_REG 0xD2
+
+/* ACPI State Registers */
+#define ACPI_SYSTEM_STATE_REG 0xE0
+#define ACPI_CPPC_CLUSTER_SEL_REG 0xE3
+#define ACPI_CPPC_CLUSTER_DATA_REG 0xE4
+#define ACPI_POWER_LIMIT_REG 0xE5
+
+
+struct smpmpro_data {
+ struct i2c_client *client;
+
+ u16 temp_support_regs;
+ u16 pwr_support_regs;
+ u16 volt_support_regs;
+ u16 other_caps;
+ u16 core_cluster_cnt_reg;
+ u16 sys_cache_pcie_cnt_reg;
+ u16 socket_info_reg;
+};
+
+static const u8 temp_regs[] = {
+ SOC_TEMP_REG,
+ SOC_VRD_TEMP_REG,
+ DIMM_VRD_TEMP_REG,
+ CORE_VRD_TEMP_REG,
+ CH0_DIMM_TEMP_REG,
+ CH1_DIMM_TEMP_REG,
+ CH2_DIMM_TEMP_REG,
+ CH3_DIMM_TEMP_REG,
+ CH4_DIMM_TEMP_REG,
+ CH5_DIMM_TEMP_REG,
+ CH6_DIMM_TEMP_REG,
+ CH7_DIMM_TEMP_REG,
+ MEM_HOT_THRESHOLD_REG,
+ SOC_VR_HOT_THRESHOLD_REG
+};
+
+static const u8 volt_regs[] = {
+ CORE_VRD_VOLT_REG,
+ SOC_VRD_VOLT_REG,
+ DIMM_VRD1_VOLT_REG,
+ DIMM_VRD2_VOLT_REG
+};
+
+enum pwr_regs {
+ PMD_VRD_PWR,
+ SOC_VRD_PWR,
+ DIMM_VRD1_PWR,
+ DIMM_VRD2_PWR,
+ CPU_VRD_PWR,
+ DIMM_VRD_PWR,
+};
+
+static const char * const label[] = {
+ "SoC",
+ "SoC VRD",
+ "DIMM VRD",
+ "DIMM VRD1",
+ "DIMM VRD2",
+ "PMD VRD",
+ "CH0 DIMM",
+ "CH1 DIMM",
+ "CH2 DIMM",
+ "CH3 DIMM",
+ "CH4 DIMM",
+ "CH5 DIMM",
+ "CH6 DIMM",
+ "CH7 DIMM",
+ "MEM HOT",
+ "SoC VR HOT",
+ "CPU VRD",
+};
+
+static const char * const gpi_label[] = {
+ "GPI CTRL 0",
+ "GPI CTRL 1",
+ "GPI CTRL 2",
+ "GPI CTRL 3",
+ "GPI CE UE MASK",
+ "GPI DATA SET",
+ "GPI DATA SET 0",
+ "GPI DATA SET 1",
+ "GPI DATA SET 2",
+ "GPI DATA SET 3",
+ "CLUSTER ERROR SET 0",
+ "CLUSTER ERROR SEL",
+ "MCU ERROR",
+ "PCIE ERROR",
+ "SYS CACHE ERR SEL",
+ "SYS CACHE ERR",
+ "PCIE ERR SEL",
+ "VRD FAULT ERR",
+ "VRD HOT ERROR",
+ "DIMM HOT ERROR",
+ "BOOT 1 ERROR",
+ "BOOT 2 ERROR",
+ "WATCHDOG STATUS",
+ "RAS INTERNAL ERROR",
+};
+
+static void smpmpro_init_device(struct i2c_client *client,
+ struct smpmpro_data *data)
+{
+ u16 ret;
+
+ ret = i2c_smbus_read_word_swapped(client, TEMP_SENSOR_SUPPORT_REG);
+ if (ret < 0)
+ return;
+ data->temp_support_regs = ret;
+
+ ret = i2c_smbus_read_word_swapped(client, PWR_SENSOR_SUPPORT_REG);
+ if (ret < 0)
+ return;
+ data->pwr_support_regs = ret;
+
+ ret = i2c_smbus_read_word_swapped(client, VOLT_SENSOR_SUPPORT_REG);
+ if (ret < 0)
+ return;
+ data->volt_support_regs = ret;
+
+ ret = i2c_smbus_read_word_swapped(client, OTHER_CAP_REG);
+ if (ret < 0)
+ return;
+ data->other_caps = ret;
+
+ ret = i2c_smbus_read_word_swapped(client, CORE_CLUSTER_CNT_REG);
+ if (ret < 0)
+ return;
+ data->core_cluster_cnt_reg = ret;
+
+ ret = i2c_smbus_read_word_swapped(client, SYS_CACHE_PCIE_CNT_REG);
+ if (ret < 0)
+ return;
+ data->sys_cache_pcie_cnt_reg = ret;
+
+ ret = i2c_smbus_read_word_swapped(client, SOCKET_INFO_REG);
+ if (ret < 0)
+ return;
+ data->socket_info_reg = ret;
+}
+
+static int smpmpro_read_temp(struct device *dev, u32 attr, int channel,
+ long *val)
+{
+ struct smpmpro_data *data = dev_get_drvdata(dev);
+ struct i2c_client *client = data->client;
+ int ret;
+
+ switch (attr) {
+ case hwmon_temp_input:
+ ret = i2c_smbus_read_word_swapped(client, temp_regs[channel]);
+ if (ret < 0)
+ return ERR_PTR(ret);
+ *val = (ret & 0x1ff) * 1000;
+ return 0;
+ default:
+ return -EOPNOTSUPP;
+ }
+}
+
+static umode_t smpmpro_temp_is_visible(const void *_data, u32 attr, int channel)
+{
+ return 0444;
+}
+
+static int smpmpro_read_in(struct device *dev, u32 attr, int channel,
+ long *val)
+{
+ struct smpmpro_data *data = dev_get_drvdata(dev);
+ struct i2c_client *client = data->client;
+ int ret;
+
+ switch (attr) {
+ case hwmon_in_input:
+ ret = i2c_smbus_read_word_swapped(client, volt_regs[channel]);
+ if (ret < 0)
+ return ERR_PTR(ret);
+ *val = ret & 0x7fff;
+ return 0;
+ default:
+ return -EOPNOTSUPP;
+ }
+}
+
+static umode_t smpmpro_in_is_visible(const void *_data, u32 attr, int channel)
+{
+ return 0444;
+}
+
+static int smpmpro_read_power(struct device *dev, u32 attr, int channel,
+ long *val)
+{
+ struct smpmpro_data *data = dev_get_drvdata(dev);
+ struct i2c_client *client = data->client;
+ int ret, ret_mw;
+ int ret2 = 0, ret2_mw = 0;
+
+ switch (attr) {
+ case hwmon_power_input:
+ switch (channel) {
+ case PMD_VRD_PWR:
+ ret = i2c_smbus_read_word_swapped(client, CORE_VRD_PWR_REG);
+ ret_mw = i2c_smbus_read_word_swapped(client, CORE_VRD_PWR_MW_REG);
+ break;
+ case SOC_VRD_PWR:
+ ret = i2c_smbus_read_word_swapped(client, SOC_VRD_PWR_REG);
+ ret_mw = i2c_smbus_read_word_swapped(client, SOC_VRD_PWR_MW_REG);
+ break;
+ case DIMM_VRD1_PWR:
+ ret = i2c_smbus_read_word_swapped(client, DIMM_VRD1_PWR_REG);
+ ret_mw = i2c_smbus_read_word_swapped(client, DIMM_VRD1_PWR_MW_REG);
+ break;
+ case DIMM_VRD2_PWR:
+ ret = i2c_smbus_read_word_swapped(client, DIMM_VRD2_PWR_REG);
+ ret_mw = i2c_smbus_read_word_swapped(client, DIMM_VRD2_PWR_MW_REG);
+ break;
+ case CPU_VRD_PWR:
+ ret = i2c_smbus_read_word_swapped(client, CORE_VRD_PWR_REG);
+ ret_mw = i2c_smbus_read_word_swapped(client, CORE_VRD_PWR_MW_REG);
+ ret2 = i2c_smbus_read_word_swapped(client, SOC_VRD_PWR_REG);
+ ret2_mw = i2c_smbus_read_word_swapped(client, SOC_VRD_PWR_MW_REG);
+ break;
+ case DIMM_VRD_PWR:
+ ret = i2c_smbus_read_word_swapped(client, DIMM_VRD1_PWR_REG);
+ ret_mw = i2c_smbus_read_word_swapped(client, DIMM_VRD1_PWR_MW_REG);
+ ret2 = i2c_smbus_read_word_swapped(client, DIMM_VRD2_PWR_REG);
+ ret2_mw = i2c_smbus_read_word_swapped(client, DIMM_VRD2_PWR_MW_REG);
+ break;
+ default:
+ return -EOPNOTSUPP;
+ }
+ if (ret < 0 || ret_mw < 0 || ret2 < 0 || ret2_mw < 0)
+ return ERR_PTR(ret < 0 ? ret : ret_mw < 0 ? ret_mw
+ : ret2 < 0 ? ret2 : ret2_mw);
+ *val = (ret + ret2)*1000000 + (ret_mw + ret2_mw)*1000;
+ return 0;
+ default:
+ return -EOPNOTSUPP;
+ }
+}
+
+static umode_t smpmpro_power_is_visible(const void *_data, u32 attr, int channel)
+{
+ return 0444;
+}
+
+
+static int smpmpro_read_gpi(struct device *dev,
+ struct device_attribute *da, char *buf)
+{
+ struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
+ struct smpmpro_data *data = dev_get_drvdata(dev);
+ struct i2c_client *client = data->client;
+ int ret;
+
+ ret = i2c_smbus_read_word_swapped(client, attr->index);
+
+ if (ret < 0)
+ return ERR_PTR(ret);
+
+ return snprintf(buf, PAGE_SIZE, "%d\n", ret);
+}
+
+static int smpmpro_read(struct device *dev, enum hwmon_sensor_types type,
+ u32 attr, int channel, long *val)
+{
+ switch (type) {
+ case hwmon_temp:
+ return smpmpro_read_temp(dev, attr, channel, val);
+ case hwmon_in:
+ return smpmpro_read_in(dev, attr, channel, val);
+ case hwmon_power:
+ return smpmpro_read_power(dev, attr, channel, val);
+// case hwmon_dimm_ce_thres:
+// return smpmpro_read_dimm_ce_thres(dev, attr, channel, val);
+ default:
+ return -EOPNOTSUPP;
+ }
+}
+
+static int smpmpro_write_gpi(struct device *dev,
+ struct device_attribute *da,
+ const char *buf, size_t count)
+{
+ struct sensor_device_attribute *attr = to_sensor_dev_attr(da);
+ struct smpmpro_data *data = dev_get_drvdata(dev);
+ struct i2c_client *client = data->client;
+ unsigned long val;
+ int ret;
+
+ ret = kstrtoul(buf, 16, &val);
+
+ ret = i2c_smbus_write_word_swapped(client, attr->index, val);
+ if (ret < 0)
+ return -EPROTO;
+
+ return count;
+}
+
+static int smpmpro_write(struct device *dev, enum hwmon_sensor_types type,
+ u32 attr, int channel, long val)
+{
+ return -EOPNOTSUPP;
+}
+
+static umode_t smpmpro_is_visible(const void *data,
+ enum hwmon_sensor_types type,
+ u32 attr, int channel)
+{
+ switch (type) {
+ case hwmon_temp:
+ return smpmpro_temp_is_visible(data, attr, channel);
+ case hwmon_in:
+ return smpmpro_in_is_visible(data, attr, channel);
+ case hwmon_power:
+ return smpmpro_power_is_visible(data, attr, channel);
+// case hwmon_dimm_ce_thres:
+// return smpmpro_dimm_ce_thres_is_visible(data, attr, channel);
+ default:
+ return 0;
+ }
+}
+
+static ssize_t show_label(struct device *dev, struct device_attribute *devattr,
+ char *buf)
+{
+ int index = to_sensor_dev_attr(devattr)->index;
+
+ return sprintf(buf, "%s\n", label[index]);
+}
+
+static ssize_t show_gpi_label(struct device *dev,
+ struct device_attribute *devattr, char *buf)
+{
+ int index = to_sensor_dev_attr(devattr)->index;
+
+ return sprintf(buf, "%s\n", gpi_label[index]);
+}
+
+static const u32 smpmpro_temp_config[] = {
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ HWMON_T_INPUT,
+ 0
+};
+
+static const struct hwmon_channel_info smpmpro_temp = {
+ .type = hwmon_temp,
+ .config = smpmpro_temp_config,
+};
+
+static const u32 smpmpro_in_config[] = {
+ HWMON_I_INPUT,
+ HWMON_I_INPUT,
+ HWMON_I_INPUT,
+ HWMON_I_INPUT,
+ 0
+};
+
+static const struct hwmon_channel_info smpmpro_in = {
+ .type = hwmon_in,
+ .config = smpmpro_in_config,
+};
+
+static const u32 smpmpro_power_config[] = {
+ HWMON_P_INPUT,
+ HWMON_P_INPUT,
+ HWMON_P_INPUT,
+ HWMON_P_INPUT,
+ HWMON_P_INPUT,
+ HWMON_P_INPUT,
+ 0
+};
+
+static const struct hwmon_channel_info smpmpro_power = {
+ .type = hwmon_power,
+ .config = smpmpro_power_config,
+};
+
+static const struct hwmon_channel_info *smpmpro_info[] = {
+ &smpmpro_temp,
+ &smpmpro_in,
+ &smpmpro_power,
+ NULL
+};
+
+static const struct hwmon_ops smpmpro_hwmon_ops = {
+ .is_visible = smpmpro_is_visible,
+ .read = smpmpro_read,
+ .write = smpmpro_write,
+};
+
+static const struct hwmon_chip_info smpmpro_chip_info = {
+ .ops = &smpmpro_hwmon_ops,
+ .info = smpmpro_info,
+};
+
+static SENSOR_DEVICE_ATTR(temp1_label, 0444, show_label, NULL, 0);
+static SENSOR_DEVICE_ATTR(temp2_label, 0444, show_label, NULL, 1);
+static SENSOR_DEVICE_ATTR(temp3_label, 0444, show_label, NULL, 2);
+static SENSOR_DEVICE_ATTR(temp4_label, 0444, show_label, NULL, 5);
+static SENSOR_DEVICE_ATTR(temp5_label, 0444, show_label, NULL, 6);
+static SENSOR_DEVICE_ATTR(temp6_label, 0444, show_label, NULL, 7);
+static SENSOR_DEVICE_ATTR(temp7_label, 0444, show_label, NULL, 8);
+static SENSOR_DEVICE_ATTR(temp8_label, 0444, show_label, NULL, 9);
+static SENSOR_DEVICE_ATTR(temp9_label, 0444, show_label, NULL, 10);
+static SENSOR_DEVICE_ATTR(temp10_label, 0444, show_label, NULL, 11);
+static SENSOR_DEVICE_ATTR(temp11_label, 0444, show_label, NULL, 12);
+static SENSOR_DEVICE_ATTR(temp12_label, 0444, show_label, NULL, 13);
+static SENSOR_DEVICE_ATTR(temp13_label, 0444, show_label, NULL, 14);
+static SENSOR_DEVICE_ATTR(temp14_label, 0444, show_label, NULL, 15);
+
+static SENSOR_DEVICE_ATTR(in0_label, 0444, show_label, NULL, 5);
+static SENSOR_DEVICE_ATTR(in1_label, 0444, show_label, NULL, 1);
+static SENSOR_DEVICE_ATTR(in2_label, 0444, show_label, NULL, 3);
+static SENSOR_DEVICE_ATTR(in3_label, 0444, show_label, NULL, 4);
+
+static SENSOR_DEVICE_ATTR(power1_label, 0444, show_label, NULL, 5);
+static SENSOR_DEVICE_ATTR(power2_label, 0444, show_label, NULL, 1);
+static SENSOR_DEVICE_ATTR(power3_label, 0444, show_label, NULL, 3);
+static SENSOR_DEVICE_ATTR(power4_label, 0444, show_label, NULL, 4);
+static SENSOR_DEVICE_ATTR(power5_label, 0444, show_label, NULL, 16);
+static SENSOR_DEVICE_ATTR(power6_label, 0444, show_label, NULL, 2);
+
+static SENSOR_DEVICE_ATTR(gpi0_label, 0444, show_gpi_label, NULL, 0);
+static SENSOR_DEVICE_ATTR(gpi0_input, 0644, smpmpro_read_gpi, smpmpro_write_gpi, GPI_CTRL0_REG);
+static SENSOR_DEVICE_ATTR(gpi1_label, 0444, show_gpi_label, NULL, 1);
+static SENSOR_DEVICE_ATTR(gpi1_input, 0644, smpmpro_read_gpi, smpmpro_write_gpi, GPI_CTRL1_REG);
+static SENSOR_DEVICE_ATTR(gpi2_label, 0444, show_gpi_label, NULL, 2);
+static SENSOR_DEVICE_ATTR(gpi2_input, 0644, smpmpro_read_gpi, smpmpro_write_gpi, GPI_CTRL2_REG);
+static SENSOR_DEVICE_ATTR(gpi3_label, 0444, show_gpi_label, NULL, 3);
+static SENSOR_DEVICE_ATTR(gpi3_input, 0644, smpmpro_read_gpi, smpmpro_write_gpi, GPI_CTRL3_REG);
+static SENSOR_DEVICE_ATTR(gpi4_label, 0444, show_gpi_label, NULL, 4);
+static SENSOR_DEVICE_ATTR(gpi4_input, 0644, smpmpro_read_gpi,
+ smpmpro_write_gpi, GPI_CE_UE_MASK_REG);
+static SENSOR_DEVICE_ATTR(gpi5_label, 0444, show_gpi_label, NULL, 5);
+static SENSOR_DEVICE_ATTR(gpi5_input, 0444, smpmpro_read_gpi, NULL, GPI_DATA_SET_REG);
+static SENSOR_DEVICE_ATTR(gpi6_label, 0444, show_gpi_label, NULL, 6);
+static SENSOR_DEVICE_ATTR(gpi6_input, 0444, smpmpro_read_gpi, NULL, GPI_DATA_SET0_REG);
+static SENSOR_DEVICE_ATTR(gpi7_label, 0444, show_gpi_label, NULL, 7);
+static SENSOR_DEVICE_ATTR(gpi7_input, 0444, smpmpro_read_gpi, NULL, GPI_DATA_SET1_REG);
+static SENSOR_DEVICE_ATTR(gpi8_label, 0444, show_gpi_label, NULL, 8);
+static SENSOR_DEVICE_ATTR(gpi8_input, 0444, smpmpro_read_gpi, NULL, GPI_DATA_SET2_REG);
+static SENSOR_DEVICE_ATTR(gpi9_label, 0444, show_gpi_label, NULL, 9);
+static SENSOR_DEVICE_ATTR(gpi9_input, 0444, smpmpro_read_gpi, NULL, GPI_DATA_SET3_REG);
+static SENSOR_DEVICE_ATTR(gpi10_label, 0444, show_gpi_label, NULL, 10);
+static SENSOR_DEVICE_ATTR(gpi10_input, 0444, smpmpro_read_gpi, NULL, GPI_CLUSTER_ERR_SET0_REG);
+static SENSOR_DEVICE_ATTR(gpi11_label, 0444, show_gpi_label, NULL, 11);
+static SENSOR_DEVICE_ATTR(gpi11_input, 0444, smpmpro_read_gpi, NULL, GPI_CLUSTER_ERR_SEL_REG);
+static SENSOR_DEVICE_ATTR(gpi12_label, 0444, show_gpi_label, NULL, 12);
+static SENSOR_DEVICE_ATTR(gpi12_input, 0444, smpmpro_read_gpi, NULL, GPI_MCU_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi13_label, 0444, show_gpi_label, NULL, 13);
+static SENSOR_DEVICE_ATTR(gpi13_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_PCIE_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi14_label, 0444, show_gpi_label, NULL, 14);
+static SENSOR_DEVICE_ATTR(gpi14_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_SYS_CACHE_ERR_SEL_REG);
+static SENSOR_DEVICE_ATTR(gpi15_label, 0444, show_gpi_label, NULL, 15);
+static SENSOR_DEVICE_ATTR(gpi15_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_SYS_CACHE_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi16_label, 0444, show_gpi_label, NULL, 16);
+static SENSOR_DEVICE_ATTR(gpi16_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_PCIE_ERR_SEL_REG);
+static SENSOR_DEVICE_ATTR(gpi17_label, 0444, show_gpi_label, NULL, 17);
+static SENSOR_DEVICE_ATTR(gpi17_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_VRD_FAULT_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi18_label, 0444, show_gpi_label, NULL, 18);
+static SENSOR_DEVICE_ATTR(gpi18_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_VRD_HOT_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi19_label, 0444, show_gpi_label, NULL, 19);
+static SENSOR_DEVICE_ATTR(gpi19_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_DIMM_HOT_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi20_label, 0444, show_gpi_label, NULL, 20);
+static SENSOR_DEVICE_ATTR(gpi20_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_BOOT_ERR1_REG);
+static SENSOR_DEVICE_ATTR(gpi21_label, 0444, show_gpi_label, NULL, 21);
+static SENSOR_DEVICE_ATTR(gpi21_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_BOOT_ERR2_REG);
+static SENSOR_DEVICE_ATTR(gpi22_label, 0444, show_gpi_label, NULL, 22);
+static SENSOR_DEVICE_ATTR(gpi22_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_WDT_STS_REG);
+static SENSOR_DEVICE_ATTR(gpi23_label, 0444, show_gpi_label, NULL, 23);
+static SENSOR_DEVICE_ATTR(gpi23_input, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_REG);
+
+static SENSOR_DEVICE_ATTR(gpi_core_cluster_sel, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_CORE_CLUSTER_SEL_REG);
+static SENSOR_DEVICE_ATTR(gpi_core_l1_err, 0444,
+ smpmpro_read_gpi, NULL, GPI_CORE_L1_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi_core_l2_err, 0444,
+ smpmpro_read_gpi, NULL, GPI_CORE_L2_ERR_REG);
+static SENSOR_DEVICE_ATTR(gpi_sys_cache_inst_sel, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_SYS_CACHE_INST_SEL_REG);
+static SENSOR_DEVICE_ATTR(gpi_sys_cache_err, 0444,
+ smpmpro_read_gpi, NULL, GPI_SYS_CACHE_ERR_REG);
+
+static SENSOR_DEVICE_ATTR(gpi_mcu_dimm_select, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_MCU_DIMM_SELECT_REG);
+static SENSOR_DEVICE_ATTR(gpi_mcu_dimm_err, 0444,
+ smpmpro_read_gpi, NULL, GPI_MCU_DIMM_ERR_REG);
+
+static SENSOR_DEVICE_ATTR(gpi_ras_err_smpro_type, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_SMPRO_TYPE_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_pmpro_type, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_PMPRO_TYPE_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_smpro_info_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_SMPRO_INFO_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_smpro_info_hi, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_SMPRO_INFO_HI_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_smpro_data_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_SMPRO_DATA_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_smpro_data_hi, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_SMPRO_DATA_HI_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_warn_smpro_info_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_WARN_SMPRO_INFO_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_warn_smpro_info_hi, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_WARN_SMPRO_INFO_HI_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_pmpro_info_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_PMPRO_INFO_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_pmpro_info_hi, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_PMPRO_INFO_HI_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_pmpro_data_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_PMPRO_DATA_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_err_pmpro_data_hi, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_ERR_PMPRO_DATA_HI_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_warn_pmpro_info_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_WARN_PMPRO_INFO_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_ras_warn_pmpro_info_hi, 0444,
+ smpmpro_read_gpi, NULL, GPI_RAS_WARN_PMPRO_INFO_HI_REG);
+
+static SENSOR_DEVICE_ATTR(gpi_boot_stage_select, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_BOOT_STAGE_SELECT_REG);
+static SENSOR_DEVICE_ATTR(gpi_boot_stage_status_lo, 0444,
+ smpmpro_read_gpi, NULL, GPI_BOOT_STAGE_STATUS_LO_REG);
+static SENSOR_DEVICE_ATTR(gpi_boot_stage_cur_stage, 0444,
+ smpmpro_read_gpi, NULL, GPI_BOOT_STAGE_CUR_STAGE_REG);
+
+static SENSOR_DEVICE_ATTR(gpi_pcie_err_sel, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_PCIE_ERR_SEL_REG);
+static SENSOR_DEVICE_ATTR(gpi_pcie_err_type, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_PCIE_ERR_TYPE_REG);
+static SENSOR_DEVICE_ATTR(gpi_pcie_err_device, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, GPI_PCIE_ERR_DEVICE_REG);
+
+static SENSOR_DEVICE_ATTR(other_ce_err_cnt, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, OTHER_CE_ERR_CNT_REG);
+static SENSOR_DEVICE_ATTR(other_ce_err_len, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, OTHER_CE_ERR_LEN_REG);
+static SENSOR_DEVICE_ATTR(other_ce_err_data, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, OTHER_CE_ERR_DATA_REG);
+static SENSOR_DEVICE_ATTR(other_ue_err_cnt, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, OTHER_UE_ERR_CNT_REG);
+static SENSOR_DEVICE_ATTR(other_ue_err_len, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, OTHER_UE_ERR_LEN_REG);
+static SENSOR_DEVICE_ATTR(other_ue_err_data, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, OTHER_UE_ERR_DATA_REG);
+
+static SENSOR_DEVICE_ATTR(acpi_system_state, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, ACPI_SYSTEM_STATE_REG);
+static SENSOR_DEVICE_ATTR(acpi_cppc_cluster_sel, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, ACPI_CPPC_CLUSTER_SEL_REG);
+static SENSOR_DEVICE_ATTR(acpi_cppc_cluster_data, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, ACPI_CPPC_CLUSTER_DATA_REG);
+static SENSOR_DEVICE_ATTR(acpi_power_limit, 0644,
+ smpmpro_read_gpi, smpmpro_write_gpi, ACPI_POWER_LIMIT_REG);
+
+static struct attribute *smpmpro_attrs[] = {
+ &sensor_dev_attr_gpi0_label.dev_attr.attr,
+ &sensor_dev_attr_gpi0_input.dev_attr.attr,
+ &sensor_dev_attr_gpi1_label.dev_attr.attr,
+ &sensor_dev_attr_gpi1_input.dev_attr.attr,
+ &sensor_dev_attr_gpi2_label.dev_attr.attr,
+ &sensor_dev_attr_gpi2_input.dev_attr.attr,
+ &sensor_dev_attr_gpi3_label.dev_attr.attr,
+ &sensor_dev_attr_gpi3_input.dev_attr.attr,
+ &sensor_dev_attr_gpi4_label.dev_attr.attr,
+ &sensor_dev_attr_gpi4_input.dev_attr.attr,
+ &sensor_dev_attr_gpi5_label.dev_attr.attr,
+ &sensor_dev_attr_gpi5_input.dev_attr.attr,
+ &sensor_dev_attr_gpi6_label.dev_attr.attr,
+ &sensor_dev_attr_gpi6_input.dev_attr.attr,
+ &sensor_dev_attr_gpi7_label.dev_attr.attr,
+ &sensor_dev_attr_gpi7_input.dev_attr.attr,
+ &sensor_dev_attr_gpi8_label.dev_attr.attr,
+ &sensor_dev_attr_gpi8_input.dev_attr.attr,
+ &sensor_dev_attr_gpi9_label.dev_attr.attr,
+ &sensor_dev_attr_gpi9_input.dev_attr.attr,
+ &sensor_dev_attr_gpi10_label.dev_attr.attr,
+ &sensor_dev_attr_gpi10_input.dev_attr.attr,
+ &sensor_dev_attr_gpi11_label.dev_attr.attr,
+ &sensor_dev_attr_gpi11_input.dev_attr.attr,
+ &sensor_dev_attr_gpi12_label.dev_attr.attr,
+ &sensor_dev_attr_gpi12_input.dev_attr.attr,
+ &sensor_dev_attr_gpi13_label.dev_attr.attr,
+ &sensor_dev_attr_gpi13_input.dev_attr.attr,
+ &sensor_dev_attr_gpi14_label.dev_attr.attr,
+ &sensor_dev_attr_gpi14_input.dev_attr.attr,
+ &sensor_dev_attr_gpi15_label.dev_attr.attr,
+ &sensor_dev_attr_gpi15_input.dev_attr.attr,
+ &sensor_dev_attr_gpi16_label.dev_attr.attr,
+ &sensor_dev_attr_gpi16_input.dev_attr.attr,
+ &sensor_dev_attr_gpi17_label.dev_attr.attr,
+ &sensor_dev_attr_gpi17_input.dev_attr.attr,
+ &sensor_dev_attr_gpi18_label.dev_attr.attr,
+ &sensor_dev_attr_gpi18_input.dev_attr.attr,
+ &sensor_dev_attr_gpi19_label.dev_attr.attr,
+ &sensor_dev_attr_gpi19_input.dev_attr.attr,
+ &sensor_dev_attr_gpi20_label.dev_attr.attr,
+ &sensor_dev_attr_gpi20_input.dev_attr.attr,
+ &sensor_dev_attr_gpi21_label.dev_attr.attr,
+ &sensor_dev_attr_gpi21_input.dev_attr.attr,
+ &sensor_dev_attr_gpi22_label.dev_attr.attr,
+ &sensor_dev_attr_gpi22_input.dev_attr.attr,
+ &sensor_dev_attr_gpi23_label.dev_attr.attr,
+ &sensor_dev_attr_gpi23_input.dev_attr.attr,
+
+ &sensor_dev_attr_temp1_label.dev_attr.attr,
+ &sensor_dev_attr_temp2_label.dev_attr.attr,
+ &sensor_dev_attr_temp3_label.dev_attr.attr,
+ &sensor_dev_attr_temp4_label.dev_attr.attr,
+ &sensor_dev_attr_temp5_label.dev_attr.attr,
+ &sensor_dev_attr_temp6_label.dev_attr.attr,
+ &sensor_dev_attr_temp7_label.dev_attr.attr,
+ &sensor_dev_attr_temp8_label.dev_attr.attr,
+ &sensor_dev_attr_temp9_label.dev_attr.attr,
+ &sensor_dev_attr_temp10_label.dev_attr.attr,
+ &sensor_dev_attr_temp11_label.dev_attr.attr,
+ &sensor_dev_attr_temp12_label.dev_attr.attr,
+ &sensor_dev_attr_temp13_label.dev_attr.attr,
+ &sensor_dev_attr_temp14_label.dev_attr.attr,
+
+ &sensor_dev_attr_in0_label.dev_attr.attr,
+ &sensor_dev_attr_in1_label.dev_attr.attr,
+ &sensor_dev_attr_in2_label.dev_attr.attr,
+ &sensor_dev_attr_in3_label.dev_attr.attr,
+
+ &sensor_dev_attr_power1_label.dev_attr.attr,
+ &sensor_dev_attr_power2_label.dev_attr.attr,
+ &sensor_dev_attr_power3_label.dev_attr.attr,
+ &sensor_dev_attr_power4_label.dev_attr.attr,
+ &sensor_dev_attr_power5_label.dev_attr.attr,
+ &sensor_dev_attr_power6_label.dev_attr.attr,
+
+ &sensor_dev_attr_gpi_core_cluster_sel.dev_attr.attr,
+ &sensor_dev_attr_gpi_core_l1_err.dev_attr.attr,
+ &sensor_dev_attr_gpi_core_l2_err.dev_attr.attr,
+ &sensor_dev_attr_gpi_sys_cache_inst_sel.dev_attr.attr,
+ &sensor_dev_attr_gpi_sys_cache_err.dev_attr.attr,
+
+ &sensor_dev_attr_gpi_mcu_dimm_select.dev_attr.attr,
+ &sensor_dev_attr_gpi_mcu_dimm_err.dev_attr.attr,
+
+ &sensor_dev_attr_gpi_ras_err_smpro_type.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_pmpro_type.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_smpro_info_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_smpro_info_hi.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_smpro_data_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_smpro_data_hi.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_warn_smpro_info_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_warn_smpro_info_hi.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_pmpro_info_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_pmpro_info_hi.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_pmpro_data_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_err_pmpro_data_hi.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_warn_pmpro_info_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_ras_warn_pmpro_info_hi.dev_attr.attr,
+
+ &sensor_dev_attr_gpi_boot_stage_select.dev_attr.attr,
+ &sensor_dev_attr_gpi_boot_stage_status_lo.dev_attr.attr,
+ &sensor_dev_attr_gpi_boot_stage_cur_stage.dev_attr.attr,
+
+ &sensor_dev_attr_gpi_pcie_err_sel.dev_attr.attr,
+ &sensor_dev_attr_gpi_pcie_err_type.dev_attr.attr,
+ &sensor_dev_attr_gpi_pcie_err_device.dev_attr.attr,
+
+ &sensor_dev_attr_other_ce_err_cnt.dev_attr.attr,
+ &sensor_dev_attr_other_ce_err_len.dev_attr.attr,
+ &sensor_dev_attr_other_ce_err_data.dev_attr.attr,
+ &sensor_dev_attr_other_ue_err_cnt.dev_attr.attr,
+ &sensor_dev_attr_other_ue_err_len.dev_attr.attr,
+ &sensor_dev_attr_other_ue_err_data.dev_attr.attr,
+
+ &sensor_dev_attr_acpi_system_state.dev_attr.attr,
+ &sensor_dev_attr_acpi_cppc_cluster_sel.dev_attr.attr,
+ &sensor_dev_attr_acpi_cppc_cluster_data.dev_attr.attr,
+ &sensor_dev_attr_acpi_power_limit.dev_attr.attr,
+
+ NULL
+};
+ATTRIBUTE_GROUPS(smpmpro);
+
+static int smpmpro_i2c_probe(struct i2c_client *client,
+ const struct i2c_device_id *id)
+{
+ struct i2c_adapter *adapter = client->adapter;
+ struct device *dev = &client->dev;
+ struct smpmpro_data *data;
+ struct device *hwmon_dev;
+
+ if (!i2c_check_functionality(adapter,
+ I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA))
+ return -ENODEV;
+
+ data = devm_kzalloc(dev, sizeof(struct smpmpro_data), GFP_KERNEL);
+ if (!data)
+ return -ENOMEM;
+
+ data->client = client;
+
+ /* Initialize the Altra SMPMPro chip */
+ smpmpro_init_device(client, data);
+
+ hwmon_dev = devm_hwmon_device_register_with_info(dev, client->name,
+ data,
+ &smpmpro_chip_info,
+ smpmpro_groups);
+ return PTR_ERR_OR_ZERO(hwmon_dev);
+}
+
+static const struct i2c_device_id smpmpro_i2c_id[] = {
+ { "smpmpro", 0 },
+ { }
+};
+MODULE_DEVICE_TABLE(i2c, smpmpro_i2c_id);
+
+static struct i2c_driver smpmpro_driver = {
+ .class = I2C_CLASS_HWMON,
+ .probe = smpmpro_i2c_probe,
+ .driver = {
+ .name = "smpmpro",
+ },
+ .id_table = smpmpro_i2c_id,
+};
+
+module_i2c_driver(smpmpro_driver);
+
+MODULE_AUTHOR("Thinh Pham <thinh.pham at amperecomputing.com>");
+MODULE_AUTHOR("Dien Nguyen <dinguyen at amperecomputing.com>");
+MODULE_AUTHOR("Hoang Nguyen <hnguyen at amperecomputing.com>");
+MODULE_DESCRIPTION("Altra SMPMPro driver");
+MODULE_LICENSE("GPL");
--
2.17.1
More information about the openbmc
mailing list