I'm trying to add our proximity sensor to our BSP. I've created the kernel driver and a HAL class, and I'm testing it using the AndroSensor from the Google Play.
I'm receiving events in my HAL class (see below class), but the AndroSensor app never get them. Any help on what I'm missing/or any pointers would be much appreciated!
My HAL class:
/*
* Copyright (C) 2008 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include <fcntl.h>
#include <errno.h>
#include <math.h>
#include <poll.h>
#include <unistd.h>
#include <dirent.h>
#include <sys/select.h>
#include <cutils/log.h>
#include <cutils/properties.h>
#include <sys/types.h>
#include <pwd.h>
#include <grp.h>
#include "ProximitySensor.h"
/*****************************************************************************/
ProximitySensor::ProximitySensor()
: SensorBase(NULL, "sfh7773"),
mEnabled(0),
mInputReader(4),
mHasPendingEvent(false)
{
char buffer[PROPERTY_VALUE_MAX];
mPendingEvent.version = sizeof(sensors_event_t);
mPendingEvent.sensor = ID_P;
mPendingEvent.type = SENSOR_TYPE_PROXIMITY;
memset(mPendingEvent.data, 0, sizeof(mPendingEvent.data));
if (data_fd) {
property_get("ro.hardware.proximitysensor", buffer, "0");
strcpy(input_sysfs_path, buffer);
input_sysfs_path_len = strlen(input_sysfs_path);
enable(0, 1);
}
ALOGE("ProximitySensor: constructor - path=\"%s\"", input_sysfs_path);
}
ProximitySensor::~ProximitySensor() {
if (mEnabled) {
enable(0, 0);
}
ALOGE("ProximitySensor: destructor");
}
int ProximitySensor::setInitialState() {
struct input_absinfo absinfo;
if (!ioctl(data_fd, EVIOCGABS(EVENT_TYPE_PROXIMITY), &absinfo)) {
mHasPendingEvent = true;
mPendingEvent.distance = 5;
}
return 0;
}
int ProximitySensor::enable(int32_t, int en) {
int flags = en ? 1 : 0;
struct passwd *passwd = getpwuid (getuid());
struct group *grp = getgrgid(passwd->pw_gid);
ALOGE("ProximitySensor: enabled(%d), user=\"%s\", group=\"%s\", sys_path=\"%s\"", en,
passwd->pw_name, grp->gr_name, input_sysfs_path);
if (flags != mEnabled) {
int fd;
strcpy(&input_sysfs_path[input_sysfs_path_len], en ? "power_state" : "prox0_raw_en");
fd = open(input_sysfs_path, O_RDWR);
if (fd >= 0) {
char buf[2];
buf[1] = 0;
if (flags) {
buf[0] = '1';
} else {
buf[0] = '0';
}
write(fd, buf, sizeof(buf));
close(fd);
strcpy(&input_sysfs_path[input_sysfs_path_len],
en ? "prox0_raw_en" : "power_state");
fd = open(input_sysfs_path, O_RDWR);
if (fd >= 0) {
char buf[2];
buf[1] = 0;
if (flags) {
buf[0] = '1';
} else {
buf[0] = '0';
}
write(fd, buf, sizeof(buf));
close(fd);
mEnabled = flags;
setInitialState();
ALOGE("ProximitySensor::enable: return #1");
return 0;
}
}
ALOGE("ProximitySensor::enable: fd=%d, return #2", fd);
return -1;
}
ALOGE("ProximitySensor::enable: return #3");
return 0;
}
bool ProximitySensor::hasPendingEvents() const {
return mHasPendingEvent;
}
int ProximitySensor::readEvents(sensors_event_t* data, int count)
{
if (count < 1)
return -EINVAL;
if (mHasPendingEvent) {
mHasPendingEvent = false;
mPendingEvent.timestamp = getTimestamp();
*data = mPendingEvent;
return mEnabled ? 1 : 0;
}
ssize_t n = mInputReader.fill(data_fd);
if (n < 0)
return n;
int numEventReceived = 0;
input_event const* event;
while (count && mInputReader.readEvent(&event)) {
int type = event->type;
ALOGE("ProximitySensor: readEvents (type=%d, code=%d, value=%d)",
type, event->code, event->value);
if (type == EV_ABS) {
if (event->code == EVENT_TYPE_PROXIMITY) {
mPendingMask |= 1<<Proximity;
if (event->value > 80) {
mPendingEvent.distance = 0;
} else {
mPendingEvent.distance = 5;
}
}
} else if (type == EV_SYN) {
mPendingEvent.timestamp = timevalToNano(event->time);
if (mEnabled) {
*data++ = mPendingEvent;
count--;
numEventReceived++;
}
} else {
ALOGE("ProximitySensor: unknown event (type=%d, code=%d)",
type, event->code);
}
mInputReader.next();
}
return numEventReceived;
}
void ProximitySensor::processEvent(int code, int value)
{
ALOGE("ProximitySensor: processEvent(code=%d, value=%d)",
code, value);
mPendingMask |= 1<<Proximity;
}
Log from readEvents;
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=106)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=117)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=124)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=126)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=127)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=128)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=71)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=3, code=25, value=0)
E/Sensors ( 2472): ProximitySensor: readEvents (type=0, code=0, value=0)
Solved! Go to Solution.
I had to call the SensorBase enable function from my enable function. Unfortunately I didn't have the time to investigate exactly why that is (Which really annoys my thorough mindset. I normally wouldn't check anything in that I didn't fully understand). Next up is the vibrator. It doesn't have a chip to control it, straight on/off. I could only find drivers for vibrators with a control chip, so if anyone has some pointers feel free to enlighten me... I'll make a discussion thread tomorrow...
I had to call the SensorBase enable function from my enable function. Unfortunately I didn't have the time to investigate exactly why that is (Which really annoys my thorough mindset. I normally wouldn't check anything in that I didn't fully understand). Next up is the vibrator. It doesn't have a chip to control it, straight on/off. I could only find drivers for vibrators with a control chip, so if anyone has some pointers feel free to enlighten me... I'll make a discussion thread tomorrow...
Fixed...
Thomas, could you out your answer here or in orignal discussion please?