你好!欢迎来到 !
语言
当前位置: 首页>> 技术中心>> 单片机入门>> 高手经验!STM32单片机学习I2C通信

高手经验!STM32单片机学习I2C通信

关键字: STM32 单片机 I2C通信 寄存器 作者:admin 来源:不详 发布时间:2018-05-18 浏览:28

I2C总线是由NXP(原PHILIPS)公司设计,有十分简洁的物理层定义,其特性如下:

· 只要求两条总线线路:一条串行数据线SDA,一条串行时钟线SCL;

· 每个连接到总线的器件都可以通过唯一的地址和一直存在的简单的主机/从机关系软件设定地址,主机可以作为主机发送器或主机接收器;

· 它是一个真正的多主机总线,如果两个或更多主机同时初始化,数据传输可以通过冲突检测和仲裁防止数据被破坏;

· 串行的8 位双向数据传输位速率在标准模式下可达100kbit/s,快速模式下可达400kbit/s,高速模式下可达3.4Mbit/s;

· 连接到相同总线的IC 数量只受到总线的最大电容400pF 限制。

其典型的接口连线如下:

I2C的协议很简单:

数据的有效性

在传输数据的时候,SDA线必须在时钟的高电平周期保持稳定,SDA的高或低电平状态只有在SCL 线的时钟信号是低电平时才能改变 。

起始和停止条件

SCL 线是高电平时,SDA 线从高电平向低电平切换,这个情况表示起始条件;

SCL 线是高电平时,SDA 线由低电平向高电平切换,这个情况表示停止条件。

字节格式

发送到SDA 线上的每个字节必须为8 位,每次传输可以发送的字节数量不受限制。每个字节后必须处理一个响应位。

应答响应

数据传输必须带响应,相关的响应时钟脉冲由主机产生。在响应的时钟脉冲期间发送器释放SDA 线(高)。

在响应的时钟脉冲期间,接收器必须将SDA 线拉低,使它在这个时钟脉冲的高电平期间保持稳定的低电平。

也就是说主器件发送完一字节数据后要接收一个应答位(低电平),从器件接收完一个字节后要发送一个低电平。

寻址方式(7位地址方式)

第一个字节的头7 位组成了从机地址,最低位(LSB)是第8 位,它决定了传输的 普通的和带重复开始条件的7位地址格式方向。第一个字节的最低位是

“0”,表示主机会写信息到被选中的从机;

“1”表示主机会向从机读信息。

当发送了一个地址后,系统中的每个器件都在起始条件后将头7 位与它自己的地址比较,如果一样,器件会判定它被主机寻址,至于是从机接收器还是从机发送器,都由R/W 位决定。

仲裁

I2C是所主机总线,每个设备都可以成为主机,但任一时刻只能有一个主机。

STM32至少有一个I2C接口,提供多主机功能,可以实现所有I2C总线的时序、协议、仲裁和定时功能,支持标准和快速传输两种模式,同时与SMBus 2.0兼容。

本实验直接操作寄存器实现对I2C总线结构的EEPROM AT24c02的写入和读取。AT24c02相关操作详见 单片机读取EEPROM(AT24C02)。

库函数实现使用STM32的两个I2C模拟I2C设备间的数据收发,并通过串口查看数据交换情况。

直接操作寄存器

首先需要配置I2C接口的时钟,相关寄存器如下:

I2C_CR2寄存器低五位:

FREQ[5:0]:I2C模块时钟频率 ,必须设置正确的输入时钟频率以产生正确的时序,允许的范围在2~36MHz之间:

000000:禁用 000001:禁用 000010:2MHz ... 100100:36MHz 大于100100:禁用。

用于设置I2C设备的输入时钟,本例使用的是PLCK1总线上的时钟所以为36Mhz;

时钟控制寄存器(I2C_CCR)低12位:

CCR[11:0]:快速/标准模式下的时钟控制分频系数(主模式),该分频系数用于设置主模式下的SCL时钟。

在I2C标准模式或SMBus模式下:

Thigh = CCR ×TPCLK1

Tlow = CCR ×TPCLK1

时钟周期为 T = Thigh + Tlow;

例如:在标准模式下,FREQR = 36 即36Mhz,产生200kHz的SCL的频率

时钟控制分频系数 = Freqr /2/f f 为想得到的频率

配置好时钟,还需要配置本机地址,I2C支持7位地址和10位地址,这里用的是7位地址:

自身地址寄存器1(I2C_OAR1)[7:1]:接口地址,地址的7~1位。

其他相关操作参见代码,有详细注释:(system.h 和 stm32f10x_it.h 等相关代码参照 STM32 直接操作寄存器开发环境配置)

User/main.c

01 #include
02 #include "system.h"
03 #include "usart.h"
04 #include "i2c.h"
05
06 #define LED1 PAout(4)
07 #define LED2 PAout(5)
08 #define LED3 PAout(6)
09 #define LED4 PAout(7)
10
11 voidGpio_Init(void);
12
13 intmain(void)
14 {
15
16 Rcc_Init(9);//系统时钟设置
17
18 Usart1_Init(72,9600);
19
20 Nvic_Init(1,0,I2C1_EV_IRQChannel,4);//设置抢占优先级为1,响应优先级为0,中断分组为4
21
22 Nvic_Init(0,0,I2C1_ER_IRQChannel,4);//设置I2C错误中断抢占优先级为0
23
24 Gpio_Init();
25
26 I2c_Init(0x30);//设置I2C1地址为0x30
27
28 I2c_Start();
29
30 while(1);
31 }
32
33
34 voidGpio_Init(void)
35 {
36 RCC->APB2ENR |= 1<<2;//使能PORTA时钟
37 RCC->APB2ENR |= 1<<3;//使能PORTB时钟;
38
39
40 GPIOA->CRL &= 0x0000FFFF;// PA0~3设置为浮空输入,PA4~7设置为推挽输出
41 GPIOA->CRL |= 0x33334444;
42
43
44 GPIOB->CRL &= 0x00FFFFFF;//PB6 I2C1_SCL ,PB7 I2C1_SDL
45 GPIOB->CRL |= 0xFF000000;//复用开漏输出
46
47 //USART1 串口I/O设置
48
49 GPIOA -> CRH &= 0xFFFFF00F;//设置USART1 的Tx(PA.9)为第二功能推挽,50MHz;Rx(PA.10)为浮空输入
50 GPIOA -> CRH |= 0x000008B0;
51
52 }

User/stm32f10x_it.c

001 #include "stm32f10x_it.h"
002 #include "system.h"
003 #include "stdio.h"
004 #include "i2c.h"
005
006 #define LED1 PAout(4)
007 #define LED2 PAout(5)
008 #define LED3 PAout(6)
009 #define LED4 PAout(7)
010
011 #define ADDRS_R 0xA1 //读操作地址
012 #define ADDRS_W 0xA0 //写操作地址
013
014 u8 go = 0;//操作步骤标记
015
016 voidI2C1_EV_IRQHandler(void)//I2C1 Event Interrupt
017 {
018 u16 clear = 0;
019
020 if(I2C1 -> SR1 & 1<<0 )//已发送起始条件,写数据寄存器的操作将清除该位
021 {
022 printf("\r\n I2C1 Start .. \r\n");
023
024 switch(go)
025 {
026 case0:{
027 I2c_Write(ADDRS_W);//写入从机地址,写指令操作地址
028 break;
029 }
030 case1:{
031 I2c_Write(ADDRS_W);//写入从机地址,写指令操作地址
032 break;
033 }
034 case2:{
035 I2c_Write(ADDRS_R);//写入从机地址,读数据操作地址
036 break;
037 }
038 }
039
040 }
041
042 if(I2C1 -> SR1 & 1<<1 )//从机地址已发送
043 {
044 printf("\r\n I2C1 has send address .. \r\n");
045 clear = I2C1 -> SR2;//读取SR2可以清除该位中断
046
047 switch(go)
048 {
049 case0:{
050 I2c_Write(0x01);//写入待写入的EEPROM单元地址
051 break;
052 }
053
054 case1:{
055 I2c_Write(0x01);//写入待写入的EEPROM单元地址
056 break;
057 }
058 case2:{
059 delay(100000);
060 printf("\r\n Read 0x%X from At24c02 ,Address 0x01 .. \r\n",I2c_Read());
061 I2c_Stop();
062 break;
063 }
064 }
065
066 }
067
068 if(I2C1 -> SR1 & 1<<2 )//字节发送结束 发送地址字节时,不触发此中断
069 {
070
071 //printf("\r\n I2C1 send byte success .. \r\n");
072 switch(go)
073 {
074 case0:{
075 I2c_Write(0x86);//写入数据
076 printf("\r\n Write 0x%X to At24c02 ,Address 0x01 .. \r\n",0x86);
077 //I2c_Stop();
078
079 delay(10000);
080 go = 1;
081 I2c_Start();
082 break;
083 }
084
085 case1:{
086
087 delay(10000);
088 go = 2;
089 I2c_Start();
090 break;
091 }
092 case2:{
093
094 break;
095 }
096 }
097
098 }
099
100 delay(100000);
101 LED3 = 1;
102
103 //I2C1 -> CR2 &= ~(1<<9); //事件中断关闭
104 }
105
106 voidI2C1_ER_IRQHandler(void)//I2C1 Error Interrupt
107 {
108 delay(100000);
109 LED4 = 1;
110
111 if(I2C1->SR1 & 1<<10)//应答失败
112 {
113 printf("\r\n ACK ERROR .. \r\n");
114
115 I2C1->SR1 &=~(1<<10);//清除中断
116 }
117
118 if(I2C1->SR1 & 1<<14)//超时
119 {
120 printf("\r\n Timeout .. \r\n");
121
122 I2C1->SR1 &=~(1<<14);//清除中断
123 }
124
125 if(I2C1->SR1 & 1<<11)//过载/欠载
126 {
127 printf("\r\n Overrun/Underrun .. \r\n");
128 I2C1->SR1 &=~(1<<11);//清除中断
129 }
130
131 if(I2C1->SR1 & 1<<9)//仲裁丢失
132 {
133 printf("\r\n Arbitration lost .. \r\n");
134 I2C1->SR1 &=~(1<<9);//清除中断
135 }
136
137 if(I2C1->SR1 & 1<<8)//总线出错
138 {
139 printf("\r\n Bus error .. \r\n");
140 I2C1->SR1 &=~(1<<8);//清除中断
141 }
142
143
144 }

Library/src/i2c.c

view sourceprint?

01 #include "i2c.h"
02
03 voidI2c_Init(u16 Addr )
04 {
05
06 RCC -> APB1ENR |= 1<<21;//打开I2C1时钟
07 //RCC -> APB1ENR |= 1<<22; //打开I2C2时钟
08
09 RCC->APB1RSTR |= 1<<21;//复位I2C1
10 RCC->APB1RSTR &= ~(1<<21);//复位结束I2C1
11 //RCC->APB1RSTR |= 1<<22; //复位I2C2
12
13 //I2C1 -> CR1 |= 1<<15; //复位寄存器
14
15 //I2C模块时钟频率,2~36MHz之间
16 I2C1 -> CR2 |= 36 ;//000000:禁用 000001:禁用 000010:2MHz ... 100100:36MHz
17
18
19 I2C1 -> CCR |= 0<<15;//I2C主模式 0:标准模式的I2C 1:快速模式的I2C
20 //I2C1 -> CCR |= 1<<14; //快速模式时的占空比 0 Tlow/Thigh = 2 1 Tlow/Thigh = 16/9
21
22 //得到200kHz频率
23 I2C1 -> CCR |= 90<<0;//时钟控制分频系数 = PCLK1 /2/f f 为想得到的频率
24
25 //主模式最大上升时间
26 I2C1 -> TRISE |= 37;//最大允许SCL上升时间为1000ns,故TRISE[5:0]中必须写入(1us/(1/36)us = 36+1)。
27
28 I2C1 -> CR1 |= 1<<10;//打开ACK应答,在接收到一个字节后返回一个应答
29 I2C1 -> CR1 |= 1<<6;//广播呼叫使能
30
31 I2C1 -> OAR1 |= 0<<15;//寻址模式 1 响应10位地址 0 响应7位地址
32
33 I2C1 -> OAR1 |= 1<<14;//必须始终由软件保持为 1
34
35 I2C1 -> OAR1 |= Addr <<1 ;//设置接口地址的 7~1位
36
37 //I2C1 -> OAR1 |= 0 ; //设置10位地址模式时地址第0位
38 //I2C1 -> OAR1 |= 0<<8; //设置10位地址模式时地址第9~8位
39
40 //I2C1 -> CR2 |= 1<<10; //缓冲器中断使能
41 I2C1 -> CR2 |= 1<<9;//事件中断使能
42 I2C1 -> CR2 |= 1<<8;//出错中断使能
43
44 I2C1 -> CR1 |= 1<<0;//开启I2C1
45 }
46
47
48 voidI2c_Start()
49 {
50
51 I2C1 -> CR1 |= 1<<8;//I2C1产生起始条件
52 }
53
54 voidI2c_Stop()
55 {
56 I2C1 -> CR1 |= 1<<9;//I2C1产生停止条件
57 }
58
59
60 voidI2c_Write(u8 data)
61 {
62 I2C1 -> DR = data;
63 }
64
65 u8 I2c_Read()
66 {
67 while(!(I2C1 -> SR1 & 1<<6));//接收到数据标志位
68
69 returnI2C1 -> DR;
70 }
71
72 voidI2c_End()//关闭I2C
73 {
74 I2C1 -> CR1 &= ~(1<<0);
75 }

Library/inc/i2c.h

1 #include
2
3 voidI2c_Init(u16 Addr );
4
5 voidI2c_Start(void);
6 voidI2c_Stop(void);
7 voidI2c_Write(u8 data);
8 u8 I2c_Read(void);
9 voidI2c_End(void);

串口接收数据如下:

I2C1 Start ..

I2C1 has send address ..

Write 0x86 to At24c02 ,Address 0x01 ..

I2C1 Start ..

I2C1 has send address ..

I2C1 Start ..

I2C1 has send address ..

Read 0x86 from At24c02 ,Address 0x01 ..

库函数操作

main.c

001 #include "stm32f10x.h"
002 #include "stdio.h"
003
004 #define PRINTF_ON 1
005
006 voidRCC_Configuration(void);
007 voidGPIO_Configuration(void);
008 voidUSART_Configuration(void);
009 voidI2C_Configuration(void);
010 voidNVIC_Configuration(void);
011
012
013 u8 I2C1_ADDRESS = 0x30;//7位 I2C 地址
014 u8 I2C2_ADDRESS = 0x31;
015
016 #define Size 4
017
018 vu8 I2C1_Buffer_Tx[Size] = {1,2,3,4};
019 vu8 I2C2_Buffer_Rx[Size] = {0};
020
021 u32 BufferSize = Size ;
022
023 intmain(void)
024 {
025 RCC_Configuration();
026 GPIO_Configuration();
027 USART_Configuration();
028 I2C_Configuration();
029 NVIC_Configuration();
030
031 I2C_GenerateSTART(I2C1,ENABLE);
032
033 while(1);
034 }
035
036 voidI2C_Configuration(void)
037 {
038 I2C_InitTypeDef I2C_InitStructure;
039
040 I2C_InitStructure.I2C_Mode = I2C_Mode_I2C;
041 I2C_InitStructure.I2C_DutyCycle = I2C_DutyCycle_2;
042 I2C_InitStructure.I2C_OwnAddress1 = I2C1_ADDRESS;
043 I2C_InitStructure.I2C_Ack = I2C_Ack_Enable;
044 I2C_InitStructure.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit;
045 I2C_InitStructure.I2C_ClockSpeed = 200000;
046 I2C_Init(I2C1,&I2C_InitStructure);
047
048 I2C_InitStructure.I2C_Mode = I2C_Mode_I2C;
049 I2C_InitStructure.I2C_DutyCycle = I2C_DutyCycle_2;
050 I2C_InitStructure.I2C_OwnAddress1 = I2C2_ADDRESS;
051 I2C_InitStructure.I2C_Ack = I2C_Ack_Enable;
052 I2C_InitStructure.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit;
053 I2C_InitStructure.I2C_ClockSpeed = 200000;
054 I2C_Init(I2C2,&I2C_InitStructure);
055
056
057 I2C_ITConfig(I2C1,I2C_IT_EVT|I2C_IT_BUF,ENABLE);
058 I2C_ITConfig(I2C2,I2C_IT_EVT|I2C_IT_BUF,ENABLE);
059
060 I2C_Cmd(I2C1,ENABLE);
061 I2C_Cmd(I2C2,ENABLE);
062 }
063
064 voidNVIC_Configuration(void)
065 {
066 NVIC_InitTypeDef NVIC_InitStructure;
067
068 NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
069
070 NVIC_InitStructure.NVIC_IRQChannel = I2C1_EV_IRQn;
071 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
072 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
073 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
074 NVIC_Init(&NVIC_InitStructure);
075
076 NVIC_InitStructure.NVIC_IRQChannel = I2C2_EV_IRQn;
077 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
078 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
079 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
080 NVIC_Init(&NVIC_InitStructure);
081 }
082
083 voidGPIO_Configuration(void)
084 {
085 GPIO_InitTypeDef GPIO_InitStructure;
086
087 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
088
089 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6|GPIO_Pin_7;
090 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_OD;
091 GPIO_Init(GPIOB , &GPIO_InitStructure);
092
093 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10|GPIO_Pin_11;
094 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
095 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_OD;
096 GPIO_Init(GPIOB , &GPIO_InitStructure);
097
098
099 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
100 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
101 GPIO_Init(GPIOA , &GPIO_InitStructure);
102
103 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;
104 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
105 GPIO_Init(GPIOA , &GPIO_InitStructure);
106 }
107
108 voidRCC_Configuration(void)
109 {
110 /* 定义枚举类型变量 HSEStartUpStatus */
111 ErrorStatus HSEStartUpStatus;
112
113 /* 复位系统时钟设置*/
114 RCC_DeInit();
115 /* 开启HSE*/
116 RCC_HSEConfig(RCC_HSE_ON);
117 /* 等待HSE起振并稳定*/
118 HSEStartUpStatus = RCC_WaitForHSEStartUp();
119 /* 判断HSE起是否振成功,是则进入if()内部 */
120 if(HSEStartUpStatus == SUCCESS)
121 {
122 /* 选择HCLK(AHB)时钟源为SYSCLK 1分频 */
123 RCC_HCLKConfig(RCC_SYSCLK_Div1);
124 /* 选择PCLK2时钟源为 HCLK(AHB) 1分频 */
125 RCC_PCLK2Config(RCC_HCLK_Div1);
126 /* 选择PCLK1时钟源为 HCLK(AHB) 2分频 */
127 RCC_PCLK1Config(RCC_HCLK_Div2);
128 /* 设置FLASH延时周期数为2 */
129 FLASH_SetLatency(FLASH_Latency_2);
130 /* 使能FLASH预取缓存 */
131 FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);
132 /* 选择锁相环(PLL)时钟源为HSE 1分频,倍频数为9,则PLL输出频率为 8MHz * 9 = 72MHz */
133 RCC_PLLConfig(RCC_PLLSource_HSE_Div1, RCC_PLLMul_9);
134 /* 使能PLL */
135 RCC_PLLCmd(ENABLE);
136 /* 等待PLL输出稳定 */
137 while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET);
138 /* 选择SYSCLK时钟源为PLL */
139 RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);
140 /* 等待PLL成为SYSCLK时钟源 */
141 while(RCC_GetSYSCLKSource() != 0x08);
142 }
143 /* 打开APB2总线上的GPIOA时钟*/
144 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_GPIOB|RCC_APB2Periph_USART1, ENABLE);
145
146 //RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);
147
148 RCC_APB1PeriphClockCmd(RCC_APB1Periph_I2C1|RCC_APB1Periph_I2C2,ENABLE);
149 //RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR|RCC_APB1Periph_BKP|RCC_APB1Periph_WWDG|RCC_APB1Periph_SPI2, ENABLE);
150
151 }
152
153
154 voidUSART_Configuration(void)
155 {
156 USART_InitTypeDef USART_InitStructure;
157 USART_ClockInitTypeDef USART_ClockInitStructure;
158
159 USART_ClockInitStructure.USART_Clock = USART_Clock_Disable;
160 USART_ClockInitStructure.USART_CPOL = USART_CPOL_Low;
161 USART_ClockInitStructure.USART_CPHA = USART_CPHA_2Edge;
162 USART_ClockInitStructure.USART_LastBit = USART_LastBit_Disable;
163 USART_ClockInit(USART1 , &USART_ClockInitStructure);
164
165 USART_InitStructure.USART_BaudRate = 9600;
166 USART_InitStructure.USART_WordLength = USART_WordLength_8b;
167 USART_InitStructure.USART_StopBits = USART_StopBits_1;
168 USART_InitStructure.USART_Parity = USART_Parity_No;
169 USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
170 USART_InitStructure.USART_Mode = USART_Mode_Rx|USART_Mode_Tx;
171 USART_Init(USART1,&USART_InitStructure);
172
173 USART_Cmd(USART1,ENABLE);
174 }
175
176 #if PRINTF_ON
177
178 intfputc(intch,FILE*f)
179 {
180 USART_SendData(USART1,(u8) ch);
181 while(USART_GetFlagStatus(USART1,USART_FLAG_TC) == RESET);
182 returnch;
183 }
184
185 #endif

stm32f10x_it.c

view sourceprint?

01 #include "stm32f10x_it.h"
02 #include "stdio.h"
03
04 externu32 BufferSize ;
05 externu8 I2C1_ADDRESS ;
06 externu8 I2C2_ADDRESS ;
07
08 externvu8 I2C1_Buffer_Tx[];
09 externvu8 I2C2_Buffer_Rx[];
10 vu32 Tx_Counter = 0;
11 vu32 Rx_Counter = 0;
12
13 voidI2C1_EV_IRQHandler(void)
14 {
15 switch(I2C_GetLastEvent(I2C1))
16 {
17 caseI2C_EVENT_MASTER_MODE_SELECT://已发送启始条件
18 {
19 I2C_Send7bitAddress(I2C1,I2C2_ADDRESS,I2C_Direction_Transmitter);
20 break;
21 }
22 caseI2C_EVENT_MASTER_TRANSMITTER_MODE_SELECTED://已发送从机地址
23 {
24 printf("\r\n The I2C1 has send data %d \r\n",I2C1_Buffer_Tx[Rx_Counter]);
25 I2C_SendData(I2C1,I2C1_Buffer_Tx[Tx_Counter++]);
26 break;
27 }
28 caseI2C_EVENT_MASTER_BYTE_TRANSMITTED://第一个数据已发送
29 {
30 if(Tx_Counter
31 {
32 printf("\r\n The I2C1 has send data %d \r\n",I2C1_Buffer_Tx[Rx_Counter]);
33 I2C_SendData(I2C1,I2C1_Buffer_Tx[Tx_Counter++]);
34
35 }else{
36 I2C_GenerateSTOP(I2C1,ENABLE);
37 I2C_ITConfig(I2C1,I2C_IT_EVT|I2C_IT_BUF,DISABLE);//计数发送的个数
38 }
39
40 break;
41 }
42 default: {break;}
43 }
44 }
45
46
47 voidI2C2_EV_IRQHandler(void)
48 {
49 switch(I2C_GetLastEvent(I2C2))
50 {
51 caseI2C_EVENT_SLAVE_RECEIVER_ADDRESS_MATCHED://收到匹配的地址数据
52 {
53 break;
54 }
55 caseI2C_EVENT_SLAVE_BYTE_RECEIVED://收到数据
56 {
57 if(Rx_Counter < BufferSize )
58 {
59 I2C2_Buffer_Rx[Rx_Counter] = I2C_ReceiveData(I2C2);
60 printf("\r\n The I2C2 has received data %d \r\n",I2C2_Buffer_Rx[Rx_Counter++]);//计数收到的个数
61 }
62 break;
63 }
64 caseI2C_EVENT_SLAVE_STOP_DETECTED://收到结束条件
65 {
66 I2C_ClearFlag(I2C2,I2C_FLAG_STOPF);
67 I2C_ITConfig(I2C1,I2C_IT_EVT|I2C_IT_BUF,DISABLE);
68
69 break;
70 }
71 default: {break;}
72 }
73 }

编辑:admin 最后修改时间:2018-05-18

联系方式

0755-82591179

传真:0755-82591176

邮箱:vicky@yingtexin.net

地址:深圳市龙华区民治街道民治大道973万众润丰创业园A栋2楼A08

Copyright ? 2014-2023 All Rights Reserved.粤ICP备14043402号-4

Baidu
map