Library containing Crazyflie 2.0 sensors drivers: - LPS25H (barometer) - MPU9250 (IMU) - PMW3901 (optical flow) - VL53L0X (range)
Dependents: Drones-Controlador controladoatitude_cteste Drone_Controlador_Atitude optical_test
MPU9250/MPU9250.cpp@8:930aa9d0f5ae, 2018-05-14 (annotated)
- Committer:
- fbob
- Date:
- Mon May 14 20:18:20 2018 +0000
- Revision:
- 8:930aa9d0f5ae
- Child:
- 9:350a1d643ef1
Update init functions
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
fbob | 8:930aa9d0f5ae | 1 | #include "MPU9250.h" |
fbob | 8:930aa9d0f5ae | 2 | |
fbob | 8:930aa9d0f5ae | 3 | /** Class constructor */ |
fbob | 8:930aa9d0f5ae | 4 | MPU9250::MPU9250(PinName sda, PinName scl) : i2c(sda, scl) |
fbob | 8:930aa9d0f5ae | 5 | { |
fbob | 8:930aa9d0f5ae | 6 | } |
fbob | 8:930aa9d0f5ae | 7 | |
fbob | 8:930aa9d0f5ae | 8 | /** Try to initialize sensor (return true if succeed and false if failed) */ |
fbob | 8:930aa9d0f5ae | 9 | bool MPU9250::init() |
fbob | 8:930aa9d0f5ae | 10 | { |
fbob | 8:930aa9d0f5ae | 11 | // Setup I2C bus |
fbob | 8:930aa9d0f5ae | 12 | setup_i2c(); |
fbob | 8:930aa9d0f5ae | 13 | |
fbob | 8:930aa9d0f5ae | 14 | // Test I2C bus |
fbob | 8:930aa9d0f5ae | 15 | if (test_i2c()) { |
fbob | 8:930aa9d0f5ae | 16 | // Setup accelerometer and gyroscope configurations |
fbob | 8:930aa9d0f5ae | 17 | setup_accel(); |
fbob | 8:930aa9d0f5ae | 18 | setup_gyro(); |
fbob | 8:930aa9d0f5ae | 19 | // Setup auxiliary I2C bus pins |
fbob | 8:930aa9d0f5ae | 20 | setup_aux_i2c(); |
fbob | 8:930aa9d0f5ae | 21 | return true; |
fbob | 8:930aa9d0f5ae | 22 | } else { |
fbob | 8:930aa9d0f5ae | 23 | return false; |
fbob | 8:930aa9d0f5ae | 24 | } |
fbob | 8:930aa9d0f5ae | 25 | } |
fbob | 8:930aa9d0f5ae | 26 | |
fbob | 8:930aa9d0f5ae | 27 | /** Read sensor data */ |
fbob | 8:930aa9d0f5ae | 28 | void MPU9250::read() |
fbob | 8:930aa9d0f5ae | 29 | { |
fbob | 8:930aa9d0f5ae | 30 | // Read accelerometer and gyroscope data |
fbob | 8:930aa9d0f5ae | 31 | read_accel(); |
fbob | 8:930aa9d0f5ae | 32 | read_gyro(); |
fbob | 8:930aa9d0f5ae | 33 | } |
fbob | 8:930aa9d0f5ae | 34 | |
fbob | 8:930aa9d0f5ae | 35 | /** Setup I2C bus */ |
fbob | 8:930aa9d0f5ae | 36 | void MPU9250::setup_i2c() |
fbob | 8:930aa9d0f5ae | 37 | { |
fbob | 8:930aa9d0f5ae | 38 | // Setup I2C bus frequency to 100kHz |
fbob | 8:930aa9d0f5ae | 39 | i2c.frequency(400000); |
fbob | 8:930aa9d0f5ae | 40 | } |
fbob | 8:930aa9d0f5ae | 41 | |
fbob | 8:930aa9d0f5ae | 42 | /** Test I2C bus */ |
fbob | 8:930aa9d0f5ae | 43 | bool MPU9250::test_i2c() |
fbob | 8:930aa9d0f5ae | 44 | { |
fbob | 8:930aa9d0f5ae | 45 | // Read device identity |
fbob | 8:930aa9d0f5ae | 46 | uint8_t device_id = read_reg(WHO_AM_I); |
fbob | 8:930aa9d0f5ae | 47 | |
fbob | 8:930aa9d0f5ae | 48 | // Check if device identity is 0x71 |
fbob | 8:930aa9d0f5ae | 49 | if (device_id == 0x71) { |
fbob | 8:930aa9d0f5ae | 50 | return true; |
fbob | 8:930aa9d0f5ae | 51 | } else { |
fbob | 8:930aa9d0f5ae | 52 | return false; |
fbob | 8:930aa9d0f5ae | 53 | } |
fbob | 8:930aa9d0f5ae | 54 | } |
fbob | 8:930aa9d0f5ae | 55 | |
fbob | 8:930aa9d0f5ae | 56 | /** Setup auxiliary I2C bus pins */ |
fbob | 8:930aa9d0f5ae | 57 | void MPU9250::setup_aux_i2c() |
fbob | 8:930aa9d0f5ae | 58 | { |
fbob | 8:930aa9d0f5ae | 59 | // Write |
fbob | 8:930aa9d0f5ae | 60 | write_reg(INT_PIN_CFG, 0b00000010); |
fbob | 8:930aa9d0f5ae | 61 | } |
fbob | 8:930aa9d0f5ae | 62 | |
fbob | 8:930aa9d0f5ae | 63 | /** Setup accelerometer configurations (full-scale range) */ |
fbob | 8:930aa9d0f5ae | 64 | void MPU9250::setup_accel(accel_scale a_scale) |
fbob | 8:930aa9d0f5ae | 65 | { |
fbob | 8:930aa9d0f5ae | 66 | // Write configuration data |
fbob | 8:930aa9d0f5ae | 67 | write_reg(ACCEL_CONFIG_1, (0b000 << 5) | (a_scale << 3) | 0b000); |
fbob | 8:930aa9d0f5ae | 68 | |
fbob | 8:930aa9d0f5ae | 69 | // Adjust resolution [m/s^2 / bit] accordingly to choose scale (g) |
fbob | 8:930aa9d0f5ae | 70 | switch (a_scale) { |
fbob | 8:930aa9d0f5ae | 71 | case ACCEL_SCALE_2G: |
fbob | 8:930aa9d0f5ae | 72 | a_res = (2.0f*GRAVITY)/32768.0f; |
fbob | 8:930aa9d0f5ae | 73 | break; |
fbob | 8:930aa9d0f5ae | 74 | case ACCEL_SCALE_4G: |
fbob | 8:930aa9d0f5ae | 75 | a_res = (4.0f*GRAVITY)/32768.0f; |
fbob | 8:930aa9d0f5ae | 76 | break; |
fbob | 8:930aa9d0f5ae | 77 | case ACCEL_SCALE_8G: |
fbob | 8:930aa9d0f5ae | 78 | a_res = (8.0f*GRAVITY)/32768.0f; |
fbob | 8:930aa9d0f5ae | 79 | break; |
fbob | 8:930aa9d0f5ae | 80 | case ACCEL_SCALE_16G: |
fbob | 8:930aa9d0f5ae | 81 | a_res = (16.0f*GRAVITY)/32768.0f; |
fbob | 8:930aa9d0f5ae | 82 | break; |
fbob | 8:930aa9d0f5ae | 83 | } |
fbob | 8:930aa9d0f5ae | 84 | } |
fbob | 8:930aa9d0f5ae | 85 | |
fbob | 8:930aa9d0f5ae | 86 | /** Setup gyroscope configurations (full-scale range) */ |
fbob | 8:930aa9d0f5ae | 87 | void MPU9250::setup_gyro(gyro_scale g_scale) |
fbob | 8:930aa9d0f5ae | 88 | { |
fbob | 8:930aa9d0f5ae | 89 | // Write configuration data |
fbob | 8:930aa9d0f5ae | 90 | write_reg(GYRO_CONFIG, (0b000 << 5) | (g_scale << 3) | 0b000); |
fbob | 8:930aa9d0f5ae | 91 | |
fbob | 8:930aa9d0f5ae | 92 | // Adjust resolution [rad/s / bit] accordingly to choose scale |
fbob | 8:930aa9d0f5ae | 93 | switch (g_scale) { |
fbob | 8:930aa9d0f5ae | 94 | case GYRO_SCALE_250DPS: |
fbob | 8:930aa9d0f5ae | 95 | g_res = (250.0f*(PI/180.0f))/32768.0f; |
fbob | 8:930aa9d0f5ae | 96 | break; |
fbob | 8:930aa9d0f5ae | 97 | case GYRO_SCALE_500DPS: |
fbob | 8:930aa9d0f5ae | 98 | g_res = (500.0f*(PI/180.0f))/32768.0f; |
fbob | 8:930aa9d0f5ae | 99 | break; |
fbob | 8:930aa9d0f5ae | 100 | case GYRO_SCALE_1000DPS: |
fbob | 8:930aa9d0f5ae | 101 | g_res = (1000.0f*(PI/180.0f))/32768.0f; |
fbob | 8:930aa9d0f5ae | 102 | break; |
fbob | 8:930aa9d0f5ae | 103 | case GYRO_SCALE_2000DPS: |
fbob | 8:930aa9d0f5ae | 104 | g_res = (2000.0f*(PI/180.0f))/32768.0f; |
fbob | 8:930aa9d0f5ae | 105 | break; |
fbob | 8:930aa9d0f5ae | 106 | } |
fbob | 8:930aa9d0f5ae | 107 | } |
fbob | 8:930aa9d0f5ae | 108 | |
fbob | 8:930aa9d0f5ae | 109 | /** Read accelerometer output data */ |
fbob | 8:930aa9d0f5ae | 110 | void MPU9250::read_accel() |
fbob | 8:930aa9d0f5ae | 111 | { |
fbob | 8:930aa9d0f5ae | 112 | // Read raw data (two 8 bit data for each axis) |
fbob | 8:930aa9d0f5ae | 113 | uint8_t ax_raw_h = read_reg(ACCEL_XOUT_H); |
fbob | 8:930aa9d0f5ae | 114 | uint8_t ax_raw_l = read_reg(ACCEL_XOUT_L); |
fbob | 8:930aa9d0f5ae | 115 | uint8_t ay_raw_h = read_reg(ACCEL_YOUT_H); |
fbob | 8:930aa9d0f5ae | 116 | uint8_t ay_raw_l = read_reg(ACCEL_YOUT_L); |
fbob | 8:930aa9d0f5ae | 117 | uint8_t az_raw_h = read_reg(ACCEL_ZOUT_H); |
fbob | 8:930aa9d0f5ae | 118 | uint8_t az_raw_l = read_reg(ACCEL_ZOUT_L); |
fbob | 8:930aa9d0f5ae | 119 | |
fbob | 8:930aa9d0f5ae | 120 | // Reassemble raw data (one 16 bit data for each axis) |
fbob | 8:930aa9d0f5ae | 121 | int16_t ax_raw = (ax_raw_h << 8) | ax_raw_l; |
fbob | 8:930aa9d0f5ae | 122 | int16_t ay_raw = (ay_raw_h << 8) | ay_raw_l; |
fbob | 8:930aa9d0f5ae | 123 | int16_t az_raw = (az_raw_h << 8) | az_raw_l; |
fbob | 8:930aa9d0f5ae | 124 | |
fbob | 8:930aa9d0f5ae | 125 | // Convert raw data to SI units [m/s^2] |
fbob | 8:930aa9d0f5ae | 126 | ax = ax_raw * a_res; |
fbob | 8:930aa9d0f5ae | 127 | ay = ay_raw * a_res; |
fbob | 8:930aa9d0f5ae | 128 | az = az_raw * a_res; |
fbob | 8:930aa9d0f5ae | 129 | } |
fbob | 8:930aa9d0f5ae | 130 | |
fbob | 8:930aa9d0f5ae | 131 | /** Read accelerometer data */ |
fbob | 8:930aa9d0f5ae | 132 | void MPU9250::read_gyro() |
fbob | 8:930aa9d0f5ae | 133 | { |
fbob | 8:930aa9d0f5ae | 134 | // Read raw data (two 8 bit data for each axis) |
fbob | 8:930aa9d0f5ae | 135 | uint8_t gx_raw_h = read_reg(GYRO_XOUT_H); |
fbob | 8:930aa9d0f5ae | 136 | uint8_t gx_raw_l = read_reg(GYRO_XOUT_L); |
fbob | 8:930aa9d0f5ae | 137 | uint8_t gy_raw_h = read_reg(GYRO_YOUT_H); |
fbob | 8:930aa9d0f5ae | 138 | uint8_t gy_raw_l = read_reg(GYRO_YOUT_L); |
fbob | 8:930aa9d0f5ae | 139 | uint8_t gz_raw_h = read_reg(GYRO_ZOUT_H); |
fbob | 8:930aa9d0f5ae | 140 | uint8_t gz_raw_l = read_reg(GYRO_ZOUT_L); |
fbob | 8:930aa9d0f5ae | 141 | |
fbob | 8:930aa9d0f5ae | 142 | // Reassemble raw data (one 16 bit data for each axis) |
fbob | 8:930aa9d0f5ae | 143 | int16_t gx_raw = (gx_raw_h << 8 ) | gx_raw_l; |
fbob | 8:930aa9d0f5ae | 144 | int16_t gy_raw = (gy_raw_h << 8 ) | gy_raw_l; |
fbob | 8:930aa9d0f5ae | 145 | int16_t gz_raw = (gz_raw_h << 8 ) | gz_raw_l; |
fbob | 8:930aa9d0f5ae | 146 | |
fbob | 8:930aa9d0f5ae | 147 | // Convert raw data to SI units [rad/s] |
fbob | 8:930aa9d0f5ae | 148 | gx = gx_raw * g_res; |
fbob | 8:930aa9d0f5ae | 149 | gy = gy_raw * g_res; |
fbob | 8:930aa9d0f5ae | 150 | gz = gz_raw * g_res; |
fbob | 8:930aa9d0f5ae | 151 | } |
fbob | 8:930aa9d0f5ae | 152 | |
fbob | 8:930aa9d0f5ae | 153 | /** Write data into register on MPU9250 I2C bus address */ |
fbob | 8:930aa9d0f5ae | 154 | void MPU9250::write_reg(uint8_t reg, uint8_t data) |
fbob | 8:930aa9d0f5ae | 155 | { |
fbob | 8:930aa9d0f5ae | 156 | // Register address and data that will be writed |
fbob | 8:930aa9d0f5ae | 157 | char i2c_reg_data[2] = {reg, data}; |
fbob | 8:930aa9d0f5ae | 158 | |
fbob | 8:930aa9d0f5ae | 159 | // Point to register address and write data |
fbob | 8:930aa9d0f5ae | 160 | i2c.write(MPU9250_ADDRESS, i2c_reg_data, 2); |
fbob | 8:930aa9d0f5ae | 161 | } |
fbob | 8:930aa9d0f5ae | 162 | |
fbob | 8:930aa9d0f5ae | 163 | /** Read data from register on MPU9250 I2C bus address */ |
fbob | 8:930aa9d0f5ae | 164 | char MPU9250::read_reg(uint8_t reg) |
fbob | 8:930aa9d0f5ae | 165 | { |
fbob | 8:930aa9d0f5ae | 166 | // Register address |
fbob | 8:930aa9d0f5ae | 167 | char i2c_reg[1] = {reg}; |
fbob | 8:930aa9d0f5ae | 168 | // Data that will be readed |
fbob | 8:930aa9d0f5ae | 169 | char i2c_data[1]; |
fbob | 8:930aa9d0f5ae | 170 | |
fbob | 8:930aa9d0f5ae | 171 | // Point to register address |
fbob | 8:930aa9d0f5ae | 172 | i2c.write(MPU9250_ADDRESS, i2c_reg, 1); |
fbob | 8:930aa9d0f5ae | 173 | // Read data |
fbob | 8:930aa9d0f5ae | 174 | i2c.read(MPU9250_ADDRESS, i2c_data, 1); |
fbob | 8:930aa9d0f5ae | 175 | |
fbob | 8:930aa9d0f5ae | 176 | // Return readed data |
fbob | 8:930aa9d0f5ae | 177 | return i2c_data[0]; |
fbob | 8:930aa9d0f5ae | 178 | } |