udp 多线程客户端和单线程服务器端

论坛 期权论坛 编程之家     
选择匿名的用户   2021-6-2 16:17   1372   0

具体功能: 客户端读取本地的文件,将内容发给服务器,服务器打印接收到的信息并返回当前服务器的时间,客户端接收到服务器发的消息,打印


客户端:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <pthread.h>
#include <netdb.h>
#include <fcntl.h>

#define MAX_THREAD 26
#define BUFFER_SIZE 1024

char *src_path = "/home/test";

struct MYPARAM
{
    char *server_ip;
    char *server_port;
};

//读取本地文件
void read_file(char buffer[], char* src)
{
    char buffer1[1024];
    int read_size;
    int src_fd;
    //打开本地文件 
    if((src_fd = open(src, O_RDONLY)) < 0)
    {
        perror("Open /home/test  failed:");
        exit(1);
    }
    //读取本地文件 
    if((read_size = read(src_fd, buffer, sizeof(buffer1))) < 0 )
    {
        perror("Read failed:");
        exit(1);
    }
}

void* thread(void *arg)
{
    char sendBuffer[BUFFER_SIZE];
    char recvBuffer[BUFFER_SIZE];
    struct MYPARAM recv_para;
    recv_para = *(struct MYPARAM *)arg;

    struct timeval time_out;
    time_out.tv_sec = 100;
    time_out.tv_usec = 0;

    int clientsocket = 0;
    clientsocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
    setsockopt(clientsocket, SOL_SOCKET, SO_RCVTIMEO, &time_out, sizeof(time_out));
    //构造服务器地址
    struct sockaddr_in serveraddr;
    memset(&serveraddr, 0, sizeof(serveraddr));
    serveraddr.sin_family = AF_INET;
    serveraddr.sin_port = htons(atoi(recv_para.server_port));
    //将ip字符串地址转换成网络字节序
    inet_pton(AF_INET, recv_para.server_ip, &serveraddr.sin_addr);

    read_file(sendBuffer,src_path);

    //发送数据
    int sendlen = 0;
    if((sendlen = sendto(clientsocket, sendBuffer, strlen(sendBuffer), 0,
                        (struct sockaddr*)&serveraddr, sizeof(serveraddr))) < 0)
    {
        perror(" Send to error \n");
        exit(1);
    }
    printf("Child thread [%d]:Has Send to server %d bytes \n",(unsigned int)pthread_self(),sendlen);
    //接收服务器发来的消息
    int recvlen = 0;
    recvlen = recvfrom(clientsocket, recvBuffer, sizeof(recvBuffer), 0, NULL,NULL);
    if(recvlen < 0)
    {
        printf("recvlen =  %d \n" , recvlen);
        perror("\n Recieve from server error");
        exit(1);
    }
    printf("Child thread [%d]: recv frome server: %s ", (unsigned int)pthread_self(), recvBuffer);
    printf("leave thread [%d] \n", (unsigned int)pthread_self());
    pthread_exit(NULL);
}

int main(int argc,char *argv[])
{
    if(argc !=3)
    {
        printf("\n Usage: %s <ip and port of server",argv[0]);
        return 1;
    }
    struct MYPARAM param;
    param.server_ip = argv[1];
    param.server_port = argv[2];
    pthread_t thread_id[MAX_THREAD];
    int rc[MAX_THREAD];
    int i;
    for(i = 0; i < MAX_THREAD; i ++)
    {
        rc[i] = pthread_create(&thread_id[i], NULL, thread, (void *) &param);
        if(rc[i] != 0)
            printf("create thread %d failed!\n",i);
        printf("create thread %d !\n",i);
    }
    int j;
    for(j = 0; j < MAX_THREAD; j ++)
        pthread_join(thread_id[j],NULL);
   return 0;
}
服务器端:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netdb.h>
#include <time.h>
#include <arpa/inet.h>

int main()
{
    int serversock = 0;
    serversock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);

    //初始化服务器地址
    struct sockaddr_in serveraddr;
    memset(&serveraddr, 0, sizeof(serveraddr));
    serveraddr.sin_family = AF_INET;
    serveraddr.sin_addr.s_addr = htonl(INADDR_ANY);
    serveraddr.sin_port = htons(1516);

    bind(serversock, (struct sockaddr*)&serveraddr, sizeof(serveraddr));

    struct sockaddr_in clientaddr;
    memset(&clientaddr, 0, sizeof(clientaddr));
    int c_addr_len = sizeof(clientaddr);

    printf("UDP Server is running.......\n");

    int recvlen = 0;
    int sendlen = 0;

    while(1)
    {
        char recvbuffer[1024];
        memset(recvbuffer, 0, sizeof(recvbuffer));
        if((recvlen = recvfrom(serversock, recvbuffer, sizeof(recvbuffer), 0,
                        (struct sockaddr*)&clientaddr, (socklen_t*)&c_addr_len)) < 0)
        {
            perror("\n Recieve from error:");
            exit(1);
        }
        printf("Recieve from client<%s:%d>:  \"", inet_ntoa(clientaddr.sin_addr), ntohs(clientaddr.sin_port));
        fputs(recvbuffer, stdout);
        fputs("  \" \n", stdout);
       
        char sendbuffer[1024];
        
        //获取时间并发送给客户端
        time_t ticks;
        ticks = time(NULL);
        snprintf(sendbuffer, sizeof(sendbuffer), "%.24s\r\n", ctime(&ticks));
        strcat(sendbuffer, str);
        if((sendlen = sendto(serversock, sendbuffer,
                             sizeof(sendbuffer), 0, (struct sockaddr*)&clientaddr, c_addr_len)) < 0)
        {
            perror("\nSend to error: ");
            exit(1);
        }
       sleep(1);
    }
    return 0;
}



分享到 :
0 人收藏
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

积分:3875789
帖子:775174
精华:0
期权论坛 期权论坛
发布
内容

下载期权论坛手机APP