bmi088-board 技术手册
大约 5 分钟Sailor 调试助手
bmi088-board 技术手册
Important
注意这是最早的V1.0 协议的产品,对现在的上位机并不适用。
渲染
实物
bmi088-board 开源地址
协议
BMI088模块16位寄存器
数据 | 说明 |
---|---|
bit0 | 模块复位 |
bit1 | 陀螺仪校准 |
bit2 | CAN输出使能 |
bit3 | USART输出使能 |
bit4 | 保留 |
bit5 | 保留 |
bit6 | 保留 |
bit7 | 保留 |
bit8 | 保留 |
bit9 | 保留 |
bit10 | 保留 |
bit11 | 保留 |
bit12 | 保留 |
bit13 | 保留 |
bit14 | USART命令有效控制位 |
bit15 | CAN命令有效控制位 |
上电复位状态bit2=1,bit3=1,其余位位0,即使能所有输出
同时向模块发送CAN或USART数据,CAN数据具有更高优先级
使用CAN发送数据
0X8004
->关闭串口输出,CAN持续输出姿态数据使用USART发送数据
0X4008
->在保证CAN未发送(bit15=0)的情况下,关闭CAN输出,USART持续输出,注意发送数据需要协议打包
UART方式通信协议
通信要求
配置为波特率 115200
,8
位数据位,1
位停止位,无
硬件流控,无
校验位,发送频率 100Hz
.
接口协议说明
SEASKY通信协议-详情见 串口协议文件
BMI088端发送接口(float数据长度- 10)
数据 说明 IMU_USART_ID 0X0001 bmi088_flag 16位寄存器 float_data[0] accel.x float_data[1] accel.y float_data[2] accel.z float_data[3] rate.x float_data[4] rate.y float_data[5] rate.z float_data[6] gyro.yaw float_data[7] gyro.yaw_c(连续) float_data[8] gyro.pitch float_data[9] gyro.roll 发送函数(该模块发送调用函数)
void imu_usart_send(void)
{
static uint8_t send_data[60];//保证大于发送的数据
uint16_t tx_flag=0,send_data_len=0;
/*发送寄存器赋值*/
tx_flag |= imu_ctr_t.ctr.res&0x01;
tx_flag |= (imu_ctr_t.ctr.cmd<<1)&0x01;
/*发送的数据赋值*/
imu_ctr_t.ctr.float_data[0] = imu_ctr_t.imu_t->accel.x;
imu_ctr_t.ctr.float_data[1] = imu_ctr_t.imu_t->accel.y;
imu_ctr_t.ctr.float_data[2] = imu_ctr_t.imu_t->accel.z;
imu_ctr_t.ctr.float_data[3] = imu_ctr_t.imu_t->angle_rate.x;
imu_ctr_t.ctr.float_data[4] = imu_ctr_t.imu_t->angle_rate.y;
imu_ctr_t.ctr.float_data[5] = imu_ctr_t.imu_t->angle_rate.z;
imu_ctr_t.ctr.float_data[6] = imu_ctr_t.imu_t->gyro.yaw;
imu_ctr_t.ctr.float_data[7] = imu_ctr_t.imu_t->continuous_gyro.yaw;
imu_ctr_t.ctr.float_data[8] = imu_ctr_t.imu_t->gyro.pitch;
imu_ctr_t.ctr.float_data[9] = imu_ctr_t.imu_t->gyro.roll;
get_protocol_send_data(IMU_USART_TX_ID,tx_flag,&imu_ctr_t.ctr.float_data[0],
10,send_data,&send_data_len);
usart_send(send_data,send_data_len);
}
- BMI088控制数据(float数据长度为0)
数据 | 说明 |
---|---|
IMU_USART_ID | 0X0201 |
bmi088_flag | 16位寄存器 |
使用端向BMI088发送数据,详情见 串口协议文件
- 寄存器数据打包函数
get_protocol_send_data
(0X0201,//信号id
flag,//16位寄存器
NULL,//待发送的float数据
0,//float的数据长度
usart6_tx_buf,//待发送的数据帧
&usart6_tx_length);//待发送的数据帧长度
CAN方式通信
- CAN波特率1MHZ、发送频率100Hz
- 协议部分
- 定义共用体变量
typedef union
{
float data_f;
uint8_t data_u8[4];
}data_f_u8;
协议说明(单次发送-单个ID)
信号数据
ID | union | float | u8 |
---|---|---|---|
0X301 | X_ACC | data_f | data_u8[4] |
X_RATE | data_f | data_u8[4] | |
0X302 | Y_ACC | data_f | data_u8[4] |
Y_RATE | data_f | data_u8[4] | |
0X303 | Z_ACC | data_f | data_u8[4] |
Z_RATE | data_f | data_u8[4] | |
0X304 | YAW | data_f | data_u8[4] |
YAW_C(连续) | data_f | data_u8[4] | |
0X305 | pitch | data_f | data_u8[4] |
roll | data_f | data_u8[4] |
- 控制数据(can有8byte,此处只使用2byte)
ID | union | u8 |
---|---|---|
0X306 | flag | data_u8[8] |
使用can向bmi088发送控制数据
/*设定BMI088*/
void set_can_tx_bmi088(uint16_t flag)
{
CanTxMsg TxMessage;
TxMessage.StdId= CAN_TX_BMI088_CMD;
TxMessage.IDE = 0;
TxMessage.RTR = 0;
TxMessage.DLC = 8;
TxMessage.Data[0] = flag >> 8;
TxMessage.Data[1] = flag;
TxMessage.Data[2] = 0 >> 8;
TxMessage.Data[3] = 0;
TxMessage.Data[4] = 0 >> 8;
TxMessage.Data[5] = 0;
TxMessage.Data[6] = 0 >> 8;
TxMessage.Data[7] = 0;
CAN_Transmit(CAN2,&TxMessage);
}
- BMI088模块端发送
bmi088模块端的can发送函数
void CAN_Send_Msg(uint32_t Send_StdId,float data1,float data2)
{
static CAN_TxHeaderTypeDef Tx_Message;
static uint8_t Tx_Buf[8];
uint32_t send_mail_box;
data_f_u8 Tx_data[2];
Tx_Message.StdId = Send_StdId;//设置id
Tx_Message.IDE = CAN_ID_STD;
Tx_Message.RTR = CAN_RTR_DATA;
Tx_Message.DLC = 0x08;
Tx_data[0].data_f=data1;
Tx_data[1].data_f=data2;
for(int i=0; i<8; i++)
{
Tx_Buf[i]=Tx_data[i/4].data_u8[i%4];
}
while(HAL_CAN_AddTxMessage(&hcan1, &Tx_Message,Tx_Buf, &send_mail_box));
}
BMI088模块端发送函数调用
.. code-block:: c
:caption: bmi088模块端的can发送数据.
:linenos:
CAN_Send_Msg(0x301,imu_ctr_t.imu_t->accel.x,imu_ctr_t.imu_t->angle_rate.x);
CAN_Send_Msg(0x302,imu_ctr_t.imu_t->accel.y,imu_ctr_t.imu_t->angle_rate.y);
CAN_Send_Msg(0x303,imu_ctr_t.imu_t->accel.z,imu_ctr_t.imu_t->angle_rate.z);
CAN_Send_Msg(0x304,imu_ctr_t.imu_t->gyro.yaw,imu_ctr_t.imu_t->continuous_gyro.yaw);
CAN_Send_Msg(0x305,imu_ctr_t.imu_t->gyro.pitch,imu_ctr_t.imu_t->gyro.roll);
使用端接收示例
可以使用枚举定义如下变量
bmi088模块端的can发送数据
CAN_RX_BMI088_X = 0X301,
CAN_RX_BMI088_Y = 0X302,
CAN_RX_BMI088_Z = 0X303,
CAN_RX_BMI088_YAW = 0X304,
CAN_RX_BMI088_GYRO = 0X305,
CAN_TX_BMI088_CMD = 0X306
- 结构体
bmi088模块端的can发送数据
typedef union
{
float data_f;
uint8_t data_u8[4];
} data_f_u8;
typedef struct
{
struct
{
uint8_t res:1;//<<0
uint8_t cmd:1;//<<1
uint8_t can_out_cmd:1;//<<2
uint8_t usart_out_cmd:1;//<<3
uint16_t flag;
} imu_ctr;
struct
{
float x;
float y;
float z;
} acc;
struct
{
float x;
float y;
float z;
} rate;
struct
{
float yaw;
float pitch;
float roll;
float yaw_c;
} angle;
} seasky_bmi088;
- 数据解读
bmi088模块端的can发送数据
void get_bmi088(float *imu_1,float *imu_2,uint8_t *data)
{
data_f_u8 rx_buf[2];
for(int i=0; i<8; i++)
{
rx_buf[i/4].data_u8[i%4]=data[i];
}
*imu_1 = rx_buf[0].data_f;
*imu_2 = rx_buf[1].data_f;
}
- 对应到具体数据
can接收中断调用
void get_moto_info2(void)
{
CanRxMsg RxMessage;
int i;
CAN_Receive(CAN2,CAN_FIFO0,&RxMessage);
switch(RxMessage.StdId)
{
case CAN_RX_BMI088_X :
get_bmi088x(RxMessage.Data);
break;
case CAN_RX_BMI088_Y :
get_bmi088y(RxMessage.Data);
break;
case CAN_RX_BMI088_Z :
get_bmi088z(RxMessage.Data);
break;
case CAN_RX_BMI088_YAW :
get_bmi088_yaw(RxMessage.Data);
break;
case CAN_RX_BMI088_GYRO:
get_bmi088_angle(RxMessage.Data);
break;
default:
;
break;
}
}
can接收中断调用.
void get_bmi088x(uint8_t *data)
{
get_bmi088(&imu_rm.acc.x,&imu_rm.rate.x,data);
}
void get_bmi088y(uint8_t *data)
{
get_bmi088(&imu_rm.acc.y,&imu_rm.rate.y,data);
}
void get_bmi088z(uint8_t *data)
{
get_bmi088(&imu_rm.acc.z,&imu_rm.rate.z,data);
}
void get_bmi088_yaw(uint8_t *data)
{
get_bmi088(&imu_rm.angle.yaw,&imu_rm.angle.yaw_c,data);
}
void get_bmi088_angle(uint8_t *data)
{
get_bmi088(&imu_rm.angle.pitch,&imu_rm.angle.roll,data);
}
- 接收端发送控制数据(寄存器赋值处理不完整)
can发送数据.
void imu_set(void)
{
imu_rm.imu_ctr.flag |= imu_rm.imu_ctr.res&0x01;
imu_rm.imu_ctr.flag |= (imu_rm.imu_ctr.cmd<<1)&0x01;
set_can_tx_bmi088(imu_rm.imu_ctr.flag);
}