Merge master.kernel.org:/pub/scm/linux/kernel/git/gregkh/i2c-2.6

This commit is contained in:
Linus Torvalds 2005-09-06 00:31:02 -07:00
commit 8566cfc9fe
145 changed files with 4448 additions and 2767 deletions

View file

@ -2,16 +2,11 @@ Kernel driver lm78
==================
Supported chips:
* National Semiconductor LM78
* National Semiconductor LM78 / LM78-J
Prefix: 'lm78'
Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports)
Datasheet: Publicly available at the National Semiconductor website
http://www.national.com/
* National Semiconductor LM78-J
Prefix: 'lm78-j'
Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports)
Datasheet: Publicly available at the National Semiconductor website
http://www.national.com/
* National Semiconductor LM79
Prefix: 'lm79'
Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports)

174
Documentation/hwmon/w83792d Normal file
View file

@ -0,0 +1,174 @@
Kernel driver w83792d
=====================
Supported chips:
* Winbond W83792D
Prefix: 'w83792d'
Addresses scanned: I2C 0x2c - 0x2f
Datasheet: http://www.winbond.com.tw/E-WINBONDHTM/partner/PDFresult.asp?Pname=1035
Author: Chunhao Huang
Contact: DZShen <DZShen@Winbond.com.tw>
Module Parameters
-----------------
* init int
(default 1)
Use 'init=0' to bypass initializing the chip.
Try this if your computer crashes when you load the module.
* force_subclients=bus,caddr,saddr,saddr
This is used to force the i2c addresses for subclients of
a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b'
to force the subclients of chip 0x2f on bus 0 to i2c addresses
0x4a and 0x4b.
Description
-----------
This driver implements support for the Winbond W83792AD/D.
Detection of the chip can sometimes be foiled because it can be in an
internal state that allows no clean access (Bank with ID register is not
currently selected). If you know the address of the chip, use a 'force'
parameter; this will put it into a more well-behaved state first.
The driver implements three temperature sensors, seven fan rotation speed
sensors, nine voltage sensors, and two automatic fan regulation
strategies called: Smart Fan I (Thermal Cruise mode) and Smart Fan II.
Automatic fan control mode is possible only for fan1-fan3. Fan4-fan7 can run
synchronized with selected fan (fan1-fan3). This functionality and manual PWM
control for fan4-fan7 is not yet implemented.
Temperatures are measured in degrees Celsius and measurement resolution is 1
degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when
the temperature gets higher than the Overtemperature Shutdown value; it stays
on until the temperature falls below the Hysteresis value.
Fan rotation speeds are reported in RPM (rotations per minute). An alarm is
triggered if the rotation speed has dropped below a programmable limit. Fan
readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 or
128) to give the readings more range or accuracy.
Voltage sensors (also known as IN sensors) report their values in millivolts.
An alarm is triggered if the voltage has crossed a programmable minimum
or maximum limit.
Alarms are provided as output from "realtime status register". Following bits
are defined:
bit - alarm on:
0 - in0
1 - in1
2 - temp1
3 - temp2
4 - temp3
5 - fan1
6 - fan2
7 - fan3
8 - in2
9 - in3
10 - in4
11 - in5
12 - in6
13 - VID change
14 - chassis
15 - fan7
16 - tart1
17 - tart2
18 - tart3
19 - in7
20 - in8
21 - fan4
22 - fan5
23 - fan6
Tart will be asserted while target temperature cannot be achieved after 3 minutes
of full speed rotation of corresponding fan.
In addition to the alarms described above, there is a CHAS alarm on the chips
which triggers if your computer case is open (This one is latched, contrary
to realtime alarms).
The chips only update values each 3 seconds; reading them more often will
do no harm, but will return 'old' values.
W83792D PROBLEMS
----------------
Known problems:
- This driver is only for Winbond W83792D C version device, there
are also some motherboards with B version W83792D device. The
calculation method to in6-in7(measured value, limits) is a little
different between C and B version. C or B version can be identified
by CR[0x49h].
- The function of vid and vrm has not been finished, because I'm NOT
very familiar with them. Adding support is welcome.
  - The function of chassis open detection needs more tests.
- If you have ASUS server board and chip was not found: Then you will
need to upgrade to latest (or beta) BIOS. If it does not help please
contact us.
Fan control
-----------
Manual mode
-----------
Works as expected. You just need to specify desired PWM/DC value (fan speed)
in appropriate pwm# file.
Thermal cruise
--------------
In this mode, W83792D provides the Smart Fan system to automatically control
fan speed to keep the temperatures of CPU and the system within specific
range. At first a wanted temperature and interval must be set. This is done
via thermal_cruise# file. The tolerance# file serves to create T +- tolerance
interval. The fan speed will be lowered as long as the current temperature
remains below the thermal_cruise# +- tolerance# value. Once the temperature
exceeds the high limit (T+tolerance), the fan will be turned on with a
specific speed set by pwm# and automatically controlled its PWM duty cycle
with the temperature varying. Three conditions may occur:
(1) If the temperature still exceeds the high limit, PWM duty
cycle will increase slowly.
(2) If the temperature goes below the high limit, but still above the low
limit (T-tolerance), the fan speed will be fixed at the current speed because
the temperature is in the target range.
(3) If the temperature goes below the low limit, PWM duty cycle will decrease
slowly to 0 or a preset stop value until the temperature exceeds the low
limit. (The preset stop value handling is not yet implemented in driver)
Smart Fan II
------------
W83792D also provides a special mode for fan. Four temperature points are
available. When related temperature sensors detects the temperature in preset
temperature region (sf2_point@_fan# +- tolerance#) it will cause fans to run
on programmed value from sf2_level@_fan#. You need to set four temperatures
for each fan.
/sys files
----------
pwm[1-3] - this file stores PWM duty cycle or DC value (fan speed) in range:
0 (stop) to 255 (full)
pwm[1-3]_enable - this file controls mode of fan/temperature control:
* 0 Disabled
* 1 Manual mode
* 2 Smart Fan II
* 3 Thermal Cruise
pwm[1-3]_mode - Select PWM of DC mode
* 0 DC
* 1 PWM
thermal_cruise[1-3] - Selects the desired temperature for cruise (degC)
tolerance[1-3] - Value in degrees of Celsius (degC) for +- T
sf2_point[1-4]_fan[1-3] - four temperature points for each fan for Smart Fan II
sf2_level[1-3]_fan[1-3] - three PWM/DC levels for each fan for Smart Fan II

View file

@ -4,22 +4,13 @@ Kernel driver max6875
Supported chips:
* Maxim MAX6874, MAX6875
Prefix: 'max6875'
Addresses scanned: 0x50, 0x52
Addresses scanned: None (see below)
Datasheet:
http://pdfserv.maxim-ic.com/en/ds/MAX6874-MAX6875.pdf
Author: Ben Gardner <bgardner@wabtec.com>
Module Parameters
-----------------
* allow_write int
Set to non-zero to enable write permission:
*0: Read only
1: Read and write
Description
-----------
@ -33,34 +24,85 @@ registers.
The Maxim MAX6874 is a similar, mostly compatible device, with more intputs
and outputs:
vin gpi vout
MAX6874 6 4 8
MAX6875 4 3 5
MAX6874 chips can have four different addresses (as opposed to only two for
the MAX6875). The additional addresses (0x54 and 0x56) are not probed by
this driver by default, but the probe module parameter can be used if
needed.
See the datasheet for details on how to program the EEPROM.
See the datasheet for more information.
Sysfs entries
-------------
eeprom_user - 512 bytes of user-defined EEPROM space. Only writable if
allow_write was set and register 0x43 is 0.
eeprom_config - 70 bytes of config EEPROM. Note that changes will not get
loaded into register space until a power cycle or device reset.
reg_config - 70 bytes of register space. Any changes take affect immediately.
eeprom - 512 bytes of user-defined EEPROM space.
General Remarks
---------------
A typical application will require that the EEPROMs be programmed once and
never altered afterwards.
Valid addresses for the MAX6875 are 0x50 and 0x52.
Valid addresses for the MAX6874 are 0x50, 0x52, 0x54 and 0x56.
The driver does not probe any address, so you must force the address.
Example:
$ modprobe max6875 force=0,0x50
The MAX6874/MAX6875 ignores address bit 0, so this driver attaches to multiple
addresses. For example, for address 0x50, it also reserves 0x51.
The even-address instance is called 'max6875', the odd one is 'max6875 subclient'.
Programming the chip using i2c-dev
----------------------------------
Use the i2c-dev interface to access and program the chips.
Reads and writes are performed differently depending on the address range.
The configuration registers are at addresses 0x00 - 0x45.
Use i2c_smbus_write_byte_data() to write a register and
i2c_smbus_read_byte_data() to read a register.
The command is the register number.
Examples:
To write a 1 to register 0x45:
i2c_smbus_write_byte_data(fd, 0x45, 1);
To read register 0x45:
value = i2c_smbus_read_byte_data(fd, 0x45);
The configuration EEPROM is at addresses 0x8000 - 0x8045.
The user EEPROM is at addresses 0x8100 - 0x82ff.
Use i2c_smbus_write_word_data() to write a byte to EEPROM.
The command is the upper byte of the address: 0x80, 0x81, or 0x82.
The data word is the lower part of the address or'd with data << 8.
cmd = address >> 8;
val = (address & 0xff) | (data << 8);
Example:
To write 0x5a to address 0x8003:
i2c_smbus_write_word_data(fd, 0x80, 0x5a03);
Reading data from the EEPROM is a little more complicated.
Use i2c_smbus_write_byte_data() to set the read address and then
i2c_smbus_read_byte() or i2c_smbus_read_i2c_block_data() to read the data.
Example:
To read data starting at offset 0x8100, first set the address:
i2c_smbus_write_byte_data(fd, 0x81, 0x00);
And then read the data
value = i2c_smbus_read_byte(fd);
or
count = i2c_smbus_read_i2c_block_data(fd, 0x84, buffer);
The block read should read 16 bytes.
0x84 is the block read command.
See the datasheet for more details.

View file

@ -115,7 +115,7 @@ CHECKING THROUGH /DEV
If you try to access an adapter from a userspace program, you will have
to use the /dev interface. You will still have to check whether the
functionality you need is supported, of course. This is done using
the I2C_FUNCS ioctl. An example, adapted from the lm_sensors i2c_detect
the I2C_FUNCS ioctl. An example, adapted from the lm_sensors i2cdetect
program, is below:
int file;

View file

@ -1,4 +1,4 @@
Revision 4, 2004-03-30
Revision 5, 2005-07-29
Jean Delvare <khali@linux-fr.org>
Greg KH <greg@kroah.com>
@ -17,20 +17,22 @@ yours for best results.
Technical changes:
* [Includes] Get rid of "version.h". Replace <linux/i2c-proc.h> with
<linux/i2c-sensor.h>. Includes typically look like that:
* [Includes] Get rid of "version.h" and <linux/i2c-proc.h>.
Includes typically look like that:
#include <linux/module.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h> /* if you need VRM support */
#include <linux/hwmon.h> /* for hardware monitoring drivers */
#include <linux/hwmon-sysfs.h>
#include <linux/hwmon-vid.h> /* if you need VRM support */
#include <asm/io.h> /* if you have I/O operations */
Please respect this inclusion order. Some extra headers may be
required for a given driver (e.g. "lm75.h").
* [Addresses] SENSORS_I2C_END becomes I2C_CLIENT_END, SENSORS_ISA_END
becomes I2C_CLIENT_ISA_END.
* [Addresses] SENSORS_I2C_END becomes I2C_CLIENT_END, ISA addresses
are no more handled by the i2c core.
SENSORS_INSMOD_<n> becomes I2C_CLIENT_INSMOD_<n>.
* [Client data] Get rid of sysctl_id. Try using standard names for
register values (for example, temp_os becomes temp_max). You're
@ -66,13 +68,15 @@ Technical changes:
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
ISA-only drivers of course don't need this.
Call i2c_probe() instead of i2c_detect().
* [Detect] As mentioned earlier, the flags parameter is gone.
The type_name and client_name strings are replaced by a single
name string, which will be filled with a lowercase, short string
(typically the driver name, e.g. "lm75").
In i2c-only drivers, drop the i2c_is_isa_adapter check, it's
useless.
useless. Same for isa-only drivers, as the test would always be
true. Only hybrid drivers (which are quite rare) still need it.
The errorN labels are reduced to the number needed. If that number
is 2 (i2c-only drivers), it is advised that the labels are named
exit and exit_free. For i2c+isa drivers, labels should be named
@ -86,6 +90,8 @@ Technical changes:
device_create_file. Move the driver initialization before any
sysfs file creation.
Drop client->id.
Drop any 24RF08 corruption prevention you find, as this is now done
at the i2c-core level, and doing it twice voids it.
* [Init] Limits must not be set by the driver (can be done later in
user-space). Chip should not be reset default (although a module
@ -93,7 +99,8 @@ Technical changes:
limited to the strictly necessary steps.
* [Detach] Get rid of data, remove the call to
i2c_deregister_entry.
i2c_deregister_entry. Do not log an error message if
i2c_detach_client fails, as i2c-core will now do it for you.
* [Update] Don't access client->data directly, use
i2c_get_clientdata(client) instead.

View file

@ -148,15 +148,15 @@ are defined in i2c.h to help you support them, as well as a generic
detection algorithm.
You do not have to use this parameter interface; but don't try to use
function i2c_probe() (or i2c_detect()) if you don't.
function i2c_probe() if you don't.
NOTE: If you want to write a `sensors' driver, the interface is slightly
different! See below.
Probing classes (i2c)
---------------------
Probing classes
---------------
All parameters are given as lists of unsigned 16-bit integers. Lists are
terminated by I2C_CLIENT_END.
@ -171,12 +171,18 @@ The following lists are used internally:
ignore: insmod parameter.
A list of pairs. The first value is a bus number (-1 for any I2C bus),
the second is the I2C address. These addresses are never probed.
This parameter overrules 'normal' and 'probe', but not the 'force' lists.
This parameter overrules the 'normal_i2c' list only.
force: insmod parameter.
A list of pairs. The first value is a bus number (-1 for any I2C bus),
the second is the I2C address. A device is blindly assumed to be on
the given address, no probing is done.
Additionally, kind-specific force lists may optionally be defined if
the driver supports several chip kinds. They are grouped in a
NULL-terminated list of pointers named forces, those first element if the
generic force list mentioned above. Each additional list correspond to an
insmod parameter of the form force_<kind>.
Fortunately, as a module writer, you just have to define the `normal_i2c'
parameter. The complete declaration could look like this:
@ -186,66 +192,17 @@ parameter. The complete declaration could look like this:
/* Magic definition of all other variables and things */
I2C_CLIENT_INSMOD;
/* Or, if your driver supports, say, 2 kind of devices: */
I2C_CLIENT_INSMOD_2(foo, bar);
If you use the multi-kind form, an enum will be defined for you:
enum chips { any_chip, foo, bar, ... }
You can then (and certainly should) use it in the driver code.
Note that you *have* to call the defined variable `normal_i2c',
without any prefix!
Probing classes (sensors)
-------------------------
If you write a `sensors' driver, you use a slightly different interface.
As well as I2C addresses, we have to cope with ISA addresses. Also, we
use a enum of chip types. Don't forget to include `sensors.h'.
The following lists are used internally. They are all lists of integers.
normal_i2c: filled in by the module writer. Terminated by SENSORS_I2C_END.
A list of I2C addresses which should normally be examined.
normal_isa: filled in by the module writer. Terminated by SENSORS_ISA_END.
A list of ISA addresses which should normally be examined.
probe: insmod parameter. Initialize this list with SENSORS_I2C_END values.
A list of pairs. The first value is a bus number (SENSORS_ISA_BUS for
the ISA bus, -1 for any I2C bus), the second is the address. These
addresses are also probed, as if they were in the 'normal' list.
ignore: insmod parameter. Initialize this list with SENSORS_I2C_END values.
A list of pairs. The first value is a bus number (SENSORS_ISA_BUS for
the ISA bus, -1 for any I2C bus), the second is the I2C address. These
addresses are never probed. This parameter overrules 'normal' and
'probe', but not the 'force' lists.
Also used is a list of pointers to sensors_force_data structures:
force_data: insmod parameters. A list, ending with an element of which
the force field is NULL.
Each element contains the type of chip and a list of pairs.
The first value is a bus number (SENSORS_ISA_BUS for the ISA bus,
-1 for any I2C bus), the second is the address.
These are automatically translated to insmod variables of the form
force_foo.
So we have a generic insmod variabled `force', and chip-specific variables
`force_CHIPNAME'.
Fortunately, as a module writer, you just have to define the `normal_i2c'
and `normal_isa' parameters, and define what chip names are used.
The complete declaration could look like this:
/* Scan i2c addresses 0x37, and 0x48 to 0x4f */
static unsigned short normal_i2c[] = { 0x37, 0x48, 0x49, 0x4a, 0x4b, 0x4c,
0x4d, 0x4e, 0x4f, I2C_CLIENT_END };
/* Scan ISA address 0x290 */
static unsigned int normal_isa[] = {0x0290,SENSORS_ISA_END};
/* Define chips foo and bar, as well as all module parameters and things */
SENSORS_INSMOD_2(foo,bar);
If you have one chip, you use macro SENSORS_INSMOD_1(chip), if you have 2
you use macro SENSORS_INSMOD_2(chip1,chip2), etc. If you do not want to
bother with chip types, you can use SENSORS_INSMOD_0.
A enum is automatically defined as follows:
enum chips { any_chip, chip1, chip2, ... }
Attaching to an adapter
-----------------------
@ -264,17 +221,10 @@ detected at a specific address, another callback is called.
return i2c_probe(adapter,&addr_data,&foo_detect_client);
}
For `sensors' drivers, use the i2c_detect function instead:
int foo_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter,&addr_data,&foo_detect_client);
}
Remember, structure `addr_data' is defined by the macros explained above,
so you do not have to define it yourself.
The i2c_probe or i2c_detect function will call the foo_detect_client
The i2c_probe function will call the foo_detect_client
function only for those i2c addresses that actually have a device on
them (unless a `force' parameter was used). In addition, addresses that
are already in use (by some other registered client) are skipped.
@ -283,19 +233,18 @@ are already in use (by some other registered client) are skipped.
The detect client function
--------------------------
The detect client function is called by i2c_probe or i2c_detect.
The `kind' parameter contains 0 if this call is due to a `force'
parameter, and -1 otherwise (for i2c_detect, it contains 0 if
this call is due to the generic `force' parameter, and the chip type
number if it is due to a specific `force' parameter).
The detect client function is called by i2c_probe. The `kind' parameter
contains -1 for a probed detection, 0 for a forced detection, or a positive
number for a forced detection with a chip type forced.
Below, some things are only needed if this is a `sensors' driver. Those
parts are between /* SENSORS ONLY START */ and /* SENSORS ONLY END */
markers.
This function should only return an error (any value != 0) if there is
some reason why no more detection should be done anymore. If the
detection just fails for this address, return 0.
Returning an error different from -ENODEV in a detect function will cause
the detection to stop: other addresses and adapters won't be scanned.
This should only be done on fatal or internal errors, such as a memory
shortage or i2c_attach_client failing.
For now, you can ignore the `flags' parameter. It is there for future use.
@ -320,11 +269,10 @@ For now, you can ignore the `flags' parameter. It is there for future use.
const char *type_name = "";
int is_isa = i2c_is_isa_adapter(adapter);
if (is_isa) {
/* Do this only if the chip can additionally be found on the ISA bus
(hybrid chip). */
/* If this client can't be on the ISA bus at all, we can stop now
(call `goto ERROR0'). But for kicks, we will assume it is all
right. */
if (is_isa) {
/* Discard immediately if this ISA range is already used */
if (check_region(address,FOO_EXTENT))
@ -495,15 +443,13 @@ much simpler than the attachment code, fortunately!
/* SENSORS ONLY END */
/* Try to detach the client from i2c space */
if ((err = i2c_detach_client(client))) {
printk("foo.o: Client deregistration failed, client not detached.\n");
if ((err = i2c_detach_client(client)))
return err;
}
/* SENSORS ONLY START */
/* HYBRID SENSORS CHIP ONLY START */
if i2c_is_isa_client(client)
release_region(client->addr,LM78_EXTENT);
/* SENSORS ONLY END */
/* HYBRID SENSORS CHIP ONLY END */
kfree(client); /* Frees client data too, if allocated at the same time */
return 0;

View file

@ -933,6 +933,13 @@ M: khc@pm.waw.pl
W: http://www.kernel.org/pub/linux/utils/net/hdlc/
S: Maintained
HARDWARE MONITORING
P: Jean Delvare
M: khali@linux-fr.org
L: lm-sensors@lm-sensors.org
W: http://www.lm-sensors.nu/
S: Maintained
HARMONY SOUND DRIVER
P: Kyle McMartin
M: kyle@parisc-linux.org
@ -1014,7 +1021,7 @@ P: William Irwin
M: wli@holomorphy.com
S: Maintained
I2C AND SENSORS DRIVERS
I2C SUBSYSTEM
P: Greg Kroah-Hartman
M: greg@kroah.com
P: Jean Delvare

View file

@ -12,12 +12,20 @@ config HWMON
of a system. Most modern motherboards include such a device. It
can include temperature sensors, voltage sensors, fan speed
sensors and various additional features such as the ability to
control the speed of the fans.
control the speed of the fans. If you want this support you
should say Y here and also to the specific driver(s) for your
sensors chip(s) below.
This support can also be built as a module. If so, the module
will be called hwmon.
config HWMON_VID
tristate
default n
config SENSORS_ADM1021
tristate "Analog Devices ADM1021 and compatibles"
depends on HWMON && I2C
select I2C_SENSOR
help
If you say yes here you get support for Analog Devices ADM1021
and ADM1023 sensor chips and clones: Maxim MAX1617 and MAX1617A,
@ -30,7 +38,7 @@ config SENSORS_ADM1021
config SENSORS_ADM1025
tristate "Analog Devices ADM1025 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for Analog Devices ADM1025
and Philips NE1619 sensor chips.
@ -41,7 +49,7 @@ config SENSORS_ADM1025
config SENSORS_ADM1026
tristate "Analog Devices ADM1026 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for Analog Devices ADM1026
sensor chip.
@ -52,7 +60,6 @@ config SENSORS_ADM1026
config SENSORS_ADM1031
tristate "Analog Devices ADM1031 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Analog Devices ADM1031
and ADM1030 sensor chips.
@ -63,7 +70,7 @@ config SENSORS_ADM1031
config SENSORS_ADM9240
tristate "Analog Devices ADM9240 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for Analog Devices ADM9240,
Dallas DS1780, National Semiconductor LM81 sensor chips.
@ -74,7 +81,7 @@ config SENSORS_ADM9240
config SENSORS_ASB100
tristate "Asus ASB100 Bach"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for the ASB100 Bach sensor
chip found on some Asus mainboards.
@ -85,7 +92,7 @@ config SENSORS_ASB100
config SENSORS_ATXP1
tristate "Attansic ATXP1 VID controller"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for the Attansic ATXP1 VID
controller.
@ -99,7 +106,6 @@ config SENSORS_ATXP1
config SENSORS_DS1621
tristate "Dallas Semiconductor DS1621 and DS1625"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Dallas Semiconductor
DS1621 and DS1625 sensor chips.
@ -110,7 +116,6 @@ config SENSORS_DS1621
config SENSORS_FSCHER
tristate "FSC Hermes"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Fujitsu Siemens
Computers Hermes sensor chips.
@ -121,7 +126,6 @@ config SENSORS_FSCHER
config SENSORS_FSCPOS
tristate "FSC Poseidon"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Fujitsu Siemens
Computers Poseidon sensor chips.
@ -132,7 +136,6 @@ config SENSORS_FSCPOS
config SENSORS_GL518SM
tristate "Genesys Logic GL518SM"
depends on HWMON && I2C
select I2C_SENSOR
help
If you say yes here you get support for Genesys Logic GL518SM
sensor chips.
@ -143,7 +146,7 @@ config SENSORS_GL518SM
config SENSORS_GL520SM
tristate "Genesys Logic GL520SM"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for Genesys Logic GL520SM
sensor chips.
@ -154,7 +157,8 @@ config SENSORS_GL520SM
config SENSORS_IT87
tristate "ITE IT87xx and compatibles"
depends on HWMON && I2C
select I2C_SENSOR
select I2C_ISA
select HWMON_VID
help
If you say yes here you get support for ITE IT87xx sensor chips
and clones: SiS960.
@ -165,7 +169,6 @@ config SENSORS_IT87
config SENSORS_LM63
tristate "National Semiconductor LM63"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for the National Semiconductor
LM63 remote diode digital temperature sensor with integrated fan
@ -178,7 +181,6 @@ config SENSORS_LM63
config SENSORS_LM75
tristate "National Semiconductor LM75 and compatibles"
depends on HWMON && I2C
select I2C_SENSOR
help
If you say yes here you get support for National Semiconductor LM75
sensor chips and clones: Dallas Semiconductor DS75 and DS1775 (in
@ -194,7 +196,6 @@ config SENSORS_LM75
config SENSORS_LM77
tristate "National Semiconductor LM77"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for National Semiconductor LM77
sensor chips.
@ -205,7 +206,8 @@ config SENSORS_LM77
config SENSORS_LM78
tristate "National Semiconductor LM78 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
select HWMON_VID
help
If you say yes here you get support for National Semiconductor LM78,
LM78-J and LM79.
@ -216,7 +218,6 @@ config SENSORS_LM78
config SENSORS_LM80
tristate "National Semiconductor LM80"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for National Semiconductor
LM80 sensor chips.
@ -227,7 +228,6 @@ config SENSORS_LM80
config SENSORS_LM83
tristate "National Semiconductor LM83"
depends on HWMON && I2C
select I2C_SENSOR
help
If you say yes here you get support for National Semiconductor
LM83 sensor chips.
@ -238,7 +238,7 @@ config SENSORS_LM83
config SENSORS_LM85
tristate "National Semiconductor LM85 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for National Semiconductor LM85
sensor chips and clones: ADT7463, EMC6D100, EMC6D102 and ADM1027.
@ -249,7 +249,7 @@ config SENSORS_LM85
config SENSORS_LM87
tristate "National Semiconductor LM87"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select HWMON_VID
help
If you say yes here you get support for National Semiconductor LM87
sensor chips.
@ -260,7 +260,6 @@ config SENSORS_LM87
config SENSORS_LM90
tristate "National Semiconductor LM90 and compatibles"
depends on HWMON && I2C
select I2C_SENSOR
help
If you say yes here you get support for National Semiconductor LM90,
LM86, LM89 and LM99, Analog Devices ADM1032 and Maxim MAX6657 and
@ -275,7 +274,6 @@ config SENSORS_LM90
config SENSORS_LM92
tristate "National Semiconductor LM92 and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for National Semiconductor LM92
and Maxim MAX6635 sensor chips.
@ -286,7 +284,6 @@ config SENSORS_LM92
config SENSORS_MAX1619
tristate "Maxim MAX1619 sensor chip"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for MAX1619 sensor chip.
@ -296,8 +293,8 @@ config SENSORS_MAX1619
config SENSORS_PC87360
tristate "National Semiconductor PC87360 family"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
select HWMON_VID
help
If you say yes here you get access to the hardware monitoring
functions of the National Semiconductor PC8736x Super-I/O chips.
@ -311,7 +308,6 @@ config SENSORS_PC87360
config SENSORS_SIS5595
tristate "Silicon Integrated Systems Corp. SiS5595"
depends on HWMON && I2C && PCI && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
help
If you say yes here you get support for the integrated sensors in
@ -323,7 +319,6 @@ config SENSORS_SIS5595
config SENSORS_SMSC47M1
tristate "SMSC LPC47M10x and compatibles"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
help
If you say yes here you get support for the integrated fan
@ -336,7 +331,6 @@ config SENSORS_SMSC47M1
config SENSORS_SMSC47B397
tristate "SMSC LPC47B397-NC"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
help
If you say yes here you get support for the SMSC LPC47B397-NC
@ -348,7 +342,6 @@ config SENSORS_SMSC47B397
config SENSORS_VIA686A
tristate "VIA686A"
depends on HWMON && I2C && PCI
select I2C_SENSOR
select I2C_ISA
help
If you say yes here you get support for the integrated sensors in
@ -360,7 +353,8 @@ config SENSORS_VIA686A
config SENSORS_W83781D
tristate "Winbond W83781D, W83782D, W83783S, W83627HF, Asus AS99127F"
depends on HWMON && I2C
select I2C_SENSOR
select I2C_ISA
select HWMON_VID
help
If you say yes here you get support for the Winbond W8378x series
of sensor chips: the W83781D, W83782D, W83783S and W83627HF,
@ -369,10 +363,18 @@ config SENSORS_W83781D
This driver can also be built as a module. If so, the module
will be called w83781d.
config SENSORS_W83792D
tristate "Winbond W83792D"
depends on HWMON && I2C && EXPERIMENTAL
help
If you say yes here you get support for the Winbond W83792D chip.
This driver can also be built as a module. If so, the module
will be called w83792d.
config SENSORS_W83L785TS
tristate "Winbond W83L785TS-S"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for the Winbond W83L785TS-S
sensor chip, which is used on the Asus A7N8X, among other
@ -384,8 +386,8 @@ config SENSORS_W83L785TS
config SENSORS_W83627HF
tristate "Winbond W83627HF, W83627THF, W83637HF, W83697HF"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
select HWMON_VID
help
If you say yes here you get support for the Winbond W836X7 series
of sensor chips: the W83627HF, W83627THF, W83637HF, and the W83697HF
@ -396,7 +398,6 @@ config SENSORS_W83627HF
config SENSORS_W83627EHF
tristate "Winbond W83627EHF"
depends on HWMON && I2C && EXPERIMENTAL
select I2C_SENSOR
select I2C_ISA
help
If you say yes here you get preliminary support for the hardware
@ -404,6 +405,9 @@ config SENSORS_W83627EHF
Only fan and temperature inputs are supported at the moment, while
the chip does much more than that.
This driver also supports the W83627EHG, which is the lead-free
version of the W83627EHF.
This driver can also be built as a module. If so, the module
will be called w83627ehf.

View file

@ -2,9 +2,13 @@
# Makefile for sensor chip drivers.
#
obj-$(CONFIG_HWMON) += hwmon.o
obj-$(CONFIG_HWMON_VID) += hwmon-vid.o
# asb100, then w83781d go first, as they can override other drivers' addresses.
obj-$(CONFIG_SENSORS_ASB100) += asb100.o
obj-$(CONFIG_SENSORS_W83627HF) += w83627hf.o
obj-$(CONFIG_SENSORS_W83792D) += w83792d.o
obj-$(CONFIG_SENSORS_W83781D) += w83781d.o
obj-$(CONFIG_SENSORS_ADM1021) += adm1021.o

View file

@ -24,7 +24,8 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* Addresses to scan */
@ -32,10 +33,9 @@ static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a,
0x29, 0x2a, 0x2b,
0x4c, 0x4d, 0x4e,
I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_8(adm1021, adm1023, max1617, max1617a, thmc10, lm84, gl523sm, mc1066);
I2C_CLIENT_INSMOD_8(adm1021, adm1023, max1617, max1617a, thmc10, lm84, gl523sm, mc1066);
/* adm1021 constants specified below */
@ -89,6 +89,7 @@ clearing it. Weird, ey? --Phil */
/* Each client has this additional data */
struct adm1021_data {
struct i2c_client client;
struct class_device *class_dev;
enum chips type;
struct semaphore update_lock;
@ -185,7 +186,7 @@ static int adm1021_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, adm1021_detect);
return i2c_probe(adapter, &addr_data, adm1021_detect);
}
static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind)
@ -196,15 +197,6 @@ static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind)
int err = 0;
const char *type_name = "";
/* Make sure we aren't probing the ISA bus!! This is just a safety check
at this moment; i2c_detect really won't call us. */
#ifdef DEBUG
if (i2c_is_isa_adapter(adapter)) {
dev_dbg(&adapter->dev, "adm1021_detect called for an ISA bus adapter?!?\n");
return 0;
}
#endif
if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA))
goto error0;
@ -295,6 +287,12 @@ static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind)
adm1021_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto error2;
}
device_create_file(&new_client->dev, &dev_attr_temp1_max);
device_create_file(&new_client->dev, &dev_attr_temp1_min);
device_create_file(&new_client->dev, &dev_attr_temp1_input);
@ -305,6 +303,8 @@ static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
error2:
i2c_detach_client(new_client);
error1:
kfree(data);
error0:
@ -322,14 +322,15 @@ static void adm1021_init_client(struct i2c_client *client)
static int adm1021_detach_client(struct i2c_client *client)
{
struct adm1021_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -50,8 +50,9 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
/*
* Addresses to scan
@ -60,13 +61,12 @@
*/
static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_2(adm1025, ne1619);
I2C_CLIENT_INSMOD_2(adm1025, ne1619);
/*
* The ADM1025 registers
@ -132,6 +132,7 @@ static struct i2c_driver adm1025_driver = {
struct adm1025_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -312,7 +313,7 @@ static int adm1025_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, adm1025_detect);
return i2c_probe(adapter, &addr_data, adm1025_detect);
}
/*
@ -416,6 +417,12 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind)
adm1025_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in1_input);
device_create_file(&new_client->dev, &dev_attr_in2_input);
@ -452,6 +459,8 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -464,7 +473,7 @@ static void adm1025_init_client(struct i2c_client *client)
struct adm1025_data *data = i2c_get_clientdata(client);
int i;
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
/*
* Set high limits
@ -502,15 +511,15 @@ static void adm1025_init_client(struct i2c_client *client)
static int adm1025_detach_client(struct i2c_client *client)
{
struct adm1025_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -28,16 +28,16 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(adm1026);
I2C_CLIENT_INSMOD_1(adm1026);
static int gpio_input[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1,
-1, -1, -1, -1, -1, -1, -1, -1 };
@ -259,6 +259,7 @@ struct pwm_data {
struct adm1026_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -319,13 +320,15 @@ int adm1026_attach_adapter(struct i2c_adapter *adapter)
if (!(adapter->class & I2C_CLASS_HWMON)) {
return 0;
}
return i2c_detect(adapter, &addr_data, adm1026_detect);
return i2c_probe(adapter, &addr_data, adm1026_detect);
}
int adm1026_detach_client(struct i2c_client *client)
{
struct adm1026_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->class_dev);
i2c_detach_client(client);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -1549,12 +1552,18 @@ int adm1026_detect(struct i2c_adapter *adapter, int address,
goto exitfree;
/* Set the VRM version */
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
/* Initialize the ADM1026 chip */
adm1026_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exitdetach;
}
device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr);
device_create_file(&new_client->dev, &sensor_dev_attr_in0_max.dev_attr);
device_create_file(&new_client->dev, &sensor_dev_attr_in0_min.dev_attr);
@ -1690,6 +1699,8 @@ int adm1026_detect(struct i2c_adapter *adapter, int address,
return 0;
/* Error out and cleanup code */
exitdetach:
i2c_detach_client(new_client);
exitfree:
kfree(data);
exit:

View file

@ -26,7 +26,8 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* Following macros takes channel parameter starting from 0 to 2 */
#define ADM1031_REG_FAN_SPEED(nr) (0x08 + (nr))
@ -59,16 +60,16 @@
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_2(adm1030, adm1031);
I2C_CLIENT_INSMOD_2(adm1030, adm1031);
typedef u8 auto_chan_table_t[8][2];
/* Each client has this additional data */
struct adm1031_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
int chip_type;
char valid; /* !=0 if following fields are valid */
@ -725,10 +726,10 @@ static int adm1031_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, adm1031_detect);
return i2c_probe(adapter, &addr_data, adm1031_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
@ -788,6 +789,12 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind)
adm1031_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_fan1_input);
device_create_file(&new_client->dev, &dev_attr_fan1_div);
device_create_file(&new_client->dev, &dev_attr_fan1_min);
@ -833,6 +840,8 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -841,11 +850,14 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind)
static int adm1031_detach_client(struct i2c_client *client)
{
struct adm1031_data *data = i2c_get_clientdata(client);
int ret;
hwmon_device_unregister(data->class_dev);
if ((ret = i2c_detach_client(client)) != 0) {
return ret;
}
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}

View file

@ -45,17 +45,16 @@
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, 0x2f,
I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_3(adm9240, ds1780, lm81);
I2C_CLIENT_INSMOD_3(adm9240, ds1780, lm81);
/* ADM9240 registers */
#define ADM9240_REG_MAN_ID 0x3e
@ -150,6 +149,7 @@ static struct i2c_driver adm9240_driver = {
struct adm9240_data {
enum chips type;
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid;
unsigned long last_updated_measure;
@ -582,6 +582,12 @@ static int adm9240_detect(struct i2c_adapter *adapter, int address, int kind)
adm9240_init_client(new_client);
/* populate sysfs filesystem */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in0_min);
device_create_file(&new_client->dev, &dev_attr_in0_max);
@ -615,6 +621,9 @@ static int adm9240_detect(struct i2c_adapter *adapter, int address, int kind)
device_create_file(&new_client->dev, &dev_attr_cpu0_vid);
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -625,20 +634,20 @@ static int adm9240_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, adm9240_detect);
return i2c_probe(adapter, &addr_data, adm9240_detect);
}
static int adm9240_detach_client(struct i2c_client *client)
{
struct adm9240_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}
@ -648,7 +657,7 @@ static void adm9240_init_client(struct i2c_client *client)
u8 conf = adm9240_read_value(client, ADM9240_REG_CONFIG);
u8 mode = adm9240_read_value(client, ADM9240_REG_TEMP_CONF) & 3;
data->vrm = i2c_which_vrm(); /* need this to report vid as mV */
data->vrm = vid_which_vrm(); /* need this to report vid as mV */
dev_info(&client->dev, "Using VRM: %d.%d\n", data->vrm / 10,
data->vrm % 10);

View file

@ -39,8 +39,9 @@
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
#include <linux/init.h>
#include <linux/jiffies.h>
#include "lm75.h"
@ -54,11 +55,8 @@
/* I2C addresses to scan */
static unsigned short normal_i2c[] = { 0x2d, I2C_CLIENT_END };
/* ISA addresses to scan (none) */
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(asb100);
I2C_CLIENT_INSMOD_1(asb100);
I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: "
"{bus, clientaddr, subclientaddr1, subclientaddr2}");
@ -183,6 +181,7 @@ static u8 DIV_TO_REG(long val)
dynamically allocated, at the same time the client itself is allocated. */
struct asb100_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -621,7 +620,7 @@ static int asb100_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, asb100_detect);
return i2c_probe(adapter, &addr_data, asb100_detect);
}
static int asb100_detect_subclients(struct i2c_adapter *adapter, int address,
@ -714,14 +713,6 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind)
struct i2c_client *new_client;
struct asb100_data *data;
/* asb100 is SMBus only */
if (i2c_is_isa_adapter(adapter)) {
pr_debug("asb100.o: detect failed, "
"cannot attach to legacy adapter!\n");
err = -ENODEV;
goto ERROR0;
}
if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) {
pr_debug("asb100.o: detect failed, "
"smbus byte data not supported!\n");
@ -821,6 +812,12 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind)
data->fan_min[2] = asb100_read_value(new_client, ASB100_REG_FAN_MIN(2));
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto ERROR3;
}
device_create_file_in(new_client, 0);
device_create_file_in(new_client, 1);
device_create_file_in(new_client, 2);
@ -847,6 +844,11 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
ERROR3:
i2c_detach_client(data->lm75[1]);
i2c_detach_client(data->lm75[0]);
kfree(data->lm75[1]);
kfree(data->lm75[0]);
ERROR2:
i2c_detach_client(new_client);
ERROR1:
@ -857,21 +859,23 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind)
static int asb100_detach_client(struct i2c_client *client)
{
struct asb100_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "client deregistration failed; "
"client not detached.\n");
return err;
}
/* main client */
if (data)
hwmon_device_unregister(data->class_dev);
if (i2c_get_clientdata(client)==NULL) {
/* subclients */
if ((err = i2c_detach_client(client)))
return err;
/* main client */
if (data)
kfree(data);
/* subclient */
else
kfree(client);
} else {
/* main client */
kfree(i2c_get_clientdata(client));
}
return 0;
}
@ -969,7 +973,7 @@ static void asb100_init_client(struct i2c_client *client)
vid = asb100_read_value(client, ASB100_REG_VID_FANDIV) & 0x0f;
vid |= (asb100_read_value(client, ASB100_REG_CHIPID) & 0x01) << 4;
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
vid = vid_from_reg(vid, data->vrm);
/* Start monitoring */

View file

@ -23,8 +23,9 @@
#include <linux/module.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("System voltages control via Attansic ATXP1");
@ -40,9 +41,8 @@ MODULE_AUTHOR("Sebastian Witt <se.witt@gmx.net>");
#define ATXP1_GPIO1MASK 0x0f
static unsigned short normal_i2c[] = { 0x37, 0x4e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
SENSORS_INSMOD_1(atxp1);
I2C_CLIENT_INSMOD_1(atxp1);
static int atxp1_attach_adapter(struct i2c_adapter * adapter);
static int atxp1_detach_client(struct i2c_client * client);
@ -59,6 +59,7 @@ static struct i2c_driver atxp1_driver = {
struct atxp1_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
unsigned long last_updated;
u8 valid;
@ -252,7 +253,7 @@ static DEVICE_ATTR(gpio2, S_IRUGO | S_IWUSR, atxp1_showgpio2, atxp1_storegpio2);
static int atxp1_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, &atxp1_detect);
return i2c_probe(adapter, &addr_data, &atxp1_detect);
};
static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind)
@ -295,7 +296,7 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind)
}
/* Get VRM */
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
if ((data->vrm != 90) && (data->vrm != 91)) {
dev_err(&new_client->dev, "Not supporting VRM %d.%d\n",
@ -317,6 +318,12 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind)
goto exit_free;
}
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_gpio1);
device_create_file(&new_client->dev, &dev_attr_gpio2);
device_create_file(&new_client->dev, &dev_attr_cpu0_vid);
@ -326,6 +333,8 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -334,14 +343,17 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind)
static int atxp1_detach_client(struct i2c_client * client)
{
struct atxp1_data * data = i2c_get_clientdata(client);
int err;
hwmon_device_unregister(data->class_dev);
err = i2c_detach_client(client);
if (err)
dev_err(&client->dev, "Failed to detach client.\n");
else
kfree(i2c_get_clientdata(client));
kfree(data);
return err;
};

View file

@ -26,16 +26,16 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include "lm75.h"
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c,
0x4d, 0x4e, 0x4f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(ds1621);
I2C_CLIENT_INSMOD_1(ds1621);
static int polarity = -1;
module_param(polarity, int, 0);
MODULE_PARM_DESC(polarity, "Output's polarity: 0 = active high, 1 = active low");
@ -71,6 +71,7 @@ MODULE_PARM_DESC(polarity, "Output's polarity: 0 = active high, 1 = active low")
/* Each client has this additional data */
struct ds1621_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* !=0 if following fields are valid */
unsigned long last_updated; /* In jiffies */
@ -179,10 +180,10 @@ static DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_max, set_temp_max);
static int ds1621_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, ds1621_detect);
return i2c_probe(adapter, &addr_data, ds1621_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
int ds1621_detect(struct i2c_adapter *adapter, int address,
int kind)
{
@ -250,6 +251,12 @@ int ds1621_detect(struct i2c_adapter *adapter, int address,
ds1621_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_alarms);
device_create_file(&new_client->dev, &dev_attr_temp1_input);
device_create_file(&new_client->dev, &dev_attr_temp1_min);
@ -259,6 +266,8 @@ int ds1621_detect(struct i2c_adapter *adapter, int address,
/* OK, this is not exactly good programming practice, usually. But it is
very code-efficient in this case. */
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -267,15 +276,15 @@ int ds1621_detect(struct i2c_adapter *adapter, int address,
static int ds1621_detach_client(struct i2c_client *client)
{
struct ds1621_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -31,20 +31,20 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/*
* Addresses to scan
*/
static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(fscher);
I2C_CLIENT_INSMOD_1(fscher);
/*
* The FSCHER registers
@ -132,6 +132,7 @@ static struct i2c_driver fscher_driver = {
struct fscher_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -287,7 +288,7 @@ static int fscher_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, fscher_detect);
return i2c_probe(adapter, &addr_data, fscher_detect);
}
static int fscher_detect(struct i2c_adapter *adapter, int address, int kind)
@ -341,6 +342,12 @@ static int fscher_detect(struct i2c_adapter *adapter, int address, int kind)
fscher_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file_revision(new_client);
device_create_file_alarms(new_client);
device_create_file_control(new_client);
@ -360,6 +367,8 @@ static int fscher_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -368,15 +377,15 @@ static int fscher_detect(struct i2c_adapter *adapter, int address, int kind)
static int fscher_detach_client(struct i2c_client *client)
{
struct fscher_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -34,19 +34,19 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/init.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/*
* Addresses to scan
*/
static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(fscpos);
I2C_CLIENT_INSMOD_1(fscpos);
/*
* The FSCPOS registers
@ -113,6 +113,7 @@ static struct i2c_driver fscpos_driver = {
*/
struct fscpos_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* 0 until following fields are valid */
unsigned long last_updated; /* In jiffies */
@ -434,7 +435,7 @@ static int fscpos_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, fscpos_detect);
return i2c_probe(adapter, &addr_data, fscpos_detect);
}
int fscpos_detect(struct i2c_adapter *adapter, int address, int kind)
@ -496,6 +497,12 @@ int fscpos_detect(struct i2c_adapter *adapter, int address, int kind)
dev_info(&new_client->dev, "Found fscpos chip, rev %u\n", data->revision);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_event);
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in1_input);
@ -526,6 +533,8 @@ int fscpos_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -534,14 +543,14 @@ int fscpos_detect(struct i2c_adapter *adapter, int address, int kind)
static int fscpos_detach_client(struct i2c_client *client)
{
struct fscpos_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, client"
" not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}

View file

@ -41,14 +41,14 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_2(gl518sm_r00, gl518sm_r80);
I2C_CLIENT_INSMOD_2(gl518sm_r00, gl518sm_r80);
/* Many GL518 constants specified below */
@ -117,6 +117,7 @@ static inline u8 FAN_TO_REG(long rpm, int div)
/* Each client has this additional data */
struct gl518_data {
struct i2c_client client;
struct class_device *class_dev;
enum chips type;
struct semaphore update_lock;
@ -346,7 +347,7 @@ static int gl518_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, gl518_detect);
return i2c_probe(adapter, &addr_data, gl518_detect);
}
static int gl518_detect(struct i2c_adapter *adapter, int address, int kind)
@ -419,6 +420,12 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind)
gl518_init_client((struct i2c_client *) new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in1_input);
device_create_file(&new_client->dev, &dev_attr_in2_input);
@ -450,6 +457,8 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind)
/* OK, this is not exactly good programming practice, usually. But it is
very code-efficient in this case. */
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -477,16 +486,15 @@ static void gl518_init_client(struct i2c_client *client)
static int gl518_detach_client(struct i2c_client *client)
{
struct gl518_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}

View file

@ -26,8 +26,9 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
/* Type of the extra sensor */
static unsigned short extra_sensor_type;
@ -36,10 +37,9 @@ MODULE_PARM_DESC(extra_sensor_type, "Type of extra sensor (0=autodetect, 1=tempe
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(gl520sm);
I2C_CLIENT_INSMOD_1(gl520sm);
/* Many GL520 constants specified below
One of the inputs can be configured as either temp or voltage.
@ -120,6 +120,7 @@ static struct i2c_driver gl520_driver = {
/* Client data */
struct gl520_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until the following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -518,7 +519,7 @@ static int gl520_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, gl520_detect);
return i2c_probe(adapter, &addr_data, gl520_detect);
}
static int gl520_detect(struct i2c_adapter *adapter, int address, int kind)
@ -571,6 +572,12 @@ static int gl520_detect(struct i2c_adapter *adapter, int address, int kind)
gl520_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file_vid(new_client, 0);
device_create_file_in(new_client, 0);
@ -592,6 +599,8 @@ static int gl520_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -608,7 +617,7 @@ static void gl520_init_client(struct i2c_client *client)
conf = oldconf = gl520_read_value(client, GL520_REG_CONF);
data->alarm_mask = 0xff;
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
if (extra_sensor_type == 1)
conf &= ~0x10;
@ -639,15 +648,15 @@ static void gl520_init_client(struct i2c_client *client)
static int gl520_detach_client(struct i2c_client *client)
{
struct gl520_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

189
drivers/hwmon/hwmon-vid.c Normal file
View file

@ -0,0 +1,189 @@
/*
hwmon-vid.c - VID/VRM/VRD voltage conversions
Copyright (c) 2004 Rudolf Marek <r.marek@sh.cvut.cz>
Partly imported from i2c-vid.h of the lm_sensors project
Copyright (c) 2002 Mark D. Studebaker <mdsxyz123@yahoo.com>
With assistance from Trent Piepho <xyzzy@speakeasy.org>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <linux/config.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/hwmon-vid.h>
/*
Common code for decoding VID pins.
References:
For VRM 8.4 to 9.1, "VRM x.y DC-DC Converter Design Guidelines",
available at http://developer.intel.com/.
For VRD 10.0 and up, "VRD x.y Design Guide",
available at http://developer.intel.com/.
AMD Opteron processors don't follow the Intel specifications.
I'm going to "make up" 2.4 as the spec number for the Opterons.
No good reason just a mnemonic for the 24x Opteron processor
series.
Opteron VID encoding is:
00000 = 1.550 V
00001 = 1.525 V
. . . .
11110 = 0.800 V
11111 = 0.000 V (off)
*/
/* vrm is the VRM/VRD document version multiplied by 10.
val is the 4-, 5- or 6-bit VID code.
Returned value is in mV to avoid floating point in the kernel. */
int vid_from_reg(int val, int vrm)
{
int vid;
switch(vrm) {
case 0:
return 0;
case 100: /* VRD 10.0 */
if((val & 0x1f) == 0x1f)
return 0;
if((val & 0x1f) <= 0x09 || val == 0x0a)
vid = 10875 - (val & 0x1f) * 250;
else
vid = 18625 - (val & 0x1f) * 250;
if(val & 0x20)
vid -= 125;
vid /= 10; /* only return 3 dec. places for now */
return vid;
case 24: /* Opteron processor */
return(val == 0x1f ? 0 : 1550 - val * 25);
case 91: /* VRM 9.1 */
case 90: /* VRM 9.0 */
return(val == 0x1f ? 0 :
1850 - val * 25);
case 85: /* VRM 8.5 */
return((val & 0x10 ? 25 : 0) +
((val & 0x0f) > 0x04 ? 2050 : 1250) -
((val & 0x0f) * 50));
case 84: /* VRM 8.4 */
val &= 0x0f;
/* fall through */
default: /* VRM 8.2 */
return(val == 0x1f ? 0 :
val & 0x10 ? 5100 - (val) * 100 :
2050 - (val) * 50);
}
}
/*
After this point is the code to automatically determine which
VRM/VRD specification should be used depending on the CPU.
*/
struct vrm_model {
u8 vendor;
u8 eff_family;
u8 eff_model;
int vrm_type;
};
#define ANY 0xFF
#ifdef CONFIG_X86
static struct vrm_model vrm_models[] = {
{X86_VENDOR_AMD, 0x6, ANY, 90}, /* Athlon Duron etc */
{X86_VENDOR_AMD, 0xF, ANY, 24}, /* Athlon 64, Opteron */
{X86_VENDOR_INTEL, 0x6, 0x9, 85}, /* 0.13um too */
{X86_VENDOR_INTEL, 0x6, 0xB, 85}, /* Tualatin */
{X86_VENDOR_INTEL, 0x6, ANY, 82}, /* any P6 */
{X86_VENDOR_INTEL, 0x7, ANY, 0}, /* Itanium */
{X86_VENDOR_INTEL, 0xF, 0x0, 90}, /* P4 */
{X86_VENDOR_INTEL, 0xF, 0x1, 90}, /* P4 Willamette */
{X86_VENDOR_INTEL, 0xF, 0x2, 90}, /* P4 Northwood */
{X86_VENDOR_INTEL, 0xF, 0x3, 100}, /* P4 Prescott */
{X86_VENDOR_INTEL, 0xF, 0x4, 100}, /* P4 Prescott */
{X86_VENDOR_INTEL, 0x10,ANY, 0}, /* Itanium 2 */
{X86_VENDOR_UNKNOWN, ANY, ANY, 0} /* stop here */
};
static int find_vrm(u8 eff_family, u8 eff_model, u8 vendor)
{
int i = 0;
while (vrm_models[i].vendor!=X86_VENDOR_UNKNOWN) {
if (vrm_models[i].vendor==vendor)
if ((vrm_models[i].eff_family==eff_family)
&& ((vrm_models[i].eff_model==eff_model) ||
(vrm_models[i].eff_model==ANY)))
return vrm_models[i].vrm_type;
i++;
}
return 0;
}
int vid_which_vrm(void)
{
struct cpuinfo_x86 *c = cpu_data;
u32 eax;
u8 eff_family, eff_model;
int vrm_ret;
if (c->x86 < 6) /* Any CPU with family lower than 6 */
return 0; /* doesn't have VID and/or CPUID */
eax = cpuid_eax(1);
eff_family = ((eax & 0x00000F00)>>8);
eff_model = ((eax & 0x000000F0)>>4);
if (eff_family == 0xF) { /* use extended model & family */
eff_family += ((eax & 0x00F00000)>>20);
eff_model += ((eax & 0x000F0000)>>16)<<4;
}
vrm_ret = find_vrm(eff_family,eff_model,c->x86_vendor);
if (vrm_ret == 0)
printk(KERN_INFO "hwmon-vid: Unknown VRM version of your "
"x86 CPU\n");
return vrm_ret;
}
/* and now something completely different for the non-x86 world */
#else
int vid_which_vrm(void)
{
printk(KERN_INFO "hwmon-vid: Unknown VRM version of your CPU\n");
return 0;
}
#endif
EXPORT_SYMBOL(vid_from_reg);
EXPORT_SYMBOL(vid_which_vrm);
MODULE_AUTHOR("Rudolf Marek <r.marek@sh.cvut.cz>");
MODULE_DESCRIPTION("hwmon-vid driver");
MODULE_LICENSE("GPL");

98
drivers/hwmon/hwmon.c Normal file
View file

@ -0,0 +1,98 @@
/*
hwmon.c - part of lm_sensors, Linux kernel modules for hardware monitoring
This file defines the sysfs class "hwmon", for use by sensors drivers.
Copyright (C) 2005 Mark M. Hoffman <mhoffman@lightlink.com>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
*/
#include <linux/module.h>
#include <linux/device.h>
#include <linux/err.h>
#include <linux/kdev_t.h>
#include <linux/idr.h>
#include <linux/hwmon.h>
#define HWMON_ID_PREFIX "hwmon"
#define HWMON_ID_FORMAT HWMON_ID_PREFIX "%d"
static struct class *hwmon_class;
static DEFINE_IDR(hwmon_idr);
/**
* hwmon_device_register - register w/ hwmon sysfs class
* @dev: the device to register
*
* hwmon_device_unregister() must be called when the class device is no
* longer needed.
*
* Returns the pointer to the new struct class device.
*/
struct class_device *hwmon_device_register(struct device *dev)
{
struct class_device *cdev;
int id;
if (idr_pre_get(&hwmon_idr, GFP_KERNEL) == 0)
return ERR_PTR(-ENOMEM);
if (idr_get_new(&hwmon_idr, NULL, &id) < 0)
return ERR_PTR(-ENOMEM);
id = id & MAX_ID_MASK;
cdev = class_device_create(hwmon_class, MKDEV(0,0), dev,
HWMON_ID_FORMAT, id);
if (IS_ERR(cdev))
idr_remove(&hwmon_idr, id);
return cdev;
}
/**
* hwmon_device_unregister - removes the previously registered class device
*
* @cdev: the class device to destroy
*/
void hwmon_device_unregister(struct class_device *cdev)
{
int id;
if (sscanf(cdev->class_id, HWMON_ID_FORMAT, &id) == 1) {
class_device_unregister(cdev);
idr_remove(&hwmon_idr, id);
} else
dev_dbg(cdev->dev,
"hwmon_device_unregister() failed: bad class ID!\n");
}
static int __init hwmon_init(void)
{
hwmon_class = class_create(THIS_MODULE, "hwmon");
if (IS_ERR(hwmon_class)) {
printk(KERN_ERR "hwmon.c: couldn't create sysfs class\n");
return PTR_ERR(hwmon_class);
}
return 0;
}
static void __exit hwmon_exit(void)
{
class_destroy(hwmon_class);
}
module_init(hwmon_init);
module_exit(hwmon_exit);
EXPORT_SYMBOL_GPL(hwmon_device_register);
EXPORT_SYMBOL_GPL(hwmon_device_unregister);
MODULE_AUTHOR("Mark M. Hoffman <mhoffman@lightlink.com>");
MODULE_DESCRIPTION("hardware monitoring sysfs/class support");
MODULE_LICENSE("GPL");

View file

@ -36,19 +36,21 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/hwmon-sysfs.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
#include <asm/io.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d,
0x2e, 0x2f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0x0290, I2C_CLIENT_ISA_END };
static unsigned short isa_address = 0x290;
/* Insmod parameters */
SENSORS_INSMOD_2(it87, it8712);
I2C_CLIENT_INSMOD_2(it87, it8712);
#define REG 0x2e /* The register to read/write */
#define DEV 0x07 /* Register: Logical device select */
@ -192,6 +194,7 @@ static int DIV_TO_REG(int val)
allocated. */
struct it87_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -218,7 +221,7 @@ struct it87_data {
static int it87_attach_adapter(struct i2c_adapter *adapter);
static int it87_find(int *address);
static int it87_isa_attach_adapter(struct i2c_adapter *adapter);
static int it87_detect(struct i2c_adapter *adapter, int address, int kind);
static int it87_detach_client(struct i2c_client *client);
@ -239,6 +242,14 @@ static struct i2c_driver it87_driver = {
.detach_client = it87_detach_client,
};
static struct i2c_driver it87_isa_driver = {
.owner = THIS_MODULE,
.name = "it87-isa",
.attach_adapter = it87_isa_attach_adapter,
.detach_client = it87_detach_client,
};
static ssize_t show_in(struct device *dev, struct device_attribute *attr,
char *buf)
{
@ -686,11 +697,16 @@ static int it87_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, it87_detect);
return i2c_probe(adapter, &addr_data, it87_detect);
}
/* SuperIO detection - will change normal_isa[0] if a chip is found */
static int it87_find(int *address)
static int it87_isa_attach_adapter(struct i2c_adapter *adapter)
{
return it87_detect(adapter, isa_address, -1);
}
/* SuperIO detection - will change isa_address if a chip is found */
static int __init it87_find(int *address)
{
int err = -ENODEV;
@ -721,7 +737,7 @@ static int it87_find(int *address)
return err;
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
int it87_detect(struct i2c_adapter *adapter, int address, int kind)
{
int i;
@ -738,7 +754,7 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind)
/* Reserve the ISA region */
if (is_isa)
if (!request_region(address, IT87_EXTENT, it87_driver.name))
if (!request_region(address, IT87_EXTENT, it87_isa_driver.name))
goto ERROR0;
/* Probe whether there is anything available on this address. Already
@ -784,7 +800,7 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind)
i2c_set_clientdata(new_client, data);
new_client->addr = address;
new_client->adapter = adapter;
new_client->driver = &it87_driver;
new_client->driver = is_isa ? &it87_isa_driver : &it87_driver;
new_client->flags = 0;
/* Now, we do the remaining detection. */
@ -840,6 +856,12 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind)
it87_init_client(new_client, data);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto ERROR3;
}
device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr);
device_create_file(&new_client->dev, &sensor_dev_attr_in1_input.dev_attr);
device_create_file(&new_client->dev, &sensor_dev_attr_in2_input.dev_attr);
@ -897,13 +919,15 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind)
}
if (data->type == it8712) {
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
device_create_file_vrm(new_client);
device_create_file_vid(new_client);
}
return 0;
ERROR3:
i2c_detach_client(new_client);
ERROR2:
kfree(data);
ERROR1:
@ -915,17 +939,17 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind)
static int it87_detach_client(struct i2c_client *client)
{
struct it87_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
if(i2c_is_isa_client(client))
release_region(client->addr, IT87_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -1158,16 +1182,28 @@ static struct it87_data *it87_update_device(struct device *dev)
static int __init sm_it87_init(void)
{
int addr;
int addr, res;
if (!it87_find(&addr)) {
normal_isa[0] = addr;
isa_address = addr;
}
return i2c_add_driver(&it87_driver);
res = i2c_add_driver(&it87_driver);
if (res)
return res;
res = i2c_isa_add_driver(&it87_isa_driver);
if (res) {
i2c_del_driver(&it87_driver);
return res;
}
return 0;
}
static void __exit sm_it87_exit(void)
{
i2c_isa_del_driver(&it87_isa_driver);
i2c_del_driver(&it87_driver);
}

View file

@ -42,8 +42,9 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon-sysfs.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/*
* Addresses to scan
@ -51,13 +52,12 @@
*/
static unsigned short normal_i2c[] = { 0x4c, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(lm63);
I2C_CLIENT_INSMOD_1(lm63);
/*
* The LM63 registers
@ -152,6 +152,7 @@ static struct i2c_driver lm63_driver = {
struct lm63_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -358,7 +359,7 @@ static int lm63_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm63_detect);
return i2c_probe(adapter, &addr_data, lm63_detect);
}
/*
@ -437,6 +438,12 @@ static int lm63_detect(struct i2c_adapter *adapter, int address, int kind)
lm63_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
if (data->config & 0x04) { /* tachometer enabled */
device_create_file(&new_client->dev,
&sensor_dev_attr_fan1_input.dev_attr);
@ -462,6 +469,8 @@ static int lm63_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -505,15 +514,15 @@ static void lm63_init_client(struct i2c_client *client)
static int lm63_detach_client(struct i2c_client *client)
{
struct lm63_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -23,17 +23,17 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include "lm75.h"
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c,
0x4d, 0x4e, 0x4f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(lm75);
I2C_CLIENT_INSMOD_1(lm75);
/* Many LM75 constants specified below */
@ -46,6 +46,7 @@ SENSORS_INSMOD_1(lm75);
/* Each client has this additional data */
struct lm75_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* !=0 if following fields are valid */
unsigned long last_updated; /* In jiffies */
@ -107,10 +108,10 @@ static int lm75_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm75_detect);
return i2c_probe(adapter, &addr_data, lm75_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
static int lm75_detect(struct i2c_adapter *adapter, int address, int kind)
{
int i;
@ -119,16 +120,6 @@ static int lm75_detect(struct i2c_adapter *adapter, int address, int kind)
int err = 0;
const char *name = "";
/* Make sure we aren't probing the ISA bus!! This is just a safety check
at this moment; i2c_detect really won't call us. */
#ifdef DEBUG
if (i2c_is_isa_adapter(adapter)) {
dev_dbg(&adapter->dev,
"lm75_detect called for an ISA bus adapter?!?\n");
goto exit;
}
#endif
if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA |
I2C_FUNC_SMBUS_WORD_DATA))
goto exit;
@ -208,12 +199,20 @@ static int lm75_detect(struct i2c_adapter *adapter, int address, int kind)
lm75_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_temp1_max);
device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst);
device_create_file(&new_client->dev, &dev_attr_temp1_input);
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -222,8 +221,10 @@ static int lm75_detect(struct i2c_adapter *adapter, int address, int kind)
static int lm75_detach_client(struct i2c_client *client)
{
struct lm75_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->class_dev);
i2c_detach_client(client);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -251,8 +252,12 @@ static int lm75_write_value(struct i2c_client *client, u8 reg, u16 value)
static void lm75_init_client(struct i2c_client *client)
{
/* Initialize the LM75 chip */
lm75_write_value(client, LM75_REG_CONF, 0);
int reg;
/* Enable if in shutdown mode */
reg = lm75_read_value(client, LM75_REG_CONF);
if (reg >= 0 && (reg & 0x01))
lm75_write_value(client, LM75_REG_CONF, reg & 0xfe);
}
static struct lm75_data *lm75_update_device(struct device *dev)

View file

@ -25,7 +25,7 @@
which contains this code, we don't worry about the wasted space.
*/
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
/* straight from the datasheet */
#define LM75_TEMP_MIN (-55000)

View file

@ -30,15 +30,14 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(lm77);
I2C_CLIENT_INSMOD_1(lm77);
/* The LM77 registers */
#define LM77_REG_TEMP 0x00
@ -51,6 +50,7 @@ SENSORS_INSMOD_1(lm77);
/* Each client has this additional data */
struct lm77_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid;
unsigned long last_updated; /* In jiffies */
@ -208,10 +208,10 @@ static int lm77_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm77_detect);
return i2c_probe(adapter, &addr_data, lm77_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
static int lm77_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
@ -317,6 +317,12 @@ static int lm77_detect(struct i2c_adapter *adapter, int address, int kind)
lm77_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_temp1_input);
device_create_file(&new_client->dev, &dev_attr_temp1_crit);
device_create_file(&new_client->dev, &dev_attr_temp1_min);
@ -327,6 +333,8 @@ static int lm77_detect(struct i2c_adapter *adapter, int address, int kind)
device_create_file(&new_client->dev, &dev_attr_alarms);
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -335,8 +343,10 @@ static int lm77_detect(struct i2c_adapter *adapter, int address, int kind)
static int lm77_detach_client(struct i2c_client *client)
{
struct lm77_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->class_dev);
i2c_detach_client(client);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}

View file

@ -23,7 +23,10 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
#include <asm/io.h>
/* Addresses to scan */
@ -31,10 +34,10 @@ static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24,
0x25, 0x26, 0x27, 0x28, 0x29,
0x2a, 0x2b, 0x2c, 0x2d, 0x2e,
0x2f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0x0290, I2C_CLIENT_ISA_END };
static unsigned short isa_address = 0x290;
/* Insmod parameters */
SENSORS_INSMOD_3(lm78, lm78j, lm79);
I2C_CLIENT_INSMOD_2(lm78, lm79);
/* Many LM78 constants specified below */
@ -104,13 +107,6 @@ static inline int TEMP_FROM_REG(s8 val)
return val * 1000;
}
/* VID: mV
REG: (see doc/vid) */
static inline int VID_FROM_REG(u8 val)
{
return val==0x1f ? 0 : val>=0x10 ? 5100-val*100 : 2050-val*50;
}
#define DIV_FROM_REG(val) (1 << (val))
/* There are some complications in a module like this. First off, LM78 chips
@ -134,6 +130,7 @@ static inline int VID_FROM_REG(u8 val)
allocated. */
struct lm78_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -156,6 +153,7 @@ struct lm78_data {
static int lm78_attach_adapter(struct i2c_adapter *adapter);
static int lm78_isa_attach_adapter(struct i2c_adapter *adapter);
static int lm78_detect(struct i2c_adapter *adapter, int address, int kind);
static int lm78_detach_client(struct i2c_client *client);
@ -174,6 +172,14 @@ static struct i2c_driver lm78_driver = {
.detach_client = lm78_detach_client,
};
static struct i2c_driver lm78_isa_driver = {
.owner = THIS_MODULE,
.name = "lm78-isa",
.attach_adapter = lm78_isa_attach_adapter,
.detach_client = lm78_detach_client,
};
/* 7 Voltages */
static ssize_t show_in(struct device *dev, char *buf, int nr)
{
@ -445,7 +451,7 @@ static DEVICE_ATTR(fan3_div, S_IRUGO, show_fan_3_div, NULL);
static ssize_t show_vid(struct device *dev, struct device_attribute *attr, char *buf)
{
struct lm78_data *data = lm78_update_device(dev);
return sprintf(buf, "%d\n", VID_FROM_REG(data->vid));
return sprintf(buf, "%d\n", vid_from_reg(82, data->vid));
}
static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL);
@ -465,10 +471,15 @@ static int lm78_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm78_detect);
return i2c_probe(adapter, &addr_data, lm78_detect);
}
/* This function is called by i2c_detect */
static int lm78_isa_attach_adapter(struct i2c_adapter *adapter)
{
return lm78_detect(adapter, isa_address, -1);
}
/* This function is called by i2c_probe */
int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
{
int i, err;
@ -485,7 +496,8 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
/* Reserve the ISA region */
if (is_isa)
if (!request_region(address, LM78_EXTENT, lm78_driver.name)) {
if (!request_region(address, LM78_EXTENT,
lm78_isa_driver.name)) {
err = -EBUSY;
goto ERROR0;
}
@ -540,7 +552,7 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
i2c_set_clientdata(new_client, data);
new_client->addr = address;
new_client->adapter = adapter;
new_client->driver = &lm78_driver;
new_client->driver = is_isa ? &lm78_isa_driver : &lm78_driver;
new_client->flags = 0;
/* Now, we do the remaining detection. */
@ -559,10 +571,9 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
/* Determine the chip type. */
if (kind <= 0) {
i = lm78_read_value(new_client, LM78_REG_CHIPID);
if (i == 0x00 || i == 0x20)
if (i == 0x00 || i == 0x20 /* LM78 */
|| i == 0x40) /* LM78-J */
kind = lm78;
else if (i == 0x40)
kind = lm78j;
else if ((i & 0xfe) == 0xc0)
kind = lm79;
else {
@ -578,8 +589,6 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
if (kind == lm78) {
client_name = "lm78";
} else if (kind == lm78j) {
client_name = "lm78-j";
} else if (kind == lm79) {
client_name = "lm79";
}
@ -605,6 +614,12 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
}
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto ERROR3;
}
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in0_min);
device_create_file(&new_client->dev, &dev_attr_in0_max);
@ -643,6 +658,8 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
ERROR3:
i2c_detach_client(new_client);
ERROR2:
kfree(data);
ERROR1:
@ -654,18 +671,18 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind)
static int lm78_detach_client(struct i2c_client *client)
{
struct lm78_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
if(i2c_is_isa_client(client))
release_region(client->addr, LM78_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -777,18 +794,31 @@ static struct lm78_data *lm78_update_device(struct device *dev)
static int __init sm_lm78_init(void)
{
return i2c_add_driver(&lm78_driver);
int res;
res = i2c_add_driver(&lm78_driver);
if (res)
return res;
res = i2c_isa_add_driver(&lm78_isa_driver);
if (res) {
i2c_del_driver(&lm78_driver);
return res;
}
return 0;
}
static void __exit sm_lm78_exit(void)
{
i2c_isa_del_driver(&lm78_isa_driver);
i2c_del_driver(&lm78_driver);
}
MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>");
MODULE_DESCRIPTION("LM78, LM78-J and LM79 driver");
MODULE_DESCRIPTION("LM78/LM79 driver");
MODULE_LICENSE("GPL");
module_init(sm_lm78_init);

View file

@ -26,15 +26,15 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c,
0x2d, 0x2e, 0x2f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(lm80);
I2C_CLIENT_INSMOD_1(lm80);
/* Many LM80 constants specified below */
@ -107,6 +107,7 @@ static inline long TEMP_FROM_REG(u16 temp)
struct lm80_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* !=0 if following fields are valid */
unsigned long last_updated; /* In jiffies */
@ -389,7 +390,7 @@ static int lm80_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm80_detect);
return i2c_probe(adapter, &addr_data, lm80_detect);
}
int lm80_detect(struct i2c_adapter *adapter, int address, int kind)
@ -451,6 +452,12 @@ int lm80_detect(struct i2c_adapter *adapter, int address, int kind)
data->fan_min[1] = lm80_read_value(new_client, LM80_REG_FAN_MIN(2));
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto error_detach;
}
device_create_file(&new_client->dev, &dev_attr_in0_min);
device_create_file(&new_client->dev, &dev_attr_in1_min);
device_create_file(&new_client->dev, &dev_attr_in2_min);
@ -487,6 +494,8 @@ int lm80_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
error_detach:
i2c_detach_client(new_client);
error_free:
kfree(data);
exit:
@ -495,15 +504,15 @@ int lm80_detect(struct i2c_adapter *adapter, int address, int kind)
static int lm80_detach_client(struct i2c_client *client)
{
struct lm80_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -32,8 +32,9 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon-sysfs.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/*
* Addresses to scan
@ -45,13 +46,12 @@ static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a,
0x29, 0x2a, 0x2b,
0x4c, 0x4d, 0x4e,
I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(lm83);
I2C_CLIENT_INSMOD_1(lm83);
/*
* The LM83 registers
@ -138,6 +138,7 @@ static struct i2c_driver lm83_driver = {
struct lm83_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -212,7 +213,7 @@ static int lm83_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm83_detect);
return i2c_probe(adapter, &addr_data, lm83_detect);
}
/*
@ -312,6 +313,12 @@ static int lm83_detect(struct i2c_adapter *adapter, int address, int kind)
*/
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev,
&sensor_dev_attr_temp1_input.dev_attr);
device_create_file(&new_client->dev,
@ -340,6 +347,8 @@ static int lm83_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -348,15 +357,15 @@ static int lm83_detect(struct i2c_adapter *adapter, int address, int kind)
static int lm83_detach_client(struct i2c_client *client)
{
struct lm83_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -28,15 +28,15 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_6(lm85b, lm85c, adm1027, adt7463, emc6d100, emc6d102);
I2C_CLIENT_INSMOD_6(lm85b, lm85c, adm1027, adt7463, emc6d100, emc6d102);
/* The LM85 registers */
@ -281,15 +281,6 @@ static int ZONE_TO_REG( int zone )
#define PPR_TO_REG(val,fan) (SENSORS_LIMIT((val)-1,0,3)<<(fan *2))
#define PPR_FROM_REG(val,fan) ((((val)>>(fan * 2))&0x03)+1)
/* i2c-vid.h defines vid_from_reg() */
#define VID_FROM_REG(val,vrm) (vid_from_reg((val),(vrm)))
/* Unlike some other drivers we DO NOT set initial limits. Use
* the config file to set limits. Some users have reported
* motherboards shutting down when we set limits in a previous
* version of the driver.
*/
/* Chip sampling rates
*
* Some sensors are not updated more frequently than once per second
@ -339,6 +330,7 @@ struct lm85_autofan {
struct lm85_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -1019,7 +1011,7 @@ int lm85_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm85_detect);
return i2c_probe(adapter, &addr_data, lm85_detect);
}
int lm85_detect(struct i2c_adapter *adapter, int address,
@ -1031,11 +1023,6 @@ int lm85_detect(struct i2c_adapter *adapter, int address,
int err = 0;
const char *type_name = "";
if (i2c_is_isa_adapter(adapter)) {
/* This chip has no ISA interface */
goto ERROR0 ;
};
if (!i2c_check_functionality(adapter,
I2C_FUNC_SMBUS_BYTE_DATA)) {
/* We need to be able to do byte I/O */
@ -1160,12 +1147,18 @@ int lm85_detect(struct i2c_adapter *adapter, int address,
goto ERROR1;
/* Set the VRM version */
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
/* Initialize the LM85 chip */
lm85_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto ERROR2;
}
device_create_file(&new_client->dev, &dev_attr_fan1_input);
device_create_file(&new_client->dev, &dev_attr_fan2_input);
device_create_file(&new_client->dev, &dev_attr_fan3_input);
@ -1235,6 +1228,8 @@ int lm85_detect(struct i2c_adapter *adapter, int address,
return 0;
/* Error out and cleanup code */
ERROR2:
i2c_detach_client(new_client);
ERROR1:
kfree(data);
ERROR0:
@ -1243,8 +1238,10 @@ int lm85_detect(struct i2c_adapter *adapter, int address,
int lm85_detach_client(struct i2c_client *client)
{
struct lm85_data *data = i2c_get_clientdata(client);
hwmon_device_unregister(data->class_dev);
i2c_detach_client(client);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}

View file

@ -57,8 +57,9 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
/*
* Addresses to scan
@ -66,13 +67,12 @@
*/
static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(lm87);
I2C_CLIENT_INSMOD_1(lm87);
/*
* The LM87 registers
@ -175,6 +175,7 @@ static struct i2c_driver lm87_driver = {
struct lm87_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* In jiffies */
@ -537,7 +538,7 @@ static int lm87_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm87_detect);
return i2c_probe(adapter, &addr_data, lm87_detect);
}
/*
@ -608,6 +609,12 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind)
data->in_scale[7] = 1875;
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_in1_input);
device_create_file(&new_client->dev, &dev_attr_in1_min);
device_create_file(&new_client->dev, &dev_attr_in1_max);
@ -673,6 +680,8 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -685,7 +694,7 @@ static void lm87_init_client(struct i2c_client *client)
u8 config;
data->channel = lm87_read_value(client, LM87_REG_CHANNEL_MODE);
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
config = lm87_read_value(client, LM87_REG_CONFIG);
if (!(config & 0x01)) {
@ -719,15 +728,15 @@ static void lm87_init_client(struct i2c_client *client)
static int lm87_detach_client(struct i2c_client *client)
{
struct lm87_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -75,8 +75,9 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon-sysfs.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/*
* Addresses to scan
@ -89,13 +90,12 @@
*/
static unsigned short normal_i2c[] = { 0x4c, 0x4d, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_6(lm90, adm1032, lm99, lm86, max6657, adt7461);
I2C_CLIENT_INSMOD_6(lm90, adm1032, lm99, lm86, max6657, adt7461);
/*
* The LM90 registers
@ -200,6 +200,7 @@ static struct i2c_driver lm90_driver = {
struct lm90_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -352,7 +353,7 @@ static int lm90_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm90_detect);
return i2c_probe(adapter, &addr_data, lm90_detect);
}
/*
@ -500,6 +501,12 @@ static int lm90_detect(struct i2c_adapter *adapter, int address, int kind)
lm90_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev,
&sensor_dev_attr_temp1_input.dev_attr);
device_create_file(&new_client->dev,
@ -524,6 +531,8 @@ static int lm90_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -547,15 +556,15 @@ static void lm90_init_client(struct i2c_client *client)
static int lm90_detach_client(struct i2c_client *client)
{
struct lm90_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -44,17 +44,16 @@
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* The LM92 and MAX6635 have 2 two-state pins for address selection,
resulting in 4 possible addresses. */
static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b,
I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(lm92);
I2C_CLIENT_INSMOD_1(lm92);
/* The LM92 registers */
#define LM92_REG_CONFIG 0x01 /* 8-bit, RW */
@ -96,6 +95,7 @@ static struct i2c_driver lm92_driver;
/* Client data (each client gets its own) */
struct lm92_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -359,6 +359,12 @@ static int lm92_detect(struct i2c_adapter *adapter, int address, int kind)
lm92_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_temp1_input);
device_create_file(&new_client->dev, &dev_attr_temp1_crit);
device_create_file(&new_client->dev, &dev_attr_temp1_crit_hyst);
@ -370,6 +376,8 @@ static int lm92_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -380,20 +388,20 @@ static int lm92_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, lm92_detect);
return i2c_probe(adapter, &addr_data, lm92_detect);
}
static int lm92_detach_client(struct i2c_client *client)
{
struct lm92_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -31,20 +31,19 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a,
0x29, 0x2a, 0x2b,
0x4c, 0x4d, 0x4e,
I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(max1619);
I2C_CLIENT_INSMOD_1(max1619);
/*
* The MAX1619 registers
@ -104,6 +103,7 @@ static struct i2c_driver max1619_driver = {
struct max1619_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -179,7 +179,7 @@ static int max1619_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, max1619_detect);
return i2c_probe(adapter, &addr_data, max1619_detect);
}
/*
@ -275,6 +275,12 @@ static int max1619_detect(struct i2c_adapter *adapter, int address, int kind)
max1619_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_temp1_input);
device_create_file(&new_client->dev, &dev_attr_temp2_input);
device_create_file(&new_client->dev, &dev_attr_temp2_min);
@ -285,6 +291,8 @@ static int max1619_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -308,15 +316,15 @@ static void max1619_init_client(struct i2c_client *client)
static int max1619_detach_client(struct i2c_client *client)
{
struct max1619_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

File diff suppressed because it is too large Load diff

View file

@ -55,7 +55,9 @@
#include <linux/ioport.h>
#include <linux/pci.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include <linux/init.h>
#include <linux/jiffies.h>
#include <asm/io.h>
@ -68,14 +70,10 @@ module_param(force_addr, ushort, 0);
MODULE_PARM_DESC(force_addr,
"Initialize the base address of the sensors");
/* Addresses to scan.
/* Device address
Note that we can't determine the ISA address until we have initialized
our module */
static unsigned short normal_i2c[] = { I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(sis5595);
static unsigned short address;
/* Many SIS5595 constants specified below */
@ -168,6 +166,7 @@ static inline u8 DIV_TO_REG(int val)
allocated. */
struct sis5595_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
struct semaphore update_lock;
@ -190,8 +189,7 @@ struct sis5595_data {
static struct pci_dev *s_bridge; /* pointer to the (only) sis5595 */
static int sis5595_attach_adapter(struct i2c_adapter *adapter);
static int sis5595_detect(struct i2c_adapter *adapter, int address, int kind);
static int sis5595_detect(struct i2c_adapter *adapter);
static int sis5595_detach_client(struct i2c_client *client);
static int sis5595_read_value(struct i2c_client *client, u8 register);
@ -202,9 +200,7 @@ static void sis5595_init_client(struct i2c_client *client);
static struct i2c_driver sis5595_driver = {
.owner = THIS_MODULE,
.name = "sis5595",
.id = I2C_DRIVERID_SIS5595,
.flags = I2C_DF_NOTIFY,
.attach_adapter = sis5595_attach_adapter,
.attach_adapter = sis5595_detect,
.detach_client = sis5595_detach_client,
};
@ -476,14 +472,7 @@ static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, ch
static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL);
/* This is called when the module is loaded */
static int sis5595_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, sis5595_detect);
}
int sis5595_detect(struct i2c_adapter *adapter, int address, int kind)
static int sis5595_detect(struct i2c_adapter *adapter)
{
int err = 0;
int i;
@ -492,10 +481,6 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind)
char val;
u16 a;
/* Make sure we are probing the ISA bus!! */
if (!i2c_is_isa_adapter(adapter))
goto exit;
if (force_addr)
address = force_addr & ~(SIS5595_EXTENT - 1);
/* Reserve the ISA region */
@ -578,6 +563,12 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind)
}
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in0_min);
device_create_file(&new_client->dev, &dev_attr_in0_max);
@ -608,7 +599,9 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind)
device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst);
}
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit_release:
@ -619,18 +612,17 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind)
static int sis5595_detach_client(struct i2c_client *client)
{
struct sis5595_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
if (i2c_is_isa_client(client))
release_region(client->addr, SIS5595_EXTENT);
release_region(client->addr, SIS5595_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -745,7 +737,6 @@ static int __devinit sis5595_pci_probe(struct pci_dev *dev,
{
u16 val;
int *i;
int addr = 0;
for (i = blacklist; *i != 0; i++) {
struct pci_dev *dev;
@ -761,22 +752,19 @@ static int __devinit sis5595_pci_probe(struct pci_dev *dev,
pci_read_config_word(dev, SIS5595_BASE_REG, &val))
return -ENODEV;
addr = val & ~(SIS5595_EXTENT - 1);
if (addr == 0 && force_addr == 0) {
address = val & ~(SIS5595_EXTENT - 1);
if (address == 0 && force_addr == 0) {
dev_err(&dev->dev, "Base address not set - upgrade BIOS or use force_addr=0xaddr\n");
return -ENODEV;
}
if (force_addr)
addr = force_addr; /* so detect will get called */
if (!addr) {
if (!address) {
dev_err(&dev->dev,"No SiS 5595 sensors found.\n");
return -ENODEV;
}
normal_isa[0] = addr;
s_bridge = pci_dev_get(dev);
if (i2c_add_driver(&sis5595_driver)) {
if (i2c_isa_add_driver(&sis5595_driver)) {
pci_dev_put(s_bridge);
s_bridge = NULL;
}
@ -803,7 +791,7 @@ static void __exit sm_sis5595_exit(void)
{
pci_unregister_driver(&sis5595_pci_driver);
if (s_bridge != NULL) {
i2c_del_driver(&sis5595_driver);
i2c_isa_del_driver(&sis5595_driver);
pci_dev_put(s_bridge);
s_bridge = NULL;
}

View file

@ -31,23 +31,14 @@
#include <linux/ioport.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include <linux/init.h>
#include <asm/io.h>
static unsigned short normal_i2c[] = { I2C_CLIENT_END };
/* Address is autodetected, there is no default value */
static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END };
static struct i2c_force_data forces[] = {{NULL}};
enum chips { any_chip, smsc47b397 };
static struct i2c_address_data addr_data = {
.normal_i2c = normal_i2c,
.normal_isa = normal_isa,
.probe = normal_i2c, /* cheat */
.ignore = normal_i2c, /* cheat */
.forces = forces,
};
static unsigned short address;
/* Super-I/0 registers and commands */
@ -100,6 +91,7 @@ static u8 smsc47b397_reg_temp[] = {0x25, 0x26, 0x27, 0x80};
struct smsc47b397_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
struct semaphore update_lock;
@ -215,52 +207,40 @@ sysfs_fan(4);
#define device_create_file_fan(client, num) \
device_create_file(&client->dev, &dev_attr_fan##num##_input)
static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind);
static int smsc47b397_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, smsc47b397_detect);
}
static int smsc47b397_detach_client(struct i2c_client *client)
{
struct smsc47b397_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
release_region(client->addr, SMSC_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
static int smsc47b397_detect(struct i2c_adapter *adapter);
static struct i2c_driver smsc47b397_driver = {
.owner = THIS_MODULE,
.name = "smsc47b397",
.id = I2C_DRIVERID_SMSC47B397,
.flags = I2C_DF_NOTIFY,
.attach_adapter = smsc47b397_attach_adapter,
.attach_adapter = smsc47b397_detect,
.detach_client = smsc47b397_detach_client,
};
static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind)
static int smsc47b397_detect(struct i2c_adapter *adapter)
{
struct i2c_client *new_client;
struct smsc47b397_data *data;
int err = 0;
if (!i2c_is_isa_adapter(adapter)) {
return 0;
}
if (!request_region(addr, SMSC_EXTENT, smsc47b397_driver.name)) {
dev_err(&adapter->dev, "Region 0x%x already in use!\n", addr);
if (!request_region(address, SMSC_EXTENT, smsc47b397_driver.name)) {
dev_err(&adapter->dev, "Region 0x%x already in use!\n",
address);
return -EBUSY;
}
@ -272,7 +252,7 @@ static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind)
new_client = &data->client;
i2c_set_clientdata(new_client, data);
new_client->addr = addr;
new_client->addr = address;
init_MUTEX(&data->lock);
new_client->adapter = adapter;
new_client->driver = &smsc47b397_driver;
@ -285,6 +265,12 @@ static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind)
if ((err = i2c_attach_client(new_client)))
goto error_free;
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto error_detach;
}
device_create_file_temp(new_client, 1);
device_create_file_temp(new_client, 2);
device_create_file_temp(new_client, 3);
@ -297,14 +283,16 @@ static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind)
return 0;
error_detach:
i2c_detach_client(new_client);
error_free:
kfree(data);
error_release:
release_region(addr, SMSC_EXTENT);
release_region(address, SMSC_EXTENT);
return err;
}
static int __init smsc47b397_find(unsigned int *addr)
static int __init smsc47b397_find(unsigned short *addr)
{
u8 id, rev;
@ -333,15 +321,15 @@ static int __init smsc47b397_init(void)
{
int ret;
if ((ret = smsc47b397_find(normal_isa)))
if ((ret = smsc47b397_find(&address)))
return ret;
return i2c_add_driver(&smsc47b397_driver);
return i2c_isa_add_driver(&smsc47b397_driver);
}
static void __exit smsc47b397_exit(void)
{
i2c_del_driver(&smsc47b397_driver);
i2c_isa_del_driver(&smsc47b397_driver);
}
MODULE_AUTHOR("Mark M. Hoffman <mhoffman@lightlink.com>");

View file

@ -30,21 +30,14 @@
#include <linux/ioport.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include <linux/init.h>
#include <asm/io.h>
static unsigned short normal_i2c[] = { I2C_CLIENT_END };
/* Address is autodetected, there is no default value */
static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END };
static struct i2c_force_data forces[] = {{NULL}};
enum chips { any_chip, smsc47m1 };
static struct i2c_address_data addr_data = {
.normal_i2c = normal_i2c,
.normal_isa = normal_isa,
.forces = forces,
};
static unsigned short address;
/* Super-I/0 registers and commands */
@ -108,6 +101,7 @@ superio_exit(void)
struct smsc47m1_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
struct semaphore update_lock;
@ -121,9 +115,7 @@ struct smsc47m1_data {
};
static int smsc47m1_attach_adapter(struct i2c_adapter *adapter);
static int smsc47m1_find(int *address);
static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind);
static int smsc47m1_detect(struct i2c_adapter *adapter);
static int smsc47m1_detach_client(struct i2c_client *client);
static int smsc47m1_read_value(struct i2c_client *client, u8 reg);
@ -136,9 +128,7 @@ static struct smsc47m1_data *smsc47m1_update_device(struct device *dev,
static struct i2c_driver smsc47m1_driver = {
.owner = THIS_MODULE,
.name = "smsc47m1",
.id = I2C_DRIVERID_SMSC47M1,
.flags = I2C_DF_NOTIFY,
.attach_adapter = smsc47m1_attach_adapter,
.attach_adapter = smsc47m1_detect,
.detach_client = smsc47m1_detach_client,
};
@ -354,14 +344,7 @@ fan_present(2);
static DEVICE_ATTR(alarms, S_IRUGO, get_alarms, NULL);
static int smsc47m1_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, smsc47m1_detect);
}
static int smsc47m1_find(int *address)
static int __init smsc47m1_find(unsigned short *addr)
{
u8 val;
@ -388,10 +371,10 @@ static int smsc47m1_find(int *address)
}
superio_select();
*address = (superio_inb(SUPERIO_REG_BASE) << 8)
| superio_inb(SUPERIO_REG_BASE + 1);
*addr = (superio_inb(SUPERIO_REG_BASE) << 8)
| superio_inb(SUPERIO_REG_BASE + 1);
val = superio_inb(SUPERIO_REG_ACT);
if (*address == 0 || (val & 0x01) == 0) {
if (*addr == 0 || (val & 0x01) == 0) {
printk(KERN_INFO "smsc47m1: Device is disabled, will not use\n");
superio_exit();
return -ENODEV;
@ -401,17 +384,13 @@ static int smsc47m1_find(int *address)
return 0;
}
static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind)
static int smsc47m1_detect(struct i2c_adapter *adapter)
{
struct i2c_client *new_client;
struct smsc47m1_data *data;
int err = 0;
int fan1, fan2, pwm1, pwm2;
if (!i2c_is_isa_adapter(adapter)) {
return 0;
}
if (!request_region(address, SMSC_EXTENT, smsc47m1_driver.name)) {
dev_err(&adapter->dev, "Region 0x%x already in use!\n", address);
return -EBUSY;
@ -461,6 +440,13 @@ static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind)
function. */
smsc47m1_update_device(&new_client->dev, 1);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto error_detach;
}
if (fan1) {
device_create_file(&new_client->dev, &dev_attr_fan1_input);
device_create_file(&new_client->dev, &dev_attr_fan1_min);
@ -494,6 +480,8 @@ static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
error_detach:
i2c_detach_client(new_client);
error_free:
kfree(data);
error_release:
@ -503,16 +491,16 @@ static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind)
static int smsc47m1_detach_client(struct i2c_client *client)
{
struct smsc47m1_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
release_region(client->addr, SMSC_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -573,16 +561,16 @@ static struct smsc47m1_data *smsc47m1_update_device(struct device *dev,
static int __init sm_smsc47m1_init(void)
{
if (smsc47m1_find(normal_isa)) {
if (smsc47m1_find(&address)) {
return -ENODEV;
}
return i2c_add_driver(&smsc47m1_driver);
return i2c_isa_add_driver(&smsc47m1_driver);
}
static void __exit sm_smsc47m1_exit(void)
{
i2c_del_driver(&smsc47m1_driver);
i2c_isa_del_driver(&smsc47m1_driver);
}
MODULE_AUTHOR("Mark D. Studebaker <mdsxyz123@yahoo.com>");

View file

@ -35,7 +35,9 @@
#include <linux/pci.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include <linux/init.h>
#include <asm/io.h>
@ -47,14 +49,10 @@ module_param(force_addr, ushort, 0);
MODULE_PARM_DESC(force_addr,
"Initialize the base address of the sensors");
/* Addresses to scan.
/* Device address
Note that we can't determine the ISA address until we have initialized
our module */
static unsigned short normal_i2c[] = { I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(via686a);
static unsigned short address;
/*
The Via 686a southbridge has a LM78-like chip integrated on the same IC.
@ -297,6 +295,7 @@ static inline long TEMP_FROM_REG10(u16 val)
via686a client is allocated. */
struct via686a_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* !=0 if following fields are valid */
unsigned long last_updated; /* In jiffies */
@ -315,8 +314,7 @@ struct via686a_data {
static struct pci_dev *s_bridge; /* pointer to the (only) via686a */
static int via686a_attach_adapter(struct i2c_adapter *adapter);
static int via686a_detect(struct i2c_adapter *adapter, int address, int kind);
static int via686a_detect(struct i2c_adapter *adapter);
static int via686a_detach_client(struct i2c_client *client);
static inline int via686a_read_value(struct i2c_client *client, u8 reg)
@ -576,22 +574,13 @@ static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL);
static struct i2c_driver via686a_driver = {
.owner = THIS_MODULE,
.name = "via686a",
.id = I2C_DRIVERID_VIA686A,
.flags = I2C_DF_NOTIFY,
.attach_adapter = via686a_attach_adapter,
.attach_adapter = via686a_detect,
.detach_client = via686a_detach_client,
};
/* This is called when the module is loaded */
static int via686a_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, via686a_detect);
}
static int via686a_detect(struct i2c_adapter *adapter, int address, int kind)
static int via686a_detect(struct i2c_adapter *adapter)
{
struct i2c_client *new_client;
struct via686a_data *data;
@ -599,13 +588,6 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind)
const char client_name[] = "via686a";
u16 val;
/* Make sure we are probing the ISA bus!! */
if (!i2c_is_isa_adapter(adapter)) {
dev_err(&adapter->dev,
"via686a_detect called for an I2C bus adapter?!?\n");
return 0;
}
/* 8231 requires multiple of 256, we enforce that on 686 as well */
if (force_addr)
address = force_addr & 0xFF00;
@ -637,7 +619,7 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind)
if (!(data = kmalloc(sizeof(struct via686a_data), GFP_KERNEL))) {
err = -ENOMEM;
goto ERROR0;
goto exit_release;
}
memset(data, 0, sizeof(struct via686a_data));
@ -655,12 +637,18 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind)
init_MUTEX(&data->update_lock);
/* Tell the I2C layer a new client has arrived */
if ((err = i2c_attach_client(new_client)))
goto ERROR3;
goto exit_free;
/* Initialize the VIA686A chip */
via686a_init_client(new_client);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_in0_input);
device_create_file(&new_client->dev, &dev_attr_in1_input);
device_create_file(&new_client->dev, &dev_attr_in2_input);
@ -695,25 +683,27 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
ERROR3:
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
ERROR0:
exit_release:
release_region(address, VIA686A_EXTENT);
return err;
}
static int via686a_detach_client(struct i2c_client *client)
{
struct via686a_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
release_region(client->addr, VIA686A_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -810,29 +800,25 @@ static int __devinit via686a_pci_probe(struct pci_dev *dev,
const struct pci_device_id *id)
{
u16 val;
int addr = 0;
if (PCIBIOS_SUCCESSFUL !=
pci_read_config_word(dev, VIA686A_BASE_REG, &val))
return -ENODEV;
addr = val & ~(VIA686A_EXTENT - 1);
if (addr == 0 && force_addr == 0) {
address = val & ~(VIA686A_EXTENT - 1);
if (address == 0 && force_addr == 0) {
dev_err(&dev->dev, "base address not set - upgrade BIOS "
"or use force_addr=0xaddr\n");
return -ENODEV;
}
if (force_addr)
addr = force_addr; /* so detect will get called */
if (!addr) {
if (!address) {
dev_err(&dev->dev, "No Via 686A sensors found.\n");
return -ENODEV;
}
normal_isa[0] = addr;
s_bridge = pci_dev_get(dev);
if (i2c_add_driver(&via686a_driver)) {
if (i2c_isa_add_driver(&via686a_driver)) {
pci_dev_put(s_bridge);
s_bridge = NULL;
}
@ -859,7 +845,7 @@ static void __exit sm_via686a_exit(void)
{
pci_unregister_driver(&via686a_pci_driver);
if (s_bridge != NULL) {
i2c_del_driver(&via686a_driver);
i2c_isa_del_driver(&via686a_driver);
pci_dev_put(s_bridge);
s_bridge = NULL;
}

View file

@ -9,6 +9,9 @@
Thanks to Leon Moonen, Steve Cliffe and Grant Coady for their help
in testing and debugging this driver.
This driver also supports the W83627EHG, which is the lead-free
version of the W83627EHF.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
@ -37,17 +40,14 @@
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/err.h>
#include <asm/io.h>
#include "lm75.h"
/* Addresses to scan
The actual ISA address is read from Super-I/O configuration space */
static unsigned short normal_i2c[] = { I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0, I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(w83627ehf);
/* The actual ISA address is read from Super-I/O configuration space */
static unsigned short address;
/*
* Super-I/O constants and functions
@ -174,6 +174,7 @@ temp1_to_reg(int temp)
struct w83627ehf_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
struct semaphore update_lock;
@ -666,15 +667,12 @@ static void w83627ehf_init_client(struct i2c_client *client)
}
}
static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind)
static int w83627ehf_detect(struct i2c_adapter *adapter)
{
struct i2c_client *client;
struct w83627ehf_data *data;
int i, err = 0;
if (!i2c_is_isa_adapter(adapter))
return 0;
if (!request_region(address, REGION_LENGTH, w83627ehf_driver.name)) {
err = -EBUSY;
goto exit;
@ -720,6 +718,12 @@ static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind)
data->has_fan |= (1 << 4);
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&client->dev, &dev_attr_fan1_input);
device_create_file(&client->dev, &dev_attr_fan1_min);
device_create_file(&client->dev, &dev_attr_fan1_div);
@ -753,6 +757,8 @@ static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
exit_detach:
i2c_detach_client(client);
exit_free:
kfree(data);
exit_release:
@ -761,24 +767,17 @@ static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind)
return err;
}
static int w83627ehf_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, w83627ehf_detect);
}
static int w83627ehf_detach_client(struct i2c_client *client)
{
struct w83627ehf_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
release_region(client->addr, REGION_LENGTH);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -786,12 +785,11 @@ static int w83627ehf_detach_client(struct i2c_client *client)
static struct i2c_driver w83627ehf_driver = {
.owner = THIS_MODULE,
.name = "w83627ehf",
.flags = I2C_DF_NOTIFY,
.attach_adapter = w83627ehf_attach_adapter,
.attach_adapter = w83627ehf_detect,
.detach_client = w83627ehf_detach_client,
};
static int __init w83627ehf_find(int sioaddr, int *address)
static int __init w83627ehf_find(int sioaddr, unsigned short *addr)
{
u16 val;
@ -809,8 +807,8 @@ static int __init w83627ehf_find(int sioaddr, int *address)
superio_select(W83627EHF_LD_HWM);
val = (superio_inb(SIO_REG_ADDR) << 8)
| superio_inb(SIO_REG_ADDR + 1);
*address = val & ~(REGION_LENGTH - 1);
if (*address == 0) {
*addr = val & ~(REGION_LENGTH - 1);
if (*addr == 0) {
superio_exit();
return -ENODEV;
}
@ -826,16 +824,16 @@ static int __init w83627ehf_find(int sioaddr, int *address)
static int __init sensors_w83627ehf_init(void)
{
if (w83627ehf_find(0x2e, &normal_isa[0])
&& w83627ehf_find(0x4e, &normal_isa[0]))
if (w83627ehf_find(0x2e, &address)
&& w83627ehf_find(0x4e, &address))
return -ENODEV;
return i2c_add_driver(&w83627ehf_driver);
return i2c_isa_add_driver(&w83627ehf_driver);
}
static void __exit sensors_w83627ehf_exit(void)
{
i2c_del_driver(&w83627ehf_driver);
i2c_isa_del_driver(&w83627ehf_driver);
}
MODULE_AUTHOR("Jean Delvare <khali@linux-fr.org>");

View file

@ -42,8 +42,10 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
#include <asm/io.h>
#include "lm75.h"
@ -56,12 +58,11 @@ module_param(force_i2c, byte, 0);
MODULE_PARM_DESC(force_i2c,
"Initialize the i2c address of the sensors");
/* Addresses to scan */
static unsigned short normal_i2c[] = { I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0, I2C_CLIENT_ISA_END };
/* The actual ISA address is read from Super-I/O configuration space */
static unsigned short address;
/* Insmod parameters */
SENSORS_INSMOD_4(w83627hf, w83627thf, w83697hf, w83637hf);
enum chips { any_chip, w83627hf, w83627thf, w83697hf, w83637hf };
static int init = 1;
module_param(init, bool, 0);
@ -277,6 +278,7 @@ static inline u8 DIV_TO_REG(long val)
dynamically allocated, at the same time when a new client is allocated. */
struct w83627hf_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -314,9 +316,7 @@ struct w83627hf_data {
};
static int w83627hf_attach_adapter(struct i2c_adapter *adapter);
static int w83627hf_detect(struct i2c_adapter *adapter, int address,
int kind);
static int w83627hf_detect(struct i2c_adapter *adapter);
static int w83627hf_detach_client(struct i2c_client *client);
static int w83627hf_read_value(struct i2c_client *client, u16 register);
@ -328,9 +328,7 @@ static void w83627hf_init_client(struct i2c_client *client);
static struct i2c_driver w83627hf_driver = {
.owner = THIS_MODULE,
.name = "w83627hf",
.id = I2C_DRIVERID_W83627HF,
.flags = I2C_DF_NOTIFY,
.attach_adapter = w83627hf_attach_adapter,
.attach_adapter = w83627hf_detect,
.detach_client = w83627hf_detach_client,
};
@ -959,16 +957,7 @@ device_create_file(&client->dev, &dev_attr_temp##offset##_type); \
} while (0)
/* This function is called when:
* w83627hf_driver is inserted (when this module is loaded), for each
available adapter
* when a new adapter is inserted (and w83627hf_driver is still present) */
static int w83627hf_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, w83627hf_detect);
}
static int w83627hf_find(int sioaddr, int *address)
static int __init w83627hf_find(int sioaddr, unsigned short *addr)
{
u16 val;
@ -988,32 +977,24 @@ static int w83627hf_find(int sioaddr, int *address)
superio_select(W83627HF_LD_HWM);
val = (superio_inb(WINB_BASE_REG) << 8) |
superio_inb(WINB_BASE_REG + 1);
*address = val & ~(WINB_EXTENT - 1);
if (*address == 0 && force_addr == 0) {
*addr = val & ~(WINB_EXTENT - 1);
if (*addr == 0 && force_addr == 0) {
superio_exit();
return -ENODEV;
}
if (force_addr)
*address = force_addr; /* so detect will get called */
superio_exit();
return 0;
}
int w83627hf_detect(struct i2c_adapter *adapter, int address,
int kind)
static int w83627hf_detect(struct i2c_adapter *adapter)
{
int val;
int val, kind;
struct i2c_client *new_client;
struct w83627hf_data *data;
int err = 0;
const char *client_name = "";
if (!i2c_is_isa_adapter(adapter)) {
err = -ENODEV;
goto ERROR0;
}
if(force_addr)
address = force_addr & ~(WINB_EXTENT - 1);
@ -1102,6 +1083,12 @@ int w83627hf_detect(struct i2c_adapter *adapter, int address,
data->fan_min[2] = w83627hf_read_value(new_client, W83781D_REG_FAN_MIN(3));
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto ERROR3;
}
device_create_file_in(new_client, 0);
if (kind != w83697hf)
device_create_file_in(new_client, 1);
@ -1152,6 +1139,8 @@ int w83627hf_detect(struct i2c_adapter *adapter, int address,
return 0;
ERROR3:
i2c_detach_client(new_client);
ERROR2:
kfree(data);
ERROR1:
@ -1162,16 +1151,16 @@ int w83627hf_detect(struct i2c_adapter *adapter, int address,
static int w83627hf_detach_client(struct i2c_client *client)
{
struct w83627hf_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
hwmon_device_unregister(data->class_dev);
if ((err = i2c_detach_client(client)))
return err;
}
release_region(client->addr, WINB_EXTENT);
kfree(i2c_get_clientdata(client));
kfree(data);
return 0;
}
@ -1327,7 +1316,7 @@ static void w83627hf_init_client(struct i2c_client *client)
data->vrm = (data->vrm_ovt & 0x01) ? 90 : 82;
} else {
/* Convert VID to voltage based on default VRM */
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
}
tmp = w83627hf_read_value(client, W83781D_REG_SCFG1);
@ -1485,20 +1474,17 @@ static struct w83627hf_data *w83627hf_update_device(struct device *dev)
static int __init sensors_w83627hf_init(void)
{
int addr;
if (w83627hf_find(0x2e, &addr)
&& w83627hf_find(0x4e, &addr)) {
if (w83627hf_find(0x2e, &address)
&& w83627hf_find(0x4e, &address)) {
return -ENODEV;
}
normal_isa[0] = addr;
return i2c_add_driver(&w83627hf_driver);
return i2c_isa_add_driver(&w83627hf_driver);
}
static void __exit sensors_w83627hf_exit(void)
{
i2c_del_driver(&w83627hf_driver);
i2c_isa_del_driver(&w83627hf_driver);
}
MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>, "

View file

@ -38,8 +38,10 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/i2c-vid.h>
#include <linux/i2c-isa.h>
#include <linux/hwmon.h>
#include <linux/hwmon-vid.h>
#include <linux/err.h>
#include <asm/io.h>
#include "lm75.h"
@ -47,10 +49,10 @@
static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, 0x25,
0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b,
0x2c, 0x2d, 0x2e, 0x2f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { 0x0290, I2C_CLIENT_ISA_END };
static unsigned short isa_address = 0x290;
/* Insmod parameters */
SENSORS_INSMOD_5(w83781d, w83782d, w83783s, w83627hf, as99127f);
I2C_CLIENT_INSMOD_5(w83781d, w83782d, w83783s, w83627hf, as99127f);
I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: "
"{bus, clientaddr, subclientaddr1, subclientaddr2}");
@ -218,6 +220,7 @@ DIV_TO_REG(long val, enum chips type)
allocated. */
struct w83781d_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore lock;
enum chips type;
@ -255,6 +258,7 @@ struct w83781d_data {
};
static int w83781d_attach_adapter(struct i2c_adapter *adapter);
static int w83781d_isa_attach_adapter(struct i2c_adapter *adapter);
static int w83781d_detect(struct i2c_adapter *adapter, int address, int kind);
static int w83781d_detach_client(struct i2c_client *client);
@ -273,6 +277,14 @@ static struct i2c_driver w83781d_driver = {
.detach_client = w83781d_detach_client,
};
static struct i2c_driver w83781d_isa_driver = {
.owner = THIS_MODULE,
.name = "w83781d-isa",
.attach_adapter = w83781d_isa_attach_adapter,
.detach_client = w83781d_detach_client,
};
/* following are the sysfs callback functions */
#define show_in_reg(reg) \
static ssize_t show_##reg (struct device *dev, char *buf, int nr) \
@ -856,7 +868,13 @@ w83781d_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, w83781d_detect);
return i2c_probe(adapter, &addr_data, w83781d_detect);
}
static int
w83781d_isa_attach_adapter(struct i2c_adapter *adapter)
{
return w83781d_detect(adapter, isa_address, -1);
}
/* Assumes that adapter is of I2C, not ISA variety.
@ -961,10 +979,10 @@ w83781d_detect_subclients(struct i2c_adapter *adapter, int address, int kind,
ERROR_SC_3:
i2c_detach_client(data->lm75[0]);
ERROR_SC_2:
if (NULL != data->lm75[1])
if (data->lm75[1])
kfree(data->lm75[1]);
ERROR_SC_1:
if (NULL != data->lm75[0])
if (data->lm75[0])
kfree(data->lm75[0]);
ERROR_SC_0:
return err;
@ -999,7 +1017,7 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind)
if (is_isa)
if (!request_region(address, W83781D_EXTENT,
w83781d_driver.name)) {
w83781d_isa_driver.name)) {
dev_dbg(&adapter->dev, "Request of region "
"0x%x-0x%x for w83781d failed\n", address,
address + W83781D_EXTENT - 1);
@ -1057,7 +1075,7 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind)
new_client->addr = address;
init_MUTEX(&data->lock);
new_client->adapter = adapter;
new_client->driver = &w83781d_driver;
new_client->driver = is_isa ? &w83781d_isa_driver : &w83781d_driver;
new_client->flags = 0;
/* Now, we do the remaining detection. */
@ -1189,6 +1207,12 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind)
data->pwmenable[i] = 1;
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto ERROR4;
}
device_create_file_in(new_client, 0);
if (kind != w83783s)
device_create_file_in(new_client, 1);
@ -1241,6 +1265,15 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind)
return 0;
ERROR4:
if (data->lm75[1]) {
i2c_detach_client(data->lm75[1]);
kfree(data->lm75[1]);
}
if (data->lm75[0]) {
i2c_detach_client(data->lm75[0]);
kfree(data->lm75[0]);
}
ERROR3:
i2c_detach_client(new_client);
ERROR2:
@ -1255,24 +1288,26 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind)
static int
w83781d_detach_client(struct i2c_client *client)
{
struct w83781d_data *data = i2c_get_clientdata(client);
int err;
/* main client */
if (data)
hwmon_device_unregister(data->class_dev);
if (i2c_is_isa_client(client))
release_region(client->addr, W83781D_EXTENT);
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
if ((err = i2c_detach_client(client)))
return err;
}
if (i2c_get_clientdata(client)==NULL) {
/* subclients */
/* main client */
if (data)
kfree(data);
/* subclient */
else
kfree(client);
} else {
/* main client */
kfree(i2c_get_clientdata(client));
}
return 0;
}
@ -1443,7 +1478,7 @@ w83781d_init_client(struct i2c_client *client)
w83781d_write_value(client, W83781D_REG_BEEP_INTS2, 0);
}
data->vrm = i2c_which_vrm();
data->vrm = vid_which_vrm();
if ((type != w83781d) && (type != as99127f)) {
tmp = w83781d_read_value(client, W83781D_REG_SCFG1);
@ -1613,12 +1648,25 @@ static struct w83781d_data *w83781d_update_device(struct device *dev)
static int __init
sensors_w83781d_init(void)
{
return i2c_add_driver(&w83781d_driver);
int res;
res = i2c_add_driver(&w83781d_driver);
if (res)
return res;
res = i2c_isa_add_driver(&w83781d_isa_driver);
if (res) {
i2c_del_driver(&w83781d_driver);
return res;
}
return 0;
}
static void __exit
sensors_w83781d_exit(void)
{
i2c_isa_del_driver(&w83781d_isa_driver);
i2c_del_driver(&w83781d_driver);
}

1649
drivers/hwmon/w83792d.c Normal file

File diff suppressed because it is too large Load diff

View file

@ -36,7 +36,8 @@
#include <linux/slab.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/hwmon.h>
#include <linux/err.h>
/* How many retries on register read error */
#define MAX_RETRIES 5
@ -47,13 +48,12 @@
*/
static unsigned short normal_i2c[] = { 0x2e, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/*
* Insmod parameters
*/
SENSORS_INSMOD_1(w83l785ts);
I2C_CLIENT_INSMOD_1(w83l785ts);
/*
* The W83L785TS-S registers
@ -105,6 +105,7 @@ static struct i2c_driver w83l785ts_driver = {
struct w83l785ts_data {
struct i2c_client client;
struct class_device *class_dev;
struct semaphore update_lock;
char valid; /* zero until following fields are valid */
unsigned long last_updated; /* in jiffies */
@ -140,7 +141,7 @@ static int w83l785ts_attach_adapter(struct i2c_adapter *adapter)
{
if (!(adapter->class & I2C_CLASS_HWMON))
return 0;
return i2c_detect(adapter, &addr_data, w83l785ts_detect);
return i2c_probe(adapter, &addr_data, w83l785ts_detect);
}
/*
@ -239,11 +240,19 @@ static int w83l785ts_detect(struct i2c_adapter *adapter, int address, int kind)
*/
/* Register sysfs hooks */
data->class_dev = hwmon_device_register(&new_client->dev);
if (IS_ERR(data->class_dev)) {
err = PTR_ERR(data->class_dev);
goto exit_detach;
}
device_create_file(&new_client->dev, &dev_attr_temp1_input);
device_create_file(&new_client->dev, &dev_attr_temp1_max);
return 0;
exit_detach:
i2c_detach_client(new_client);
exit_free:
kfree(data);
exit:
@ -252,15 +261,15 @@ static int w83l785ts_detect(struct i2c_adapter *adapter, int address, int kind)
static int w83l785ts_detach_client(struct i2c_client *client)
{
struct w83l785ts_data *data = i2c_get_clientdata(client);
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
return err;
}
hwmon_device_unregister(data->class_dev);
kfree(i2c_get_clientdata(client));
if ((err = i2c_detach_client(client)))
return err;
kfree(data);
return 0;
}

View file

@ -4,12 +4,8 @@
obj-$(CONFIG_I2C) += i2c-core.o
obj-$(CONFIG_I2C_CHARDEV) += i2c-dev.o
obj-$(CONFIG_I2C_SENSOR) += i2c-sensor.o
obj-y += busses/ chips/ algos/
i2c-sensor-objs := i2c-sensor-detect.o i2c-sensor-vid.o
ifeq ($(CONFIG_I2C_DEBUG_CORE),y)
EXTRA_CFLAGS += -DDEBUG
endif

View file

@ -519,8 +519,6 @@ static u32 bit_func(struct i2c_adapter *adap)
/* -----exported algorithm data: ------------------------------------- */
static struct i2c_algorithm i2c_bit_algo = {
.name = "Bit-shift algorithm",
.id = I2C_ALGO_BIT,
.master_xfer = bit_xfer,
.functionality = bit_func,
};
@ -541,8 +539,6 @@ int i2c_bit_add_bus(struct i2c_adapter *adap)
DEB2(dev_dbg(&adap->dev, "hw routines registered.\n"));
/* register new adapter to i2c module... */
adap->id |= i2c_bit_algo.id;
adap->algo = &i2c_bit_algo;
adap->timeout = 100; /* default values, should */

View file

@ -713,8 +713,6 @@ static u32 iic_func(struct i2c_adapter *adap)
/* -----exported algorithm data: ------------------------------------- */
static struct i2c_algorithm iic_algo = {
.name = "ITE IIC algorithm",
.id = I2C_ALGO_IIC,
.master_xfer = iic_xfer,
.algo_control = algo_control, /* ioctl */
.functionality = iic_func,
@ -738,8 +736,6 @@ int i2c_iic_add_bus(struct i2c_adapter *adap)
adap->name));
/* register new adapter to i2c module... */
adap->id |= iic_algo.id;
adap->algo = &iic_algo;
adap->timeout = 100; /* default values, should */

View file

@ -187,12 +187,14 @@ static int pca_xfer(struct i2c_adapter *i2c_adap,
int numbytes = 0;
int state;
int ret;
int timeout = 100;
state = pca_status(adap);
if ( state != 0xF8 ) {
dev_dbg(&i2c_adap->dev, "bus is not idle. status is %#04x\n", state );
/* FIXME: what to do. Force stop ? */
return -EREMOTEIO;
while ((state = pca_status(adap)) != 0xf8 && timeout--) {
msleep(10);
}
if (state != 0xf8) {
dev_dbg(&i2c_adap->dev, "bus is not idle. status is %#04x\n", state);
return -EIO;
}
DEB1("{{{ XFER %d messages\n", num);
@ -354,8 +356,6 @@ static int pca_init(struct i2c_algo_pca_data *adap)
}
static struct i2c_algorithm pca_algo = {
.name = "PCA9564 algorithm",
.id = I2C_ALGO_PCA,
.master_xfer = pca_xfer,
.functionality = pca_func,
};
@ -369,8 +369,6 @@ int i2c_pca_add_bus(struct i2c_adapter *adap)
int rval;
/* register new adapter to i2c module... */
adap->id |= pca_algo.id;
adap->algo = &pca_algo;
adap->timeout = 100; /* default values, should */

View file

@ -459,8 +459,6 @@ static u32 pcf_func(struct i2c_adapter *adap)
/* -----exported algorithm data: ------------------------------------- */
static struct i2c_algorithm pcf_algo = {
.name = "PCF8584 algorithm",
.id = I2C_ALGO_PCF,
.master_xfer = pcf_xfer,
.functionality = pcf_func,
};
@ -476,8 +474,6 @@ int i2c_pcf_add_bus(struct i2c_adapter *adap)
DEB2(dev_dbg(&adap->dev, "hw routines registered.\n"));
/* register new adapter to i2c module... */
adap->id |= pcf_algo.id;
adap->algo = &pcf_algo;
adap->timeout = 100; /* default values, should */

View file

@ -149,7 +149,7 @@ static int sgi_xfer(struct i2c_adapter *i2c_adap, struct i2c_msg *msgs,
err = i2c_write(adap, p->buf, p->len);
}
return err;
return (err < 0) ? err : i;
}
static u32 sgi_func(struct i2c_adapter *adap)
@ -158,8 +158,6 @@ static u32 sgi_func(struct i2c_adapter *adap)
}
static struct i2c_algorithm sgi_algo = {
.name = "SGI algorithm",
.id = I2C_ALGO_SGI,
.master_xfer = sgi_xfer,
.functionality = sgi_func,
};
@ -169,7 +167,6 @@ static struct i2c_algorithm sgi_algo = {
*/
int i2c_sgi_add_bus(struct i2c_adapter *adap)
{
adap->id |= sgi_algo.id;
adap->algo = &sgi_algo;
return i2c_add_adapter(adap);

View file

@ -135,8 +135,6 @@ static u32 bit_func(struct i2c_adapter *adap)
/* -----exported algorithm data: ------------------------------------- */
static struct i2c_algorithm i2c_sibyte_algo = {
.name = "SiByte algorithm",
.id = I2C_ALGO_SIBYTE,
.smbus_xfer = smbus_xfer,
.algo_control = algo_control, /* ioctl */
.functionality = bit_func,
@ -151,8 +149,6 @@ int i2c_sibyte_add_bus(struct i2c_adapter *i2c_adap, int speed)
struct i2c_algo_sibyte_data *adap = i2c_adap->algo_data;
/* register new adapter to i2c module... */
i2c_adap->id |= i2c_sibyte_algo.id;
i2c_adap->algo = &i2c_sibyte_algo;
/* Set the frequency to 100 kHz */

View file

@ -182,14 +182,8 @@ config I2C_IOP3XX
will be called i2c-iop3xx.
config I2C_ISA
tristate "ISA Bus support"
tristate
depends on I2C
help
If you say yes to this option, support will be included for i2c
interfaces that are on the ISA bus.
This driver can also be built as a module. If so, the module
will be called i2c-isa.
config I2C_ITE
tristate "ITE I2C Adapter"

View file

@ -472,8 +472,6 @@ static u32 ali1535_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-i2c SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = ali1535_access,
.functionality = ali1535_func,
};

View file

@ -366,8 +366,6 @@ static void ali1563_shutdown(struct pci_dev *dev)
}
static struct i2c_algorithm ali1563_algorithm = {
.name = "Non-i2c SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = ali1563_access,
.functionality = ali1563_func,
};

View file

@ -462,8 +462,6 @@ static u32 ali15x3_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = ali15x3_access,
.functionality = ali15x3_func,
};

View file

@ -295,8 +295,6 @@ static u32 amd756_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = amd756_access,
.functionality = amd756_func,
};

View file

@ -323,8 +323,6 @@ static u32 amd8111_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus 2.0 adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = amd8111_access,
.functionality = amd8111_func,
};

View file

@ -283,8 +283,6 @@ au1550_func(struct i2c_adapter *adap)
}
static struct i2c_algorithm au1550_algo = {
.name = "Au1550 algorithm",
.id = I2C_ALGO_AU1550,
.master_xfer = au1550_xfer,
.functionality = au1550_func,
};

View file

@ -535,8 +535,6 @@ static u32 i801_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = i801_access,
.functionality = i801_func,
};

View file

@ -627,8 +627,6 @@ static u32 iic_func(struct i2c_adapter *adap)
}
static struct i2c_algorithm iic_algo = {
.name = "IBM IIC algorithm",
.id = I2C_ALGO_OCP,
.master_xfer = iic_xfer,
.functionality = iic_func
};
@ -727,7 +725,7 @@ static int __devinit iic_probe(struct ocp_device *ocp){
adap = &dev->adap;
strcpy(adap->name, "IBM IIC");
i2c_set_adapdata(adap, dev);
adap->id = I2C_HW_OCP | iic_algo.id;
adap->id = I2C_HW_OCP;
adap->algo = &iic_algo;
adap->client_register = NULL;
adap->client_unregister = NULL;

View file

@ -399,8 +399,6 @@ iop3xx_i2c_func(struct i2c_adapter *adap)
}
static struct i2c_algorithm iop3xx_i2c_algo = {
.name = "IOP3xx I2C algorithm",
.id = I2C_ALGO_IOP3XX,
.master_xfer = iop3xx_i2c_master_xfer,
.algo_control = iop3xx_i2c_algo_control,
.functionality = iop3xx_i2c_func,

View file

@ -1,6 +1,8 @@
/*
i2c-isa.c - Part of lm_sensors, Linux kernel modules for hardware
monitoring
i2c-isa.c - an i2c-core-like thing for ISA hardware monitoring chips
Copyright (C) 2005 Jean Delvare <khali@linux-fr.org>
Based on the i2c-isa pseudo-adapter from the lm_sensors project
Copyright (c) 1998, 1999 Frodo Looijaard <frodol@dds.nl>
This program is free software; you can redistribute it and/or modify
@ -18,30 +20,36 @@
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* This implements an i2c algorithm/adapter for ISA bus. Not that this is
on first sight very useful; almost no functionality is preserved.
Except that it makes writing drivers for chips which can be on both
the SMBus and the ISA bus very much easier. See lm78.c for an example
of this. */
/* This implements an i2c-core-like thing for ISA hardware monitoring
chips. Such chips are linked to the i2c subsystem for historical
reasons (because the early ISA hardware monitoring chips such as the
LM78 had both an I2C and an ISA interface). They used to be
registered with the main i2c-core, but as a first step in the
direction of a clean separation between I2C and ISA chip drivers,
we now have this separate core for ISA ones. It is significantly
more simple than the real one, of course, because we don't have to
handle multiple busses: there is only one (fake) ISA adapter.
It is worth noting that we still rely on i2c-core for some things
at the moment - but hopefully this won't last. */
#include <linux/init.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/i2c.h>
#include <linux/i2c-isa.h>
static u32 isa_func(struct i2c_adapter *adapter);
/* This is the actual algorithm we define */
static struct i2c_algorithm isa_algorithm = {
.name = "ISA bus algorithm",
.id = I2C_ALGO_ISA,
.functionality = isa_func,
};
/* There can only be one... */
static struct i2c_adapter isa_adapter = {
.owner = THIS_MODULE,
.id = I2C_HW_ISA,
.class = I2C_CLASS_HWMON,
.algo = &isa_algorithm,
.name = "ISA main adapter",
@ -53,17 +61,146 @@ static u32 isa_func(struct i2c_adapter *adapter)
return 0;
}
/* Copied from i2c-core */
static ssize_t show_adapter_name(struct device *dev,
struct device_attribute *attr, char *buf)
{
struct i2c_adapter *adap = dev_to_i2c_adapter(dev);
return sprintf(buf, "%s\n", adap->name);
}
static DEVICE_ATTR(name, S_IRUGO, show_adapter_name, NULL);
static int i2c_isa_device_probe(struct device *dev)
{
return -ENODEV;
}
static int i2c_isa_device_remove(struct device *dev)
{
return 0;
}
/* We implement an interface which resembles i2c_{add,del}_driver,
but for i2c-isa drivers. We don't have to remember and handle lists
of drivers and adapters so this is much more simple, of course. */
int i2c_isa_add_driver(struct i2c_driver *driver)
{
int res;
/* Add the driver to the list of i2c drivers in the driver core */
driver->driver.name = driver->name;
driver->driver.bus = &i2c_bus_type;
driver->driver.probe = i2c_isa_device_probe;
driver->driver.remove = i2c_isa_device_remove;
res = driver_register(&driver->driver);
if (res)
return res;
dev_dbg(&isa_adapter.dev, "Driver %s registered\n", driver->name);
/* Now look for clients */
driver->attach_adapter(&isa_adapter);
return 0;
}
int i2c_isa_del_driver(struct i2c_driver *driver)
{
struct list_head *item, *_n;
struct i2c_client *client;
int res;
/* Detach all clients belonging to this one driver */
list_for_each_safe(item, _n, &isa_adapter.clients) {
client = list_entry(item, struct i2c_client, list);
if (client->driver != driver)
continue;
dev_dbg(&isa_adapter.dev, "Detaching client %s at 0x%x\n",
client->name, client->addr);
if ((res = driver->detach_client(client))) {
dev_err(&isa_adapter.dev, "Failed, driver "
"%s not unregistered!\n",
driver->name);
return res;
}
}
/* Get the driver off the core list */
driver_unregister(&driver->driver);
dev_dbg(&isa_adapter.dev, "Driver %s unregistered\n", driver->name);
return 0;
}
static int __init i2c_isa_init(void)
{
return i2c_add_adapter(&isa_adapter);
init_MUTEX(&isa_adapter.clist_lock);
INIT_LIST_HEAD(&isa_adapter.clients);
isa_adapter.nr = ANY_I2C_ISA_BUS;
isa_adapter.dev.parent = &platform_bus;
sprintf(isa_adapter.dev.bus_id, "i2c-%d", isa_adapter.nr);
isa_adapter.dev.driver = &i2c_adapter_driver;
isa_adapter.dev.release = &i2c_adapter_dev_release;
device_register(&isa_adapter.dev);
device_create_file(&isa_adapter.dev, &dev_attr_name);
/* Add this adapter to the i2c_adapter class */
memset(&isa_adapter.class_dev, 0x00, sizeof(struct class_device));
isa_adapter.class_dev.dev = &isa_adapter.dev;
isa_adapter.class_dev.class = &i2c_adapter_class;
strlcpy(isa_adapter.class_dev.class_id, isa_adapter.dev.bus_id,
BUS_ID_SIZE);
class_device_register(&isa_adapter.class_dev);
dev_dbg(&isa_adapter.dev, "%s registered\n", isa_adapter.name);
return 0;
}
static void __exit i2c_isa_exit(void)
{
i2c_del_adapter(&isa_adapter);
#ifdef DEBUG
struct list_head *item, *_n;
struct i2c_client *client = NULL;
#endif
/* There should be no more active client */
#ifdef DEBUG
dev_dbg(&isa_adapter.dev, "Looking for clients\n");
list_for_each_safe(item, _n, &isa_adapter.clients) {
client = list_entry(item, struct i2c_client, list);
dev_err(&isa_adapter.dev, "Driver %s still has an active "
"ISA client at 0x%x\n", client->driver->name,
client->addr);
}
if (client != NULL)
return;
#endif
/* Clean up the sysfs representation */
dev_dbg(&isa_adapter.dev, "Unregistering from sysfs\n");
init_completion(&isa_adapter.dev_released);
init_completion(&isa_adapter.class_dev_released);
class_device_unregister(&isa_adapter.class_dev);
device_remove_file(&isa_adapter.dev, &dev_attr_name);
device_unregister(&isa_adapter.dev);
/* Wait for sysfs to drop all references */
dev_dbg(&isa_adapter.dev, "Waiting for sysfs completion\n");
wait_for_completion(&isa_adapter.dev_released);
wait_for_completion(&isa_adapter.class_dev_released);
dev_dbg(&isa_adapter.dev, "%s unregistered\n", isa_adapter.name);
}
MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>");
EXPORT_SYMBOL(i2c_isa_add_driver);
EXPORT_SYMBOL(i2c_isa_del_driver);
MODULE_AUTHOR("Jean Delvare <khali@linux-fr.org>");
MODULE_DESCRIPTION("ISA bus access through i2c");
MODULE_LICENSE("GPL");

View file

@ -87,12 +87,9 @@ static const char *__kw_state_names[] = {
};
#endif /* DEBUG */
static int probe;
MODULE_AUTHOR("Benjamin Herrenschmidt <benh@kernel.crashing.org>");
MODULE_DESCRIPTION("I2C driver for Apple's Keywest");
MODULE_LICENSE("GPL");
module_param(probe, bool, 0);
#ifdef POLLED_MODE
/* Don't schedule, the g5 fan controller is too
@ -498,8 +495,6 @@ keywest_func(struct i2c_adapter * adapter)
/* For now, we only handle combined mode (smbus) */
static struct i2c_algorithm keywest_algorithm = {
.name = "Keywest i2c",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = keywest_smbus_xfer,
.master_xfer = keywest_xfer,
.functionality = keywest_func,
@ -621,7 +616,6 @@ create_iface(struct device_node *np, struct device *dev)
sprintf(chan->adapter.name, "%s %d", np->parent->name, i);
chan->iface = iface;
chan->chan_no = i;
chan->adapter.id = I2C_ALGO_SMBUS;
chan->adapter.algo = &keywest_algorithm;
chan->adapter.algo_data = NULL;
chan->adapter.client_register = NULL;
@ -635,15 +629,6 @@ create_iface(struct device_node *np, struct device *dev)
chan->adapter.name);
i2c_set_adapdata(&chan->adapter, NULL);
}
if (probe) {
printk("Probe: ");
for (addr = 0x00; addr <= 0x7f; addr++) {
if (i2c_smbus_xfer(&chan->adapter,addr,
0,0,0,I2C_SMBUS_QUICK,NULL) >= 0)
printk("%02x ", addr);
}
printk("\n");
}
}
printk(KERN_INFO "Found KeyWest i2c on \"%s\", %d channel%s, stepping: %d bits\n",

View file

@ -272,8 +272,6 @@ static u32 mpc_functionality(struct i2c_adapter *adap)
}
static struct i2c_algorithm mpc_algo = {
.name = "MPC algorithm",
.id = I2C_ALGO_MPC107,
.master_xfer = mpc_xfer,
.functionality = mpc_functionality,
};
@ -281,7 +279,7 @@ static struct i2c_algorithm mpc_algo = {
static struct i2c_adapter mpc_ops = {
.owner = THIS_MODULE,
.name = "MPC adapter",
.id = I2C_ALGO_MPC107 | I2C_HW_MPC107,
.id = I2C_HW_MPC107,
.algo = &mpc_algo,
.class = I2C_CLASS_HWMON,
.timeout = 1,

View file

@ -423,18 +423,16 @@ static int
mv64xxx_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msgs[], int num)
{
struct mv64xxx_i2c_data *drv_data = i2c_get_adapdata(adap);
int i, rc = 0;
int i, rc;
for (i=0; i<num; i++)
if ((rc = mv64xxx_i2c_execute_msg(drv_data, &msgs[i])) != 0)
break;
if ((rc = mv64xxx_i2c_execute_msg(drv_data, &msgs[i])) < 0)
return rc;
return rc;
return num;
}
static struct i2c_algorithm mv64xxx_i2c_algo = {
.name = MV64XXX_I2C_CTLR_NAME " algorithm",
.id = I2C_ALGO_MV64XXX,
.master_xfer = mv64xxx_i2c_xfer,
.functionality = mv64xxx_i2c_functionality,
};
@ -523,7 +521,7 @@ mv64xxx_i2c_probe(struct device *dev)
drv_data->freq_m = pdata->freq_m;
drv_data->freq_n = pdata->freq_n;
drv_data->irq = platform_get_irq(pd, 0);
drv_data->adapter.id = I2C_ALGO_MV64XXX | I2C_HW_MV64XXX;
drv_data->adapter.id = I2C_HW_MV64XXX;
drv_data->adapter.algo = &mv64xxx_i2c_algo;
drv_data->adapter.owner = THIS_MODULE;
drv_data->adapter.class = I2C_CLASS_HWMON;

View file

@ -110,8 +110,6 @@ static u32 nforce2_func(struct i2c_adapter *adapter);
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = nforce2_access,
.functionality = nforce2_func,
};
@ -131,7 +129,6 @@ static s32 nforce2_access(struct i2c_adapter * adap, u16 addr,
struct nforce2_smbus *smbus = adap->algo_data;
unsigned char protocol, pec, temp;
unsigned char len = 0; /* to keep the compiler quiet */
int timeout = 0;
int i;
protocol = (read_write == I2C_SMBUS_READ) ? NVIDIA_SMB_PRTCL_READ :
@ -191,29 +188,10 @@ static s32 nforce2_access(struct i2c_adapter * adap, u16 addr,
case I2C_SMBUS_PROC_CALL:
dev_err(&adap->dev, "I2C_SMBUS_PROC_CALL not supported!\n");
return -1;
/*
outb_p(command, NVIDIA_SMB_CMD);
outb_p(data->word, NVIDIA_SMB_DATA);
outb_p(data->word >> 8, NVIDIA_SMB_DATA + 1);
protocol = NVIDIA_SMB_PRTCL_PROC_CALL | pec;
read_write = I2C_SMBUS_READ;
break;
*/
case I2C_SMBUS_BLOCK_PROC_CALL:
dev_err(&adap->dev, "I2C_SMBUS_BLOCK_PROC_CALL not supported!\n");
return -1;
/*
protocol |= pec;
len = min_t(u8, data->block[0], 31);
outb_p(command, NVIDIA_SMB_CMD);
outb_p(len, NVIDIA_SMB_BCNT);
for (i = 0; i < len; i++)
outb_p(data->block[i + 1], NVIDIA_SMB_DATA + i);
protocol = NVIDIA_SMB_PRTCL_BLOCK_PROC_CALL | pec;
read_write = I2C_SMBUS_READ;
break;
*/
case I2C_SMBUS_WORD_DATA_PEC:
case I2C_SMBUS_BLOCK_DATA_PEC:
@ -232,12 +210,6 @@ static s32 nforce2_access(struct i2c_adapter * adap, u16 addr,
temp = inb_p(NVIDIA_SMB_STS);
#if 0
do {
i2c_do_pause(1);
temp = inb_p(NVIDIA_SMB_STS);
} while (((temp & NVIDIA_SMB_STS_DONE) == 0) && (timeout++ < MAX_TIMEOUT));
#endif
if (~temp & NVIDIA_SMB_STS_DONE) {
udelay(500);
temp = inb_p(NVIDIA_SMB_STS);
@ -247,9 +219,10 @@ static s32 nforce2_access(struct i2c_adapter * adap, u16 addr,
temp = inb_p(NVIDIA_SMB_STS);
}
if ((timeout >= MAX_TIMEOUT) || (~temp & NVIDIA_SMB_STS_DONE)
|| (temp & NVIDIA_SMB_STS_STATUS))
if ((~temp & NVIDIA_SMB_STS_DONE) || (temp & NVIDIA_SMB_STS_STATUS)) {
dev_dbg(&adap->dev, "SMBus Timeout! (0x%02x)\n", temp);
return -1;
}
if (read_write == I2C_SMBUS_WRITE)
return 0;

View file

@ -399,8 +399,6 @@ static u32 piix4_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = piix4_access,
.functionality = piix4_func,
};

View file

@ -568,7 +568,6 @@ static u32 s3c24xx_i2c_func(struct i2c_adapter *adap)
/* i2c bus registration info */
static struct i2c_algorithm s3c24xx_i2c_algorithm = {
.name = "S3C2410-I2C-Algorithm",
.master_xfer = s3c24xx_i2c_xfer,
.functionality = s3c24xx_i2c_func,
};

View file

@ -357,8 +357,6 @@ static u32 sis5595_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = sis5595_access,
.functionality = sis5595_func,
};

View file

@ -448,8 +448,6 @@ static int sis630_setup(struct pci_dev *sis630_dev)
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = sis630_access,
.functionality = sis630_func,
};

View file

@ -249,8 +249,6 @@ static u32 sis96x_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = sis96x_access,
.functionality = sis96x_func,
};

View file

@ -109,8 +109,6 @@ static u32 stub_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.functionality = stub_func,
.smbus_xfer = stub_xfer,
};

View file

@ -286,8 +286,6 @@ static u32 vt596_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm smbus_algorithm = {
.name = "Non-I2C SMBus adapter",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = vt596_access,
.functionality = vt596_func,
};

View file

@ -395,8 +395,6 @@ static u32 scx200_acb_func(struct i2c_adapter *adapter)
/* For now, we only handle combined mode (smbus) */
static struct i2c_algorithm scx200_acb_algorithm = {
.name = "NatSemi SCx200 ACCESS.bus",
.id = I2C_ALGO_SMBUS,
.smbus_xfer = scx200_acb_smbus_xfer,
.functionality = scx200_acb_func,
};
@ -456,7 +454,7 @@ static int __init scx200_acb_create(int base, int index)
i2c_set_adapdata(adapter, iface);
snprintf(adapter->name, I2C_NAME_SIZE, "SCx200 ACB%d", index);
adapter->owner = THIS_MODULE;
adapter->id = I2C_ALGO_SMBUS;
adapter->id = I2C_HW_SMBUS_SCX200;
adapter->algo = &scx200_acb_algorithm;
adapter->class = I2C_CLASS_HWMON;

View file

@ -2,17 +2,12 @@
# Miscellaneous I2C chip drivers configuration
#
config I2C_SENSOR
tristate
default n
menu "Miscellaneous I2C Chip support"
depends on I2C
config SENSORS_DS1337
tristate "Dallas Semiconductor DS1337 and DS1339 Real Time Clock"
depends on I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Dallas Semiconductor
DS1337 and DS1339 real-time clock chips.
@ -23,7 +18,6 @@ config SENSORS_DS1337
config SENSORS_DS1374
tristate "Maxim/Dallas Semiconductor DS1374 Real Time Clock"
depends on I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Dallas Semiconductor
DS1374 real-time clock chips.
@ -34,7 +28,6 @@ config SENSORS_DS1374
config SENSORS_EEPROM
tristate "EEPROM reader"
depends on I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get read-only access to the EEPROM data
available on modern memory DIMMs and Sony Vaio laptops. Such
@ -46,7 +39,6 @@ config SENSORS_EEPROM
config SENSORS_PCF8574
tristate "Philips PCF8574 and PCF8574A"
depends on I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Philips PCF8574 and
PCF8574A chips.
@ -67,7 +59,6 @@ config SENSORS_PCA9539
config SENSORS_PCF8591
tristate "Philips PCF8591"
depends on I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for Philips PCF8591 chips.
@ -77,7 +68,6 @@ config SENSORS_PCF8591
config SENSORS_RTC8564
tristate "Epson 8564 RTC chip"
depends on I2C && EXPERIMENTAL
select I2C_SENSOR
help
If you say yes here you get support for the Epson 8564 RTC chip.

View file

@ -17,7 +17,6 @@
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <linux/string.h>
#include <linux/rtc.h> /* get the user-level API */
#include <linux/bcd.h>
@ -39,9 +38,8 @@
* Functions declaration
*/
static unsigned short normal_i2c[] = { 0x68, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
SENSORS_INSMOD_1(ds1337);
I2C_CLIENT_INSMOD_1(ds1337);
static int ds1337_attach_adapter(struct i2c_adapter *adapter);
static int ds1337_detect(struct i2c_adapter *adapter, int address, int kind);
@ -227,7 +225,7 @@ int ds1337_do_command(int bus, int cmd, void *arg)
static int ds1337_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, ds1337_detect);
return i2c_probe(adapter, &addr_data, ds1337_detect);
}
/*
@ -354,11 +352,8 @@ static int ds1337_detach_client(struct i2c_client *client)
int err;
struct ds1337_data *data = i2c_get_clientdata(client);
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed, "
"client not detached.\n");
if ((err = i2c_detach_client(client)))
return err;
}
list_del(&data->list);
kfree(data);

View file

@ -53,7 +53,6 @@ static struct i2c_client_address_data addr_data = {
.normal_i2c = normal_addr,
.probe = ignore,
.ignore = ignore,
.force = ignore,
};
static ulong ds1374_read_rtc(void)
@ -166,7 +165,7 @@ static void ds1374_set_tlet(ulong arg)
"can't confirm time set from rtc chip\n");
}
ulong new_time;
static ulong new_time;
DECLARE_TASKLET_DISABLED(ds1374_tasklet, ds1374_set_tlet, (ulong) & new_time);

View file

@ -33,15 +33,13 @@
#include <linux/sched.h>
#include <linux/jiffies.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x50, 0x51, 0x52, 0x53, 0x54,
0x55, 0x56, 0x57, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(eeprom);
I2C_CLIENT_INSMOD_1(eeprom);
/* Size of EEPROM in bytes */
@ -153,21 +151,16 @@ static struct bin_attribute eeprom_attr = {
static int eeprom_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, eeprom_detect);
return i2c_probe(adapter, &addr_data, eeprom_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
int eeprom_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
struct eeprom_data *data;
int err = 0;
/* prevent 24RF08 corruption */
if (kind < 0)
i2c_smbus_xfer(adapter, address, 0, 0, 0,
I2C_SMBUS_QUICK, NULL);
/* There are three ways we can read the EEPROM data:
(1) I2C block reads (faster, but unsupported by most adapters)
(2) Consecutive byte reads (100% overhead)
@ -231,10 +224,8 @@ static int eeprom_detach_client(struct i2c_client *client)
int err;
err = i2c_detach_client(client);
if (err) {
dev_err(&client->dev, "Client deregistration failed, client not detached.\n");
if (err)
return err;
}
kfree(i2c_get_clientdata(client));

View file

@ -42,7 +42,6 @@ static struct i2c_client_address_data addr_data = {
.normal_i2c = normal_addr,
.probe = ignore,
.ignore = ignore,
.force = ignore,
};
ulong
@ -145,7 +144,7 @@ m41t00_set_tlet(ulong arg)
return;
}
ulong new_time;
static ulong new_time;
DECLARE_TASKLET_DISABLED(m41t00_tasklet, m41t00_set_tlet, (ulong)&new_time);

View file

@ -5,97 +5,60 @@
Based on i2c/chips/eeprom.c
The MAX6875 has two EEPROM sections: config and user.
At reset, the config EEPROM is read into the registers.
The MAX6875 has a bank of registers and two banks of EEPROM.
Address ranges are defined as follows:
* 0x0000 - 0x0046 = configuration registers
* 0x8000 - 0x8046 = configuration EEPROM
* 0x8100 - 0x82FF = user EEPROM
This driver make 3 binary files available in sysfs:
reg_config - direct access to the registers
eeprom_config - acesses configuration eeprom space
eeprom_user - free for application use
This driver makes the user EEPROM available for read.
In our application, we put device serial & model numbers in user eeprom.
The registers & config EEPROM should be accessed via i2c-dev.
Notes:
1) The datasheet says that register 0x44 / EEPROM 0x8044 should NOT
be overwritten, so the driver explicitly prevents that.
2) It's a good idea to keep the config (0x45) locked in config EEPROM.
You can temporarily enable config writes by changing register 0x45.
The MAX6875 ignores the lowest address bit, so each chip responds to
two addresses - 0x50/0x51 and 0x52/0x53.
Note that the MAX6875 uses i2c_smbus_write_byte_data() to set the read
address, so this driver is destructive if loaded for the wrong EEPROM chip.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
*/
#include <linux/config.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/sched.h>
#include <linux/delay.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
#include <asm/semaphore.h>
/* Addresses to scan */
/* No address scanned by default, as this could corrupt standard EEPROMS. */
/* Do not scan - the MAX6875 access method will write to some EEPROM chips */
static unsigned short normal_i2c[] = {I2C_CLIENT_END};
static unsigned int normal_isa[] = {I2C_CLIENT_ISA_END};
/* Insmod parameters */
SENSORS_INSMOD_1(max6875);
/* this param will prevent 'accidental' writes to the eeprom */
static int allow_write = 0;
module_param(allow_write, int, 0);
MODULE_PARM_DESC(allow_write,
"Enable write access:\n"
"*0: Read only\n"
" 1: Read/Write access");
I2C_CLIENT_INSMOD_1(max6875);
/* The MAX6875 can only read/write 16 bytes at a time */
#define SLICE_SIZE 16
#define SLICE_BITS 4
/* CONFIG EEPROM is at addresses 0x8000 - 0x8045, registers are at 0 - 0x45 */
#define CONFIG_EEPROM_BASE 0x8000
#define CONFIG_EEPROM_SIZE 0x0046
#define CONFIG_EEPROM_SLICES 5
/* USER EEPROM is at addresses 0x8100 - 0x82FF */
#define USER_EEPROM_BASE 0x8100
#define USER_EEPROM_SIZE 0x0200
#define USER_EEPROM_SLICES 32
/* MAX6875 commands */
#define MAX6875_CMD_BLOCK_WRITE 0x83
#define MAX6875_CMD_BLOCK_READ 0x84
#define MAX6875_CMD_REBOOT 0x88
enum max6875_area_type {
max6875_register_config=0,
max6875_eeprom_config,
max6875_eeprom_user,
max6857_max
};
struct eeprom_block {
enum max6875_area_type type;
u8 slices;
u32 size;
u32 valid;
u32 base;
unsigned long *updated;
u8 *data;
};
#define MAX6875_CMD_BLK_READ 0x84
/* Each client has this additional data */
struct max6875_data {
struct i2c_client client;
struct semaphore update_lock;
struct eeprom_block blocks[max6857_max];
/* the above structs point into the arrays below */
u8 data[USER_EEPROM_SIZE + (CONFIG_EEPROM_SIZE*2)];
unsigned long last_updated[USER_EEPROM_SLICES + (CONFIG_EEPROM_SLICES*2)];
u32 valid;
u8 data[USER_EEPROM_SIZE];
unsigned long last_updated[USER_EEPROM_SLICES];
};
static int max6875_attach_adapter(struct i2c_adapter *adapter);
@ -111,337 +74,160 @@ static struct i2c_driver max6875_driver = {
.detach_client = max6875_detach_client,
};
static int max6875_update_slice(struct i2c_client *client,
struct eeprom_block *blk,
int slice)
static void max6875_update_slice(struct i2c_client *client, int slice)
{
struct max6875_data *data = i2c_get_clientdata(client);
int i, j, addr, count;
u8 rdbuf[SLICE_SIZE];
int retval = 0;
int i, j, addr;
u8 *buf;
if (slice >= blk->slices)
return -1;
if (slice >= USER_EEPROM_SLICES)
return;
down(&data->update_lock);
if (!(blk->valid & (1 << slice)) ||
(jiffies - blk->updated[slice] > 300 * HZ) ||
(jiffies < blk->updated[slice])) {
dev_dbg(&client->dev, "Starting eeprom update, slice %u, base %u\n",
slice, blk->base);
buf = &data->data[slice << SLICE_BITS];
addr = blk->base + (slice << SLICE_BITS);
count = blk->size - (slice << SLICE_BITS);
if (count > SLICE_SIZE) {
count = SLICE_SIZE;
if (!(data->valid & (1 << slice)) ||
time_after(jiffies, data->last_updated[slice])) {
dev_dbg(&client->dev, "Starting update of slice %u\n", slice);
data->valid &= ~(1 << slice);
addr = USER_EEPROM_BASE + (slice << SLICE_BITS);
/* select the eeprom address */
if (i2c_smbus_write_byte_data(client, addr >> 8, addr & 0xFF)) {
dev_err(&client->dev, "address set failed\n");
goto exit_up;
}
/* Preset the read address */
if (addr < 0x100) {
/* select the register */
if (i2c_smbus_write_byte(client, addr & 0xFF)) {
dev_dbg(&client->dev, "max6875 register select has failed!\n");
retval = -1;
goto exit;
if (i2c_check_functionality(client->adapter,
I2C_FUNC_SMBUS_READ_I2C_BLOCK)) {
if (i2c_smbus_read_i2c_block_data(client,
MAX6875_CMD_BLK_READ,
buf) != SLICE_SIZE) {
goto exit_up;
}
} else {
/* select the eeprom */
if (i2c_smbus_write_byte_data(client, addr >> 8, addr & 0xFF)) {
dev_dbg(&client->dev, "max6875 address set has failed!\n");
retval = -1;
goto exit;
}
}
if (i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_READ_I2C_BLOCK)) {
if (i2c_smbus_read_i2c_block_data(client, MAX6875_CMD_BLOCK_READ,
rdbuf) != SLICE_SIZE)
{
retval = -1;
goto exit;
}
memcpy(&blk->data[slice << SLICE_BITS], rdbuf, count);
} else {
for (i = 0; i < count; i++) {
for (i = 0; i < SLICE_SIZE; i++) {
j = i2c_smbus_read_byte(client);
if (j < 0)
{
retval = -1;
goto exit;
if (j < 0) {
goto exit_up;
}
blk->data[(slice << SLICE_BITS) + i] = (u8) j;
buf[i] = j;
}
}
blk->updated[slice] = jiffies;
blk->valid |= (1 << slice);
data->last_updated[slice] = jiffies;
data->valid |= (1 << slice);
}
exit:
exit_up:
up(&data->update_lock);
return retval;
}
static ssize_t max6875_read(struct kobject *kobj, char *buf, loff_t off, size_t count,
enum max6875_area_type area_type)
static ssize_t max6875_read(struct kobject *kobj, char *buf, loff_t off,
size_t count)
{
struct i2c_client *client = to_i2c_client(container_of(kobj, struct device, kobj));
struct i2c_client *client = kobj_to_i2c_client(kobj);
struct max6875_data *data = i2c_get_clientdata(client);
struct eeprom_block *blk;
int slice;
int slice, max_slice;
blk = &data->blocks[area_type];
if (off > blk->size)
if (off > USER_EEPROM_SIZE)
return 0;
if (off + count > blk->size)
count = blk->size - off;
/* Only refresh slices which contain requested bytes */
for (slice = (off >> SLICE_BITS); slice <= ((off + count - 1) >> SLICE_BITS); slice++)
max6875_update_slice(client, blk, slice);
if (off + count > USER_EEPROM_SIZE)
count = USER_EEPROM_SIZE - off;
memcpy(buf, &blk->data[off], count);
/* refresh slices which contain requested bytes */
max_slice = (off + count - 1) >> SLICE_BITS;
for (slice = (off >> SLICE_BITS); slice <= max_slice; slice++)
max6875_update_slice(client, slice);
memcpy(buf, &data->data[off], count);
return count;
}
static ssize_t max6875_user_read(struct kobject *kobj, char *buf, loff_t off, size_t count)
{
return max6875_read(kobj, buf, off, count, max6875_eeprom_user);
}
static ssize_t max6875_config_read(struct kobject *kobj, char *buf, loff_t off, size_t count)
{
return max6875_read(kobj, buf, off, count, max6875_eeprom_config);
}
static ssize_t max6875_cfgreg_read(struct kobject *kobj, char *buf, loff_t off, size_t count)
{
return max6875_read(kobj, buf, off, count, max6875_register_config);
}
static ssize_t max6875_write(struct kobject *kobj, char *buf, loff_t off, size_t count,
enum max6875_area_type area_type)
{
struct i2c_client *client = to_i2c_client(container_of(kobj, struct device, kobj));
struct max6875_data *data = i2c_get_clientdata(client);
struct eeprom_block *blk;
int slice, addr, retval;
ssize_t sent = 0;
blk = &data->blocks[area_type];
if (off > blk->size)
return 0;
if ((off + count) > blk->size)
count = blk->size - off;
if (down_interruptible(&data->update_lock))
return -EAGAIN;
/* writing to a register is done with i2c_smbus_write_byte_data() */
if (blk->type == max6875_register_config) {
for (sent = 0; sent < count; sent++) {
addr = off + sent;
if (addr == 0x44)
continue;
retval = i2c_smbus_write_byte_data(client, addr, buf[sent]);
}
} else {
int cmd, val;
/* We are writing to EEPROM */
for (sent = 0; sent < count; sent++) {
addr = blk->base + off + sent;
cmd = addr >> 8;
val = (addr & 0xff) | (buf[sent] << 8); // reversed
if (addr == 0x8044)
continue;
retval = i2c_smbus_write_word_data(client, cmd, val);
if (retval) {
goto error_exit;
}
/* A write takes up to 11 ms */
msleep(11);
}
}
/* Invalidate the scratch buffer */
for (slice = (off >> SLICE_BITS); slice <= ((off + count - 1) >> SLICE_BITS); slice++)
blk->valid &= ~(1 << slice);
error_exit:
up(&data->update_lock);
return sent;
}
static ssize_t max6875_user_write(struct kobject *kobj, char *buf, loff_t off, size_t count)
{
return max6875_write(kobj, buf, off, count, max6875_eeprom_user);
}
static ssize_t max6875_config_write(struct kobject *kobj, char *buf, loff_t off, size_t count)
{
return max6875_write(kobj, buf, off, count, max6875_eeprom_config);
}
static ssize_t max6875_cfgreg_write(struct kobject *kobj, char *buf, loff_t off, size_t count)
{
return max6875_write(kobj, buf, off, count, max6875_register_config);
}
static struct bin_attribute user_eeprom_attr = {
.attr = {
.name = "eeprom_user",
.mode = S_IRUGO | S_IWUSR | S_IWGRP,
.name = "eeprom",
.mode = S_IRUGO,
.owner = THIS_MODULE,
},
.size = USER_EEPROM_SIZE,
.read = max6875_user_read,
.write = max6875_user_write,
};
static struct bin_attribute config_eeprom_attr = {
.attr = {
.name = "eeprom_config",
.mode = S_IRUGO | S_IWUSR,
.owner = THIS_MODULE,
},
.size = CONFIG_EEPROM_SIZE,
.read = max6875_config_read,
.write = max6875_config_write,
};
static struct bin_attribute config_register_attr = {
.attr = {
.name = "reg_config",
.mode = S_IRUGO | S_IWUSR,
.owner = THIS_MODULE,
},
.size = CONFIG_EEPROM_SIZE,
.read = max6875_cfgreg_read,
.write = max6875_cfgreg_write,
.size = USER_EEPROM_SIZE,
.read = max6875_read,
};
static int max6875_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, max6875_detect);
return i2c_probe(adapter, &addr_data, max6875_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
static int max6875_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
struct i2c_client *real_client;
struct i2c_client *fake_client;
struct max6875_data *data;
int err = 0;
/* Prevent 24RF08 corruption (in case of user error) */
if (kind < 0)
i2c_smbus_xfer(adapter, address, 0, 0, 0,
I2C_SMBUS_QUICK, NULL);
if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_WRITE_BYTE_DATA
| I2C_FUNC_SMBUS_READ_BYTE))
return 0;
/* There are three ways we can read the EEPROM data:
(1) I2C block reads (faster, but unsupported by most adapters)
(2) Consecutive byte reads (100% overhead)
(3) Regular byte data reads (200% overhead)
The third method is not implemented by this driver because all
known adapters support at least the second. */
if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_READ_BYTE_DATA |
I2C_FUNC_SMBUS_BYTE |
I2C_FUNC_SMBUS_WRITE_BYTE_DATA))
goto exit;
/* Only check even addresses */
if (address & 1)
return 0;
/* OK. For now, we presume we have a valid client. We now create the
client structure, even though we cannot fill it completely yet.
But it allows us to access eeprom_{read,write}_value. */
if (!(data = kmalloc(sizeof(struct max6875_data), GFP_KERNEL))) {
err = -ENOMEM;
goto exit;
}
if (!(data = kmalloc(sizeof(struct max6875_data), GFP_KERNEL)))
return -ENOMEM;
memset(data, 0, sizeof(struct max6875_data));
new_client = &data->client;
i2c_set_clientdata(new_client, data);
new_client->addr = address;
new_client->adapter = adapter;
new_client->driver = &max6875_driver;
new_client->flags = 0;
/* A fake client is created on the odd address */
if (!(fake_client = kmalloc(sizeof(struct i2c_client), GFP_KERNEL))) {
err = -ENOMEM;
goto exit_kfree1;
}
memset(fake_client, 0, sizeof(struct i2c_client));
/* Setup the user section */
data->blocks[max6875_eeprom_user].type = max6875_eeprom_user;
data->blocks[max6875_eeprom_user].slices = USER_EEPROM_SLICES;
data->blocks[max6875_eeprom_user].size = USER_EEPROM_SIZE;
data->blocks[max6875_eeprom_user].base = USER_EEPROM_BASE;
data->blocks[max6875_eeprom_user].data = data->data;
data->blocks[max6875_eeprom_user].updated = data->last_updated;
/* Setup the config section */
data->blocks[max6875_eeprom_config].type = max6875_eeprom_config;
data->blocks[max6875_eeprom_config].slices = CONFIG_EEPROM_SLICES;
data->blocks[max6875_eeprom_config].size = CONFIG_EEPROM_SIZE;
data->blocks[max6875_eeprom_config].base = CONFIG_EEPROM_BASE;
data->blocks[max6875_eeprom_config].data = &data->data[USER_EEPROM_SIZE];
data->blocks[max6875_eeprom_config].updated = &data->last_updated[USER_EEPROM_SLICES];
/* Setup the register section */
data->blocks[max6875_register_config].type = max6875_register_config;
data->blocks[max6875_register_config].slices = CONFIG_EEPROM_SLICES;
data->blocks[max6875_register_config].size = CONFIG_EEPROM_SIZE;
data->blocks[max6875_register_config].base = 0;
data->blocks[max6875_register_config].data = &data->data[USER_EEPROM_SIZE+CONFIG_EEPROM_SIZE];
data->blocks[max6875_register_config].updated = &data->last_updated[USER_EEPROM_SLICES+CONFIG_EEPROM_SLICES];
/* Init the data */
memset(data->data, 0xff, sizeof(data->data));
/* Fill in the remaining client fields */
strlcpy(new_client->name, "max6875", I2C_NAME_SIZE);
/* Init real i2c_client */
real_client = &data->client;
i2c_set_clientdata(real_client, data);
real_client->addr = address;
real_client->adapter = adapter;
real_client->driver = &max6875_driver;
real_client->flags = 0;
strlcpy(real_client->name, "max6875", I2C_NAME_SIZE);
init_MUTEX(&data->update_lock);
/* Verify that the chip is really what we think it is */
if ((max6875_update_slice(new_client, &data->blocks[max6875_eeprom_config], 4) < 0) ||
(max6875_update_slice(new_client, &data->blocks[max6875_register_config], 4) < 0))
goto exit_kfree;
/* Init fake client data */
/* set the client data to the i2c_client so that it will get freed */
i2c_set_clientdata(fake_client, fake_client);
fake_client->addr = address | 1;
fake_client->adapter = adapter;
fake_client->driver = &max6875_driver;
fake_client->flags = 0;
strlcpy(fake_client->name, "max6875 subclient", I2C_NAME_SIZE);
/* 0x41,0x42 must be zero and 0x40 must match in eeprom and registers */
if ((data->blocks[max6875_eeprom_config].data[0x41] != 0) ||
(data->blocks[max6875_eeprom_config].data[0x42] != 0) ||
(data->blocks[max6875_register_config].data[0x41] != 0) ||
(data->blocks[max6875_register_config].data[0x42] != 0) ||
(data->blocks[max6875_eeprom_config].data[0x40] !=
data->blocks[max6875_register_config].data[0x40]))
goto exit_kfree;
/* Prevent 24RF08 corruption (in case of user error) */
i2c_smbus_write_quick(real_client, 0);
/* Tell the I2C layer a new client has arrived */
if ((err = i2c_attach_client(new_client)))
goto exit_kfree;
if ((err = i2c_attach_client(real_client)) != 0)
goto exit_kfree2;
/* create the sysfs eeprom files with the correct permissions */
if (allow_write == 0) {
user_eeprom_attr.attr.mode &= ~S_IWUGO;
user_eeprom_attr.write = NULL;
config_eeprom_attr.attr.mode &= ~S_IWUGO;
config_eeprom_attr.write = NULL;
config_register_attr.attr.mode &= ~S_IWUGO;
config_register_attr.write = NULL;
}
sysfs_create_bin_file(&new_client->dev.kobj, &user_eeprom_attr);
sysfs_create_bin_file(&new_client->dev.kobj, &config_eeprom_attr);
sysfs_create_bin_file(&new_client->dev.kobj, &config_register_attr);
if ((err = i2c_attach_client(fake_client)) != 0)
goto exit_detach;
sysfs_create_bin_file(&real_client->dev.kobj, &user_eeprom_attr);
return 0;
exit_kfree:
exit_detach:
i2c_detach_client(real_client);
exit_kfree2:
kfree(fake_client);
exit_kfree1:
kfree(data);
exit:
return err;
}
@ -450,13 +236,9 @@ static int max6875_detach_client(struct i2c_client *client)
int err;
err = i2c_detach_client(client);
if (err) {
dev_err(&client->dev, "Client deregistration failed, client not detached.\n");
if (err)
return err;
}
kfree(i2c_get_clientdata(client));
return 0;
}

View file

@ -13,14 +13,12 @@
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/hwmon-sysfs.h>
#include <linux/i2c-sensor.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = {0x74, 0x75, 0x76, 0x77, I2C_CLIENT_END};
static unsigned int normal_isa[] = {I2C_CLIENT_ISA_END};
/* Insmod parameters */
SENSORS_INSMOD_1(pca9539);
I2C_CLIENT_INSMOD_1(pca9539);
enum pca9539_cmd
{
@ -109,10 +107,10 @@ static struct attribute_group pca9539_defattr_group = {
static int pca9539_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, pca9539_detect);
return i2c_probe(adapter, &addr_data, pca9539_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
static int pca9539_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
@ -164,10 +162,8 @@ static int pca9539_detach_client(struct i2c_client *client)
{
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev, "Client deregistration failed.\n");
if ((err = i2c_detach_client(client)))
return err;
}
kfree(i2c_get_clientdata(client));
return 0;

View file

@ -39,16 +39,14 @@
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_2(pcf8574, pcf8574a);
I2C_CLIENT_INSMOD_2(pcf8574, pcf8574a);
/* Initial values */
#define PCF8574_INIT 255 /* All outputs on (input mode) */
@ -113,10 +111,10 @@ static DEVICE_ATTR(write, S_IWUSR | S_IRUGO, show_write, set_write);
static int pcf8574_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, pcf8574_detect);
return i2c_probe(adapter, &addr_data, pcf8574_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
int pcf8574_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
@ -186,11 +184,8 @@ static int pcf8574_detach_client(struct i2c_client *client)
{
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
if ((err = i2c_detach_client(client)))
return err;
}
kfree(i2c_get_clientdata(client));
return 0;

View file

@ -24,15 +24,13 @@
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
/* Addresses to scan */
static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c,
0x4d, 0x4e, 0x4f, I2C_CLIENT_END };
static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END };
/* Insmod parameters */
SENSORS_INSMOD_1(pcf8591);
I2C_CLIENT_INSMOD_1(pcf8591);
static int input_mode;
module_param(input_mode, int, 0);
@ -164,10 +162,10 @@ static DEVICE_ATTR(out0_enable, S_IWUSR | S_IRUGO,
*/
static int pcf8591_attach_adapter(struct i2c_adapter *adapter)
{
return i2c_detect(adapter, &addr_data, pcf8591_detect);
return i2c_probe(adapter, &addr_data, pcf8591_detect);
}
/* This function is called by i2c_detect */
/* This function is called by i2c_probe */
int pcf8591_detect(struct i2c_adapter *adapter, int address, int kind)
{
struct i2c_client *new_client;
@ -241,11 +239,8 @@ static int pcf8591_detach_client(struct i2c_client *client)
{
int err;
if ((err = i2c_detach_client(client))) {
dev_err(&client->dev,
"Client deregistration failed, client not detached.\n");
if ((err = i2c_detach_client(client)))
return err;
}
kfree(i2c_get_clientdata(client));
return 0;

View file

@ -67,7 +67,6 @@ static struct i2c_client_address_data addr_data = {
.normal_i2c = normal_addr,
.probe = ignore,
.ignore = ignore,
.force = ignore,
};
static int rtc8564_read_mem(struct i2c_client *client, struct mem *mem);

View file

@ -61,7 +61,7 @@ static int i2c_bus_resume(struct device * dev)
return rc;
}
static struct bus_type i2c_bus_type = {
struct bus_type i2c_bus_type = {
.name = "i2c",
.match = i2c_device_match,
.suspend = i2c_bus_suspend,
@ -78,13 +78,13 @@ static int i2c_device_remove(struct device *dev)
return 0;
}
static void i2c_adapter_dev_release(struct device *dev)
void i2c_adapter_dev_release(struct device *dev)
{
struct i2c_adapter *adap = dev_to_i2c_adapter(dev);
complete(&adap->dev_released);
}
static struct device_driver i2c_adapter_driver = {
struct device_driver i2c_adapter_driver = {
.name = "i2c_adapter",
.bus = &i2c_bus_type,
.probe = i2c_device_probe,
@ -97,7 +97,7 @@ static void i2c_adapter_class_dev_release(struct class_device *dev)
complete(&adap->class_dev_released);
}
static struct class i2c_adapter_class = {
struct class i2c_adapter_class = {
.name = "i2c-adapter",
.release = &i2c_adapter_class_dev_release,
};
@ -188,6 +188,8 @@ int i2c_add_adapter(struct i2c_adapter *adap)
strlcpy(adap->class_dev.class_id, adap->dev.bus_id, BUS_ID_SIZE);
class_device_register(&adap->class_dev);
dev_dbg(&adap->dev, "adapter [%s] registered\n", adap->name);
/* inform drivers of new adapters */
list_for_each(item,&drivers) {
driver = list_entry(item, struct i2c_driver, list);
@ -196,8 +198,6 @@ int i2c_add_adapter(struct i2c_adapter *adap)
driver->attach_adapter(adap);
}
dev_dbg(&adap->dev, "registered as adapter #%d\n", adap->nr);
out_unlock:
up(&core_lists);
return res;
@ -220,8 +220,8 @@ int i2c_del_adapter(struct i2c_adapter *adap)
break;
}
if (adap_from_list != adap) {
pr_debug("I2C: Attempting to delete an unregistered "
"adapter\n");
pr_debug("i2c-core: attempting to delete unregistered "
"adapter [%s]\n", adap->name);
res = -EINVAL;
goto out_unlock;
}
@ -230,9 +230,8 @@ int i2c_del_adapter(struct i2c_adapter *adap)
driver = list_entry(item, struct i2c_driver, list);
if (driver->detach_adapter)
if ((res = driver->detach_adapter(adap))) {
dev_warn(&adap->dev, "can't detach adapter "
"while detaching driver %s: driver "
"not detached!\n", driver->name);
dev_err(&adap->dev, "detach_adapter failed "
"for driver [%s]\n", driver->name);
goto out_unlock;
}
}
@ -247,9 +246,8 @@ int i2c_del_adapter(struct i2c_adapter *adap)
* must be deleted, as this would cause invalid states.
*/
if ((res=client->driver->detach_client(client))) {
dev_err(&adap->dev, "adapter not "
"unregistered, because client at "
"address %02x can't be detached. ",
dev_err(&adap->dev, "detach_client failed for client "
"[%s] at address 0x%02x\n", client->name,
client->addr);
goto out_unlock;
}
@ -270,7 +268,7 @@ int i2c_del_adapter(struct i2c_adapter *adap)
/* free dynamically allocated bus id */
idr_remove(&i2c_adapter_idr, adap->nr);
dev_dbg(&adap->dev, "adapter unregistered\n");
dev_dbg(&adap->dev, "adapter [%s] unregistered\n", adap->name);
out_unlock:
up(&core_lists);
@ -303,7 +301,7 @@ int i2c_add_driver(struct i2c_driver *driver)
goto out_unlock;
list_add_tail(&driver->list,&drivers);
pr_debug("i2c-core: driver %s registered.\n", driver->name);
pr_debug("i2c-core: driver [%s] registered\n", driver->name);
/* now look for instances of driver on our adapters */
if (driver->flags & I2C_DF_NOTIFY) {
@ -331,21 +329,17 @@ int i2c_del_driver(struct i2c_driver *driver)
/* Have a look at each adapter, if clients of this driver are still
* attached. If so, detach them to be able to kill the driver
* afterwards.
*/
pr_debug("i2c-core: unregister_driver - looking for clients.\n");
/* removing clients does not depend on the notify flag, else
*
* Removing clients does not depend on the notify flag, else
* invalid operation might (will!) result, when using stale client
* pointers.
*/
list_for_each(item1,&adapters) {
adap = list_entry(item1, struct i2c_adapter, list);
dev_dbg(&adap->dev, "examining adapter\n");
if (driver->detach_adapter) {
if ((res = driver->detach_adapter(adap))) {
dev_warn(&adap->dev, "while unregistering "
"dummy driver %s, adapter could "
"not be detached properly; driver "
"not unloaded!",driver->name);
dev_err(&adap->dev, "detach_adapter failed "
"for driver [%s]\n", driver->name);
goto out_unlock;
}
} else {
@ -353,16 +347,13 @@ int i2c_del_driver(struct i2c_driver *driver)
client = list_entry(item2, struct i2c_client, list);
if (client->driver != driver)
continue;
pr_debug("i2c-core.o: detaching client %s:\n", client->name);
dev_dbg(&adap->dev, "detaching client [%s] "
"at 0x%02x\n", client->name,
client->addr);
if ((res = driver->detach_client(client))) {
dev_err(&adap->dev, "while "
"unregistering driver "
"`%s', the client at "
"address %02x of "
"adapter could not "
"be detached; driver "
"not unloaded!",
driver->name,
dev_err(&adap->dev, "detach_client "
"failed for client [%s] at "
"0x%02x\n", client->name,
client->addr);
goto out_unlock;
}
@ -372,7 +363,7 @@ int i2c_del_driver(struct i2c_driver *driver)
driver_unregister(&driver->driver);
list_del(&driver->list);
pr_debug("i2c-core: driver unregistered: %s\n", driver->name);
pr_debug("i2c-core: driver [%s] unregistered\n", driver->name);
out_unlock:
up(&core_lists);
@ -417,15 +408,12 @@ int i2c_attach_client(struct i2c_client *client)
if (adapter->client_register) {
if (adapter->client_register(client)) {
dev_warn(&adapter->dev, "warning: client_register "
"seems to have failed for client %02x\n",
client->addr);
dev_dbg(&adapter->dev, "client_register "
"failed for client [%s] at 0x%02x\n",
client->name, client->addr);
}
}
dev_dbg(&adapter->dev, "client [%s] registered to adapter\n",
client->name);
if (client->flags & I2C_CLIENT_ALLOW_USE)
client->usage_count = 0;
@ -436,7 +424,8 @@ int i2c_attach_client(struct i2c_client *client)
snprintf(&client->dev.bus_id[0], sizeof(client->dev.bus_id),
"%d-%04x", i2c_adapter_id(adapter), client->addr);
pr_debug("registering %s\n", client->dev.bus_id);
dev_dbg(&adapter->dev, "client [%s] registered with bus id %s\n",
client->name, client->dev.bus_id);
device_register(&client->dev);
device_create_file(&client->dev, &dev_attr_client_name);
@ -449,8 +438,12 @@ int i2c_detach_client(struct i2c_client *client)
struct i2c_adapter *adapter = client->adapter;
int res = 0;
if ((client->flags & I2C_CLIENT_ALLOW_USE) && (client->usage_count > 0))
if ((client->flags & I2C_CLIENT_ALLOW_USE)
&& (client->usage_count > 0)) {
dev_warn(&client->dev, "Client [%s] still busy, "
"can't detach\n", client->name);
return -EBUSY;
}
if (adapter->client_unregister) {
res = adapter->client_unregister(client);
@ -669,98 +662,128 @@ int i2c_control(struct i2c_client *client,
* Will not work for 10-bit addresses!
* ----------------------------------------------------
*/
static int i2c_probe_address(struct i2c_adapter *adapter, int addr, int kind,
int (*found_proc) (struct i2c_adapter *, int, int))
{
int err;
/* Make sure the address is valid */
if (addr < 0x03 || addr > 0x77) {
dev_warn(&adapter->dev, "Invalid probe address 0x%02x\n",
addr);
return -EINVAL;
}
/* Skip if already in use */
if (i2c_check_addr(adapter, addr))
return 0;
/* Make sure there is something at this address, unless forced */
if (kind < 0) {
if (i2c_smbus_xfer(adapter, addr, 0, 0, 0,
I2C_SMBUS_QUICK, NULL) < 0)
return 0;
/* prevent 24RF08 corruption */
if ((addr & ~0x0f) == 0x50)
i2c_smbus_xfer(adapter, addr, 0, 0, 0,
I2C_SMBUS_QUICK, NULL);
}
/* Finally call the custom detection function */
err = found_proc(adapter, addr, kind);
/* -ENODEV can be returned if there is a chip at the given address
but it isn't supported by this chip driver. We catch it here as
this isn't an error. */
return (err == -ENODEV) ? 0 : err;
}
int i2c_probe(struct i2c_adapter *adapter,
struct i2c_client_address_data *address_data,
int (*found_proc) (struct i2c_adapter *, int, int))
{
int addr,i,found,err;
int i, err;
int adap_id = i2c_adapter_id(adapter);
/* Forget it if we can't probe using SMBUS_QUICK */
if (! i2c_check_functionality(adapter,I2C_FUNC_SMBUS_QUICK))
return -1;
for (addr = 0x00; addr <= 0x7f; addr++) {
/* Force entries are done first, and are not affected by ignore
entries */
if (address_data->forces) {
unsigned short **forces = address_data->forces;
int kind;
/* Skip if already in use */
if (i2c_check_addr(adapter,addr))
continue;
/* If it is in one of the force entries, we don't do any detection
at all */
found = 0;
for (i = 0; !found && (address_data->force[i] != I2C_CLIENT_END); i += 2) {
if (((adap_id == address_data->force[i]) ||
(address_data->force[i] == ANY_I2C_BUS)) &&
(addr == address_data->force[i+1])) {
dev_dbg(&adapter->dev, "found force parameter for adapter %d, addr %04x\n",
adap_id, addr);
if ((err = found_proc(adapter,addr,0)))
return err;
found = 1;
for (kind = 0; forces[kind]; kind++) {
for (i = 0; forces[kind][i] != I2C_CLIENT_END;
i += 2) {
if (forces[kind][i] == adap_id
|| forces[kind][i] == ANY_I2C_BUS) {
dev_dbg(&adapter->dev, "found force "
"parameter for adapter %d, "
"addr 0x%02x, kind %d\n",
adap_id, forces[kind][i + 1],
kind);
err = i2c_probe_address(adapter,
forces[kind][i + 1],
kind, found_proc);
if (err)
return err;
}
}
}
if (found)
continue;
/* If this address is in one of the ignores, we can forget about
it right now */
for (i = 0;
!found && (address_data->ignore[i] != I2C_CLIENT_END);
i += 2) {
if (((adap_id == address_data->ignore[i]) ||
((address_data->ignore[i] == ANY_I2C_BUS))) &&
(addr == address_data->ignore[i+1])) {
dev_dbg(&adapter->dev, "found ignore parameter for adapter %d, "
"addr %04x\n", adap_id ,addr);
found = 1;
}
}
if (found)
continue;
/* Now, we will do a detection, but only if it is in the normal or
probe entries */
for (i = 0;
!found && (address_data->normal_i2c[i] != I2C_CLIENT_END);
i += 1) {
if (addr == address_data->normal_i2c[i]) {
found = 1;
dev_dbg(&adapter->dev, "found normal i2c entry for adapter %d, "
"addr %02x\n", adap_id, addr);
}
}
for (i = 0;
!found && (address_data->probe[i] != I2C_CLIENT_END);
i += 2) {
if (((adap_id == address_data->probe[i]) ||
((address_data->probe[i] == ANY_I2C_BUS))) &&
(addr == address_data->probe[i+1])) {
found = 1;
dev_dbg(&adapter->dev, "found probe parameter for adapter %d, "
"addr %04x\n", adap_id,addr);
}
}
if (!found)
continue;
/* OK, so we really should examine this address. First check
whether there is some client here at all! */
if (i2c_smbus_xfer(adapter,addr,0,0,0,I2C_SMBUS_QUICK,NULL) >= 0)
if ((err = found_proc(adapter,addr,-1)))
return err;
}
return 0;
}
/*
* return id number for a specific adapter
*/
int i2c_adapter_id(struct i2c_adapter *adap)
{
return adap->nr;
/* Probe entries are done second, and are not affected by ignore
entries either */
for (i = 0; address_data->probe[i] != I2C_CLIENT_END; i += 2) {
if (address_data->probe[i] == adap_id
|| address_data->probe[i] == ANY_I2C_BUS) {
dev_dbg(&adapter->dev, "found probe parameter for "
"adapter %d, addr 0x%02x\n", adap_id,
address_data->probe[i + 1]);
err = i2c_probe_address(adapter,
address_data->probe[i + 1],
-1, found_proc);
if (err)
return err;
}
}
/* Normal entries are done last, unless shadowed by an ignore entry */
for (i = 0; address_data->normal_i2c[i] != I2C_CLIENT_END; i += 1) {
int j, ignore;
ignore = 0;
for (j = 0; address_data->ignore[j] != I2C_CLIENT_END;
j += 2) {
if ((address_data->ignore[j] == adap_id ||
address_data->ignore[j] == ANY_I2C_BUS)
&& address_data->ignore[j + 1]
== address_data->normal_i2c[i]) {
dev_dbg(&adapter->dev, "found ignore "
"parameter for adapter %d, "
"addr 0x%02x\n", adap_id,
address_data->ignore[j + 1]);
}
ignore = 1;
break;
}
if (ignore)
continue;
dev_dbg(&adapter->dev, "found normal entry for adapter %d, "
"addr 0x%02x\n", adap_id,
address_data->normal_i2c[i]);
err = i2c_probe_address(adapter, address_data->normal_i2c[i],
-1, found_proc);
if (err)
return err;
}
return 0;
}
struct i2c_adapter* i2c_get_adapter(int id)
@ -1171,6 +1194,12 @@ s32 i2c_smbus_xfer(struct i2c_adapter * adapter, u16 addr, unsigned short flags,
}
/* Next four are needed by i2c-isa */
EXPORT_SYMBOL_GPL(i2c_adapter_dev_release);
EXPORT_SYMBOL_GPL(i2c_adapter_driver);
EXPORT_SYMBOL_GPL(i2c_adapter_class);
EXPORT_SYMBOL_GPL(i2c_bus_type);
EXPORT_SYMBOL(i2c_add_adapter);
EXPORT_SYMBOL(i2c_del_adapter);
EXPORT_SYMBOL(i2c_add_driver);
@ -1186,7 +1215,6 @@ EXPORT_SYMBOL(i2c_master_send);
EXPORT_SYMBOL(i2c_master_recv);
EXPORT_SYMBOL(i2c_control);
EXPORT_SYMBOL(i2c_transfer);
EXPORT_SYMBOL(i2c_adapter_id);
EXPORT_SYMBOL(i2c_get_adapter);
EXPORT_SYMBOL(i2c_put_adapter);
EXPORT_SYMBOL(i2c_probe);

View file

@ -434,7 +434,8 @@ static int i2cdev_attach_adapter(struct i2c_adapter *adap)
devfs_mk_cdev(MKDEV(I2C_MAJOR, i2c_dev->minor),
S_IFCHR|S_IRUSR|S_IWUSR, "i2c/%d", i2c_dev->minor);
dev_dbg(&adap->dev, "Registered as minor %d\n", i2c_dev->minor);
pr_debug("i2c-dev: adapter [%s] registered as minor %d\n",
adap->name, i2c_dev->minor);
/* register this i2c device with the driver core */
i2c_dev->adap = adap;
@ -471,7 +472,7 @@ static int i2cdev_detach_adapter(struct i2c_adapter *adap)
wait_for_completion(&i2c_dev->released);
kfree(i2c_dev);
dev_dbg(&adap->dev, "Adapter unregistered\n");
pr_debug("i2c-dev: adapter [%s] unregistered\n", adap->name);
return 0;
}

View file

@ -1,145 +0,0 @@
/*
i2c-sensor-detect.c - Part of lm_sensors, Linux kernel modules for hardware
monitoring
Copyright (c) 1998 - 2001 Frodo Looijaard <frodol@dds.nl> and
Mark D. Studebaker <mdsxyz123@yahoo.com>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/i2c.h>
#include <linux/i2c-sensor.h>
static unsigned short empty[] = {I2C_CLIENT_END};
static unsigned int empty_isa[] = {I2C_CLIENT_ISA_END};
/* Very inefficient for ISA detects, and won't work for 10-bit addresses! */
int i2c_detect(struct i2c_adapter *adapter,
struct i2c_address_data *address_data,
int (*found_proc) (struct i2c_adapter *, int, int))
{
int addr, i, found, j, err;
struct i2c_force_data *this_force;
int is_isa = i2c_is_isa_adapter(adapter);
int adapter_id =
is_isa ? ANY_I2C_ISA_BUS : i2c_adapter_id(adapter);
unsigned short *normal_i2c;
unsigned int *normal_isa;
unsigned short *probe;
unsigned short *ignore;
/* Forget it if we can't probe using SMBUS_QUICK */
if ((!is_isa) &&
!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_QUICK))
return -1;
/* Use default "empty" list if the adapter doesn't specify any */
normal_i2c = probe = ignore = empty;
normal_isa = empty_isa;
if (address_data->normal_i2c)
normal_i2c = address_data->normal_i2c;
if (address_data->normal_isa)
normal_isa = address_data->normal_isa;
if (address_data->probe)
probe = address_data->probe;
if (address_data->ignore)
ignore = address_data->ignore;
for (addr = 0x00; addr <= (is_isa ? 0xffff : 0x7f); addr++) {
if (!is_isa && i2c_check_addr(adapter, addr))
continue;
/* If it is in one of the force entries, we don't do any
detection at all */
found = 0;
for (i = 0; !found && (this_force = address_data->forces + i, this_force->force); i++) {
for (j = 0; !found && (this_force->force[j] != I2C_CLIENT_END); j += 2) {
if ( ((adapter_id == this_force->force[j]) ||
((this_force->force[j] == ANY_I2C_BUS) && !is_isa)) &&
(addr == this_force->force[j + 1]) ) {
dev_dbg(&adapter->dev, "found force parameter for adapter %d, addr %04x\n", adapter_id, addr);
if ((err = found_proc(adapter, addr, this_force->kind)))
return err;
found = 1;
}
}
}
if (found)
continue;
/* If this address is in one of the ignores, we can forget about it
right now */
for (i = 0; !found && (ignore[i] != I2C_CLIENT_END); i += 2) {
if ( ((adapter_id == ignore[i]) ||
((ignore[i] == ANY_I2C_BUS) &&
!is_isa)) &&
(addr == ignore[i + 1])) {
dev_dbg(&adapter->dev, "found ignore parameter for adapter %d, addr %04x\n", adapter_id, addr);
found = 1;
}
}
if (found)
continue;
/* Now, we will do a detection, but only if it is in the normal or
probe entries */
if (is_isa) {
for (i = 0; !found && (normal_isa[i] != I2C_CLIENT_ISA_END); i += 1) {
if (addr == normal_isa[i]) {
dev_dbg(&adapter->dev, "found normal isa entry for adapter %d, addr %04x\n", adapter_id, addr);
found = 1;
}
}
} else {
for (i = 0; !found && (normal_i2c[i] != I2C_CLIENT_END); i += 1) {
if (addr == normal_i2c[i]) {
found = 1;
dev_dbg(&adapter->dev, "found normal i2c entry for adapter %d, addr %02x\n", adapter_id, addr);
}
}
}
for (i = 0;
!found && (probe[i] != I2C_CLIENT_END);
i += 2) {
if (((adapter_id == probe[i]) ||
((probe[i] == ANY_I2C_BUS) && !is_isa))
&& (addr == probe[i + 1])) {
dev_dbg(&adapter->dev, "found probe parameter for adapter %d, addr %04x\n", adapter_id, addr);
found = 1;
}
}
if (!found)
continue;
/* OK, so we really should examine this address. First check
whether there is some client here at all! */
if (is_isa ||
(i2c_smbus_xfer (adapter, addr, 0, 0, 0, I2C_SMBUS_QUICK, NULL) >= 0))
if ((err = found_proc(adapter, addr, -1)))
return err;
}
return 0;
}
EXPORT_SYMBOL(i2c_detect);
MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>, "
"Rudolf Marek <r.marek@sh.cvut.cz>");
MODULE_DESCRIPTION("i2c-sensor driver");
MODULE_LICENSE("GPL");

View file

@ -1,98 +0,0 @@
/*
i2c-sensor-vid.c - Part of lm_sensors, Linux kernel modules for hardware
monitoring
Copyright (c) 2004 Rudolf Marek <r.marek@sh.cvut.cz>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include <linux/config.h>
#include <linux/module.h>
#include <linux/kernel.h>
struct vrm_model {
u8 vendor;
u8 eff_family;
u8 eff_model;
int vrm_type;
};
#define ANY 0xFF
#ifdef CONFIG_X86
static struct vrm_model vrm_models[] = {
{X86_VENDOR_AMD, 0x6, ANY, 90}, /* Athlon Duron etc */
{X86_VENDOR_AMD, 0xF, ANY, 24}, /* Athlon 64, Opteron */
{X86_VENDOR_INTEL, 0x6, 0x9, 85}, /* 0.13um too */
{X86_VENDOR_INTEL, 0x6, 0xB, 85}, /* 0xB Tualatin */
{X86_VENDOR_INTEL, 0x6, ANY, 82}, /* any P6 */
{X86_VENDOR_INTEL, 0x7, ANY, 0}, /* Itanium */
{X86_VENDOR_INTEL, 0xF, 0x3, 100}, /* P4 Prescott */
{X86_VENDOR_INTEL, 0xF, ANY, 90}, /* P4 before Prescott */
{X86_VENDOR_INTEL, 0x10,ANY, 0}, /* Itanium 2 */
{X86_VENDOR_UNKNOWN, ANY, ANY, 0} /* stop here */
};
static int find_vrm(u8 eff_family, u8 eff_model, u8 vendor)
{
int i = 0;
while (vrm_models[i].vendor!=X86_VENDOR_UNKNOWN) {
if (vrm_models[i].vendor==vendor)
if ((vrm_models[i].eff_family==eff_family)&& \
((vrm_models[i].eff_model==eff_model)|| \
(vrm_models[i].eff_model==ANY)))
return vrm_models[i].vrm_type;
i++;
}
return 0;
}
int i2c_which_vrm(void)
{
struct cpuinfo_x86 *c = cpu_data;
u32 eax;
u8 eff_family, eff_model;
int vrm_ret;
if (c->x86 < 6) return 0; /* any CPU with familly lower than 6
dont have VID and/or CPUID */
eax = cpuid_eax(1);
eff_family = ((eax & 0x00000F00)>>8);
eff_model = ((eax & 0x000000F0)>>4);
if (eff_family == 0xF) { /* use extended model & family */
eff_family += ((eax & 0x00F00000)>>20);
eff_model += ((eax & 0x000F0000)>>16)<<4;
}
vrm_ret = find_vrm(eff_family,eff_model,c->x86_vendor);
if (vrm_ret == 0)
printk(KERN_INFO "i2c-sensor.o: Unknown VRM version of your"
" x86 CPU\n");
return vrm_ret;
}
/* and now for something completely different for Non-x86 world*/
#else
int i2c_which_vrm(void)
{
printk(KERN_INFO "i2c-sensor.o: Unknown VRM version of your CPU\n");
return 0;
}
#endif
EXPORT_SYMBOL(i2c_which_vrm);

View file

@ -1464,26 +1464,6 @@ static int __devinit add_card(struct pci_dev *dev,
{ 0x50, I2C_M_RD, 20, (unsigned char*) lynx->bus_info_block }
};
#ifdef CONFIG_IEEE1394_VERBOSEDEBUG
union i2c_smbus_data data;
if (i2c_smbus_xfer(i2c_ad, 80, 0, I2C_SMBUS_WRITE, 0, I2C_SMBUS_BYTE,NULL))
PRINT(KERN_ERR, lynx->id,"eeprom read start has failed");
else
{
u16 addr;
for (addr=0x00; addr < 0x100; addr++) {
if (i2c_smbus_xfer(i2c_ad, 80, 0, I2C_SMBUS_READ, 0, I2C_SMBUS_BYTE,& data)) {
PRINT(KERN_ERR, lynx->id, "unable to read i2c %x", addr);
break;
}
else
PRINT(KERN_DEBUG, lynx->id,"got serial eeprom data at %x: %x",addr, data.byte);
}
}
#endif
/* we use i2c_transfer, because i2c_smbus_read_block_data does not work properly and we
do it more efficiently in one transaction rather then using several reads */
if (i2c_transfer(i2c_ad, msg, 2) < 0) {

View file

@ -387,8 +387,6 @@ static int saa7146_i2c_xfer(struct i2c_adapter* adapter, struct i2c_msg *msg, in
/* exported algorithm data */
static struct i2c_algorithm saa7146_algo = {
.name = "saa7146 i2c algorithm",
.id = I2C_ALGO_SAA7146,
.master_xfer = saa7146_i2c_xfer,
.functionality = saa7146_i2c_func,
};
@ -412,7 +410,7 @@ int saa7146_i2c_adapter_prepare(struct saa7146_dev *dev, struct i2c_adapter *i2c
#endif
i2c_adapter->algo = &saa7146_algo;
i2c_adapter->algo_data = NULL;
i2c_adapter->id = I2C_ALGO_SAA7146;
i2c_adapter->id = I2C_HW_SAA7146;
i2c_adapter->timeout = SAA7146_I2C_TIMEOUT;
i2c_adapter->retries = SAA7146_I2C_RETRIES;
}

View file

@ -172,8 +172,6 @@ static u32 flexcop_i2c_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm flexcop_algo = {
.name = "FlexCop I2C algorithm",
.id = I2C_ALGO_BIT,
.master_xfer = flexcop_master_xfer,
.functionality = flexcop_i2c_func,
};
@ -192,7 +190,6 @@ int flexcop_i2c_init(struct flexcop_device *fc)
fc->i2c_adap.class = I2C_CLASS_TV_DIGITAL;
fc->i2c_adap.algo = &flexcop_algo;
fc->i2c_adap.algo_data = NULL;
fc->i2c_adap.id = I2C_ALGO_BIT;
if ((ret = i2c_add_adapter(&fc->i2c_adap)) < 0)
return ret;

View file

@ -141,8 +141,6 @@ static u32 cxusb_i2c_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm cxusb_i2c_algo = {
.name = "Conexant USB I2C algorithm",
.id = I2C_ALGO_BIT,
.master_xfer = cxusb_i2c_xfer,
.functionality = cxusb_i2c_func,
};

View file

@ -156,8 +156,6 @@ static u32 dibusb_i2c_func(struct i2c_adapter *adapter)
}
struct i2c_algorithm dibusb_i2c_algo = {
.name = "DiBcom USB I2C algorithm",
.id = I2C_ALGO_BIT,
.master_xfer = dibusb_i2c_xfer,
.functionality = dibusb_i2c_func,
};

View file

@ -77,8 +77,6 @@ static u32 digitv_i2c_func(struct i2c_adapter *adapter)
}
static struct i2c_algorithm digitv_i2c_algo = {
.name = "Nebula DigiTV USB I2C algorithm",
.id = I2C_ALGO_BIT,
.master_xfer = digitv_i2c_xfer,
.functionality = digitv_i2c_func,
};

View file

@ -27,7 +27,6 @@ int dvb_usb_i2c_init(struct dvb_usb_device *d)
#endif
d->i2c_adap.algo = d->props.i2c_algo;
d->i2c_adap.algo_data = NULL;
d->i2c_adap.id = I2C_ALGO_BIT;
i2c_set_adapdata(&d->i2c_adap, d);

View file

@ -633,7 +633,6 @@ static int __devinit pluto2_probe(struct pci_dev *pdev,
i2c_set_adapdata(&pluto->i2c_adap, pluto);
strcpy(pluto->i2c_adap.name, DRIVER_NAME);
pluto->i2c_adap.owner = THIS_MODULE;
pluto->i2c_adap.id = I2C_ALGO_BIT;
pluto->i2c_adap.class = I2C_CLASS_TV_DIGITAL;
pluto->i2c_adap.dev.parent = &pdev->dev;
pluto->i2c_adap.algo_data = &pluto->i2c_bit;

View file

@ -1472,8 +1472,6 @@ static void frontend_init(struct ttusb* ttusb)
static struct i2c_algorithm ttusb_dec_algo = {
.name = "ttusb dec i2c algorithm",
.id = I2C_ALGO_BIT,
.master_xfer = master_xfer,
.functionality = functionality,
};
@ -1525,7 +1523,6 @@ static int ttusb_probe(struct usb_interface *intf, const struct usb_device_id *i
#endif
ttusb->i2c_adap.algo = &ttusb_dec_algo;
ttusb->i2c_adap.algo_data = NULL;
ttusb->i2c_adap.id = I2C_ALGO_BIT;
result = i2c_add_adapter(&ttusb->i2c_adap);
if (result) {

View file

@ -391,7 +391,6 @@ static struct i2c_client_address_data addr_data = {
.normal_i2c = normal_i2c,
.probe = &ignore,
.ignore = &ignore,
.force = &ignore,
};
static struct i2c_driver i2c_driver_adv7170;

Some files were not shown because too many files have changed in this diff Show more