CHRE: senosor的使用

Table of Contents

 

chre_api接口

sensor_types.h

chreSensorDataHeader

三轴数据sensor data : chreSensorThreeAxisData

sensor.h

CHRE_EVENT_SENSOR_ACCELEROMETER_DATA

structure containing information about a Sensor: chreSensorInfo

sensor的配置

chreSensorConfigure

怎样获得加速器 sensor数据

获得sensor info

根据sensor type获得 sensor handle

根据sendor handle得到sensor info

chreSensorConfig

sensor数据的处理


chre_api接口

//chre/chre_api/include/chre_api/chre.h
/**
 * @file CHRE的实现者和nanoApps的作者使用chre_api
 * This header file includes all the headers which combine to fully define the
 * interface for the Context Hub Runtime Environment (CHRE).  This interface is
 * of interest to both implementers of CHREs and authors of nanoapps.  The API
 * documentation attempts to address concerns of both.
 */

/**
 * @mainpage
 * CHRE is the Context Hub Runtime Environment.  CHRE is used in Android to run
 * contextual applications, called nanoapps, in a low-power processing domain
 * other than the applications processor that runs Android itself.
 The CHRE
 * API, documented herein, is the common interface exposed to nanoapps for any
 * compatible CHRE implementation.  The CHRE API provides the ability for
 * creating nanoapps that are code-compatible across different CHRE
 * implementations and underlying platforms.

 * @section entry_points Entry points
 *
 * The following entry points are used to bind a nanoapp to the CHRE system, and
 * all three must be implemented by any nanoapp (see chre/nanoapp.h):
 * - nanoappStart: initialization
 * - nanoappHandleEvent: hook for event-driven processing
 * - nanoappEnd: graceful teardown
 * @section threading Threading model
 */

#include
#include
#include
#include
#include
#include
#include
#include
#include
#include

sensor_types.h

描述 sensor的头文件包括sensor_types.h and sensor.h

如Accelerometer,类型是固定的

/**
 * Accelerometer.
 *
 * Generates: CHRE_EVENT_SENSOR_ACCELEROMETER_DATA
 *
 * Note that the ACCELEROMETER_DATA is always the fully calibrated data,
 * including factory calibration and runtime calibration if available.
 */
#define CHRE_SENSOR_TYPE_ACCELEROMETER  UINT8_C(1)

chreSensorDataHeader

用在sensor数据的开头,包含数据采集的时间、数据来着那个sensor, 有多少组数据(batch mode)

struct chreSensorDataHeader {
    /**
     * The base timestamp, in nanoseconds.
     */
    uint64_t baseTimestamp;

    /**
     * The handle of the sensor producing this event.
     */
    uint32_t sensorHandle;

    /**
     * The number elements in the 'readings' array.
     *
     * This must be at least 1.
     */
    uint16_t readingCount;

    /**
     * Reserved bytes.
     *
     * These must be 0.
     */
    uint8_t reserved[2];
};

三轴数据sensor data : chreSensorThreeAxisData

struct chreSensorThreeAxisData {
    /**
     * @see chreSensorDataHeader
     */
    struct chreSensorDataHeader header;
    struct chreSensorThreeAxisSampleData {
        /**
         * @see chreSensorDataHeader
         */
        uint32_t timestampDelta;
        union {
            float values[3];
            float v[3];
            struct {
                float x;
                float y;
                float z;
            };
            float bias[3];
            struct {
                float x_bias;
                float y_bias;
                float z_bias;
            };
        };
    } readings[1];
};

sensor.h

//chre/chre_api/include/chre_api/chre/sensor.h

CHRE_EVENT_SENSOR_ACCELEROMETER_DATA

event类型的定义:某种类型的sensor发送data 事件
#define CHRE_EVENT_SENSOR_ACCELEROMETER_DATA \
    (CHRE_EVENT_SENSOR_DATA_EVENT_BASE + CHRE_SENSOR_TYPE_ACCELEROMETER)

structure containing information about a Sensor: chreSensorInfo

/**
 * A structure containing information about a Sensor.
 *
 * See documentation of individual fields below.
 */
struct chreSensorInfo {
    /**
     * The name of the sensor.
     *
     * A text name, useful for logging/debugging, describing the Sensor.  This
     * is not assured to be unique (i.e. there could be multiple sensors with
     * the name "Temperature").
     *
     * CHRE implementations may not set this as NULL.  An empty
     * string, while discouraged, is legal.
     */
    const char *sensorName;

    /**
     * One of the CHRE_SENSOR_TYPE_* defines above.
     */
    uint8_t sensorType;

    /**
     * Flag indicating if this sensor is on-change.
     *
     * An on-change sensor only generates events when underlying state
     * changes.  This has the same meaning as on-change does in the Android
     * Sensors HAL.  See sensors.h for much more details.
     *
     * A value of 1 indicates this is on-change.  0 indicates this is not
     * on-change.
     */
    uint8_t isOnChange  : 1;

    /**
     * Flag indicating if this sensor is one-shot.
     *
     * A one-shot sensor only triggers a single event, and then automatically
     * disables itself.
     *
     * A value of 1 indicates this is one-shot.  0 indicates this is not
     * on-change.
     */
    uint8_t isOneShot   : 1;
    uint8_t unusedFlags : 6;

    /**
     * The minimum sampling interval supported by this sensor, in nanoseconds.
     *
     * Requests to chreSensorConfigure with a lower interval than this will
     * fail.  If the sampling interval is not applicable to this sensor, this
     * will be set to CHRE_SENSOR_INTERVAL_DEFAULT.
     *
     * This field will be set to 0 when running on CHRE API versions prior to
     * v1.1, indicating that the minimum interval is not known.
     *
     * @since v1.1
     */
    uint64_t minInterval;
};

sensor的配置

下面的注释和代码给出了设置batch mode的方法:关心的参数是sample interval and batch interval

多长时间采集一次数据,多长时间batch mode发送到注册的 app. 

chre提供的接口是

/**
 * Convenience function that wraps chreSensorConfigure but enables batching to
 * be controlled by specifying the desired maximum batch interval rather
 * than maximum sample latency.  Users may find the batch interval to be a more
 * intuitive method of expressing the desired batching behavior.
 *
 * Batch interval is different from latency as the batch interval time is
 * counted starting when the prior event containing a batch of sensor samples is
 * delivered,
while latency starts counting when the first sample is deferred to
 * start collecting a batch
.  In other words, latency ignores the time between
 * the last sample in a batch to the first sample of the next batch, while it's
 * included in the batch interval, as illustrated below.
 *
 *  Time      0      1    2    3     4    5   6     7   8
 *  Batch                   A                B              C
 *  Sample   a1  a2  a3  b1  b2  b3  c1   c2  c3
 *  Latency  [              ]    [             ]   [            ]
 *  BatchInt                 |                  |                |
 *
 * In the diagram, the effective sample interval is 1 time unit, latency is 2
 * time units, and batch interval is 3 time units.

 *
 * @param sensorHandle See chreSensorConfigure#sensorHandle
 * @param mode See chreSensorConfigure#mode
 * @param sampleInterval See chreSensorConfigure#interval, but note that
 *     CHRE_SENSOR_INTERVAL_DEFAULT is not a supported input to this method.
 * @param batchInterval The desired maximum interval, in nanoseconds, between
 *     CHRE enqueuing each batch of sensor samples.
 * @return Same as chreSensorConfigure
 *
 * @see chreSensorConfigure
 *
 * @since v1.1
 */
static inline bool chreSensorConfigureWithBatchInterval(
        uint32_t sensorHandle, enum chreSensorConfigureMode mode,
        uint64_t sampleInterval, uint64_t batchInterval) {
    bool result = false;

    if (sampleInterval != CHRE_SENSOR_INTERVAL_DEFAULT) {
        uint64_t latency;
        if (batchInterval == CHRE_SENSOR_BATCH_INTERVAL_DEFAULT) {
            latency = CHRE_SENSOR_LATENCY_DEFAULT;
        } else if (batchInterval > sampleInterval) {
            latency = batchInterval - sampleInterval;
        } else {
            latency = CHRE_SENSOR_LATENCY_ASAP;
        }
        result = chreSensorConfigure(sensorHandle, mode, sampleInterval, latency);
    }

    return result;
}

chreSensorConfigure

 * @param interval  The interval, in nanoseconds, at which we want events from
 *     the sensor.  On success, the sensor will be set to 'interval', or a value
 *     less than 'interval'.  There is a special value
 *     CHRE_SENSOR_INTERVAL_DEFAULT, in which we don't express a preference for
 *     the interval, and allow the sensor to chose what it wants.  Note that
 *     due to batching, we may receive events less frequently than
 *     'interval'.
 * @param latency  The maximum latency, in nanoseconds, allowed before the
 *     CHRE begins delivery of an event.  This will control how many events
 *     can be queued by the sensor before requiring a delivery event.
 *     Latency is defined as the "timestamp when event is queued by the CHRE"
 *     minus "timestamp of oldest unsent data reading".

 *     Note that there is no assurance of how long it will take an event to
 *     get through a CHRE's queueing system, and thus there is no ability to
 *     request a minimum time from the occurrence of a phenomenon to when the
 *     nanoapp receives the information.  The current CHRE API has no
 *     real-time elements, although future versions may introduce some to
 *     help with this issue.
 * @returns true if the configuration succeeded, false otherwise.
 *
 * @see chreSensorConfigureMode
 * @see chreSensorFindDefault
 * @see chreSensorInfo
 */
bool chreSensorConfigure(uint32_t sensorHandle,
                         enum chreSensorConfigureMode mode,
                         uint64_t interval, uint64_t latency);

怎样获得加速器 sensor数据

获得sensor info

struct SensorState {
  const uint8_t type;
  uint32_t handle;
  bool isInitialized;
  bool enable;
  uint64_t interval;  // nsec
  uint64_t latency;  // nsec
  chreSensorInfo info;
};

SensorState sensors[] = {
  { .type = CHRE_SENSOR_TYPE_ACCELEROMETER,
    .handle = 0,
    .isInitialized = false,
    .enable = kEnableDefault,
    .interval = Milliseconds(80).toRawNanoseconds(),
    .latency = Seconds(4).toRawNanoseconds(),
    .info = {},
  },
}

根据sensor type获得 sensor handle

sensor.isInitialized = chreSensorFindDefault(sensor.type, &sensor.handle);

根据sendor handle得到sensor info

chreSensorInfo& info = sensor.info;
bool infoStatus = chreGetSensorInfo(sensor.handle, &info);

chreSensorConfig

chreSensorConfigure(sensor.handle,
            CHRE_SENSOR_CONFIGURE_MODE_CONTINUOUS, sensor.interval,
            sensor.latency);

  { .sensType =  CHRE_SENSOR_TYPE_ACCELEROMETER,  

      .mode = CHRE_SENSOR_CONFIGURE_MODE_CONTINUOUS,
      .interval = (100000000ull),     // 10 Hz,
      .latency =  (1000000000ull)   // 1 S
    }, 1 秒采集10次数据,1秒发送一次数据

sensor数据的处理

nanoappHandleEvent

/**
 * Method invoked by the CHRE when there is an event for this nanoapp.
 *
 * Every CHRE method is legal to call from this method.
 *
 * @param senderInstanceId  The Instance ID for the source of this event.
 *     Note that this may be CHRE_INSTANCE_ID, indicating that the event
 *     was generated by the CHRE.
 * @param eventType  The event type.  This might be one of the CHRE_EVENT_*
 *     types defined in this API.  But it might also be a user-defined event.
 * @param eventData  The associated data, if any, for this specific type of
 *     event.  From the nanoapp's perspective, this eventData's lifetime ends
 *     when this method returns, and thus any data the nanoapp wishes to
 *     retain must be copied.  Note that interpretation of event data is
 *     given by the event type, and for some events may not be a valid
 *     pointer.  See documentation of the specific CHRE_EVENT_* types for how to
 *     interpret this data for those.  Note that for user events, you will
 *     need to establish what this data means.
 */
void nanoappHandleEvent(uint32_t senderInstanceId, uint16_t eventType,
                        const void *eventData);

 

void nanoappHandleEvent(uint32_t senderInstanceId,
                        uint16_t eventType,
                        const void *eventData) {
  uint64_t chreTime = chreGetTime();
  uint64_t sampleTime;
  switch (eventType) {
    case CHRE_EVENT_SENSOR_ACCELEROMETER_DATA: //通过chre_event_sensor_xxx_data得到data事件
    { //对数据的处理方式各种各样,这只是个对batch data的常规处理
      const auto *ev = static_cast(eventData);
      const auto header = ev->header;
      const auto *data = ev->readings;
      sampleTime = header.baseTimestamp;

      float x = 0, y = 0, z = 0;
      for (size_t i = 0; i < header.readingCount; i++) {
        x += data[i].v[0];
        y += data[i].v[1];
        z += data[i].v[2];
        sampleTime += data[i].timestampDelta;
      }
    }

}

你可能感兴趣的:(人工智能)