1. Overview
I2C (IIC, Inter-Integrated Circuit), a two-wire serial bus, was developed by PHILIPS to connect microcontrollers and their peripherals.
It is a serial bus composed of data line SDA and clock SCL, which can send and receive data. It can transmit data bidirectionally between CPU and controlled IC, and between IC and IC. High-speed IIC bus can generally reach more than 400kbps. But in STM8, 400kHZ is the fastest speed.
It is often involved in subsequent module debugging and is a very common and easy-to-use protocol.
2. Introduction to I2C in the STM8S103 manual
After reading the Chinese manual, I personally feel that it is relatively simple. I will post the specific usage later.
3. Detailed Analysis of I2C
I2C has five core functions in total, namely:
①Start signal
②Stop signal
③Response signal
④Send data
⑤Receive data
These five core basic functions are sufficient to communicate with most sensors.
The following is a detailed introduction to each part, and some main codes are attached for your reference.
3.1 Start signal
When SCL is at a high level, SDA changes from a high level to a low level; the start signal is a level jump timing signal, not a level signal, as shown in the dotted box in the figure above.
1 2 3 4 5 6 7 8 9 10 11 12 | void Start_Signal_IIC_(void){ //Start signal: GPIO_WriteHigh(GPIOD, GPIO_PIN_2); //Data line IIC_Delay_4us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_3); //Clock line IIC_Delay_4us(); GPIO_WriteLow(GPIOD, GPIO_PIN_2); //Data line IIC_Delay_4us(); GPIO_WriteLow(GPIOD, GPIO_PIN_3); //Clock line IIC_Delay_4us(); } |
3.2 Stop Signal
When SCL is at a high level, SDA changes from a low level to a high level; the stop signal is also a level jump timing signal, not a level signal, as shown in the dotted box in the figure above.
1 2 3 4 5 6 7 | void End_Data_IIC_() { GPIO_WriteLow(GPIOD, GPIO_PIN_2); //Pull the data line low IIC_Delay_4us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_3); //Pull the clock line high IIC_Delay_4us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_2); //Pull the data line high |
1 | } |
3.3 Response signal
There are two types of response signals: active response signal and active non-response signal.
①Ack (actively pull down SDA to form a response signal)
The data of the I2C bus are transmitted in bytes (8 bits). After the sending device sends a byte, the data bus is released during the 9th pulse of the clock, and the receiver sends an ACK (pulling the level of the data bus low) to indicate that the data has been successfully received.
1 2 3 4 5 6 7 8 9 | //Active response signal void vIIC_Ack() { GPIO_WriteLow(GPIOD, GPIO_PIN_2); IIC_Delay_4us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); GPIO_WriteLow(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); } |
②NAck (actively does not pull down SDA and does not form a response signal)
During the 9th pulse of the clock, the transmitter releases the data bus, and the receiver does not pull the data bus low, indicating a NACK. NACK has two uses:
a. Generally indicates that the receiver did not successfully receive the data byte;
b. When the receiver is the master, after receiving the last byte, it should send a NACK signal to notify the controlled transmitter to end data transmission and release the bus so that the master receiver can send a stop signal STOP.
1 2 3 4 5 6 7 8 9 10 | // Actively do not answer void vIIC_NAck() { GPIO_WriteHigh(GPIOD, GPIO_PIN_2); IIC_Delay_4us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); GPIO_WriteLow(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); } |
③ReadAck (wait for response signal)
This signal is used when the host is waiting for a response from the slave after sending data.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | u8 bIIC_ReadACK() { GPIO_Init(GPIOD, GPIO_PIN_2, GPIO_MODE_IN_PU_IT); //Change SDA to input mode. GPIO_WriteHigh(GPIOD, GPIO_PIN_3); //Pull the clock line high. IIC_Delay_4us(); if(IIC_SDA_R != 0) { //Low has response GPIO_WriteLow(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); GPIO_Init(GPIOD, GPIO_PIN_2, GPIO_MODE_OUT_PP_HIGH_FAST);//SDA return 1; } else //High no response { GPIO_WriteLow(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); GPIO_Init(GPIOD, GPIO_PIN_2, GPIO_MODE_OUT_PP_HIGH_FAST);//SDA return 0; } } |
3.4 Sending Data
After sending the start signal, the communication begins and the master sends an 8-bit data. Then, the master releases the SDA line and waits for the confirmation signal (ACK) from the slave.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | void Send_Data_IIC_(uint8_t Data){ int i; //Pull down the data line and clock line GPIO_WriteLow(GPIOD, GPIO_PIN_3); GPIO_WriteLow(GPIOD, GPIO_PIN_2); for(i=0;i<8;i++) { if(Data&0x80) GPIO_WriteHigh(GPIOD, GPIO_PIN_2); else GPIO_WriteLow(GPIOD, GPIO_PIN_2); Data= Data<<1; IIC_Delay_2us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); GPIO_WriteLow(GPIOD, GPIO_PIN_3); IIC_Delay_2us(); } } |
3.5 Receiving Data
After sending the start signal, the communication starts, and the host sends an 8-bit data. Then, the slave receives the data and returns an acknowledgment signal (ACK) to the host. Only then does the host start receiving data. After the host completes receiving the data, it sends a NACK signal to the slave to notify the receiving end to end data reception.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 | //Receive function uint8_t uIIC_RecvByte() { uint8_t i,uReceiveByte = 0; GPIO_Init(GPIOD, GPIO_PIN_2, GPIO_MODE_IN_PU_IT); for(i=0;i<8;i++) { uReceiveByte <<= 1; IIC_Delay_4us(); GPIO_WriteHigh(GPIOD, GPIO_PIN_3); //Read data level when the clock line is high IIC_Delay_4us(); if(IIC_SDA_R !=0 ) { uReceiveByte|=0x01; } IIC_Delay_4us(); GPIO_WriteLow(GPIOD, GPIO_PIN_3); IIC_Delay_4us(); } GPIO_Init(GPIOD, GPIO_PIN_2, GPIO_MODE_OUT_PP_HIGH_FAST); return uReceiveByte; } |
3.6 I2C communication overall process
The following figure perfectly illustrates the changes of SDA and SCL lines during the whole process of iic from receiving to sending. Combined with the above explanation and process code, this figure can help memory and understanding.
4. Routines
4.1 Compilation environment:
IAR is used here for compilation, which is relatively easy to use. In the future, when using the STM32 development board, it is recommended to use CUBE to directly generate the initialization function, which is very convenient to use with Keil5.
4.2 Main chip:
My main chip is 103 in the STM8S series. Among them, STM8S 003, 005, 103, 105 have the same configuration (peripherals and CPU frequency, FLASH), and can be burned if the code is the same.
4.3 Code & Analysis
The iic code can drive almost all clock modules on the market, so the code here can call the code of the clock module. I have explained each function, you can learn more about it.
From the above code, we can know that this protocol is composed of data line and clock line. Data transmission and reception require pulling up the data line or pulling down the clock line. So it is recommended to use the library function to pull up and down directly. If you want convenience, adding a macro definition can be more intuitive and convenient.
5. Conclusion
The above are the core functions of iic. I have written each function very clearly. In the next blog, I will post the sensor communication blog based on the iic clock module. You can continue to read the next blog for reference.
Previous article:Renaming an existing project to another project in STVD
Next article:Detailed explanation of STM8 IAP upgrade program design - IAR environment
Recommended ReadingLatest update time:2024-11-15 18:03
- Popular Resources
- Popular amplifiers
- Mission-oriented wireless communications for cooperative sensing in intelligent unmanned systems
- Autonomous mobile robots and multi-robot systems motion-planning, communication, and swarming (Kagan
- STM8 C language programming (1) - basic program and startup code analysis
- Description of the BLDC back-EMF sampling method based on the STM8 official library
Professor at Beihang University, dedicated to promoting microcontrollers and embedded systems for over 20 years.
- LED chemical incompatibility test to see which chemicals LEDs can be used with
- Application of ARM9 hardware coprocessor on WinCE embedded motherboard
- What are the key points for selecting rotor flowmeter?
- LM317 high power charger circuit
- A brief analysis of Embest's application and development of embedded medical devices
- Single-phase RC protection circuit
- stm32 PVD programmable voltage monitor
- Introduction and measurement of edge trigger and level trigger of 51 single chip microcomputer
- Improved design of Linux system software shell protection technology
- What to do if the ABB robot protection device stops
- P22-009_Butterfly E3106 Cord Board Solution
- Keysight Technologies Helps Samsung Electronics Successfully Validate FiRa® 2.0 Safe Distance Measurement Test Case
- Innovation is not limited to Meizhi, Welling will appear at the 2024 China Home Appliance Technology Conference
- Innovation is not limited to Meizhi, Welling will appear at the 2024 China Home Appliance Technology Conference
- Huawei's Strategic Department Director Gai Gang: The cumulative installed base of open source Euler operating system exceeds 10 million sets
- Download from the Internet--ARM Getting Started Notes
- Learn ARM development(22)
- Learn ARM development(21)
- Learn ARM development(20)
- Learn ARM development(19)
- How much do you know about the rising star of CAT1?
- The Hall sensor signal is asymmetric and the HALL C high level is too low. What is the cause? How to solve it?
- [Reprint] "Very Silly" Circuit Problem (Part 2)
- Find a DC circuit that outputs positive and negative 12V output
- Sensor Problems
- Thank you~ee
- The company's idle equipment, antique goods, if you need them, come
- Pay attention! Nine commonly overlooked ADC technical specifications
- Do you want to improve your ability to manage tests in the automotive industry? This is the right article for you!
- Analysis of transistor drive circuit and level conversion