|
單片機(jī)源程序如下:
- /***************************************************************************************
- * 工程名 :W5500模塊-服務(wù)端模式例程
- * 描述 :W5500的端口0工作在服務(wù)端模式,則等待《TCP&UDP測(cè)試工具》上創(chuàng)建的客戶端主動(dòng)與服務(wù)端連接,
- * 連接成功后,服務(wù)端定時(shí)給客戶端發(fā)送字符串"\r\nWelcome To ChuangWeiElec!\r\n",
- * 同時(shí)將接收到客戶端發(fā)來的數(shù)據(jù)回發(fā)給客戶端。
- * 實(shí)驗(yàn)平臺(tái):51單片機(jī)開發(fā)板+ W5500以太網(wǎng)(TCP/IP)模塊
- * 硬件連接: P3^2 -> W5500_RST
- * P3^3 -> W5500_INT(本例程沒有用到中斷,此引腳可以不接)
- * P3^6 -> W5500_SCS
- * P3^7 -> W5500_SCK
- * P3^4 -> W5500_MISO
- * P3^5 -> W5500_MOSI
- * 庫版本 :ST_v3.5
- ***************************************************************************************/
- /*例程網(wǎng)絡(luò)參數(shù)*/
- //網(wǎng)關(guān):192.168.1.1
- //掩碼: 255.255.255.0
- //物理地址:0C 29 AB 7C 00 01
- //本機(jī)IP地址:192.168.1.199
- //端口0的端口號(hào):5000
- //端口0的目的IP地址:192.168.1.190
- //端口0的目的端口號(hào):6000
- #include <reg51.h>
- #include "W5500.h"
- #include <string.h>
- void Delay(unsigned int d); //延時(shí)函數(shù)(ms)
- /*******************************************************************************
- * 函數(shù)名 : W5500_Initialization
- * 描述 : W5500初始貨配置
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 無
- *******************************************************************************/
- void W5500_Initialization(void)
- {
- W5500_Init(); //初始化W5500寄存器函數(shù)
- Detect_Gateway(); //檢查網(wǎng)關(guān)服務(wù)器
- Socket_Init(0); //指定Socket(0~7)初始化,初始化端口0
- }
- /*******************************************************************************
- * 函數(shù)名 : Load_Net_Parameters
- * 描述 : 裝載網(wǎng)絡(luò)參數(shù)
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 網(wǎng)關(guān)、掩碼、物理地址、本機(jī)IP地址、端口號(hào)、目的IP地址、目的端口號(hào)、端口工作模式
- *******************************************************************************/
- void Load_Net_Parameters(void)
- {
- Gateway_IP[0] = 192;//加載網(wǎng)關(guān)參數(shù)
- Gateway_IP[1] = 168;
- Gateway_IP[2] = 1;
- Gateway_IP[3] = 1;
- Sub_Mask[0]=255;//加載子網(wǎng)掩碼
- Sub_Mask[1]=255;
- Sub_Mask[2]=255;
- Sub_Mask[3]=0;
- Phy_Addr[0]=0x0c;//加載物理地址
- Phy_Addr[1]=0x29;
- Phy_Addr[2]=0xab;
- Phy_Addr[3]=0x7c;
- Phy_Addr[4]=0x00;
- Phy_Addr[5]=0x01;
- IP_Addr[0]=192;//加載本機(jī)IP地址
- IP_Addr[1]=168;
- IP_Addr[2]=1;
- IP_Addr[3]=199;
- S0_Port[0] = 0x13;//加載端口0的端口號(hào)5000
- S0_Port[1] = 0x88;
- // S0_DIP[0]=192;//加載端口0的目的IP地址
- // S0_DIP[1]=168;
- // S0_DIP[2]=1;
- // S0_DIP[3]=190;
- //
- // S0_DPort[0] = 0x17;//加載端口0的目的端口號(hào)6000
- // S0_DPort[1] = 0x70;
- S0_Mode=TCP_SERVER;//加載端口0的工作模式,TCP服務(wù)端模式
- }
- /*******************************************************************************
- * 函數(shù)名 : W5500_Socket_Set
- * 描述 : W5500端口初始化配置
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 分別設(shè)置4個(gè)端口,根據(jù)端口工作模式,將端口置于TCP服務(wù)器、TCP客戶端或UDP模式.
- * 從端口狀態(tài)字節(jié)Socket_State可以判斷端口的工作情況
- *******************************************************************************/
- void W5500_Socket_Set(void)
- {
- if(S0_State==0)//端口0初始化配置
- {
- if(S0_Mode==TCP_SERVER)//TCP服務(wù)器模式
- {
- if(Socket_Listen(0)==TRUE)
- S0_State=S_INIT;
- else
- S0_State=0;
- }
- else if(S0_Mode==TCP_CLIENT)//TCP客戶端模式
- {
- if(Socket_Connect(0)==TRUE)
- S0_State=S_INIT;
- else
- S0_State=0;
- }
- else//UDP模式
- {
- if(Socket_UDP(0)==TRUE)
- S0_State=S_INIT|S_CONN;
- else
- S0_State=0;
- }
- }
- }
- /*******************************************************************************
- * 函數(shù)名 : Process_Socket_Data
- * 描述 : W5500接收并發(fā)送接收到的數(shù)據(jù)
- * 輸入 : s:端口號(hào)
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 本過程先調(diào)用S_rx_process()從W5500的端口接收數(shù)據(jù)緩沖區(qū)讀取數(shù)據(jù),
- * 然后將讀取的數(shù)據(jù)從Rx_Buffer拷貝到Temp_Buffer緩沖區(qū)進(jìn)行處理。
- * 處理完畢,將數(shù)據(jù)從Temp_Buffer拷貝到Tx_Buffer緩沖區(qū)。調(diào)用S_tx_process()
- * 發(fā)送數(shù)據(jù)。
- *******************************************************************************/
- void Process_Socket_Data(SOCKET s)
- {
- unsigned short size;
- size=Read_SOCK_Data_Buffer(s, Rx_Buffer);
- memcpy(Tx_Buffer, Rx_Buffer, size);
- Write_SOCK_Data_Buffer(s, Tx_Buffer, size);
- }
- /*******************************************************************************
- * 函數(shù)名 : main
- * 描述 : 主函數(shù),用戶程序從main函數(shù)開始運(yùn)行
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : int:返回值為一個(gè)16位整形數(shù)
- * 說明 : 無
- *******************************************************************************/
- int main(void)
- {
- unsigned int W5500_Send_Delay_Counter =0;
- Load_Net_Parameters(); //裝載網(wǎng)絡(luò)參數(shù)
- W5500_Hardware_Reset(); //硬件復(fù)位W5500
- W5500_Initialization(); //W5500初始貨配置
- while (1)
- {
- W5500_Socket_Set();//W5500端口初始化配置
-
- W5500_Interrupt_Process();//W5500中斷處理程序框架
- if((S0_Data & S_RECEIVE) == S_RECEIVE)//如果Socket0接收到數(shù)據(jù)
- {
- S0_Data&=~S_RECEIVE;
- Process_Socket_Data(0);//W5500接收并發(fā)送接收到的數(shù)據(jù)
- }
- else if(W5500_Send_Delay_Counter >= 3000)//定時(shí)發(fā)送字符串
- {
- if(S0_State == (S_INIT|S_CONN))
- {
- S0_Data&=~S_TRANSMITOK;
- memcpy(Tx_Buffer, "\r\nWelcome To ChuangWeiElec!\r\n", 27);
- Write_SOCK_Data_Buffer(0, Tx_Buffer, 27);//指定Socket(0~7)發(fā)送數(shù)據(jù)處理,端口0發(fā)送27字節(jié)數(shù)據(jù)
- }
- W5500_Send_Delay_Counter=0;
- }
- W5500_Send_Delay_Counter++;
- }
- }
- /*******************************************************************************
- * 函數(shù)名 : Delay
- * 描述 : 延時(shí)函數(shù)(ms)
- * 輸入 : d:延時(shí)系數(shù),單位為毫秒
- * 輸出 : 無
- * 返回 : 無
- * 說明 : 延時(shí)是利用Timer2定時(shí)器產(chǎn)生的1毫秒的計(jì)數(shù)來實(shí)現(xiàn)的
- *******************************************************************************/
- void Delay(unsigned int x)
- {
- unsigned int i,j;
- for(j=0;j<5;j++)
- for(i=0;i<x;i++);
- }
復(fù)制代碼- /**********************************************************************************
- * 文件名 :W5500.c
- * 描述 :W5500 驅(qū)動(dòng)函數(shù)庫
- * 庫版本 :ST_v3.5
- **********************************************************************************/
-
- #include "W5500.h"
- /***************----- 網(wǎng)絡(luò)參數(shù)變量定義 -----***************/
- unsigned char Gateway_IP[4];//網(wǎng)關(guān)IP地址
- unsigned char Sub_Mask[4]; //子網(wǎng)掩碼
- unsigned char Phy_Addr[6]; //物理地址(MAC)
- unsigned char IP_Addr[4]; //本機(jī)IP地址
- unsigned char S0_Port[2]; //端口0的端口號(hào)
- unsigned char S0_DIP[4]; //端口0目的IP地址
- unsigned char S0_DPort[2]; //端口0目的端口號(hào)
- unsigned char UDP_DIPR[4]; //UDP(廣播)模式,目的主機(jī)IP地址
- unsigned char UDP_DPORT[2]; //UDP(廣播)模式,目的主機(jī)端口號(hào)
- /***************----- 端口的運(yùn)行模式 -----***************/
- unsigned char S0_Mode =3; //端口0的運(yùn)行模式,0:TCP服務(wù)器模式,1:TCP客戶端模式,2:UDP(廣播)模式
- #define TCP_SERVER 0x00 //TCP服務(wù)器模式
- #define TCP_CLIENT 0x01 //TCP客戶端模式
- #define UDP_MODE 0x02 //UDP(廣播)模式
- /***************----- 端口的運(yùn)行狀態(tài) -----***************/
- unsigned char S0_State =0; //端口0狀態(tài)記錄,1:端口完成初始化,2端口完成連接(可以正常傳輸數(shù)據(jù))
- #define S_INIT 0x01 //端口完成初始化
- #define S_CONN 0x02 //端口完成連接,可以正常傳輸數(shù)據(jù)
- /***************----- 端口收發(fā)數(shù)據(jù)的狀態(tài) -----***************/
- unsigned char S0_Data; //端口0接收和發(fā)送數(shù)據(jù)的狀態(tài),1:端口接收到數(shù)據(jù),2:端口發(fā)送數(shù)據(jù)完成
- #define S_RECEIVE 0x01 //端口接收到一個(gè)數(shù)據(jù)包
- #define S_TRANSMITOK 0x02 //端口發(fā)送一個(gè)數(shù)據(jù)包完成
- /***************----- 端口數(shù)據(jù)緩沖區(qū) -----***************/
- unsigned char Rx_Buffer[30]; //端口接收數(shù)據(jù)緩沖區(qū)
- unsigned char Tx_Buffer[30]; //端口發(fā)送數(shù)據(jù)緩沖區(qū)
- unsigned char W5500_Interrupt; //W5500中斷標(biāo)志(0:無中斷,1:有中斷)
- /*******************************************************************************
- * 函數(shù)名 : SPI_ReadByte
- * 描述 : 讀取一個(gè)字節(jié)SPI返回的數(shù)據(jù)
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 讀取到的寄存器數(shù)據(jù)
- * 說明 : 無
- *******************************************************************************/
- unsigned char SPI_Read_Byte(void)
- {
- unsigned char i,rByte=0;
-
- W5500_SCLK=0;
- for(i=0;i<8;i++)
- {
- W5500_SCLK=1;
- rByte<<=1;
- rByte|=W5500_MISO;
- W5500_SCLK=0;
- }
- return rByte;
- }
- /*******************************************************************************
- * 函數(shù)名 : Read_SOCK_Data_Buffer
- * 描述 : 從W5500接收數(shù)據(jù)緩沖區(qū)中讀取數(shù)據(jù)
- * 輸入 : s:端口號(hào),*dat_ptr:數(shù)據(jù)保存緩沖區(qū)指針
- * 輸出 : 無
- * 返回值 : 讀取到的數(shù)據(jù)長(zhǎng)度,rx_size個(gè)字節(jié)
- * 說明 : 無
- *******************************************************************************/
- unsigned short Read_SOCK_Data_Buffer(SOCKET s, unsigned char *dat_ptr)
- {
- unsigned short rx_size;
- unsigned short offset, offset1;
- unsigned short i;
- unsigned char j;
- rx_size=Read_W5500_SOCK_2Byte(s,Sn_RX_RSR);
- if(rx_size==0) return 0;//沒接收到數(shù)據(jù)則返回
- if(rx_size>1460) rx_size=1460;
- offset=Read_W5500_SOCK_2Byte(s,Sn_RX_RD);
- offset1=offset;
- offset&=(S_RX_SIZE-1);//計(jì)算實(shí)際的物理地址
- W5500_SCS=0;//置W5500的SCS為低電平
- SPI_Send_Short(offset);//寫16位地址
- SPI_Send_Byte(VDM|RWB_READ|(s*0x20+0x18));//寫控制字節(jié),N個(gè)字節(jié)數(shù)據(jù)長(zhǎng)度,讀數(shù)據(jù),選擇端口s的寄存器
-
- if((offset+rx_size)<S_RX_SIZE)//如果最大地址未超過W5500接收緩沖區(qū)寄存器的最大地址
- {
- for(i=0;i<rx_size;i++)//循環(huán)讀取rx_size個(gè)字節(jié)數(shù)據(jù)
- {
- j=SPI_Read_Byte();//讀取1個(gè)字節(jié)數(shù)據(jù)
- *dat_ptr=j;//將讀取到的數(shù)據(jù)保存到數(shù)據(jù)保存緩沖區(qū)
- dat_ptr++;//數(shù)據(jù)保存緩沖區(qū)指針地址自增1
- }
- }
- else//如果最大地址超過W5500接收緩沖區(qū)寄存器的最大地址
- {
- offset=S_RX_SIZE-offset;
- for(i=0;i<offset;i++)//循環(huán)讀取出前offset個(gè)字節(jié)數(shù)據(jù)
- {
- j=SPI_Read_Byte();//讀取1個(gè)字節(jié)數(shù)據(jù)
- *dat_ptr=j;//將讀取到的數(shù)據(jù)保存到數(shù)據(jù)保存緩沖區(qū)
- dat_ptr++;//數(shù)據(jù)保存緩沖區(qū)指針地址自增1
- }
- W5500_SCS=1; //置W5500的SCS為高電平
- W5500_SCS=0;//置W5500的SCS為低電平
- SPI_Send_Short(0x00);//寫16位地址
- SPI_Send_Byte(VDM|RWB_READ|(s*0x20+0x18));//寫控制字節(jié),N個(gè)字節(jié)數(shù)據(jù)長(zhǎng)度,讀數(shù)據(jù),選擇端口s的寄存器
- for(;i<rx_size;i++)//循環(huán)讀取后rx_size-offset個(gè)字節(jié)數(shù)據(jù)
- {
- j=SPI_Read_Byte();//讀取1個(gè)字節(jié)數(shù)據(jù)
- *dat_ptr=j;//將讀取到的數(shù)據(jù)保存到數(shù)據(jù)保存緩沖區(qū)
- dat_ptr++;//數(shù)據(jù)保存緩沖區(qū)指針地址自增1
- }
- }
- W5500_SCS=1; //置W5500的SCS為高電平
- offset1+=rx_size;//更新實(shí)際物理地址,即下次讀取接收到的數(shù)據(jù)的起始地址
- Write_W5500_SOCK_2Byte(s, Sn_RX_RD, offset1);
- Write_W5500_SOCK_1Byte(s, Sn_CR, RECV);//發(fā)送啟動(dòng)接收命令
- return rx_size;//返回接收到數(shù)據(jù)的長(zhǎng)度
- }
- /*******************************************************************************
- * 函數(shù)名 : Write_SOCK_Data_Buffer
- * 描述 : 將數(shù)據(jù)寫入W5500的數(shù)據(jù)發(fā)送緩沖區(qū)
- * 輸入 : s:端口號(hào),*dat_ptr:數(shù)據(jù)保存緩沖區(qū)指針,size:待寫入數(shù)據(jù)的長(zhǎng)度
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 無
- *******************************************************************************/
- void Write_SOCK_Data_Buffer(SOCKET s, unsigned char *dat_ptr, unsigned short size)
- {
- unsigned short offset,offset1;
- unsigned short i;
- //如果是UDP模式,可以在此設(shè)置目的主機(jī)的IP和端口號(hào)
- if((Read_W5500_SOCK_1Byte(s,Sn_MR)&0x0f) != SOCK_UDP)//如果Socket打開失敗
- {
- Write_W5500_SOCK_4Byte(s, Sn_DIPR, UDP_DIPR);//設(shè)置目的主機(jī)IP
- Write_W5500_SOCK_2Byte(s, Sn_DPORTR, UDP_DPORT[0]*256+UDP_DPORT[1]);//設(shè)置目的主機(jī)端口號(hào)
- }
- offset=Read_W5500_SOCK_2Byte(s,Sn_TX_WR);
- offset1=offset;
- offset&=(S_TX_SIZE-1);//計(jì)算實(shí)際的物理地址
- W5500_SCS=0;//置W5500的SCS為低電平
- SPI_Send_Short(offset);//寫16位地址
- SPI_Send_Byte(VDM|RWB_WRITE|(s*0x20+0x10));//寫控制字節(jié),N個(gè)字節(jié)數(shù)據(jù)長(zhǎng)度,寫數(shù)據(jù),選擇端口s的寄存器
- if((offset+size)<S_TX_SIZE)//如果最大地址未超過W5500發(fā)送緩沖區(qū)寄存器的最大地址
- {
- for(i=0;i<size;i++)//循環(huán)寫入size個(gè)字節(jié)數(shù)據(jù)
- {
- SPI_Send_Byte(*dat_ptr++);//寫入一個(gè)字節(jié)的數(shù)據(jù)
- }
- }
- else//如果最大地址超過W5500發(fā)送緩沖區(qū)寄存器的最大地址
- {
- offset=S_TX_SIZE-offset;
- for(i=0;i<offset;i++)//循環(huán)寫入前offset個(gè)字節(jié)數(shù)據(jù)
- {
- SPI_Send_Byte(*dat_ptr++);//寫入一個(gè)字節(jié)的數(shù)據(jù)
- }
- W5500_SCS=1; //置W5500的SCS為高電平
- W5500_SCS=0;//置W5500的SCS為低電平
- SPI_Send_Short(0x00);//寫16位地址
- SPI_Send_Byte(VDM|RWB_WRITE|(s*0x20+0x10));//寫控制字節(jié),N個(gè)字節(jié)數(shù)據(jù)長(zhǎng)度,寫數(shù)據(jù),選擇端口s的寄存器
- for(;i<size;i++)//循環(huán)寫入size-offset個(gè)字節(jié)數(shù)據(jù)
- {
- SPI_Send_Byte(*dat_ptr++);//寫入一個(gè)字節(jié)的數(shù)據(jù)
- }
- }
- W5500_SCS=1; //置W5500的SCS為高電平
- offset1+=size;//更新實(shí)際物理地址,即下次寫待發(fā)送數(shù)據(jù)到發(fā)送數(shù)據(jù)緩沖區(qū)的起始地址
- Write_W5500_SOCK_2Byte(s, Sn_TX_WR, offset1);
- Write_W5500_SOCK_1Byte(s, Sn_CR, SEND);//發(fā)送啟動(dòng)發(fā)送命令
- }
- /*******************************************************************************
- * 函數(shù)名 : W5500_Hardware_Reset
- * 描述 : 硬件復(fù)位W5500
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : W5500的復(fù)位引腳保持低電平至少500us以上,才能重圍W5500
- *******************************************************************************/
- void W5500_Hardware_Reset(void)
- {
- W5500_RST=0;//復(fù)位引腳拉低
- Delay(200);
- W5500_RST=1;//復(fù)位引腳拉高
- Delay(200);
- while((Read_W5500_1Byte(PHYCFGR)&LINK)==0);//等待以太網(wǎng)連接完成
- }
- /*******************************************************************************
- * 函數(shù)名 : W5500_Init
- * 描述 : 初始化W5500寄存器函數(shù)
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 在使用W5500之前,先對(duì)W5500初始化
- *******************************************************************************/
- void W5500_Init(void)
- {
- unsigned char i=0;
- Write_W5500_1Byte(MR, RST);//軟件復(fù)位W5500,置1有效,復(fù)位后自動(dòng)清0
- Delay(10);//延時(shí)10ms,自己定義該函數(shù)
- //設(shè)置網(wǎng)關(guān)(Gateway)的IP地址,Gateway_IP為4字節(jié)unsigned char數(shù)組,自己定義
- //使用網(wǎng)關(guān)可以使通信突破子網(wǎng)的局限,通過網(wǎng)關(guān)可以訪問到其它子網(wǎng)或進(jìn)入Internet
- Write_W5500_nByte(GAR, Gateway_IP, 4);
-
- //設(shè)置子網(wǎng)掩碼(MASK)值,SUB_MASK為4字節(jié)unsigned char數(shù)組,自己定義
- //子網(wǎng)掩碼用于子網(wǎng)運(yùn)算
- Write_W5500_nByte(SUBR,Sub_Mask,4);
-
- //設(shè)置物理地址,PHY_ADDR為6字節(jié)unsigned char數(shù)組,自己定義,用于唯一標(biāo)識(shí)網(wǎng)絡(luò)設(shè)備的物理地址值
- //該地址值需要到IEEE申請(qǐng),按照OUI的規(guī)定,前3個(gè)字節(jié)為廠商代碼,后三個(gè)字節(jié)為產(chǎn)品序號(hào)
- //如果自己定義物理地址,注意第一個(gè)字節(jié)必須為偶數(shù)
- Write_W5500_nByte(SHAR,Phy_Addr,6);
- //設(shè)置本機(jī)的IP地址,IP_ADDR為4字節(jié)unsigned char數(shù)組,自己定義
- //注意,網(wǎng)關(guān)IP必須與本機(jī)IP屬于同一個(gè)子網(wǎng),否則本機(jī)將無法找到網(wǎng)關(guān)
- Write_W5500_nByte(SIPR,IP_Addr,4);
-
- //設(shè)置發(fā)送緩沖區(qū)和接收緩沖區(qū)的大小,參考W5500數(shù)據(jù)手冊(cè)
- for(i=0;i<8;i++)
- {
- Write_W5500_SOCK_1Byte(i,Sn_RXBUF_SIZE, 0x02);//Socket Rx memory size=2k
- Write_W5500_SOCK_1Byte(i,Sn_TXBUF_SIZE, 0x02);//Socket Tx mempry size=2k
- }
- //設(shè)置重試時(shí)間,默認(rèn)為2000(200ms)
- //每一單位數(shù)值為100微秒,初始化時(shí)值設(shè)為2000(0x07D0),等于200毫秒
- Write_W5500_2Byte(RTR, 0x07d0);
- //設(shè)置重試次數(shù),默認(rèn)為8次
- //如果重發(fā)的次數(shù)超過設(shè)定值,則產(chǎn)生超時(shí)中斷(相關(guān)的端口中斷寄存器中的Sn_IR 超時(shí)位(TIMEOUT)置“1”)
- Write_W5500_1Byte(RCR,8);
- }
- /*******************************************************************************
- * 函數(shù)名 : Detect_Gateway
- * 描述 : 檢查網(wǎng)關(guān)服務(wù)器
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 成功返回TRUE(0xFF),失敗返回FALSE(0x00)
- * 說明 : 無
- *******************************************************************************/
- unsigned char Detect_Gateway(void)
- {
- unsigned char ip_adde[4];
- ip_adde[0]=IP_Addr[0]+1;
- ip_adde[1]=IP_Addr[1]+1;
- ip_adde[2]=IP_Addr[2]+1;
- ip_adde[3]=IP_Addr[3]+1;
- //檢查網(wǎng)關(guān)及獲取網(wǎng)關(guān)的物理地址
- Write_W5500_SOCK_4Byte(0,Sn_DIPR,ip_adde);//向目的地址寄存器寫入與本機(jī)IP不同的IP值
- Write_W5500_SOCK_1Byte(0,Sn_MR,MR_TCP);//設(shè)置socket為TCP模式
- Write_W5500_SOCK_1Byte(0,Sn_CR,OPEN);//打開Socket
- Delay(5);//延時(shí)5ms
-
- if(Read_W5500_SOCK_1Byte(0,Sn_SR) != SOCK_INIT)//如果socket打開失敗
- {
- Write_W5500_SOCK_1Byte(0,Sn_CR,CLOSE);//打開不成功,關(guān)閉Socket
- return FALSE;//返回FALSE(0x00)
- }
- Write_W5500_SOCK_1Byte(0,Sn_CR,CONNECT);//設(shè)置Socket為Connect模式
- do
- {
- unsigned char j=0;
- j=Read_W5500_SOCK_1Byte(0,Sn_IR);//讀取Socket0中斷標(biāo)志寄存器
- if(j!=0)
- Write_W5500_SOCK_1Byte(0,Sn_IR,j);
- Delay(5);//延時(shí)5ms
- if((j&IR_TIMEOUT) == IR_TIMEOUT)
- {
- return FALSE;
- }
- else if(Read_W5500_SOCK_1Byte(0,Sn_DHAR) != 0xff)
- {
- Write_W5500_SOCK_1Byte(0,Sn_CR,CLOSE);//關(guān)閉Socket
- return TRUE;
- }
- }while(1);
- }
- /*******************************************************************************
- * 函數(shù)名 : Socket_Init
- * 描述 : 指定Socket(0~7)初始化
- * 輸入 : s:待初始化的端口
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 無
- *******************************************************************************/
- void Socket_Init(SOCKET s)
- {
- //設(shè)置分片長(zhǎng)度,參考W5500數(shù)據(jù)手冊(cè),該值可以不修改
- Write_W5500_SOCK_2Byte(0, Sn_MSSR, 30);//最大分片字節(jié)數(shù)=30(0x001e)
- //設(shè)置指定端口
- switch(s)
- {
- case 0:
- //設(shè)置端口0的端口號(hào)
- Write_W5500_SOCK_2Byte(0, Sn_PORT, S0_Port[0]*256+S0_Port[1]);
-
- break;
- case 1:
- break;
- case 2:
- break;
- case 3:
- break;
- case 4:
- break;
- case 5:
- break;
- case 6:
- break;
- case 7:
- break;
- default:
- break;
- }
- }
- /*******************************************************************************
- * 函數(shù)名 : Socket_Connect
- * 描述 : 設(shè)置指定Socket(0~7)為客戶端與遠(yuǎn)程服務(wù)器連接
- * 輸入 : s:待設(shè)定的端口
- * 輸出 : 無
- * 返回值 : 成功返回TRUE(0xFF),失敗返回FALSE(0x00)
- * 說明 : 當(dāng)本機(jī)Socket工作在客戶端模式時(shí),引用該程序,與遠(yuǎn)程服務(wù)器建立連接
- * 如果啟動(dòng)連接后出現(xiàn)超時(shí)中斷,則與服務(wù)器連接失敗,需要重新調(diào)用該程序連接
- * 該程序每調(diào)用一次,就與服務(wù)器產(chǎn)生一次連接
- *******************************************************************************/
- unsigned char Socket_Connect(SOCKET s)
- {
- Write_W5500_SOCK_1Byte(s,Sn_MR,MR_TCP);//設(shè)置socket為TCP模式
- Write_W5500_SOCK_1Byte(s,Sn_CR,OPEN);//打開Socket
- Delay(5);//延時(shí)5ms
- if(Read_W5500_SOCK_1Byte(s,Sn_SR)!=SOCK_INIT)//如果socket打開失敗
- {
- Write_W5500_SOCK_1Byte(s,Sn_CR,CLOSE);//打開不成功,關(guān)閉Socket
- return FALSE;//返回FALSE(0x00)
- }
- Write_W5500_SOCK_1Byte(s,Sn_CR,CONNECT);//設(shè)置Socket為Connect模式
- return TRUE;//返回TRUE,設(shè)置成功
- }
- /*******************************************************************************
- * 函數(shù)名 : Socket_Listen
- * 描述 : 設(shè)置指定Socket(0~7)作為服務(wù)器等待遠(yuǎn)程主機(jī)的連接
- * 輸入 : s:待設(shè)定的端口
- * 輸出 : 無
- * 返回值 : 成功返回TRUE(0xFF),失敗返回FALSE(0x00)
- * 說明 : 當(dāng)本機(jī)Socket工作在服務(wù)器模式時(shí),引用該程序,等等遠(yuǎn)程主機(jī)的連接
- * 該程序只調(diào)用一次,就使W5500設(shè)置為服務(wù)器模式
- *******************************************************************************/
- unsigned char Socket_Listen(SOCKET s)
- {
- Write_W5500_SOCK_1Byte(s,Sn_MR,MR_TCP);//設(shè)置socket為TCP模式
- Write_W5500_SOCK_1Byte(s,Sn_CR,OPEN);//打開Socket
- Delay(5);//延時(shí)5ms
- if(Read_W5500_SOCK_1Byte(s,Sn_SR)!=SOCK_INIT)//如果socket打開失敗
- {
- Write_W5500_SOCK_1Byte(s,Sn_CR,CLOSE);//打開不成功,關(guān)閉Socket
- return FALSE;//返回FALSE(0x00)
- }
- Write_W5500_SOCK_1Byte(s,Sn_CR,LISTEN);//設(shè)置Socket為偵聽模式
- Delay(5);//延時(shí)5ms
- if(Read_W5500_SOCK_1Byte(s,Sn_SR)!=SOCK_LISTEN)//如果socket設(shè)置失敗
- {
- Write_W5500_SOCK_1Byte(s,Sn_CR,CLOSE);//設(shè)置不成功,關(guān)閉Socket
- return FALSE;//返回FALSE(0x00)
- }
- return TRUE;
- //至此完成了Socket的打開和設(shè)置偵聽工作,至于遠(yuǎn)程客戶端是否與它建立連接,則需要等待Socket中斷,
- //以判斷Socket的連接是否成功。參考W5500數(shù)據(jù)手冊(cè)的Socket中斷狀態(tài)
- //在服務(wù)器偵聽模式不需要設(shè)置目的IP和目的端口號(hào)
- }
- /*******************************************************************************
- * 函數(shù)名 : Socket_UDP
- * 描述 : 設(shè)置指定Socket(0~7)為UDP模式
- * 輸入 : s:待設(shè)定的端口
- * 輸出 : 無
- * 返回值 : 成功返回TRUE(0xFF),失敗返回FALSE(0x00)
- * 說明 : 如果Socket工作在UDP模式,引用該程序,在UDP模式下,Socket通信不需要建立連接
- * 該程序只調(diào)用一次,就使W5500設(shè)置為UDP模式
- *******************************************************************************/
- unsigned char Socket_UDP(SOCKET s)
- {
- Write_W5500_SOCK_1Byte(s,Sn_MR,MR_UDP);//設(shè)置Socket為UDP模式*/
- Write_W5500_SOCK_1Byte(s,Sn_CR,OPEN);//打開Socket*/
- Delay(5);//延時(shí)5ms
- if(Read_W5500_SOCK_1Byte(s,Sn_SR)!=SOCK_UDP)//如果Socket打開失敗
- {
- Write_W5500_SOCK_1Byte(s,Sn_CR,CLOSE);//打開不成功,關(guān)閉Socket
- return FALSE;//返回FALSE(0x00)
- }
- else
- return TRUE;
- //至此完成了Socket的打開和UDP模式設(shè)置,在這種模式下它不需要與遠(yuǎn)程主機(jī)建立連接
- //因?yàn)镾ocket不需要建立連接,所以在發(fā)送數(shù)據(jù)前都可以設(shè)置目的主機(jī)IP和目的Socket的端口號(hào)
- //如果目的主機(jī)IP和目的Socket的端口號(hào)是固定的,在運(yùn)行過程中沒有改變,那么也可以在這里設(shè)置
- }
- /*******************************************************************************
- * 函數(shù)名 : W5500_Interrupt_Process
- * 描述 : W5500中斷處理程序框架
- * 輸入 : 無
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 無
- *******************************************************************************/
- void W5500_Interrupt_Process(void)
- {
- unsigned char i,j;
- IntDispose:
- i=Read_W5500_1Byte(SIR);//讀取端口中斷標(biāo)志寄存器
- if((i & S0_INT) == S0_INT)//Socket0事件處理
- {
- j=Read_W5500_SOCK_1Byte(0,Sn_IR);//讀取Socket0中斷標(biāo)志寄存器
- Write_W5500_SOCK_1Byte(0,Sn_IR,j);
- if(j&IR_CON)//在TCP模式下,Socket0成功連接
- {
- S0_State|=S_CONN;//網(wǎng)絡(luò)連接狀態(tài)0x02,端口完成連接,可以正常傳輸數(shù)據(jù)
- }
- if(j&IR_DISCON)//在TCP模式下Socket斷開連接處理
- {
- Write_W5500_SOCK_1Byte(0,Sn_CR,CLOSE);//關(guān)閉端口,等待重新打開連接
- Socket_Init(0); //指定Socket(0~7)初始化,初始化端口0
- S0_State=0;//網(wǎng)絡(luò)連接狀態(tài)0x00,端口連接失敗
- }
- if(j&IR_SEND_OK)//Socket0數(shù)據(jù)發(fā)送完成,可以再次啟動(dòng)S_tx_process()函數(shù)發(fā)送數(shù)據(jù)
- {
- S0_Data|=S_TRANSMITOK;//端口發(fā)送一個(gè)數(shù)據(jù)包完成
- }
- if(j&IR_RECV)//Socket接收到數(shù)據(jù),可以啟動(dòng)S_rx_process()函數(shù)
- {
- S0_Data|=S_RECEIVE;//端口接收到一個(gè)數(shù)據(jù)包
- }
- if(j&IR_TIMEOUT)//Socket連接或數(shù)據(jù)傳輸超時(shí)處理
- {
- Write_W5500_SOCK_1Byte(0,Sn_CR,CLOSE);// 關(guān)閉端口,等待重新打開連接
- S0_State=0;//網(wǎng)絡(luò)連接狀態(tài)0x00,端口連接失敗
- }
- }
- if(Read_W5500_1Byte(SIR) != 0)
- goto IntDispose;
- }
復(fù)制代碼
51hei.png (6.05 KB, 下載次數(shù): 69)
下載附件
2022-5-27 17:04 上傳
Keil代碼下載:
W5500模塊-服務(wù)端模式例程(51單片機(jī)).zip
(86.31 KB, 下載次數(shù): 125)
2022-5-27 16:04 上傳
點(diǎn)擊文件名下載附件
下載積分: 黑幣 -5
|
評(píng)分
-
查看全部評(píng)分
|