BMI270 interrupts and register readouts

I'm using the nano ble 33 sense rev2 and I'm trying to get interrupts from the BMI270. Using the arduino_BMI270_BMM150 library interrupts only come in about 50% of the times I restart or reupload the program. I have verified that the value on the data ready register on the BMI270's side changes every 40ms, as expected based on the 25Hz sampling frequency that I set. This also happens in the 50% of cases when the interrupts "don't come through". From the hardware schematics I know that BMI_INT1, the interrupt pin of the BMI, is connected to GPIO32/P0_11 on the NINA module. I want to somehow read what value is on this pin and hence I want to read the register that corresponds to it (if that makes sense). I have searched both the NINA B3 datasheet and that of the microprocessor, but I can't figure it out and don't know exactly where to look. I tried to use digitalRead directly, but by doing so killed the IMU on my previous board (you might notice, I'm not an electronics expert). If I use the attachInterrupt function from Arduino and use P0_11 or p11, nothing happens. How can I find out which register to read or how else can I read the value on p11 without killing my IMU?

Here is my code that will print "Got new data!" at 25Hz, but only in 50% of the cases where I upload the code to my board. Commented out code is an alternative for the line customIMU.onInterrupt(handleInterrupt); by using the arduino attachInterrupt instead of the interrupt handler from the BMI library. With that code, I never get "Got new data!" printed.

#include <Arduino.h>
#include <Arduino_BMI270_BMM150.h>

#define BMI270_I2C_ADRESS 0x68

class MyBoschSensor: public BoschSensorClass {

  public:
    MyBoschSensor(TwoWire& wire = Wire) : BoschSensorClass(wire) {};

  protected:
    virtual int8_t configure_sensor(struct bmi2_dev *dev)
    {
      int8_t rslt;
      uint8_t sens_list[2] = { BMI2_ACCEL, BMI2_GYRO };

      struct bmi2_int_pin_config int_pin_cfg;
      int_pin_cfg.pin_type = BMI2_INT1;
      int_pin_cfg.int_latch = BMI2_INT_NON_LATCH;
      int_pin_cfg.pin_cfg[0].lvl = BMI2_INT_ACTIVE_HIGH;
      int_pin_cfg.pin_cfg[0].od = BMI2_INT_PUSH_PULL;
      int_pin_cfg.pin_cfg[0].output_en = BMI2_INT_OUTPUT_ENABLE;
      int_pin_cfg.pin_cfg[0].input_en = BMI2_INT_INPUT_DISABLE;

      struct bmi2_sens_config sens_cfg[2];
      sens_cfg[0].type = BMI2_ACCEL;
      sens_cfg[0].cfg.acc.bwp = BMI2_ACC_OSR2_AVG2;
      sens_cfg[0].cfg.acc.odr = BMI2_ACC_ODR_25HZ;
      sens_cfg[0].cfg.acc.filter_perf = BMI2_PERF_OPT_MODE;
      sens_cfg[0].cfg.acc.range = BMI2_ACC_RANGE_4G;
      sens_cfg[1].type = BMI2_GYRO;
      sens_cfg[1].cfg.gyr.filter_perf = BMI2_PERF_OPT_MODE;
      sens_cfg[1].cfg.gyr.bwp = BMI2_GYR_OSR2_MODE;
      sens_cfg[1].cfg.gyr.odr = BMI2_GYR_ODR_25HZ;
      sens_cfg[1].cfg.gyr.range = BMI2_GYR_RANGE_2000;
      sens_cfg[1].cfg.gyr.ois_range = BMI2_GYR_OIS_2000;

      rslt = bmi2_set_int_pin_config(&int_pin_cfg, dev);
      if (rslt != BMI2_OK)
        return rslt;

      rslt = bmi2_map_data_int(BMI2_DRDY_INT, BMI2_INT1, dev);
      if (rslt != BMI2_OK)
        return rslt;

      rslt = bmi2_set_sensor_config(sens_cfg, 2, dev);
      if (rslt != BMI2_OK)
        return rslt;

      rslt = bmi2_sensor_enable(sens_list, 2, dev);
      if (rslt != BMI2_OK)
        return rslt;

      return rslt;
    }
};

volatile bool interruptDetected;

MyBoschSensor customIMU(Wire1);

byte readRegister(byte reg) {
  Wire1.beginTransmission(BMI270_I2C_ADRESS);
  Wire1.write(reg);
  Wire1.endTransmission(false);

  Wire1.requestFrom(BMI270_I2C_ADRESS, (byte)1);
  return Wire1.read();
}


void handleInterrupt() {
  interruptDetected = true;
  digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
}

void initializeImu() {
  customIMU.debug(Serial);
  customIMU.onInterrupt(handleInterrupt);
  customIMU.begin();
}

byte registerToRead = 0x1D;
int pin = p11;

void setup() {
  Wire1.begin();
  Serial.begin(9600);
  while (!Serial);

  pinMode(LED_BUILTIN, OUTPUT);
  //pinMode(pin, INPUT);


  initializeImu();
  delay(500);
  
  //attachInterrupt(digitalPinToInterrupt(pin), handleInterrupt, RISING);
  //delay(500);
}

void loop() {
  byte value = readRegister(registerToRead);

  Serial.print("Register value: ");
  Serial.print(": 0x");
  Serial.println(value, HEX);

  if (interruptDetected) {
    Serial.println("Got new data!");
    interruptDetected = false;
  }
}

Hi @naomifleur

I also work on how to enable Interrupt on Arduino Sense Rev2 + BMI270.
Unfortunately, I find that we can only access Dxx pins (those pins which are exposed) by attachedInterrupt().

I checked the official Arduino library you used, seems it only "reads the register" rather than "reads the pin". From my perspective, it is not a real interruption. LOL.

I also check the Arduino source code at "C:\Users\HeLix\AppData\Local\Arduino15\packages\arduino\hardware\mbed_nano\4.0.4\variants\ARDUINO_NANO33BLE" (Windows11), seems that only part of the pins (which are exposed) are defined. Apparently, GPIO32 or P0.11 are not mentioned.

So my conclusion is: Arduino seems not support such an operation. I am not 100% sure I am right.

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.