Introduction
The MPU-6050 is a popular module that contains a temperature sensor, accelerometer, and gyroscope. A user may read the sensor information over I2C or SPI. Two documents are publicly available for reading data out of the IC registers. These are:
Context
Reading individual registers of the IMU over I2C skews samples across time because of bus communication latency. Consequently, a sequential read of the X, Y, and Z axis registers of a sensor are not synchronized. To address this, the device provides a 1024-byte internal FIFO queue. Data configured to be pushed to the queue are pushed together at the sample rate. Hence reading the FIFO yields synchronized data.
See (2), section 7.17:
The MPU-60X0 contains a 1024-byte FIFO register that is accessible via the Serial Interface. The FIFO configuration register determines which data is written into the FIFO. Possible choices include gyro data, accelerometer data, temperature readings, auxiliary sensor readings, and FSYNC input. A FIFO counter keeps track of how many bytes of valid data are contained in the FIFO. The FIFO register supports burst reads. The interrupt function may be used to determine when new data is available
Problem
The datasheets specify that in order to read from the FIFO, you must perform the following:
- Enable the FIFO (bit 6, register
0x6A, Document (1), Section 4.29) - Configure the FIFO with what sensor information to push (register
0x23, Document (1), Section 4.7). I enableXG_FIFO_EN,YG_FIFO_EN,ZG_FIFO_EN, andACCEL_FIFO_ENby setting bits 6, 5, 4, and 3 respectively.
If you have performed these steps, then it claims (Document (1), Section 4.33) that:
Data is written to the FIFO in order of register number (from lowest to highest). If all the FIFO enable flags (see below) are enabled and all External Sensor Data registers (Registers 73 to 96) are associated with a Slave device, the contents of registers 59 through 96 will be written in order at the Sample Rate. The contents of the sensor data registers (Registers 59 to 96) are written into the FIFO buffer when their corresponding FIFO enable flags are set to 1 in FIFO_EN (Register 35).
However, I find that this does not hold true. Given the flags I have enabled in the configuration register, I expect the following sequence to come from the FIFO:
* ----------------------------------------------------------- *
* BYTE # | VALUE | Register (dec) *
* ----------------------------------------------------------- *
* 0 | ACCEL_XOUT[15:8] | 59 *
* 1 | ACCEL_XOUT[7:0] | 60 *
* ----------------------------------------------------------- *
* 2 | ACCEL_YOUT[15:8] | 61 *
* 3 | ACCEL_YOUT[7:0] | 62 *
* ----------------------------------------------------------- *
* 4 | ACCEL_ZOUT[15:8] | 63 *
* 5 | ACCEL_ZOUT[7:0] | 64 *
* ----------------------------------------------------------- *
* 6 | GYRO_XOUT[15:8] | 67 *
* 7 | GYRO_XOUT[7:0] | 68 *
* ----------------------------------------------------------- *
* 8 | GYRO_YOUT[15:8] | 69 *
* 9 | GYRO_YOUT[7:0] | 70 *
* ----------------------------------------------------------- *
* 10 | GYRO_ZOUT[15:8] | 71 *
* 11 | GYRO_ZOUT[7:0] | 72 *
* ----------------------------------------------------------- *
Yet reading 12 bytes from the FIFO does not correspond with the same data when reading individual registers. It also doesn't seem to make much sense when I accelerate the IMU, or rotate it. I therefore am not sure how exactly to read the FIFO. This is the problem I face
Q&A
- Are you sure you are correctly writing to registers?: Yes, I am able to set various configurations such as the sampling rate, interrupts, etc. I am confident I am correctly able to read from the FIFO
- Are you sure there is anything in the FIFO to read?: Yes, I have enabled FIFO overflow interrupts. I currently wait for an interrupt, and then read from the FIFO register.
- Are you checking the FIFO length register before reading? Yes, it contains 1024 bytes (maximum capacity) when the FIFO-overflow interrupt occurs.
- Haven't other people done this before?: Nobody has a concrete explanation on how to read the FIFO (e.g: this similar question on another forum that gets an RTFM). A majority of searchable questions related to reading the FIFO are (a) unanswered, (b) told to use generic XYZ Arduino library (I cannot use it), (c) told to read the data sheet (I have).