网络编程--采用UDP协议的C/S架构实现

文章目录

  • 采用UDP协议的C/S架构实现
  • UDP协议传输文件的实现

采用UDP协议的C/S架构实现


UDP 的通信流程如下:

网络编程--采用UDP协议的C/S架构实现_第1张图片

服务器端的实现udp_cs_server.c

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 

void printPerror(const char *str)
{
    printf("%s: %d: ", __FILE__, __LINE__);
    perror(str);
}

int main()
{
    // 建立套接字
    int sfd = socket(AF_INET, SOCK_DGRAM, 0);
    if(-1 == sfd) {
        printPerror("socket");
        exit(-1);
    }

    // 把套接字和本地主机信息进行绑定
    struct sockaddr_in saddr;
    bzero(&saddr, sizeof(saddr));
    saddr.sin_family = AF_INET;
    saddr.sin_port = htons(8888);
    saddr.sin_addr.s_addr = INADDR_ANY;
    if(bind(sfd, (struct sockaddr *)&saddr, sizeof(struct sockaddr)) == -1) {
        printPerror("bind");
        close(sfd);
        exit(-1);
    }

    char buf[512] = {0};
    while(1) {
        // 接收来自客户端的消息
        struct sockaddr_in fromaddr;
        bzero(&fromaddr, sizeof(fromaddr));
        int fromaddrlen = sizeof(struct sockaddr);
        if(recvfrom(sfd, buf, sizeof(buf), 0, (struct sockaddr *)&fromaddr, &fromaddrlen) == -1) {
            printPerror("recvfrom");
            close(sfd);
            exit(-1);
        }
        printf("receive from %s %d, the message is: %s\n", inet_ntoa(fromaddr.sin_addr), ntohs(fromaddr.sin_port), buf);

        // 发生消息
        sendto(sfd, "world", 6, 0, (struct sockaddr *)&fromaddr, sizeof(struct sockaddr));
    }

    close(sfd);
}

客户端的实现udp_cs_client.c

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 

void printPerror(const char *str)
{
    printf("%s: %d: ", __FILE__, __LINE__);
    perror(str);
}

int main(int argc, char *argv[])
{
    // 建立套接字
    int sfd = socket(AF_INET, SOCK_DGRAM, 0);
    if(-1 == sfd) {
        printPerror("socket");
        exit(-1);
    }

    // 发生消息
    struct sockaddr_in toaddr;
    bzero(&toaddr, sizeof(toaddr));
    toaddr.sin_family = AF_INET;
    toaddr.sin_port = htons(8888);
    toaddr.sin_addr.s_addr = inet_addr(argv[1]); // 此处为服务器的ip
    sendto(sfd, "hello", 6, 0, (struct sockaddr *)&toaddr, sizeof(struct sockaddr));

    // 接收消息
    char buf[512] = {0};
    struct sockaddr_in fromaddr;
    bzero(&fromaddr, sizeof(fromaddr));
    int fromaddrlen = sizeof(struct sockaddr);
    if(recvfrom(sfd, buf, sizeof(buf), 0, (struct sockaddr *)&fromaddr, &fromaddrlen) == -1) {
        printPerror("recvfrom");
        close(sfd);
        exit(-1);
    }
    printf("receive from %s %d, the message is: %s\n", inet_ntoa(fromaddr.sin_addr), ntohs(fromaddr.sin_port), buf);

    close(sfd);
}

UDP协议传输文件的实现


UDP 发生文件时,先发送文件的大小,再发送文件的内容。

服务器端代码的实现:udp_cs_server_file.c

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 

void printPerror(const char *str)
{
    printf("%s: %d: ", __FILE__, __LINE__);
    perror(str);
}

int main()
{
    int sfd = socket(AF_INET, SOCK_DGRAM, 0);
    if(-1 == sfd) {
        printPerror("socket");
        exit(-1);
    }

    struct sockaddr_in saddr;
    bzero(&saddr, sizeof(saddr));
    saddr.sin_family = AF_INET;
    saddr.sin_port = htons(8888);
    saddr.sin_addr.s_addr = INADDR_ANY;
    if(bind(sfd, (struct sockaddr *)&saddr, sizeof(struct sockaddr)) == -1) {
        printPerror("bind");
        close(sfd);
        exit(-1);
    }

    char buf[512] = {0};
    struct sockaddr_in fromaddr;
    bzero(&fromaddr, sizeof(fromaddr));
    int fromaddrlen = sizeof(struct sockaddr);
    if(recvfrom(sfd, buf, sizeof(buf), 0, (struct sockaddr *)&fromaddr, &fromaddrlen) == -1) {
        printPerror("recvfrom");
        close(sfd);
        exit(-1);
    }
    printf("receive from %s %d, the message is: %s\n", inet_ntoa(fromaddr.sin_addr), ntohs(fromaddr.sin_port), buf);

    FILE *fp = fopen("1.txt", "rb");
    struct stat st; // 获取文件大小
    stat("1.txt", &st);
    int filelen = st.st_size;
    sendto(sfd, (void*)&filelen, sizeof(int), 0, (struct sockaddr *)&fromaddr, sizeof(struct sockaddr));

    // 发送文件数据
    while(!feof(fp)) {
        int len = fread(buf, 1, sizeof(buf), fp);
        sendto(sfd, buf, len, 0, (struct sockaddr *)&fromaddr, sizeof(struct sockaddr));
    }

    close(sfd);
}

创建客户端代码udp_cs_client_file.c

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 

#define BUFSIZE 512

void printPerror(const char *str)
{
    printf("%s: %d: ", __FILE__, __LINE__);
    perror(str);
}

int main(int argc, char *argv[])
{
    int sfd = socket(AF_INET, SOCK_DGRAM, 0);
    if(-1 == sfd) {
        printPerror("socket");
        exit(-1);
    }

    struct sockaddr_in toaddr;
    bzero(&toaddr, sizeof(toaddr));
    toaddr.sin_family = AF_INET;
    toaddr.sin_port = htons(8888);
    toaddr.sin_addr.s_addr = inet_addr(argv[1]); // 此处为服务器的ip
    sendto(sfd, "hello", 6, 0, (struct sockaddr *)&toaddr, sizeof(struct sockaddr));

    char buf[BUFSIZE] = {0};
    struct sockaddr_in fromaddr;
    bzero(&fromaddr, sizeof(fromaddr));
    int fromaddrlen = sizeof(struct sockaddr);
    int filelen = 0; // 用于保存文件的长度
    FILE *fp = fopen("2.txt", "w+b");
    recvfrom(sfd, (void *)&filelen, sizeof(int), 0, (struct sockaddr *)&fromaddr, &fromaddrlen);
    printf("the length of file is %d\n", filelen);
    printf("Create a new file!\n");
    printf("begin to receive file content!\n");

    // 接收此文件
    while(1) {
        int len = recvfrom(sfd, buf, sizeof(buf), 0, (struct sockaddr *)&fromaddr, &fromaddrlen);
        if(len < BUFSIZE) {
            // 如果接收的长度小于BUFFSIZE,则表示最后一次接收
            fwrite(buf, sizeof(char), len, fp);
            break;
        }
        fwrite(buf, sizeof(char), len, fp);
    }
    printf("receive file finished!\n");

    close(sfd);
}

你可能感兴趣的:(Linux编程)