Qmi8658a姿态传感器使用心得(2)linux

1 .COD 原理

COD 支持按需校准陀螺仪的X和Y轴。QMI8658A可以校准陀螺仪的X和Y轴的内部增益,提供更精确的灵敏度和更紧密的灵敏度分布。注意:Z轴不受COD影响。

1.1 运行COD的步骤

  1. 设置CTRL7.aEN = 0 和 CTRL7.gEN = 0 以禁用加速度计和陀螺仪。
  2. 通过CTRL9命令发送CTRL_CMD_ON_DEMAND_CALIBRATION (0xA2)。
  3. 等待大约1.5秒,直到QMI8658A完成CTRL9命令。
  4. 读取COD_STATUS寄存器(0x46)以检查COD执行的结果和状态。

1.2 COD状态

如果COD命令成功执行,COD_STATUS寄存器将输出0x00表示成功。非零值表示不同的失败模式。参阅COD状态寄存器(5.7)的详细信息。

1.3 保存和恢复新的增益参数

在成功运行COD后,新的增益将应用于未来的X和Y轴数据,并将这些参数更新到以下寄存器,供主机读取和保存:

  1. 陀螺仪-X增益 (16 bits) 将存储在dVX_L和dVX_H寄存器 (0x51, 0x52)
  2. 陀螺仪-Y增益 (16 bits) 将存储在dVY_L和dVY_H寄存器 (0x53, 0x54)
  3. 陀螺仪-Z增益 (16 bits) 将存储在dVZ_L和dVZ_H寄存器 (0x55, 0x56)

1.4恢复增益参数

  1. 禁用加速度计和陀螺仪 (设置CTRL7.aEN = 0 和 CTRL7.gEN = 0)。
  2. 将保存的陀螺仪-X增益写入寄存器CAL1_L和CAL1_H (0x0B, 0x0C)。
  3. 将保存的陀螺仪-Y增益写入寄存器CAL2_L和CAL2_H (0x0D, 0x0E)。
  4. 将保存的陀螺仪-Z增益写入寄存器CAL3_L和CAL3_H (0x0F, 0x10)。
  5. 写入0xAA到CTRL9寄存器以执行CTRL_CMD_APPLY_GYRO_GAINS命令。

2. COD状态寄存器

COD_STATUS寄存器地址:0x46

Bits名称默认描述
7X_Limit_L_Fail1’b00: COD通过低灵敏度检查; 1: COD失败
6X_Limit_H_Fail1’b00: COD通过高灵敏度检查; 1: COD失败
5Y_Limit_L_Fail1’b00: COD通过低灵敏度检查; 1: COD失败
4Y_Limit_H_Fail1’b00: COD通过高灵敏度检查; 1: COD失败
3Accel_Check1’b00: 加速度计检查通过; 1: 加速度计检查失败
2Startup_Failed1’b00: 陀螺仪启动成功; 1: 陀螺仪启动失败
1Gyro_Enabled1’b00: COD调用时陀螺仪未启用; 1: COD调用时陀螺仪启用
0COD_Failed1’b00: COD成功; 1: COD失败

3.CTRL9命令列表

CTRL9寄存器地址:0x0A

Command NameCommand ValueProtocol TypeDescription
CTRL_CMD_ACK0x00Ctrl9Host acknowledges to end the protocol
CTRL_CMD_RST_FIFO0x04Ctrl9Reset FIFO from Host
CTRL_CMD_REQ_FIFO0x05Ctrl9RGet FIFO data from Device
CTRL_CMD_WRITE_WOM_SETTING0x08WCtrl9Set up and enable Wake on Motion (WoM)
CTRL_CMD_ACCEL_HOST_DELTA_OFFSET0x09WCtrl9Change accelerometer offset
CTRL_CMD_GYRO_HOST_DELTA_OFFSET0x0AWCtrl9Change gyroscope offset
CTRL_CMD_CONFIGURE_TAP0x0CWCtrl9Configure Tap detection
CTRL_CMD_CONFIGURE_PEDOMETER0x0DWCtrl9Configure Pedometer
CTRL_CMD_CONFIGURE_MOTION0x0EWCtrl9Configure Any Motion / No Motion detection
CTRL_CMD_RESET_PEDOMETER0x0FWCtrl9Reset pedometer count
CTRL_CMD_COPY_USID0x10Ctrl9RCopy USID and FW Version to UI registers
CTRL_CMD_SET_RPU0x11WCtrl9Configures IO pull-ups
CTRL_CMD_AHB_CLOCK_GATING0x12WCtrl9Internal AHB clock gating switch
CTRL_CMD_ON_DEMAND_CALIBRATION0xA2WCtrl9On-Demand Calibration on gyroscope
CTRL_CMD_APPLY_GYRO_GAINS0xAAWCtrl9Restore the saved Gyroscope gains

4.配置方法:

        特别注意:在校准过程中,尽量保持安静,减少环境对于校准结果的干扰;
        并且可以在开发过程中设计循环来实现定期校准的效果。保证陀螺仪的准确
        回复过往的增益参数时要注意变化。

void start_calibration(){
    // Disable sensor and set calibration
    writeRegister(CTRL7, 0x00);  // Disable sensor
    
    writeRegister(CTRL9, 0xA2);  // send calibration command
    
    delay(1500);  // delay
    
    uint8_t statusInt = readRegister(STATUSINT);
    if (statusInt & 0x80) {
        // CmdDone is ok
    } else {
        // CmdDone is fail
    }

    writeRegister(CTRL9, 0x00);  // comfirm calibratino success
    
    uint8_t COD_STATUS = readRegister(0x46);
    if (COD_STATUS == 0x00) {
        // calibration success
    } else {
        // calibration fail
    }
    
    //update the gain 
    uint16_t gyroXGain = readRegister(0x51) | (readRegister(0x52) << 8);
    uint16_t gyroYGain = readRegister(0x53) | (readRegister(0x54) << 8);
    uint16_t gyroZGain = readRegister(0x55) | (readRegister(0x56) << 8);
    
    //save the data and send back to qmi8658a
    // Disable sensor and set calibration
    writeRegister(CTRL7, 0x00);

    // write in gyrox
    writeRegister(0x0B, gyroXGain & 0xFF);
    writeRegister(0x0C, (gyroXGain >> 8) & 0xFF);

    // write in gyroy
    writeRegister(0x0D, gyroYGain & 0xFF);
    writeRegister(0x0E, (gyroYGain >> 8) & 0xFF);

    // write in gytoz
    writeRegister(0x0F, gyroZGain & 0xFF);
    writeRegister(0x10, (gyroZGain >> 8) & 0xFF);

    //send command to CTRL9 and follow the permision
    writeRegister(CTRL9, 0xAA);  // update the gain

5.自检:

5.1加速度计自检

加速度计自检用于确定加速度计是否工作在可接受的参数范围内。该功能通过对加速度计的 X、Y 和 Z 轴施加静电力,并检测其机械结构响应。以下是实现自检的步骤:

  1. 禁用传感器 (CTRL7 = 0x00)。
  2. 设置适当的加速度计 ODR(CTRL2.aODR)并将 CTRL2.aST(bit7)置 1 以触发自检。
  3. 如果启用 INT2(CTRL1.bit4 = 1),等待 QMI8658A 将 INT2 置高,或 STATUSINT.bit0 置 1。
  4. 将 CTRL2.aST(bit7) 置 0,以清除 STATUSINT1.bit0 和/或 INT2。
  5. 检查 QMI8658A 将 INT2 置低,并将 STATUSINT1.bit0 置 0。
  6. 读取加速度计自检结果:
    • X 轴:dVX_L 和 dVX_H(寄存器 0x51 和 0x52)
    • Y 轴:dVY_L 和 dVY_H(寄存器 0x53 和 0x54)
    • Z 轴:dVZ_L 和 dVZ_H(寄存器 0x55 和 0x56)

如果三个轴的绝对结果均高于 200mg,则加速度计可视为功能正常。否则,视为功能不正常。

5.2陀螺仪自检

陀螺仪自检用于确定陀螺仪是否工作正常。该功能通过对陀螺仪的 X、Y 和 Z 轴施加静电力,并检测其机械结构响应。以下是实现自检的步骤:

  1. 禁用传感器 (CTRL7 = 0x00)。
  2. 将 gST 置 1(CTRL3.bit7 = 1)。
  3. 如果启用 INT2,等待 QMI8658A 将 INT2 置高,或 STATUSINT.bit0 置 1。
  4. 将 CTRL3.aST(bit7) 置 0,以清除 STATUSINT1.bit0 和/或 INT2。
  5. 检查 QMI8658A 将 INT2 置低,或将 STATUSINT1.bit0 置 0。
  6. 读取陀螺仪自检结果:
    • X 轴:dVX_L 和 dVX_H(寄存器 0x51 和 0x52)
    • Y 轴:dVY_L 和 dVY_H(寄存器 0x53 和 0x54)
    • Z 轴:dVZ_L 和 dVZ_H(寄存器 0x55 和 0x56)
// 加速度计自检
void accelerometer_self_test() {
    printf("Starting Accelerometer Self-Test...\n");
    
    // 禁用传感器
    write_register(CTRL7, 0x00);

    // 设置加速度计自检
    uint8_t ctrl2_val = read_register(CTRL2);
    ctrl2_val |= (1 << 7); // 设置aST位
    write_register(CTRL2, ctrl2_val);

    // 等待自检完成
    while (!(read_register(STATUSINT) & 0x01));

    // 读取自检结果
    int16_t ax = (int16_t)read_register_16(dVX_L, dVX_H);
    int16_t ay = (int16_t)read_register_16(dVY_L, dVY_H);
    int16_t az = (int16_t)read_register_16(dVZ_L, dVZ_H);

    printf("Accelerometer Self-Test Results:\n");
    printf("X: %d mg\n", ax);
    printf("Y: %d mg\n", ay);
    printf("Z: %d mg\n", az);

    // 清除aST位
    ctrl2_val &= ~(1 << 7);
    write_register(CTRL2, ctrl2_val);
}

// 陀螺仪自检
void gyroscope_self_test() {
    printf("Starting Gyroscope Self-Test...\n");

    // 禁用传感器
    write_register(CTRL7, 0x00);

    // 设置陀螺仪自检
    uint8_t ctrl3_val = read_register(CTRL3);
    ctrl3_val |= (1 << 7); // 设置gST位
    write_register(CTRL3, ctrl3_val);

    // 等待自检完成
    while (!(read_register(STATUSINT) & 0x01));

    // 读取自检结果
    int16_t gx = (int16_t)read_register_16(dVX_L, dVX_H);
    int16_t gy = (int16_t)read_register_16(dVY_L, dVY_H);
    int16_t gz = (int16_t)read_register_16(dVZ_L, dVZ_H);

    printf("Gyroscope Self-Test Results:\n");
    printf("X: %d dps\n", gx);
    printf("Y: %d dps\n", gy);
    printf("Z: %d dps\n", gz);

    // 清除gST位
    ctrl3_val &= ~(1 << 7);
    write_register(CTRL3, ctrl3_val);
}

  • 29
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值