748 lines
29 KiB
C
748 lines
29 KiB
C
/*
|
||
* eth_drive.c
|
||
*
|
||
* Created on: 2023年1月5日
|
||
* Author: Administrator
|
||
*/
|
||
|
||
|
||
#include "interface_etherent.h"
|
||
#include "interface_config.h"
|
||
#include <string.h>
|
||
#include "eth_driver.h"
|
||
#include "eth_driver.h"
|
||
//*********************************************************************
|
||
//全局变量
|
||
u8 MACAddr[6]= {0}; //MAC address
|
||
u8 IPAddr[4] = { 192, 168, 17, 30 }; //IP address
|
||
u8 GWIPAddr[4] = { 192, 168, 17, 1 }; //Gateway IP address
|
||
u8 IPMask[4] = { 255, 255, 255, 0 }; //subnet mask
|
||
u16 srcport = 8011; //source port
|
||
u16 LocalPort = 8000;
|
||
u16 DownloadPort = 7811;
|
||
u8 SocketRecvBuf0[WCHNET_NUM_TCP][RECE_BUF_LEN] = {0}; //socket receive buffer
|
||
u8 SocketRecvBuf1[RECE_BUF_LEN] = {0}; //socket receive buffer
|
||
u8 SocketRecvBuf2[RECE_BUF_LEN] = {0}; //socket receive buffer
|
||
|
||
u16 Desport = 7900;
|
||
|
||
u8 pc_ipAddr[4] = { 192, 168, 17, 2 }; //计算机IP address
|
||
|
||
u8 remote_base_ip[4] = { 192, 168, 10, 8 }; //远程基站IP address
|
||
u16 remote_port = 1008; //远程基站端口
|
||
|
||
u8 tcp_socket[WCHNET_NUM_TCP]; //Save the currently connected socket
|
||
|
||
|
||
SystemDataRecord g_systemDataRecord = {0,0,0,0};
|
||
|
||
u8 SocketId = 0;
|
||
u8 SocketId2 = 1;
|
||
u8 SocketId3 = 2;
|
||
u8 SocketId4 = 3;
|
||
u8 ETHResBuf[500] = {0};
|
||
u32 ETHUDPTxLen = 0;
|
||
|
||
uint8_t portableOcuTimeOutCnt = 0;
|
||
uint8_t remoteOcuTimeOutCnt = 0;
|
||
|
||
uint8_t OwnMasterTimCnt = 0;
|
||
uint8_t OwnMasterOnline = 0;
|
||
|
||
uint8_t portableOcuOnline = 0;
|
||
uint8_t remoteOcuOnline = 0;
|
||
|
||
Timer ethernet_timer_interface;
|
||
|
||
Timer ethernet_timer_interface1;
|
||
/*********************************************************************
|
||
* @fn mStopIfError
|
||
*
|
||
* @brief check if error.
|
||
*
|
||
* @param iError - error constants.
|
||
*
|
||
* @return none
|
||
*/
|
||
void mStopIfError(u8 iError)
|
||
{
|
||
if (iError == WCHNET_ERR_SUCCESS)
|
||
return;
|
||
printf("Error: %02X\r\n", (u16) iError);
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn IAP_EEPROM_ERASE
|
||
*
|
||
* @brief erase Data-Flash block, minimal block is 256B
|
||
*
|
||
* @param Page_Address - the address of the page being erased.
|
||
* Length - Erased data length
|
||
*
|
||
* @return none
|
||
*/
|
||
void IAP_EEPROM_ERASE(uint32_t Page_Address, u32 Length)
|
||
{
|
||
u32 NbrOfPage, EraseCounter;
|
||
|
||
FLASH_Unlock_Fast();
|
||
NbrOfPage = Length / FLASH_PAGE_SIZE;
|
||
|
||
for (EraseCounter = 0; EraseCounter < NbrOfPage; EraseCounter++) {
|
||
FLASH_ErasePage_Fast( Page_Address + (FLASH_PAGE_SIZE * EraseCounter)); //Erase 256B
|
||
}
|
||
FLASH_Lock_Fast();
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn IAP_EEPROM_WRITE
|
||
*
|
||
* @brief write Data-Flash data block
|
||
*
|
||
* @param StartAddr - the address of the page being written.
|
||
* Buffer - data buff
|
||
* Length - written data length
|
||
*
|
||
* @return FLASH_Status
|
||
*/
|
||
void IAP_EEPROM_WRITE( u32 StartAddr, u8 *Buffer, u32 Length )
|
||
{
|
||
u32 address = StartAddr;
|
||
u32 *p_buff = (u32 *)Buffer;
|
||
u16 pageNum = Length / FLASH_PAGE_SIZE;
|
||
u16 lastDataNum = Length % FLASH_PAGE_SIZE;
|
||
u16 i;
|
||
|
||
if(pageNum){ //write by page(256B)
|
||
FLASH_Unlock_Fast();
|
||
|
||
for(i = 0; i < pageNum; i++)
|
||
FLASH_ProgramPage_Fast((address + FLASH_PAGE_SIZE * i),(p_buff + (FLASH_PAGE_SIZE / 4) * i));
|
||
|
||
FLASH_Lock_Fast();
|
||
}
|
||
|
||
if(lastDataNum){ //write by a half word(2B)
|
||
u8 *p_buff1 = Buffer + FLASH_PAGE_SIZE * pageNum;
|
||
address = StartAddr + FLASH_PAGE_SIZE * pageNum;
|
||
FLASH_Unlock();
|
||
|
||
for(i = 0; i < lastDataNum; i += 2)
|
||
FLASH_ProgramHalfWord((address + i), *(u16 *)(p_buff1 + i));
|
||
|
||
FLASH_Lock();
|
||
}
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn IAP_EEPROM_READ
|
||
*
|
||
* @brief read Data-Flash data block
|
||
*
|
||
* @param StartAddr - the address of the page being read.
|
||
* Buffer - data buff
|
||
* Length - read data length
|
||
*
|
||
* @return none
|
||
*/
|
||
void IAP_EEPROM_READ( u32 StartAddr, u8 *Buffer, u32 Length )
|
||
{
|
||
u32 address = StartAddr;
|
||
u32 *p_buff = (u32 *)Buffer;
|
||
|
||
while(address < (StartAddr + Length))
|
||
{
|
||
*p_buff = (*(u32 *)address);
|
||
address += 4;
|
||
p_buff++;
|
||
}
|
||
}
|
||
/*********************************************************************
|
||
* @fn WCHNET_UdpServerRecv
|
||
*
|
||
* @brief UDP Receive data function
|
||
*
|
||
*@param socinf - socket information.
|
||
* ipaddr - The IP address from which the data was sent
|
||
* port - source port
|
||
* buf - pointer to the data buffer
|
||
* len - received data length
|
||
* @return none
|
||
*/
|
||
void WCHNET_UdpServerRecv(struct _SCOK_INF *socinf, u32 ipaddr, u16 port, u8 *buf, u32 len)
|
||
{
|
||
u8 ip_addr[4];
|
||
//---------------------------------------------------------------------------------------
|
||
if((0xFF == buf[0]) && (0xBB == buf[1]))//自主计算机手动遥控器或者远程遥控器
|
||
{
|
||
portableOcuOnline = 1;
|
||
portableOcuTimeOutCnt = 0;
|
||
}
|
||
else if((0xFF == buf[0]) && (0xCC == buf[1]))//自主计算器 自动
|
||
{
|
||
portableOcuOnline = 1;
|
||
|
||
}
|
||
else if(DF_DownloadDesIPAdress == ip_addr[3])//以太网接收
|
||
{
|
||
}
|
||
else
|
||
{
|
||
}
|
||
}
|
||
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_UdpServerRecv
|
||
*
|
||
* @brief UDP Receive data function
|
||
*
|
||
*@param socinf - socket information.
|
||
* ipaddr - The IP address from which the data was sent
|
||
* port - source port
|
||
* buf - pointer to the data buffer
|
||
* len - received data length
|
||
* @return none
|
||
*/
|
||
void WCHNET_UdpServerRecv1(struct _SCOK_INF *socinf, u32 ipaddr, u16 port, u8 *buf, u32 len)//端口8000
|
||
{
|
||
//---------------------------------------------------------------------------------------
|
||
if( (0x80 == buf[0]) && (0x00 == buf[1]) )
|
||
{
|
||
memcpy((uint8_t *)&(un_request_frame.arr[0]),buf, sizeof(UnRequestFrame));
|
||
printf("read_id = %d \r\n",request_read_id);
|
||
//20250412 保存请求者信息
|
||
for (uint8_t i = 0; i < 4; i++)
|
||
{
|
||
str_RequestMessage.ip_adesser[i] = ipaddr & 0xff;
|
||
ipaddr = ipaddr >> 8;
|
||
}
|
||
str_RequestMessage.port = port;
|
||
|
||
publishMessage(&un_request_frame, 1);
|
||
}
|
||
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_UdpServerRecv
|
||
*
|
||
* @brief UDP Receive data function
|
||
*
|
||
*@param socinf - socket information.
|
||
* ipaddr - The IP address from which the data was sent
|
||
* port - source port
|
||
* buf - pointer to the data buffer
|
||
* len - received data length
|
||
* @return none
|
||
*/
|
||
void WCHNET_UdpServerRecv2(struct _SCOK_INF *socinf, u32 ipaddr, u16 port, u8 *buf, u32 len)//端口7811
|
||
{
|
||
u8 ip_addr[4];
|
||
u16 i = 0;
|
||
u32 PCLen2 = 0;
|
||
u8 ENETTxMessage[8] = {0,0,0,0,0,0,0,0};
|
||
//---------------------------------------------------------------------------------------
|
||
printf("Remote IP:");
|
||
for (i = 0; i < 4; i++) {
|
||
ip_addr[i] = ipaddr & 0xff;
|
||
printf("%d ", ip_addr[i]);
|
||
ipaddr = ipaddr >> 8;
|
||
}
|
||
printf("srcport = %d len = %d socketid = %d\r\n", port, len,
|
||
socinf->SockIndex);
|
||
|
||
if((buf[0] == 0x01) && (buf[1] == 0x0A))//接收指令进入boot,然后重启 20230430增加
|
||
{
|
||
g_systemDataRecord.canBootloaderUpgrade = CAN_BOOTLOADER_UPGRADE;//设置boot标志
|
||
IAP_EEPROM_ERASE(DATA_START_ADDR, FLASH_PAGE_SIZE);
|
||
IAP_EEPROM_WRITE(DATA_START_ADDR, (uint8_t *)&g_systemDataRecord, 4);
|
||
|
||
//写入标志量
|
||
while(1)
|
||
{
|
||
NVIC_SystemReset();//重启
|
||
}
|
||
}
|
||
else if((buf[0] == 0x01) && (buf[1] == 0x01))//反馈当前状态
|
||
{
|
||
IAP_EEPROM_READ( DATA_START_ADDR, (uint8_t *)&g_systemDataRecord, 4 );
|
||
|
||
PCLen2 = 8;
|
||
ENETTxMessage[0] = 0x01;
|
||
ENETTxMessage[1] = 0x01;
|
||
ENETTxMessage[2] = 0;//主版本号,两字节
|
||
ENETTxMessage[3] = 1;
|
||
ENETTxMessage[4] = 0;//次版本号,两字节
|
||
ENETTxMessage[5] = 0;
|
||
ENETTxMessage[6] = 0;
|
||
ENETTxMessage[7] = NORMAL_ON;//1:固件是Bootloader, 0:固件是APP
|
||
|
||
UdpSendToData(SocketId3,ENETTxMessage,&PCLen2,ip_addr,port);//测试
|
||
}
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_CreateTcpSocket
|
||
*
|
||
* @brief Create TCP Socket
|
||
*
|
||
* @return none
|
||
*/
|
||
void WCHNET_CreateTcpSocket(void)
|
||
{
|
||
u8 i;
|
||
SOCK_INF TmpSocketInf;
|
||
|
||
memset((void *) &TmpSocketInf, 0, sizeof(SOCK_INF));
|
||
memcpy((void *) TmpSocketInf.IPAddr, remote_base_ip, 4);
|
||
TmpSocketInf.DesPort = remote_port;
|
||
TmpSocketInf.SourPort = 1008;
|
||
TmpSocketInf.ProtoType = PROTO_TYPE_TCP;
|
||
TmpSocketInf.RecvBufLen = RECE_BUF_LEN;
|
||
i = WCHNET_SocketCreat(&SocketId3, &TmpSocketInf);
|
||
printf("SocketId %d\r\n", SocketId3);
|
||
mStopIfError(i);
|
||
i = WCHNET_SocketConnect(SocketId3); //make a TCP connection
|
||
mStopIfError(i);
|
||
}
|
||
|
||
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_CreateUdpSocket
|
||
*
|
||
* @brief Create UDP Socket
|
||
*
|
||
* @return none
|
||
*/
|
||
void WCHNET_CreateUdpSocket(void)
|
||
{
|
||
// u8 i;
|
||
SOCK_INF TmpSocketInf;
|
||
|
||
// memset((void *) &TmpSocketInf, 0, sizeof(SOCK_INF));
|
||
// TmpSocketInf.SourPort = srcport;
|
||
// TmpSocketInf.ProtoType = PROTO_TYPE_UDP;
|
||
// TmpSocketInf.RecvStartPoint = (u32) SocketRecvBuf0;
|
||
// TmpSocketInf.RecvBufLen = UDP_RECE_BUF_LEN;
|
||
// TmpSocketInf.AppCallBack = WCHNET_UdpServerRecv;
|
||
// i = WCHNET_SocketCreat(&SocketId, &TmpSocketInf);
|
||
// printf("WCHNET_SocketCreat %d\r\n", SocketId);
|
||
// mStopIfError(i);
|
||
#if KEEPALIVE_ENABLE //Configure keep alive parameters
|
||
{
|
||
struct _KEEP_CFG cfg;
|
||
|
||
cfg.KLIdle = 20000;
|
||
cfg.KLIntvl = 15000;
|
||
cfg.KLCount = 9;
|
||
WCHNET_ConfigKeepLive(&cfg);
|
||
}
|
||
#endif
|
||
memset(tcp_socket, 0xff, WCHNET_NUM_TCP);
|
||
|
||
WCHNET_CreateTcpSocket();
|
||
// memset((void *) &TmpSocketInf, 0, sizeof(SOCK_INF));
|
||
// TmpSocketInf.SourPort = srcport;
|
||
// TmpSocketInf.ProtoType = PROTO_TYPE_TCP;
|
||
// i = WCHNET_SocketCreat(&SocketId, &TmpSocketInf);
|
||
// printf("SocketIdForListen %d\r\n", SocketId);
|
||
// mStopIfError(i);
|
||
// i = WCHNET_SocketListen(SocketId); //listen for connections
|
||
// mStopIfError(i);
|
||
|
||
//
|
||
memset((void *)&TmpSocketInf, 0, sizeof(SOCK_INF));
|
||
TmpSocketInf.SourPort = LocalPort;
|
||
TmpSocketInf.ProtoType = PROTO_TYPE_UDP;
|
||
TmpSocketInf.RecvStartPoint = (u32) SocketRecvBuf1;
|
||
TmpSocketInf.RecvBufLen = RECE_BUF_LEN;
|
||
TmpSocketInf.AppCallBack = WCHNET_UdpServerRecv1;
|
||
WCHNET_SocketCreat(&SocketId2, &TmpSocketInf);
|
||
printf("WCHNET_SocketCreat %d\r\n", SocketId2);
|
||
// WCHNET_ModifyRecvBuf(SocketId, (u32)SocketRecvBuf[SocketId], RECE_BUF_LEN);
|
||
|
||
memset((void *) &TmpSocketInf, 0, sizeof(SOCK_INF));
|
||
TmpSocketInf.SourPort = DownloadPort;
|
||
TmpSocketInf.ProtoType = PROTO_TYPE_UDP;
|
||
TmpSocketInf.RecvStartPoint = (u32) SocketRecvBuf2;
|
||
TmpSocketInf.RecvBufLen = RECE_BUF_LEN;
|
||
TmpSocketInf.AppCallBack = WCHNET_UdpServerRecv2;
|
||
WCHNET_SocketCreat(&SocketId3, &TmpSocketInf);
|
||
printf("WCHNET_SocketCreat %d\r\n", SocketId3);
|
||
|
||
|
||
// mStopIfError(i);
|
||
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_DataLoopback
|
||
*
|
||
* @brief Data loopback function.
|
||
*
|
||
* @param id - socket id.
|
||
*
|
||
* @return none
|
||
*/
|
||
void WCHNET_DataLoopback(u8 id)
|
||
{
|
||
#if 1
|
||
u8 i;
|
||
u32 len;
|
||
u32 endAddr = SocketInf[id].RecvStartPoint + SocketInf[id].RecvBufLen; //Receive buffer end address
|
||
|
||
if ((SocketInf[id].RecvReadPoint + SocketInf[id].RecvRemLen) > endAddr)
|
||
{ //Calculate the length of the received data
|
||
len = endAddr - SocketInf[id].RecvReadPoint;
|
||
}
|
||
else
|
||
{
|
||
len = SocketInf[id].RecvRemLen;
|
||
}
|
||
|
||
|
||
if(remote_port == SocketInf[id].DesPort)//接收数据,源端口正确就认为以太网传输RTCM数据
|
||
{
|
||
memcpy(&RTCM_Buffer1.dma_buffer[RTCM_Buffer1.active_buf][0],(u8 *) SocketInf[id].RecvReadPoint,len);
|
||
RTCM_Buffer1.type = ethernet;
|
||
RTCM_Buffer1.buf_len = (uint16_t)len;
|
||
RTCM_Buffer1.active_buf ^= 1;
|
||
RTCM_Buffer1.eth_cnt ++;//累加判断
|
||
publishMessage(&RTCM_Buffer1, 1);
|
||
}
|
||
|
||
// printf("源端口: %u, 目标端口: %u\n",
|
||
// SocketInf[id].SourPort, SocketInf[id].DesPort);
|
||
|
||
|
||
// i = WCHNET_SocketSend(id, (u8 *) SocketInf[id].RecvReadPoint, &len); //send data
|
||
|
||
if (i == WCHNET_ERR_SUCCESS) {
|
||
WCHNET_SocketRecv(id, NULL, &len); //Clear sent data
|
||
}
|
||
#else
|
||
u32 len, totallen;
|
||
u8 *p = MyBuf, TransCnt = 255;
|
||
|
||
len = WCHNET_SocketRecvLen(id, NULL); //query length
|
||
printf("Receive Len = %d\r\n", len);
|
||
totallen = len;
|
||
WCHNET_SocketRecv(id, MyBuf, &len); //Read the data of the receive buffer into MyBuf
|
||
while(1){
|
||
len = totallen;
|
||
WCHNET_SocketSend(id, p, &len); //Send the data
|
||
totallen -= len; //Subtract the sent length from the total length
|
||
p += len; //offset buffer pointer
|
||
if( !--TransCnt ) break; //Timeout exit
|
||
if(totallen) continue; //If the data is not sent, continue to send
|
||
break; //After sending, exit
|
||
}
|
||
#endif
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_HandleSockInt
|
||
*
|
||
* @brief Socket Interrupt Handle
|
||
*
|
||
* @param socketid - socket id.
|
||
* intstat - interrupt status
|
||
*
|
||
* @return none
|
||
*/
|
||
void WCHNET_HandleSockInt(u8 socketid, u8 intstat)
|
||
{
|
||
u8 i;
|
||
if (intstat & SINT_STAT_RECV) //receive data
|
||
{
|
||
WCHNET_DataLoopback(socketid);
|
||
}
|
||
if (intstat & SINT_STAT_CONNECT) //connect successfully
|
||
{
|
||
#if KEEPALIVE_ENABLE
|
||
WCHNET_SocketSetKeepLive(socketid, ENABLE);
|
||
#endif
|
||
WCHNET_ModifyRecvBuf(socketid, (u32) SocketRecvBuf0[socketid], RECE_BUF_LEN);
|
||
for (i = 0; i < WCHNET_MAX_SOCKET_NUM; i++) {
|
||
if (tcp_socket[i] == 0xff) { //save connected socket id
|
||
tcp_socket[i] = socketid;
|
||
break;
|
||
}
|
||
}
|
||
printf("TCP Connect Success\r\n");
|
||
printf("socket id: %d\r\n",tcp_socket[i]);
|
||
}
|
||
if (intstat & SINT_STAT_DISCONNECT) //disconnect
|
||
{
|
||
for (i = 0; i < WCHNET_MAX_SOCKET_NUM; i++) { //delete disconnected socket id
|
||
if (tcp_socket[i] == socketid) {
|
||
tcp_socket[i] = 0xff;
|
||
break;
|
||
}
|
||
}
|
||
printf("TCP Disconnect\r\n");
|
||
}
|
||
if (intstat & SINT_STAT_TIM_OUT) //timeout disconnect
|
||
{
|
||
for (i = 0; i < WCHNET_MAX_SOCKET_NUM; i++) { //delete disconnected socket id
|
||
if (tcp_socket[i] == socketid) {
|
||
tcp_socket[i] = 0xff;
|
||
break;
|
||
}
|
||
}
|
||
printf("TCP Timeout\r\n");
|
||
WCHNET_CreateTcpSocket();
|
||
}
|
||
}
|
||
|
||
/*********************************************************************
|
||
* @fn WCHNET_HandleGlobalInt
|
||
*
|
||
* @brief Global Interrupt Handle
|
||
*
|
||
* @return none
|
||
*/
|
||
void WCHNET_HandleGlobalInt(void)
|
||
{
|
||
u8 intstat;
|
||
u16 i;
|
||
u8 socketint;
|
||
|
||
enter_critical_section();
|
||
|
||
intstat = WCHNET_GetGlobalInt(); //get global interrupt flag
|
||
if (intstat & GINT_STAT_UNREACH) //Unreachable interrupt
|
||
{
|
||
// printf("GINT_STAT_UNREACH\r\n");
|
||
}
|
||
if (intstat & GINT_STAT_IP_CONFLI) //IP conflict
|
||
{
|
||
printf("GINT_STAT_IP_CONFLI\r\n");
|
||
}
|
||
if (intstat & GINT_STAT_PHY_CHANGE) //PHY status change
|
||
{
|
||
i = WCHNET_GetPHYStatus();
|
||
if (i & PHY_Linked_Status)
|
||
printf("PHY Link Success\r\n");
|
||
}
|
||
if (intstat & GINT_STAT_SOCKET) { //socket related interrupt
|
||
for (i = 0; i < WCHNET_MAX_SOCKET_NUM; i++) {
|
||
socketint = WCHNET_GetSocketInt(i);
|
||
if (socketint)
|
||
WCHNET_HandleSockInt(i, socketint);
|
||
}
|
||
}
|
||
|
||
exit_critical_section(0x00);
|
||
}
|
||
|
||
/**
|
||
* @brief UDP send, specify the target IP and target port
|
||
*
|
||
* @param socketid - socket id value
|
||
* @param *buf - Address of the sent data
|
||
* @param(in) *slen - Address of the sent length
|
||
* @param *sip - destination IP address
|
||
* @param port - destination port
|
||
*
|
||
* @param(out) *slen - actual length sent
|
||
*
|
||
* @return @ERR_T
|
||
*/
|
||
uint8_t UdpSendToData(uint8_t socketid, uint8_t *buf, uint32_t *slen, uint8_t *sip, uint16_t port)//发送数据
|
||
{
|
||
uint16_t i = 0;
|
||
//--------------------------------------------------------------
|
||
WCHNET_SocketUdpSendTo( socketid, buf, slen,sip, port);//发送
|
||
|
||
while(slen[0] != 0)//判断缓存是否空闲,空闲执行往下,否则就就等待一段时间,超时就直接跳出函数
|
||
{
|
||
i++;
|
||
if(i > DF_EthInfoWiteTime)
|
||
{
|
||
i = 0;
|
||
return DF_SEND_Fail;//发送失败
|
||
}
|
||
}
|
||
return DF_SEND_Success;
|
||
}
|
||
|
||
/*@brief 计算字节累加校验码(取低8位)
|
||
? @param data 待校验数据的起始地址
|
||
? @param len 数据长度(单位:字节)
|
||
? @return 校验码(低8位)
|
||
?*/
|
||
uint8_t CalculateChecksum(const uint8_t* data, size_t len)
|
||
{
|
||
uint32_t checksum = 0; // 使用32位变量防止溢出
|
||
|
||
for (size_t i = 0; i < len; ++i) {
|
||
checksum += data[i]; // 累加每个字节
|
||
}
|
||
return (uint8_t)(checksum & 0xFF); // 取低8位
|
||
}
|
||
|
||
|
||
// 以太网定时器信号处理函数
|
||
static void ethernetInterfaceTimerProcess(void *signal_id)
|
||
{
|
||
static u_int32_t navigation_output_len = 0;
|
||
// static u_int32_t navigation_output_len1 = 0;
|
||
//----------------------------------------------------------------------
|
||
if (signal_id == &navigation_output1)
|
||
{
|
||
|
||
navigation_outputC1.bit_data.frame_header = 0xCCAA;
|
||
navigation_outputC1.bit_data.frame_type = 0x2700;
|
||
navigation_outputC1.bit_data.frame_length = 0x4100;
|
||
navigation_outputC1.bit_data.accumulated ++;
|
||
|
||
navigation_outputC1.bit_data.time = 0X00;
|
||
navigation_outputC1.bit_data.car_speed = 0X00;
|
||
|
||
//小端转换为大端
|
||
navigation_outputC1.bit_data.gyroscope_x_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.gyroscope_x_axis);
|
||
navigation_outputC1.bit_data.gyroscope_y_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.gyroscope_y_axis);
|
||
navigation_outputC1.bit_data.gyroscope_z_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.gyroscope_z_axis);
|
||
navigation_outputC1.bit_data.acceleration_x_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.acceleration_x_axis);
|
||
navigation_outputC1.bit_data.acceleration_y_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.acceleration_y_axis);
|
||
navigation_outputC1.bit_data.acceleration_z_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.acceleration_z_axis);
|
||
|
||
navigation_outputC1.bit_data.magnetic_x_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.magnetic_x_axis);
|
||
navigation_outputC1.bit_data.magnetic_y_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.magnetic_y_axis);
|
||
navigation_outputC1.bit_data.magnetic_z_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.magnetic_z_axis);
|
||
|
||
navigation_outputC1.bit_data.lon = SWAP_ENDIAN_32(navigation_output1.bit_data.lon);
|
||
navigation_outputC1.bit_data.lat = SWAP_ENDIAN_32(navigation_output1.bit_data.lat);
|
||
navigation_outputC1.bit_data.high = SWAP_ENDIAN_32(navigation_output1.bit_data.high);
|
||
|
||
navigation_outputC1.bit_data.gps_speed = SWAP_ENDIAN_16(navigation_output1.bit_data.gps_speed);
|
||
navigation_outputC1.bit_data.dual_antenna_heading = SWAP_ENDIAN_16(navigation_output1.bit_data.dual_antenna_heading);
|
||
navigation_outputC1.bit_data.car_speed = SWAP_ENDIAN_16(navigation_output1.bit_data.car_speed);
|
||
navigation_outputC1.bit_data.time = SWAP_ENDIAN_32(navigation_output1.bit_data.time);
|
||
navigation_outputC1.bit_data.rtk_state = navigation_output1.bit_data.rtk_state;
|
||
|
||
navigation_outputC1.bit_data.crc1 = CalculateChecksum(&navigation_outputC1.arr[0],sizeof(UnInfNavigationOutputC)-1);
|
||
|
||
|
||
// for(uint8_t i = 0; i < WCHNET_NUM_TCP; i++)
|
||
// {
|
||
// if(tcp_socket[i] != 0xFF)
|
||
// {
|
||
// if(0 == navigation_output_len1)
|
||
// {
|
||
// navigation_output_len1 = sizeof(navigation_outputC1);
|
||
// }
|
||
|
||
// i = WCHNET_SocketSend(tcp_socket[i], (uint8_t *)&navigation_outputC1, &navigation_output_len1); //send data
|
||
// if (i == WCHNET_ERR_SUCCESS) {
|
||
// WCHNET_SocketRecv(tcp_socket[i], NULL, &navigation_output_len1); //Clear sent data
|
||
// }
|
||
// }
|
||
// }
|
||
}
|
||
else if (signal_id == &navigation_output2)
|
||
{
|
||
|
||
navigation_output2.bit_data.frame_header = 0xCCAA;
|
||
navigation_output2.bit_data.frame_type = 0x2700;
|
||
navigation_output2.bit_data.frame_length = 0x3100;
|
||
navigation_output2.bit_data.accumulated ++;
|
||
|
||
navigation_output2.bit_data.time = 0X00;
|
||
navigation_output2.bit_data.car_speed = 0X00;
|
||
|
||
//小端转换为大端
|
||
navigation_output2.bit_data.gyroscope_x_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.gyroscope_x_axis);
|
||
navigation_output2.bit_data.gyroscope_y_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.gyroscope_y_axis);
|
||
navigation_output2.bit_data.gyroscope_z_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.gyroscope_z_axis);
|
||
navigation_output2.bit_data.acceleration_x_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.acceleration_x_axis);
|
||
navigation_output2.bit_data.acceleration_y_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.acceleration_y_axis);
|
||
navigation_output2.bit_data.acceleration_z_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.acceleration_z_axis);
|
||
|
||
navigation_output2.bit_data.magnetic_x_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.magnetic_x_axis);
|
||
navigation_output2.bit_data.magnetic_y_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.magnetic_y_axis);
|
||
navigation_output2.bit_data.magnetic_z_axis = SWAP_ENDIAN_16(navigation_output1.bit_data.magnetic_z_axis);
|
||
|
||
navigation_output2.bit_data.lon = SWAP_ENDIAN_32(navigation_output1.bit_data.lon);
|
||
navigation_output2.bit_data.lat = SWAP_ENDIAN_32(navigation_output1.bit_data.lat);
|
||
navigation_output2.bit_data.high = SWAP_ENDIAN_32(navigation_output1.bit_data.high);
|
||
|
||
navigation_output2.bit_data.gps_speed = SWAP_ENDIAN_16(navigation_output1.bit_data.gps_speed);
|
||
navigation_output2.bit_data.dual_antenna_heading = SWAP_ENDIAN_16(navigation_output1.bit_data.dual_antenna_heading);
|
||
navigation_output2.bit_data.car_speed = SWAP_ENDIAN_16(navigation_output1.bit_data.car_speed);
|
||
navigation_output2.bit_data.time = SWAP_ENDIAN_32(navigation_output1.bit_data.time);
|
||
navigation_output2.bit_data.rtk_state = navigation_output1.bit_data.rtk_state;
|
||
|
||
navigation_output2.bit_data.crc1 = CalculateChecksum(&navigation_output2.arr[0],sizeof(UnInfNavigationOutput)-1);
|
||
|
||
if(0 == navigation_output_len)
|
||
{
|
||
navigation_output_len = sizeof(navigation_output2);
|
||
}
|
||
UdpSendToData(SocketId2, (uint8_t *)&navigation_output2, &navigation_output_len, &str_RequestMessage.ip_adesser[0],str_RequestMessage.port);//发送数据
|
||
}
|
||
else
|
||
{
|
||
|
||
}
|
||
}
|
||
|
||
void ethInterruptProcess(void *signal_id)
|
||
{
|
||
/*Ethernet library main task function,
|
||
* which needs to be called cyclically*/
|
||
WCHNET_MainTask();
|
||
/*Query the Ethernet global interrupt,
|
||
* if there is an interrupt, call the global interrupt handler*/
|
||
if(WCHNET_QueryGlobalInt())
|
||
{
|
||
WCHNET_HandleGlobalInt();
|
||
}
|
||
|
||
timerStart(ðernet_timer_interface, 1,1); //1ms调用一次
|
||
}
|
||
|
||
void ethernetFaultProcess(void *signal_id)//以太网RTCM连接判断。
|
||
{
|
||
static uint8_t eth_cnt_last = 0;
|
||
if( (RTCM_Buffer1.eth_cnt == eth_cnt_last) && (ethernet == RTCM_Buffer1.type) )//如果数据一样,且那5s就是断开连接了。
|
||
{
|
||
RTCM_Buffer1.type = init;
|
||
}
|
||
else
|
||
{
|
||
eth_cnt_last = RTCM_Buffer1.eth_cnt;
|
||
}
|
||
timerStart(ðernet_timer_interface1, 8000,1); //8s调用一次
|
||
}
|
||
|
||
|
||
|
||
|
||
void ethernetInterfaceInit(void)
|
||
{
|
||
//-----------------------------------
|
||
// 订阅定时器信号,用于定时采集
|
||
subscribe(&navigation_output1, ethernetInterfaceTimerProcess);
|
||
subscribe(&navigation_output2, ethernetInterfaceTimerProcess);
|
||
subscribe(ðernet_timer_interface, ethInterruptProcess);
|
||
subscribe(ðernet_timer_interface1, ethernetFaultProcess); //1ms调用一次
|
||
|
||
timerStart(ðernet_timer_interface, 1,1); //1ms调用一次
|
||
|
||
timerStart(ðernet_timer_interface1, 5000,1); //5s调用一次
|
||
|
||
|
||
|
||
|
||
printf( "ethernetInterface: initial OK %d\n",getCurrentTime());
|
||
}
|
||
|
||
|
||
|
||
|
||
|