• <li id="00i08"><input id="00i08"></input></li>
  • <sup id="00i08"><tbody id="00i08"></tbody></sup>
    <abbr id="00i08"></abbr>
  • 新聞中心

    EEPW首頁 > 嵌入式系統 > 設計應用 > stm8s開發(八) IIC的使用:IIC主機通信!

    stm8s開發(八) IIC的使用:IIC主機通信!

    作者: 時間:2017-09-19 來源:網絡 收藏

      前面講過兩個常用的串口,UART和SPI,這次這次講解一下另一個常用的串口:(I2C)通信

    本文引用地址:http://www.czjhyjcfj.com/article/201709/364477.htm

      科普:一般有兩根信號線,一根是雙向的數據線SDA,另一根是時鐘線SCL。所有接到總線設備上的串行數據SDA都接到總線的SDA上,各設備的時鐘線SCL接到總線的SCL上。

      通信過程:

      主模式時,IIC接口啟動數據傳輸并產生時鐘信號。串行數據傳輸總是以起始條件開始并以停止條件結束。起始條件和停止條件都是在主模式下由軟件控制產生。

      從模式時,IIC接口能識別它自己的地址(7位或10位)和廣播呼叫地址。軟件能夠控制開啟或禁止廣播呼叫地址的識別。

      數據和地址按8位/字節進行傳輸,高位在前。跟在起始條件后的1或2個字節是地址(7位模式為1個字節,10位模式為2個字節)。地址只在主模式發送。

      在一個字節傳輸的8個時鐘后的第9個時鐘期間,接收器必須回送一個應答位(ACK)給發送器。參考下圖。

        

     

      詳細協議可以參考:http://blog.csdn.net/subkiller/article/details/6854910

      和SPI差不多,使用IIC無非就一個初始化,一個數據發送,一個數據接收,三大功能。

      初始化分初始化為主機、從機,不過一般和外部芯片通信單片機都是作為主機。

      void IIC_Master_Init(void)

      {

      CLK_PCKENR1 |= 0x01; //使能IIC外設時鐘

      PB_DDR &= 0xcf;

      PB_CR1 &= 0xcf;

      PB_CR2 &= 0xcf;

      I2C_CR1 = 0x00; //允許時鐘延展,禁止廣播呼叫,禁止iic

      I2C_FREQR = 0x01; //輸入時鐘頻率8MHz

      I2C_OARH = 0x40; //七位地址模式

      I2C_OARL = 0xa0; //自身地址0xa0

      I2C_CCRL = 0xff; //

      I2C_CCRH = 0x00; //標準模式

      I2C_TRISER = 0x02;

      I2C_CR1 |= 0x01; //使能iic外設

      }

      這里使用的是STM8S105片上的IIC引腳PB4、PB5。另外就是需要使能IIC的時鐘。

      發送和接收數據這里只給出一個最簡單的例子,因為不同的外部芯片的通信方式不一樣,不過一般都是:

      讀操作:開始 -> 發送外設地址 -> 開始 ->發送需要讀取的寄存器地址 -> 讀一個字節 -> (可能再讀一個字節) ->。。。 -> 結束

      寫操作:開始 -> 發送外設地址 -> 發送需要寫入的寄存器地址 -> 寫一個字節 ->

      void IIC_Write_Byte(u8 DeviceAddress, u8 Address, u8 Data)

      {

      vu8 temp = 0;

      while((I2C_SR3 & 0x02) != 0); //等待IIC總線空閑

      IIC_Start();

      while((I2C_SR1 & 0x01) == 0); //EV5,起始信號已經發送

      I2C_DR = (DeviceAddress & 0xfe); // 發送iic從器件物理地址,最低位0,寫操作

      while((I2C_SR1 & 0x02) == 0); //地址已經被發送

      temp = I2C_SR1; //清除ADDR標志位

      temp = I2C_SR3;

      while((I2C_SR1 & 0x80) == 0); //等待發送寄存器為空

      I2C_DR = Address; //發送要寫入的寄存器地址

      while((I2C_SR1 & 0x04) == 0); //等待發送完成

      while((I2C_SR1 & 0x80) == 0); //等待發送寄存器為空

      I2C_DR = Data; //發送要寫入的數據

      while((I2C_SR1 & 0x04) == 0); //等待發送完成

      temp = I2C_SR1; //清零BTF標志位

      temp = I2C_DR;

      IIC_Stop(); //發送停止信號

      }

      unsigned char IIC_Read_Byte(u8 DeviceAddress, u8 Address)

      {

      vu8 temp = 0;

      short read_data = 0;

      while((I2C_SR3 & 0x02) != 0); //等待IIC總線空閑

      I2C_CR2 |= 0x04; //使能ACK

      IIC_Start();

      while((I2C_SR1 & 0x01) == 0); //EV5,起始信號已經發送

      I2C_DR = (DeviceAddress & 0xfe); // 發送iic從器件物理地址,最低位0,寫操作

      while((I2C_SR1 & 0x02) == 0); //地址已經被發送

      temp = I2C_SR1; //清除ADDR標志位

      temp = I2C_SR3;

      while((I2C_SR1 & 0x80) == 0); //等待發送寄存器為空

      I2C_DR = Address; // 發送要讀取的寄存器地址

      while((I2C_SR1 & 0x04) == 0); //等待數據發送完成

      IIC_Start();

      while((I2C_SR1 & 0x01) == 0); //EV5,起始信號已經發送

      I2C_DR = (DeviceAddress | 0x01); // 發送iic從器件物理地址,最低位1,讀操作

      while((I2C_SR1 & 0x02) == 0); //地址已經被發送

      temp = I2C_SR1; //清除ADDR標志位

      temp = I2C_SR3;

      while((I2C_SR1 & 0x40) == 0); //等待接收數據寄存器非空

      read_data = I2C_DR;

      I2C_CR2 &= 0xfb; //讀取數據下,發送stop必須禁止ack,才能釋放從機

      temp = I2C_SR1; //清零BTF標志位

      temp = I2C_DR;

      IIC_Stop();

      return read_data;

      }

      附上在IAR環境下的項目工程,包括了SPI、IIC、PWM、AWU、USART、EEPROM等片上硬件的初始化代碼。

      http://download.csdn.NET/detail/devintt/9454188

      讀操作:開始 -> 發送外設地址 -> 開始 ->發送需要讀取的寄存器地址 -> 讀一個字節 -> (可能再讀一個字節) ->。。。 -> 結束



    關鍵詞: stm8s IIC

    評論


    相關推薦

    技術專區

    關閉
    主站蜘蛛池模板: 新化县| 农安县| 平利县| 定远县| 普兰店市| 新乡市| 定日县| 保山市| 永新县| 汉寿县| 大埔区| 北宁市| 绵竹市| 调兵山市| 汝州市| 滦南县| 饶河县| 旬邑县| 修武县| 抚宁县| 潮安县| 临朐县| 綦江县| 清苑县| 驻马店市| 冀州市| 鹤峰县| 东方市| 丹寨县| 资溪县| 家居| 若尔盖县| 喀喇| 兴文县| 巴彦淖尔市| 怀化市| 垦利县| 手机| 溧阳市| 南开区| 五家渠市|