为方便在各平台下改动小,采取最通用的函数实现,不考虑效率,只求结构框架清晰,避免日后遗忘。
完整例子代码如下:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <unistd.h>
#define SERVER_LISTEN_PORT 3721
int main(int argc, char *argv[])
{
printf("TCP server started!\n");
int socketListen, socketClient;
int saLength, err;
char *strClientIp;
struct sockaddr_in saServer;
struct sockaddr_in saClient;
saLength = sizeof(struct sockaddr);
socketListen = socket(AF_INET, SOCK_STREAM, 0);
if (socketListen == -1)
{
printf("socket() : Server listen socket create error.\n");
return -1;
}
(void)memset(&saServer, 0, saLength);
saServer.sin_family = AF_INET;
saServer.sin_port = htons(SERVER_LISTEN_PORT);
saServer.sin_addr.s_addr = htonl(INADDR_ANY);//默认监听本机所有地址
//saServer.sin_addr.s_addr = inet_addr("127.0.0.1");//或者监听某IP地址
err = bind(socketListen, (struct sockaddr *)(&saServer), saLength);
if (err == -1)
{
printf("bind() : Bind the server socket error.\n");
return -1;
}
err = listen(socketListen, 4096);
if (err == -1)
{
printf("listen() : Server socket listen error.\n");
return -1;
}
for ( ;; )
{
saLength = sizeof(struct sockaddr_in);
socketClient = accept(socketListen, (struct sockaddr *)&saClient, &saLength);
if (socketClient == -1)
{
printf("accept() : accept the client socket error.\n");
continue;
}
//已经有客户连接上来了,下面可以对客户套接字进行recv和send或read和write,进行各种业务逻辑实现了。
//已经有客户连接上来了,下面可以对客户套接字进行recv和send或read和write,进行各种业务逻辑实现了。
strClientIp = inet_ntoa(saClient.sin_addr);
printf("accept the connection from remote client %s.\n", strClientIp);
err = send(socketClient, "welcome connect the net server.", strlen("welcome connect the net server."), 0);
if (err == -1)
{
printf("send() : Send data to client socket error.\n");
close(socketClient);
exit(0);
}
close(socketClient);
}
close(socketListen);
return 0;
}
客户端程序暂时不写,可以用telnet来测试,如:
telnet 127.0.0.1 3721