drivers/hwmon/emc1403.c

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

File Facts

System
Linux kernel
Corpus path
drivers/hwmon/emc1403.c
Extension
.c
Size
17294 bytes
Lines
701
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 thermal_data {
	enum emc1403_chip chip;
	struct regmap *regmap;
};

static ssize_t power_state_show(struct device *dev, struct device_attribute *attr, char *buf)
{
	struct thermal_data *data = dev_get_drvdata(dev);
	unsigned int val;
	int retval;

	retval = regmap_read(data->regmap, 0x03, &val);
	if (retval < 0)
		return retval;
	return sysfs_emit(buf, "%d\n", !!(val & BIT(6)));
}

static ssize_t power_state_store(struct device *dev, struct device_attribute *attr,
				 const char *buf, size_t count)
{
	struct thermal_data *data = dev_get_drvdata(dev);
	unsigned long val;
	int retval;

	if (kstrtoul(buf, 10, &val))
		return -EINVAL;

	retval = regmap_update_bits(data->regmap, 0x03, BIT(6),
				    val ? BIT(6) : 0);
	if (retval < 0)
		return retval;
	return count;
}

static DEVICE_ATTR_RW(power_state);

static struct attribute *emc1403_attrs[] = {
	&dev_attr_power_state.attr,
	NULL
};
ATTRIBUTE_GROUPS(emc1403);

static int emc1403_detect(struct i2c_client *client,
			struct i2c_board_info *info)
{
	int id;
	/* Check if thermal chip is SMSC and EMC1403 or EMC1423 */

	id = i2c_smbus_read_byte_data(client, THERMAL_SMSC_ID_REG);
	if (id != 0x5d)
		return -ENODEV;

	id = i2c_smbus_read_byte_data(client, THERMAL_PID_REG);
	switch (id) {
	case 0x20:
		strscpy(info->type, "emc1402", I2C_NAME_SIZE);
		break;
	case 0x21:
		strscpy(info->type, "emc1403", I2C_NAME_SIZE);
		break;
	case 0x22:
		strscpy(info->type, "emc1422", I2C_NAME_SIZE);
		break;
	case 0x23:
		strscpy(info->type, "emc1423", I2C_NAME_SIZE);
		break;
	case 0x25:
		strscpy(info->type, "emc1404", I2C_NAME_SIZE);
		break;
	case 0x27:
		strscpy(info->type, "emc1424", I2C_NAME_SIZE);
		break;
	case 0x29:
		strscpy(info->type, "emc1428", I2C_NAME_SIZE);
		break;
	case 0x59:
		strscpy(info->type, "emc1438", I2C_NAME_SIZE);
		break;
	case 0x60:
		strscpy(info->type, "emc1442", I2C_NAME_SIZE);
		break;
	default:
		return -ENODEV;
	}

	id = i2c_smbus_read_byte_data(client, THERMAL_REVISION_REG);
	if (id < 0x01 || id > 0x04)
		return -ENODEV;

	return 0;

Annotation

Implementation Notes