Thingy91x ADXL367 Motion Detection Only Triggers Once After Reboot

Environment
Hardware: Thingy:91 X (nRF9151)
SDK: nRF Connect SDK v2.8.0
Zephyr: v4.2.99
Driver: ADXL367 with interrupt-based activity detection
Configuration: CONFIG_ADXL367_TRIGGER_GLOBAL_THREAD=y

Problem Description

Motion detection triggers successfully once after reboot, but then stops working completely. Subsequent motion events are not detected until the device is power cycled.

Expected behavior: Continuous motion detection with callbacks on each motion event
Actual behavior: First motion event works, then silence forever

Current Configuration

// Activity detection settings
CONFIG_ADXL367_ACTIVITY_DETECTION_MODE=y
CONFIG_ADXL367_INACTIVITY_DETECTION_MODE=n
CONFIG_ADXL367_ACTIVITY_THRESHOLD=50 // 50 * 250mg = 12.5g threshold
CONFIG_ADXL367_ACTIVITY_TIME=1 // 1 sample at 100Hz
CONFIG_ADXL367_TRIGGER_GLOBAL_THREAD=y

// Using DEFAULT mode (not LINKED/LOOPED) for activity-only detection

Application Code

static void motion_trigger_handler(const struct device *dev,
const struct sensor_trigger *trigger)
{
LOG_INF("Motion detected! (Activity interrupt)");
// ... callback logic
}

int motion_enable(void)
{
struct sensor_trigger trig = {
.type = SENSOR_TRIG_THRESHOLD,
.chan = SENSOR_CHAN_ACCEL_XYZ,
};

return sensor_trigger_set(accel_dev, &trig, motion_trigger_handler);
}

Debugging Done

Verified interrupt re-enable logic: Modified adxl367_trigger.c to ensure GPIO interrupt is always re-enabled even on STATUS register read failures
Checked processing mode: Using ADXL367_DEFAULT mode (not LINKED) since inactivity detection is disabled
Verified GPIO configuration: INT1 pin configured correctly, first interrupt fires successfully
Added logging: Confirmed STATUS register reads complete and handlers are called

Observations

First motion event: Interrupt fires, handler called, logs appear
Second motion event onwards: No interrupt, no handler, complete silence
After power cycle: First motion works again, then stops

Questions

Does the ADXL367 require special acknowledgment of activity interrupts beyond reading the STATUS register?
Should activity detection be configured differently for continuous triggering?
Are there any undocumented register settings needed for the interrupt to re-arm automatically?
Could this be related to the activity timer (ADXL367_TIME_ACT) with a value of 1 sample?

Request

Has anyone successfully implemented continuous motion detection with the ADXL367 on Zephyr? Any insights into what might cause the interrupt to stop firing after the first trigger would be greatly appreciated.

  • There's basically no way to make it work properly. I'm expecting a solution, this should be a high priority issue. It's clearly not working and it's most definitely not a skill or effort issue. It's DOA with non proper support in the sdk

  • It is suspicious that there is no connection between P0.11 of the nRF9151 and INT1 of the ADXL367 in the Thingy:91X devicetree overlay. I modified the overlay to add this connection.

    On the actual board, INT1 is not only connected to the nRF9151 but also to the nRF5340. I believe the corresponding nRF5340 pin is left floating. Unfortunately, this cannot be verified with a logic analyzer because there is no test point and the trace is routed on the inner layers.

  • Additionally, the AI insists that the Threshold Activity Register and Threshold Inactivity Register use a scale factor of 7.8 mg/LSB (for the +-2g rangebut I could not find any reference to this value in the datasheet.

  • Hi! I also want to use this accelerometer, here is what works for me (based on the accel_trig sample in zephyr, running on a thingy91x' ADXL367)

    # boards/thingy91x_nrf9151_ns.conf

    ```c
    CONFIG_ADXL367_ACTIVITY_DETECTION_MODE=y
    CONFIG_ADXL367_INACTIVITY_DETECTION_MODE=n
    CONFIG_ADXL367_ACTIVITY_THRESHOLD=50
    CONFIG_ADXL367_ACTIVITY_TIME=10
    CONFIG_ADXL367_TRIGGER_GLOBAL_THREAD=y
    ```

    # boards/thingy91x_nrf9151_ns.overlay

    ```c

    / {
        aliases {
            accel0 = &accel;
        };
    };

    &accel {
        status="okay";
    };

    ```

    # src/main.c

    ```c

    /*
     * Copyright 2024 NXP
     * Copyright (c) 2018 Phytec Messtechnik GmbH
     *
     * SPDX-License-Identifier: Apache-2.0
     */

    #include <zephyr/kernel.h>
    #include <zephyr/drivers/sensor.h>
    #include <stdio.h>

    K_SEM_DEFINE(sem, 0, 1); /* starts off "not available" */

    static void tap_trigger_handler(const struct device *dev, const struct sensor_trigger *trigger)
    {
        ARG_UNUSED(trigger);
        printf("TAP detected==========================================================\n\n\n\n\n");

        if (sensor_sample_fetch_chan(dev, SENSOR_CHAN_ACCEL_XYZ) < 0) {
            printf("ERROR: SENSOR_CHAN_ACCEL_XYZ fetch failed\n");
        }

        k_sem_give(&sem);
    }

    int main(void)
    {
        struct sensor_value data[3];
        const struct device *const dev = DEVICE_DT_GET(DT_ALIAS(accel0));

        struct sensor_trigger trig = {
            .type = SENSOR_TRIG_DATA_READY,
            .chan = SENSOR_CHAN_ACCEL_XYZ,
        };

        if (!device_is_ready(dev)) {
            printf("Device %s is not ready\n", dev->name);
            return 0;
        }


        trig.type = SENSOR_TRIG_THRESHOLD;
        trig.chan = SENSOR_CHAN_ACCEL_XYZ;
        if (sensor_trigger_set(dev, &trig, tap_trigger_handler) < 0) {
            printf("Could not set tap trigger\n");
            return 0;
        }


        while (1) {
            k_sem_take(&sem, K_FOREVER);
            sensor_channel_get(dev, SENSOR_CHAN_ACCEL_XYZ, data);

            /* Print accel x,y,z data */
            printf("%16s [m/s^2]:    (%12.6f, %12.6f, %12.6f)\n", dev->name,
                   sensor_value_to_double(&data[0]), sensor_value_to_double(&data[1]),
                   sensor_value_to_double(&data[2]));
        }
    }

    ```

    The sensitivity is just about right to not trigger while the thingy91x is sitting on my desk while I'm typing, but as soon as I pick up the device it triggers a few times.

Related