1, Introduction to STM32F103C8T6
STM32F103C8T6 is a 32-bit microcontroller based on Cortex-M3 core launched by St. the hardware is packaged with LQFP48 and belongs to STM32 series of microcontrollers of ST company. All the information can be downloaded from the wildfire official website Wildfire data download center
2, Light up
To turn on the LED, you need to use the GPIO port.
In order to turn on the LED, three steps are required:
- Open the clock of GPIO port
- Initialize GPIO port (select push-pull output)
- Set low level
(1) Turn on the clock
- Address of GPIO:
- Clock address:
-
That is 0x40021018, to open the clock of three IO ports, you need to set all three bits to 1:
#define RCC_APB2ENR (*(unsigned int *)0x40021018) // Turn on the clock RCC_APB2ENR |= (1<<3); // Turn on GPIOB clock RCC_APB2ENR |= (1<<4); // Turn on GPIOC clock RCC_APB2ENR |= (1<<2); // Turn on GPIOA clock
(2) Initialization
The GPIO port has eight modes:
- Input float
- Input pull-up
- Input drop-down
- Analog input
- Open drain output
- push-pull outputs
- Push pull multiplexing function
- Open drain multiplexing function
Push pull output is used here
Ports 1-7 are low and ports 8-15 are high. Each pin is controlled by four bits.
Take GPIOB and pin 0 (B0) as an example, set it as push-pull output, and set the maximum speed to 10MHz, then set the four bits of control B0 to 0001:
#define GPIOB_CRL (*(unsigned int *)0x40010c00) // The last four digits change to 0001 GPIOB_CRL |= (1<<0); // The last bit changes to 1 GPIOB_CRL &= ~(0xE<<0); // The reciprocal 2, 3 and 4 bits change to 0
For B0 of GPIOB, C15 of GPIOC and A0 of GPIOA, the settings are as follows:
#define GPIOB_CRL (*(unsigned int *)0x40010C00) #define GPIOC_CRH (*(unsigned int *)0x40011004) #define GPIOA_CRL (*(unsigned int *)0x40010800) // Configure GPIO port as push free output // GPIOB --- the last four digits are 0001 GPIOB_CRL |= (1<<0); // The last bit changes to 1 GPIOB_CRL &= ~(0xE<<0); // The reciprocal 2, 3 and 4 bits change to 0 // GPIOC --- the first four digits are 0001 GPIOC_CRH |= (1<<28); // The fourth bit changes to 1 GPIOC_CRH &= ~(0xE0000000); // The first three digits change to 0 // GPIOA --- the last four digits are 0001 GPIOA_CRL |= (1<<0); // The last bit changes to 1 GPIOA_CRL &= ~(0xE<<0); // The reciprocal 2, 3 and 4 bits change to 0
(3) Set low level
The output high level is 1 and the low level is 0
Take GPIOB and pin 0 (B0) as an example, set them to low level
#define GPIOB_ODR (*(unsigned int *)0x40010C0C) GPIOB_ODR &= ~(1<<0); // The last bit becomes 0
For B0 of GPIOB, C15 of GPIOC and A0 of GPIOA, the settings are as follows:
#define GPIOB_ODR (*(unsigned int *)0x40010C0C) #define GPIOC_ODR (*(unsigned int *)0x4001100C) #define GPIOA_ODR (*(unsigned int *)0x4001080C) GPIOB_ODR &= ~(1<<0); //The last bit becomes 0 GPIOC_ODR &= ~(1<<15); //The last 16 bits become 0 GPIOA_ODR &= ~(1<<0); //The last digit becomes
3, keil create project
1. Create a new uVision project
2. Select an appropriate location to name and save
3. The chip selects STM32F103C8 under STM32F103
4. Copy and paste the startup_stm32f10x_md.s file into the directory of the project file just created, which is generally located in the directory of yehuo [STM32F103C8T6 - core board] data / 3-USART1 receiving and sending / Libraries/CMSIS/startup /
5. Introduce startup_stm32f10x_md.s
6. Create a new main.c file
7.main.c code
#define GPIOB_BASE 0x40010C00 #define GPIOC_BASE 0x40011000 #define GPIOA_BASE 0x40010800 #define RCC_APB2ENR (*(unsigned int *)0x40021018) #define GPIOB_CRL (*(unsigned int *)0x40010C00) #define GPIOC_CRH (*(unsigned int *)0x40011004) #define GPIOA_CRL (*(unsigned int *)0x40010800) #define GPIOB_ODR (*(unsigned int *)0x40010C0C) #define GPIOC_ODR (*(unsigned int *)0x4001100C) #define GPIOA_ODR (*(unsigned int *)0x4001080C) void SystemInit(void); void Delay_ms(volatile unsigned int); void Delay_ms( volatile unsigned int t) { unsigned int i; while(t--) for (i=0;i<800;i++); } int main(){ // ???? RCC_APB2ENR |= (1<<3); // ?? GPIOB ?? RCC_APB2ENR |= (1<<4); // ?? GPIOC ?? RCC_APB2ENR |= (1<<2); // ?? GPIOA ?? // ?? GPIO ????? // ?? GPIOB ????? 0001 (B0) GPIOB_CRL |= (1<<0); // ???????1 GPIOB_CRL &= ~(0xE); // ???????????0 // ?? GPIOC ???? 0001 (C15) GPIOC_CRH |= (1<<28); // ??????1 GPIOC_CRH &= ~(0xE0000000); // ??????0 // ?? GPIOA ????? 0001 (A0) GPIOA_CRL |= (1<<0); // ???????1 GPIOA_CRL &= ~(0xE); // ???????????0 // 3?LED??????(????) GPIOB_ODR |= (1<<0); // ???????1 GPIOC_ODR |= (1<<15); // ???15????1 GPIOA_ODR |= (1<<0); // ???????1 while(1){ GPIOB_ODR &= ~(1<<0); // ??1 Delay_ms(1000000); GPIOB_ODR |= (1<<0); // ??1 Delay_ms(1000000); GPIOC_ODR &= ~(1<<15); // ??2 Delay_ms(1000000); GPIOC_ODR |= (1<<15); // ??2 Delay_ms(1000000); GPIOA_ODR &= ~(1<<0); // ??3 Delay_ms(1000000); GPIOA_ODR |= (1<<0); // ??3 Delay_ms(1000000); } } void SystemInit(){ }
4, Connecting circuit
For USB to TTL module and stm32f103c8t6 connection
GND — GND
3v3 — 3v3
TXD — A10
RXD — A9
5, Compiling and burning code
(1) Compile
1. Select Create hex file
2.bulid generates. hex files
3. Generate Object/test4.hex successfully (test5 is changed to test4 because the project has been rebuilt)
(2) Preparation for burning
1. Download CH341SerSetup.exe, install it with administrator privileges, and load the USB serial port driver
2. Download one of FlyMcu.exe or mcuisp.exe to facilitate burning
(3) Burning program
Burn with FlyMcu
(4) Results
6, Assembler implementation
RCC_APB2ENR EQU 0x40021018;to configure RCC register,Clock,0x40021018 Is the clock address GPIOB_BASE EQU 0x40010C00 GPIOC_BASE EQU 0x40011000 GPIOA_BASE EQU 0x40010800 GPIOB_CRL EQU 0x40010C00 GPIOC_CRH EQU 0x40011004 GPIOA_CRL EQU 0x40010800 GPIOB_ODR EQU 0x40010C0C GPIOC_ODR EQU 0x4001100C GPIOA_ODR EQU 0x4001080C Stack_Size EQU 0x00000400;Stack size AREA STACK, NOINIT, READWRITE, ALIGN=3 ;NOINIT: = NO Init,Not initialized. READWRITE : Readable and writable. ALIGN =3 : 2^3 Alignment, i.e. 8-byte alignment. Stack_Mem SPACE Stack_Size __initial_sp AREA RESET, DATA, READONLY __Vectors DCD __initial_sp ; Top of Stack DCD Reset_Handler ; Reset Handler AREA |.text|, CODE, READONLY THUMB REQUIRE8 PRESERVE8 ENTRY Reset_Handler bl LED_Init;bl: A linked jump instruction. When using this instruction to jump, the current address(PC)It will be sent automatically LR register MainLoop BL LED_ON_C BL Delay BL LED_OFF_C BL Delay BL LED_ON_A BL Delay BL LED_OFF_A BL Delay BL LED_ON_B BL Delay BL LED_OFF_B BL Delay B MainLoop;B:Unconditional jump. LED_Init;LED initialization PUSH {R0,R1, LR};R0,R1,LR Put the values in the stack ;Control clock LDR R0,=RCC_APB2ENR;LDR Is to load the address into the register(such as R0). ORR R0,R0,#0x1c LDR R1,=RCC_APB2ENR STR R0,[R1] ;initialization GPIOA_CRL LDR R0,=GPIOA_CRL BIC R0,R0,#0x0fffffff;BIC reverses the immediate number first, and then compares it by bit LDR R1,=GPIOA_CRL STR R0,[R1] LDR R0,=GPIOA_CRL ORR R0,#0x00000001 LDR R1,=GPIOA_CRL STR R0,[R1] ;take PA0 Set 1 MOV R0,#0x01 LDR R1,=GPIOA_ORD STR R0,[R1] ;initialization GPIOB_CRL LDR R0,=GPIOB_CRL BIC R0,R0,#0x0fffffff;BIC reverses the immediate number first, and then compares it by bit LDR R1,=GPIOB_CRL STR R0,[R1] LDR R0,=GPIOB_CRL ORR R0,#0x00000001 LDR R1,=GPIOB_CRL STR R0,[R1] ;take PB0 Set 1 MOV R0,#0x01 LDR R1,=GPIOA_ORD STR R0,[R1] ;initialization GPIOC LDR R0,=GPIOC_CRH BIC R0,R0,#0x0fffffff LDR R1,=GPIOC_CRH STR R0,[R1] LDR R0,=GPIOC_CRH ORR R0,#0x01000000 LDR R1,=GPIOC_CRH STR R0,[R1] ;take PC15 Set 1 MOV R0,#0x8000 LDR R1,=GPIOC_ORD STR R0,[R1] POP {R0,R1,PC};Store the previously stored in the stack R0,R1,LR Value returned to R0,R1,PC LED_ON_A PUSH {R0,R1, LR} MOV R0,#0x00 LDR R1,=GPIOA_ORD STR R0,[R1] POP {R0,R1,PC} LED_OFF_A PUSH {R0,R1, LR} MOV R0,#0x01 LDR R1,=GPIOA_ORD STR R0,[R1] POP {R0,R1,PC} LED_ON_B;Light up PUSH {R0,R1, LR} MOV R0,#0x00 LDR R1,=GPIOB_ORD STR R0,[R1] POP {R0,R1,PC} LED_OFF_B;Turn off the light PUSH {R0,R1, LR} MOV R0,#0x01 LDR R1,=GPIOB_ORD STR R0,[R1] POP {R0,R1,PC} LED_ON_C;Light up PUSH {R0,R1, LR} MOV R0,#0x00 LDR R1,=GPIOC_ORD STR R0,[R1] POP {R0,R1,PC} LED_OFF_C;Turn off the light PUSH {R0,R1, LR} MOV R0,#0x0100 LDR R1,=GPIOC_ORD STR R0,[R1] POP {R0,R1,PC} Delay PUSH {R0,R1, LR} MOVS R0,#0 MOVS R1,#0 MOVS R2,#0 DelayLoop0 ADDS R0,R0,#1 CMP R0,#330 BCC DelayLoop0 MOVS R0,#0 ADDS R1,R1,#1 CMP R1,#330 BCC DelayLoop0 MOVS R0,#0 MOVS R1,#0 ADDS R2,R2,#1 CMP R2,#15 BCC DelayLoop0 POP {R0,R1,PC} NOP END
7, Summary
The running water lamp experiment of stm32 chip takes into account the practical ability and other aspects. The code burning fails and the serial port cannot be opened. It may be that there is no download driver, the USB driver fails, or the circuit problem. This experiment has a certain understanding of the input and output, working principle and register address of each serial port of stm32 chip. If the personal mastery is not deep enough, there will be failure in all links There is no end to learning. Through continuous learning, we will better understand these contents and find appropriate methods.