Skip to content
This repository was archived by the owner on Jun 2, 2025. It is now read-only.

Commit 0034fd3

Browse files
Merge pull request #19 from HeronMkII/imu
IMU updates - lib-common conversions, packet printing
2 parents ddf3d55 + 7023edb commit 0034fd3

File tree

4 files changed

+52
-83
lines changed

4 files changed

+52
-83
lines changed

lib-common

manual_tests/imu_test/imu_test.c

Lines changed: 36 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22
NOTE: SET COOLTERM BAUD RATE TO 115,200
33
*/
44

5+
#include <conversions/conversions.h>
6+
57
#include "../../src/imu.h"
68

79
void receive_and_print_packets(uint16_t count) {
@@ -45,7 +47,7 @@ void test_prod_id(void) {
4547
void test_accel_once(void) {
4648
print("\nGetting acceleration...\n\n");
4749

48-
int16_t x = 0, y = 0, z = 0;
50+
uint16_t x = 0, y = 0, z = 0;
4951
if (!get_imu_accel(&x, &y, &z)) {
5052
print("\nGet acceleration: FAIL\n\n");
5153
return;
@@ -69,7 +71,7 @@ void test_accel_inf(void) {
6971
}
7072

7173
void test_accel_fast_once(void) {
72-
int16_t x = 0, y = 0, z = 0;
74+
uint16_t x = 0, y = 0, z = 0;
7375
get_imu_accel(&x, &y, &z);
7476
print("Acceleration: x = %+.6f, y = %+.6f, z = %+.6f\n",
7577
imu_raw_data_to_double(x, IMU_ACCEL_Q),
@@ -80,8 +82,8 @@ void test_accel_fast_once(void) {
8082
void test_uncal_gyro_once(void) {
8183
print("\nGetting uncalibrated gyroscope...\n\n");
8284

83-
int16_t x = 0, y = 0, z = 0;
84-
int16_t bias_x = 0, bias_y = 0, bias_z = 0;
85+
uint16_t x = 0, y = 0, z = 0;
86+
uint16_t bias_x = 0, bias_y = 0, bias_z = 0;
8587
if (!get_imu_uncal_gyro(&x, &y, &z, &bias_x, &bias_y, &bias_z)) {
8688
print("\nGet uncalibrated gyroscope: FAIL\n\n");
8789
return;
@@ -91,14 +93,14 @@ void test_uncal_gyro_once(void) {
9193
print("Get uncalibrated gyroscope: SUCCESS\n");
9294
print("Raw: x = %d, y = %d, z = %d\n", x, y, z);
9395
print("Converted: x = %.6f, y = %.6f, z = %.6f\n",
94-
imu_raw_data_to_double(x, IMU_UNCAL_GYRO_Q),
95-
imu_raw_data_to_double(y, IMU_UNCAL_GYRO_Q),
96-
imu_raw_data_to_double(z, IMU_UNCAL_GYRO_Q));
96+
imu_raw_data_to_gyro(x),
97+
imu_raw_data_to_gyro(y),
98+
imu_raw_data_to_gyro(z));
9799
print("Raw: bias_x = %d, bias_y = %d, bias_z = %d\n", bias_x, bias_y, bias_z);
98100
print("Converted: bias_x = %.6f, bias_y = %.6f, bias_z = %.6f\n",
99-
imu_raw_data_to_double(bias_x, IMU_UNCAL_GYRO_Q),
100-
imu_raw_data_to_double(bias_y, IMU_UNCAL_GYRO_Q),
101-
imu_raw_data_to_double(bias_z, IMU_UNCAL_GYRO_Q));
101+
imu_raw_data_to_gyro(bias_x),
102+
imu_raw_data_to_gyro(bias_y),
103+
imu_raw_data_to_gyro(bias_z));
102104
print("\n");
103105
}
104106

@@ -110,18 +112,18 @@ void test_uncal_gyro_inf(void) {
110112
}
111113

112114
void test_uncal_gyro_fast_once(void) {
113-
int16_t x = 0, y = 0, z = 0;
115+
uint16_t x = 0, y = 0, z = 0;
114116
get_imu_uncal_gyro(&x, &y, &z, NULL, NULL, NULL);
115117
print("Uncalibrated Gyroscope: x = %+.6f, y = %+.6f, z = %+.6f\n",
116-
imu_raw_data_to_double(x, IMU_UNCAL_GYRO_Q),
117-
imu_raw_data_to_double(y, IMU_UNCAL_GYRO_Q),
118-
imu_raw_data_to_double(z, IMU_UNCAL_GYRO_Q));
118+
imu_raw_data_to_gyro(x),
119+
imu_raw_data_to_gyro(y),
120+
imu_raw_data_to_gyro(z));
119121
}
120122

121123
void test_cal_gyro_once(void) {
122124
print("\nGetting calibrated gyroscope...\n\n");
123125

124-
int16_t x = 0, y = 0, z = 0;
126+
uint16_t x = 0, y = 0, z = 0;
125127
if (!get_imu_cal_gyro(&x, &y, &z)) {
126128
print("\nGet calibrated gyroscope.: FAIL\n\n");
127129
return;
@@ -131,9 +133,9 @@ void test_cal_gyro_once(void) {
131133
print("Get calibrated gyroscope.: SUCCESS\n");
132134
print("Raw: x = %d, y = %d, z = %d\n", x, y, z);
133135
print("Converted: x = %.6f, y = %.6f, z = %.6f\n",
134-
imu_raw_data_to_double(x, IMU_CAL_GYRO_Q),
135-
imu_raw_data_to_double(y, IMU_CAL_GYRO_Q),
136-
imu_raw_data_to_double(z, IMU_CAL_GYRO_Q));
136+
imu_raw_data_to_gyro(x),
137+
imu_raw_data_to_gyro(y),
138+
imu_raw_data_to_gyro(z));
137139
print("\n");
138140
}
139141

@@ -146,38 +148,38 @@ void test_cal_gyro_inf(void) {
146148

147149
// Without success/fail print statements
148150
void test_cal_gyro_fast_once(void) {
149-
int16_t x = 0, y = 0, z = 0;
151+
uint16_t x = 0, y = 0, z = 0;
150152
get_imu_cal_gyro(&x, &y, &z);
151153
print("Calibrated Gyroscope: x = %+.6f, y = %+.6f, z = %+.6f\n",
152-
imu_raw_data_to_double(x, IMU_CAL_GYRO_Q),
153-
imu_raw_data_to_double(y, IMU_CAL_GYRO_Q),
154-
imu_raw_data_to_double(z, IMU_CAL_GYRO_Q));
154+
imu_raw_data_to_gyro(x),
155+
imu_raw_data_to_gyro(y),
156+
imu_raw_data_to_gyro(z));
155157
}
156158

157159
// Compare uncalibrated with calibrated
158160
void test_gyro_comp_inf(void) {
159161
print("\nGetting gyroscope...\n\n");
160162

161163
while (1) {
162-
int16_t uncal_x = 0, uncal_y = 0, uncal_z = 0;
163-
int16_t bias_x = 0, bias_y = 0, bias_z = 0;
164+
uint16_t uncal_x = 0, uncal_y = 0, uncal_z = 0;
165+
uint16_t bias_x = 0, bias_y = 0, bias_z = 0;
164166
get_imu_uncal_gyro(&uncal_x, &uncal_y, &uncal_z, &bias_x, &bias_y, &bias_z);
165-
int16_t cal_x = 0, cal_y = 0, cal_z = 0;
167+
uint16_t cal_x = 0, cal_y = 0, cal_z = 0;
166168
get_imu_cal_gyro(&cal_x, &cal_y, &cal_z);
167169

168170
print("\n");
169171
print("Uncalibrated: x = %+.6f, y = %+.6f, z = %+.6f\n",
170-
imu_raw_data_to_double(uncal_x, IMU_UNCAL_GYRO_Q),
171-
imu_raw_data_to_double(uncal_y, IMU_UNCAL_GYRO_Q),
172-
imu_raw_data_to_double(uncal_z, IMU_UNCAL_GYRO_Q));
172+
imu_raw_data_to_gyro(uncal_x),
173+
imu_raw_data_to_gyro(uncal_y),
174+
imu_raw_data_to_gyro(uncal_z));
173175
print("Calibrated: x = %+.6f, y = %+.6f, z = %+.6f\n",
174-
imu_raw_data_to_double(cal_x, IMU_CAL_GYRO_Q),
175-
imu_raw_data_to_double(cal_y, IMU_CAL_GYRO_Q),
176-
imu_raw_data_to_double(cal_z, IMU_CAL_GYRO_Q));
176+
imu_raw_data_to_gyro(cal_x),
177+
imu_raw_data_to_gyro(cal_y),
178+
imu_raw_data_to_gyro(cal_z));
177179
print("Bias: x = %+.6f, y = %+.6f, z = %+.6f\n",
178-
imu_raw_data_to_double(bias_x, IMU_UNCAL_GYRO_Q),
179-
imu_raw_data_to_double(bias_y, IMU_UNCAL_GYRO_Q),
180-
imu_raw_data_to_double(bias_z, IMU_UNCAL_GYRO_Q));
180+
imu_raw_data_to_gyro(bias_x),
181+
imu_raw_data_to_gyro(bias_y),
182+
imu_raw_data_to_gyro(bias_z));
181183
}
182184
}
183185

src/imu.c

Lines changed: 10 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -159,20 +159,6 @@ uint8_t imu_data[IMU_DATA_MAX_LEN] = { 0x00 };
159159
uint16_t imu_data_len = 0;
160160

161161

162-
163-
164-
// TODO - modify lib-common print_bytes, fix uint16_t bug for len/i
165-
void print_hex(uint8_t* data, uint16_t len) {
166-
if (len == 0) {
167-
return;
168-
}
169-
print("%.2x", data[0]);
170-
for (uint16_t i = 1; i < len; i++) {
171-
print(":%.2x", data[i]);
172-
}
173-
print("\n");
174-
}
175-
176162
/*
177163
Initializes the IMU (#0 p. 43).
178164
*/
@@ -361,9 +347,9 @@ uint8_t receive_imu_packet(void) {
361347
#ifdef IMU_DEBUG
362348
print("data_len = %u\n", data_len);
363349
print("Header: ");
364-
print_hex(imu_header, IMU_HEADER_LEN);
350+
print_bytes(imu_header, IMU_HEADER_LEN);
365351
print("Data: ");
366-
print_hex(imu_data, imu_data_len);
352+
print_bytes(imu_data, imu_data_len);
367353

368354
// Print data as string
369355
// for (uint16_t i = 0; i < imu_data_len; i++) {
@@ -407,9 +393,9 @@ uint8_t send_imu_packet(uint8_t channel) {
407393
#ifdef IMU_DEBUG
408394
print("\nSending IMU SPI:\n");
409395
print("Header: ");
410-
print_hex(imu_header, IMU_HEADER_LEN);
396+
print_bytes(imu_header, IMU_HEADER_LEN);
411397
print("Data: ");
412-
print_hex(imu_data, imu_data_len);
398+
print_bytes(imu_data, imu_data_len);
413399
#endif
414400

415401
// Set feature command (#1 p.55-56)
@@ -509,25 +495,13 @@ uint8_t disable_imu_feat(uint8_t feat_report_id) {
509495
return send_imu_set_feat_cmd(feat_report_id, 0);
510496
}
511497

512-
/*
513-
Converts the raw 16-bit signed fixed-point value from the input report to the actual floating-point measurement using the Q point.
514-
Q point - number of fractional digits after (to the right of) the decimal point, i.e. higher Q point means smaller/more precise number (#1 p.22)
515-
https://en.wikipedia.org/wiki/Q_(number_format)
516-
Similar to reference library qToFloat()
517-
raw_data - 16 bit raw value
518-
q_point - number of binary digits to shift
519-
*/
520-
double imu_raw_data_to_double(int16_t raw_data, uint8_t q_point) {
521-
// Implement power of 2 with a bitshift instead of pow(), which links to the
522-
// math library and increases the binary size by ~1.3kB
523-
return ((double) raw_data) / ((double) (1 << q_point));
524-
}
498+
525499

526500
/*
527501
Enables a feature, gets one input report, and disables the feature.
528502
This only works for features that provide an input report of 5 bytes (timebase reference) + 10 bytes (sensor data, last 6 bytes are x/y/z)
529503
*/
530-
uint8_t get_imu_data(uint8_t feat_report_id, int16_t* x, int16_t* y, int16_t* z) {
504+
uint8_t get_imu_data(uint8_t feat_report_id, uint16_t* x, uint16_t* y, uint16_t* z) {
531505
// Send set feature command, receive get feature response
532506
if (!enable_imu_feat(feat_report_id)) {
533507
return 0;
@@ -576,7 +550,7 @@ uint8_t get_imu_data(uint8_t feat_report_id, int16_t* x, int16_t* y, int16_t* z)
576550
x, y, z are signed fixed-point
577551
"The units are m/s^2. The Q point is 8." (#1 p.58)
578552
*/
579-
uint8_t get_imu_accel(int16_t* x, int16_t* y, int16_t* z) {
553+
uint8_t get_imu_accel(uint16_t* x, uint16_t* y, uint16_t* z) {
580554
return get_imu_data(IMU_ACCEL, x, y, z);
581555
}
582556

@@ -587,7 +561,7 @@ Calibrated gyroscope - drift-compensated rotational velocity
587561
588562
x, y, z are signed fixed-point
589563
*/
590-
uint8_t get_imu_cal_gyro(int16_t* x, int16_t* y, int16_t* z) {
564+
uint8_t get_imu_cal_gyro(uint16_t* x, uint16_t* y, uint16_t* z) {
591565
return get_imu_data(IMU_CAL_GYRO, x, y, z);
592566
}
593567

@@ -600,8 +574,8 @@ x, y, z are signed fixed-point
600574
601575
This does not use `get_imu_data()` because its input report format is different.
602576
*/
603-
uint8_t get_imu_uncal_gyro(int16_t* x, int16_t* y, int16_t* z, int16_t* bias_x,
604-
int16_t* bias_y, int16_t* bias_z) {
577+
uint8_t get_imu_uncal_gyro(uint16_t* x, uint16_t* y, uint16_t* z, uint16_t* bias_x,
578+
uint16_t* bias_y, uint16_t* bias_z) {
605579

606580
// Send set feature command, receive get feature response
607581
if (!enable_imu_feat(IMU_UNCAL_GYRO)) {

src/imu.h

Lines changed: 5 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -38,11 +38,6 @@
3838
#define IMU_UNCAL_GYRO 0x07
3939
#define IMU_RAW_GYRO 0x15
4040

41-
// Q points
42-
#define IMU_ACCEL_Q 8
43-
#define IMU_UNCAL_GYRO_Q 9
44-
#define IMU_CAL_GYRO_Q 9
45-
4641
// Default report inteval (60ms, in microseconds)
4742
#define IMU_DEF_REPORT_INTERVAL 0x0000EA60
4843

@@ -72,12 +67,10 @@ uint8_t send_imu_set_feat_cmd(uint8_t feat_report_id, uint32_t report_interval);
7267
uint8_t enable_imu_feat(uint8_t feat_report_id);
7368
uint8_t disable_imu_feat(uint8_t feat_report_id);
7469

75-
double imu_raw_data_to_double(int16_t raw_data, uint8_t q_point);
76-
77-
uint8_t get_imu_data(uint8_t feat_report_id, int16_t* x, int16_t* y, int16_t* z);
78-
uint8_t get_imu_accel(int16_t* x, int16_t* y, int16_t* z);
79-
uint8_t get_imu_uncal_gyro(int16_t* x, int16_t* y, int16_t* z, int16_t* bias_x,
80-
int16_t* bias_y, int16_t* bias_z);
81-
uint8_t get_imu_cal_gyro(int16_t* x, int16_t* y, int16_t* z);
70+
uint8_t get_imu_data(uint8_t feat_report_id, uint16_t* x, uint16_t* y, uint16_t* z);
71+
uint8_t get_imu_accel(uint16_t* x, uint16_t* y, uint16_t* z);
72+
uint8_t get_imu_uncal_gyro(uint16_t* x, uint16_t* y, uint16_t* z, uint16_t* bias_x,
73+
uint16_t* bias_y, uint16_t* bias_z);
74+
uint8_t get_imu_cal_gyro(uint16_t* x, uint16_t* y, uint16_t* z);
8275

8376
#endif

0 commit comments

Comments
 (0)