• Linux 网络编程三(socket代码详解)


    //网络编程客户端
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <unistd.h>
    #include <errno.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <arpa/inet.h>//htons()函数头文件
    #include <netinet/in.h>//inet_addr()头文件
    
    int main(int arg,char *args[])
    {
        int st=socket(AF_INET,SOCK_STREAM,0);//初始化socket
        if(st==-1)
        {
            printf("init socket failed ! error message :%s
    ",strerror(errno));
            return -1;
        }
        struct sockaddr_in addr;//定义IP地址结构
        memset(&addr,0,sizeof(addr));
        addr.sin_family=AF_INET;//设置结构地址类型为TCP/IP地址
        /*
         字节转化
                网络当中传输数据是以字节为单位,short类型无法在网络中传输,必须转化成网络类型,
                例如short类型有2个字节,在网络传输中无法知道哪个是高位字节,那个是低位字节,所以系统提供htons()函数来处理。
                所以,在网络中传输非char型数据,必须调用相应的系统函数,将这个类型转化成网络中的char类型。
         */
        addr.sin_port=htons(8080);//指定端口号  htons:将short类型从host字节类型到net字节类型转化
        /*
         IP地址在内存中是一个整数,但是我们习惯于写一个字符串
         inet_addr()函数能将一个字符串的IP地址转化成一个int类型数字
         */
        addr.sin_addr.s_addr=inet_addr("127.0.0.1");
        //调用connect()函数连接结构addr指定的IP地址和端口号
        /*
          connect()函数第二个参数详解:
          struct sockaddr类型是一个比较旧的类型,现在一般都使用struct sockaddr_in类型
              但是struct sockaddr和struct sockaddr_in类型是相互兼容的
         */
        if(connect(st,(struct sockaddr *)&addr,sizeof(addr))==-1)
        {
            printf("connect failed ! error message :%s
    ",strerror(errno));
            goto END;
        }
        char buf[1024]={0};
        strcpy(buf,"fly on air !
    ");
        if(send(st,buf,strlen(buf),0)==-1)//发送buf中的数据
        {
            printf("send failed ! error message:%s
    ",strerror(errno));
            goto END;
        }
    END:
        close(st);
        return 0;
    }
    //网络编程服务端
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>
    #include <unistd.h>
    #include <errno.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <arpa/inet.h>//htons()函数头文件
    #include <netinet/in.h>//inet_addr()头文件
    
    int main(int arg,char *args[])
    {
        int st=socket(AF_INET,SOCK_STREAM,0);//初始化socket
        if(st==-1)
        {
            printf("init socket failed ! error message :%s
    ",strerror(errno));
            return -1;
        }
    
        int on=1;
        if(setsockopt(st,SOL_SOCKET,SO_REUSEADDR,&on,sizeof(on))==-1)
        {
            printf("setsockopt failed ! error message :%s
    ",strerror(errno));
            goto END;
        }
    
        struct sockaddr_in addr;
        memset(&addr,0,sizeof(addr));
        addr.sin_family=AF_INET;
        //服务端绑定端口号时,需要去系统设置里将该端口号打开
        addr.sin_port=htons(8080);
        /*
         htonl()函数将一个4字节的long类型数据转化成网络类型
         */
        addr.sin_addr.s_addr=htonl(INADDR_ANY);//INADDR_ANY代表这个server上所有的地址
        //将IP地址与server进行绑定
        if(bind(st,(struct sockaddr *)&addr,sizeof(addr))==-1)
        {
            printf("bind IP addr failed ! error message:%s
    ",strerror(errno));
            goto END;
        }
        //server开始listen
        if(listen(st,10)==-1)
        {
            printf("listen failed ! error message :%s
    ",strerror(errno));
            goto END;
        }
        int client_st=0;//client端socket
        struct sockaddr_in clientaddr;//client端的IP地址
        char buf[1024]={0};
        int i=0;
        while(i<1)
        {
            memset(&clientaddr,0,sizeof(clientaddr));
            socklen_t len= sizeof(clientaddr);//表示client地址的最大字节数
            /*
             accept会阻塞当前线程,直到有客户端连接过来,accept()函数返回client端的socket描述符
             */
            client_st=accept(st,(struct sockaddr *)&clientaddr,&len);
            if(client_st==-1)
            {
                printf("accept failed ! error message :%s
    ",strerror(errno));
                goto END;
            }
            if(recv(client_st,buf,sizeof(buf),0)==-1)//接收来自client端的消息
            {
                printf("recv failed , send from IP  error message:%s
    ",strerror(errno));
                close(client_st);//关闭client端socket
                goto END;
            }
            printf("%s",buf);
            close(client_st);//关闭client端socket
            memset(buf,0,sizeof(buf));
            i++;
        }
    END:
        close(st);//关闭服务器socket
        return 0;
    }
    .SUFFIXES:.c .o
    CC=gcc
    SRCS1=myclient.c
    SRCS2=server.c
    OBJS1=$(SRCS1:.c=.o)
    OBJS2=$(SRCS2:.c=.o)
    EXEC1=mclient
    EXEC2=mserver
    
    start:$(OBJS1) $(OBJS2)
        $(CC) -o $(EXEC1) $(OBJS1)
        $(CC) -o $(EXEC2) $(OBJS2)
        @echo "-------ok-----------"
    .c.o:
        $(CC) -Wall -g -o $@ -c $<
    clean:
        rm -f $(OBJS1)
        rm -f $(EXEC1)
        rm -f $(OBJS2)
        rm -f $(EXEC2)
    Linux打开端口号

  • 相关阅读:
    【洛谷】P1303 A*B Problem(高精度乘法模板)
    快速幂
    【洛谷】P1601 A+B Problem 高精(高精度加法模板)
    进制转换
    【洛谷】P1551 亲戚(并查集模板)
    求最大公约数的两种方法
    快速排序
    异或交换两个数
    数字字符串互相转换的三种方法
    Hello world(我来啦)
  • 原文地址:https://www.cnblogs.com/zhanggaofeng/p/5870103.html
Copyright © 2020-2023  润新知