mirror of
https://github.com/lm-sensors/lm-sensors.git
synced 2026-10-31 13:10:30 +00:00
Add VID support to the pc87360 driver.
git-svn-id: http://lm-sensors.org/svn/lm-sensors/trunk@2603 7894878c-1315-0410-8ee3-d5d059ff63e0
This commit is contained in:
1 parent
6927c8e1c5
commit
4fd3781e12
5 files changed
+79
-4
No files matched your search
@@ -151,6 +151,12 @@ recommendations.
|
||||
Each voltage measured has associated low and high limit, each of which
|
||||
triggers an alarm when crossed.
|
||||
|
||||
When available, VID inputs are used to provide the nominal CPU Core voltage.
|
||||
The driver will default to VRM 9.0, but this can be changed from user-space.
|
||||
The chipsets can handle two sets of VID inputs (on dual-CPU systems), but
|
||||
the driver will only export one for now. This may change later if there is
|
||||
a need.
|
||||
|
||||
|
||||
General Remarks
|
||||
---------------
|
||||
|
||||
@@ -2069,6 +2069,9 @@ chip "pc87366-*"
|
||||
|
||||
# Voltage inputs
|
||||
|
||||
# Set VRM version (default 9.0)
|
||||
# set vrm 9.0
|
||||
|
||||
label in7 "Vsb"
|
||||
label in8 "Vdd"
|
||||
label in9 "Vbat"
|
||||
|
||||
+63
-4
@@ -41,6 +41,7 @@
|
||||
#include <linux/init.h>
|
||||
#include <asm/io.h>
|
||||
#include "version.h"
|
||||
#include "sensors_vid.h"
|
||||
|
||||
static unsigned short normal_i2c[] = { SENSORS_I2C_END };
|
||||
static unsigned short normal_i2c_range[] = { SENSORS_I2C_END };
|
||||
@@ -49,7 +50,7 @@ static unsigned int normal_isa_range[] = { SENSORS_ISA_END };
|
||||
static struct i2c_force_data forces[] = {{NULL}};
|
||||
static u8 devid;
|
||||
static unsigned int extra_isa[] = { 0x0000, 0x0000, 0x0000 };
|
||||
static u8 confreg[3];
|
||||
static u8 confreg[4];
|
||||
|
||||
enum chips { any_chip, pc87360, pc87363, pc87364, pc87365, pc87366 };
|
||||
static struct i2c_address_data addr_data = {
|
||||
@@ -168,6 +169,7 @@ static inline u8 PWM_TO_REG(int val, int inv)
|
||||
#define PC87365_REG_IN_STATUS 0x0A
|
||||
#define PC87365_REG_IN_ALARMS1 0x00
|
||||
#define PC87365_REG_IN_ALARMS2 0x01
|
||||
#define PC87365_REG_VID 0x06
|
||||
|
||||
#define IN_FROM_REG(val,ref) (((val) * (ref) + 128) / 256)
|
||||
#define IN_TO_REG(val,ref) ((val)<0 ? 0 : \
|
||||
@@ -215,6 +217,9 @@ struct pc87360_data {
|
||||
u8 in_crit[3]; /* Register value */
|
||||
u8 in_status[14]; /* Register value */
|
||||
u16 in_alarms; /* Register values, combined, masked */
|
||||
u8 vid_conf; /* Configuration register value */
|
||||
u8 vrm;
|
||||
u8 vid; /* Register value */
|
||||
|
||||
u8 temp[3]; /* Register value */
|
||||
u8 temp_min[3]; /* Register value */
|
||||
@@ -255,6 +260,10 @@ void pc87365_in(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results);
|
||||
void pc87365_in_status(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results);
|
||||
void pc87365_vid(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results);
|
||||
void pc87365_vrm(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results);
|
||||
|
||||
void pc87365_temp(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results);
|
||||
@@ -319,6 +328,9 @@ static struct i2c_driver pc87360_driver = {
|
||||
#define PC87365_SYSCTL_TEMP5_STATUS 2312 /* not for PC87365 */
|
||||
#define PC87365_SYSCTL_TEMP6_STATUS 2313 /* not for PC87365 */
|
||||
|
||||
#define PC87365_SYSCTL_VID 2400
|
||||
#define PC87365_SYSCTL_VRM 2401
|
||||
|
||||
#define PC87365_STATUS_IN_MIN 0x02
|
||||
#define PC87365_STATUS_IN_MAX 0x04
|
||||
|
||||
@@ -451,6 +463,10 @@ static ctl_table pc87365_dir_table_template[] = { /* PC87366 too */
|
||||
&i2c_proc_real, &i2c_sysctl_real, NULL, &pc87365_in_status},
|
||||
{PC87365_SYSCTL_TEMP6_STATUS, "temp6_status", NULL, 0, 0444, NULL,
|
||||
&i2c_proc_real, &i2c_sysctl_real, NULL, &pc87365_in_status},
|
||||
{PC87365_SYSCTL_VID, "vid", NULL, 0, 0444, NULL,
|
||||
&i2c_proc_real, &i2c_sysctl_real, NULL, &pc87365_vid},
|
||||
{PC87365_SYSCTL_VRM, "vrm", NULL, 0, 0644, NULL,
|
||||
&i2c_proc_real, &i2c_sysctl_real, NULL, &pc87365_vrm},
|
||||
{0}
|
||||
};
|
||||
|
||||
@@ -525,16 +541,25 @@ static int pc87360_find(u8 *devid, int *address)
|
||||
} else if (i==1) { /* Voltages */
|
||||
/* Are we using thermistors? */
|
||||
if (*devid == 0xE9) { /* PC87366 */
|
||||
/* This register is not logical-device
|
||||
specific, just that we won't need it if we
|
||||
don't use the VLM device */
|
||||
/* These registers are not logical-device
|
||||
specific, just that we won't need them if
|
||||
we don't use the VLM device */
|
||||
confreg[2] = superio_inb(0x2B);
|
||||
confreg[3] = superio_inb(0x25);
|
||||
|
||||
if (confreg[2] & 0x40) {
|
||||
printk(KERN_INFO "pc87360.o: Using "
|
||||
"thermistors for temperature "
|
||||
"monitoring\n");
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
if (confreg[3] & 0xE0) {
|
||||
printk(KERN_INFO "pc87360.o: VID "
|
||||
"inputs routed (mode %d)\n",
|
||||
confreg[3] & 0xE0);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -644,6 +669,9 @@ int pc87360_detect(struct i2c_adapter *adapter, int address,
|
||||
printk(KERN_DEBUG "Using %s reference voltage\n",
|
||||
(i&0x02) ? "external" : "internal");
|
||||
#endif
|
||||
|
||||
data->vid_conf = confreg[3];
|
||||
data->vrm = 90;
|
||||
}
|
||||
|
||||
/* Fan clock dividers may be needed before any data is read */
|
||||
@@ -960,6 +988,9 @@ static void pc87360_update_client(struct i2c_client *client)
|
||||
| ((pc87360_read_value(data, LD_IN,
|
||||
NO_BANK, PC87365_REG_IN_ALARMS2)
|
||||
& 0x07) << 8);
|
||||
data->vid = (data->vid_conf & 0xE0) ?
|
||||
pc87360_read_value(data, LD_IN,
|
||||
NO_BANK, PC87365_REG_VID) : 0x1F;
|
||||
}
|
||||
|
||||
/* Temperatures */
|
||||
@@ -1181,6 +1212,34 @@ void pc87365_in_status(struct i2c_client *client, int operation, int ctl_name,
|
||||
}
|
||||
}
|
||||
|
||||
void pc87365_vid(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results)
|
||||
{
|
||||
struct pc87360_data *data = client->data;
|
||||
if (operation == SENSORS_PROC_REAL_INFO)
|
||||
*nrels_mag = 3;
|
||||
else if (operation == SENSORS_PROC_REAL_READ) {
|
||||
pc87360_update_client(client);
|
||||
results[0] = vid_from_reg(data->vid & 0x1f, data->vrm);
|
||||
*nrels_mag = 1;
|
||||
}
|
||||
}
|
||||
|
||||
void pc87365_vrm(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results)
|
||||
{
|
||||
struct pc87360_data *data = client->data;
|
||||
if (operation == SENSORS_PROC_REAL_INFO)
|
||||
*nrels_mag = 1;
|
||||
else if (operation == SENSORS_PROC_REAL_READ) {
|
||||
results[0] = data->vrm;
|
||||
*nrels_mag = 1;
|
||||
} else if (operation == SENSORS_PROC_REAL_WRITE) {
|
||||
if (*nrels_mag >= 1)
|
||||
data->vrm = results[0];
|
||||
}
|
||||
}
|
||||
|
||||
void pc87365_temp(struct i2c_client *client, int operation, int ctl_name,
|
||||
int *nrels_mag, long *results)
|
||||
{
|
||||
|
||||
@@ -4617,6 +4617,10 @@ static sensors_chip_feature pc87365_features[] =
|
||||
NOMAP, R, PC87365_SYSCTL_TEMP5_STATUS, VALUE(1), 0 },
|
||||
{ SENSORS_PC87360_TEMP6_STATUS, "temp6_status", SENSORS_PC87360_TEMP6,
|
||||
NOMAP, R, PC87365_SYSCTL_TEMP6_STATUS, VALUE(1), 0 },
|
||||
{ SENSORS_PC87360_VID, "vid", NOMAP, NOMAP,
|
||||
R, PC87365_SYSCTL_VID, VALUE(1), 3 },
|
||||
{ SENSORS_PC87360_VRM, "vrm", NOMAP, NOMAP,
|
||||
RW, PC87365_SYSCTL_VRM, VALUE(1), 1 },
|
||||
{ 0 }
|
||||
};
|
||||
|
||||
|
||||
@@ -1749,6 +1749,9 @@
|
||||
#define SENSORS_PC87360_TEMP5_STATUS 215 /* R */
|
||||
#define SENSORS_PC87360_TEMP6_STATUS 216 /* R */
|
||||
|
||||
#define SENSORS_PC87360_VID 240 /* R */
|
||||
#define SENSORS_PC87360_VRM 241 /* RW */
|
||||
|
||||
#define SENSORS_LM92_PREFIX "lm92"
|
||||
|
||||
#define SENSORS_LM92_TEMP_HIGH 1 /* RW */
|
||||
|
||||
Reference in new issue
Block a user