autorope / donkeycar

Open source hardware and software platform to build a small scale self driving car.
http://www.donkeycar.com
MIT License
3.13k stars 1.29k forks source link

When using the mpu9250-jmdev library with the mpu9250 IMU an OSError: [Errno 121] Remote I/O error occurs when attempting to access the magnetometer #1190

Open TCIII opened 3 months ago

TCIII commented 3 months ago

Hardware: RPi 4B 4GB OS: Bullseye DC: v5.0.dev3 MPU: mpu9250 on Robo HAT MM1 at hex address 0x69

IMU configuration in myconfig.py:

# IMU for imu model
HAVE_IMU = True
IMU_SENSOR = 'mpu9250'          # (mpu6050|mpu9250)
IMU_ADDRESS = 0x69
IMU_DLP_CONFIG = 3

Result when running manage.py drive from the CLI:

using donkey v5.0.dev3 ...
INFO:donkeycar.config:loading config file: /home/tciii/mycar/config.py
INFO:donkeycar.config:loading personal config over-rides from myconfig.py
Traceback (most recent call last):
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 96, in configure
    self.configureAK8963(self.mfs, self.mode)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 232, in configureAK8963
    self.writeAK(AK8963_CNTL1, 0x00, 0.1)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 1012, in writeAK
    self.bus.write_byte_data(self.address_ak, register, value)
  File "/usr/local/lib/python3.9/dist-packages/smbus2/smbus2.py", line 455, in write_byte_data
    ioctl(self.fd, I2C_SMBUS, msg)
OSError: [Errno 121] Remote I/O error

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 96, in configure
    self.configureAK8963(self.mfs, self.mode)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 232, in configureAK8963
    self.writeAK(AK8963_CNTL1, 0x00, 0.1)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 1012, in writeAK
    self.bus.write_byte_data(self.address_ak, register, value)
  File "/usr/local/lib/python3.9/dist-packages/smbus2/smbus2.py", line 455, in write_byte_data
    ioctl(self.fd, I2C_SMBUS, msg)
OSError: [Errno 121] Remote I/O error

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/home/tciii/mycar/manage.py", line 494, in <module>
    drive(cfg, use_joystick=args['--js'], camera_type=args['--camera'])
  File "/home/tciii/mycar/manage.py", line 113, in drive
    add_imu(V, cfg)
  File "/home/tciii/projects/donkeycar/donkeycar/templates/complete.py", line 917, in add_imu
    imu = IMU(sensor=cfg.IMU_SENSOR, addr=cfg.IMU_ADDRESS,
  File "/home/tciii/projects/donkeycar/donkeycar/parts/imu.py", line 55, in __init__
    self.sensor.configure()
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 101, in configure
    self.configure(retry - 1)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 101, in configure
    self.configure(retry - 1)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 104, in configure
    raise err
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 96, in configure
    self.configureAK8963(self.mfs, self.mode)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 232, in configureAK8963
    self.writeAK(AK8963_CNTL1, 0x00, 0.1)
  File "/home/tciii/env/lib/python3.9/site-packages/mpu9250_jmdev/mpu_9250.py", line 1012, in writeAK
    self.bus.write_byte_data(self.address_ak, register, value)
  File "/usr/local/lib/python3.9/dist-packages/smbus2/smbus2.py", line 455, in write_byte_data
    ioctl(self.fd, I2C_SMBUS, msg)
OSError: [Errno 121] Remote I/O error

Since the mpu9250 is a combination of the mpu6050 imu and the the AK8963 magnetometer, using the mpu6050-raspberrypi library in place of the mpu9250-jmdev library allows error free access to only the mpu6050 imu.

TCIII

TCIII commented 3 months ago

A recommended solution for the Remote I/O error that occurs when attempting to access the AK8963 magnetometer on the mpu9250 imu/magnetometer module is to use the imusensor library in place of the mpu9250-jmdev library,

Additionally, an in-depth tutorial for using the imusensor library with the RPi and the mpu9250 imu/magnetometer can be found here.

Error free access to both the mpu6050 imu and the AK8963 magnetometer when using the imusensor library was validated using the following code snippet:

import os
import sys
import time
import smbus

from imusensor.MPU9250 import MPU9250

address = 0x68
bus = smbus.SMBus(1)
imu = MPU9250.MPU9250(bus, address)
imu.begin()

while True:
    imu.readSensor()
    imu.computeOrientation()

    print ("Accel x: {0} ; Accel y : {1} ; Accel z : {2}".format(imu.AccelVals[0], imu.AccelVals[1], imu.AccelVals[2]))
    print ("Gyro x: {0} ; Gyro y : {1} ; Gyro z : {2}".format(imu.GyroVals[0], imu.GyroVals[1], imu.GyroVals[2]))
    print ("Mag x: {0} ; Mag y : {1} ; Mag z : {2}".format(imu.MagVals[0], imu.MagVals[1], imu.MagVals[2]))
    print ("roll: {0} ; pitch : {1} ; yaw : {2}".format(imu.roll, imu.pitch, imu.yaw))
    time.sleep(0.1)

I did have to install the easydict module, which was not mentioned in the prerequisites, to get the python code to run.

When running this code snippet the CLI displayed uncalibrated imu and magnetometer values without an I/O error. To use the imusensor library with the Donkey Car imu.py part will require a rewrite of the mpu9250 def to remove references to the mpu9250-jmdev library and replace them with the imusensor library.

TCIII