STM32+W5500 network communication
Board: STM32F103C8
Module: W5500
Transplantation system: uc/OS-III
Compiler: keil & stm32cubemx
Burning tool: FlyMcu
1, W5500 & demos
1. W5500 Ethernet module
Niren_W5500 module is an Ethernet module based on WIZnet W5500 chip, which is the successor of clay figurine electronics Niren_W5100 module is an Ethernet module with better performance and higher cost performance. Module integrated hardware TCP/IP protocol: internal 32K byte memory as TX/RX
Cache: support 10/100Mbps transmission rate; Support the simultaneous operation of 8 independent ports; At the same time, the module also supports 3.3V or 5V power supply. When 5V power supply, it can also output 3.3V power supply, which is convenient for users to use in different single chip microcomputer systems; The communication mode between module and MCU system is simple and convenient SPI communication.
Row pin identification | Function description | Connection method | Row pin identification | Function description | |
---|---|---|---|---|---|
3.3V | 3.3V power input pin | – | 5V | 5V power input pin | – |
MISO | SPI master input slave output pin | A6 | GND | Power ground pin | – |
MOSI | SPI master output slave input pin | A7 | RST | W5500 hardware initialization pin (active at low level) | A15 |
SCS | SPI SLAVE select pin (active at low level) | A4 | INT | W5500 interrupt pin (active at low level) | C4 |
SCLK | SPI clock pin | A5 | NC | Hang in the air | – |
2. Manufacturer Demo test
Data address:
Link: https://pan.baidu.com/s/1fiWWfmWQT9CNh4EimU-Igw
Extraction code: 1234
For the debugging process of specific routines, please refer to Niren in the compressed package_ W5500 Module User Manual (open with Adobe Reader)
client:
Server side:
UDP:
2, STM32+W5500+modbus protocol programming
1. Download address of engineering documents
Engineering documents: https://github.com/Wattson1128/Embedded-System/tree/main/week15-W5500/stm32_w5500_freemodbus_v1-master
2. Source code demonstration
Core part:
main.c
int main(void) { unsigned char i; /* Initialize STM32F103 */ System_Initialization();//system configuration SysTick_Init();//Start the system tick timer SysTick /* Config W5500 */ W5500_Configuration();//W5500 configuration Delay_ms(200);//Delay waiting /* Modbus-TCP Init */ eMBTCPInit(MB_TCP_PORT_USE_DEFAULT); //Port dependent event module initialization Delay_ms(200); //Delay waiting /* Enable Modbus-TCP Stack */ eMBEnable();//Activate protocol stack printf("\r\nModbus-TCP Start!\r\n"); printf("IP:192.168.1.128\r\n"); while(1) { i=Read_SOCK_1_Byte(0,Sn_SR); //Read W5500 status if(i==0) { do { Delay_ms(100);//Delay waiting }while(Socket_Listen(0)==FALSE);//Set "Socket n" to "TCP server mode" } else if(i==SOCK_ESTABLISHED) //Establish TCP connection { eMBPoll();//Start modbus listening BSP_LED();//Coil control LED } } }
Configuration function of W5500
/* W5500 configuration */ void W5500_Configuration() { unsigned char array[6]; GPIO_SetBits(GPIO_W5500_RST_PORT, GPIO_W5500_RST_Pin);//Pull up Delay_ms(100); /*delay 100ms Delay using systick 1ms time base*/ //Waiting for Ethernet link while((Read_1_Byte(PHYCFGR)&LINK)==0); /* Waiting for Ethernet Link */ Write_1_Byte(MR, RST);//Write one byte to W5500 general register Delay_ms(20); /*delay 20ms */ /* Set Gateway IP as: 192.168.1.1 */ array[0]=192; array[1]=168; array[2]=1; array[3]=1; Write_Bytes(GAR, array, 4);//Set gateway IP /* Set Subnet Mask as: 255.255.255.0 */ array[0]=255; array[1]=255; array[2]=255; array[3]=0; Write_Bytes(SUBR, array, 4);//Set subnet mask /* Set MAC Address as: 0x48,0x53,0x00,0x57,0x55,0x00 */ array[0]=0x48; array[1]=0x53; array[2]=0x00; array[3]=0x57; array[4]=0x55; array[5]=0x00; Write_Bytes(SHAR, array, 6);//Set MAC address /* Set W5500 IP as: 192.168.1.128 */ array[0]=192; array[1]=168; array[2]=1; array[3]=128; Write_Bytes(SIPR, array, 4);//Set IP address of W5500 }
3, web service of STM32+W5500
1. Project Download:
https://github.com/Wattson1128/Embedded-System/tree/main/week15-W5500/HTTP_Server-Two_Page
2. Source code demonstration:
Core code:
main.c:
int main(void) { Systick_Init(72);//System clock initialization GPIO_Configuration(); //GPIO configuration USART1_Init(); //Serial port initialization: 115200@8-n-1 printf("W5500 EVB initialization over.\r\n"); Reset_W5500(); WIZ_SPI_Init();//W5500 related pin configuration printf("W5500 initialized!\r\n"); if(GPIO_ReadInputDataBit(GPIOB,GPIO_Pin_7)) { DefaultSet();//Factory value } else { get_config();//read config data from flash } printf("Firmware ver%d.%d\r\n",ConfigMsg.sw_ver[0],ConfigMsg.sw_ver[1]); if(ConfigMsg.debug==0) ConfigMsg.debug=1; set_network();//Configure network information printf("Network is ready.\r\n"); while(1) { if(ConfigMsg.JTXD_Control == 0) do_http();//Open http service else JTXD_do_http(); if(reboot_flag) NVIC_SystemReset();//Initiate system reset request to reset MCU // reboot(); } }
GPIO.C
void GPIO_Configuration(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA |RCC_APB2Periph_GPIOB |RCC_APB2Periph_GPIOC|RCC_APB2Periph_AFIO , ENABLE); // Port A output GPIO_InitStructure.GPIO_Pin =GPIO_Pin_0|GPIO_Pin_1| GPIO_Pin_2 |GPIO_Pin_3; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOA, &GPIO_InitStructure); // GPIO_ResetBits(GPIOA, GPIO_Pin_0); // GPIO_ResetBits(GPIOA, GPIO_Pin_1); // GPIO_SetBits(GPIOA, GPIO_Pin_2); // led off // GPIO_SetBits(GPIOA, GPIO_Pin_3); // led off // Port B output; GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOB, &GPIO_InitStructure); GPIO_SetBits(GPIOB, GPIO_Pin_9); // Port C input // GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6; // GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; // GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; // GPIO_Init(GPIOC, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7;//Control flash GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; GPIO_Init(GPIOB, &GPIO_InitStructure); GPIO_SetBits(GPIOB, GPIO_Pin_7); }
W5500 configuration:
void WIZ_SPI_Init(void) { SPI_InitTypeDef SPI_InitStructure; GPIO_InitTypeDef GPIO_InitStructure; RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI2, ENABLE); RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOB |RCC_APB2Periph_AFIO , ENABLE); // Port B output GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOB, &GPIO_InitStructure); GPIO_SetBits(GPIOB, GPIO_Pin_12); /* Configure SPIy pins: SCK, MISO and MOSI */ GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13| GPIO_Pin_14| GPIO_Pin_15; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOB, &GPIO_InitStructure); /* SPI Config -------------------------------------------------------------*/ SPI_InitStructure.SPI_Direction = SPI_Direction_2Lines_FullDuplex; SPI_InitStructure.SPI_Mode = SPI_Mode_Master; SPI_InitStructure.SPI_DataSize = SPI_DataSize_8b; SPI_InitStructure.SPI_CPOL = SPI_CPOL_Low; SPI_InitStructure.SPI_CPHA = SPI_CPHA_1Edge; SPI_InitStructure.SPI_NSS = SPI_NSS_Soft; SPI_InitStructure.SPI_BaudRatePrescaler = SPI_BaudRatePrescaler_4; SPI_InitStructure.SPI_FirstBit = SPI_FirstBit_MSB; SPI_InitStructure.SPI_CRCPolynomial = 7; SPI_Init(SPI2, &SPI_InitStructure); SPI_Cmd(SPI2, ENABLE); }
http request:
void do_http(void) { uint8 ch=SOCK_HTTP; uint16 len; st_http_request *http_request; memset(rx_buf,0x00,MAX_URI_SIZE); http_request = (st_http_request*)rx_buf; // struct of http request /* http service start */ switch(getSn_SR(ch)) { case SOCK_INIT: listen(ch); break; case SOCK_LISTEN: break; case SOCK_ESTABLISHED: //case SOCK_CLOSE_WAIT: if(getSn_IR(ch) & Sn_IR_CON) { setSn_IR(ch, Sn_IR_CON); } if ((len = getSn_RX_RSR(ch)) > 0) { len = recv(ch, (uint8*)http_request, len); *(((uint8*)http_request)+len) = 0; proc_http(ch, (uint8*)http_request); // request is processed disconnect(ch); } break; case SOCK_CLOSE_WAIT: if ((len = getSn_RX_RSR(ch)) > 0) { //printf("close wait: %d\r\n",len); len = recv(ch, (uint8*)http_request, len); *(((uint8*)http_request)+len) = 0; proc_http(ch, (uint8*)http_request); // request is processed } disconnect(ch); break; case SOCK_CLOSED: socket(ch, Sn_MR_TCP, 80, 0x00); /* reinitialize the socket */ break; default: break; }// end of switch } void JTXD_do_http(void) { uint8 ch=SOCK_HTTP; uint16 len; st_http_request *http_request; memset(rx_buf,0x00,MAX_URI_SIZE); http_request = (st_http_request*)rx_buf; // struct of http request /* http service start */ switch(getSn_SR(ch)) { case SOCK_INIT: listen(ch); break; case SOCK_LISTEN: break; case SOCK_ESTABLISHED: //case SOCK_CLOSE_WAIT: if(getSn_IR(ch) & Sn_IR_CON) { setSn_IR(ch, Sn_IR_CON); } if ((len = getSn_RX_RSR(ch)) > 0) { len = recv(ch, (uint8*)http_request, len); *(((uint8*)http_request)+len) = 0; JTXD_proc_http(ch, (uint8*)http_request); // request is processed disconnect(ch); } break; case SOCK_CLOSE_WAIT: if ((len = getSn_RX_RSR(ch)) > 0) { //printf("close wait: %d\r\n",len); len = recv(ch, (uint8*)http_request, len); *(((uint8*)http_request)+len) = 0; JTXD_proc_http(ch, (uint8*)http_request); // request is processed } disconnect(ch); break; case SOCK_CLOSED: socket(ch, Sn_MR_TCP, 80, 0x00); /* reinitialize the socket */ break; default: break; }// end of switch }
4, Summary
w5500 switches between the default value and flash through the operation of PB7 pin.