STM32平衡车-MPU6050的DMP库移植

本文目录

  • 一、硬件接线
  • 二、需要移植的三个文件夹
    • 1. DMP文件夹目录
    • 2. IIC文件夹目录
    • 3. MPU6050文件夹目录
  • 三、文件内容
    • IO12C.c
    • IO12C.h
    • MPU6050.c
    • MPU6050.h
    • main.c
  • 四、附录
    • 1.更改IIC引脚

  

一、硬件接线

SCL-- PA11
SDA-- PA12
VCC-- 3.3v
GND-- GND

二、需要移植的三个文件夹

在这里插入图片描述

1. DMP文件夹目录

在这里插入图片描述

2. IIC文件夹目录

在这里插入图片描述

3. MPU6050文件夹目录

在这里插入图片描述

三、文件内容

IO12C.c

#include "ioi2c.h"
#include "sys.h"
#include "delay.h"/**************************实现函数********************************************
*函数原型:		void IIC_Init(void)
*功  能:		初始化I2C对应的接口引脚。
*******************************************************************************/
void IIC_Init(void)
{			GPIO_InitTypeDef GPIO_InitStructure;  //定义结构体GPIO_InitStructureRCC_APB2PeriphClockCmd(	RCC_APB2Periph_GPIOA, ENABLE );	//使能GPIOA时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12|GPIO_Pin_11;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP ;   //推挽输出GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;GPIO_Init(GPIOA, &GPIO_InitStructure);      //GPIOA初始化
}/**************************实现函数********************************************
*函数原型:		void IIC_Start(void)
*功  能:		产生IIC起始信号
*******************************************************************************/
int IIC_Start(void)
{SDA_OUT();     //sda线输出IIC_SDA=1;if(!READ_SDA)return 0;	IIC_SCL=1;delay_us(1);IIC_SDA=0;//START:when CLK is high,DATA change form high to low if(READ_SDA)return 0;delay_us(1);IIC_SCL=0;//钳住I2C总线,准备发送或接收数据 return 1;
}/**************************实现函数********************************************
*函数原型:		void IIC_Stop(void)
*功  能:	    //产生IIC停止信号
*******************************************************************************/	  
void IIC_Stop(void)
{SDA_OUT();//sda线输出IIC_SCL=0;IIC_SDA=0;//STOP:when CLK is high DATA change form low to highdelay_us(1);IIC_SCL=1; IIC_SDA=1;//发送I2C总线结束信号delay_us(1);							   	
}/**************************实现函数********************************************
*函数原型:		u8 IIC_Wait_Ack(void)
*功  能:	    等待应答信号到来 
//返回值:1,接收应答失败
//        0,接收应答成功
*******************************************************************************/
int IIC_Wait_Ack(void)
{u8 ucErrTime=0;SDA_IN();      //SDA设置为输入  IIC_SDA=1;delay_us(1);	   IIC_SCL=1;delay_us(1);	 while(READ_SDA){ucErrTime++;if(ucErrTime>50){IIC_Stop();return 0;}delay_us(1);}IIC_SCL=0;//时钟输出0 	   return 1;  
} /**************************实现函数********************************************
*函数原型:		void IIC_Ack(void)
*功  能:	    产生ACK应答
*******************************************************************************/
void IIC_Ack(void)
{IIC_SCL=0;SDA_OUT();IIC_SDA=0;delay_us(1);IIC_SCL=1;delay_us(1);IIC_SCL=0;
}/**************************实现函数********************************************
*函数原型:		void IIC_NAck(void)
*功  能:	    产生NACK应答
*******************************************************************************/	    
void IIC_NAck(void)
{IIC_SCL=0;SDA_OUT();IIC_SDA=1;delay_us(1);IIC_SCL=1;delay_us(1);IIC_SCL=0;
}
/**************************实现函数********************************************
*函数原型:		void IIC_Send_Byte(u8 txd)
*功  能:	    IIC发送一个字节
*******************************************************************************/		  
void IIC_Send_Byte(u8 txd)
{                        u8 t;   SDA_OUT(); 	    IIC_SCL=0;//拉低时钟开始数据传输for(t=0;t<8;t++){              IIC_SDA=(txd&0x80)>>7;txd<<=1; 	  delay_us(1);   IIC_SCL=1;delay_us(1); IIC_SCL=0;	delay_us(1);}	 
} 	 /**************************实现函数********************************************
*函数原型:		bool i2cWrite(uint8_t addr, uint8_t reg, uint8_t data)
*功  能:		
*******************************************************************************/
int i2cWrite(uint8_t addr, uint8_t reg, uint8_t len, uint8_t *data)
{int i;if (!IIC_Start())return 1;IIC_Send_Byte(addr << 1 );if (!IIC_Wait_Ack()) {IIC_Stop();return 1;}IIC_Send_Byte(reg);IIC_Wait_Ack();for (i = 0; i < len; i++) {IIC_Send_Byte(data[i]);if (!IIC_Wait_Ack()) {IIC_Stop();return 0;}}IIC_Stop();return 0;
}
/**************************实现函数********************************************
*函数原型:		bool i2cWrite(uint8_t addr, uint8_t reg, uint8_t data)
*功  能:		
*******************************************************************************/
int i2cRead(uint8_t addr, uint8_t reg, uint8_t len, uint8_t *buf)
{if (!IIC_Start())return 1;IIC_Send_Byte(addr << 1);if (!IIC_Wait_Ack()) {IIC_Stop();return 1;}IIC_Send_Byte(reg);IIC_Wait_Ack();IIC_Start();IIC_Send_Byte((addr << 1)+1);IIC_Wait_Ack();while (len) {if (len == 1)*buf = IIC_Read_Byte(0);else*buf = IIC_Read_Byte(1);buf++;len--;}IIC_Stop();return 0;
}/**************************实现函数********************************************
*函数原型:		u8 IIC_Read_Byte(unsigned char ack)
*功  能:	    //读1个字节,ack=1时,发送ACK,ack=0,发送nACK 
*******************************************************************************/  
u8 IIC_Read_Byte(unsigned char ack)
{unsigned char i,receive=0;SDA_IN();//SDA设置为输入for(i=0;i<8;i++ ){IIC_SCL=0; delay_us(2);IIC_SCL=1;receive<<=1;if(READ_SDA)receive++;   delay_us(2); }					 if (ack)IIC_Ack(); //发送ACK elseIIC_NAck();//发送nACK  return receive;
}/**************************实现函数********************************************
*函数原型:		unsigned char I2C_ReadOneByte(unsigned char I2C_Addr,unsigned char addr)
*功  能:	    读取指定设备 指定寄存器的一个值
输入	I2C_Addr  目标设备地址addr	   寄存器地址
返回   读出来的值
*******************************************************************************/ 
unsigned char I2C_ReadOneByte(unsigned char I2C_Addr,unsigned char addr)
{unsigned char res=0;IIC_Start();	IIC_Send_Byte(I2C_Addr);	   //发送写命令res++;IIC_Wait_Ack();IIC_Send_Byte(addr); res++;  //发送地址IIC_Wait_Ack();	  //IIC_Stop();//产生一个停止条件	IIC_Start();IIC_Send_Byte(I2C_Addr+1); res++;          //进入接收模式			   IIC_Wait_Ack();res=IIC_Read_Byte(0);	   IIC_Stop();//产生一个停止条件return res;
}/**************************实现函数********************************************
*函数原型:		u8 IICreadBytes(u8 dev, u8 reg, u8 length, u8 *data)
*功  能:	    读取指定设备 指定寄存器的 length个值
输入	dev  目标设备地址reg	  寄存器地址length 要读的字节数*data  读出的数据将要存放的指针
返回   读出来的字节数量
*******************************************************************************/ 
u8 IICreadBytes(u8 dev, u8 reg, u8 length, u8 *data){u8 count = 0;IIC_Start();IIC_Send_Byte(dev);	   //发送写命令IIC_Wait_Ack();IIC_Send_Byte(reg);   //发送地址IIC_Wait_Ack();	  IIC_Start();IIC_Send_Byte(dev+1);  //进入接收模式	IIC_Wait_Ack();for(count=0;count<length;count++){if(count!=length-1)data[count]=IIC_Read_Byte(1);  //带ACK的读数据else  data[count]=IIC_Read_Byte(0);	 //最后一个字节NACK}IIC_Stop();//产生一个停止条件return count;
}/**************************实现函数********************************************
*函数原型:		u8 IICwriteBytes(u8 dev, u8 reg, u8 length, u8* data)
*功  能:	    将多个字节写入指定设备 指定寄存器
输入	dev  目标设备地址reg	  寄存器地址length 要写的字节数*data  将要写的数据的首地址
返回   返回是否成功
*******************************************************************************/ 
u8 IICwriteBytes(u8 dev, u8 reg, u8 length, u8* data){u8 count = 0;IIC_Start();IIC_Send_Byte(dev);	   //发送写命令IIC_Wait_Ack();IIC_Send_Byte(reg);   //发送地址IIC_Wait_Ack();	  for(count=0;count<length;count++){IIC_Send_Byte(data[count]); IIC_Wait_Ack(); }IIC_Stop();//产生一个停止条件return 1; //status == 0;
}/**************************实现函数********************************************
*函数原型:		u8 IICreadByte(u8 dev, u8 reg, u8 *data)
*功  能:	    读取指定设备 指定寄存器的一个值
输入	dev  目标设备地址reg	   寄存器地址*data  读出的数据将要存放的地址
返回   1
*******************************************************************************/ 
u8 IICreadByte(u8 dev, u8 reg, u8 *data){*data=I2C_ReadOneByte(dev, reg);return 1;
}/**************************实现函数********************************************
*函数原型:		unsigned char IICwriteByte(unsigned char dev, unsigned char reg, unsigned char data)
*功  能:	    写入指定设备 指定寄存器一个字节
输入	dev  目标设备地址reg	   寄存器地址data  将要写入的字节
返回   1
*******************************************************************************/ 
unsigned char IICwriteByte(unsigned char dev, unsigned char reg, unsigned char data){return IICwriteBytes(dev, reg, 1, &data);
}/**************************实现函数********************************************
*函数原型:		u8 IICwriteBits(u8 dev,u8 reg,u8 bitStart,u8 length,u8 data)
*功  能:	    读 修改 写 指定设备 指定寄存器一个字节 中的多个位
输入	dev  目标设备地址reg	   寄存器地址bitStart  目标字节的起始位length   位长度data    存放改变目标字节位的值
返回   成功 为1 失败为0
*******************************************************************************/ 
u8 IICwriteBits(u8 dev,u8 reg,u8 bitStart,u8 length,u8 data)
{u8 b;if (IICreadByte(dev, reg, &b) != 0) {u8 mask = (0xFF << (bitStart + 1)) | 0xFF >> ((8 - bitStart) + length - 1);data <<= (8 - length);data >>= (7 - bitStart);b &= mask;b |= data;return IICwriteByte(dev, reg, b);} else {return 0;}
}/**************************实现函数********************************************
*函数原型:		u8 IICwriteBit(u8 dev, u8 reg, u8 bitNum, u8 data)
*功  能:	    读 修改 写 指定设备 指定寄存器一个字节 中的1个位
输入	dev  目标设备地址reg	   寄存器地址bitNum  要修改目标字节的bitNum位data  为0 时,目标位将被清0 否则将被置位
返回   成功 为1 失败为0
*******************************************************************************/ 
u8 IICwriteBit(u8 dev, u8 reg, u8 bitNum, u8 data){u8 b;IICreadByte(dev, reg, &b);b = (data != 0) ? (b | (1 << bitNum)) : (b & ~(1 << bitNum));return IICwriteByte(dev, reg, b);
}//------------------End of File----------------------------

IO12C.h

#ifndef __IOI2C_H
#define __IOI2C_H
#include "stm32f10x.h"/**************************************************************************
作者:平衡小车之家
我的淘宝小店:http://shop114407458.taobao.com/
**************************************************************************/
//IO口操作宏定义
#define BITBAND(addr, bitnum) ((addr & 0xF0000000)+0x2000000+((addr &0xFFFFF)<<5)+(bitnum<<2)) 
#define MEM_ADDR(addr)  *((volatile unsigned long  *)(addr)) 
#define BIT_ADDR(addr, bitnum)   MEM_ADDR(BITBAND(addr, bitnum))  //IO口地址映射
#define GPIOA_ODR_Addr    (GPIOA_BASE+12) //0x4001080C 
#define GPIOB_ODR_Addr    (GPIOB_BASE+12) //0x40010C0C 
#define GPIOC_ODR_Addr    (GPIOC_BASE+12) //0x4001100C 
#define GPIOD_ODR_Addr    (GPIOD_BASE+12) //0x4001140C 
#define GPIOE_ODR_Addr    (GPIOE_BASE+12) //0x4001180C 
#define GPIOF_ODR_Addr    (GPIOF_BASE+12) //0x40011A0C    
#define GPIOG_ODR_Addr    (GPIOG_BASE+12) //0x40011E0C    #define GPIOA_IDR_Addr    (GPIOA_BASE+8) //0x40010808 
#define GPIOB_IDR_Addr    (GPIOB_BASE+8) //0x40010C08 
#define GPIOC_IDR_Addr    (GPIOC_BASE+8) //0x40011008 
#define GPIOD_IDR_Addr    (GPIOD_BASE+8) //0x40011408 
#define GPIOE_IDR_Addr    (GPIOE_BASE+8) //0x40011808 
#define GPIOF_IDR_Addr    (GPIOF_BASE+8) //0x40011A08 
#define GPIOG_IDR_Addr    (GPIOG_BASE+8) //0x40011E08 #define PCout(n)   BIT_ADDR(GPIOC_ODR_Addr,n)  //输出 
#define PCin(n)    BIT_ADDR(GPIOC_IDR_Addr,n)  //输入 #define PBout(n)   BIT_ADDR(GPIOB_ODR_Addr,n)  //输出 
#define PBin(n)    BIT_ADDR(GPIOB_IDR_Addr,n)  //输入 #define PEout(n)   BIT_ADDR(GPIOE_ODR_Addr,n)  //输出 
#define PEin(n)    BIT_ADDR(GPIOE_IDR_Addr,n)  //输入 //IO方向设置
#define SDA_IN()  {GPIOA->CRH&=0XFFF0FFFF;GPIOA->CRH|=8<<16;}
#define SDA_OUT() {GPIOA->CRH&=0XFFF0FFFF;GPIOA->CRH|=3<<16;}//IO操作函数	 
#define IIC_SCL    PAout(11) //SCL
#define IIC_SDA    PAout(12) //SDA	 
#define READ_SDA   PAin(12)  //输入SDA //IIC所有操作函数
void IIC_Init(void);                //初始化IIC的IO口				 
int IIC_Start(void);				//发送IIC开始信号
void IIC_Stop(void);	  			//发送IIC停止信号
void IIC_Send_Byte(u8 txd);			//IIC发送一个字节
u8 IIC_Read_Byte(unsigned char ack);//IIC读取一个字节
int IIC_Wait_Ack(void); 				//IIC等待ACK信号
void IIC_Ack(void);					//IIC发送ACK信号
void IIC_NAck(void);				//IIC不发送ACK信号void IIC_Write_One_Byte(u8 daddr,u8 addr,u8 data);
u8 IIC_Read_One_Byte(u8 daddr,u8 addr);	 
unsigned char I2C_Readkey(unsigned char I2C_Addr);unsigned char I2C_ReadOneByte(unsigned char I2C_Addr,unsigned char addr);
unsigned char IICwriteByte(unsigned char dev, unsigned char reg, unsigned char data);
u8 IICwriteBytes(u8 dev, u8 reg, u8 length, u8* data);
u8 IICwriteBits(u8 dev,u8 reg,u8 bitStart,u8 length,u8 data);
u8 IICwriteBit(u8 dev,u8 reg,u8 bitNum,u8 data);
u8 IICreadBytes(u8 dev, u8 reg, u8 length, u8 *data);int i2cWrite(uint8_t addr, uint8_t reg, uint8_t len, uint8_t *data);
int i2cRead(uint8_t addr, uint8_t reg, uint8_t len, uint8_t *buf);#endif//------------------End of File----------------------------

MPU6050.c

#include "MPU6050.h"
#include "IOI2C.h"#define PRINT_ACCEL     (0x01)
#define PRINT_GYRO      (0x02)
#define PRINT_QUAT      (0x04)
#define ACCEL_ON        (0x01)
#define GYRO_ON         (0x02)
#define MOTION          (0)
#define NO_MOTION       (1)
#define DEFAULT_MPU_HZ  (200)
#define FLASH_SIZE      (512)
#define FLASH_MEM_START ((void*)0x1800)
#define q30  1073741824.0f/**************************************************************************
作者:平衡小车之家
我的淘宝小店:http://shop114407458.taobao.com/
**************************************************************************/
short gyro[3], accel[3], sensors;
float Pitch,Roll,Yaw; 
float q0=1.0f,q1=0.0f,q2=0.0f,q3=0.0f;
static signed char gyro_orientation[9] = {-1, 0, 0,0,-1, 0,0, 0, 1};static  unsigned short inv_row_2_scale(const signed char *row)
{unsigned short b;if (row[0] > 0)b = 0;else if (row[0] < 0)b = 4;else if (row[1] > 0)b = 1;else if (row[1] < 0)b = 5;else if (row[2] > 0)b = 2;else if (row[2] < 0)b = 6;elseb = 7;      // errorreturn b;
}static  unsigned short inv_orientation_matrix_to_scalar(const signed char *mtx)
{unsigned short scalar;scalar = inv_row_2_scale(mtx);scalar |= inv_row_2_scale(mtx + 3) << 3;scalar |= inv_row_2_scale(mtx + 6) << 6;return scalar;
}static void run_self_test(void)
{int result;long gyro[3], accel[3];result = mpu_run_self_test(gyro, accel);if (result == 0x7) {/* Test passed. We can trust the gyro data here, so let's push it down* to the DMP.*/float sens;unsigned short accel_sens;mpu_get_gyro_sens(&sens);gyro[0] = (long)(gyro[0] * sens);gyro[1] = (long)(gyro[1] * sens);gyro[2] = (long)(gyro[2] * sens);dmp_set_gyro_bias(gyro);mpu_get_accel_sens(&accel_sens);accel[0] *= accel_sens;accel[1] *= accel_sens;accel[2] *= accel_sens;dmp_set_accel_bias(accel);printf("setting bias succesfully ......\r\n");}
}uint8_t buffer[14];int16_t  MPU6050_FIFO[6][11];
int16_t Gx_offset=0,Gy_offset=0,Gz_offset=0;/**************************实现函数********************************************
*函数原型:		void  MPU6050_newValues(int16_t ax,int16_t ay,int16_t az,int16_t gx,int16_t gy,int16_t gz)
*功  能:	    将新的ADC数据更新到 FIFO数组,进行滤波处理
*******************************************************************************/void  MPU6050_newValues(int16_t ax,int16_t ay,int16_t az,int16_t gx,int16_t gy,int16_t gz)
{
unsigned char i ;
int32_t sum=0;
for(i=1;i<10;i++){	//FIFO 操作
MPU6050_FIFO[0][i-1]=MPU6050_FIFO[0][i];
MPU6050_FIFO[1][i-1]=MPU6050_FIFO[1][i];
MPU6050_FIFO[2][i-1]=MPU6050_FIFO[2][i];
MPU6050_FIFO[3][i-1]=MPU6050_FIFO[3][i];
MPU6050_FIFO[4][i-1]=MPU6050_FIFO[4][i];
MPU6050_FIFO[5][i-1]=MPU6050_FIFO[5][i];
}
MPU6050_FIFO[0][9]=ax;//将新的数据放置到 数据的最后面
MPU6050_FIFO[1][9]=ay;
MPU6050_FIFO[2][9]=az;
MPU6050_FIFO[3][9]=gx;
MPU6050_FIFO[4][9]=gy;
MPU6050_FIFO[5][9]=gz;sum=0;
for(i=0;i<10;i++){	//求当前数组的合,再取平均值sum+=MPU6050_FIFO[0][i];
}
MPU6050_FIFO[0][10]=sum/10;sum=0;
for(i=0;i<10;i++){sum+=MPU6050_FIFO[1][i];
}
MPU6050_FIFO[1][10]=sum/10;sum=0;
for(i=0;i<10;i++){sum+=MPU6050_FIFO[2][i];
}
MPU6050_FIFO[2][10]=sum/10;sum=0;
for(i=0;i<10;i++){sum+=MPU6050_FIFO[3][i];
}
MPU6050_FIFO[3][10]=sum/10;sum=0;
for(i=0;i<10;i++){sum+=MPU6050_FIFO[4][i];
}
MPU6050_FIFO[4][10]=sum/10;sum=0;
for(i=0;i<10;i++){sum+=MPU6050_FIFO[5][i];
}
MPU6050_FIFO[5][10]=sum/10;
}/**************************实现函数********************************************
*函数原型:		void MPU6050_setClockSource(uint8_t source)
*功  能:	    设置  MPU6050 的时钟源* CLK_SEL | Clock Source* --------+--------------------------------------* 0       | Internal oscillator* 1       | PLL with X Gyro reference* 2       | PLL with Y Gyro reference* 3       | PLL with Z Gyro reference* 4       | PLL with external 32.768kHz reference* 5       | PLL with external 19.2MHz reference* 6       | Reserved* 7       | Stops the clock and keeps the timing generator in reset
*******************************************************************************/
void MPU6050_setClockSource(uint8_t source){IICwriteBits(devAddr, MPU6050_RA_PWR_MGMT_1, MPU6050_PWR1_CLKSEL_BIT, MPU6050_PWR1_CLKSEL_LENGTH, source);}/** Set full-scale gyroscope range.* @param range New full-scale gyroscope range value* @see getFullScaleRange()* @see MPU6050_GYRO_FS_250* @see MPU6050_RA_GYRO_CONFIG* @see MPU6050_GCONFIG_FS_SEL_BIT* @see MPU6050_GCONFIG_FS_SEL_LENGTH*/
void MPU6050_setFullScaleGyroRange(uint8_t range) {IICwriteBits(devAddr, MPU6050_RA_GYRO_CONFIG, MPU6050_GCONFIG_FS_SEL_BIT, MPU6050_GCONFIG_FS_SEL_LENGTH, range);
}/**************************实现函数********************************************
*函数原型:		void MPU6050_setFullScaleAccelRange(uint8_t range)
*功  能:	    设置  MPU6050 加速度计的最大量程
*******************************************************************************/
void MPU6050_setFullScaleAccelRange(uint8_t range) {IICwriteBits(devAddr, MPU6050_RA_ACCEL_CONFIG, MPU6050_ACONFIG_AFS_SEL_BIT, MPU6050_ACONFIG_AFS_SEL_LENGTH, range);
}/**************************实现函数********************************************
*函数原型:		void MPU6050_setSleepEnabled(uint8_t enabled)
*功  能:	    设置  MPU6050 是否进入睡眠模式enabled =1   睡觉enabled =0   工作
*******************************************************************************/
void MPU6050_setSleepEnabled(uint8_t enabled) {IICwriteBit(devAddr, MPU6050_RA_PWR_MGMT_1, MPU6050_PWR1_SLEEP_BIT, enabled);
}/**************************实现函数********************************************
*函数原型:		uint8_t MPU6050_getDeviceID(void)
*功  能:	    读取  MPU6050 WHO_AM_I 标识	 将返回 0x68
*******************************************************************************/
uint8_t MPU6050_getDeviceID(void) {IICreadBytes(devAddr, MPU6050_RA_WHO_AM_I, 1, buffer);return buffer[0];
}/**************************实现函数********************************************
*函数原型:		uint8_t MPU6050_testConnection(void)
*功  能:	    检测MPU6050 是否已经连接
*******************************************************************************/
uint8_t MPU6050_testConnection(void) {if(MPU6050_getDeviceID() == 0x68)  //0b01101000;return 1;else return 0;
}/**************************实现函数********************************************
*函数原型:		void MPU6050_setI2CMasterModeEnabled(uint8_t enabled)
*功  能:	    设置 MPU6050 是否为AUX I2C线的主机
*******************************************************************************/
void MPU6050_setI2CMasterModeEnabled(uint8_t enabled) {IICwriteBit(devAddr, MPU6050_RA_USER_CTRL, MPU6050_USERCTRL_I2C_MST_EN_BIT, enabled);
}/**************************实现函数********************************************
*函数原型:		void MPU6050_setI2CBypassEnabled(uint8_t enabled)
*功  能:	    设置 MPU6050 是否为AUX I2C线的主机
*******************************************************************************/
void MPU6050_setI2CBypassEnabled(uint8_t enabled) {IICwriteBit(devAddr, MPU6050_RA_INT_PIN_CFG, MPU6050_INTCFG_I2C_BYPASS_EN_BIT, enabled);
}/**************************实现函数********************************************
*函数原型:		void MPU6050_initialize(void)
*功  能:	    初始化 	MPU6050 以进入可用状态。
*******************************************************************************/
void MPU6050_initialize(void) {MPU6050_setClockSource(MPU6050_CLOCK_PLL_YGYRO); //设置时钟MPU6050_setFullScaleGyroRange(MPU6050_GYRO_FS_2000);//陀螺仪最大量程 +-1000度每秒MPU6050_setFullScaleAccelRange(MPU6050_ACCEL_FS_2);	//加速度度最大量程 +-2GMPU6050_setSleepEnabled(0); //进入工作状态MPU6050_setI2CMasterModeEnabled(0);	 //不让MPU6050 控制AUXI2CMPU6050_setI2CBypassEnabled(0);	 //主控制器的I2C与	MPU6050的AUXI2C	直通。控制器可以直接访问HMC5883L
}/**************************************************************************
函数功能:MPU6050内置DMP的初始化
入口参数:无
返回  值:无
作    者:平衡小车之家
**************************************************************************/
void DMP_Init(void)
{ u8 temp[1]={0};i2cRead(0x68,0x75,1,temp);// printf("mpu_set_sensor complete ......\r\n");if(temp[0]!=0x68)NVIC_SystemReset();if(!mpu_init()){if(!mpu_set_sensors(INV_XYZ_GYRO | INV_XYZ_ACCEL));// printf("mpu_set_sensor complete ......\r\n");if(!mpu_configure_fifo(INV_XYZ_GYRO | INV_XYZ_ACCEL));// printf("mpu_configure_fifo complete ......\r\n");if(!mpu_set_sample_rate(DEFAULT_MPU_HZ));// printf("mpu_set_sample_rate complete ......\r\n");if(!dmp_load_motion_driver_firmware());//printf("dmp_load_motion_driver_firmware complete ......\r\n");if(!dmp_set_orientation(inv_orientation_matrix_to_scalar(gyro_orientation)));// printf("dmp_set_orientation complete ......\r\n");if(!dmp_set_fifo_rate(DEFAULT_MPU_HZ));//	 printf("dmp_set_fifo_rate complete ......\r\n");if(!mpu_set_dmp_state(1));// printf("mpu_set_dmp_state complete ......\r\n");run_self_test();if(!dmp_enable_feature(DMP_FEATURE_6X_LP_QUAT | DMP_FEATURE_TAP |DMP_FEATURE_ANDROID_ORIENT | DMP_FEATURE_SEND_RAW_ACCEL | DMP_FEATURE_SEND_CAL_GYRO |DMP_FEATURE_GYRO_CAL));// printf("dmp_enable_feature complete ......\r\n");}
}
/**************************************************************************
函数功能:读取MPU6050内置DMP的姿态信息
入口参数:无
返回  值:无
作    者:平衡小车之家
**************************************************************************/
void Read_DMP(void)
{	unsigned long sensor_timestamp;unsigned char more;long quat[4];dmp_read_fifo(gyro, accel, quat, &sensor_timestamp, &sensors, &more);		if (sensors & INV_WXYZ_QUAT ){    q0=quat[0] / q30;q1=quat[1] / q30;q2=quat[2] / q30;q3=quat[3] / q30;Pitch = asin(-2 * q1 * q3 + 2 * q0* q2)* 57.3; 	Roll = atan2(2 * q2 * q3 + 2 * q0 * q1, -2 * q1 * q1 - 2 * q2* q2 + 1)* 57.3; // roll		 Yaw = 	atan2(2*(q1*q2 + q0*q3),q0*q0+q1*q1-q2*q2-q3*q3) * 57.3;}}
/**************************************************************************
函数功能:读取MPU6050内置温度传感器数据
入口参数:无
返回  值:摄氏温度
作    者:平衡小车之家
**************************************************************************/
int Read_Temperature(void)
{	   float Temp;Temp=(I2C_ReadOneByte(devAddr,MPU6050_RA_TEMP_OUT_H)<<8)+I2C_ReadOneByte(devAddr,MPU6050_RA_TEMP_OUT_L);if(Temp>32768) Temp-=65536;Temp=(36.53+Temp/340)*10;return (int)Temp;
}
//------------------End of File----------------------------

MPU6050.h

#ifndef __MPU6050_H
#define __MPU6050_H#include "sys.h"
#define devAddr  0xD0#define MPU6050_ADDRESS_AD0_LOW     0x68 // address pin low (GND), default for InvenSense evaluation board
#define MPU6050_ADDRESS_AD0_HIGH    0x69 // address pin high (VCC)
#define MPU6050_DEFAULT_ADDRESS     MPU6050_ADDRESS_AD0_LOW#define MPU6050_RA_XG_OFFS_TC       0x00 //[7] PWR_MODE, [6:1] XG_OFFS_TC, [0] OTP_BNK_VLD
#define MPU6050_RA_YG_OFFS_TC       0x01 //[7] PWR_MODE, [6:1] YG_OFFS_TC, [0] OTP_BNK_VLD
#define MPU6050_RA_ZG_OFFS_TC       0x02 //[7] PWR_MODE, [6:1] ZG_OFFS_TC, [0] OTP_BNK_VLD
#define MPU6050_RA_X_FINE_GAIN      0x03 //[7:0] X_FINE_GAIN
#define MPU6050_RA_Y_FINE_GAIN      0x04 //[7:0] Y_FINE_GAIN
#define MPU6050_RA_Z_FINE_GAIN      0x05 //[7:0] Z_FINE_GAIN
#define MPU6050_RA_XA_OFFS_H        0x06 //[15:0] XA_OFFS
#define MPU6050_RA_XA_OFFS_L_TC     0x07
#define MPU6050_RA_YA_OFFS_H        0x08 //[15:0] YA_OFFS
#define MPU6050_RA_YA_OFFS_L_TC     0x09
#define MPU6050_RA_ZA_OFFS_H        0x0A //[15:0] ZA_OFFS
#define MPU6050_RA_ZA_OFFS_L_TC     0x0B
#define MPU6050_RA_XG_OFFS_USRH     0x13 //[15:0] XG_OFFS_USR
#define MPU6050_RA_XG_OFFS_USRL     0x14
#define MPU6050_RA_YG_OFFS_USRH     0x15 //[15:0] YG_OFFS_USR
#define MPU6050_RA_YG_OFFS_USRL     0x16
#define MPU6050_RA_ZG_OFFS_USRH     0x17 //[15:0] ZG_OFFS_USR
#define MPU6050_RA_ZG_OFFS_USRL     0x18
#define MPU6050_RA_SMPLRT_DIV       0x19
#define MPU6050_RA_CONFIG           0x1A
#define MPU6050_RA_GYRO_CONFIG      0x1B
#define MPU6050_RA_ACCEL_CONFIG     0x1C
#define MPU6050_RA_FF_THR           0x1D
#define MPU6050_RA_FF_DUR           0x1E
#define MPU6050_RA_MOT_THR          0x1F
#define MPU6050_RA_MOT_DUR          0x20
#define MPU6050_RA_ZRMOT_THR        0x21
#define MPU6050_RA_ZRMOT_DUR        0x22
#define MPU6050_RA_FIFO_EN          0x23
#define MPU6050_RA_I2C_MST_CTRL     0x24
#define MPU6050_RA_I2C_SLV0_ADDR    0x25
#define MPU6050_RA_I2C_SLV0_REG     0x26
# define MPU6050_RA_I2C_SLV0_CTRL    0x27
#define MPU6050_RA_I2C_SLV1_ADDR    0x28
#define MPU6050_RA_I2C_SLV1_REG     0x29
#define MPU6050_RA_I2C_SLV1_CTRL    0x2A
#define MPU6050_RA_I2C_SLV2_ADDR    0x2B
#define MPU6050_RA_I2C_SLV2_REG     0x2C
#define MPU6050_RA_I2C_SLV2_CTRL    0x2D
#define MPU6050_RA_I2C_SLV3_ADDR    0x2E
#define MPU6050_RA_I2C_SLV3_REG     0x2F
#define MPU6050_RA_I2C_SLV3_CTRL    0x30
#define MPU6050_RA_I2C_SLV4_ADDR    0x31
#define MPU6050_RA_I2C_SLV4_REG     0x32
#define MPU6050_RA_I2C_SLV4_DO      0x33
#define MPU6050_RA_I2C_SLV4_CTRL    0x34
#define MPU6050_RA_I2C_SLV4_DI      0x35
#define MPU6050_RA_I2C_MST_STATUS   0x36
#define MPU6050_RA_INT_PIN_CFG      0x37
#define MPU6050_RA_INT_ENABLE       0x38
#define MPU6050_RA_DMP_INT_STATUS   0x39
#define MPU6050_RA_INT_STATUS       0x3A
#define MPU6050_RA_ACCEL_XOUT_H     0x3B
#define MPU6050_RA_ACCEL_XOUT_L     0x3C
#define MPU6050_RA_ACCEL_YOUT_H     0x3D
#define MPU6050_RA_ACCEL_YOUT_L     0x3E
#define MPU6050_RA_ACCEL_ZOUT_H     0x3F
#define MPU6050_RA_ACCEL_ZOUT_L     0x40
#define MPU6050_RA_TEMP_OUT_H       0x41
#define MPU6050_RA_TEMP_OUT_L       0x42
#define MPU6050_RA_GYRO_XOUT_H      0x43
#define MPU6050_RA_GYRO_XOUT_L      0x44
#define MPU6050_RA_GYRO_YOUT_H      0x45
#define MPU6050_RA_GYRO_YOUT_L      0x46
#define MPU6050_RA_GYRO_ZOUT_H      0x47
#define MPU6050_RA_GYRO_ZOUT_L      0x48
#define MPU6050_RA_EXT_SENS_DATA_00 0x49
#define MPU6050_RA_EXT_SENS_DATA_01 0x4A
#define MPU6050_RA_EXT_SENS_DATA_02 0x4B
#define MPU6050_RA_EXT_SENS_DATA_03 0x4C
#define MPU6050_RA_EXT_SENS_DATA_04 0x4D
#define MPU6050_RA_EXT_SENS_DATA_05 0x4E
#define MPU6050_RA_EXT_SENS_DATA_06 0x4F
#define MPU6050_RA_EXT_SENS_DATA_07 0x50
#define MPU6050_RA_EXT_SENS_DATA_08 0x51
#define MPU6050_RA_EXT_SENS_DATA_09 0x52
#define MPU6050_RA_EXT_SENS_DATA_10 0x53
#define MPU6050_RA_EXT_SENS_DATA_11 0x54
#define MPU6050_RA_EXT_SENS_DATA_12 0x55
#define MPU6050_RA_EXT_SENS_DATA_13 0x56
#define MPU6050_RA_EXT_SENS_DATA_14 0x57
#define MPU6050_RA_EXT_SENS_DATA_15 0x58
#define MPU6050_RA_EXT_SENS_DATA_16 0x59
#define MPU6050_RA_EXT_SENS_DATA_17 0x5A
#define MPU6050_RA_EXT_SENS_DATA_18 0x5B
#define MPU6050_RA_EXT_SENS_DATA_19 0x5C
#define MPU6050_RA_EXT_SENS_DATA_20 0x5D
#define MPU6050_RA_EXT_SENS_DATA_21 0x5E
#define MPU6050_RA_EXT_SENS_DATA_22 0x5F
#define MPU6050_RA_EXT_SENS_DATA_23 0x60
#define MPU6050_RA_MOT_DETECT_STATUS    0x61
#define MPU6050_RA_I2C_SLV0_DO      0x63
#define MPU6050_RA_I2C_SLV1_DO      0x64
#define MPU6050_RA_I2C_SLV2_DO      0x65
#define MPU6050_RA_I2C_SLV3_DO      0x66
#define MPU6050_RA_I2C_MST_DELAY_CTRL   0x67
#define MPU6050_RA_SIGNAL_PATH_RESET    0x68
#define MPU6050_RA_MOT_DETECT_CTRL      0x69
#define MPU6050_RA_USER_CTRL        0x6A
#define MPU6050_RA_PWR_MGMT_1       0x6B
#define MPU6050_RA_PWR_MGMT_2       0x6C
#define MPU6050_RA_BANK_SEL         0x6D
#define MPU6050_RA_MEM_START_ADDR   0x6E
#define MPU6050_RA_MEM_R_W          0x6F
#define MPU6050_RA_DMP_CFG_1        0x70
#define MPU6050_RA_DMP_CFG_2        0x71
#define MPU6050_RA_FIFO_COUNTH      0x72
#define MPU6050_RA_FIFO_COUNTL      0x73
#define MPU6050_RA_FIFO_R_W         0x74
#define MPU6050_RA_WHO_AM_I         0x75#define MPU6050_TC_PWR_MODE_BIT     7
#define MPU6050_TC_OFFSET_BIT       6
#define MPU6050_TC_OFFSET_LENGTH    6
#define MPU6050_TC_OTP_BNK_VLD_BIT  0#define MPU6050_VDDIO_LEVEL_VLOGIC  0
#define MPU6050_VDDIO_LEVEL_VDD     1#define MPU6050_CFG_EXT_SYNC_SET_BIT    5
#define MPU6050_CFG_EXT_SYNC_SET_LENGTH 3
#define MPU6050_CFG_DLPF_CFG_BIT    2
#define MPU6050_CFG_DLPF_CFG_LENGTH 3#define MPU6050_EXT_SYNC_DISABLED       0x0
#define MPU6050_EXT_SYNC_TEMP_OUT_L     0x1
#define MPU6050_EXT_SYNC_GYRO_XOUT_L    0x2
#define MPU6050_EXT_SYNC_GYRO_YOUT_L    0x3
#define MPU6050_EXT_SYNC_GYRO_ZOUT_L    0x4
#define MPU6050_EXT_SYNC_ACCEL_XOUT_L   0x5
#define MPU6050_EXT_SYNC_ACCEL_YOUT_L   0x6
#define MPU6050_EXT_SYNC_ACCEL_ZOUT_L   0x7#define MPU6050_DLPF_BW_256         0x00
#define MPU6050_DLPF_BW_188         0x01
#define MPU6050_DLPF_BW_98          0x02
#define MPU6050_DLPF_BW_42          0x03
#define MPU6050_DLPF_BW_20          0x04
#define MPU6050_DLPF_BW_10          0x05
#define MPU6050_DLPF_BW_5           0x06#define MPU6050_GCONFIG_FS_SEL_BIT      4
#define MPU6050_GCONFIG_FS_SEL_LENGTH   2#define MPU6050_GYRO_FS_250         0x00
#define MPU6050_GYRO_FS_500         0x01
#define MPU6050_GYRO_FS_1000        0x02
#define MPU6050_GYRO_FS_2000        0x03#define MPU6050_ACONFIG_XA_ST_BIT           7
#define MPU6050_ACONFIG_YA_ST_BIT           6
#define MPU6050_ACONFIG_ZA_ST_BIT           5
#define MPU6050_ACONFIG_AFS_SEL_BIT         4
#define MPU6050_ACONFIG_AFS_SEL_LENGTH      2
#define MPU6050_ACONFIG_ACCEL_HPF_BIT       2
#define MPU6050_ACONFIG_ACCEL_HPF_LENGTH    3#define MPU6050_ACCEL_FS_2          0x00
#define MPU6050_ACCEL_FS_4          0x01
#define MPU6050_ACCEL_FS_8          0x02
#define MPU6050_ACCEL_FS_16         0x03#define MPU6050_DHPF_RESET          0x00
#define MPU6050_DHPF_5              0x01
#define MPU6050_DHPF_2P5            0x02
#define MPU6050_DHPF_1P25           0x03
#define MPU6050_DHPF_0P63           0x04
#define MPU6050_DHPF_HOLD           0x07#define MPU6050_TEMP_FIFO_EN_BIT    7
#define MPU6050_XG_FIFO_EN_BIT      6
#define MPU6050_YG_FIFO_EN_BIT      5
#define MPU6050_ZG_FIFO_EN_BIT      4
#define MPU6050_ACCEL_FIFO_EN_BIT   3
#define MPU6050_SLV2_FIFO_EN_BIT    2
#define MPU6050_SLV1_FIFO_EN_BIT    1
#define MPU6050_SLV0_FIFO_EN_BIT    0#define MPU6050_MULT_MST_EN_BIT     7
#define MPU6050_WAIT_FOR_ES_BIT     6
#define MPU6050_SLV_3_FIFO_EN_BIT   5
#define MPU6050_I2C_MST_P_NSR_BIT   4
#define MPU6050_I2C_MST_CLK_BIT     3
#define MPU6050_I2C_MST_CLK_LENGTH  4#define MPU6050_CLOCK_DIV_348       0x0
#define MPU6050_CLOCK_DIV_333       0x1
#define MPU6050_CLOCK_DIV_320       0x2
#define MPU6050_CLOCK_DIV_308       0x3
#define MPU6050_CLOCK_DIV_296       0x4
#define MPU6050_CLOCK_DIV_286       0x5
#define MPU6050_CLOCK_DIV_276       0x6
#define MPU6050_CLOCK_DIV_267       0x7
#define MPU6050_CLOCK_DIV_258       0x8
#define MPU6050_CLOCK_DIV_500       0x9
#define MPU6050_CLOCK_DIV_471       0xA
#define MPU6050_CLOCK_DIV_444       0xB
#define MPU6050_CLOCK_DIV_421       0xC
#define MPU6050_CLOCK_DIV_400       0xD
#define MPU6050_CLOCK_DIV_381       0xE
#define MPU6050_CLOCK_DIV_364       0xF#define MPU6050_I2C_SLV_RW_BIT      7
#define MPU6050_I2C_SLV_ADDR_BIT    6
#define MPU6050_I2C_SLV_ADDR_LENGTH 7
#define MPU6050_I2C_SLV_EN_BIT      7
#define MPU6050_I2C_SLV_BYTE_SW_BIT 6
#define MPU6050_I2C_SLV_REG_DIS_BIT 5
#define MPU6050_I2C_SLV_GRP_BIT     4
#define MPU6050_I2C_SLV_LEN_BIT     3
#define MPU6050_I2C_SLV_LEN_LENGTH  4#define MPU6050_I2C_SLV4_RW_BIT         7
#define MPU6050_I2C_SLV4_ADDR_BIT       6
#define MPU6050_I2C_SLV4_ADDR_LENGTH    7
#define MPU6050_I2C_SLV4_EN_BIT         7
#define MPU6050_I2C_SLV4_INT_EN_BIT     6
#define MPU6050_I2C_SLV4_REG_DIS_BIT    5
#define MPU6050_I2C_SLV4_MST_DLY_BIT    4
#define MPU6050_I2C_SLV4_MST_DLY_LENGTH 5#define MPU6050_MST_PASS_THROUGH_BIT    7
#define MPU6050_MST_I2C_SLV4_DONE_BIT   6
#define MPU6050_MST_I2C_LOST_ARB_BIT    5
#define MPU6050_MST_I2C_SLV4_NACK_BIT   4
#define MPU6050_MST_I2C_SLV3_NACK_BIT   3
#define MPU6050_MST_I2C_SLV2_NACK_BIT   2
#define MPU6050_MST_I2C_SLV1_NACK_BIT   1
#define MPU6050_MST_I2C_SLV0_NACK_BIT   0#define MPU6050_INTCFG_INT_LEVEL_BIT        7
#define MPU6050_INTCFG_INT_OPEN_BIT         6
#define MPU6050_INTCFG_LATCH_INT_EN_BIT     5
#define MPU6050_INTCFG_INT_RD_CLEAR_BIT     4
#define MPU6050_INTCFG_FSYNC_INT_LEVEL_BIT  3
#define MPU6050_INTCFG_FSYNC_INT_EN_BIT     2
#define MPU6050_INTCFG_I2C_BYPASS_EN_BIT    1
#define MPU6050_INTCFG_CLKOUT_EN_BIT        0#define MPU6050_INTMODE_ACTIVEHIGH  0x00
#define MPU6050_INTMODE_ACTIVELOW   0x01#define MPU6050_INTDRV_PUSHPULL     0x00
#define MPU6050_INTDRV_OPENDRAIN    0x01#define MPU6050_INTLATCH_50USPULSE  0x00
#define MPU6050_INTLATCH_WAITCLEAR  0x01#define MPU6050_INTCLEAR_STATUSREAD 0x00
#define MPU6050_INTCLEAR_ANYREAD    0x01#define MPU6050_INTERRUPT_FF_BIT            7
#define MPU6050_INTERRUPT_MOT_BIT           6
#define MPU6050_INTERRUPT_ZMOT_BIT          5
#define MPU6050_INTERRUPT_FIFO_OFLOW_BIT    4
#define MPU6050_INTERRUPT_I2C_MST_INT_BIT   3
#define MPU6050_INTERRUPT_PLL_RDY_INT_BIT   2
#define MPU6050_INTERRUPT_DMP_INT_BIT       1
#define MPU6050_INTERRUPT_DATA_RDY_BIT      0// TODO: figure out what these actually do
// UMPL source code is not very obivous
#define MPU6050_DMPINT_5_BIT            5
#define MPU6050_DMPINT_4_BIT            4
#define MPU6050_DMPINT_3_BIT            3
#define MPU6050_DMPINT_2_BIT            2
#define MPU6050_DMPINT_1_BIT            1
#define MPU6050_DMPINT_0_BIT            0#define MPU6050_MOTION_MOT_XNEG_BIT     7
#define MPU6050_MOTION_MOT_XPOS_BIT     6
#define MPU6050_MOTION_MOT_YNEG_BIT     5
#define MPU6050_MOTION_MOT_YPOS_BIT     4
#define MPU6050_MOTION_MOT_ZNEG_BIT     3
#define MPU6050_MOTION_MOT_ZPOS_BIT     2
#define MPU6050_MOTION_MOT_ZRMOT_BIT    0#define MPU6050_DELAYCTRL_DELAY_ES_SHADOW_BIT   7
#define MPU6050_DELAYCTRL_I2C_SLV4_DLY_EN_BIT   4
#define MPU6050_DELAYCTRL_I2C_SLV3_DLY_EN_BIT   3
#define MPU6050_DELAYCTRL_I2C_SLV2_DLY_EN_BIT   2
#define MPU6050_DELAYCTRL_I2C_SLV1_DLY_EN_BIT   1
#define MPU6050_DELAYCTRL_I2C_SLV0_DLY_EN_BIT   0#define MPU6050_PATHRESET_GYRO_RESET_BIT    2
#define MPU6050_PATHRESET_ACCEL_RESET_BIT   1
#define MPU6050_PATHRESET_TEMP_RESET_BIT    0#define MPU6050_DETECT_ACCEL_ON_DELAY_BIT       5
#define MPU6050_DETECT_ACCEL_ON_DELAY_LENGTH    2
#define MPU6050_DETECT_FF_COUNT_BIT             3
#define MPU6050_DETECT_FF_COUNT_LENGTH          2
#define MPU6050_DETECT_MOT_COUNT_BIT            1
#define MPU6050_DETECT_MOT_COUNT_LENGTH         2#define MPU6050_DETECT_DECREMENT_RESET  0x0
#define MPU6050_DETECT_DECREMENT_1      0x1
#define MPU6050_DETECT_DECREMENT_2      0x2
#define MPU6050_DETECT_DECREMENT_4      0x3#define MPU6050_USERCTRL_DMP_EN_BIT             7
#define MPU6050_USERCTRL_FIFO_EN_BIT            6
#define MPU6050_USERCTRL_I2C_MST_EN_BIT         5
#define MPU6050_USERCTRL_I2C_IF_DIS_BIT         4
#define MPU6050_USERCTRL_DMP_RESET_BIT          3
#define MPU6050_USERCTRL_FIFO_RESET_BIT         2
#define MPU6050_USERCTRL_I2C_MST_RESET_BIT      1
#define MPU6050_USERCTRL_SIG_COND_RESET_BIT     0#define MPU6050_PWR1_DEVICE_RESET_BIT   7
#define MPU6050_PWR1_SLEEP_BIT          6
#define MPU6050_PWR1_CYCLE_BIT          5
#define MPU6050_PWR1_TEMP_DIS_BIT       3
#define MPU6050_PWR1_CLKSEL_BIT         2
#define MPU6050_PWR1_CLKSEL_LENGTH      3#define MPU6050_CLOCK_INTERNAL          0x00
#define MPU6050_CLOCK_PLL_XGYRO         0x01
#define MPU6050_CLOCK_PLL_YGYRO         0x02
#define MPU6050_CLOCK_PLL_ZGYRO         0x03
#define MPU6050_CLOCK_PLL_EXT32K        0x04
#define MPU6050_CLOCK_PLL_EXT19M        0x05
#define MPU6050_CLOCK_KEEP_RESET        0x07#define MPU6050_PWR2_LP_WAKE_CTRL_BIT       7
#define MPU6050_PWR2_LP_WAKE_CTRL_LENGTH    2
#define MPU6050_PWR2_STBY_XA_BIT            5
#define MPU6050_PWR2_STBY_YA_BIT            4
#define MPU6050_PWR2_STBY_ZA_BIT            3
#define MPU6050_PWR2_STBY_XG_BIT            2
#define MPU6050_PWR2_STBY_YG_BIT            1
#define MPU6050_PWR2_STBY_ZG_BIT            0#define MPU6050_WAKE_FREQ_1P25      0x0
#define MPU6050_WAKE_FREQ_2P5       0x1
#define MPU6050_WAKE_FREQ_5         0x2
#define MPU6050_WAKE_FREQ_10        0x3#define MPU6050_BANKSEL_PRFTCH_EN_BIT       6
#define MPU6050_BANKSEL_CFG_USER_BANK_BIT   5
#define MPU6050_BANKSEL_MEM_SEL_BIT         4
#define MPU6050_BANKSEL_MEM_SEL_LENGTH      5#define MPU6050_WHO_AM_I_BIT        6
#define MPU6050_WHO_AM_I_LENGTH     6
extern	short gyro[3], accel[3];
extern int16_t Gx_offset,Gy_offset,Gz_offset;
extern float Acc1G_Values;
extern float  Pitch,Roll,Yaw; 
//供外部调用的API
void MPU6050_initialize(void); //初始化
uint8_t MPU6050_testConnection(void); //检测MPU6050是否存在
//读取ADC值
void MPU6050_getMotion6(int16_t* ax, int16_t* ay, int16_t* az, int16_t* gx, int16_t* gy, int16_t* gz);
void MPU6050_getlastMotion6(int16_t* ax, int16_t* ay, int16_t* az, int16_t* gx, int16_t* gy, int16_t* gz);
uint8_t MPU6050_getDeviceID(void); //读取MPU6050的ID
void MPU6050_InitGyro_Offset(void);//初始化陀螺仪偏置
void DMP_Init(void);
void Read_DMP(void);
int Read_Temperature(void);
#endif

main.c

#include "stm32f10x.h"
#include "sys.h"int main()
{IIC_Init();                     //模拟IIC初始化MPU6050_initialize();           //=====MPU6050初始化	DMP_Init();                     //初始化DMP   while(1){Read_DMP();                      //===读取倾角printf("%f",Pitch);   //xprintf("%f",Roll);  //yprintf("%f",Yaw);  //z} 
}

四、附录

1.更改IIC引脚

若修改IIC引脚需要修改以下内容:
(1)初始化的引脚
在这里插入图片描述
(2)输出输入引脚
在这里插入图片描述

(3)寄存器
在这里插入图片描述
   这里GPIOX的CRH寄存器,管理的是引脚8-15,CRL寄存器管理的引脚是0-7。所以修改引脚几就需要对应的修改寄存器对应的值即可。左移多少位需要看第几号引脚,每个引脚对应寄存器的4个位置。

假如改为引脚PA7:

#define SDA_IN()  {GPIOA->CRL&=0X0FFFFFFF;GPIOA->CRL|=8<<28;}
#define SDA_OUT() {GPIOA->CRL&=0X0FFFFFFF;GPIOA->CRL|=3<<28;}

假如改为引脚PA8:

#define SDA_IN()  {GPIOA->CRH&=0XFFFFFFF0;GPIOA->CRH|=8<<0;}
#define SDA_OUT() {GPIOA->CRH&=0XFFFFFFF0;GPIOA->CRH|=3<<0;}

假如改为引脚PA9:

#define SDA_IN()  {GPIOA->CRH&=0XFFFFFF0F;GPIOA->CRH|=8<<4;}
#define SDA_OUT() {GPIOA->CRH&=0XFFFFFF0F;GPIOA->CRH|=3<<4;}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/833538.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

winscp断点续传

背景 超大文件上传&#xff0c; scp可能因为网络或其他原因中断&#xff0c;并且已上传完的文件无法同步。如何断点续传呢&#xff1f;使用winscp软件 winscp安装 百度搜索&#xff0c;自行安装 开启断点续传功能 https://jingyan.baidu.com/article/fdffd1f8395529b2e98ca…

图纸管理的高效策略与最佳实践

图纸管理的高效策略与最佳实践 在工程设计、产品研发和建筑行业中&#xff0c;图纸管理是一项至关重要的任务。随着项目规模的扩大和复杂性的增加&#xff0c;如何高效、有序地管理图纸已成为企业和团队关注的焦点。本文将为您介绍图纸管理的高效策略与最佳实践&#xff0c;帮助…

一文搞懂深度学习:最全神经网络介绍

本文是深度学习系列文章的第二篇&#xff0c;我们将深入探讨各种类型的人工神经网络&#xff0c;探索它们独特的特性和应用。 01 神经网络介绍 人工神经网络已经彻底改变了机器学习领域&#xff0c;并成为人工智能的基石&#xff0c;它的设计目的是模仿人类大脑的结构和功能&a…

ubuntu_Docker安装配置

什么是docker? Docker 是一个开源的应用容器引擎&#xff0c;让开发者可以打包他们的应用以及依赖包到一个可移植的镜像中&#xff0c;然后发布到任何流行的 Linux或Windows操作系统的机器上&#xff0c;也可以实现虚拟化。容器是完全使用沙箱机制&#xff0c;相互之间不会有…

『ZJUBCA Collaboration』WTF Academy 赞助支持

非常荣幸宣布&#xff0c;浙江大学区块链协会收到WTF Academy的赞助与支持&#xff0c;未来将共同开展更多深度合作。 WTF Academy是开发者的Web3开源大学&#xff0c;旨在通过开源教育让100,000名开发者进入到Web3。截止目前&#xff0c;WTF开源教程在GitHub收获超15,000 ⭐&a…

【LAMMPS学习】八、基础知识(5.9)LAMMPS 近场动力学

8. 基础知识 此部分描述了如何使用 LAMMPS 为用户和开发人员执行各种任务。术语表页面还列出了 MD 术语,以及相应 LAMMPS 手册页的链接。 LAMMPS 源代码分发的 examples 目录中包含的示例输入脚本以及示例脚本页面上突出显示的示例输入脚本还展示了如何设置和运行各种模拟。 …

Ubuntu软件中心不显示

装完Ubuntu后没有Software -- 更新apt sudo apt update -- 升级apt sudo apt upgrade -- 重启 sudo systemctl reboot-- 安装snap sudo apt-get install snap -- 安装软件商店 sudo snap install snap-store -- 更新软件商店 sudo snap refresh snap-store安装成功&#xff01…

学QT的第二天~

小黑子鉴别界面 #include "mywidget.h" void MyWidget::bth1() { if(edit3 ->text()"520cxk"&&edit4 ->text()"1314520") { qDebug()<< "你好&#xff0c;真爱粉"; this->close(); } else { speecher->sa…

【建网护网三十载】 守护不息创新不止,C3安全AI未来!

30年&#xff0c;中国互联网从起步探索到领先全球。1994年4月20日&#xff0c;中国正式开通首条64K的国际专线&#xff0c;标志着我国成功实现与国际互联网的全功能接轨&#xff0c;展开互联网快速发展的三十载。 回望30年&#xff0c;亲历建网&#xff0c;投身建设&#xff0c…

Charles抓包工具

Charles是一个HTTP代理工具&#xff0c;使开发人员能够查看客服端和服务器之间的所有HTTP/ HTTPS/SSL网络请求。 Charles是在PC环境下常用的网络抓包截取工具&#xff0c;在做移动开发时&#xff0c;我们为了调试客户端与服务端的网络通讯协议&#xff0c;常常需要截取网络请求…

大数据集成平台建设方案-word原件资料

基础支撑平台主要承担系统总体架构与各个应用子系统的交互&#xff0c;第三方系统与总体架构的交互。需要满足内部业务在该平台的基础上&#xff0c;实现平台对于子系统的可扩展性。基于以上分析对基础支撑平台&#xff0c;提出了以下要求&#xff1a; (1) 基于平台的基础架构&…

iframe通信postMessage

iframe嵌入页面是实现微前端的方式之一。由于浏览器的跨域限制&#xff0c;iframe与父页面之间的通信变得不是那么容易。postMessage解决了这个问题。从广义上讲&#xff0c;一个窗口可以获得对另一个窗口的引用&#xff08;比如 targetWindow window.parent&#xff09;&…

spring bean生命周期全部过程

Spring Bean的生命周期包括以下全部过程&#xff1a; 实例化&#xff1a;在Spring容器启动时&#xff0c;根据配置文件或注解等信息创建Bean的实例。属性赋值&#xff1a;如果Bean有属性需要进行初始化&#xff0c;Spring容器会自动为这些属性进行赋值。自定义初始化方法&…

线程理论篇1

本章问题&#xff1a;什么是线程?线程的使用场景&#xff1f;什么是线程池&#xff1f;线程池是如何工作的&#xff1f;线程池共享了哪些资源?线程安全代码怎么写&#xff1f;什么是线程安全? 什么是线程&#xff1f; 线程是为了提高进程的效率。进程的地址空间中保存了cpu…

【mysql】mysql单表查询、多表查询、分组查询、子查询等案例详细解析

✨✨ 欢迎大家来到景天科技苑✨✨ &#x1f388;&#x1f388; 养成好习惯&#xff0c;先赞后看哦~&#x1f388;&#x1f388; &#x1f3c6; 作者简介&#xff1a;景天科技苑 &#x1f3c6;《头衔》&#xff1a;大厂架构师&#xff0c;华为云开发者社区专家博主&#xff0c;…

嵌入式C语言高级教程:实现基于STM32的人工智能语音识别系统

在嵌入式系统中实现语音识别技术可以极大地增强设备的交互性。本教程将指导您如何在STM32微控制器上使用TensorFlow Lite for Microcontrollers实现基本的语音识别功能。 一、开发环境准备 硬件要求 微控制器&#xff1a;STM32F746NG&#xff0c;支持足够的运算能力和内存来…

spring高级篇(七)

1、异常处理 在DispatcherServlet中&#xff0c;doDispatch(HttpServletRequest request, HttpServletResponse response) 方法用于进行任务处理&#xff1a; 在捕获到异常后没有立刻进行处理&#xff0c;而是先用一个局部变量dispatchException进行记录&#xff0c;然后统一由…

VMware虚拟机中ubuntu使用记录(5)—— 如何在ubuntu中安装USB相机ros驱动并获取usb摄像头数据

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 一、ROS下USB相机驱动1.准备工作(1) 下载驱动(2) 创建ROS工作空间 2. 安装usb_cam驱动(1) 安装usb_cam驱动包(2) 编译代码 3. 修改usb_cam驱动的配置文件(1) 查看US…

一路串联电机的绕制原理

这里要说明的一点是 对于一路串联的电机&#xff0c;无论是一把线圈还是两把线圈&#xff0c;出来的都是只有两个线头&#xff0c;可看做一个整体来对待&#xff01; 绕制具体原理 同心式线圈绕制 前面说的都是等距式的 线圈绕制&#xff0c;下面我们讲解一下同心式的绕制办法…

##07 从线性回归到神经网络:PyTorch实战解析

文章目录 前言线性回归基础理论背景实现步骤 神经网络介绍理论背景实现步骤 从线性回归到神经网络结论 前言 在深度学习的浩瀚宇宙中&#xff0c;线性回归和神经网络是两个基本但极其重要的概念。线性回归模型是统计学和机器学习的基石之一&#xff0c;而神经网络则是深度学习…