STM32硬件IIC操作


Stm32具有IIC接口,接口有以下主要特性

多主機功能:該模塊既可做主設備也可做從設備

主設備功能

C地址檢測

產生和檢測7/10位地址和廣播呼叫

支持不同的通訊速度

狀態標志:

發送器/接收器模式標志

字節發送結束標志

總線忙標志

錯誤標志

2個中斷向量

可選的拉長時鍾功能

具單字節緩沖器的DMA

雖然很多人說STM的硬件IIC不好用,但是對於這么一個設備去探索一下還是很有必要的,指不定哪天就用上了呢,

IIC借口一共有九個寄存器,比較重要的幾個寄存器分別如下

1.       CR1


由這幾個位我們可以正常產生標准IICSTART條件STOP條件,ACKNOACK

CR2


控制IIC的通行頻率

這兩位檢測IIC總線是否收到數據


 

1.       對於硬件IIC的初始化流程包括

1.       配置IO,配置為GPIO_Mode_AF_OD模式

2.       選擇IIC模式

3.       選擇是否使能自動應答以及設備地址長度

4.       設置IIC總線的傳輸速率

2.       硬件IIC的讀寫操作其實邏輯上和標准總線類似,也是發送地址等待ack發送數據等待ACK,但是因為有硬件的自動參與,所以我們不需要延時了

 

具體代碼如下

 

void HmcIICInit(void)
{
	/*GPIO初始化*/
	GPIO_InitTypeDef GPIO_InitStructure;
	/* 配置硬件IIC需要的變量 */ 
	I2C_InitTypeDef I2C_InitStructure; 

	/* 使能與 I2C1 有關的時鍾 */
	RCC_APB2PeriphClockCmd  (RCC_APB2Periph_GPIOB,ENABLE ); 
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_I2C1,ENABLE);  

	/* PB6-I2C1_SCL、PB7-I2C1_SDA*/
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7; 
	GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; 
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_OD; 
	GPIO_Init(GPIOB, &GPIO_InitStructure); 

	/*IIC外設初始化*/

	/* I2C 配置 */
	I2C_InitStructure.I2C_Mode = I2C_Mode_I2C ;     //配置為普通IIC模式
	//I2C_InitStructure.I2C_DutyCycle = I2C_DutyCycle_2; 
	//I2C_InitStructure.I2C_OwnAddress1 = SlaveAddress; 
	I2C_InitStructure.I2C_Ack = I2C_Ack_Enable;  //使能自動應答   
	I2C_InitStructure.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit; 
	I2C_InitStructure.I2C_ClockSpeed = 50000;   //5K的速度?


	/* I2C1 初始化 */
	I2C_Init(I2C1, &I2C_InitStructure);	   

	/* 使能 I2C1 */
	I2C_Cmd  (I2C1,ENABLE); 
	/*允許應答模式*/
	I2C_AcknowledgeConfig(I2C1, ENABLE);   
}

void HmcByteWrite(u8 addr,u8 dataValue)
{
	I2C_GenerateSTART(I2C1,ENABLE);

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_MODE_SELECT));

	I2C_Send7bitAddress(I2C1,HMC_ADDR,I2C_Direction_Transmitter);

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED));

	I2C_SendData(I2C1,addr);

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_BYTE_TRANSMITTED));

	I2C_SendData(I2C1,dataValue);

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_BYTE_TRANSMITTED));

	I2C_GenerateSTOP(I2C1,ENABLE);

}

u8 HmcByteRead(u8 addr)
{
	u8 dataValue;

	while(I2C_GetFlagStatus(I2C1,I2C_FLAG_BUSY));

	I2C_GenerateSTART(I2C1,ENABLE);//起始信號

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_MODE_SELECT));

	I2C_Send7bitAddress(I2C1,HMC_ADDR,I2C_Direction_Transmitter);//發送設備地址+寫信號

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED));//

	I2C_Cmd(I2C1,ENABLE);

	I2C_SendData(I2C1,addr);//發送存儲單元地址,從0開始

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_BYTE_TRANSMITTED));

	I2C_GenerateSTART(I2C1,ENABLE);//起始信號

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_MODE_SELECT));

	I2C_Send7bitAddress(I2C1,HMC_ADDR,I2C_Direction_Receiver);//發送設備地址+讀信號

	while(!I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_RECEIVER_MODE_SELECTED));

	I2C_AcknowledgeConfig(I2C1,DISABLE);

	I2C_GenerateSTOP(I2C1,ENABLE);

	while(!(I2C_CheckEvent(I2C1,I2C_EVENT_MASTER_BYTE_RECEIVED)));

	dataValue=I2C_ReceiveData(I2C1);//讀出寄存器數據

	return dataValue;
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM