LWIP为了提高兼容性也可以通过Scoket实现,主要是代码函数在文件#include <lwip/sockets.h>中,以下是主要相关代码
/** @ingroup socket */
#define accept(s,addr,addrlen) lwip_accept(s,addr,addrlen)
/** @ingroup socket */
#define bind(s,name,namelen) lwip_bind(s,name,namelen)
/** @ingroup socket */
#define shutdown(s,how) lwip_shutdown(s,how)
/** @ingroup socket */
#define getpeername(s,name,namelen) lwip_getpeername(s,name,namelen)
/** @ingroup socket */
#define getsockname(s,name,namelen) lwip_getsockname(s,name,namelen)
/** @ingroup socket */
#define setsockopt(s,level,optname,opval,optlen) lwip_setsockopt(s,level,optname,opval,optlen)
/** @ingroup socket */
#define getsockopt(s,level,optname,opval,optlen) lwip_getsockopt(s,level,optname,opval,optlen)
/** @ingroup socket */
#define closesocket(s) lwip_close(s)
/** @ingroup socket */
#define connect(s,name,namelen) lwip_connect(s,name,namelen)
/** @ingroup socket */
#define listen(s,backlog) lwip_listen(s,backlog)
/** @ingroup socket */
#define recv(s,mem,len,flags) lwip_recv(s,mem,len,flags)
/** @ingroup socket */
#define recvfrom(s,mem,len,flags,from,fromlen) lwip_recvfrom(s,mem,len,flags,from,fromlen)
/** @ingroup socket */
#define send(s,dataptr,size,flags) lwip_send(s,dataptr,size,flags)
/** @ingroup socket */
#define sendmsg(s,message,flags) lwip_sendmsg(s,message,flags)
/** @ingroup socket */
#define sendto(s,dataptr,size,flags,to,tolen) lwip_sendto(s,dataptr,size,flags,to,tolen)
/** @ingroup socket */
#define socket(domain,type,protocol) lwip_socket(domain,type,protocol)
/** @ingroup socket */
#define select(maxfdp1,readset,writeset,exceptset,timeout) lwip_select(maxfdp1,readset,writeset,exceptset,timeout)
/** @ingroup socket */
#define ioctlsocket(s,cmd,argp) lwip_ioctl(s,cmd,argp)
TCP程序编写
实现环境
1.移植Freertos
2.移植LWIP,开启LWIP_SOCKET
#include "tcp_server_test.h"
#include "lwip/opt.h"
#include <lwip/sockets.h>
#include "lwip/sys.h"
#include "lwip/api.h"
#include "string.h"
#if LWIP_SOCKET //需要开启Scoket才能使用
#define RECV_DATA (1024UL)
#define LOCAL_PORT (6133UL)
#define BACKLOG (5UL)/*最大监听数*/
#define LWIP_TCP_DEBUG_ENABLE 1
#if LWIP_TCP_DEBUG_ENABLE
#define LWIP_TCP_DEBUG printf
#else
#define LWIP_TCP_DEBUG(...)
#endif
static void tcp_server_thread(void *arg)
{
int sockfd = -1,connected; /*socket句柄和建立连接后的句柄*/
struct sockaddr_in server_addr,client_addr;
socklen_t sin_size;
int recv_data_len;
uint8_t recv_data[RECV_DATA];
LWIP_TCP_DEBUG("tcp server port %d\n\n",LOCAL_PORT);
again:
//创建scoket描述符 AF_INET 使用ipv4地址
sockfd = socket(AF_INET, SOCK_STREAM, 0);
if (sockfd < 0)
{
LWIP_TCP_DEBUG("Socket error\n");
close(sockfd);
vTaskDelay(100);
goto again;
}
//
server_addr.sin_family = AF_INET; //该属性表示接收本机或其他机器传输
server_addr.sin_addr.s_addr = htonl(INADDR_ANY); //本机IP
server_addr.sin_port = htons(LOCAL_PORT); //端口号
memset(&(server_addr.sin_zero), 0, sizeof(server_addr.sin_zero));
if (bind(sockfd, (struct sockaddr *)&server_addr, sizeof(struct sockaddr)) == -1)
{
LWIP_TCP_DEBUG("Unable to bind\n");
close(sockfd);
vTaskDelay(100);
goto again;
}
//设置最大监听数
if (listen(sockfd, BACKLOG) == -1)
{
LWIP_TCP_DEBUG("Listen error\n");
close(sockfd);
vTaskDelay(100);
goto again;
}
while(1)
{
sin_size = sizeof(struct sockaddr_in);
//在这里阻塞知道接收到消息,参数分别是socket句柄,接收到的地址信息以及大小
connected = accept(sockfd, (struct sockaddr *)&client_addr, &sin_size);
LWIP_TCP_DEBUG("new client connected from (%s, %d)\n", inet_ntoa(client_addr.sin_addr), ntohs(client_addr.sin_port));
int tcp_nodelay = 1;//don't delay send to coalesce packets
setsockopt(connected,IPPROTO_TCP,TCP_NODELAY,(void *) &tcp_nodelay,sizeof(int));
while(1)
{
recv_data_len = recv(connected, recv_data, RECV_DATA, 0);
if (recv_data_len <= 0)
{
break;
}
LWIP_TCP_DEBUG("recv %d len data\n",recv_data_len);
//发送内容
write(connected,recv_data,recv_data_len);
}
if (connected >= 0)
{
close(connected);
}
connected = -1;
}
if (sockfd >= 0)
{
close(sockfd);
}
}
#endif
void tcp_server_init(void)
{
#if LWIP_SOCKET
sys_thread_new("tcpecho_thread", tcp_server_thread, NULL, 512, 4);
#endif
}
验证如下
推荐一个很好的博主:https://blog.csdn.net/Chuangke_Andy/article/details/121420376