Search code examples
androidlinuxlinux-kernelandroid-sensorsiio

How to read data from LSM330 in /dev/iio:deviceX?


I am trying to interface a LSM330 accelerometer/gyroscope module on an i.MX6 board. The module is connected to an I2C bus, the relevant parts of the device tree file are as follows:

&i2c1 {
    clock-frequency = <100000>;
    pinctrl-names = "default";
    pinctrl-0 = <&pinctrl_i2c1_2>;
    status = "okay";

    /* LSM330 motion detector (accelerometer) */
    lsm330_accel: lsm330_accel@0x1e {
        compatible = "st,lsm330-accel";
        st,drdy-int-pin = <1>;
        reg = <0x1e>;
    };

    /* LSM330 motion detector (gyroscope) */
    lsm330_gyro: lsm330_gyro@0x6a {
        compatible = "st,lsm330-gyro";
        st,drdy-int-pin = <2>;
        reg = <0x6a>;
    };
};

The module shows up as /dev/iio:device0 for the accelerometer and /dev/iio:device1 for the gyroscope. They also show up as /sys/bus/iio/devices/iio:device0and /sys/bus/iio/devices/iio:device1. I can get the sensor readings via cat in_accel_x_raw etc. However, running cat /dev/iio:device0 immediately returns and produce no output.

After searching around the Internet, I also tried the commands:

cd /sys/bus/iio/devices/iio_sysfs_trigger
echo 0 > add_trigger
cd /sys/bus/iio/devices/iio:device0
echo 1 > scan_elements/in_accel_x_en
echo 1 > scan_elements/in_accel_y_en
echo 1 > scan_elements/in_accel_z_en
echo 1 > scan_elements/in_timestamp_en
echo sysfstrig0 > trigger/current_trigger
echo 100 > buffer/length
echo 1 > buffer/enable
echo 1 > /sys/bus/iio/devices/trigger0/trigger_now

This should set the channels, enable the buffer and get some readings into the buffer. As far as I know, cat /dev/iio:device0 should display the buffer, but it is giving me Device or resource busy. Further reads from the kernel with cat /sys/bus/iio/devices/iio:device0/in_accel_x_raw no longer works and give the same error message.

I am very new to the linux kernel, my goal is to expose the sensor data to the Android system so the user can rotate the screen etc. How do I get Android to obtain sensor readings from the module?


Solution

  • After looking at the android logcat, it turns out the Android HAL does not have permissions to read or write to the directories in the sysfs. I ended up putting a bunch of chmod commands in the init.rc file so Android can access the sensor data.

    # Change permissions for the LSM330 sysfs entries (accelerometer)
    chmod 0666 /sys/bus/iio/devices/iio\:device0/sampling_frequency
    chmod 0666 /sys/bus/iio/devices/iio\:device0/buffer/enable
    chmod 0666 /sys/bus/iio/devices/iio\:device0/buffer/length
    chmod 0666 /sys/bus/iio/devices/iio\:device0/trigger/current_trigger
    chmod 0666 /sys/bus/iio/devices/iio\:device0/scan_elements/in_accel_x_en
    chmod 0666 /sys/bus/iio/devices/iio\:device0/scan_elements/in_accel_y_en
    chmod 0666 /sys/bus/iio/devices/iio\:device0/scan_elements/in_accel_z_en
    chmod 0666 /sys/bus/iio/devices/iio\:device0/scan_elements/in_timestamp_en
    chmod 0666 /dev/iio\:device0
    

    Hope this helps someone.