日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > linux >内容正文

linux

linux i2c dev.h freq,STM32F103ZET(基于秉火开发板)+Cubemx(F1 V1.60库)+IIC+AT24C02(修复官方例程读写死机bug)...

發布時間:2023/12/14 linux 35 豆豆
生活随笔 收集整理的這篇文章主要介紹了 linux i2c dev.h freq,STM32F103ZET(基于秉火开发板)+Cubemx(F1 V1.60库)+IIC+AT24C02(修复官方例程读写死机bug)... 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

首先說明下開發條件:

1、開發板:秉火霸道,STM32F103ZET

2、軟件:Cubemx V4.23(F1 V1.60庫)

3、硬件:AT24C02 256KByte

問題描述:Cubemx生成IIC代碼會出現死機問題,或者壓根運行不了!

問題原因:

1、ST為了規避飛利浦IIC專利問題,將STM32的硬件IIC設計的比較復雜,而且穩定性不怎么好,所以一般教程都不推薦使用。

2、Cubemx生成的代碼有Bug!

解決辦法:

1、設置

2、IIC的回調函數里面需要將時鐘初始化放在引腳初始化之前!

void HAL_I2C_MspInit(I2C_HandleTypeDef* hi2c)

{

GPIO_InitTypeDef GPIO_InitStruct;

if(hi2c->Instance==I2C1)

{

/* USER CODE BEGIN I2C1_MspInit 0 */

__HAL_RCC_I2C1_CLK_ENABLE(); //默認生成的放在了引腳初始化后面!

/* USER CODE END I2C1_MspInit 0 */

/**I2C1 GPIO Configuration

PB6 ? ? ------> I2C1_SCL

PB7 ? ? ------> I2C1_SDA

*/

GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7;

GPIO_InitStruct.Mode = GPIO_MODE_AF_OD;

GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;

HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);

/* Peripheral clock enable */

/* USER CODE BEGIN I2C1_MspInit 1 */

/* USER CODE END I2C1_MspInit 1 */

}

}

3、函數的具體應用需要結合AT24C02的數據手冊,符合AT24C02的要求!

我們在讀寫IIC時,即使不知道IIC的協議是什么,直接調用 HAL_I2C_Mem_Write(I2C_HandleTypeDef *hi2c, uint16_t DevAddress, uint16_t MemAddress, uint16_t MemAddSize, uint8_t *pData, uint16_t Size, uint32_t Timeout) 這個函數就可以對IIC的設備進行讀寫,這就是Cubemx的優勢!

我先解釋下這個函數里面的幾個變量:

I2C_HandleTypeDef *hi2c IIC的句柄

uint16_t DevAddress IIC設備的外部地址

uint16_t MemAddress?IIC設備的內部地址

uint16_t MemAddSize 讀寫內部地址的方式,一般使用I2C_MEMADD_SIZE_8BIT方式

注意只有兩種選擇:I2C_MEMADD_SIZE_8BIT 或者 I2C_MEMADD_SIZE_16BIT

uint8_t *pData 寫入的數組或者指針

uint16_t Size 寫入的字節數!

注意:如果是AT24C02,這個字節數不能超過8!!!!!這也叫AT24C02的頁寫入!當然這是為了提高速度,如果你想不出錯也不在乎速度,你可以將字節數設置為1,這樣肯定不會出錯!

????uint32_t Timeout 時間超時

4、程序實現

注意:需要在寫函數后面加入短延時!

uint8_t I2c_Buf_Write[256];

uint8_t I2c_Buf_Read[256];

uint8_t I2C_Test(void)

{

uint16_t i;

i2cStatus=HAL_I2C_IsDeviceReady(&hi2c1, 0xA0, 256, 1000); ?//0表示ready

printf("i2cStatus = %d\r\n ", i2cStatus);

i2cStatus1=HAL_I2C_GetState(&hi2c1);//32表示ready ?HAL_I2C_STATE_READY ?= 0x20U, ? /*!< Peripheral Initialized and ready for use ?*/

printf("i2cStatus1 = %d\r\n ", i2cStatus1);

printf("寫入的數據\n\r");

for ( i=0; i<256; i++ ) //填充緩沖

{

I2c_Buf_Write[i] = i;

HAL_I2C_Mem_Write(&hi2c1, (uint16_t)EEPROM_Block0_ADDRESS, i, I2C_MEMADD_SIZE_8BIT, (uint8_t*)(&(I2c_Buf_Write[i])), 1, 10000);//一個字節一個字節寫,如果需要頁寫入(不超過8),使用40行的函數

// HAL_I2C_Mem_Write(&hi2c1, (uint16_t)EEPROM_Block0_ADDRESS, 0x00, I2C_MEMADD_SIZE_8BIT,(uint8_t*)I2c_Buf_Write, 8, 10000);//不能超過8個字節,如果超過需要分開寫,for循環里面改為i=i+8

printf("0xX ", I2c_Buf_Write[i]);

HAL_Delay(5);//不能少

}

EEPROM_INFO("\n\r寫成功\n\r");

HAL_Delay(500);

EEPROM_INFO("\n\r讀出的數據\n\r");

//將EEPROM讀出數據順序保持到I2c_Buf_Read中

//if(HAL_I2C_GetState(&hi2c1) == 0x20 ) //加入檢測

if( HAL_I2C_IsDeviceReady(&hi2c1, 0xA0, 256, 1000) == HAL_OK)//另外一種檢測方法

{

HAL_I2C_Mem_Read(&hi2c1, (uint16_t)(EEPROM_Block0_ADDRESS+1 ),0x00, I2C_MEMADD_SIZE_8BIT,(uint8_t *)I2c_Buf_Read, 256, 10000); //讀對字節數沒有限制

}

//將I2c_Buf_Read中的數據通過串口打印

for (i=0; i<256; i++)

{

printf("0xX ", I2c_Buf_Read[i]);

if(I2c_Buf_Read[i] != I2c_Buf_Write[i])

{

EEPROM_ERROR("0xX ", I2c_Buf_Read[i]);

EEPROM_ERROR("錯誤:I2C EEPROM寫入與讀出的數據不一致\n\r");

return 0;

}

}

EEPROM_INFO("I2C(AT24C02)讀寫測試成功\n\r");

return 1;

}

5、聯系方式:微信Startingray,本人準備將cubemx的小bug解決的過程記錄下來,也是給愛好者一點啟示,歡迎微信和我溝通,共同進步!個人覺得Cubemx是未來的發展方向,可以使我們避免很多小錯誤,但是由于現在軟件版本之間的兼容性,加上不同版本庫之間存在的bug,還是需要我們在使用時時刻保持警惕!

2020.08.22重新學習記錄:

1、開發板:秉火霸道,STM32F103ZET

2、軟件:Cubemx V6.01(F1 V1.80庫)

還有IIC的7bit地址是0x50,但是調用的函數需要的是8bit表示的這個地址應該是0xA0

很遺憾IIC的BUG還存在,而且如果使用FSMC的時候,IIC的配置會影響FSMC,兩者一起用的時候要注意。

總結

以上是生活随笔為你收集整理的linux i2c dev.h freq,STM32F103ZET(基于秉火开发板)+Cubemx(F1 V1.60库)+IIC+AT24C02(修复官方例程读写死机bug)...的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。