linux TCP/UDP

目录

  • [1.TCP server](#1.TCP server)
    • [1.1 TCP服务器建立](#1.1 TCP服务器建立)
    • [1.2 TCP循环服务器](#1.2 TCP循环服务器)
    • [1.3 TCP并发服务器](#1.3 TCP并发服务器)
    • [1.4 TCP并发服务器(进程)](#1.4 TCP并发服务器(进程))
  • [2. TCP client](#2. TCP client)
    • [2.1 TCP客户端建立](#2.1 TCP客户端建立)
    • [2.2 TCP循环客户端](#2.2 TCP循环客户端)
  • [3. UDP server](#3. UDP server)
  • [4. UDP client](#4. UDP client)
  • [5. UDP Multicast send](#5. UDP Multicast send)
  • [6. 常用函数](#6. 常用函数)
    • [6.1 socket()](#6.1 socket())
    • [6.2 htons()](#6.2 htons())
    • [6.3 ntohs()](#6.3 ntohs())
    • [6.4 inet_addr()](#6.4 inet_addr())
    • [6.5 accept()](#6.5 accept())
    • [6.6 recv()](#6.6 recv())

1.TCP server

1.1 TCP服务器建立

步骤:

1.建立tcp socket;

2.初始化tcp server struct;

3.绑定 tcp server struct 到 socket;

4.设置监听;

5.accept等待客户端连接;

6.关闭监听连接;

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <bits/types.h>

int main(int argc, char *argv[])
{
    if(argc != 3)
    {
        printf("format error usage:./a.out <ip> <port>\n");
        return -1;
    }
    struct sockaddr_in server_addr, client_addr;
    int socket_fd = 0;
    
    
    socket_fd = socket(AF_INET, SOCK_STREAM, 0);
    if(socket_fd < 0)
    {
        perror("socket建立失败");
        return -1;
    }
    printf("socket_fd=%d\n", socket_fd);

    /*设置tcpserver sockaddr_in 结构体中相关参数*/
    bzero(&server_addr, sizeof(server_addr)); 
    server_addr.sin_family = AF_INET;
    server_addr.sin_port = htons(atoi(argv[2]));
    server_addr.sin_addr.s_addr = inet_addr(argv[1]);

    /*绑定函数bind()*/
    int blind_fd;
    blind_fd = bind(socket_fd, (struct sockaddr*)&server_addr, sizeof(server_addr));
    if(blind_fd == -1)
    {
        perror("绑定失败");
        return -1;
    }
    printf("绑定成功\n");
    /*调用listen()函数,设置监听模式*/
    if (listen(socket_fd, 10) == -1)
    {
        perror("监听失败");
        return -1;
    }
    printf("监听中...\n");
    /*调用accept()函数,等待客户端的连接*/
    int connect_fd;
    socklen_t client_addr_len = sizeof(client_addr);
    char recv_buf[128];
    memset(recv_buf , 0, sizeof(recv_buf));
    while(1)
    {
        connect_fd = accept(socket_fd, (struct sockaddr*)&client_addr, &client_addr_len);
        if(connect_fd < 0)
        {
            perror("client 连接失败");
            return -1;
        }
        printf("客户端[%s:%d:%d]已连接\n",
            inet_ntoa(client_addr.sin_addr),
            ntohs(client_addr.sin_port),
            atoi(argv[2]));
        while(1)
        {
            //接收数据
            if (recv(connect_fd, recv_buf, 128, 0) == -1)
            {
                perror("接收数据失败");
                return -1;
            }
            //显示接收数据
            // printf("接收的数据:%s\n", recv_buf);
            printf("接收来自[%s:%d:%d]的数据:%s\n", 
                inet_ntoa(client_addr.sin_addr), 
                ntohs(client_addr.sin_port), 
                atoi(argv[2]),
                recv_buf);
            //返回接受信息至客户端
            send(connect_fd, recv_buf,  sizeof(connect_fd), 0);
        }
    }
    close(connect_fd);
    close(socket_fd);
    return 0;
}

执行结果

1.2 TCP循环服务器

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>

#define BUFFER_SIZE		128

int main(int argc, char *argv[])
{
     int listenfd, connfd, n;
     struct sockaddr_in servaddr, cliaddr;
     socklen_t peerlen;
     char buf[BUFFER_SIZE];
     
     if (argc < 3)
     {
        printf("Usage : %s <ip> <port>\n", argv[0]);
        return -1;
     }

     /*建立Socket连接*/
     if ((listenfd = socket(AF_INET,SOCK_STREAM,0))== -1)
     {
         perror("socket");
         return -1;
     }
       
     /*设置sockaddr_in 结构体中相关参数*/
     bzero(&servaddr, sizeof(servaddr));    
     servaddr.sin_family = AF_INET;
     servaddr.sin_port = htons(atoi(argv[2]));
     servaddr.sin_addr.s_addr = inet_addr(argv[1]);
    
     
     /*绑定函数bind()*/
     if (bind(listenfd, (struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
     {
         perror("绑定失败");
         return -1;
     }
        
     /*调用listen()函数,设置监听模式*/
     if (listen(listenfd, 10) == -1)
     {
         perror("开始监听");
         return -1;
     }
        
     /*调用accept()函数,等待客户端的连接*/
     peerlen = sizeof(cliaddr);
     while ( 1 )
     {
         if ((connfd = accept(listenfd, (struct sockaddr *)&cliaddr, &peerlen)) < 0)
         {
            perror("accept");
            return -1;
         }
         printf("connection from [%s:%d]\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port));
     
     /*调用recv()函数接收客户端发送的数据*/
         while ((n = recv(connfd, buf, BUFFER_SIZE, 0)) > 0)
         {
             printf("echo : %s", buf);
             send(connfd, buf, n, 0);
         }
         printf("客户端关闭\n");
         close(connfd);
     }

     close(listenfd);
     return -1;
}

1.3 TCP并发服务器

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <signal.h>

#define BUFFER_SIZE     128

int main(int argc, char *argv[])
{
     int listenfd, connfd, n;
     pid_t pid;
     struct sockaddr_in servaddr, cliaddr;
     socklen_t peerlen;
     char buf[BUFFER_SIZE];

     if (argc < 3)
     {
        printf("Usage : %s <ip> <port>\n", argv[0]);
        return -1;
     }

     /*建立Socket连接*/
     if ((listenfd = socket(AF_INET,SOCK_STREAM,0))== -1)
     {
         perror("socket");
         return -1;
     }

     /*设置sockaddr_in 结构体中相关参数*/
     bzero(&servaddr, sizeof(servaddr));
     servaddr.sin_family = AF_INET;
     servaddr.sin_port = htons(atoi(argv[2]));
     servaddr.sin_addr.s_addr = inet_addr(argv[1]);


     /*绑定函数bind()*/
     if (bind(listenfd, (struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
     {
         perror("bind");
         return -1;
     }

     /*调用listen()函数,设置监听模式*/
     if (listen(listenfd, 10) == -1)
     {
         perror("listen");
         return -1;
     }

     signal(SIGCHLD, SIG_IGN); /* 忽略SIGCHLD信号,避免僵死进程*/

     /*调用accept()函数,等待客户端的连接*/
     peerlen = sizeof(cliaddr);
     while ( 1 )
     {
         if ((connfd = accept(listenfd, (struct sockaddr *)&cliaddr, &peerlen)) < 0)
         {
            perror("accept");
            return -1;
         }
         printf("connection from [%s:%d]\n", inet_ntoa(cliaddr.sin_addr), 
                ntohs(cliaddr.sin_port));
         if ((pid = fork()) < 0)  /* 创建子进程 */
         {
            perror("fork");
            return -1;
         }
         else if (pid == 0)
         {
             /*调用recv()函数接收客户端发送的数据*/
             while ((n = recv(connfd, buf, BUFFER_SIZE, 0)) > 0)
             {
                printf("echo : %s", buf);
                send(connfd, buf, n, 0);
             }
             printf("client is closed\n");
             return 0;  /* 子进程结束 */
         }
         else
         {
            close(connfd);
         }
     }

     close(listenfd);
     return 0;
}

1.4 TCP并发服务器(进程)

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <signal.h>


int main(int argc, char *argv[])
{
    if(argc != 3)
    {
        printf("error format:./%s <IP> <port>\n", argv[0]);
        return -1;
    }
    //
    int socket_fd, listen_fd;
    struct sockaddr_in server_str, client_str;

    //建立socket
    socket_fd = socket(AF_INET, SOCK_STREAM, 0);
    if(socket_fd == -1)
    {
        perror("socket创建失败");
        return -1;
    }
    printf("socket_fd=%d\n", socket_fd);
    //服务器结构体初始化
    memset(&server_str, 0, sizeof(server_str));
    server_str.sin_family = AF_INET;
    server_str.sin_port = htons(atoi(argv[2]));
    server_str.sin_addr.s_addr = inet_addr(argv[1]);

    //绑定socket与server结构体
    if (bind(socket_fd, (struct sockaddr *)&server_str, sizeof(server_str)) < 0)
     {
         perror("bind");
         return -1;
     }
     printf("绑定成功\n");

     listen_fd = listen(socket_fd, 10);
     if(socket_fd == -1)
     {
        perror("监听失败");
        return -1;
     }
     printf("监听中...%d\n", listen_fd);

     //忽略SIGCHLD信号,避免僵死进程
     signal(SIGCHLD, SIG_IGN);
     int connect_fd, pid_fd, client_len;
     char ip_addrstr[128] = {0};
     client_len = sizeof(client_str);
     while(1)
     {
        connect_fd = accept(socket_fd, (struct sockaddr *)&client_str, &client_len);
        if(connect_fd < 0)
        {   
            printf("客户端[%s]连接失败\n", inet_ntoa(client_str.sin_addr));
            perror("client disconnect");
            return -1;
        }
        printf("客户端[%s]连接成功\n", inet_ntoa(client_str.sin_addr));
        // ip_addrstr[128] = inet_ntoa(client_str.sin_addr);
        pid_fd = fork();
        if(pid_fd < 0) //建立子进程失败
        {
            perror("son process final");
            return -1;
        }
        else if(pid_fd == 0) //成功创建子进程
        {
            char son_pro_buf[1024] = {0};
            int son_pro_recv_fd, son_send_fd;
            char son_process_ip = inet_ntoa(client_str.sin_addr);
            char son_recv_buf[1024] = {0};
            printf("进入子进程\n");
            while((son_pro_recv_fd = recv(connect_fd, son_recv_buf, 1024, 0)) > 0)
            {
                son_send_fd = send(connect_fd, son_recv_buf, son_pro_recv_fd, 0);
                if(son_send_fd == -1)
                {
                    printf("向客户端[%s]发送数据失败\n", son_process_ip);
                }
                else
                {
                    printf("服务器收到数据:%s\n", son_recv_buf);
                }
            }
            // perror("sonprocess field");
            printf("客户端[%s]关闭\n", inet_ntoa(client_str.sin_addr));
            return 0;
        }
        else
        {
            close(connect_fd);
        }
    }
    close(socket_fd);
    return 0;
}

2. TCP client

2.1 TCP客户端建立

1.建立socket;

2.设置并初始化server结构体;

3.调用connect函数向服务器建立tcp连接;

4.send()函数向服务器发送数据;

5.接收服务器数据;

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>


#define BUFFER_SIZE 128

int main(int argc, char *argv[])
{
     int sockfd;
     char buf[BUFFER_SIZE] = "Hello Server";
     struct sockaddr_in servaddr;
     
     if (argc < 3)
     {
        printf("Usage : %s <ip> <port>\n", argv[0]);
        exit(-1);
     }

     
     /*创建Socket*/
     if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1)
     {
         perror("socket");
         exit(-1);
     }
     
     /*设置sockaddr_in 结构体中相关参数*/
     bzero(&servaddr, sizeof(servaddr));
     servaddr.sin_family = AF_INET;
     servaddr.sin_port = htons(atoi(argv[2]));
     servaddr.sin_addr.s_addr = inet_addr(argv[1]);
     
     /*调用connect()函数向服务器端建立TCP连接*/
     if(connect(sockfd,(struct sockaddr *)&servaddr, 
                            sizeof(servaddr))== -1)
     {
          perror("connect");
          exit(-1);
     }
     /*发送消息给服务器端*/
     send(sockfd, buf, sizeof(buf), 0);
     if (recv(sockfd, buf, sizeof(buf), 0) == -1)
     {
        perror("recv");
        exit(-1);
     }
     printf("recv from server : %s\n", buf);
     close(sockfd);
     exit(0);
}

连续输入数据并发送

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>

int main(int argc, char *argv[])
{
    if(argc != 3)
    {
        printf("format error usage:./a.out <ip> <port>\n");
        return -1;
    }
    struct sockaddr_in client_stru, server_stru;
    int socket_fd = 0;
    
    //TCP 流
    socket_fd = socket(AF_INET, SOCK_STREAM, 0);
    if(socket_fd < 0)
    {
        perror("socket建立失败");
        return -1;
    }
    printf("socket_fd=%d\n", socket_fd);

    /*设置tcpserver sockaddr_in 结构体中相关参数*/
    bzero(&server_stru, sizeof(server_stru)); 
    server_stru.sin_family = AF_INET;
    server_stru.sin_port = htons(atoi(argv[2]));
    server_stru.sin_addr.s_addr = inet_addr(argv[1]);

    /*建立连接*/
    int connect_fd;
    connect_fd = connect(socket_fd, (struct sockaddr*)&server_stru, sizeof(server_stru));
    if(connect_fd == -1)
    {
        perror("连接失败");
        return -1;
    }
    printf("连接成功\n");
    /*发送数据*/
    char hello[] = "hello world\n";
    char send_buf[1024] = {0};
    char recv_buf[1024] = {0};
    int send_fd = 0;
    int fgets_len;
    while(1)
    {
        fgets_len = fgets(send_buf, sizeof(send_buf), stdin);

        send_fd = send(socket_fd, send_buf, strlen(send_buf), 0);
        
        //阻塞接收
        if (recv(socket_fd, recv_buf, sizeof(recv_buf), 0) == -1)
        {
            perror("接收数据失败");
            return -1;
        }
        printf("收到的数据为:%s\n", recv_buf);
    }
    close(connect_fd);
    close(socket_fd);
    return 0;
}

TCP SERVER 使用本文内容

TCP CLIENT 结束到的数据

2.2 TCP循环客户端

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>

#define BUFFER_SIZE 128

int main(int argc, char *argv[])
{
	int sockfd;
	char buf[BUFFER_SIZE];
	struct sockaddr_in servaddr;

	if (argc < 3)
	{
		printf("Usage : %s <ip> <port>\n", argv[0]);
		return -1;
	}


	/*创建Socket*/
	if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1)
	{
		perror("socket");
		return -1;
	}

	/*设置sockaddr_in 结构体中相关参数*/
	bzero(&servaddr, sizeof(servaddr));
	servaddr.sin_family = AF_INET;
	servaddr.sin_port = htons(atoi(argv[2]));
	servaddr.sin_addr.s_addr = inet_addr(argv[1]);

	/*调用connect()函数向服务器端建立TCP连接*/
	if(connect(sockfd,(struct sockaddr *)&servaddr, 
				sizeof(servaddr))== -1)
	{
		perror("connect");
		return -1;
	}

	/*循环从键盘输入*/
	while ( 1 )
	{
		printf("input > ");
		fgets(buf, sizeof(buf), stdin);
		if (strcmp(buf, "quit\n") == 0) 
			break;  	/*若输入input,跳出循环*/

		send(sockfd, buf, sizeof(buf), 0);  		/*发送消息给服务器端*/

		bzero(buf, sizeof(buf));

		recv(sockfd, buf, sizeof(buf), 0);  		/*接收服务器端发回的消息*/
		printf("recv from server : %s\n", buf);
	}
	printf("client exit\n");
	close(sockfd);  /*关闭TCP连接*/
	return 0;
}

3. UDP server

1.建立socket();

2.设置服务器结构体;

3.绑定结构体与socket();

4.接收数据,保存client结构体数据;

5.发送数据;

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>

#define BUFFER_SIZE		128

int main(int argc, char *argv[])
{
	int sockfd;
	struct sockaddr_in servaddr, cliaddr;
	socklen_t peerlen;
	char buf[BUFFER_SIZE];

	if (argc < 3)
	{
		printf("Usage : %s <ip> <port>\n", argv[0]);
		exit(-1);
	}

	/*建立Socket连接*/
	if ((sockfd = socket(AF_INET,SOCK_DGRAM,0))== -1)
	{
		perror("socket创建失败");
		return -1;
	}
	printf("sockfd = %d\n", sockfd);

	/*设置sockaddr_in 结构体中相关参数*/
	bzero(&servaddr, sizeof(servaddr));    
	servaddr.sin_family = AF_INET;
	servaddr.sin_port = htons(atoi(argv[2]));
	servaddr.sin_addr.s_addr = inet_addr(argv[1]);


	/*绑定函数bind()*/
	if (bind(sockfd, (struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
	{
		perror("bind");
		exit(-1);
	}
	printf("绑定成功!\n");


	/*调用recvfrom()函数,等待接收客户端的数据*/
	peerlen = sizeof(cliaddr);
	while (1)
	{
		if (recvfrom(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&cliaddr, &peerlen) < 0)
		{
			perror("recvfrom");
			return -1;
		}
        //
		printf("Received a message: %s\n", buf);
        //置入发送内容
		// strcpy(buf, "Welcome to server");
        //发送数据
		sendto(sockfd, buf, strlen(buf), 0, (struct sockaddr *)&cliaddr, peerlen);
	}

	close(sockfd);
	return 0;
}

执行结果

增加输出IP及端口号

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>

#define BUFFER_SIZE		128

int main(int argc, char *argv[])
{
	int sockfd;
	struct sockaddr_in servaddr, cliaddr;
	socklen_t peerlen;
	char buf[BUFFER_SIZE];

	if (argc < 3)
	{
		printf("Usage : %s <ip> <port>\n", argv[0]);
		exit(-1);
	}

	/*建立Socket连接*/
	if ((sockfd = socket(AF_INET,SOCK_DGRAM,0))== -1)
	{
		perror("socket创建失败");
		return -1;
	}
	printf("sockfd = %d\n", sockfd);

	/*设置sockaddr_in 结构体中相关参数*/
	bzero(&servaddr, sizeof(servaddr));    
	servaddr.sin_family = AF_INET;
	servaddr.sin_port = htons(atoi(argv[2])); 
	// servaddr.sin_addr.s_addr = inet_addr(argv[1]);  //INADDR_ANY;  //监听所有网卡
    servaddr.sin_addr.s_addr = INADDR_ANY;  //INADDR_ANY;  //监听所有网卡

	/*绑定函数bind()*/
	if (bind(sockfd, (struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
	{
		perror("bind");
		return -1;
	}
	printf("绑定成功!\n");


	/*调用recvfrom()函数,等待接收客户端的数据*/
	peerlen = sizeof(cliaddr);
	while (1)
	{
		if (recvfrom(sockfd, buf, sizeof(buf), 0, (struct sockaddr *)&cliaddr, &peerlen) < 0)
		{
			perror("recvfrom");
			return -1;
		}
        //
		printf("收到[%s:%d]的数据: %s\n", inet_ntoa(cliaddr.sin_addr), ntohs(cliaddr.sin_port), buf);
        //置入发送内容
		// strcpy(buf, "Welcome to server");
        //发送数据
		sendto(sockfd, buf, strlen(buf), 0, (struct sockaddr *)&cliaddr, peerlen);
	}

	close(sockfd);
	return 0;
}

4. UDP client

1.建立socket();

2.设置服务器结构体;

4.发送数据;

5.接收数据;

复制代码
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>

#define BUFFER_SIZE 128

int main(int argc, char *argv[])
{
    int sockfd;
    char buf[BUFFER_SIZE] = "Hello Server";
    struct sockaddr_in servaddr;
    
    if (argc < 3)
    {
       printf("Usage : %s <ip> <port>\n", argv[0]);
       return -1;
    }

    /*创建Socket*/
    if ((sockfd = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
    {
       perror("socket");
       return -1;
    }
     
     /*设置sockaddr_in 结构体中相关参数*/
     bzero(&servaddr, sizeof(servaddr));
     servaddr.sin_family = AF_INET;
     servaddr.sin_port = htons(atoi(argv[2]));
     servaddr.sin_addr.s_addr = inet_addr(argv[1]);
     
     /*发送消息给服务器端*/
     char send_buf[1024] = {0};
     int fgets_flag;
    sendto(sockfd, buf, strlen(buf), 0, (struct sockaddr *)&servaddr, sizeof (servaddr));
    if (recvfrom(sockfd, send_buf, sizeof(send_buf), 0, NULL, NULL) < 0)
    {
        perror("recvfrom");
        return -1;
    }
    printf("收到服务器数据: %s\n", send_buf);

     close(sockfd);
     return 0;
}

5. UDP Multicast send

linux组播发送步骤:

1.建立socket();

创建 SOCK_DGRAM(UDP) 套接字。

2.填充组播struct();:

IP_MULTICAST_IF:指定从哪个网卡接口发送组播(必须设置,否则内核无法选出口);

IP_MULTICAST_TTL:设置组播数据包的跳数限制(默认 1,仅局域网);

IP_MULTICAST_LOOP:是否允许回环到本机(默认开启);

3.加入组播(绑定);

4.发送数据;

Linux 组播(Multicast)发送的核心原理是:基于 UDP 协议,向组播 IP 地址发送数据,由网络设备(交换机 / 路由器)根据组播组成员关系,将数据包复制并转发给所有加入该组的接收者,一发多收。

6. 常用函数

6.1 socket()

接口函数,套接字

socket(AF_INET, SOCK_STREAM, 0);

返回值:

-1 -> 建立socket失败;

整数,创建套接字描述符;

参数:

AF_INET:IPV4协议,IPV6不常用;

SOCK_STREAM:流,TCP使用,UDP使用SOCK_STREAM,流较为稳定;

最后一个参数0:自动匹配协议,使用0就行,也可以手动指定,IPPROTO_TCP制定TCP,IPPROTO_UDP指定UDP。

6.2 htons()

Host to Network Short(主机字节序 → 网络字节序,短整型)

作用:把主机端的端口号,转换成网络能识别的格式

头文件:

#include <arpa/inet.h> // Linux/macOS

#include <winsock2.h> // Windows

函数原型:

uint16_t htons(uint16_t hostshort);

用法:

复制代码
// 端口必须用 htons 转换
server_addr.sin_port = htons(8080);

6.3 ntohs()

打印客户端 IP、端口时必须用

和 htons() 是一对相反操作

用法:

ntohs(cliaddr.sin_port)

6.4 inet_addr()

C 网络编程中用于 IP 地址格式转换

作用:把点分十进制字符串 IP(如 "192.168.1.1")转换成网络字节序的整数 IP

转换失败返回 INADDR_NONE(值为 0xffffffff)

头文件:

#include <arpa/inet.h> // Linux/macOS

#include <winsock2.h> // Windows

函数原型:

in_addr_t inet_addr(const char *cp);

用法:

复制代码
struct sockaddr_in server_addr;

// 直接转换并赋值 IP 地址
server_addr.sin_addr.s_addr = inet_addr("192.168.1.100");

特殊用法:

INADDR_ANY = 监听本机所有网卡(等价 inet_addr("0.0.0.0"))

复制代码
server_addr.sin_addr.s_addr = INADDR_ANY;

6.5 accept()

作用:从「等待连接队列」里取出一个客户端连接,创建一个新的套接字专门和这个客户端通信

函数原型:

int accept(int sockfd, struct sockaddr *addr, socklen_t *addrlen);

参数:

sockfd:就是 socket() 创建、bind()/listen() 用过的 监听套接字;

addr:传出参数:用来保存客户端的 IP 和端口;

addrlen:传入:地址结构体大小;传出:客户端地址实际长度。

返回值:

返回一个文件描述符 fd,这个 fd 专门用来和客户端通信(recv / send),失败返回-1;

6.6 recv()

服务器函数,专门用来和客户端接收数据

相关推荐
王燕龙(大卫)2 小时前
通过文心快码,2小时完成一周的工作量
服务器·网络·tcp/ip
yuyuzururu2 小时前
计算机网络实验作业-IP分组分片和ARP实验
网络·tcp/ip·计算机网络
杰克崔2 小时前
preempt_count()、in_interrupt()等上下文判断常用函数及宏介绍
linux·运维·服务器·车载系统
生活很暖很治愈2 小时前
Linux——TCP通信
linux·运维·tcp/ip
开开心心就好2 小时前
小巧绿色免费关机工具,支持定时倒计时
linux·运维·服务器·安全·powerpoint·1024程序员节·foxmail
孫治AllenSun3 小时前
【Linux】配置服务自启动
linux·运维·服务器
rell3363 小时前
机顶盒播放udp/rtp马赛克
java·网络·网络协议·udp
小生不才yz3 小时前
【Makefile 专家之路 | 基础篇】03. 规矩方圆:书写规则详解(通配符、文件搜索与伪目标)
linux
tang777894 小时前
哪些行业用动态代理ip?哪些行业用静态代理IP?怎样区分动态ip和静态ip?(互联网人必码·实用长文)
大数据·网络·爬虫·python·网络协议·tcp/ip·智能路由器