[PATCH/RFC] Change accelerometers to use ABS events rather than REL events.

Neil Brown neilb at suse.de
Fri Mar 6 02:02:22 CET 2009


[Obviously if this patch is accepted we need to tell developers about
 it.  I have a number of other improvements to the accelerometers I
 hope to deliver over the next couple of weeks.  They will have minimal
 or zero disruption to current code. ]


REL events should be used when there is no absolute reference, and
only changes are meaningful.  The classic example is a "mouse" where
the absolute position of the device is not measurable and not
particularly meaning, but change in position from one time to the next
is interesting.
With REL events, a value of '0' is not reported, as 'not change' is
not interesting.
With REL events, the expectation is that successive values will be
eventually summed (possibly with acceleration and clipping
adjustments) to get a usable value.

ABS events should be used when there is an absolute references against
which things that be measured.
With ABS events, the 'current value' is meaningful and can be read
(EVIOCGABS).
With ABS events, the value '0' is very meaningful and is reported.
However if consecutive values are the same, the value is only reported
once.
ABS events can be used as-is or compared with previous events to get
some measure of change.
An obvious example is a touchscreen where each measure in
independently meaningful.

Acceleration is an absolute value as it is measuring against a frame
of reference.  '0' acceleration is just as meaningful as any other
value, and finding the 'current' acceleration is each direction is a
potentially useful thing to do.

The Freerunner accelerometers currently report REL events.  This is
wrong.  So this patch changes them to report ABS events.

With this patch, the min/max/level/fuzz values are left at zero.  It
might be useful to make use of these in a subsequent patch.
min/max/level can be used to calibrate the accelerometers if accuracy
is important.
fuzz could possibly be used in conjunction with the 'threshold' sysfs
value to get less frequent, lower-precision reports.

This may well break some applications that read accelerometer data.
This cannot be helped, but it is quite easy to write code that copes
with the incorrect EV_REL events as well as the more correct and
useful EV_ABS events.

Signed-off-by: NeilBrown <neilb at suse.de>
---
 drivers/input/misc/lis302dl.c |   21 +++++++++------------
 1 files changed, 9 insertions(+), 12 deletions(-)

diff --git a/drivers/input/misc/lis302dl.c b/drivers/input/misc/lis302dl.c
index 772c09c..f31e548 100644
--- a/drivers/input/misc/lis302dl.c
+++ b/drivers/input/misc/lis302dl.c
@@ -285,11 +285,11 @@ static void lis302dl_bitbang_read_sample(struct lis302dl_info *lis)
 
 	/* we have a valid sample set? */
 	if (read[0] & LIS302DL_STATUS_XYZDA) {
-		input_report_rel(lis->input_dev, REL_X, mg_per_sample *
+		input_report_abs(lis->input_dev, ABS_X, mg_per_sample *
 			    (s8)read[LIS302DL_REG_OUT_X - LIS302DL_REG_STATUS]);
-		input_report_rel(lis->input_dev, REL_Y, mg_per_sample *
+		input_report_abs(lis->input_dev, ABS_Y, mg_per_sample *
 			    (s8)read[LIS302DL_REG_OUT_Y - LIS302DL_REG_STATUS]);
-		input_report_rel(lis->input_dev, REL_Z, mg_per_sample *
+		input_report_abs(lis->input_dev, ABS_Z, mg_per_sample *
 			    (s8)read[LIS302DL_REG_OUT_Z - LIS302DL_REG_STATUS]);
 
 		input_sync(lis->input_dev);
@@ -712,15 +712,12 @@ static int __devinit lis302dl_probe(struct spi_device *spi)
 		goto bail_inp_reg;
 	}
 
-	set_bit(EV_REL, lis->input_dev->evbit);
-	set_bit(REL_X, lis->input_dev->relbit);
-	set_bit(REL_Y, lis->input_dev->relbit);
-	set_bit(REL_Z, lis->input_dev->relbit);
-/*	set_bit(EV_KEY, lis->input_dev->evbit);
-	set_bit(BTN_X, lis->input_dev->keybit);
-	set_bit(BTN_Y, lis->input_dev->keybit);
-	set_bit(BTN_Z, lis->input_dev->keybit);
-*/
+	set_bit(EV_ABS, lis->input_dev->evbit);
+	input_set_abs_params(lis->input_dev, ABS_X, 0, 0, 0, 0);
+	input_set_abs_params(lis->input_dev, ABS_Y, 0, 0, 0, 0);
+	input_set_abs_params(lis->input_dev, ABS_Z, 0, 0, 0, 0);
+	
+
 	lis->threshold = 0;
 	lis->duration = 0;
 	memset(&lis->wakeup, 0, sizeof(lis->wakeup));
-- 
1.6.1.3




More information about the openmoko-kernel mailing list