drivers/hwmon/isl28022.c

Source file repositories/reference/linux-study-clean/drivers/hwmon/isl28022.c

File Facts

System
Linux kernel
Corpus path
drivers/hwmon/isl28022.c
Extension
.c
Size
11956 bytes
Lines
502
Domain
Driver Families
Bucket
drivers/hwmon
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

struct isl28022_data {
	struct regmap		*regmap;
	u32			shunt;
	u32			gain;
	u32			average;
};

static int isl28022_read_in(struct device *dev, u32 attr, int channel, long *val)
{
	struct isl28022_data *data = dev_get_drvdata(dev);
	unsigned int regval;
	int err;
	u16 sign_bit;

	switch (channel) {
	case 0:
		switch (attr) {
		case hwmon_in_input:
			err = regmap_read(data->regmap,
					  ISL28022_REG_BUS, &regval);
			if (err < 0)
				return err;
			/* driver supports only 60V mode (BRNG 11) */
			*val = (long)(((u16)regval) & 0xFFFC);
			break;
		default:
			return -EOPNOTSUPP;
		}
		break;
	case 1:
		switch (attr) {
		case hwmon_in_input:
			err = regmap_read(data->regmap,
					  ISL28022_REG_SHUNT, &regval);
			if (err < 0)
				return err;
			switch (data->gain) {
			case 8:
				sign_bit = (regval >> 15) & 0x01;
				*val = (long)((((u16)regval) & 0x7FFF) -
					(sign_bit * 32768)) / 100;
				break;
			case 4:
				sign_bit = (regval >> 14) & 0x01;
				*val = (long)((((u16)regval) & 0x3FFF) -
					(sign_bit * 16384)) / 100;
				break;
			case 2:
				sign_bit = (regval >> 13) & 0x01;
				*val = (long)((((u16)regval) & 0x1FFF) -
					(sign_bit * 8192)) / 100;
				break;
			case 1:
				sign_bit = (regval >> 12) & 0x01;
				*val = (long)((((u16)regval) & 0x0FFF) -
					(sign_bit * 4096)) / 100;
				break;
			}
			break;
		default:
			return -EOPNOTSUPP;
		}
		break;
	default:
		return -EOPNOTSUPP;
	}

	return 0;
}

static int isl28022_read_current(struct device *dev, u32 attr, long *val)
{
	struct isl28022_data *data = dev_get_drvdata(dev);
	unsigned int regval;
	int err;
	u16 sign_bit;

	switch (attr) {
	case hwmon_curr_input:
		err = regmap_read(data->regmap,
				  ISL28022_REG_CURRENT, &regval);
		if (err < 0)
			return err;
		sign_bit = (regval >> 15) & 0x01;
		*val = (((long)(((u16)regval) & 0x7FFF) - (sign_bit * 32768)) *
			1250L * (long)data->gain) / (long)data->shunt;
		break;
	default:
		return -EOPNOTSUPP;
	}

Annotation

Implementation Notes