Merge branch 'tty-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh...
[pandora-kernel.git] / drivers / hwmon / lm85.c
index d56da2e..1e22984 100644 (file)
 /* Addresses to scan */
 static const unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END };
 
-/* Insmod parameters */
-I2C_CLIENT_INSMOD_7(lm85b, lm85c, adm1027, adt7463, adt7468, emc6d100,
-                   emc6d102);
+enum chips {
+       any_chip, lm85b, lm85c,
+       adm1027, adt7463, adt7468,
+       emc6d100, emc6d102
+};
 
 /* The LM85 registers */
 
@@ -62,9 +64,12 @@ I2C_CLIENT_INSMOD_7(lm85b, lm85c, adm1027, adt7463, adt7468, emc6d100,
 #define        LM85_REG_VERSTEP                0x3f
 
 #define        ADT7468_REG_CFG5                0x7c
-#define                ADT7468_OFF64           0x01
+#define                ADT7468_OFF64           (1 << 0)
+#define                ADT7468_HFPWM           (1 << 1)
 #define        IS_ADT7468_OFF64(data)          \
        ((data)->type == adt7468 && !((data)->cfg5 & ADT7468_OFF64))
+#define        IS_ADT7468_HFPWM(data)          \
+       ((data)->type == adt7468 && !((data)->cfg5 & ADT7468_HFPWM))
 
 /* These are the recognized values for the above regs */
 #define        LM85_COMPANY_NATIONAL           0x01
@@ -323,8 +328,7 @@ struct lm85_data {
        struct lm85_zone zone[3];
 };
 
-static int lm85_detect(struct i2c_client *client, int kind,
-                      struct i2c_board_info *info);
+static int lm85_detect(struct i2c_client *client, struct i2c_board_info *info);
 static int lm85_probe(struct i2c_client *client,
                      const struct i2c_device_id *id);
 static int lm85_remove(struct i2c_client *client);
@@ -357,7 +361,7 @@ static struct i2c_driver lm85_driver = {
        .remove         = lm85_remove,
        .id_table       = lm85_id,
        .detect         = lm85_detect,
-       .address_data   = &addr_data,
+       .address_list   = normal_i2c,
 };
 
 
@@ -566,8 +570,14 @@ static ssize_t show_pwm_freq(struct device *dev,
 {
        int nr = to_sensor_dev_attr(attr)->index;
        struct lm85_data *data = lm85_update_device(dev);
-       return sprintf(buf, "%d\n", FREQ_FROM_REG(data->freq_map,
-                                                 data->pwm_freq[nr]));
+       int freq;
+
+       if (IS_ADT7468_HFPWM(data))
+               freq = 22500;
+       else
+               freq = FREQ_FROM_REG(data->freq_map, data->pwm_freq[nr]);
+
+       return sprintf(buf, "%d\n", freq);
 }
 
 static ssize_t set_pwm_freq(struct device *dev,
@@ -579,10 +589,22 @@ static ssize_t set_pwm_freq(struct device *dev,
        long val = simple_strtol(buf, NULL, 10);
 
        mutex_lock(&data->update_lock);
-       data->pwm_freq[nr] = FREQ_TO_REG(data->freq_map, val);
-       lm85_write_value(client, LM85_REG_AFAN_RANGE(nr),
-               (data->zone[nr].range << 4)
-               | data->pwm_freq[nr]);
+       /* The ADT7468 has a special high-frequency PWM output mode,
+        * where all PWM outputs are driven by a 22.5 kHz clock.
+        * This might confuse the user, but there's not much we can do. */
+       if (data->type == adt7468 && val >= 11300) {    /* High freq. mode */
+               data->cfg5 &= ~ADT7468_HFPWM;
+               lm85_write_value(client, ADT7468_REG_CFG5, data->cfg5);
+       } else {                                        /* Low freq. mode */
+               data->pwm_freq[nr] = FREQ_TO_REG(data->freq_map, val);
+               lm85_write_value(client, LM85_REG_AFAN_RANGE(nr),
+                                (data->zone[nr].range << 4)
+                                | data->pwm_freq[nr]);
+               if (data->type == adt7468) {
+                       data->cfg5 |= ADT7468_HFPWM;
+                       lm85_write_value(client, ADT7468_REG_CFG5, data->cfg5);
+               }
+       }
        mutex_unlock(&data->update_lock);
        return count;
 }
@@ -1156,8 +1178,7 @@ static int lm85_is_fake(struct i2c_client *client)
 }
 
 /* Return 0 if detection is successful, -ENODEV otherwise */
-static int lm85_detect(struct i2c_client *client, int kind,
-                      struct i2c_board_info *info)
+static int lm85_detect(struct i2c_client *client, struct i2c_board_info *info)
 {
        struct i2c_adapter *adapter = client->adapter;
        int address = client->addr;
@@ -1259,6 +1280,7 @@ static int lm85_probe(struct i2c_client *client,
        switch (data->type) {
        case adm1027:
        case adt7463:
+       case adt7468:
        case emc6d100:
        case emc6d102:
                data->freq_map = adm1027_freq_map;