通過STM32F103RC驅動W5500入網,需要先確定以下幾點:
1、硬件電路連接情況,STM32F103RC的SPI對應的端口,SPI1和SPI2的硬件端口對應關係如下:
電路設計時,如要使用SPI接口,必須把對應的引腳接對。
2、要確保電腦和STM32驅動W5500的板子聯網在同一局域網內。
3、在電腦的cmd命令窗口中,輸入ipconfig查出自己電腦的IP。
4、在cmd命令串口中,隨意ping一個IP,確保ping不通;待調試好的程序下載完成後,再ping這個IP,如果ping通了,說明STM32F103RC驅動W5500入網成功。
我使用的板子,使用的SPI2,端口對應關係如下:
硬件資源情況如上,我使用的IDE是Keil5 。W5500在官網上提供了驅動代碼,下載下來
軟件部分需要做以下操作:
1、配置RCC,SPI,GPIO
2、註冊函數指針,此步是W5500驅動部分必須要做的。
3、初始化W5500芯片,配置網關,子網掩碼,MAC地址和IP地址
做完這幾步就可以ping通了。
主函數如下:
#ifndef __STM32F10X_H
#define __STM32F10X_H
#include "stm32f10x.h"
#endif
#ifndef __Z_HARDWARE_SPI_H
#define __Z_HARDWARE_SPI_H
#include "z_hardware_spi.h"
#endif
#ifndef __Z_UTIL_TIME_H
#define __Z_UTIL_TIME_H
#include "z_util_time.h"
#endif
#ifndef __Z_UTIL_NET_H
#define __Z_UTIL_NET_H
#include "z_util_net.h"
#endif
int main(void)
{
init_system_hardware();
delay_ms(2000);
config_register_function();
delay_ms(100);
init_w5500();
for(;;)
{
}
}
SPI操作相關的代碼如下:
#ifndef __Z_HARDWARE_SPI_H
#define __Z_HARDWARE_SPI_H
#include "z_hardware_spi.h"
#endif
void init_system_spi(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
SPI_InitTypeDef SPI_InitStructure;
/* Enable SPI2 and GPIOB clocks */
RCC_APB1PeriphClockCmd(RCC_APB1Periph_SPI2, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);
/* Configure SPI1 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);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_14;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
GPIO_Init(GPIOB, &GPIO_InitStructure);
/* Set Chip Select pin */
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);
/* Set SPI interface */
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);
}
void init_gpio(void)
{
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
GPIO_Init(GPIOB, &GPIO_InitStructure);
GPIO_ResetBits(GPIOB, GPIO_Pin_11);//RST
}
void init_system_hardware(void)
{
init_system_spi();
init_gpio();
}
void func_spi_write_a_byte(uint8_t TxData)
{
SPI_I2S_SendData(SPI2, TxData);
while(SPI_I2S_GetFlagStatus(SPI2, SPI_I2S_FLAG_TXE) == RESET);
}
uint8_t func_spi_read_a_byte(void)
{
//SPI_I2S_ReceiveData(SPI2);
//SPI_I2S_SendData(SPI2, 0xff);
while(SPI_I2S_GetFlagStatus(SPI2, SPI_I2S_FLAG_TXE) == RESET);
/* Read 1 byte */
return SPI_I2S_ReceiveData(SPI2);
}
void func_spi_crisenter(void)
{
__set_PRIMASK(1);
}
void func_spi_crisexit(void)
{
__set_PRIMASK(0);
}
void func_spi_cs_select(void)
{
GPIO_ResetBits(GPIOB, GPIO_Pin_12);
}
void func_spi_cs_deselect(void)
{
GPIO_SetBits(GPIOB, GPIO_Pin_12);
}
初始化W5500的代碼如下:
#ifndef __Z_UTIL_NET_H
#define __Z_UTIL_NET_H
#include "z_util_net.h"
#endif
void init_w5500(void)
{
wiz_NetInfo gWIZNETINFO = { .mac = {0x48, 0x53, 0x00,0x57, 0x55, 0x00},
.ip = {10, 0, 0, 114},
.sn = {255,255,255,0},
.gw = {10, 0, 0, 1},
.dns = {8, 8, 8, 8},
.dhcp = NETINFO_STATIC };
//uint8_t tmp;
// Reset W5500
GPIO_SetBits(GPIOB, GPIO_Pin_11);
delay_ms(100);
// Waiting for Ethernet Link
while((WIZCHIP_READ(PHYCFGR | (0x01|_W5500_SPI_READ_ | WIZCHIP_CREG_BLOCK))& 0x01) == 0);
delay_ms(1000);
// Write RST to W5500 Common Register
WIZCHIP_WRITE(MR|(0x01|_W5500_SPI_READ_ | WIZCHIP_CREG_BLOCK), MR_RST);
delay_ms(100);
// Set MAC IP GW SN
//ctlnetwork(CN_SET_NETINFO, (void*)&gWIZNETINFO);
WIZCHIP_WRITE_BUF(GAR, gWIZNETINFO.gw, 4);
WIZCHIP_WRITE_BUF(SUBR, gWIZNETINFO.sn, 4);
WIZCHIP_WRITE_BUF(SHAR, gWIZNETINFO.mac, 6);
WIZCHIP_WRITE_BUF(SIPR, gWIZNETINFO.ip, 4);
}
void config_register_function(void)
{
reg_wizchip_cris_cbfunc(func_spi_crisenter, func_spi_crisexit);
#if _WIZCHIP_IO_MODE_ == _WIZCHIP_IO_MODE_SPI_VDM_
reg_wizchip_cs_cbfunc(func_spi_cs_select, func_spi_cs_deselect);
#elif _WIZCHIP_IO_MODE_ == _WIZCHIP_IO_MODE_SPI_FDM_
reg_wizchip_cs_cbfunc(SPI_CS_Select, SPI_CS_Deselect);
#else
#if (_WIZCHIP_IO_MODE_ & _WIZCHIP_IO_MODE_SIP_) != _WIZCHIP_IO_MODE_SIP_
#error "Unknown _WIZCHIP_IO_MODE_"
#else
reg_wizchip_cs_cbfunc(wizchip_select, wizchip_deselect);
#endif
#endif
reg_wizchip_spi_cbfunc(func_spi_read_a_byte, func_spi_write_a_byte);
}
代碼編譯後下載到板子中,ping的效果如下:
代碼下載地址: