Linux Audio

Check our new training course

Loading...
v3.1
 
  1/*
  2 * Hardware monitoring driver for Maxim MAX34440/MAX34441
  3 *
  4 * Copyright (c) 2011 Ericsson AB.
  5 *
  6 * This program is free software; you can redistribute it and/or modify
  7 * it under the terms of the GNU General Public License as published by
  8 * the Free Software Foundation; either version 2 of the License, or
  9 * (at your option) any later version.
 10 *
 11 * This program is distributed in the hope that it will be useful,
 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 14 * GNU General Public License for more details.
 15 *
 16 * You should have received a copy of the GNU General Public License
 17 * along with this program; if not, write to the Free Software
 18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 19 */
 20
 
 21#include <linux/kernel.h>
 22#include <linux/module.h>
 23#include <linux/init.h>
 24#include <linux/err.h>
 25#include <linux/i2c.h>
 26#include "pmbus.h"
 27
 28enum chips { max34440, max34441 };
 29
 30#define MAX34440_MFR_VOUT_PEAK		0xd4
 31#define MAX34440_MFR_IOUT_PEAK		0xd5
 32#define MAX34440_MFR_TEMPERATURE_PEAK	0xd6
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 33
 34#define MAX34440_STATUS_OC_WARN		(1 << 0)
 35#define MAX34440_STATUS_OC_FAULT	(1 << 1)
 36#define MAX34440_STATUS_OT_FAULT	(1 << 5)
 37#define MAX34440_STATUS_OT_WARN		(1 << 6)
 38
 39static int max34440_read_word_data(struct i2c_client *client, int page, int reg)
 
 
 
 
 
 
 
 
 
 
 40{
 41	int ret;
 
 
 42
 43	switch (reg) {
 
 
 
 
 
 
 
 
 
 
 
 
 44	case PMBUS_VIRT_READ_VOUT_MAX:
 45		ret = pmbus_read_word_data(client, page,
 46					   MAX34440_MFR_VOUT_PEAK);
 47		break;
 
 
 
 
 
 
 48	case PMBUS_VIRT_READ_IOUT_MAX:
 49		ret = pmbus_read_word_data(client, page,
 50					   MAX34440_MFR_IOUT_PEAK);
 51		break;
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 52	case PMBUS_VIRT_READ_TEMP_MAX:
 53		ret = pmbus_read_word_data(client, page,
 54					   MAX34440_MFR_TEMPERATURE_PEAK);
 55		break;
 
 
 
 
 
 56	case PMBUS_VIRT_RESET_VOUT_HISTORY:
 57	case PMBUS_VIRT_RESET_IOUT_HISTORY:
 58	case PMBUS_VIRT_RESET_TEMP_HISTORY:
 59		ret = 0;
 60		break;
 61	default:
 62		ret = -ENODATA;
 63		break;
 64	}
 65	return ret;
 66}
 67
 68static int max34440_write_word_data(struct i2c_client *client, int page,
 69				    int reg, u16 word)
 70{
 
 
 71	int ret;
 72
 73	switch (reg) {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 74	case PMBUS_VIRT_RESET_VOUT_HISTORY:
 75		ret = pmbus_write_word_data(client, page,
 
 
 
 
 76					    MAX34440_MFR_VOUT_PEAK, 0);
 77		break;
 78	case PMBUS_VIRT_RESET_IOUT_HISTORY:
 79		ret = pmbus_write_word_data(client, page,
 80					    MAX34440_MFR_IOUT_PEAK, 0);
 
 
 
 
 81		break;
 82	case PMBUS_VIRT_RESET_TEMP_HISTORY:
 83		ret = pmbus_write_word_data(client, page,
 84					    MAX34440_MFR_TEMPERATURE_PEAK,
 85					    0xffff);
 
 
 
 86		break;
 87	default:
 88		ret = -ENODATA;
 89		break;
 90	}
 91	return ret;
 92}
 93
 94static int max34440_read_byte_data(struct i2c_client *client, int page, int reg)
 95{
 96	int ret;
 97	int mfg_status;
 98
 99	ret = pmbus_set_page(client, page);
100	if (ret < 0)
101		return ret;
 
 
102
103	switch (reg) {
104	case PMBUS_STATUS_IOUT:
105		mfg_status = pmbus_read_word_data(client, 0,
106						  PMBUS_STATUS_MFR_SPECIFIC);
107		if (mfg_status < 0)
108			return mfg_status;
109		if (mfg_status & MAX34440_STATUS_OC_WARN)
110			ret |= PB_IOUT_OC_WARNING;
111		if (mfg_status & MAX34440_STATUS_OC_FAULT)
112			ret |= PB_IOUT_OC_FAULT;
113		break;
114	case PMBUS_STATUS_TEMPERATURE:
115		mfg_status = pmbus_read_word_data(client, 0,
116						  PMBUS_STATUS_MFR_SPECIFIC);
117		if (mfg_status < 0)
118			return mfg_status;
119		if (mfg_status & MAX34440_STATUS_OT_WARN)
120			ret |= PB_TEMP_OT_WARNING;
121		if (mfg_status & MAX34440_STATUS_OT_FAULT)
122			ret |= PB_TEMP_OT_FAULT;
123		break;
124	default:
125		ret = -ENODATA;
126		break;
127	}
128	return ret;
129}
130
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
131static struct pmbus_driver_info max34440_info[] = {
132	[max34440] = {
133		.pages = 14,
134		.format[PSC_VOLTAGE_IN] = direct,
135		.format[PSC_VOLTAGE_OUT] = direct,
136		.format[PSC_TEMPERATURE] = direct,
137		.format[PSC_CURRENT_OUT] = direct,
138		.m[PSC_VOLTAGE_IN] = 1,
139		.b[PSC_VOLTAGE_IN] = 0,
140		.R[PSC_VOLTAGE_IN] = 3,	    /* R = 0 in datasheet reflects mV */
141		.m[PSC_VOLTAGE_OUT] = 1,
142		.b[PSC_VOLTAGE_OUT] = 0,
143		.R[PSC_VOLTAGE_OUT] = 3,    /* R = 0 in datasheet reflects mV */
144		.m[PSC_CURRENT_OUT] = 1,
145		.b[PSC_CURRENT_OUT] = 0,
146		.R[PSC_CURRENT_OUT] = 3,    /* R = 0 in datasheet reflects mA */
147		.m[PSC_TEMPERATURE] = 1,
148		.b[PSC_TEMPERATURE] = 0,
149		.R[PSC_TEMPERATURE] = 2,
150		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
151		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
152		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
153		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
154		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
155		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
156		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
157		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
158		.func[4] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
159		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
160		.func[5] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
161		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
162		.func[6] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
163		.func[7] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
164		.func[8] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
165		.func[9] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
166		.func[10] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
167		.func[11] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
168		.func[12] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
169		.func[13] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
170		.read_byte_data = max34440_read_byte_data,
171		.read_word_data = max34440_read_word_data,
172		.write_word_data = max34440_write_word_data,
173	},
174	[max34441] = {
175		.pages = 12,
176		.format[PSC_VOLTAGE_IN] = direct,
177		.format[PSC_VOLTAGE_OUT] = direct,
178		.format[PSC_TEMPERATURE] = direct,
179		.format[PSC_CURRENT_OUT] = direct,
180		.format[PSC_FAN] = direct,
181		.m[PSC_VOLTAGE_IN] = 1,
182		.b[PSC_VOLTAGE_IN] = 0,
183		.R[PSC_VOLTAGE_IN] = 3,
184		.m[PSC_VOLTAGE_OUT] = 1,
185		.b[PSC_VOLTAGE_OUT] = 0,
186		.R[PSC_VOLTAGE_OUT] = 3,
187		.m[PSC_CURRENT_OUT] = 1,
188		.b[PSC_CURRENT_OUT] = 0,
189		.R[PSC_CURRENT_OUT] = 3,
190		.m[PSC_TEMPERATURE] = 1,
191		.b[PSC_TEMPERATURE] = 0,
192		.R[PSC_TEMPERATURE] = 2,
193		.m[PSC_FAN] = 1,
194		.b[PSC_FAN] = 0,
195		.R[PSC_FAN] = 0,
196		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
197		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
198		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
199		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
200		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
201		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
202		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
203		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
204		.func[4] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
205		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
206		.func[5] = PMBUS_HAVE_FAN12 | PMBUS_HAVE_STATUS_FAN12,
207		.func[6] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
208		.func[7] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
209		.func[8] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
210		.func[9] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
211		.func[10] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
212		.func[11] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
213		.read_byte_data = max34440_read_byte_data,
214		.read_word_data = max34440_read_word_data,
215		.write_word_data = max34440_write_word_data,
216	},
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
217};
218
219static int max34440_probe(struct i2c_client *client,
220			  const struct i2c_device_id *id)
221{
222	return pmbus_do_probe(client, id, &max34440_info[id->driver_data]);
223}
224
225static int max34440_remove(struct i2c_client *client)
226{
227	return pmbus_do_remove(client);
 
 
 
 
 
 
 
 
 
 
 
228}
229
230static const struct i2c_device_id max34440_id[] = {
231	{"max34440", max34440},
232	{"max34441", max34441},
 
 
 
 
233	{}
234};
235
236MODULE_DEVICE_TABLE(i2c, max34440_id);
237
238/* This is the driver that will be inserted */
239static struct i2c_driver max34440_driver = {
240	.driver = {
241		   .name = "max34440",
242		   },
243	.probe = max34440_probe,
244	.remove = max34440_remove,
245	.id_table = max34440_id,
246};
247
248static int __init max34440_init(void)
249{
250	return i2c_add_driver(&max34440_driver);
251}
252
253static void __exit max34440_exit(void)
254{
255	i2c_del_driver(&max34440_driver);
256}
257
258MODULE_AUTHOR("Guenter Roeck");
259MODULE_DESCRIPTION("PMBus driver for Maxim MAX34440/MAX34441");
260MODULE_LICENSE("GPL");
261module_init(max34440_init);
262module_exit(max34440_exit);
v6.8
  1// SPDX-License-Identifier: GPL-2.0-or-later
  2/*
  3 * Hardware monitoring driver for Maxim MAX34440/MAX34441
  4 *
  5 * Copyright (c) 2011 Ericsson AB.
  6 * Copyright (c) 2012 Guenter Roeck
 
 
 
 
 
 
 
 
 
 
 
 
 
  7 */
  8
  9#include <linux/bitops.h>
 10#include <linux/kernel.h>
 11#include <linux/module.h>
 12#include <linux/init.h>
 13#include <linux/err.h>
 14#include <linux/i2c.h>
 15#include "pmbus.h"
 16
 17enum chips { max34440, max34441, max34446, max34451, max34460, max34461 };
 18
 19#define MAX34440_MFR_VOUT_PEAK		0xd4
 20#define MAX34440_MFR_IOUT_PEAK		0xd5
 21#define MAX34440_MFR_TEMPERATURE_PEAK	0xd6
 22#define MAX34440_MFR_VOUT_MIN		0xd7
 23
 24#define MAX34446_MFR_POUT_PEAK		0xe0
 25#define MAX34446_MFR_POUT_AVG		0xe1
 26#define MAX34446_MFR_IOUT_AVG		0xe2
 27#define MAX34446_MFR_TEMPERATURE_AVG	0xe3
 28
 29#define MAX34440_STATUS_OC_WARN		BIT(0)
 30#define MAX34440_STATUS_OC_FAULT	BIT(1)
 31#define MAX34440_STATUS_OT_FAULT	BIT(5)
 32#define MAX34440_STATUS_OT_WARN		BIT(6)
 33
 34/*
 35 * The whole max344* family have IOUT_OC_WARN_LIMIT and IOUT_OC_FAULT_LIMIT
 36 * swapped from the standard pmbus spec addresses.
 37 */
 38#define MAX34440_IOUT_OC_WARN_LIMIT	0x46
 39#define MAX34440_IOUT_OC_FAULT_LIMIT	0x4A
 40
 41#define MAX34451_MFR_CHANNEL_CONFIG	0xe4
 42#define MAX34451_MFR_CHANNEL_CONFIG_SEL_MASK	0x3f
 
 
 43
 44struct max34440_data {
 45	int id;
 46	struct pmbus_driver_info info;
 47};
 48
 49#define to_max34440_data(x)  container_of(x, struct max34440_data, info)
 50
 51static const struct i2c_device_id max34440_id[];
 52
 53static int max34440_read_word_data(struct i2c_client *client, int page,
 54				   int phase, int reg)
 55{
 56	int ret;
 57	const struct pmbus_driver_info *info = pmbus_get_driver_info(client);
 58	const struct max34440_data *data = to_max34440_data(info);
 59
 60	switch (reg) {
 61	case PMBUS_IOUT_OC_FAULT_LIMIT:
 62		ret = pmbus_read_word_data(client, page, phase,
 63					   MAX34440_IOUT_OC_FAULT_LIMIT);
 64		break;
 65	case PMBUS_IOUT_OC_WARN_LIMIT:
 66		ret = pmbus_read_word_data(client, page, phase,
 67					   MAX34440_IOUT_OC_WARN_LIMIT);
 68		break;
 69	case PMBUS_VIRT_READ_VOUT_MIN:
 70		ret = pmbus_read_word_data(client, page, phase,
 71					   MAX34440_MFR_VOUT_MIN);
 72		break;
 73	case PMBUS_VIRT_READ_VOUT_MAX:
 74		ret = pmbus_read_word_data(client, page, phase,
 75					   MAX34440_MFR_VOUT_PEAK);
 76		break;
 77	case PMBUS_VIRT_READ_IOUT_AVG:
 78		if (data->id != max34446 && data->id != max34451)
 79			return -ENXIO;
 80		ret = pmbus_read_word_data(client, page, phase,
 81					   MAX34446_MFR_IOUT_AVG);
 82		break;
 83	case PMBUS_VIRT_READ_IOUT_MAX:
 84		ret = pmbus_read_word_data(client, page, phase,
 85					   MAX34440_MFR_IOUT_PEAK);
 86		break;
 87	case PMBUS_VIRT_READ_POUT_AVG:
 88		if (data->id != max34446)
 89			return -ENXIO;
 90		ret = pmbus_read_word_data(client, page, phase,
 91					   MAX34446_MFR_POUT_AVG);
 92		break;
 93	case PMBUS_VIRT_READ_POUT_MAX:
 94		if (data->id != max34446)
 95			return -ENXIO;
 96		ret = pmbus_read_word_data(client, page, phase,
 97					   MAX34446_MFR_POUT_PEAK);
 98		break;
 99	case PMBUS_VIRT_READ_TEMP_AVG:
100		if (data->id != max34446 && data->id != max34460 &&
101		    data->id != max34461)
102			return -ENXIO;
103		ret = pmbus_read_word_data(client, page, phase,
104					   MAX34446_MFR_TEMPERATURE_AVG);
105		break;
106	case PMBUS_VIRT_READ_TEMP_MAX:
107		ret = pmbus_read_word_data(client, page, phase,
108					   MAX34440_MFR_TEMPERATURE_PEAK);
109		break;
110	case PMBUS_VIRT_RESET_POUT_HISTORY:
111		if (data->id != max34446)
112			return -ENXIO;
113		ret = 0;
114		break;
115	case PMBUS_VIRT_RESET_VOUT_HISTORY:
116	case PMBUS_VIRT_RESET_IOUT_HISTORY:
117	case PMBUS_VIRT_RESET_TEMP_HISTORY:
118		ret = 0;
119		break;
120	default:
121		ret = -ENODATA;
122		break;
123	}
124	return ret;
125}
126
127static int max34440_write_word_data(struct i2c_client *client, int page,
128				    int reg, u16 word)
129{
130	const struct pmbus_driver_info *info = pmbus_get_driver_info(client);
131	const struct max34440_data *data = to_max34440_data(info);
132	int ret;
133
134	switch (reg) {
135	case PMBUS_IOUT_OC_FAULT_LIMIT:
136		ret = pmbus_write_word_data(client, page, MAX34440_IOUT_OC_FAULT_LIMIT,
137					    word);
138		break;
139	case PMBUS_IOUT_OC_WARN_LIMIT:
140		ret = pmbus_write_word_data(client, page, MAX34440_IOUT_OC_WARN_LIMIT,
141					    word);
142		break;
143	case PMBUS_VIRT_RESET_POUT_HISTORY:
144		ret = pmbus_write_word_data(client, page,
145					    MAX34446_MFR_POUT_PEAK, 0);
146		if (ret)
147			break;
148		ret = pmbus_write_word_data(client, page,
149					    MAX34446_MFR_POUT_AVG, 0);
150		break;
151	case PMBUS_VIRT_RESET_VOUT_HISTORY:
152		ret = pmbus_write_word_data(client, page,
153					    MAX34440_MFR_VOUT_MIN, 0x7fff);
154		if (ret)
155			break;
156		ret = pmbus_write_word_data(client, page,
157					    MAX34440_MFR_VOUT_PEAK, 0);
158		break;
159	case PMBUS_VIRT_RESET_IOUT_HISTORY:
160		ret = pmbus_write_word_data(client, page,
161					    MAX34440_MFR_IOUT_PEAK, 0);
162		if (!ret && (data->id == max34446 || data->id == max34451))
163			ret = pmbus_write_word_data(client, page,
164					MAX34446_MFR_IOUT_AVG, 0);
165
166		break;
167	case PMBUS_VIRT_RESET_TEMP_HISTORY:
168		ret = pmbus_write_word_data(client, page,
169					    MAX34440_MFR_TEMPERATURE_PEAK,
170					    0x8000);
171		if (!ret && data->id == max34446)
172			ret = pmbus_write_word_data(client, page,
173					MAX34446_MFR_TEMPERATURE_AVG, 0);
174		break;
175	default:
176		ret = -ENODATA;
177		break;
178	}
179	return ret;
180}
181
182static int max34440_read_byte_data(struct i2c_client *client, int page, int reg)
183{
184	int ret = 0;
185	int mfg_status;
186
187	if (page >= 0) {
188		ret = pmbus_set_page(client, page, 0xff);
189		if (ret < 0)
190			return ret;
191	}
192
193	switch (reg) {
194	case PMBUS_STATUS_IOUT:
195		mfg_status = pmbus_read_word_data(client, 0, 0xff,
196						  PMBUS_STATUS_MFR_SPECIFIC);
197		if (mfg_status < 0)
198			return mfg_status;
199		if (mfg_status & MAX34440_STATUS_OC_WARN)
200			ret |= PB_IOUT_OC_WARNING;
201		if (mfg_status & MAX34440_STATUS_OC_FAULT)
202			ret |= PB_IOUT_OC_FAULT;
203		break;
204	case PMBUS_STATUS_TEMPERATURE:
205		mfg_status = pmbus_read_word_data(client, 0, 0xff,
206						  PMBUS_STATUS_MFR_SPECIFIC);
207		if (mfg_status < 0)
208			return mfg_status;
209		if (mfg_status & MAX34440_STATUS_OT_WARN)
210			ret |= PB_TEMP_OT_WARNING;
211		if (mfg_status & MAX34440_STATUS_OT_FAULT)
212			ret |= PB_TEMP_OT_FAULT;
213		break;
214	default:
215		ret = -ENODATA;
216		break;
217	}
218	return ret;
219}
220
221static int max34451_set_supported_funcs(struct i2c_client *client,
222					 struct max34440_data *data)
223{
224	/*
225	 * Each of the channel 0-15 can be configured to monitor the following
226	 * functions based on MFR_CHANNEL_CONFIG[5:0]
227	 * 0x10: Sequencing + voltage monitoring (only valid for PAGES 0–11)
228	 * 0x20: Voltage monitoring (no sequencing)
229	 * 0x21: Voltage read only
230	 * 0x22: Current monitoring
231	 * 0x23: Current read only
232	 * 0x30: General-purpose input active low
233	 * 0x34: General-purpose input active high
234	 * 0x00:  Disabled
235	 */
236
237	int page, rv;
238
239	for (page = 0; page < 16; page++) {
240		rv = i2c_smbus_write_byte_data(client, PMBUS_PAGE, page);
241		if (rv < 0)
242			return rv;
243
244		rv = i2c_smbus_read_word_data(client,
245					      MAX34451_MFR_CHANNEL_CONFIG);
246		if (rv < 0)
247			return rv;
248
249		switch (rv & MAX34451_MFR_CHANNEL_CONFIG_SEL_MASK) {
250		case 0x10:
251		case 0x20:
252			data->info.func[page] = PMBUS_HAVE_VOUT |
253				PMBUS_HAVE_STATUS_VOUT;
254			break;
255		case 0x21:
256			data->info.func[page] = PMBUS_HAVE_VOUT;
257			break;
258		case 0x22:
259			data->info.func[page] = PMBUS_HAVE_IOUT |
260				PMBUS_HAVE_STATUS_IOUT;
261			break;
262		case 0x23:
263			data->info.func[page] = PMBUS_HAVE_IOUT;
264			break;
265		default:
266			break;
267		}
268	}
269
270	return 0;
271}
272
273static struct pmbus_driver_info max34440_info[] = {
274	[max34440] = {
275		.pages = 14,
276		.format[PSC_VOLTAGE_IN] = direct,
277		.format[PSC_VOLTAGE_OUT] = direct,
278		.format[PSC_TEMPERATURE] = direct,
279		.format[PSC_CURRENT_OUT] = direct,
280		.m[PSC_VOLTAGE_IN] = 1,
281		.b[PSC_VOLTAGE_IN] = 0,
282		.R[PSC_VOLTAGE_IN] = 3,	    /* R = 0 in datasheet reflects mV */
283		.m[PSC_VOLTAGE_OUT] = 1,
284		.b[PSC_VOLTAGE_OUT] = 0,
285		.R[PSC_VOLTAGE_OUT] = 3,    /* R = 0 in datasheet reflects mV */
286		.m[PSC_CURRENT_OUT] = 1,
287		.b[PSC_CURRENT_OUT] = 0,
288		.R[PSC_CURRENT_OUT] = 3,    /* R = 0 in datasheet reflects mA */
289		.m[PSC_TEMPERATURE] = 1,
290		.b[PSC_TEMPERATURE] = 0,
291		.R[PSC_TEMPERATURE] = 2,
292		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
293		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
294		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
295		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
296		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
297		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
298		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
299		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
300		.func[4] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
301		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
302		.func[5] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
303		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
304		.func[6] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
305		.func[7] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
306		.func[8] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
307		.func[9] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
308		.func[10] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
309		.func[11] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
310		.func[12] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
311		.func[13] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
312		.read_byte_data = max34440_read_byte_data,
313		.read_word_data = max34440_read_word_data,
314		.write_word_data = max34440_write_word_data,
315	},
316	[max34441] = {
317		.pages = 12,
318		.format[PSC_VOLTAGE_IN] = direct,
319		.format[PSC_VOLTAGE_OUT] = direct,
320		.format[PSC_TEMPERATURE] = direct,
321		.format[PSC_CURRENT_OUT] = direct,
322		.format[PSC_FAN] = direct,
323		.m[PSC_VOLTAGE_IN] = 1,
324		.b[PSC_VOLTAGE_IN] = 0,
325		.R[PSC_VOLTAGE_IN] = 3,
326		.m[PSC_VOLTAGE_OUT] = 1,
327		.b[PSC_VOLTAGE_OUT] = 0,
328		.R[PSC_VOLTAGE_OUT] = 3,
329		.m[PSC_CURRENT_OUT] = 1,
330		.b[PSC_CURRENT_OUT] = 0,
331		.R[PSC_CURRENT_OUT] = 3,
332		.m[PSC_TEMPERATURE] = 1,
333		.b[PSC_TEMPERATURE] = 0,
334		.R[PSC_TEMPERATURE] = 2,
335		.m[PSC_FAN] = 1,
336		.b[PSC_FAN] = 0,
337		.R[PSC_FAN] = 0,
338		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
339		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
340		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
341		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
342		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
343		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
344		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
345		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
346		.func[4] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
347		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
348		.func[5] = PMBUS_HAVE_FAN12 | PMBUS_HAVE_STATUS_FAN12,
349		.func[6] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
350		.func[7] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
351		.func[8] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
352		.func[9] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
353		.func[10] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
354		.func[11] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
355		.read_byte_data = max34440_read_byte_data,
356		.read_word_data = max34440_read_word_data,
357		.write_word_data = max34440_write_word_data,
358	},
359	[max34446] = {
360		.pages = 7,
361		.format[PSC_VOLTAGE_IN] = direct,
362		.format[PSC_VOLTAGE_OUT] = direct,
363		.format[PSC_TEMPERATURE] = direct,
364		.format[PSC_CURRENT_OUT] = direct,
365		.format[PSC_POWER] = direct,
366		.m[PSC_VOLTAGE_IN] = 1,
367		.b[PSC_VOLTAGE_IN] = 0,
368		.R[PSC_VOLTAGE_IN] = 3,
369		.m[PSC_VOLTAGE_OUT] = 1,
370		.b[PSC_VOLTAGE_OUT] = 0,
371		.R[PSC_VOLTAGE_OUT] = 3,
372		.m[PSC_CURRENT_OUT] = 1,
373		.b[PSC_CURRENT_OUT] = 0,
374		.R[PSC_CURRENT_OUT] = 3,
375		.m[PSC_POWER] = 1,
376		.b[PSC_POWER] = 0,
377		.R[PSC_POWER] = 3,
378		.m[PSC_TEMPERATURE] = 1,
379		.b[PSC_TEMPERATURE] = 0,
380		.R[PSC_TEMPERATURE] = 2,
381		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
382		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT | PMBUS_HAVE_POUT,
383		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
384		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
385		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
386		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT | PMBUS_HAVE_POUT,
387		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT
388		  | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT,
389		.func[4] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
390		.func[5] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
391		.func[6] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
392		.read_byte_data = max34440_read_byte_data,
393		.read_word_data = max34440_read_word_data,
394		.write_word_data = max34440_write_word_data,
395	},
396	[max34451] = {
397		.pages = 21,
398		.format[PSC_VOLTAGE_OUT] = direct,
399		.format[PSC_TEMPERATURE] = direct,
400		.format[PSC_CURRENT_OUT] = direct,
401		.m[PSC_VOLTAGE_OUT] = 1,
402		.b[PSC_VOLTAGE_OUT] = 0,
403		.R[PSC_VOLTAGE_OUT] = 3,
404		.m[PSC_CURRENT_OUT] = 1,
405		.b[PSC_CURRENT_OUT] = 0,
406		.R[PSC_CURRENT_OUT] = 2,
407		.m[PSC_TEMPERATURE] = 1,
408		.b[PSC_TEMPERATURE] = 0,
409		.R[PSC_TEMPERATURE] = 2,
410		/* func 0-15 is set dynamically before probing */
411		.func[16] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
412		.func[17] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
413		.func[18] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
414		.func[19] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
415		.func[20] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
416		.read_word_data = max34440_read_word_data,
417		.write_word_data = max34440_write_word_data,
418	},
419	[max34460] = {
420		.pages = 18,
421		.format[PSC_VOLTAGE_OUT] = direct,
422		.format[PSC_TEMPERATURE] = direct,
423		.m[PSC_VOLTAGE_OUT] = 1,
424		.b[PSC_VOLTAGE_OUT] = 0,
425		.R[PSC_VOLTAGE_OUT] = 3,
426		.m[PSC_TEMPERATURE] = 1,
427		.b[PSC_TEMPERATURE] = 0,
428		.R[PSC_TEMPERATURE] = 2,
429		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
430		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
431		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
432		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
433		.func[4] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
434		.func[5] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
435		.func[6] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
436		.func[7] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
437		.func[8] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
438		.func[9] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
439		.func[10] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
440		.func[11] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
441		.func[13] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
442		.func[14] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
443		.func[15] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
444		.func[16] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
445		.func[17] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
446		.read_word_data = max34440_read_word_data,
447		.write_word_data = max34440_write_word_data,
448	},
449	[max34461] = {
450		.pages = 23,
451		.format[PSC_VOLTAGE_OUT] = direct,
452		.format[PSC_TEMPERATURE] = direct,
453		.m[PSC_VOLTAGE_OUT] = 1,
454		.b[PSC_VOLTAGE_OUT] = 0,
455		.R[PSC_VOLTAGE_OUT] = 3,
456		.m[PSC_TEMPERATURE] = 1,
457		.b[PSC_TEMPERATURE] = 0,
458		.R[PSC_TEMPERATURE] = 2,
459		.func[0] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
460		.func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
461		.func[2] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
462		.func[3] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
463		.func[4] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
464		.func[5] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
465		.func[6] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
466		.func[7] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
467		.func[8] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
468		.func[9] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
469		.func[10] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
470		.func[11] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
471		.func[12] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
472		.func[13] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
473		.func[14] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
474		.func[15] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT,
475		/* page 16 is reserved */
476		.func[17] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
477		.func[18] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
478		.func[19] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
479		.func[20] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
480		.func[21] = PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP,
481		.read_word_data = max34440_read_word_data,
482		.write_word_data = max34440_write_word_data,
483	},
484};
485
486static int max34440_probe(struct i2c_client *client)
 
487{
488	struct max34440_data *data;
489	int rv;
490
491	data = devm_kzalloc(&client->dev, sizeof(struct max34440_data),
492			    GFP_KERNEL);
493	if (!data)
494		return -ENOMEM;
495	data->id = i2c_match_id(max34440_id, client)->driver_data;
496	data->info = max34440_info[data->id];
497
498	if (data->id == max34451) {
499		rv = max34451_set_supported_funcs(client, data);
500		if (rv)
501			return rv;
502	}
503
504	return pmbus_do_probe(client, &data->info);
505}
506
507static const struct i2c_device_id max34440_id[] = {
508	{"max34440", max34440},
509	{"max34441", max34441},
510	{"max34446", max34446},
511	{"max34451", max34451},
512	{"max34460", max34460},
513	{"max34461", max34461},
514	{}
515};
 
516MODULE_DEVICE_TABLE(i2c, max34440_id);
517
518/* This is the driver that will be inserted */
519static struct i2c_driver max34440_driver = {
520	.driver = {
521		   .name = "max34440",
522		   },
523	.probe = max34440_probe,
 
524	.id_table = max34440_id,
525};
526
527module_i2c_driver(max34440_driver);
 
 
 
 
 
 
 
 
528
529MODULE_AUTHOR("Guenter Roeck");
530MODULE_DESCRIPTION("PMBus driver for Maxim MAX34440/MAX34441");
531MODULE_LICENSE("GPL");
532MODULE_IMPORT_NS(PMBUS);