summaryrefslogtreecommitdiffstats
path: root/hal
diff options
context:
space:
mode:
authorJyoti Bhayana <jbhayana@google.com>2020-09-08 14:38:02 -0700
committerJyoti Bhayana <jbhayana@google.com>2020-09-18 16:56:56 -0700
commit45a82661021d997dc5042239e58e420ef367d331 (patch)
treeb658c8e24ef3063c741228bcb8a5835e2b1a5d58 /hal
parent11dfa08a25c7a506257ea39e75e38fc5b180bf4f (diff)
downloaddevice_google_trout-45a82661021d997dc5042239e58e420ef367d331.tar.gz
device_google_trout-45a82661021d997dc5042239e58e420ef367d331.tar.bz2
device_google_trout-45a82661021d997dc5042239e58e420ef367d331.zip
Adding support for Sensor configuration and making sure that accel and
gyro comply with Android Car Coordinate system Bug:163421259 Test: Build and run cts test testAccelerometer_50hz_batching making sure that MeanVerification test pass Change-Id: I2612427aa16ac20a8882d89de952aaf14b5b16df
Diffstat (limited to 'hal')
-rw-r--r--hal/sensors/2.0/Android.bp4
-rw-r--r--hal/sensors/2.0/Sensor.cpp175
-rw-r--r--hal/sensors/2.0/Sensor.h42
-rw-r--r--hal/sensors/2.0/SensorsSubHal.cpp93
-rw-r--r--hal/sensors/2.0/SensorsSubHal.h13
-rw-r--r--hal/sensors/2.0/config/Android.bp20
-rw-r--r--hal/sensors/2.0/config/api/current.txt88
-rw-r--r--hal/sensors/2.0/config/api/last_current.txt0
-rw-r--r--hal/sensors/2.0/config/api/last_removed.txt0
-rw-r--r--hal/sensors/2.0/config/api/removed.txt1
-rw-r--r--hal/sensors/2.0/config/sensor_hal_configuration.xml52
-rw-r--r--hal/sensors/2.0/config/sensor_hal_configuration.xsd78
-rw-r--r--hal/sensors/2.0/iio_utils.cpp1
13 files changed, 465 insertions, 102 deletions
diff --git a/hal/sensors/2.0/Android.bp b/hal/sensors/2.0/Android.bp
index 2fb5466..bd35203 100644
--- a/hal/sensors/2.0/Android.bp
+++ b/hal/sensors/2.0/Android.bp
@@ -39,11 +39,13 @@ cc_library {
],
static_libs: [
"android.hardware.sensors@2.X-multihal",
+ "libxml2",
],
cflags: [
- "-DLOG_TAG=\"GoogleIIOSensorSubHal\"",
"-Wall",
"-Wextra",
"-Werror",
],
+ generated_sources: ["sensor_hal_configuration_V1_0"],
+ generated_headers: ["sensor_hal_configuration_V1_0"],
}
diff --git a/hal/sensors/2.0/Sensor.cpp b/hal/sensors/2.0/Sensor.cpp
index b5288e2..c221039 100644
--- a/hal/sensors/2.0/Sensor.cpp
+++ b/hal/sensors/2.0/Sensor.cpp
@@ -13,6 +13,7 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+#define LOG_TAG "GoogleIIOSensorSubHal"
#include "Sensor.h"
#include <hardware/sensors.h>
@@ -30,6 +31,7 @@ namespace implementation {
using ::android::hardware::sensors::V1_0::MetaDataEventType;
using ::android::hardware::sensors::V1_0::SensorFlagBits;
using ::android::hardware::sensors::V1_0::SensorStatus;
+using ::sensor::hal::configuration::V1_0::Orientation;
SensorBase::SensorBase(int32_t sensorHandle, ISensorsEventCallback* callback, SensorType type)
: mIsEnabled(false), mSamplingPeriodNs(0), mCallback(callback), mMode(OperationMode::NORMAL) {
@@ -69,7 +71,7 @@ SensorBase::~SensorBase() {
}
HWSensorBase::~HWSensorBase() {
- close(mpollfd_iio.fd);
+ close(mPollFdIio.fd);
}
const SensorInfo& SensorBase::getSensorInfo() const {
@@ -84,10 +86,10 @@ void HWSensorBase::batch(int32_t samplingPeriodNs) {
int i = 0;
mSamplingPeriodNs = samplingPeriodNs;
std::vector<double>::iterator low =
- std::lower_bound(miio_data.sampling_freq_avl.begin(),
- miio_data.sampling_freq_avl.end(), sampling_frequency);
- i = low - miio_data.sampling_freq_avl.begin();
- set_sampling_frequency(miio_data.sysfspath, miio_data.sampling_freq_avl[i]);
+ std::lower_bound(mIioData.sampling_freq_avl.begin(),
+ mIioData.sampling_freq_avl.end(), sampling_frequency);
+ i = low - mIioData.sampling_freq_avl.begin();
+ set_sampling_frequency(mIioData.sysfspath, mIioData.sampling_freq_avl[i]);
// Wake up the 'run' thread to check if a new event should be generated now
mWaitCV.notify_all();
}
@@ -97,7 +99,7 @@ void HWSensorBase::activate(bool enable) {
std::unique_lock<std::mutex> lock(mRunMutex);
if (mIsEnabled != enable) {
mIsEnabled = enable;
- enable_sensor(miio_data.sysfspath, enable);
+ enable_sensor(mIioData.sysfspath, enable);
mWaitCV.notify_all();
}
}
@@ -120,27 +122,33 @@ Result SensorBase::flush() {
return Result::OK;
}
+template <size_t N>
+float getChannelData(const std::array<float, N>& channelData, int64_t map, bool negate) {
+ return negate ? -channelData[map] : channelData[map];
+}
+
void HWSensorBase::processScanData(uint8_t* data, Event* evt) {
- float channelData[NUM_OF_CHANNEL_SUPPORTED - 1];
+ std::array<float, NUM_OF_DATA_CHANNELS> channelData;
unsigned int chanIdx;
evt->sensorHandle = mSensorInfo.sensorHandle;
evt->sensorType = mSensorInfo.type;
- for (auto i = 0u; i < miio_data.channelInfo.size(); i++) {
- chanIdx = miio_data.channelInfo[i].index;
- const int64_t val = *reinterpret_cast<int64_t*>(
- data + chanIdx * miio_data.channelInfo[i].storage_bytes);
+ for (auto i = 0u; i < mIioData.channelInfo.size(); i++) {
+ chanIdx = mIioData.channelInfo[i].index;
+ const int64_t val =
+ *reinterpret_cast<int64_t*>(data + chanIdx * mIioData.channelInfo[i].storage_bytes);
// If the channel index is the last, it is timestamp
// else it is sensor data
- if (chanIdx == miio_data.channelInfo.size() - 1) {
+ if (chanIdx == mIioData.channelInfo.size() - 1) {
evt->timestamp = val;
} else {
- channelData[chanIdx] = (static_cast<float>(val) * miio_data.resolution);
+ channelData[chanIdx] = static_cast<float>(val) * mIioData.resolution;
}
}
- evt->u.vec3.x = channelData[0];
- evt->u.vec3.y = channelData[1];
- evt->u.vec3.z = channelData[2];
+
+ evt->u.vec3.x = getChannelData(channelData, mXMap, mXNegate);
+ evt->u.vec3.y = getChannelData(channelData, mYMap, mYNegate);
+ evt->u.vec3.z = getChannelData(channelData, mZMap, mZNegate);
evt->u.vec3.status = SensorStatus::ACCURACY_HIGH;
}
@@ -157,19 +165,19 @@ void HWSensorBase::run() {
return ((mIsEnabled && mMode == OperationMode::NORMAL) || mStopThread);
});
} else {
- err = poll(&mpollfd_iio, 1, mSamplingPeriodNs * 1000);
+ err = poll(&mPollFdIio, 1, mSamplingPeriodNs * 1000);
if (err <= 0) {
- ALOGE("Sensor %s poll returned %d", miio_data.name.c_str(), err);
+ ALOGE("Sensor %s poll returned %d", mIioData.name.c_str(), err);
continue;
}
- if (mpollfd_iio.revents & POLLIN) {
- read_size = read(mpollfd_iio.fd, &msensor_raw_data[0], mscan_size);
+ if (mPollFdIio.revents & POLLIN) {
+ read_size = read(mPollFdIio.fd, &mSensorRawData[0], mScanSize);
if (read_size <= 0) {
- ALOGE("%s: Failed to read data from iio char device.", miio_data.name.c_str());
+ ALOGE("%s: Failed to read data from iio char device.", mIioData.name.c_str());
continue;
}
events.clear();
- processScanData(&msensor_raw_data[0], &event);
+ processScanData(&mSensorRawData[0], &event);
events.push_back(event);
mCallback->postEvents(events, isWakeUpSensor());
}
@@ -210,15 +218,103 @@ Result SensorBase::injectEvent(const Event& event) {
ssize_t HWSensorBase::calculateScanSize() {
ssize_t numBytes = 0;
- for (auto i = 0u; i < miio_data.channelInfo.size(); i++) {
- numBytes += miio_data.channelInfo[i].storage_bytes;
+ for (auto i = 0u; i < mIioData.channelInfo.size(); i++) {
+ numBytes += mIioData.channelInfo[i].storage_bytes;
}
return numBytes;
}
-HWSensorBase::HWSensorBase(int32_t sensorHandle, ISensorsEventCallback* callback, SensorType type,
- const struct iio_device_data& data)
- : SensorBase(sensorHandle, callback, type) {
+status_t checkAxis(int64_t map) {
+ if (map < 0 || map >= NUM_OF_DATA_CHANNELS)
+ return BAD_VALUE;
+ else
+ return OK;
+}
+
+std::optional<std::vector<Orientation>> getOrientation(
+ std::optional<std::vector<Configuration>> config) {
+ if (!config) return std::nullopt;
+ if (config->empty()) return std::nullopt;
+ Configuration& sensorCfg = (*config)[0];
+ return sensorCfg.getOrientation();
+}
+
+status_t checkOrientation(std::optional<std::vector<Configuration>> config) {
+ status_t ret = OK;
+ std::optional<std::vector<Orientation>> sensorOrientationList = getOrientation(config);
+ if (!sensorOrientationList) return OK;
+ if (sensorOrientationList->empty()) return OK;
+ Orientation& sensorOrientation = (*sensorOrientationList)[0];
+ if (!sensorOrientation.getFirstX() || !sensorOrientation.getFirstY() ||
+ !sensorOrientation.getFirstZ())
+ return BAD_VALUE;
+
+ int64_t xMap = sensorOrientation.getFirstX()->getMap();
+ ret = checkAxis(xMap);
+ if (ret != OK) return ret;
+ int64_t yMap = sensorOrientation.getFirstY()->getMap();
+ ret = checkAxis(yMap);
+ if (ret != OK) return ret;
+ int64_t zMap = sensorOrientation.getFirstZ()->getMap();
+ ret = checkAxis(zMap);
+ if (ret != OK) return ret;
+ if (xMap == yMap || yMap == zMap || zMap == xMap) return BAD_VALUE;
+ return ret;
+}
+
+void HWSensorBase::setAxisDefaultValues() {
+ mXMap = 0;
+ mYMap = 1;
+ mZMap = 2;
+ mXNegate = mYNegate = mZNegate = false;
+}
+void HWSensorBase::setOrientation(std::optional<std::vector<Configuration>> config) {
+ std::optional<std::vector<Orientation>> sensorOrientationList = getOrientation(config);
+
+ if (sensorOrientationList && !sensorOrientationList->empty()) {
+ Orientation& sensorOrientation = (*sensorOrientationList)[0];
+
+ if (sensorOrientation.getRotate()) {
+ mXMap = sensorOrientation.getFirstX()->getMap();
+ mXNegate = sensorOrientation.getFirstX()->getNegate();
+ mYMap = sensorOrientation.getFirstY()->getMap();
+ mYNegate = sensorOrientation.getFirstY()->getNegate();
+ mZMap = sensorOrientation.getFirstZ()->getMap();
+ mZNegate = sensorOrientation.getFirstZ()->getNegate();
+ } else {
+ setAxisDefaultValues();
+ }
+ } else {
+ setAxisDefaultValues();
+ }
+}
+
+status_t checkIIOData(const struct iio_device_data& iio_data) {
+ status_t ret = OK;
+ for (auto i = 0u; i < iio_data.channelInfo.size(); i++) {
+ if (iio_data.channelInfo[i].index > NUM_OF_DATA_CHANNELS) return BAD_VALUE;
+ }
+ return ret;
+}
+HWSensorBase* HWSensorBase::buildSensor(int32_t sensorHandle, ISensorsEventCallback* callback,
+ const struct iio_device_data& iio_data,
+ const std::optional<std::vector<Configuration>>& config) {
+ if (checkOrientation(config) != OK) {
+ ALOGE("Orientation of the sensor %s in the configuration file is invalid",
+ iio_data.name.c_str());
+ return nullptr;
+ }
+ if (checkIIOData(iio_data) != OK) {
+ ALOGE("IIO channel index of the sensor %s is invalid", iio_data.name.c_str());
+ return nullptr;
+ }
+ return new HWSensorBase(sensorHandle, callback, iio_data, config);
+}
+
+HWSensorBase::HWSensorBase(int32_t sensorHandle, ISensorsEventCallback* callback,
+ const struct iio_device_data& data,
+ const std::optional<std::vector<Configuration>>& config)
+ : SensorBase(sensorHandle, callback, data.type) {
std::string buffer_path;
mSensorInfo.flags |= SensorFlagBits::CONTINUOUS_MODE;
mSensorInfo.name = data.name;
@@ -226,7 +322,8 @@ HWSensorBase::HWSensorBase(int32_t sensorHandle, ISensorsEventCallback* callback
mSensorInfo.maxRange = data.max_range * data.resolution;
mSensorInfo.power =
(data.power_microwatts / 1000.f) / SENSOR_VOLTAGE_DEFAULT; // converting uW to mA
- miio_data = data;
+ mIioData = data;
+ setOrientation(config);
unsigned int max_sampling_frequency = 0;
unsigned int min_sampling_frequency = UINT_MAX;
for (auto i = 0u; i < data.sampling_freq_avl.size(); i++) {
@@ -237,26 +334,16 @@ HWSensorBase::HWSensorBase(int32_t sensorHandle, ISensorsEventCallback* callback
}
mSensorInfo.minDelay = frequency_to_us(max_sampling_frequency);
mSensorInfo.maxDelay = frequency_to_us(min_sampling_frequency);
- mscan_size = calculateScanSize();
+ mScanSize = calculateScanSize();
buffer_path = "/dev/iio:device";
- buffer_path.append(std::to_string(miio_data.iio_dev_num));
- mpollfd_iio.fd = open(buffer_path.c_str(), O_RDONLY | O_NONBLOCK);
- if (mpollfd_iio.fd < 0) {
+ buffer_path.append(std::to_string(mIioData.iio_dev_num));
+ mPollFdIio.fd = open(buffer_path.c_str(), O_RDONLY | O_NONBLOCK);
+ if (mPollFdIio.fd < 0) {
ALOGE("%s: Failed to open iio char device (%s).", data.name.c_str(), buffer_path.c_str());
return;
}
- mpollfd_iio.events = POLLIN;
- msensor_raw_data.resize(mscan_size);
-}
-
-Accelerometer::Accelerometer(int32_t sensorHandle, ISensorsEventCallback* callback,
- const struct iio_device_data& data)
- : HWSensorBase(sensorHandle, callback, SensorType::ACCELEROMETER, data) {
-}
-
-Gyroscope::Gyroscope(int32_t sensorHandle, ISensorsEventCallback* callback,
- const struct iio_device_data& data)
- : HWSensorBase(sensorHandle, callback, SensorType::GYROSCOPE, data) {
+ mPollFdIio.events = POLLIN;
+ mSensorRawData.resize(mScanSize);
}
} // namespace implementation
diff --git a/hal/sensors/2.0/Sensor.h b/hal/sensors/2.0/Sensor.h
index b8a927b..8f537ad 100644
--- a/hal/sensors/2.0/Sensor.h
+++ b/hal/sensors/2.0/Sensor.h
@@ -24,14 +24,19 @@
#include <thread>
#include <vector>
#include "iio_utils.h"
+#include "sensor_hal_configuration_V1_0.h"
#define NUM_OF_CHANNEL_SUPPORTED 4
+// Subtract the timestamp channel to get the number of data channels
+#define NUM_OF_DATA_CHANNELS NUM_OF_CHANNEL_SUPPORTED - 1
using ::android::hardware::sensors::V1_0::Event;
using ::android::hardware::sensors::V1_0::OperationMode;
using ::android::hardware::sensors::V1_0::Result;
using ::android::hardware::sensors::V1_0::SensorInfo;
using ::android::hardware::sensors::V1_0::SensorType;
+using ::sensor::hal::configuration::V1_0::AxisType;
+using ::sensor::hal::configuration::V1_0::Configuration;
namespace android {
namespace hardware {
@@ -90,36 +95,31 @@ class SensorBase {
// HWSensorBase represents the actual physical sensor provided as the IIO device
class HWSensorBase : public SensorBase {
public:
- HWSensorBase(int32_t sensorHandle, ISensorsEventCallback* callback, SensorType type,
- const struct iio_device_data& iio_data);
- virtual ~HWSensorBase() = 0;
+ static HWSensorBase* buildSensor(int32_t sensorHandle, ISensorsEventCallback* callback,
+ const struct iio_device_data& iio_data,
+ const std::optional<std::vector<Configuration>>& config);
+ ~HWSensorBase();
void batch(int32_t samplingPeriodNs);
void activate(bool enable);
-
- struct iio_device_data miio_data;
+ struct iio_device_data mIioData;
private:
- ssize_t mscan_size;
- struct pollfd mpollfd_iio;
- std::vector<uint8_t> msensor_raw_data;
+ ssize_t mScanSize;
+ struct pollfd mPollFdIio;
+ std::vector<uint8_t> mSensorRawData;
+ int64_t mXMap, mYMap, mZMap;
+ bool mXNegate, mYNegate, mZNegate;
+
+ HWSensorBase(int32_t sensorHandle, ISensorsEventCallback* callback,
+ const struct iio_device_data& iio_data,
+ const std::optional<std::vector<Configuration>>& config);
ssize_t calculateScanSize();
void run();
+ void setOrientation(std::optional<std::vector<Configuration>> config);
void processScanData(uint8_t* data, Event* evt);
+ void setAxisDefaultValues();
};
-
-class Accelerometer : public HWSensorBase {
- public:
- Accelerometer(int32_t sensorHandle, ISensorsEventCallback* callback,
- const struct iio_device_data& iio_data);
-};
-
-class Gyroscope : public HWSensorBase {
- public:
- Gyroscope(int32_t sensorHandle, ISensorsEventCallback* callback,
- const struct iio_device_data& iio_data);
-};
-
} // namespace implementation
} // namespace subhal
} // namespace V2_0
diff --git a/hal/sensors/2.0/SensorsSubHal.cpp b/hal/sensors/2.0/SensorsSubHal.cpp
index 93fc948..4d80d9f 100644
--- a/hal/sensors/2.0/SensorsSubHal.cpp
+++ b/hal/sensors/2.0/SensorsSubHal.cpp
@@ -13,6 +13,8 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+#define LOG_TAG "GoogleIIOSensorSubHal"
+
#include "SensorsSubHal.h"
#include <android/hardware/sensors/2.0/types.h>
#include <log/log.h>
@@ -32,59 +34,87 @@ namespace implementation {
using ::android::hardware::Void;
using ::android::hardware::sensors::V1_0::Event;
-using ::android::hardware::sensors::V1_0::OperationMode;
using ::android::hardware::sensors::V1_0::RateLevel;
-using ::android::hardware::sensors::V1_0::Result;
using ::android::hardware::sensors::V1_0::SharedMemInfo;
using ::android::hardware::sensors::V2_0::SensorTimeout;
using ::android::hardware::sensors::V2_0::WakeLockQueueFlagBits;
using ::android::hardware::sensors::V2_0::implementation::ScopedWakelock;
+using ::sensor::hal::configuration::V1_0::Sensor;
+using ::sensor::hal::configuration::V1_0::SensorHalConfiguration;
#define SENSOR_SUPPORTED(SENSOR_NAME, SENSOR_TYPE) \
{ .name = SENSOR_NAME, .type = SENSOR_TYPE, }
+#define SENSOR_XML_CONFIG_FILE_NAME "sensor_hal_configuration.xml"
+static const char* gSensorConfigLocationList[] = {"/odm/etc/sensors/", "/vendor/etc/sensors/"};
+static const int gSensorConfigLocationListSize =
+ (sizeof(gSensorConfigLocationList) / sizeof(gSensorConfigLocationList[0]));
+
+#define MODULE_NAME "android.hardware.sensors@2.0-Google-IIO-Subhal"
+
static const std::vector<sensors_supported_hal> sensors_supported = {
SENSOR_SUPPORTED("scmi.iio.accel", SensorType::ACCELEROMETER),
SENSOR_SUPPORTED("scmi.iio.gyro", SensorType::GYROSCOPE),
};
+static std::optional<std::vector<Sensor>> readSensorsConfigFromXml() {
+ for (int i = 0; i < gSensorConfigLocationListSize; i++) {
+ const auto sensor_config_file =
+ std::string(gSensorConfigLocationList[i]) + SENSOR_XML_CONFIG_FILE_NAME;
+ auto sensorConfig = ::sensor::hal::configuration::V1_0::read(sensor_config_file.c_str());
+ if (sensorConfig) {
+ auto modulesList = sensorConfig->getFirstModules()->get_module();
+ for (auto module : modulesList) {
+ if (module.getHalName().compare(MODULE_NAME) == 0) {
+ return module.getFirstSensors()->getSensor();
+ }
+ }
+ }
+ }
+ ALOGI("Could not find the sensors configuration for module %s", MODULE_NAME);
+ return std::nullopt;
+}
+
+static std::optional<std::vector<Configuration>> getSensorConfiguration(
+ const std::vector<Sensor>& sensor_list, const std::string& name, SensorType type) {
+ for (auto sensor : sensor_list) {
+ if ((name.compare(sensor.getName()) == 0) && (type == (SensorType)sensor.getType())) {
+ return sensor.getConfiguration();
+ }
+ }
+ ALOGI("Could not find the sensor configuration for %s ", name.c_str());
+ return std::nullopt;
+}
+
SensorsSubHal::SensorsSubHal() : mCallback(nullptr), mNextHandle(1) {
int err;
std::vector<iio_device_data> iio_devices;
+ const auto sensors_config_list = readSensorsConfigFromXml();
err = load_iio_devices(&iio_devices, sensors_supported);
if (err == 0) {
- for (auto i = 0u; i < iio_devices.size(); i++) {
- err = scan_elements(iio_devices[i].sysfspath, &iio_devices[i]);
+ for (auto& iio_device : iio_devices) {
+ err = scan_elements(iio_device.sysfspath, &iio_device);
if (err == 0) {
- err = enable_sensor(iio_devices[i].sysfspath, false);
+ err = enable_sensor(iio_device.sysfspath, false);
if (err == 0) {
- switch (iio_devices[i].type) {
- case SensorType::ACCELEROMETER:
- if (iio_devices[i].channelInfo.size() == NUM_OF_CHANNEL_SUPPORTED) {
- AddSensor<Accelerometer>(iio_devices[i]);
- } else {
- ALOGE("Unexpected number of channels for Accelerometer");
- }
- break;
-
- case SensorType::GYROSCOPE:
- if (iio_devices[i].channelInfo.size() == NUM_OF_CHANNEL_SUPPORTED) {
- AddSensor<Gyroscope>(iio_devices[i]);
- } else {
- ALOGE("Unexpected number fo channels for Gyroscope");
- }
- break;
-
- default:
- break;
+ std::optional<std::vector<Configuration>> sensor_configuration = std::nullopt;
+ if (sensors_config_list)
+ sensor_configuration = getSensorConfiguration(
+ *sensors_config_list, iio_device.name, iio_device.type);
+
+ if (iio_device.channelInfo.size() == NUM_OF_CHANNEL_SUPPORTED) {
+ AddSensor(iio_device, sensor_configuration);
+ } else {
+ ALOGE("SensorsSubHal(): Unexpected number of channels for sensor %s",
+ iio_device.sysfspath.c_str());
}
} else {
ALOGE("SensorsSubHal(): Error in enabling_sensor %s to %d error code %d",
- iio_devices[i].sysfspath.c_str(), false, err);
+ iio_device.sysfspath.c_str(), false, err);
}
} else {
ALOGE("SensorsSubHal(): Error in scanning channels for IIO device %s error code %d",
- iio_devices[i].sysfspath.c_str(), err);
+ iio_device.sysfspath.c_str(), err);
}
}
} else {
@@ -185,7 +215,7 @@ Return<void> SensorsSubHal::debug(const hidl_handle& fd, const hidl_vec<hidl_str
stream << "handle: " << info.sensorHandle << std::endl;
stream << "resolution: " << info.resolution << " minDelay: " << info.minDelay
<< " maxDelay:" << info.maxDelay << std::endl;
- stream << "iio path" << hwSensor->miio_data.sysfspath << std::endl;
+ stream << "iio path" << hwSensor->mIioData.sysfspath << std::endl;
}
stream << std::endl;
@@ -206,6 +236,15 @@ void SensorsSubHal::postEvents(const std::vector<Event>& events, bool wakeup) {
ScopedWakelock wakelock = mCallback->createScopedWakelock(wakeup);
mCallback->postEvents(events, std::move(wakelock));
}
+void SensorsSubHal::AddSensor(const struct iio_device_data& iio_data,
+ const std::optional<std::vector<Configuration>>& config) {
+ HWSensorBase* sensor = HWSensorBase::buildSensor(mNextHandle++ /* sensorHandle */,
+ this /* callback */, iio_data, config);
+ if (sensor != nullptr)
+ mSensors[sensor->getSensorInfo().sensorHandle] = std::unique_ptr<SensorBase>(sensor);
+ else
+ ALOGE("Unable to add sensor %s as buildSensor returned null", iio_data.name.c_str());
+}
} // namespace implementation
} // namespace subhal
diff --git a/hal/sensors/2.0/SensorsSubHal.h b/hal/sensors/2.0/SensorsSubHal.h
index 47d9f98..26a5aad 100644
--- a/hal/sensors/2.0/SensorsSubHal.h
+++ b/hal/sensors/2.0/SensorsSubHal.h
@@ -33,6 +33,8 @@ using ::android::hardware::sensors::V1_0::OperationMode;
using ::android::hardware::sensors::V1_0::Result;
using ::android::hardware::sensors::V2_0::implementation::IHalProxyCallback;
using ::android::hardware::sensors::V2_0::subhal::implementation::ISensorsEventCallback;
+using ::sensor::hal::configuration::V1_0::Configuration;
+
/**
* Implementation of a ISensorsSubHal that can be used as a reference HAL implementation of sensors
* multihal 2.0. See the README file for more details.
@@ -80,15 +82,8 @@ class SensorsSubHal : public ISensorsSubHal, public ISensorsEventCallback {
void postEvents(const std::vector<Event>& events, bool wakeup) override;
protected:
- template <class T>
- void AddSensor(const struct iio_device_data& iio_data) {
- static_assert(std::is_base_of<SensorBase, T>::value == true,
- "AddSensor called for Non-Sensor Type!!");
-
- std::unique_ptr<T> sensor = std::make_unique<T>(mNextHandle++ /* sensorHandle */,
- this /* callback */, iio_data);
- mSensors[sensor->getSensorInfo().sensorHandle] = std::move(sensor);
- }
+ void AddSensor(const struct iio_device_data& iio_data,
+ const std::optional<std::vector<Configuration>>& config);
/**
* A map of the available sensors
diff --git a/hal/sensors/2.0/config/Android.bp b/hal/sensors/2.0/config/Android.bp
new file mode 100644
index 0000000..1067e89
--- /dev/null
+++ b/hal/sensors/2.0/config/Android.bp
@@ -0,0 +1,20 @@
+//
+// Copyright (C) 2020 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.
+
+xsd_config {
+ name: "sensor_hal_configuration_V1_0",
+ srcs: ["sensor_hal_configuration.xsd"],
+ package_name: "sensor.hal.configuration.V1_0",
+}
diff --git a/hal/sensors/2.0/config/api/current.txt b/hal/sensors/2.0/config/api/current.txt
new file mode 100644
index 0000000..ef088c9
--- /dev/null
+++ b/hal/sensors/2.0/config/api/current.txt
@@ -0,0 +1,88 @@
+// Signature format: 2.0
+package sensor.hal.configuration.V1_0 {
+
+ public class AxisType {
+ ctor public AxisType();
+ method public java.math.BigInteger getMap();
+ method public boolean getNegate();
+ method public void setMap(java.math.BigInteger);
+ method public void setNegate(boolean);
+ }
+
+ public class Configuration {
+ ctor public Configuration();
+ method public sensor.hal.configuration.V1_0.Location getLocation();
+ method public sensor.hal.configuration.V1_0.Orientation getOrientation();
+ method public void setLocation(sensor.hal.configuration.V1_0.Location);
+ method public void setOrientation(sensor.hal.configuration.V1_0.Orientation);
+ }
+
+ public class Location {
+ ctor public Location();
+ method public java.math.BigDecimal getX();
+ method public java.math.BigDecimal getY();
+ method public java.math.BigDecimal getZ();
+ method public void setX(java.math.BigDecimal);
+ method public void setY(java.math.BigDecimal);
+ method public void setZ(java.math.BigDecimal);
+ }
+
+ public class Modules {
+ ctor public Modules();
+ method public java.util.List<sensor.hal.configuration.V1_0.Modules.Module> getModule();
+ }
+
+ public static class Modules.Module {
+ ctor public Modules.Module();
+ method public String getHalName();
+ method public float getHalVersion();
+ method public sensor.hal.configuration.V1_0.Sensors getSensors();
+ method public void setHalName(String);
+ method public void setHalVersion(float);
+ method public void setSensors(sensor.hal.configuration.V1_0.Sensors);
+ }
+
+ public class Orientation {
+ ctor public Orientation();
+ method public boolean getRotate();
+ method public sensor.hal.configuration.V1_0.AxisType getX();
+ method public sensor.hal.configuration.V1_0.AxisType getY();
+ method public sensor.hal.configuration.V1_0.AxisType getZ();
+ method public void setRotate(boolean);
+ method public void setX(sensor.hal.configuration.V1_0.AxisType);
+ method public void setY(sensor.hal.configuration.V1_0.AxisType);
+ method public void setZ(sensor.hal.configuration.V1_0.AxisType);
+ }
+
+ public class Sensor {
+ ctor public Sensor();
+ method public sensor.hal.configuration.V1_0.Configuration getConfiguration();
+ method public String getName();
+ method public java.math.BigInteger getType();
+ method public void setConfiguration(sensor.hal.configuration.V1_0.Configuration);
+ method public void setName(String);
+ method public void setType(java.math.BigInteger);
+ }
+
+ public class SensorHalConfiguration {
+ ctor public SensorHalConfiguration();
+ method public sensor.hal.configuration.V1_0.Modules getModules();
+ method public float getVersion();
+ method public void setModules(sensor.hal.configuration.V1_0.Modules);
+ method public void setVersion(float);
+ }
+
+ public class Sensors {
+ ctor public Sensors();
+ method public java.util.List<sensor.hal.configuration.V1_0.Sensor> getSensor();
+ }
+
+ public class XmlParser {
+ ctor public XmlParser();
+ method public static sensor.hal.configuration.V1_0.SensorHalConfiguration read(java.io.InputStream) throws javax.xml.datatype.DatatypeConfigurationException, java.io.IOException, org.xmlpull.v1.XmlPullParserException;
+ method public static String readText(org.xmlpull.v1.XmlPullParser) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
+ method public static void skip(org.xmlpull.v1.XmlPullParser) throws java.io.IOException, org.xmlpull.v1.XmlPullParserException;
+ }
+
+}
+
diff --git a/hal/sensors/2.0/config/api/last_current.txt b/hal/sensors/2.0/config/api/last_current.txt
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/hal/sensors/2.0/config/api/last_current.txt
diff --git a/hal/sensors/2.0/config/api/last_removed.txt b/hal/sensors/2.0/config/api/last_removed.txt
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/hal/sensors/2.0/config/api/last_removed.txt
diff --git a/hal/sensors/2.0/config/api/removed.txt b/hal/sensors/2.0/config/api/removed.txt
new file mode 100644
index 0000000..d802177
--- /dev/null
+++ b/hal/sensors/2.0/config/api/removed.txt
@@ -0,0 +1 @@
+// Signature format: 2.0
diff --git a/hal/sensors/2.0/config/sensor_hal_configuration.xml b/hal/sensors/2.0/config/sensor_hal_configuration.xml
new file mode 100644
index 0000000..cdf8732
--- /dev/null
+++ b/hal/sensors/2.0/config/sensor_hal_configuration.xml
@@ -0,0 +1,52 @@
+<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
+<!-- Copyright (C) 2020 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.
+-->
+
+<sensorHalConfiguration version="1.0" xmlns:xi="http://www.w3.org/2001/XInclude">
+ <modules>
+ <module halName="android.hardware.sensors@2.0-Google-IIO-Subhal" halVersion="2.0">
+ <sensors>
+ <sensor name="scmi.iio.accel" type="1">
+ <configuration>
+ <orientation rotate="true">
+ <x map="0" negate="false"/>
+ <y map="1" negate="true"/>
+ <z map="2" negate="true"/>
+ </orientation>
+ <location>
+ <x>0</x>
+ <y>0</y>
+ <z>0</z>
+ </location>
+ </configuration>
+ </sensor>
+ <sensor name="scmi.iio.gyro" type="4">
+ <configuration>
+ <orientation rotate="true">
+ <x map="0" negate="false"/>
+ <y map="1" negate="true"/>
+ <z map="2" negate="true"/>
+ </orientation>
+ <location>
+ <x>0</x>
+ <y>0</y>
+ <z>0</z>
+ </location>
+ </configuration>
+ </sensor>
+ </sensors>
+ </module>
+ </modules>
+</sensorHalConfiguration>
diff --git a/hal/sensors/2.0/config/sensor_hal_configuration.xsd b/hal/sensors/2.0/config/sensor_hal_configuration.xsd
new file mode 100644
index 0000000..78a42e6
--- /dev/null
+++ b/hal/sensors/2.0/config/sensor_hal_configuration.xsd
@@ -0,0 +1,78 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2020 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.
+-->
+<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
+ <xs:complexType name="axisType">
+ <xs:attribute name="map" type="xs:positiveInteger" use="required"/>
+ <xs:attribute name="negate" type="xs:boolean" use="required"/>
+ </xs:complexType>
+ <xs:complexType name="orientation">
+ <xs:sequence>
+ <xs:element name="x" type="axisType"/>
+ <xs:element name="y" type="axisType"/>
+ <xs:element name="z" type="axisType"/>
+ </xs:sequence>
+ <xs:attribute name="rotate" type="xs:boolean" use="required"/>
+ </xs:complexType>
+ <xs:complexType name="location">
+ <xs:sequence>
+ <xs:element name="x" type="xs:decimal"/>
+ <xs:element name="y" type="xs:decimal"/>
+ <xs:element name="z" type="xs:decimal"/>
+ </xs:sequence>
+ </xs:complexType>
+ <xs:complexType name="configuration">
+ <xs:sequence>
+ <xs:element name="orientation" type="orientation" />
+ <xs:element name="location" type="location" />
+ </xs:sequence>
+ </xs:complexType>
+ <!-- attribute type describes the sensor type. Possible values are the Enum
+ values of SensorType specified in hardware/interfaces/sensors/1.0/types.hal
+ -->
+ <xs:complexType name="sensor">
+ <xs:sequence>
+ <xs:element name="configuration" type="configuration"/>
+ </xs:sequence>
+ <xs:attribute name="name" type="xs:string" use="required"/>
+ <xs:attribute name="type" type="xs:positiveInteger" use="required"/>
+ </xs:complexType>
+ <xs:complexType name="sensors">
+ <xs:sequence>
+ <xs:element name="sensor" type="sensor" maxOccurs="unbounded"/>
+ </xs:sequence>
+ </xs:complexType>
+ <xs:complexType name="modules">
+ <xs:sequence>
+ <xs:element name="module" maxOccurs="unbounded">
+ <xs:complexType>
+ <xs:sequence>
+ <xs:element name="sensors" type="sensors"/>
+ </xs:sequence>
+ <xs:attribute name="halName" type="xs:string" use="required"/>
+ <xs:attribute name="halVersion" type="xs:float" use="required"/>
+ </xs:complexType>
+ </xs:element>
+ </xs:sequence>
+ </xs:complexType>
+ <xs:element name="sensorHalConfiguration">
+ <xs:complexType>
+ <xs:sequence>
+ <xs:element name="modules" type="modules"/>
+ </xs:sequence>
+ <xs:attribute type="xs:float" name="version" use="required"/>
+ </xs:complexType>
+ </xs:element>
+</xs:schema>
diff --git a/hal/sensors/2.0/iio_utils.cpp b/hal/sensors/2.0/iio_utils.cpp
index c6ff53a..6e31e5f 100644
--- a/hal/sensors/2.0/iio_utils.cpp
+++ b/hal/sensors/2.0/iio_utils.cpp
@@ -13,6 +13,7 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+#define LOG_TAG "GoogleIIOSensorSubHal"
#include "iio_utils.h"
#include <errno.h>