diff options
author | Guenter Roeck <linux@roeck-us.net> | 2012-02-24 06:40:53 -0500 |
---|---|---|
committer | Guenter Roeck <guenter.roeck@ericsson.com> | 2012-03-18 21:27:52 -0400 |
commit | 927112696654f4c96a85aa8a494866cbc6ccfbe6 (patch) | |
tree | 0c27c60740018af7640627663b3f0f19339ae3b2 /drivers/hwmon | |
parent | 590defe59ef9596dcd892d2d8395d730c510323d (diff) |
hwmon: (adm1275) Add support for ADM1075
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
Diffstat (limited to 'drivers/hwmon')
-rw-r--r-- | drivers/hwmon/pmbus/Kconfig | 4 | ||||
-rw-r--r-- | drivers/hwmon/pmbus/adm1275.c | 88 |
2 files changed, 86 insertions, 6 deletions
diff --git a/drivers/hwmon/pmbus/Kconfig b/drivers/hwmon/pmbus/Kconfig index 1f0d0110b6b8..9246d0154f74 100644 --- a/drivers/hwmon/pmbus/Kconfig +++ b/drivers/hwmon/pmbus/Kconfig | |||
@@ -31,8 +31,8 @@ config SENSORS_ADM1275 | |||
31 | default n | 31 | default n |
32 | help | 32 | help |
33 | If you say yes here you get hardware monitoring support for Analog | 33 | If you say yes here you get hardware monitoring support for Analog |
34 | Devices ADM1275 and ADM1276 Hot-Swap Controller and Digital Power | 34 | Devices ADM1075, ADM1275, and ADM1276 Hot-Swap Controller and Digital |
35 | Monitor. | 35 | Power Monitors. |
36 | 36 | ||
37 | This driver can also be built as a module. If so, the module will | 37 | This driver can also be built as a module. If so, the module will |
38 | be called adm1275. | 38 | be called adm1275. |
diff --git a/drivers/hwmon/pmbus/adm1275.c b/drivers/hwmon/pmbus/adm1275.c index 5e4421e57eb0..60aad9570f01 100644 --- a/drivers/hwmon/pmbus/adm1275.c +++ b/drivers/hwmon/pmbus/adm1275.c | |||
@@ -23,7 +23,7 @@ | |||
23 | #include <linux/i2c.h> | 23 | #include <linux/i2c.h> |
24 | #include "pmbus.h" | 24 | #include "pmbus.h" |
25 | 25 | ||
26 | enum chips { adm1275, adm1276 }; | 26 | enum chips { adm1075, adm1275, adm1276 }; |
27 | 27 | ||
28 | #define ADM1275_PEAK_IOUT 0xd0 | 28 | #define ADM1275_PEAK_IOUT 0xd0 |
29 | #define ADM1275_PEAK_VIN 0xd1 | 29 | #define ADM1275_PEAK_VIN 0xd1 |
@@ -32,6 +32,9 @@ enum chips { adm1275, adm1276 }; | |||
32 | 32 | ||
33 | #define ADM1275_VIN_VOUT_SELECT (1 << 6) | 33 | #define ADM1275_VIN_VOUT_SELECT (1 << 6) |
34 | #define ADM1275_VRANGE (1 << 5) | 34 | #define ADM1275_VRANGE (1 << 5) |
35 | #define ADM1075_IRANGE_50 (1 << 4) | ||
36 | #define ADM1075_IRANGE_25 (1 << 3) | ||
37 | #define ADM1075_IRANGE_MASK ((1 << 3) | (1 << 4)) | ||
35 | 38 | ||
36 | #define ADM1275_IOUT_WARN2_LIMIT 0xd7 | 39 | #define ADM1275_IOUT_WARN2_LIMIT 0xd7 |
37 | #define ADM1275_DEVICE_CONFIG 0xd8 | 40 | #define ADM1275_DEVICE_CONFIG 0xd8 |
@@ -42,6 +45,14 @@ enum chips { adm1275, adm1276 }; | |||
42 | 45 | ||
43 | #define ADM1275_MFR_STATUS_IOUT_WARN2 (1 << 0) | 46 | #define ADM1275_MFR_STATUS_IOUT_WARN2 (1 << 0) |
44 | 47 | ||
48 | #define ADM1075_READ_VAUX 0xdd | ||
49 | #define ADM1075_VAUX_OV_WARN_LIMIT 0xde | ||
50 | #define ADM1075_VAUX_UV_WARN_LIMIT 0xdf | ||
51 | #define ADM1075_VAUX_STATUS 0xf6 | ||
52 | |||
53 | #define ADM1075_VAUX_OV_WARN (1<<7) | ||
54 | #define ADM1075_VAUX_UV_WARN (1<<6) | ||
55 | |||
45 | struct adm1275_data { | 56 | struct adm1275_data { |
46 | int id; | 57 | int id; |
47 | bool have_oc_fault; | 58 | bool have_oc_fault; |
@@ -74,6 +85,29 @@ static int adm1275_read_word_data(struct i2c_client *client, int page, int reg) | |||
74 | } | 85 | } |
75 | ret = pmbus_read_word_data(client, 0, ADM1275_IOUT_WARN2_LIMIT); | 86 | ret = pmbus_read_word_data(client, 0, ADM1275_IOUT_WARN2_LIMIT); |
76 | break; | 87 | break; |
88 | case PMBUS_VOUT_OV_WARN_LIMIT: | ||
89 | if (data->id != adm1075) { | ||
90 | ret = -ENODATA; | ||
91 | break; | ||
92 | } | ||
93 | ret = pmbus_read_word_data(client, 0, | ||
94 | ADM1075_VAUX_OV_WARN_LIMIT); | ||
95 | break; | ||
96 | case PMBUS_VOUT_UV_WARN_LIMIT: | ||
97 | if (data->id != adm1075) { | ||
98 | ret = -ENODATA; | ||
99 | break; | ||
100 | } | ||
101 | ret = pmbus_read_word_data(client, 0, | ||
102 | ADM1075_VAUX_UV_WARN_LIMIT); | ||
103 | break; | ||
104 | case PMBUS_READ_VOUT: | ||
105 | if (data->id != adm1075) { | ||
106 | ret = -ENODATA; | ||
107 | break; | ||
108 | } | ||
109 | ret = pmbus_read_word_data(client, 0, ADM1075_READ_VAUX); | ||
110 | break; | ||
77 | case PMBUS_VIRT_READ_IOUT_MAX: | 111 | case PMBUS_VIRT_READ_IOUT_MAX: |
78 | ret = pmbus_read_word_data(client, 0, ADM1275_PEAK_IOUT); | 112 | ret = pmbus_read_word_data(client, 0, ADM1275_PEAK_IOUT); |
79 | break; | 113 | break; |
@@ -84,7 +118,7 @@ static int adm1275_read_word_data(struct i2c_client *client, int page, int reg) | |||
84 | ret = pmbus_read_word_data(client, 0, ADM1275_PEAK_VIN); | 118 | ret = pmbus_read_word_data(client, 0, ADM1275_PEAK_VIN); |
85 | break; | 119 | break; |
86 | case PMBUS_VIRT_READ_PIN_MAX: | 120 | case PMBUS_VIRT_READ_PIN_MAX: |
87 | if (data->id != adm1276) { | 121 | if (data->id == adm1275) { |
88 | ret = -ENXIO; | 122 | ret = -ENXIO; |
89 | break; | 123 | break; |
90 | } | 124 | } |
@@ -95,7 +129,7 @@ static int adm1275_read_word_data(struct i2c_client *client, int page, int reg) | |||
95 | case PMBUS_VIRT_RESET_VIN_HISTORY: | 129 | case PMBUS_VIRT_RESET_VIN_HISTORY: |
96 | break; | 130 | break; |
97 | case PMBUS_VIRT_RESET_PIN_HISTORY: | 131 | case PMBUS_VIRT_RESET_PIN_HISTORY: |
98 | if (data->id != adm1276) | 132 | if (data->id == adm1275) |
99 | ret = -ENXIO; | 133 | ret = -ENXIO; |
100 | break; | 134 | break; |
101 | default: | 135 | default: |
@@ -163,6 +197,19 @@ static int adm1275_read_byte_data(struct i2c_client *client, int page, int reg) | |||
163 | PB_IOUT_OC_FAULT : PB_IOUT_UC_FAULT; | 197 | PB_IOUT_OC_FAULT : PB_IOUT_UC_FAULT; |
164 | } | 198 | } |
165 | break; | 199 | break; |
200 | case PMBUS_STATUS_VOUT: | ||
201 | if (data->id != adm1075) { | ||
202 | ret = -ENODATA; | ||
203 | break; | ||
204 | } | ||
205 | ret = 0; | ||
206 | mfr_status = pmbus_read_byte_data(client, 0, | ||
207 | ADM1075_VAUX_STATUS); | ||
208 | if (mfr_status & ADM1075_VAUX_OV_WARN) | ||
209 | ret |= PB_VOLTAGE_OV_WARNING; | ||
210 | if (mfr_status & ADM1075_VAUX_UV_WARN) | ||
211 | ret |= PB_VOLTAGE_UV_WARNING; | ||
212 | break; | ||
166 | default: | 213 | default: |
167 | ret = -ENODATA; | 214 | ret = -ENODATA; |
168 | break; | 215 | break; |
@@ -171,6 +218,7 @@ static int adm1275_read_byte_data(struct i2c_client *client, int page, int reg) | |||
171 | } | 218 | } |
172 | 219 | ||
173 | static const struct i2c_device_id adm1275_id[] = { | 220 | static const struct i2c_device_id adm1275_id[] = { |
221 | { "adm1075", adm1075 }, | ||
174 | { "adm1275", adm1275 }, | 222 | { "adm1275", adm1275 }, |
175 | { "adm1276", adm1276 }, | 223 | { "adm1276", adm1276 }, |
176 | { } | 224 | { } |
@@ -251,7 +299,14 @@ static int adm1275_probe(struct i2c_client *client, | |||
251 | info->read_byte_data = adm1275_read_byte_data; | 299 | info->read_byte_data = adm1275_read_byte_data; |
252 | info->write_word_data = adm1275_write_word_data; | 300 | info->write_word_data = adm1275_write_word_data; |
253 | 301 | ||
254 | if (config & ADM1275_VRANGE) { | 302 | if (data->id == adm1075) { |
303 | info->m[PSC_VOLTAGE_IN] = 27169; | ||
304 | info->b[PSC_VOLTAGE_IN] = 0; | ||
305 | info->R[PSC_VOLTAGE_IN] = -1; | ||
306 | info->m[PSC_VOLTAGE_OUT] = 27169; | ||
307 | info->b[PSC_VOLTAGE_OUT] = 0; | ||
308 | info->R[PSC_VOLTAGE_OUT] = -1; | ||
309 | } else if (config & ADM1275_VRANGE) { | ||
255 | info->m[PSC_VOLTAGE_IN] = 19199; | 310 | info->m[PSC_VOLTAGE_IN] = 19199; |
256 | info->b[PSC_VOLTAGE_IN] = 0; | 311 | info->b[PSC_VOLTAGE_IN] = 0; |
257 | info->R[PSC_VOLTAGE_IN] = -2; | 312 | info->R[PSC_VOLTAGE_IN] = -2; |
@@ -271,6 +326,31 @@ static int adm1275_probe(struct i2c_client *client, | |||
271 | data->have_oc_fault = true; | 326 | data->have_oc_fault = true; |
272 | 327 | ||
273 | switch (data->id) { | 328 | switch (data->id) { |
329 | case adm1075: | ||
330 | info->format[PSC_POWER] = direct; | ||
331 | info->b[PSC_POWER] = 0; | ||
332 | info->R[PSC_POWER] = -1; | ||
333 | switch (config & ADM1075_IRANGE_MASK) { | ||
334 | case ADM1075_IRANGE_25: | ||
335 | info->m[PSC_POWER] = 8549; | ||
336 | info->m[PSC_CURRENT_OUT] = 806; | ||
337 | break; | ||
338 | case ADM1075_IRANGE_50: | ||
339 | info->m[PSC_POWER] = 4279; | ||
340 | info->m[PSC_CURRENT_OUT] = 404; | ||
341 | break; | ||
342 | default: | ||
343 | dev_err(&client->dev, "Invalid input current range"); | ||
344 | info->m[PSC_POWER] = 0; | ||
345 | info->m[PSC_CURRENT_OUT] = 0; | ||
346 | break; | ||
347 | } | ||
348 | info->func[0] |= PMBUS_HAVE_VIN | PMBUS_HAVE_PIN | ||
349 | | PMBUS_HAVE_STATUS_INPUT; | ||
350 | if (config & ADM1275_VIN_VOUT_SELECT) | ||
351 | info->func[0] |= | ||
352 | PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT; | ||
353 | break; | ||
274 | case adm1275: | 354 | case adm1275: |
275 | if (config & ADM1275_VIN_VOUT_SELECT) | 355 | if (config & ADM1275_VIN_VOUT_SELECT) |
276 | info->func[0] |= | 356 | info->func[0] |= |