aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/hwmon/hp_accel.c
diff options
context:
space:
mode:
authorGiuseppe Bilotta <giuseppe.bilotta@gmail.com>2009-02-18 17:48:24 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2009-02-18 18:37:54 -0500
commit137bad32342a613586347341d1307c2b9812ef44 (patch)
tree3ed900e263388a72f92930a8d91a9d2eb7f0a39b /drivers/hwmon/hp_accel.c
parentef2cfc790bf5f0ff189b01eabc0f4feb5e8524df (diff)
lis3lv02d: support both one- and two-byte sensors
Sensors responding with 0x3B to WHO_AM_I only have one data register per direction, thus returning a signed byte from the position which is occupied by the MSB in sensors responding with 0x3A. Since multiple sensors share the reply to WHO_AM_I, we rename the defines to better indicate what they identify (family of single and double precision sensors). We support both kind of sensors by checking for the sensor type on init and defining appropriate data-access routines and sensor limits (for the joystick) depending on what we find. [akpm@linux-foundation.org: coding-style fixes] Signed-off-by: Giuseppe Bilotta <giuseppe.bilotta@gmail.com> Acked-by: Eric Piel <Eric.Piel@tremplin-utc.net> Cc: Pavel Machek <pavel@suse.cz> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'drivers/hwmon/hp_accel.c')
-rw-r--r--drivers/hwmon/hp_accel.c36
1 files changed, 32 insertions, 4 deletions
diff --git a/drivers/hwmon/hp_accel.c b/drivers/hwmon/hp_accel.c
index dcefe1d2adbd..6b16566c4e6c 100644
--- a/drivers/hwmon/hp_accel.c
+++ b/drivers/hwmon/hp_accel.c
@@ -237,9 +237,25 @@ static void lis3lv02d_enum_resources(struct acpi_device *device)
237 printk(KERN_DEBUG DRIVER_NAME ": Error getting resources\n"); 237 printk(KERN_DEBUG DRIVER_NAME ": Error getting resources\n");
238} 238}
239 239
240static s16 lis3lv02d_read_16(acpi_handle handle, int reg)
241{
242 u8 lo, hi;
243
244 adev.read(handle, reg - 1, &lo);
245 adev.read(handle, reg, &hi);
246 /* In "12 bit right justified" mode, bit 6, bit 7, bit 8 = bit 5 */
247 return (s16)((hi << 8) | lo);
248}
249
250static s16 lis3lv02d_read_8(acpi_handle handle, int reg)
251{
252 s8 lo;
253 adev.read(handle, reg, &lo);
254 return lo;
255}
256
240static int lis3lv02d_add(struct acpi_device *device) 257static int lis3lv02d_add(struct acpi_device *device)
241{ 258{
242 u8 val;
243 int ret; 259 int ret;
244 260
245 if (!device) 261 if (!device)
@@ -253,10 +269,22 @@ static int lis3lv02d_add(struct acpi_device *device)
253 strcpy(acpi_device_class(device), ACPI_MDPS_CLASS); 269 strcpy(acpi_device_class(device), ACPI_MDPS_CLASS);
254 device->driver_data = &adev; 270 device->driver_data = &adev;
255 271
256 lis3lv02d_acpi_read(device->handle, WHO_AM_I, &val); 272 lis3lv02d_acpi_read(device->handle, WHO_AM_I, &adev.whoami);
257 if ((val != LIS3LV02DL_ID) && (val != LIS302DL_ID)) { 273 switch (adev.whoami) {
274 case LIS_DOUBLE_ID:
275 printk(KERN_INFO DRIVER_NAME ": 2-byte sensor found\n");
276 adev.read_data = lis3lv02d_read_16;
277 adev.mdps_max_val = 2048;
278 break;
279 case LIS_SINGLE_ID:
280 printk(KERN_INFO DRIVER_NAME ": 1-byte sensor found\n");
281 adev.read_data = lis3lv02d_read_8;
282 adev.mdps_max_val = 128;
283 break;
284 default:
258 printk(KERN_ERR DRIVER_NAME 285 printk(KERN_ERR DRIVER_NAME
259 ": Accelerometer chip not LIS3LV02D{L,Q}\n"); 286 ": unknown sensor type 0x%X\n", adev.whoami);
287 return -EINVAL;
260 } 288 }
261 289
262 /* If possible use a "standard" axes order */ 290 /* If possible use a "standard" axes order */