[DemoCode下载] MG51 I2C使用方法

[复制链接]
867|2
 楼主| huahuagg 发表于 2023-12-16 17:53 | 显示全部楼层 |阅读模式
  1. /*---------------------------------------------------------------------------------------------------------*/
  2. /*                                                                                                         */
  3. /* SPDX-License-Identifier: Apache-2.0                                                                     */
  4. /* Copyright(c) 2023 Nuvoton Technology Corp. All rights reserved.                                         */
  5. /*                                                                                                         */
  6. /*---------------------------------------------------------------------------------------------------------*/


  7. //***********************************************************************************************************
  8. //  File Function: MG51 I2C master mode demo code, the Slave address = 0xA4
  9. //
  10. //   ____________            _____________
  11. //  |            |   SDA    |             |
  12. //  |            |<-------->|             |
  13. //  |            |          |             |
  14. //  |MG51(M)     |          | MG51(S)     |
  15. //  |(I2C_Master)|          | (I2C_Slave) |
  16. //  |            |   SCL    |             |
  17. //  |            |--------->|             |
  18. //  |____________|          |_____________|
  19. //
  20. //  The protocol of I2C is master: start -> write 10 byte(ACK) ->stop -> start ->read 10 byte(ACK) -> stop
  21. //  Setting break point in I2C slave to check time out function
  22. //***********************************************************************************************************


  23. #include "MG51.H"


  24. #define I2C_CLOCK                 14
  25. #define I2C_SLAVE_ADDRESS         0xA4
  26. #define I2C_WR                    0
  27. #define I2C_RD                    1

  28. #define LOOP_SIZE                 10
  29. BIT   i2cErrorFlag=0;


  30. void I2C_ISR(void) interrupt 6
  31. {
  32.    if (I2TOC&SET_BIT0)
  33.       while(1);                     /* When into this loop means I2C transmit time out */
  34. }
  35. //========================================================================================================
  36. void Init_I2C(void)
  37. {
  38.     P13_OPENDRAIN_MODE;          // Modify SCL pin to Open drain mode. don't forget the pull high resister in circuit
  39.     P14_OPENDRAIN_MODE;          // Modify SDA pin to Open drain mode. don't forget the pull high resister in circuit

  40.     P13_ST_ENABLE;
  41.     P14_ST_ENABLE;

  42.     /* Set I2C clock rate */
  43.     I2CLK = I2C_CLOCK;
  44.    /* Enable I2C time out divier as clock base is Fsys/4, the time out is about 4ms when Fsys = 16MHz */
  45.     set_I2TOC_DIV;
  46.     clr_I2TOC_I2TOF;
  47.    /* Enable I2C intterupt for I2C time out */
  48.     set_EIE_EI2C;                               //enable I2C interrupt by setting IE1 bit 0
  49.     set_IE_EA;

  50.     /* Enable I2C */
  51.     set_I2CON_I2CEN;
  52. }
  53. //========================================================================================================
  54. void I2C_Error(void)
  55. {
  56.     while (1);
  57. }
  58. //========================================================================================================

  59. //--------------------------------------------------------------------------------------------
  60. //----  Page Write----------------------------------------------------------------------------
  61. //--------------------------------------------------------------------------------------------
  62. void I2C_Write_Process(UINT8 u8DAT)
  63. {
  64.     unsigned char  u8Count;

  65.     set_I2TOC_I2TOCEN;                           /* Enable I2C time out */

  66.     /* Write Step1 */
  67.     set_I2CON_STA;                              /* Send Start bit to I2C EEPROM */
  68.     clr_I2CON_SI;
  69.     while (!SI);                                /*Check SI set or not  */
  70.     if (I2STAT != 0x08)                         /*Check status value after every step   */
  71.     {
  72.         i2cErrorFlag=1;
  73.         goto I2CWRSTOP;
  74.     }
  75.    
  76.     /* Write Step2 */
  77.     clr_I2CON_STA;                              /*STA=0*/
  78.     I2DAT = (I2C_SLAVE_ADDRESS | I2C_WR);
  79.     clr_I2CON_SI;
  80.     while (!SI);                                /*Check SI set or not */
  81.     if (I2STAT != 0x18)
  82.     {
  83.         i2cErrorFlag=1;
  84.         goto I2CWRSTOP;
  85.     }

  86.     /* Write Step3 */
  87.     for (u8Count = 0; u8Count < LOOP_SIZE; u8Count++)
  88.     {
  89.         I2DAT = u8DAT;
  90.         clr_I2CON_SI;
  91.         while (!SI);                            /*Check SI set or not*/
  92.         if (I2STAT != 0x28)
  93.         {
  94.             i2cErrorFlag=1;
  95.             goto I2CWRSTOP;
  96.         }
  97.         u8DAT = ~u8DAT;
  98.     }

  99.     /* Write Step4 */
  100.     I2CWRSTOP:
  101.     set_I2CON_STO;
  102.     clr_I2CON_SI;
  103.     while (STO);                                /* Check STOP signal */
  104.     if  (i2cErrorFlag)
  105.     {
  106.       printf ("\n I2C write error !");
  107.     }
  108.   }
  109.   
  110. //--------------------------------------------------------------------------------------------
  111. //----  Page Read ----------------------------------------------------------------------------
  112. //--------------------------------------------------------------------------------------------
  113. void I2C_Read_Process(UINT8 u8DAT)
  114. {
  115.     unsigned char  u8Count;
  116.     /* Read Step1 */
  117.     set_I2CON_STA;
  118.     clr_I2CON_SI;         
  119.     while (!SI);                                //Check SI set or not
  120.     if (I2STAT != 0x08)                         //Check status value after every step
  121.     {
  122.         i2cErrorFlag=1;
  123.         goto I2CRDSTOP;
  124.     }

  125.     /* Step13 */
  126.     clr_I2CON_STA;                                    //STA needs to be cleared after START codition is generated
  127.     I2DAT = (I2C_SLAVE_ADDRESS | I2C_RD);
  128.     clr_I2CON_SI;
  129.     while (!SI);                                //Check SI set or not
  130.     if (I2STAT != 0x40)              
  131.     {
  132.         i2cErrorFlag=1;
  133.         goto I2CRDSTOP;
  134.     }
  135.    
  136.     /* Step14 */
  137.     for (u8Count = 0; u8Count <LOOP_SIZE; u8Count++)
  138.     {
  139.         set_I2CON_AA;
  140.         clr_I2CON_SI;        
  141.         while (!SI);                            //Check SI set or not
  142.         if (I2STAT != 0x50)
  143.         {
  144.             i2cErrorFlag=1;
  145.             goto I2CRDSTOP;
  146.         }
  147.         if (I2DAT != u8DAT)
  148.         {
  149.             i2cErrorFlag=1;
  150.             goto I2CRDSTOP;
  151.         }
  152.         u8DAT = ~u8DAT;
  153.     }
  154.    
  155.     /* Step15 */
  156.     clr_I2CON_AA;
  157.     clr_I2CON_SI;
  158.     while (!SI);                                //Check SI set or not
  159.     if (I2STAT != 0x58)
  160.     {
  161.         i2cErrorFlag=1;
  162.         goto I2CRDSTOP;
  163.     }

  164.     /* Step16 */
  165.     I2CRDSTOP:
  166.     set_I2CON_STO;
  167.     clr_I2CON_SI;
  168.     while (STO);                                /* Check STOP signal */
  169.     {
  170.       printf ("\n I2C read error !");
  171.     }
  172. }
  173. //========================================================================================================
  174. void main(void)
  175. {
  176.     /* UART0 settting for printf function */
  177.     MODIFY_HIRC(HIRC_24);
  178.     Enable_UART0_VCOM_printf_24M_115200();
  179.     printf ("\n Test start ...");

  180.     Init_I2C();                                 /* initial I2C circuit  */
  181.     I2C_Write_Process(0x55);                    /* I2C Master will send 10 byte 0x55,0xAA,.... to slave */
  182.     I2C_Read_Process(0x55);

  183.     while (1);
  184. /* =================== */
  185. }



21mengnan 发表于 2023-12-17 11:35 | 显示全部楼层
clr_I2CON_SI 这个SI是什么。
波尔街道的松柏 发表于 2025-9-11 15:48 | 显示全部楼层
MG51 的 I2C 使用:配置相关引脚为 I2C 功能,设置控制寄存器使能 I2C,通过数据寄存器收发,查询状态位判断通信状态。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

160

主题

1437

帖子

2

粉丝
快速回复 在线客服 返回列表 返回顶部