linux/drivers/hwmon/pmbus/pmbus_core.c

// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * Hardware monitoring driver for PMBus devices
 *
 * Copyright (c) 2010, 2011 Ericsson AB.
 * Copyright (c) 2012 Guenter Roeck
 */

#include <linux/debugfs.h>
#include <linux/kernel.h>
#include <linux/math64.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/err.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/pmbus.h>
#include <linux/regulator/driver.h>
#include <linux/regulator/machine.h>
#include <linux/of.h>
#include <linux/thermal.h>
#include "pmbus.h"

/*
 * Number of additional attribute pointers to allocate
 * with each call to krealloc
 */
#define PMBUS_ATTR_ALLOC_SIZE
#define PMBUS_NAME_SIZE

struct pmbus_sensor {};
#define to_pmbus_sensor(_attr)

struct pmbus_boolean {};
#define to_pmbus_boolean(_attr)

struct pmbus_label {};
#define to_pmbus_label(_attr)

/* Macros for converting between sensor index and register/page/status mask */

#define PB_STATUS_MASK
#define PB_REG_SHIFT
#define PB_REG_MASK
#define PB_PAGE_SHIFT
#define PB_PAGE_MASK

#define pb_reg_to_index(page, reg, mask)

#define pb_index_to_page(index)
#define pb_index_to_reg(index)
#define pb_index_to_mask(index)

struct pmbus_data {};

struct pmbus_debugfs_entry {};

static const int pmbus_fan_rpm_mask[] =;

static const int pmbus_fan_config_registers[] =;

static const int pmbus_fan_command_registers[] =;

void pmbus_clear_cache(struct i2c_client *client)
{}
EXPORT_SYMBOL_NS_GPL();

void pmbus_set_update(struct i2c_client *client, u8 reg, bool update)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_set_page(struct i2c_client *client, int page, int phase)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_write_byte(struct i2c_client *client, int page, u8 value)
{}
EXPORT_SYMBOL_NS_GPL();

/*
 * _pmbus_write_byte() is similar to pmbus_write_byte(), but checks if
 * a device specific mapping function exists and calls it if necessary.
 */
static int _pmbus_write_byte(struct i2c_client *client, int page, u8 value)
{}

int pmbus_write_word_data(struct i2c_client *client, int page, u8 reg,
			  u16 word)
{}
EXPORT_SYMBOL_NS_GPL();


static int pmbus_write_virt_reg(struct i2c_client *client, int page, int reg,
				u16 word)
{}

/*
 * _pmbus_write_word_data() is similar to pmbus_write_word_data(), but checks if
 * a device specific mapping function exists and calls it if necessary.
 */
static int _pmbus_write_word_data(struct i2c_client *client, int page, int reg,
				  u16 word)
{}

/*
 * _pmbus_write_byte_data() is similar to pmbus_write_byte_data(), but checks if
 * a device specific mapping function exists and calls it if necessary.
 */
static int _pmbus_write_byte_data(struct i2c_client *client, int page, int reg, u8 value)
{}

/*
 * _pmbus_read_byte_data() is similar to pmbus_read_byte_data(), but checks if
 * a device specific mapping function exists and calls it if necessary.
 */
static int _pmbus_read_byte_data(struct i2c_client *client, int page, int reg)
{}

int pmbus_update_fan(struct i2c_client *client, int page, int id,
		     u8 config, u8 mask, u16 command)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_read_word_data(struct i2c_client *client, int page, int phase, u8 reg)
{}
EXPORT_SYMBOL_NS_GPL();

static int pmbus_read_virt_reg(struct i2c_client *client, int page, int reg)
{}

/*
 * _pmbus_read_word_data() is similar to pmbus_read_word_data(), but checks if
 * a device specific mapping function exists and calls it if necessary.
 */
static int _pmbus_read_word_data(struct i2c_client *client, int page,
				 int phase, int reg)
{}

/* Same as above, but without phase parameter, for use in check functions */
static int __pmbus_read_word_data(struct i2c_client *client, int page, int reg)
{}

int pmbus_read_byte_data(struct i2c_client *client, int page, u8 reg)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_write_byte_data(struct i2c_client *client, int page, u8 reg, u8 value)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_update_byte_data(struct i2c_client *client, int page, u8 reg,
			   u8 mask, u8 value)
{}
EXPORT_SYMBOL_NS_GPL();

static int pmbus_read_block_data(struct i2c_client *client, int page, u8 reg,
				 char *data_buf)
{}

static struct pmbus_sensor *pmbus_find_sensor(struct pmbus_data *data, int page,
					      int reg)
{}

static int pmbus_get_fan_rate(struct i2c_client *client, int page, int id,
			      enum pmbus_fan_mode mode,
			      bool from_cache)
{}

int pmbus_get_fan_rate_device(struct i2c_client *client, int page, int id,
			      enum pmbus_fan_mode mode)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_get_fan_rate_cached(struct i2c_client *client, int page, int id,
			      enum pmbus_fan_mode mode)
{}
EXPORT_SYMBOL_NS_GPL();

static void pmbus_clear_fault_page(struct i2c_client *client, int page)
{}

void pmbus_clear_faults(struct i2c_client *client)
{}
EXPORT_SYMBOL_NS_GPL();

static int pmbus_check_status_cml(struct i2c_client *client)
{}

static bool pmbus_check_register(struct i2c_client *client,
				 int (*func)(struct i2c_client *client,
					     int page, int reg),
				 int page, int reg)
{}

static bool pmbus_check_status_register(struct i2c_client *client, int page)
{}

bool pmbus_check_byte_register(struct i2c_client *client, int page, int reg)
{}
EXPORT_SYMBOL_NS_GPL();

bool pmbus_check_word_register(struct i2c_client *client, int page, int reg)
{}
EXPORT_SYMBOL_NS_GPL();

static bool __maybe_unused pmbus_check_block_register(struct i2c_client *client,
						      int page, int reg)
{}

const struct pmbus_driver_info *pmbus_get_driver_info(struct i2c_client *client)
{}
EXPORT_SYMBOL_NS_GPL();

static int pmbus_get_status(struct i2c_client *client, int page, int reg)
{}

static void pmbus_update_sensor_data(struct i2c_client *client, struct pmbus_sensor *sensor)
{}

/*
 * Convert ieee754 sensor values to milli- or micro-units
 * depending on sensor type.
 *
 * ieee754 data format:
 *	bit 15:		sign
 *	bit 10..14:	exponent
 *	bit 0..9:	mantissa
 * exponent=0:
 *	v=(−1)^signbit * 2^(−14) * 0.significantbits
 * exponent=1..30:
 *	v=(−1)^signbit * 2^(exponent - 15) * 1.significantbits
 * exponent=31:
 *	v=NaN
 *
 * Add the number mantissa bits into the calculations for simplicity.
 * To do that, add '10' to the exponent. By doing that, we can just add
 * 0x400 to normal values and get the expected result.
 */
static long pmbus_reg2data_ieee754(struct pmbus_data *data,
				   struct pmbus_sensor *sensor)
{}

/*
 * Convert linear sensor values to milli- or micro-units
 * depending on sensor type.
 */
static s64 pmbus_reg2data_linear(struct pmbus_data *data,
				 struct pmbus_sensor *sensor)
{}

/*
 * Convert direct sensor values to milli- or micro-units
 * depending on sensor type.
 */
static s64 pmbus_reg2data_direct(struct pmbus_data *data,
				 struct pmbus_sensor *sensor)
{}

/*
 * Convert VID sensor values to milli- or micro-units
 * depending on sensor type.
 */
static s64 pmbus_reg2data_vid(struct pmbus_data *data,
			      struct pmbus_sensor *sensor)
{}

static s64 pmbus_reg2data(struct pmbus_data *data, struct pmbus_sensor *sensor)
{}

#define MAX_IEEE_MANTISSA
#define MIN_IEEE_MANTISSA

static u16 pmbus_data2reg_ieee754(struct pmbus_data *data,
				  struct pmbus_sensor *sensor, long val)
{}

#define MAX_LIN_MANTISSA
#define MIN_LIN_MANTISSA

static u16 pmbus_data2reg_linear(struct pmbus_data *data,
				 struct pmbus_sensor *sensor, s64 val)
{}

static u16 pmbus_data2reg_direct(struct pmbus_data *data,
				 struct pmbus_sensor *sensor, s64 val)
{}

static u16 pmbus_data2reg_vid(struct pmbus_data *data,
			      struct pmbus_sensor *sensor, s64 val)
{}

static u16 pmbus_data2reg(struct pmbus_data *data,
			  struct pmbus_sensor *sensor, s64 val)
{}

/*
 * Return boolean calculated from converted data.
 * <index> defines a status register index and mask.
 * The mask is in the lower 8 bits, the register index is in bits 8..23.
 *
 * The associated pmbus_boolean structure contains optional pointers to two
 * sensor attributes. If specified, those attributes are compared against each
 * other to determine if a limit has been exceeded.
 *
 * If the sensor attribute pointers are NULL, the function returns true if
 * (status[reg] & mask) is true.
 *
 * If sensor attribute pointers are provided, a comparison against a specified
 * limit has to be performed to determine the boolean result.
 * In this case, the function returns true if v1 >= v2 (where v1 and v2 are
 * sensor values referenced by sensor attribute pointers s1 and s2).
 *
 * To determine if an object exceeds upper limits, specify <s1,s2> = <v,limit>.
 * To determine if an object exceeds lower limits, specify <s1,s2> = <limit,v>.
 *
 * If a negative value is stored in any of the referenced registers, this value
 * reflects an error code which will be returned.
 */
static int pmbus_get_boolean(struct i2c_client *client, struct pmbus_boolean *b,
			     int index)
{}

static ssize_t pmbus_show_boolean(struct device *dev,
				  struct device_attribute *da, char *buf)
{}

static ssize_t pmbus_show_sensor(struct device *dev,
				 struct device_attribute *devattr, char *buf)
{}

static ssize_t pmbus_set_sensor(struct device *dev,
				struct device_attribute *devattr,
				const char *buf, size_t count)
{}

static ssize_t pmbus_show_label(struct device *dev,
				struct device_attribute *da, char *buf)
{}

static int pmbus_add_attribute(struct pmbus_data *data, struct attribute *attr)
{}

static void pmbus_dev_attr_init(struct device_attribute *dev_attr,
				const char *name,
				umode_t mode,
				ssize_t (*show)(struct device *dev,
						struct device_attribute *attr,
						char *buf),
				ssize_t (*store)(struct device *dev,
						 struct device_attribute *attr,
						 const char *buf, size_t count))
{}

static void pmbus_attr_init(struct sensor_device_attribute *a,
			    const char *name,
			    umode_t mode,
			    ssize_t (*show)(struct device *dev,
					    struct device_attribute *attr,
					    char *buf),
			    ssize_t (*store)(struct device *dev,
					     struct device_attribute *attr,
					     const char *buf, size_t count),
			    int idx)
{}

static int pmbus_add_boolean(struct pmbus_data *data,
			     const char *name, const char *type, int seq,
			     struct pmbus_sensor *s1,
			     struct pmbus_sensor *s2,
			     u8 page, u16 reg, u16 mask)
{}

/* of thermal for pmbus temperature sensors */
struct pmbus_thermal_data {};

static int pmbus_thermal_get_temp(struct thermal_zone_device *tz, int *temp)
{}

static const struct thermal_zone_device_ops pmbus_thermal_ops =;

static int pmbus_thermal_add_sensor(struct pmbus_data *pmbus_data,
				    struct pmbus_sensor *sensor, int index)
{}

static struct pmbus_sensor *pmbus_add_sensor(struct pmbus_data *data,
					     const char *name, const char *type,
					     int seq, int page, int phase,
					     int reg,
					     enum pmbus_sensor_classes class,
					     bool update, bool readonly,
					     bool convert)
{}

static int pmbus_add_label(struct pmbus_data *data,
			   const char *name, int seq,
			   const char *lstring, int index, int phase)
{}

/*
 * Search for attributes. Allocate sensors, booleans, and labels as needed.
 */

/*
 * The pmbus_limit_attr structure describes a single limit attribute
 * and its associated alarm attribute.
 */
struct pmbus_limit_attr {};

/*
 * The pmbus_sensor_attr structure describes one sensor attribute. This
 * description includes a reference to the associated limit attributes.
 */
struct pmbus_sensor_attr {};

/*
 * Add a set of limit attributes and, if supported, the associated
 * alarm attributes.
 * returns 0 if no alarm register found, 1 if an alarm register was found,
 * < 0 on errors.
 */
static int pmbus_add_limit_attrs(struct i2c_client *client,
				 struct pmbus_data *data,
				 const struct pmbus_driver_info *info,
				 const char *name, int index, int page,
				 struct pmbus_sensor *base,
				 const struct pmbus_sensor_attr *attr)
{}

static int pmbus_add_sensor_attrs_one(struct i2c_client *client,
				      struct pmbus_data *data,
				      const struct pmbus_driver_info *info,
				      const char *name,
				      int index, int page, int phase,
				      const struct pmbus_sensor_attr *attr,
				      bool paged)
{}

static bool pmbus_sensor_is_paged(const struct pmbus_driver_info *info,
				  const struct pmbus_sensor_attr *attr)
{}

static int pmbus_add_sensor_attrs(struct i2c_client *client,
				  struct pmbus_data *data,
				  const char *name,
				  const struct pmbus_sensor_attr *attrs,
				  int nattrs)
{}

static const struct pmbus_limit_attr vin_limit_attrs[] =;

static const struct pmbus_limit_attr vmon_limit_attrs[] =;

static const struct pmbus_limit_attr vout_limit_attrs[] =;

static const struct pmbus_sensor_attr voltage_attributes[] =;

/* Current attributes */

static const struct pmbus_limit_attr iin_limit_attrs[] =;

static const struct pmbus_limit_attr iout_limit_attrs[] =;

static const struct pmbus_sensor_attr current_attributes[] =;

/* Power attributes */

static const struct pmbus_limit_attr pin_limit_attrs[] =;

static const struct pmbus_limit_attr pout_limit_attrs[] =;

static const struct pmbus_sensor_attr power_attributes[] =;

/* Temperature atributes */

static const struct pmbus_limit_attr temp_limit_attrs[] =;

static const struct pmbus_limit_attr temp_limit_attrs2[] =;

static const struct pmbus_limit_attr temp_limit_attrs3[] =;

static const struct pmbus_sensor_attr temp_attributes[] =;

static const int pmbus_fan_registers[] =;

static const int pmbus_fan_status_registers[] =;

static const u32 pmbus_fan_flags[] =;

static const u32 pmbus_fan_status_flags[] =;

/* Fans */

/* Precondition: FAN_CONFIG_x_y and FAN_COMMAND_x must exist for the fan ID */
static int pmbus_add_fan_ctrl(struct i2c_client *client,
		struct pmbus_data *data, int index, int page, int id,
		u8 config)
{}

static int pmbus_add_fan_attributes(struct i2c_client *client,
				    struct pmbus_data *data)
{}

struct pmbus_samples_attr {};

struct pmbus_samples_reg {};

static struct pmbus_samples_attr pmbus_samples_registers[] =;

#define to_samples_reg(x)

static ssize_t pmbus_show_samples(struct device *dev,
				  struct device_attribute *devattr, char *buf)
{}

static ssize_t pmbus_set_samples(struct device *dev,
				 struct device_attribute *devattr,
				 const char *buf, size_t count)
{}

static int pmbus_add_samples_attr(struct pmbus_data *data, int page,
				  struct pmbus_samples_attr *attr)
{}

static int pmbus_add_samples_attributes(struct i2c_client *client,
					struct pmbus_data *data)
{}

static int pmbus_find_attributes(struct i2c_client *client,
				 struct pmbus_data *data)
{}

/*
 * The pmbus_class_attr_map structure maps one sensor class to
 * it's corresponding sensor attributes array.
 */
struct pmbus_class_attr_map {};

static const struct pmbus_class_attr_map class_attr_map[] =;

/*
 * Read the coefficients for direct mode.
 */
static int pmbus_read_coefficients(struct i2c_client *client,
				   struct pmbus_driver_info *info,
				   const struct pmbus_sensor_attr *attr)
{}

static int pmbus_init_coefficients(struct i2c_client *client,
				   struct pmbus_driver_info *info)
{}

/*
 * Identify chip parameters.
 * This function is called for all chips.
 */
static int pmbus_identify_common(struct i2c_client *client,
				 struct pmbus_data *data, int page)
{}

static int pmbus_read_status_byte(struct i2c_client *client, int page)
{}

static int pmbus_read_status_word(struct i2c_client *client, int page)
{}

/* PEC attribute support */

static ssize_t pec_show(struct device *dev, struct device_attribute *dummy,
			char *buf)
{}

static ssize_t pec_store(struct device *dev, struct device_attribute *dummy,
			 const char *buf, size_t count)
{}

static DEVICE_ATTR_RW(pec);

static void pmbus_remove_pec(void *dev)
{}

static int pmbus_init_common(struct i2c_client *client, struct pmbus_data *data,
			     struct pmbus_driver_info *info)
{}

/* A PMBus status flag and the corresponding REGULATOR_ERROR_* and REGULATOR_EVENTS_* flag */
struct pmbus_status_assoc {};

/* PMBus->regulator bit mappings for a PMBus status register */
struct pmbus_status_category {};

static const struct pmbus_status_category __maybe_unused pmbus_status_flag_map[] =;

static int _pmbus_is_enabled(struct i2c_client *client, u8 page)
{}

static int __maybe_unused pmbus_is_enabled(struct i2c_client *client, u8 page)
{}

#define to_dev_attr(_dev_attr)

static void pmbus_notify(struct pmbus_data *data, int page, int reg, int flags)
{}

static int _pmbus_get_flags(struct pmbus_data *data, u8 page, unsigned int *flags,
			   unsigned int *event, bool notify)
{}

static int __maybe_unused pmbus_get_flags(struct pmbus_data *data, u8 page, unsigned int *flags,
					  unsigned int *event, bool notify)
{}

#if IS_ENABLED(CONFIG_REGULATOR)
static int pmbus_regulator_is_enabled(struct regulator_dev *rdev)
{}

static int _pmbus_regulator_on_off(struct regulator_dev *rdev, bool enable)
{}

static int pmbus_regulator_enable(struct regulator_dev *rdev)
{}

static int pmbus_regulator_disable(struct regulator_dev *rdev)
{}

static int pmbus_regulator_get_error_flags(struct regulator_dev *rdev, unsigned int *flags)
{}

static int pmbus_regulator_get_status(struct regulator_dev *rdev)
{}

static int pmbus_regulator_get_low_margin(struct i2c_client *client, int page)
{}

static int pmbus_regulator_get_high_margin(struct i2c_client *client, int page)
{}

static int pmbus_regulator_get_voltage(struct regulator_dev *rdev)
{}

static int pmbus_regulator_set_voltage(struct regulator_dev *rdev, int min_uv,
				       int max_uv, unsigned int *selector)
{}

static int pmbus_regulator_list_voltage(struct regulator_dev *rdev,
					 unsigned int selector)
{}

const struct regulator_ops pmbus_regulator_ops =;
EXPORT_SYMBOL_NS_GPL();

static int pmbus_regulator_register(struct pmbus_data *data)
{}

static int pmbus_regulator_notify(struct pmbus_data *data, int page, int event)
{}
#else
static int pmbus_regulator_register(struct pmbus_data *data)
{
	return 0;
}

static int pmbus_regulator_notify(struct pmbus_data *data, int page, int event)
{
		return 0;
}
#endif

static int pmbus_write_smbalert_mask(struct i2c_client *client, u8 page, u8 reg, u8 val)
{}

static irqreturn_t pmbus_fault_handler(int irq, void *pdata)
{}

static int pmbus_irq_setup(struct i2c_client *client, struct pmbus_data *data)
{}

static struct dentry *pmbus_debugfs_dir;	/* pmbus debugfs directory */

#if IS_ENABLED(CONFIG_DEBUG_FS)
static int pmbus_debugfs_get(void *data, u64 *val)
{}
DEFINE_DEBUGFS_ATTRIBUTE();

static int pmbus_debugfs_get_status(void *data, u64 *val)
{}
DEFINE_DEBUGFS_ATTRIBUTE();

static ssize_t pmbus_debugfs_mfr_read(struct file *file, char __user *buf,
				       size_t count, loff_t *ppos)
{}

static const struct file_operations pmbus_debugfs_ops_mfr =;

static void pmbus_remove_debugfs(void *data)
{}

static int pmbus_init_debugfs(struct i2c_client *client,
			      struct pmbus_data *data)
{}
#else
static int pmbus_init_debugfs(struct i2c_client *client,
			      struct pmbus_data *data)
{
	return 0;
}
#endif	/* IS_ENABLED(CONFIG_DEBUG_FS) */

int pmbus_do_probe(struct i2c_client *client, struct pmbus_driver_info *info)
{}
EXPORT_SYMBOL_NS_GPL();

struct dentry *pmbus_get_debugfs_dir(struct i2c_client *client)
{}
EXPORT_SYMBOL_NS_GPL();

int pmbus_lock_interruptible(struct i2c_client *client)
{}
EXPORT_SYMBOL_NS_GPL();

void pmbus_unlock(struct i2c_client *client)
{}
EXPORT_SYMBOL_NS_GPL();

static int __init pmbus_core_init(void)
{}

static void __exit pmbus_core_exit(void)
{}

module_init();
module_exit(pmbus_core_exit);

MODULE_AUTHOR();
MODULE_DESCRIPTION();
MODULE_LICENSE();