You've already forked linux-apfs
mirror of
https://github.com/linux-apfs/linux-apfs.git
synced 2026-05-01 15:00:59 -07:00
Merge tag 'hwmon-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging
Pull hwmon updates from Guenter Roeck:
"Notable changes:
- Heiko Schocher provided a driver for TI TMP103.
- Kamil Debski provided a driver for pwm-controlled fans.
- Neelesh Gupta provided a driver for power, fan rpm, voltage and
temperature reporting on powerpc/powernv systems.
- Scott Kanowitz provided a driver supporting Lattice's POWR1220
power manager IC.
- Richard Zhu provided a pmbus front-end driver for TPS40422.
- Frans Klaver added support for TMP112 to the lm75 driver.
- Johannes Pointner added support for EPCOS B57330V2103 to the
ntc_thermistor driver.
- Guenter Roeck added support for TMP441 and TMP442 to the tmp421
driver.
- Axel Lin converted several drivers to the new hwmon API (36 of
them, if I counted correctly), and cleaned up many of the drivers
along the way.
There are also a number of patches fixing bugs discovered while
testing Axel's changes"
* tag 'hwmon-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging: (88 commits)
hwmon: (g762) Use of_property_read_u32 at appropriate place
hwmon: (sis5595) Prevent overflow problem when writing large limits
hwmon: (gpio-fan) Prevent overflow problem when writing large limits
hwmon: (ibmpowernv) Use of_property_read_u32 at appropriate place
hwmon: (lm85) Convert to devm_hwmon_device_register_with_groups
hwmon: (lm85) Avoid forward declaration
hwmon: (lm78) Convert to devm_hwmon_device_register_with_groups
hwmon: (max6697) Use of_property_read_bool at appropriate places
hwmon: (pwm-fan) Make SENSORS_PWM_FAN depend on OF
hwmon: (pwm-fan) Remove duplicate dev_set_drvdata call
hwmon: (nct6775) Remove num_attr_groups from struct nct6775_data
hwmon: (nct6775) Update module description and Kconfig for NCT6106D and NCT6791D
hwmon: (adt7411) Convert to devm_hwmon_device_register_with_groups
hwmon: (g762) Convert to hwmon_device_register_with_groups
hwmon: (emc2103) Convert to devm_hwmon_device_register_with_groups
hwmon: (smsc47m1) Avoid forward declaration
hwmon: (smsc47m192) Convert to devm_hwmon_device_register_with_groups
hwmon: (smsc47m192) Avoid forward declaration
hwmon: (max1668) Make max1668_addr_list array const
hwmon: (max6639) Make normal_i2c array const
...
This commit is contained in:
@@ -0,0 +1,23 @@
|
||||
IBM POWERNV platform sensors
|
||||
----------------------------
|
||||
|
||||
Required node properties:
|
||||
- compatible: must be one of
|
||||
"ibm,opal-sensor-cooling-fan"
|
||||
"ibm,opal-sensor-amb-temp"
|
||||
"ibm,opal-sensor-power-supply"
|
||||
"ibm,opal-sensor-power"
|
||||
- sensor-id: an opaque id provided by the firmware to the kernel, identifies a
|
||||
given sensor and its attribute data
|
||||
|
||||
Example sensors node:
|
||||
|
||||
cooling-fan#8-data {
|
||||
sensor-id = <0x7052107>;
|
||||
compatible = "ibm,opal-sensor-cooling-fan";
|
||||
};
|
||||
|
||||
amb-temp#1-thrs {
|
||||
sensor-id = <0x5096000>;
|
||||
compatible = "ibm,opal-sensor-amb-temp";
|
||||
};
|
||||
@@ -3,6 +3,7 @@ NTC Thermistor hwmon sensors
|
||||
|
||||
Requires node properties:
|
||||
- "compatible" value : one of
|
||||
"epcos,b57330v2103"
|
||||
"murata,ncp15wb473"
|
||||
"murata,ncp18wb473"
|
||||
"murata,ncp21wb473"
|
||||
|
||||
@@ -0,0 +1,12 @@
|
||||
Bindings for a fan connected to the PWM lines
|
||||
|
||||
Required properties:
|
||||
- compatible : "pwm-fan"
|
||||
- pwms : the PWM that is used to control the PWM fan
|
||||
|
||||
Example:
|
||||
pwm-fan {
|
||||
compatible = "pwm-fan";
|
||||
status = "okay";
|
||||
pwms = <&pwm 0 10000 0>;
|
||||
};
|
||||
@@ -84,5 +84,6 @@ stm,m41t80 M41T80 - SERIAL ACCESS RTC WITH ALARMS
|
||||
taos,tsl2550 Ambient Light Sensor with SMBUS/Two Wire Serial Interface
|
||||
ti,tsc2003 I2C Touch-Screen Controller
|
||||
ti,tmp102 Low Power Digital Temperature Sensor with SMBUS/Two Wire Serial Interface
|
||||
ti,tmp103 Low Power Digital Temperature Sensor with SMBUS/Two Wire Serial Interface
|
||||
ti,tmp275 Digital Temperature Sensor
|
||||
winbond,wpct301 i2c trusted platform module (TPM)
|
||||
|
||||
@@ -42,6 +42,7 @@ dmo Data Modul AG
|
||||
ebv EBV Elektronik
|
||||
edt Emerging Display Technologies
|
||||
emmicro EM Microelectronic
|
||||
epcos EPCOS AG
|
||||
epfl Ecole Polytechnique Fédérale de Lausanne
|
||||
epson Seiko Epson Corp.
|
||||
est ESTeem Wireless Modems
|
||||
|
||||
@@ -0,0 +1,41 @@
|
||||
Kernel Driver IBMPOWERNV
|
||||
========================
|
||||
|
||||
Supported systems:
|
||||
* Any recent IBM P servers based on POWERNV platform
|
||||
|
||||
Author: Neelesh Gupta
|
||||
|
||||
Description
|
||||
-----------
|
||||
|
||||
This driver implements reading the platform sensors data like temperature/fan/
|
||||
voltage/power for 'POWERNV' platform.
|
||||
|
||||
The driver uses the platform device infrastructure. It probes the device tree
|
||||
for sensor devices during the __init phase and registers them with the 'hwmon'.
|
||||
'hwmon' populates the 'sysfs' tree having attribute files, each for a given
|
||||
sensor type and its attribute data.
|
||||
|
||||
All the nodes in the DT appear under "/ibm,opal/sensors" and each valid node in
|
||||
the DT maps to an attribute file in 'sysfs'. The node exports unique 'sensor-id'
|
||||
which the driver uses to make an OPAL call to the firmware.
|
||||
|
||||
Usage notes
|
||||
-----------
|
||||
The driver is built statically with the kernel by enabling the config
|
||||
CONFIG_SENSORS_IBMPOWERNV. It can also be built as module 'ibmpowernv'.
|
||||
|
||||
Sysfs attributes
|
||||
----------------
|
||||
|
||||
fanX_input Measured RPM value.
|
||||
fanX_min Threshold RPM for alert generation.
|
||||
fanX_fault 0: No fail condition
|
||||
1: Failing fan
|
||||
tempX_input Measured ambient temperature.
|
||||
tempX_max Threshold ambient temperature for alert generation.
|
||||
inX_input Measured power supply voltage
|
||||
inX_fault 0: No fail condition.
|
||||
1: Failing power supply.
|
||||
power1_input System power consumption (microWatt)
|
||||
@@ -42,13 +42,14 @@ Supported chips:
|
||||
Addresses scanned: none
|
||||
Datasheet: Publicly available at the ST website
|
||||
http://www.st.com/internet/analog/product/121769.jsp
|
||||
* Texas Instruments TMP100, TMP101, TMP105, TMP75, TMP175, TMP275
|
||||
Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp175', 'tmp75', 'tmp275'
|
||||
* Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75, TMP175, TMP275
|
||||
Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp112', 'tmp175', 'tmp75', 'tmp275'
|
||||
Addresses scanned: none
|
||||
Datasheet: Publicly available at the Texas Instruments website
|
||||
http://www.ti.com/product/tmp100
|
||||
http://www.ti.com/product/tmp101
|
||||
http://www.ti.com/product/tmp105
|
||||
http://www.ti.com/product/tmp112
|
||||
http://www.ti.com/product/tmp75
|
||||
http://www.ti.com/product/tmp175
|
||||
http://www.ti.com/product/tmp275
|
||||
|
||||
@@ -6,6 +6,11 @@ Supported thermistors from Murata:
|
||||
Prefixes: 'ncp15wb473', 'ncp18wb473', 'ncp21wb473', 'ncp03wb473', 'ncp15wl333'
|
||||
Datasheet: Publicly available at Murata
|
||||
|
||||
Supported thermistors from EPCOS:
|
||||
* EPCOS NTC Thermistors B57330V2103
|
||||
Prefixes: b57330v2103
|
||||
Datasheet: Publicly available at EPCOS
|
||||
|
||||
Other NTC thermistors can be supported simply by adding compensation
|
||||
tables; e.g., NCP15WL333 support is added by the table ncpXXwl333.
|
||||
|
||||
|
||||
@@ -23,12 +23,11 @@ Supported chips:
|
||||
http://www.lineagepower.com/oem/pdf/PDT012A0X.pdf
|
||||
http://www.lineagepower.com/oem/pdf/UDT020A0X.pdf
|
||||
http://www.lineagepower.com/oem/pdf/MDT040A0X.pdf
|
||||
* Texas Instruments TPS40400, TPS40422
|
||||
Prefixes: 'tps40400', 'tps40422'
|
||||
* Texas Instruments TPS40400
|
||||
Prefixes: 'tps40400'
|
||||
Addresses scanned: -
|
||||
Datasheets:
|
||||
http://www.ti.com/lit/gpn/tps40400
|
||||
http://www.ti.com/lit/gpn/tps40422
|
||||
* Generic PMBus devices
|
||||
Prefix: 'pmbus'
|
||||
Addresses scanned: -
|
||||
|
||||
@@ -0,0 +1,45 @@
|
||||
Kernel driver powr1220
|
||||
==================
|
||||
|
||||
Supported chips:
|
||||
* Lattice POWR1220AT8
|
||||
Prefix: 'powr1220'
|
||||
Addresses scanned: none
|
||||
Datasheet: Publicly available at the Lattice website
|
||||
http://www.latticesemi.com/
|
||||
|
||||
Author: Scott Kanowitz <scott.kanowitz@gmail.com>
|
||||
|
||||
Description
|
||||
-----------
|
||||
|
||||
This driver supports the Lattice POWR1220AT8 chip. The POWR1220
|
||||
includes voltage monitoring for 14 inputs as well as trim settings
|
||||
for output voltages and GPIOs. This driver implements the voltage
|
||||
monitoring portion of the chip.
|
||||
|
||||
Voltages are sampled by a 12-bit ADC with a step size of 2 mV.
|
||||
An in-line attenuator allows measurements from 0 to 6 V. The
|
||||
attenuator is enabled or disabled depending on the setting of the
|
||||
input's max value. The driver will enable the attenuator for any
|
||||
value over the low measurement range maximum of 2 V.
|
||||
|
||||
The input naming convention is as follows:
|
||||
|
||||
driver name pin name
|
||||
in0 VMON1
|
||||
in1 VMON2
|
||||
in2 VMON3
|
||||
in2 VMON4
|
||||
in4 VMON5
|
||||
in5 VMON6
|
||||
in6 VMON7
|
||||
in7 VMON8
|
||||
in8 VMON9
|
||||
in9 VMON10
|
||||
in10 VMON11
|
||||
in11 VMON12
|
||||
in12 VCCA
|
||||
in13 VCCINP
|
||||
|
||||
The ADC readings are updated on request with a minimum period of 1s.
|
||||
@@ -0,0 +1,17 @@
|
||||
Kernel driver pwm-fan
|
||||
=====================
|
||||
|
||||
This driver enables the use of a PWM module to drive a fan. It uses the
|
||||
generic PWM interface thus it is hardware independent. It can be used on
|
||||
many SoCs, as long as the SoC supplies a PWM line driver that exposes
|
||||
the generic PWM API.
|
||||
|
||||
Author: Kamil Debski <k.debski@samsung.com>
|
||||
|
||||
Description
|
||||
-----------
|
||||
|
||||
The driver implements a simple interface for driving a fan connected to
|
||||
a PWM output. It uses the generic PWM interface, thus it can be used with
|
||||
a range of SoCs. The driver exposes the fan to the user space through
|
||||
the hwmon's sysfs interface.
|
||||
@@ -0,0 +1,28 @@
|
||||
Kernel driver tmp103
|
||||
====================
|
||||
|
||||
Supported chips:
|
||||
* Texas Instruments TMP103
|
||||
Prefix: 'tmp103'
|
||||
Addresses scanned: none
|
||||
Product info and datasheet: http://www.ti.com/product/tmp103
|
||||
|
||||
Author:
|
||||
Heiko Schocher <hs@denx.de>
|
||||
|
||||
Description
|
||||
-----------
|
||||
|
||||
The TMP103 is a digital output temperature sensor in a four-ball
|
||||
wafer chip-scale package (WCSP). The TMP103 is capable of reading
|
||||
temperatures to a resolution of 1°C. The TMP103 is specified for
|
||||
operation over a temperature range of –40°C to +125°C.
|
||||
|
||||
Resolution: 8 Bits
|
||||
Accuracy: ±1°C Typ (–10°C to +100°C)
|
||||
|
||||
The driver provides the common sysfs-interface for temperatures (see
|
||||
Documentation/hwmon/sysfs-interface under Temperatures).
|
||||
|
||||
Please refer how to instantiate this driver:
|
||||
Documentation/i2c/instantiating-devices
|
||||
@@ -8,12 +8,20 @@ Supported chips:
|
||||
Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html
|
||||
* Texas Instruments TMP422
|
||||
Prefix: 'tmp422'
|
||||
Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f
|
||||
Addresses scanned: I2C 0x4c, 0x4d, 0x4e and 0x4f
|
||||
Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html
|
||||
* Texas Instruments TMP423
|
||||
Prefix: 'tmp423'
|
||||
Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f
|
||||
Addresses scanned: I2C 0x4c and 0x4d
|
||||
Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html
|
||||
* Texas Instruments TMP441
|
||||
Prefix: 'tmp441'
|
||||
Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f
|
||||
Datasheet: http://www.ti.com/product/tmp441
|
||||
* Texas Instruments TMP442
|
||||
Prefix: 'tmp442'
|
||||
Addresses scanned: I2C 0x4c and 0x4d
|
||||
Datasheet: http://www.ti.com/product/tmp442
|
||||
|
||||
Authors:
|
||||
Andre Prendel <andre.prendel@gmx.de>
|
||||
@@ -21,13 +29,13 @@ Authors:
|
||||
Description
|
||||
-----------
|
||||
|
||||
This driver implements support for Texas Instruments TMP421, TMP422
|
||||
and TMP423 temperature sensor chips. These chips implement one local
|
||||
and up to one (TMP421), up to two (TMP422) or up to three (TMP423)
|
||||
remote sensors. Temperature is measured in degrees Celsius. The chips
|
||||
are wired over I2C/SMBus and specified over a temperature range of -40
|
||||
to +125 degrees Celsius. Resolution for both the local and remote
|
||||
channels is 0.0625 degree C.
|
||||
This driver implements support for Texas Instruments TMP421, TMP422,
|
||||
TMP423, TMP441, and TMP442 temperature sensor chips. These chips
|
||||
implement one local and up to one (TMP421, TMP441), up to two (TMP422,
|
||||
TMP442) or up to three (TMP423) remote sensors. Temperature is measured
|
||||
in degrees Celsius. The chips are wired over I2C/SMBus and specified
|
||||
over a temperature range of -40 to +125 degrees Celsius. Resolution
|
||||
for both the local and remote channels is 0.0625 degree C.
|
||||
|
||||
The chips support only temperature measurement. The driver exports
|
||||
the temperature values via the following sysfs files:
|
||||
|
||||
@@ -0,0 +1,64 @@
|
||||
Kernel driver tps40422
|
||||
======================
|
||||
|
||||
Supported chips:
|
||||
* TI TPS40422
|
||||
Prefix: 'tps40422'
|
||||
Addresses scanned: -
|
||||
Datasheet: http://www.ti.com/lit/gpn/tps40422
|
||||
|
||||
Author: Zhu Laiwen <richard.zhu@nsn.com>
|
||||
|
||||
|
||||
Description
|
||||
-----------
|
||||
|
||||
This driver supports TI TPS40422 Dual-Output or Two-Phase Synchronous Buck
|
||||
Controller with PMBus
|
||||
|
||||
The driver is a client driver to the core PMBus driver.
|
||||
Please see Documentation/hwmon/pmbus for details on PMBus client drivers.
|
||||
|
||||
|
||||
Usage Notes
|
||||
-----------
|
||||
|
||||
This driver does not auto-detect devices. You will have to instantiate the
|
||||
devices explicitly. Please see Documentation/i2c/instantiating-devices for
|
||||
details.
|
||||
|
||||
|
||||
Platform data support
|
||||
---------------------
|
||||
|
||||
The driver supports standard PMBus driver platform data.
|
||||
|
||||
|
||||
Sysfs entries
|
||||
-------------
|
||||
|
||||
The following attributes are supported.
|
||||
|
||||
in[1-2]_label "vout[1-2]"
|
||||
in[1-2]_input Measured voltage. From READ_VOUT register.
|
||||
in[1-2]_alarm voltage alarm.
|
||||
|
||||
curr[1-2]_input Measured current. From READ_IOUT register.
|
||||
curr[1-2]_label "iout[1-2]"
|
||||
curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register.
|
||||
curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register.
|
||||
curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT status.
|
||||
curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status.
|
||||
curr2_alarm Current high alarm. From IOUT_OC_WARNING status.
|
||||
|
||||
temp1_input Measured temperature. From READ_TEMPERATURE_2 register on page 0.
|
||||
temp1_max Maximum temperature. From OT_WARN_LIMIT register.
|
||||
temp1_crit Critical high temperature. From OT_FAULT_LIMIT register.
|
||||
temp1_max_alarm Chip temperature high alarm. Set by comparing
|
||||
READ_TEMPERATURE_2 on page 0 with OT_WARN_LIMIT if TEMP_OT_WARNING
|
||||
status is set.
|
||||
temp1_crit_alarm Chip temperature critical high alarm. Set by comparing
|
||||
READ_TEMPERATURE_2 on page 0 with OT_FAULT_LIMIT if TEMP_OT_FAULT
|
||||
status is set.
|
||||
temp2_input Measured temperature. From READ_TEMPERATURE_2 register on page 1.
|
||||
temp2_alarm Chip temperature alarm on page 1.
|
||||
+51
-6
@@ -554,6 +554,17 @@ config SENSORS_IBMPEX
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called ibmpex.
|
||||
|
||||
config SENSORS_IBMPOWERNV
|
||||
tristate "IBM POWERNV platform sensors"
|
||||
depends on PPC_POWERNV
|
||||
default y
|
||||
help
|
||||
If you say yes here you get support for the temperature/fan/power
|
||||
sensors on your PowerNV platform.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called ibmpowernv.
|
||||
|
||||
config SENSORS_IIO_HWMON
|
||||
tristate "Hwmon driver that uses channels specified via iio maps"
|
||||
depends on IIO
|
||||
@@ -608,6 +619,18 @@ config SENSORS_JC42
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called jc42.
|
||||
|
||||
config SENSORS_POWR1220
|
||||
tristate "Lattice POWR1220 Power Monitoring"
|
||||
depends on I2C
|
||||
default n
|
||||
help
|
||||
If you say yes here you get access to the hardware monitoring
|
||||
functions of the Lattice POWR1220 isp Power Supply Monitoring,
|
||||
Sequencing and Margining Controller.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called powr1220.
|
||||
|
||||
config SENSORS_LINEAGE
|
||||
tristate "Lineage Compact Power Line Power Entry Module"
|
||||
depends on I2C
|
||||
@@ -882,8 +905,8 @@ config SENSORS_LM75
|
||||
- NXP's LM75A
|
||||
- ST Microelectronics STDS75
|
||||
- TelCom (now Microchip) TCN75
|
||||
- Texas Instruments TMP100, TMP101, TMP105, TMP75, TMP175,
|
||||
TMP275
|
||||
- Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75,
|
||||
TMP175, TMP275
|
||||
|
||||
This driver supports driver model based binding through board
|
||||
specific I2C device tables.
|
||||
@@ -1061,7 +1084,7 @@ config SENSORS_NTC_THERMISTOR
|
||||
|
||||
Currently, this driver supports
|
||||
NCP15WB473, NCP18WB473, NCP21WB473, NCP03WB473, and NCP15WL333
|
||||
from Murata.
|
||||
from Murata and B57330V2103 from EPCOS.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called ntc-thermistor.
|
||||
@@ -1082,8 +1105,8 @@ config SENSORS_NCT6775
|
||||
select HWMON_VID
|
||||
help
|
||||
If you say yes here you get support for the hardware monitoring
|
||||
functionality of the Nuvoton NCT6775F, NCT6776F, NCT6779D
|
||||
and compatible Super-I/O chips. This driver replaces the
|
||||
functionality of the Nuvoton NCT6106D, NCT6775F, NCT6776F, NCT6779D,
|
||||
NCT6791D and compatible Super-I/O chips. This driver replaces the
|
||||
w83627ehf driver for NCT6775F and NCT6776F.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
@@ -1105,6 +1128,17 @@ config SENSORS_PCF8591
|
||||
|
||||
source drivers/hwmon/pmbus/Kconfig
|
||||
|
||||
config SENSORS_PWM_FAN
|
||||
tristate "PWM fan"
|
||||
depends on (PWM && OF) || COMPILE_TEST
|
||||
help
|
||||
If you say yes here you get support for fans connected to PWM lines.
|
||||
The driver uses the generic PWM interface, thus it will work on a
|
||||
variety of SoCs.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called pwm-fan.
|
||||
|
||||
config SENSORS_SHT15
|
||||
tristate "Sensiron humidity and temperature sensors. SHT15 and compat."
|
||||
depends on GPIOLIB
|
||||
@@ -1393,6 +1427,17 @@ config SENSORS_TMP102
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called tmp102.
|
||||
|
||||
config SENSORS_TMP103
|
||||
tristate "Texas Instruments TMP103"
|
||||
depends on I2C
|
||||
select REGMAP_I2C
|
||||
help
|
||||
If you say yes here you get support for Texas Instruments TMP103
|
||||
sensor chips.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called tmp103.
|
||||
|
||||
config SENSORS_TMP401
|
||||
tristate "Texas Instruments TMP401 and compatibles"
|
||||
depends on I2C
|
||||
@@ -1408,7 +1453,7 @@ config SENSORS_TMP421
|
||||
depends on I2C
|
||||
help
|
||||
If you say yes here you get support for Texas Instruments TMP421,
|
||||
TMP422 and TMP423 temperature sensor chips.
|
||||
TMP422, TMP423, TMP441, and TMP442 temperature sensor chips.
|
||||
|
||||
This driver can also be built as a module. If so, the module
|
||||
will be called tmp421.
|
||||
|
||||
@@ -71,6 +71,7 @@ obj-$(CONFIG_SENSORS_ULTRA45) += ultra45_env.o
|
||||
obj-$(CONFIG_SENSORS_I5K_AMB) += i5k_amb.o
|
||||
obj-$(CONFIG_SENSORS_IBMAEM) += ibmaem.o
|
||||
obj-$(CONFIG_SENSORS_IBMPEX) += ibmpex.o
|
||||
obj-$(CONFIG_SENSORS_IBMPOWERNV)+= ibmpowernv.o
|
||||
obj-$(CONFIG_SENSORS_IIO_HWMON) += iio_hwmon.o
|
||||
obj-$(CONFIG_SENSORS_INA209) += ina209.o
|
||||
obj-$(CONFIG_SENSORS_INA2XX) += ina2xx.o
|
||||
@@ -120,6 +121,8 @@ obj-$(CONFIG_SENSORS_NTC_THERMISTOR) += ntc_thermistor.o
|
||||
obj-$(CONFIG_SENSORS_PC87360) += pc87360.o
|
||||
obj-$(CONFIG_SENSORS_PC87427) += pc87427.o
|
||||
obj-$(CONFIG_SENSORS_PCF8591) += pcf8591.o
|
||||
obj-$(CONFIG_SENSORS_POWR1220) += powr1220.o
|
||||
obj-$(CONFIG_SENSORS_PWM_FAN) += pwm-fan.o
|
||||
obj-$(CONFIG_SENSORS_S3C) += s3c-hwmon.o
|
||||
obj-$(CONFIG_SENSORS_SCH56XX_COMMON)+= sch56xx-common.o
|
||||
obj-$(CONFIG_SENSORS_SCH5627) += sch5627.o
|
||||
@@ -135,6 +138,7 @@ obj-$(CONFIG_SENSORS_SMSC47M192)+= smsc47m192.o
|
||||
obj-$(CONFIG_SENSORS_AMC6821) += amc6821.o
|
||||
obj-$(CONFIG_SENSORS_THMC50) += thmc50.o
|
||||
obj-$(CONFIG_SENSORS_TMP102) += tmp102.o
|
||||
obj-$(CONFIG_SENSORS_TMP103) += tmp103.o
|
||||
obj-$(CONFIG_SENSORS_TMP401) += tmp401.o
|
||||
obj-$(CONFIG_SENSORS_TMP421) += tmp421.o
|
||||
obj-$(CONFIG_SENSORS_TWL4030_MADC)+= twl4030-madc-hwmon.o
|
||||
|
||||
+16
-41
@@ -39,7 +39,7 @@
|
||||
static u8 AD7414_REG_LIMIT[] = { AD7414_REG_T_HIGH, AD7414_REG_T_LOW };
|
||||
|
||||
struct ad7414_data {
|
||||
struct device *hwmon_dev;
|
||||
struct i2c_client *client;
|
||||
struct mutex lock; /* atomic read data updates */
|
||||
char valid; /* !=0 if following fields are valid */
|
||||
unsigned long next_update; /* In jiffies */
|
||||
@@ -72,8 +72,8 @@ static inline int ad7414_write(struct i2c_client *client, u8 reg, u8 value)
|
||||
|
||||
static struct ad7414_data *ad7414_update_device(struct device *dev)
|
||||
{
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct ad7414_data *data = i2c_get_clientdata(client);
|
||||
struct ad7414_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
|
||||
mutex_lock(&data->lock);
|
||||
|
||||
@@ -127,8 +127,8 @@ static ssize_t set_max_min(struct device *dev,
|
||||
struct device_attribute *attr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct ad7414_data *data = i2c_get_clientdata(client);
|
||||
struct ad7414_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
int index = to_sensor_dev_attr(attr)->index;
|
||||
u8 reg = AD7414_REG_LIMIT[index];
|
||||
long temp;
|
||||
@@ -164,7 +164,7 @@ static ssize_t show_alarm(struct device *dev, struct device_attribute *attr,
|
||||
static SENSOR_DEVICE_ATTR(temp1_min_alarm, S_IRUGO, show_alarm, NULL, 3);
|
||||
static SENSOR_DEVICE_ATTR(temp1_max_alarm, S_IRUGO, show_alarm, NULL, 4);
|
||||
|
||||
static struct attribute *ad7414_attributes[] = {
|
||||
static struct attribute *ad7414_attrs[] = {
|
||||
&sensor_dev_attr_temp1_input.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_max.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_min.dev_attr.attr,
|
||||
@@ -173,27 +173,25 @@ static struct attribute *ad7414_attributes[] = {
|
||||
NULL
|
||||
};
|
||||
|
||||
static const struct attribute_group ad7414_group = {
|
||||
.attrs = ad7414_attributes,
|
||||
};
|
||||
ATTRIBUTE_GROUPS(ad7414);
|
||||
|
||||
static int ad7414_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *dev_id)
|
||||
{
|
||||
struct device *dev = &client->dev;
|
||||
struct ad7414_data *data;
|
||||
struct device *hwmon_dev;
|
||||
int conf;
|
||||
int err;
|
||||
|
||||
if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_BYTE_DATA |
|
||||
I2C_FUNC_SMBUS_READ_WORD_DATA))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
data = devm_kzalloc(&client->dev, sizeof(struct ad7414_data),
|
||||
GFP_KERNEL);
|
||||
data = devm_kzalloc(dev, sizeof(struct ad7414_data), GFP_KERNEL);
|
||||
if (!data)
|
||||
return -ENOMEM;
|
||||
|
||||
i2c_set_clientdata(client, data);
|
||||
data->client = client;
|
||||
mutex_init(&data->lock);
|
||||
|
||||
dev_info(&client->dev, "chip found\n");
|
||||
@@ -201,38 +199,16 @@ static int ad7414_probe(struct i2c_client *client,
|
||||
/* Make sure the chip is powered up. */
|
||||
conf = i2c_smbus_read_byte_data(client, AD7414_REG_CONF);
|
||||
if (conf < 0)
|
||||
dev_warn(&client->dev,
|
||||
"ad7414_probe unable to read config register.\n");
|
||||
dev_warn(dev, "ad7414_probe unable to read config register.\n");
|
||||
else {
|
||||
conf &= ~(1 << 7);
|
||||
i2c_smbus_write_byte_data(client, AD7414_REG_CONF, conf);
|
||||
}
|
||||
|
||||
/* Register sysfs hooks */
|
||||
err = sysfs_create_group(&client->dev.kobj, &ad7414_group);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
data->hwmon_dev = hwmon_device_register(&client->dev);
|
||||
if (IS_ERR(data->hwmon_dev)) {
|
||||
err = PTR_ERR(data->hwmon_dev);
|
||||
goto exit_remove;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
exit_remove:
|
||||
sysfs_remove_group(&client->dev.kobj, &ad7414_group);
|
||||
return err;
|
||||
}
|
||||
|
||||
static int ad7414_remove(struct i2c_client *client)
|
||||
{
|
||||
struct ad7414_data *data = i2c_get_clientdata(client);
|
||||
|
||||
hwmon_device_unregister(data->hwmon_dev);
|
||||
sysfs_remove_group(&client->dev.kobj, &ad7414_group);
|
||||
return 0;
|
||||
hwmon_dev = devm_hwmon_device_register_with_groups(dev,
|
||||
client->name,
|
||||
data, ad7414_groups);
|
||||
return PTR_ERR_OR_ZERO(hwmon_dev);
|
||||
}
|
||||
|
||||
static const struct i2c_device_id ad7414_id[] = {
|
||||
@@ -246,7 +222,6 @@ static struct i2c_driver ad7414_driver = {
|
||||
.name = "ad7414",
|
||||
},
|
||||
.probe = ad7414_probe,
|
||||
.remove = ad7414_remove,
|
||||
.id_table = ad7414_id,
|
||||
};
|
||||
|
||||
|
||||
+56
-77
@@ -44,8 +44,7 @@ static const u8 AD7418_REG_TEMP[] = { AD7418_REG_TEMP_IN,
|
||||
AD7418_REG_TEMP_OS };
|
||||
|
||||
struct ad7418_data {
|
||||
struct device *hwmon_dev;
|
||||
struct attribute_group attrs;
|
||||
struct i2c_client *client;
|
||||
enum chips type;
|
||||
struct mutex lock;
|
||||
int adc_max; /* number of ADC channels */
|
||||
@@ -55,48 +54,10 @@ struct ad7418_data {
|
||||
u16 in[4];
|
||||
};
|
||||
|
||||
static int ad7418_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id);
|
||||
static int ad7418_remove(struct i2c_client *client);
|
||||
|
||||
static const struct i2c_device_id ad7418_id[] = {
|
||||
{ "ad7416", ad7416 },
|
||||
{ "ad7417", ad7417 },
|
||||
{ "ad7418", ad7418 },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(i2c, ad7418_id);
|
||||
|
||||
static struct i2c_driver ad7418_driver = {
|
||||
.driver = {
|
||||
.name = "ad7418",
|
||||
},
|
||||
.probe = ad7418_probe,
|
||||
.remove = ad7418_remove,
|
||||
.id_table = ad7418_id,
|
||||
};
|
||||
|
||||
static void ad7418_init_client(struct i2c_client *client)
|
||||
{
|
||||
struct ad7418_data *data = i2c_get_clientdata(client);
|
||||
|
||||
int reg = i2c_smbus_read_byte_data(client, AD7418_REG_CONF);
|
||||
if (reg < 0) {
|
||||
dev_err(&client->dev, "cannot read configuration register\n");
|
||||
} else {
|
||||
dev_info(&client->dev, "configuring for mode 1\n");
|
||||
i2c_smbus_write_byte_data(client, AD7418_REG_CONF, reg & 0xfe);
|
||||
|
||||
if (data->type == ad7417 || data->type == ad7418)
|
||||
i2c_smbus_write_byte_data(client,
|
||||
AD7418_REG_CONF2, 0x00);
|
||||
}
|
||||
}
|
||||
|
||||
static struct ad7418_data *ad7418_update_device(struct device *dev)
|
||||
{
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct ad7418_data *data = i2c_get_clientdata(client);
|
||||
struct ad7418_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
|
||||
mutex_lock(&data->lock);
|
||||
|
||||
@@ -165,8 +126,8 @@ static ssize_t set_temp(struct device *dev, struct device_attribute *devattr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct ad7418_data *data = i2c_get_clientdata(client);
|
||||
struct ad7418_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
long temp;
|
||||
int ret = kstrtol(buf, 10, &temp);
|
||||
|
||||
@@ -193,14 +154,15 @@ static SENSOR_DEVICE_ATTR(in2_input, S_IRUGO, show_adc, NULL, 1);
|
||||
static SENSOR_DEVICE_ATTR(in3_input, S_IRUGO, show_adc, NULL, 2);
|
||||
static SENSOR_DEVICE_ATTR(in4_input, S_IRUGO, show_adc, NULL, 3);
|
||||
|
||||
static struct attribute *ad7416_attributes[] = {
|
||||
static struct attribute *ad7416_attrs[] = {
|
||||
&sensor_dev_attr_temp1_max.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_max_hyst.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_input.dev_attr.attr,
|
||||
NULL
|
||||
};
|
||||
ATTRIBUTE_GROUPS(ad7416);
|
||||
|
||||
static struct attribute *ad7417_attributes[] = {
|
||||
static struct attribute *ad7417_attrs[] = {
|
||||
&sensor_dev_attr_temp1_max.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_max_hyst.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_input.dev_attr.attr,
|
||||
@@ -210,83 +172,100 @@ static struct attribute *ad7417_attributes[] = {
|
||||
&sensor_dev_attr_in4_input.dev_attr.attr,
|
||||
NULL
|
||||
};
|
||||
ATTRIBUTE_GROUPS(ad7417);
|
||||
|
||||
static struct attribute *ad7418_attributes[] = {
|
||||
static struct attribute *ad7418_attrs[] = {
|
||||
&sensor_dev_attr_temp1_max.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_max_hyst.dev_attr.attr,
|
||||
&sensor_dev_attr_temp1_input.dev_attr.attr,
|
||||
&sensor_dev_attr_in1_input.dev_attr.attr,
|
||||
NULL
|
||||
};
|
||||
ATTRIBUTE_GROUPS(ad7418);
|
||||
|
||||
static void ad7418_init_client(struct i2c_client *client)
|
||||
{
|
||||
struct ad7418_data *data = i2c_get_clientdata(client);
|
||||
|
||||
int reg = i2c_smbus_read_byte_data(client, AD7418_REG_CONF);
|
||||
if (reg < 0) {
|
||||
dev_err(&client->dev, "cannot read configuration register\n");
|
||||
} else {
|
||||
dev_info(&client->dev, "configuring for mode 1\n");
|
||||
i2c_smbus_write_byte_data(client, AD7418_REG_CONF, reg & 0xfe);
|
||||
|
||||
if (data->type == ad7417 || data->type == ad7418)
|
||||
i2c_smbus_write_byte_data(client,
|
||||
AD7418_REG_CONF2, 0x00);
|
||||
}
|
||||
}
|
||||
|
||||
static int ad7418_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id)
|
||||
{
|
||||
struct device *dev = &client->dev;
|
||||
struct i2c_adapter *adapter = client->adapter;
|
||||
struct ad7418_data *data;
|
||||
int err;
|
||||
struct device *hwmon_dev;
|
||||
const struct attribute_group **attr_groups = NULL;
|
||||
|
||||
if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA |
|
||||
I2C_FUNC_SMBUS_WORD_DATA))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
data = devm_kzalloc(&client->dev, sizeof(struct ad7418_data),
|
||||
GFP_KERNEL);
|
||||
data = devm_kzalloc(dev, sizeof(struct ad7418_data), GFP_KERNEL);
|
||||
if (!data)
|
||||
return -ENOMEM;
|
||||
|
||||
i2c_set_clientdata(client, data);
|
||||
|
||||
mutex_init(&data->lock);
|
||||
data->client = client;
|
||||
data->type = id->driver_data;
|
||||
|
||||
switch (data->type) {
|
||||
case ad7416:
|
||||
data->adc_max = 0;
|
||||
data->attrs.attrs = ad7416_attributes;
|
||||
attr_groups = ad7416_groups;
|
||||
break;
|
||||
|
||||
case ad7417:
|
||||
data->adc_max = 4;
|
||||
data->attrs.attrs = ad7417_attributes;
|
||||
attr_groups = ad7417_groups;
|
||||
break;
|
||||
|
||||
case ad7418:
|
||||
data->adc_max = 1;
|
||||
data->attrs.attrs = ad7418_attributes;
|
||||
attr_groups = ad7418_groups;
|
||||
break;
|
||||
}
|
||||
|
||||
dev_info(&client->dev, "%s chip found\n", client->name);
|
||||
dev_info(dev, "%s chip found\n", client->name);
|
||||
|
||||
/* Initialize the AD7418 chip */
|
||||
ad7418_init_client(client);
|
||||
|
||||
/* Register sysfs hooks */
|
||||
err = sysfs_create_group(&client->dev.kobj, &data->attrs);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
data->hwmon_dev = hwmon_device_register(&client->dev);
|
||||
if (IS_ERR(data->hwmon_dev)) {
|
||||
err = PTR_ERR(data->hwmon_dev);
|
||||
goto exit_remove;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
exit_remove:
|
||||
sysfs_remove_group(&client->dev.kobj, &data->attrs);
|
||||
return err;
|
||||
hwmon_dev = devm_hwmon_device_register_with_groups(dev,
|
||||
client->name,
|
||||
data, attr_groups);
|
||||
return PTR_ERR_OR_ZERO(hwmon_dev);
|
||||
}
|
||||
|
||||
static int ad7418_remove(struct i2c_client *client)
|
||||
{
|
||||
struct ad7418_data *data = i2c_get_clientdata(client);
|
||||
hwmon_device_unregister(data->hwmon_dev);
|
||||
sysfs_remove_group(&client->dev.kobj, &data->attrs);
|
||||
return 0;
|
||||
}
|
||||
static const struct i2c_device_id ad7418_id[] = {
|
||||
{ "ad7416", ad7416 },
|
||||
{ "ad7417", ad7417 },
|
||||
{ "ad7418", ad7418 },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(i2c, ad7418_id);
|
||||
|
||||
static struct i2c_driver ad7418_driver = {
|
||||
.driver = {
|
||||
.name = "ad7418",
|
||||
},
|
||||
.probe = ad7418_probe,
|
||||
.id_table = ad7418_id,
|
||||
};
|
||||
|
||||
module_i2c_driver(ad7418_driver);
|
||||
|
||||
|
||||
+83
-92
@@ -98,41 +98,63 @@ struct adm1021_data {
|
||||
u8 remote_temp_offset_prec;
|
||||
};
|
||||
|
||||
static int adm1021_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id);
|
||||
static int adm1021_detect(struct i2c_client *client,
|
||||
struct i2c_board_info *info);
|
||||
static void adm1021_init_client(struct i2c_client *client);
|
||||
static struct adm1021_data *adm1021_update_device(struct device *dev);
|
||||
|
||||
/* (amalysh) read only mode, otherwise any limit's writing confuse BIOS */
|
||||
static bool read_only;
|
||||
|
||||
static struct adm1021_data *adm1021_update_device(struct device *dev)
|
||||
{
|
||||
struct adm1021_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
|
||||
static const struct i2c_device_id adm1021_id[] = {
|
||||
{ "adm1021", adm1021 },
|
||||
{ "adm1023", adm1023 },
|
||||
{ "max1617", max1617 },
|
||||
{ "max1617a", max1617a },
|
||||
{ "thmc10", thmc10 },
|
||||
{ "lm84", lm84 },
|
||||
{ "gl523sm", gl523sm },
|
||||
{ "mc1066", mc1066 },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(i2c, adm1021_id);
|
||||
mutex_lock(&data->update_lock);
|
||||
|
||||
/* This is the driver that will be inserted */
|
||||
static struct i2c_driver adm1021_driver = {
|
||||
.class = I2C_CLASS_HWMON,
|
||||
.driver = {
|
||||
.name = "adm1021",
|
||||
},
|
||||
.probe = adm1021_probe,
|
||||
.id_table = adm1021_id,
|
||||
.detect = adm1021_detect,
|
||||
.address_list = normal_i2c,
|
||||
};
|
||||
if (time_after(jiffies, data->last_updated + HZ + HZ / 2)
|
||||
|| !data->valid) {
|
||||
int i;
|
||||
|
||||
dev_dbg(dev, "Starting adm1021 update\n");
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
data->temp[i] = 1000 *
|
||||
(s8) i2c_smbus_read_byte_data(
|
||||
client, ADM1021_REG_TEMP(i));
|
||||
data->temp_max[i] = 1000 *
|
||||
(s8) i2c_smbus_read_byte_data(
|
||||
client, ADM1021_REG_TOS_R(i));
|
||||
if (data->type != lm84) {
|
||||
data->temp_min[i] = 1000 *
|
||||
(s8) i2c_smbus_read_byte_data(client,
|
||||
ADM1021_REG_THYST_R(i));
|
||||
}
|
||||
}
|
||||
data->alarms = i2c_smbus_read_byte_data(client,
|
||||
ADM1021_REG_STATUS) & 0x7c;
|
||||
if (data->type == adm1023) {
|
||||
/*
|
||||
* The ADM1023 provides 3 extra bits of precision for
|
||||
* the remote sensor in extra registers.
|
||||
*/
|
||||
data->temp[1] += 125 * (i2c_smbus_read_byte_data(
|
||||
client, ADM1023_REG_REM_TEMP_PREC) >> 5);
|
||||
data->temp_max[1] += 125 * (i2c_smbus_read_byte_data(
|
||||
client, ADM1023_REG_REM_TOS_PREC) >> 5);
|
||||
data->temp_min[1] += 125 * (i2c_smbus_read_byte_data(
|
||||
client, ADM1023_REG_REM_THYST_PREC) >> 5);
|
||||
data->remote_temp_offset =
|
||||
i2c_smbus_read_byte_data(client,
|
||||
ADM1023_REG_REM_OFFSET);
|
||||
data->remote_temp_offset_prec =
|
||||
i2c_smbus_read_byte_data(client,
|
||||
ADM1023_REG_REM_OFFSET_PREC);
|
||||
}
|
||||
data->last_updated = jiffies;
|
||||
data->valid = 1;
|
||||
}
|
||||
|
||||
mutex_unlock(&data->update_lock);
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
static ssize_t show_temp(struct device *dev,
|
||||
struct device_attribute *devattr, char *buf)
|
||||
@@ -411,6 +433,15 @@ static int adm1021_detect(struct i2c_client *client,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void adm1021_init_client(struct i2c_client *client)
|
||||
{
|
||||
/* Enable ADC and disable suspend mode */
|
||||
i2c_smbus_write_byte_data(client, ADM1021_REG_CONFIG_W,
|
||||
i2c_smbus_read_byte_data(client, ADM1021_REG_CONFIG_R) & 0xBF);
|
||||
/* Set Conversion rate to 1/sec (this can be tinkered with) */
|
||||
i2c_smbus_write_byte_data(client, ADM1021_REG_CONV_RATE_W, 0x04);
|
||||
}
|
||||
|
||||
static int adm1021_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id)
|
||||
{
|
||||
@@ -440,69 +471,29 @@ static int adm1021_probe(struct i2c_client *client,
|
||||
return PTR_ERR_OR_ZERO(hwmon_dev);
|
||||
}
|
||||
|
||||
static void adm1021_init_client(struct i2c_client *client)
|
||||
{
|
||||
/* Enable ADC and disable suspend mode */
|
||||
i2c_smbus_write_byte_data(client, ADM1021_REG_CONFIG_W,
|
||||
i2c_smbus_read_byte_data(client, ADM1021_REG_CONFIG_R) & 0xBF);
|
||||
/* Set Conversion rate to 1/sec (this can be tinkered with) */
|
||||
i2c_smbus_write_byte_data(client, ADM1021_REG_CONV_RATE_W, 0x04);
|
||||
}
|
||||
static const struct i2c_device_id adm1021_id[] = {
|
||||
{ "adm1021", adm1021 },
|
||||
{ "adm1023", adm1023 },
|
||||
{ "max1617", max1617 },
|
||||
{ "max1617a", max1617a },
|
||||
{ "thmc10", thmc10 },
|
||||
{ "lm84", lm84 },
|
||||
{ "gl523sm", gl523sm },
|
||||
{ "mc1066", mc1066 },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(i2c, adm1021_id);
|
||||
|
||||
static struct adm1021_data *adm1021_update_device(struct device *dev)
|
||||
{
|
||||
struct adm1021_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
|
||||
mutex_lock(&data->update_lock);
|
||||
|
||||
if (time_after(jiffies, data->last_updated + HZ + HZ / 2)
|
||||
|| !data->valid) {
|
||||
int i;
|
||||
|
||||
dev_dbg(dev, "Starting adm1021 update\n");
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
data->temp[i] = 1000 *
|
||||
(s8) i2c_smbus_read_byte_data(
|
||||
client, ADM1021_REG_TEMP(i));
|
||||
data->temp_max[i] = 1000 *
|
||||
(s8) i2c_smbus_read_byte_data(
|
||||
client, ADM1021_REG_TOS_R(i));
|
||||
if (data->type != lm84) {
|
||||
data->temp_min[i] = 1000 *
|
||||
(s8) i2c_smbus_read_byte_data(client,
|
||||
ADM1021_REG_THYST_R(i));
|
||||
}
|
||||
}
|
||||
data->alarms = i2c_smbus_read_byte_data(client,
|
||||
ADM1021_REG_STATUS) & 0x7c;
|
||||
if (data->type == adm1023) {
|
||||
/*
|
||||
* The ADM1023 provides 3 extra bits of precision for
|
||||
* the remote sensor in extra registers.
|
||||
*/
|
||||
data->temp[1] += 125 * (i2c_smbus_read_byte_data(
|
||||
client, ADM1023_REG_REM_TEMP_PREC) >> 5);
|
||||
data->temp_max[1] += 125 * (i2c_smbus_read_byte_data(
|
||||
client, ADM1023_REG_REM_TOS_PREC) >> 5);
|
||||
data->temp_min[1] += 125 * (i2c_smbus_read_byte_data(
|
||||
client, ADM1023_REG_REM_THYST_PREC) >> 5);
|
||||
data->remote_temp_offset =
|
||||
i2c_smbus_read_byte_data(client,
|
||||
ADM1023_REG_REM_OFFSET);
|
||||
data->remote_temp_offset_prec =
|
||||
i2c_smbus_read_byte_data(client,
|
||||
ADM1023_REG_REM_OFFSET_PREC);
|
||||
}
|
||||
data->last_updated = jiffies;
|
||||
data->valid = 1;
|
||||
}
|
||||
|
||||
mutex_unlock(&data->update_lock);
|
||||
|
||||
return data;
|
||||
}
|
||||
static struct i2c_driver adm1021_driver = {
|
||||
.class = I2C_CLASS_HWMON,
|
||||
.driver = {
|
||||
.name = "adm1021",
|
||||
},
|
||||
.probe = adm1021_probe,
|
||||
.id_table = adm1021_id,
|
||||
.detect = adm1021_detect,
|
||||
.address_list = normal_i2c,
|
||||
};
|
||||
|
||||
module_i2c_driver(adm1021_driver);
|
||||
|
||||
|
||||
+97
-138
@@ -102,47 +102,13 @@ static const int in_scale[6] = { 2500, 2250, 3300, 5000, 12000, 3300 };
|
||||
(((val) < 0 ? (val) - 500 : \
|
||||
(val) + 500) / 1000))
|
||||
|
||||
/*
|
||||
* Functions declaration
|
||||
*/
|
||||
|
||||
static int adm1025_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id);
|
||||
static int adm1025_detect(struct i2c_client *client,
|
||||
struct i2c_board_info *info);
|
||||
static void adm1025_init_client(struct i2c_client *client);
|
||||
static int adm1025_remove(struct i2c_client *client);
|
||||
static struct adm1025_data *adm1025_update_device(struct device *dev);
|
||||
|
||||
/*
|
||||
* Driver data (common to all clients)
|
||||
*/
|
||||
|
||||
static const struct i2c_device_id adm1025_id[] = {
|
||||
{ "adm1025", adm1025 },
|
||||
{ "ne1619", ne1619 },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(i2c, adm1025_id);
|
||||
|
||||
static struct i2c_driver adm1025_driver = {
|
||||
.class = I2C_CLASS_HWMON,
|
||||
.driver = {
|
||||
.name = "adm1025",
|
||||
},
|
||||
.probe = adm1025_probe,
|
||||
.remove = adm1025_remove,
|
||||
.id_table = adm1025_id,
|
||||
.detect = adm1025_detect,
|
||||
.address_list = normal_i2c,
|
||||
};
|
||||
|
||||
/*
|
||||
* Client data (each client gets its own)
|
||||
*/
|
||||
|
||||
struct adm1025_data {
|
||||
struct device *hwmon_dev;
|
||||
struct i2c_client *client;
|
||||
const struct attribute_group *groups[3];
|
||||
struct mutex update_lock;
|
||||
char valid; /* zero until following fields are valid */
|
||||
unsigned long last_updated; /* in jiffies */
|
||||
@@ -158,6 +124,51 @@ struct adm1025_data {
|
||||
u8 vrm;
|
||||
};
|
||||
|
||||
static struct adm1025_data *adm1025_update_device(struct device *dev)
|
||||
{
|
||||
struct adm1025_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
|
||||
mutex_lock(&data->update_lock);
|
||||
|
||||
if (time_after(jiffies, data->last_updated + HZ * 2) || !data->valid) {
|
||||
int i;
|
||||
|
||||
dev_dbg(&client->dev, "Updating data.\n");
|
||||
for (i = 0; i < 6; i++) {
|
||||
data->in[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_IN(i));
|
||||
data->in_min[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_IN_MIN(i));
|
||||
data->in_max[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_IN_MAX(i));
|
||||
}
|
||||
for (i = 0; i < 2; i++) {
|
||||
data->temp[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_TEMP(i));
|
||||
data->temp_min[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_TEMP_LOW(i));
|
||||
data->temp_max[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_TEMP_HIGH(i));
|
||||
}
|
||||
data->alarms = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_STATUS1)
|
||||
| (i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_STATUS2) << 8);
|
||||
data->vid = (i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_VID) & 0x0f)
|
||||
| ((i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_VID4) & 0x01) << 4);
|
||||
|
||||
data->last_updated = jiffies;
|
||||
data->valid = 1;
|
||||
}
|
||||
|
||||
mutex_unlock(&data->update_lock);
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
/*
|
||||
* Sysfs stuff
|
||||
*/
|
||||
@@ -217,8 +228,8 @@ static ssize_t set_in_min(struct device *dev, struct device_attribute *attr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
int index = to_sensor_dev_attr(attr)->index;
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct adm1025_data *data = i2c_get_clientdata(client);
|
||||
struct adm1025_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
long val;
|
||||
int err;
|
||||
|
||||
@@ -238,8 +249,8 @@ static ssize_t set_in_max(struct device *dev, struct device_attribute *attr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
int index = to_sensor_dev_attr(attr)->index;
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct adm1025_data *data = i2c_get_clientdata(client);
|
||||
struct adm1025_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
long val;
|
||||
int err;
|
||||
|
||||
@@ -273,8 +284,8 @@ static ssize_t set_temp_min(struct device *dev, struct device_attribute *attr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
int index = to_sensor_dev_attr(attr)->index;
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct adm1025_data *data = i2c_get_clientdata(client);
|
||||
struct adm1025_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
long val;
|
||||
int err;
|
||||
|
||||
@@ -294,8 +305,8 @@ static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
int index = to_sensor_dev_attr(attr)->index;
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct adm1025_data *data = i2c_get_clientdata(client);
|
||||
struct adm1025_data *data = dev_get_drvdata(dev);
|
||||
struct i2c_client *client = data->client;
|
||||
long val;
|
||||
int err;
|
||||
|
||||
@@ -470,51 +481,6 @@ static int adm1025_detect(struct i2c_client *client,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int adm1025_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id)
|
||||
{
|
||||
struct adm1025_data *data;
|
||||
int err;
|
||||
u8 config;
|
||||
|
||||
data = devm_kzalloc(&client->dev, sizeof(struct adm1025_data),
|
||||
GFP_KERNEL);
|
||||
if (!data)
|
||||
return -ENOMEM;
|
||||
|
||||
i2c_set_clientdata(client, data);
|
||||
mutex_init(&data->update_lock);
|
||||
|
||||
/* Initialize the ADM1025 chip */
|
||||
adm1025_init_client(client);
|
||||
|
||||
/* Register sysfs hooks */
|
||||
err = sysfs_create_group(&client->dev.kobj, &adm1025_group);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
/* Pin 11 is either in4 (+12V) or VID4 */
|
||||
config = i2c_smbus_read_byte_data(client, ADM1025_REG_CONFIG);
|
||||
if (!(config & 0x20)) {
|
||||
err = sysfs_create_group(&client->dev.kobj, &adm1025_group_in4);
|
||||
if (err)
|
||||
goto exit_remove;
|
||||
}
|
||||
|
||||
data->hwmon_dev = hwmon_device_register(&client->dev);
|
||||
if (IS_ERR(data->hwmon_dev)) {
|
||||
err = PTR_ERR(data->hwmon_dev);
|
||||
goto exit_remove;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
exit_remove:
|
||||
sysfs_remove_group(&client->dev.kobj, &adm1025_group);
|
||||
sysfs_remove_group(&client->dev.kobj, &adm1025_group_in4);
|
||||
return err;
|
||||
}
|
||||
|
||||
static void adm1025_init_client(struct i2c_client *client)
|
||||
{
|
||||
u8 reg;
|
||||
@@ -557,61 +523,54 @@ static void adm1025_init_client(struct i2c_client *client)
|
||||
(reg&0x7E)|0x01);
|
||||
}
|
||||
|
||||
static int adm1025_remove(struct i2c_client *client)
|
||||
static int adm1025_probe(struct i2c_client *client,
|
||||
const struct i2c_device_id *id)
|
||||
{
|
||||
struct adm1025_data *data = i2c_get_clientdata(client);
|
||||
struct device *dev = &client->dev;
|
||||
struct device *hwmon_dev;
|
||||
struct adm1025_data *data;
|
||||
u8 config;
|
||||
|
||||
hwmon_device_unregister(data->hwmon_dev);
|
||||
sysfs_remove_group(&client->dev.kobj, &adm1025_group);
|
||||
sysfs_remove_group(&client->dev.kobj, &adm1025_group_in4);
|
||||
data = devm_kzalloc(dev, sizeof(struct adm1025_data), GFP_KERNEL);
|
||||
if (!data)
|
||||
return -ENOMEM;
|
||||
|
||||
return 0;
|
||||
i2c_set_clientdata(client, data);
|
||||
data->client = client;
|
||||
mutex_init(&data->update_lock);
|
||||
|
||||
/* Initialize the ADM1025 chip */
|
||||
adm1025_init_client(client);
|
||||
|
||||
/* sysfs hooks */
|
||||
data->groups[0] = &adm1025_group;
|
||||
/* Pin 11 is either in4 (+12V) or VID4 */
|
||||
config = i2c_smbus_read_byte_data(client, ADM1025_REG_CONFIG);
|
||||
if (!(config & 0x20))
|
||||
data->groups[1] = &adm1025_group_in4;
|
||||
|
||||
hwmon_dev = devm_hwmon_device_register_with_groups(dev, client->name,
|
||||
data, data->groups);
|
||||
return PTR_ERR_OR_ZERO(hwmon_dev);
|
||||
}
|
||||
|
||||
static struct adm1025_data *adm1025_update_device(struct device *dev)
|
||||
{
|
||||
struct i2c_client *client = to_i2c_client(dev);
|
||||
struct adm1025_data *data = i2c_get_clientdata(client);
|
||||
static const struct i2c_device_id adm1025_id[] = {
|
||||
{ "adm1025", adm1025 },
|
||||
{ "ne1619", ne1619 },
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(i2c, adm1025_id);
|
||||
|
||||
mutex_lock(&data->update_lock);
|
||||
|
||||
if (time_after(jiffies, data->last_updated + HZ * 2) || !data->valid) {
|
||||
int i;
|
||||
|
||||
dev_dbg(&client->dev, "Updating data.\n");
|
||||
for (i = 0; i < 6; i++) {
|
||||
data->in[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_IN(i));
|
||||
data->in_min[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_IN_MIN(i));
|
||||
data->in_max[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_IN_MAX(i));
|
||||
}
|
||||
for (i = 0; i < 2; i++) {
|
||||
data->temp[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_TEMP(i));
|
||||
data->temp_min[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_TEMP_LOW(i));
|
||||
data->temp_max[i] = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_TEMP_HIGH(i));
|
||||
}
|
||||
data->alarms = i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_STATUS1)
|
||||
| (i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_STATUS2) << 8);
|
||||
data->vid = (i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_VID) & 0x0f)
|
||||
| ((i2c_smbus_read_byte_data(client,
|
||||
ADM1025_REG_VID4) & 0x01) << 4);
|
||||
|
||||
data->last_updated = jiffies;
|
||||
data->valid = 1;
|
||||
}
|
||||
|
||||
mutex_unlock(&data->update_lock);
|
||||
|
||||
return data;
|
||||
}
|
||||
static struct i2c_driver adm1025_driver = {
|
||||
.class = I2C_CLASS_HWMON,
|
||||
.driver = {
|
||||
.name = "adm1025",
|
||||
},
|
||||
.probe = adm1025_probe,
|
||||
.id_table = adm1025_id,
|
||||
.detect = adm1025_detect,
|
||||
.address_list = normal_i2c,
|
||||
};
|
||||
|
||||
module_i2c_driver(adm1025_driver);
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user