鄙陋的prefork

/***********************************SERVER************************************************/
#include<unistd.h>
#include<error.h>
#include<stdlib.h>
#include<stdio.h>
#include<strings.h>
#include<sys/select.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<sys/wait.h>
#include<netinet/in.h>

#define PORT  9300
#define CHILD_NUM 10

typedef struct child{
   int sock;
   int id;
   pid_t  pid;
}child_t;

typedef struct childCon
{
   int sock_pair[2];
   int id;
}childCon_t;

child_t childs[CHILD_NUM];
childCon_t con[CHILD_NUM];

void do_child_work(int id)
{
    child_t c = childs[id];
    read(con[id].sock_pair[1],(void*)(&c.sock),sizeof(c.sock));
    printf("child %d get sock fd %d and exit\n",c.id,c.sock);
    exit(EXIT_SUCCESS);
}

pid_t make_child(int id)
{
    if(socketpair(AF_UNIX,SOCK_STREAM,0,con[id].sock_pair)==-1)
    {
        perror("create socket with child error");
        return -1;
    }else 
    {
        childs[id].id = id;
        pid_t p = fork();
        if(p > 0)
        {
            close(con[id].sock_pair[1]);
            childs[id].sock = con[id].sock_pair[0];
            childs[id].pid = p;

        }else if(p==0)
        {
            close(con[id].sock_pair[0]);
            do_child_work(id);        

        }else
        {
            perror("create child  error");
            return -1;
        }
    }
    return 0;
}

int main()
{
    int ls_sock;
    fd_set set;
    int max_fd ;
    struct sockaddr_in saddr;
    bzero(&saddr,sizeof(saddr));
    saddr.sin_family= AF_INET;
    saddr.sin_addr.s_addr=htonl(INADDR_ANY);
    saddr.sin_port = htons(PORT);
    FD_ZERO(&set);
    int child_use=0;
    if((ls_sock = socket(AF_INET,SOCK_STREAM,0))==-1)
    {
        perror("create socket error");
        exit(EXIT_FAILURE);
    }
    if(bind(ls_sock,(const struct sockaddr *)&saddr,sizeof(saddr))== -1)
    {
        perror("bind socket error");
        exit(EXIT_FAILURE);
    }
    int i;
    for (i=0;i<CHILD_NUM;i++)
    {
        make_child(i);
    }
    if(listen(ls_sock,200)==-1)
    {
        perror("listen socket error");
        exit(EXIT_FAILURE);
    }     
    FD_SET(ls_sock,&set);
    max_fd = ls_sock;
    while(1)
    {
        int selected;
        if((selected = select(max_fd+1,&set,NULL,NULL,NULL))==-1)
        {
            perror("select error");
            exit(EXIT_FAILURE);
        }
        if(FD_ISSET(ls_sock,&set))
        {
            int a_sock;
            socklen_t addrlen;
            struct sockaddr saddr;
            if((a_sock= accept(ls_sock,&saddr,&addrlen))== -1)
            {
                perror("accept socket error");
                exit(EXIT_FAILURE);
            }else
            {
                printf(" a client connected\n");
                if(child_use<CHILD_NUM)
                {
                    write(con[child_use].sock_pair[0],(void*)(&a_sock),sizeof(a_sock));
                    child_use++;
                }else
                {
                    break;
                }
            }
       }
    }
  int status;
  wait(&status); 
  exit(EXIT_SUCCESS);
  return 0;
}
/***********************************CLIENT************************************************/
#include<stdlib.h>
#include<netdb.h>
#include<strings.h>
#include<string.h>
#include<unistd.h>
#include <stdio.h>
#include <sys/types.h> 
#include <sys/socket.h>
#include <netinet/in.h>

int main(int argc, char *argv[])
{
    int sockfd, portno, n;
    struct sockaddr_in serv_addr;
    struct hostent *server;

    char buffer[256];

    if (argc < 3) {
        fprintf(stderr,"usage %s hostname port\n", argv[0]);
        exit(0);
    }
    portno = atoi(argv[2]);
    /* Create a socket point */
    sockfd = socket(AF_INET, SOCK_STREAM, 0);
    if (sockfd < 0) 
    {
        perror("ERROR opening socket");
        exit(1);
    }
    server = gethostbyname(argv[1]);
    if (server == NULL) {
        fprintf(stderr,"ERROR, no such host\n");
        exit(0);
    }

    bzero((char *) &serv_addr, sizeof(serv_addr));
    serv_addr.sin_family = AF_INET;
    bcopy((char *)server->h_addr, 
           (char *)&serv_addr.sin_addr.s_addr,
                server->h_length);
    serv_addr.sin_port = htons(portno);

    /* Now connect to the server */
    if (connect(sockfd,(struct sockaddr*)( &serv_addr),sizeof(serv_addr)) < 0) 
    {
         perror("ERROR connecting");
         exit(1);
    }	
    /* Now ask for a message from the user, this message
    * will be read by server
    */
    printf("Please enter the message: ");
    bzero(buffer,256);
    fgets(buffer,255,stdin);
    /* Send message to the server */
    n = write(sockfd,buffer,strlen(buffer));
    if (n < 0) 
    {
         perror("ERROR writing to socket");
         exit(1);
    }
    /* Now read server response */
    bzero(buffer,256);
    n = read(sockfd,buffer,255);
    if (n < 0) 
    {
         perror("ERROR reading from socket");
         exit(1);
    }
    printf("%s\n",buffer);
    return 0;
}
/***********************************poll版******************************************/
#include<unistd.h>
#include<error.h>
#include<stdlib.h>
#include<stdio.h>
#include<strings.h>
#include<poll.h>
#include<sys/select.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<sys/wait.h>
#include<netinet/in.h>

#define PORT  9300
#define CHILD_NUM 10

typedef struct child{
   int sock;
   int id;
   pid_t  pid;
}child_t;

typedef struct childCon
{
   int sock_pair[2];
   int id;
}childCon_t;

child_t childs[CHILD_NUM];
childCon_t con[CHILD_NUM];

void do_child_work(int id)
{
    child_t c = childs[id];
    read(con[id].sock_pair[1],(void*)(&c.sock),sizeof(c.sock));
    printf("child %d get sock fd %d and exit\n",c.id,c.sock);
    exit(EXIT_SUCCESS);
}

pid_t make_child(int id)
{
    if(socketpair(AF_UNIX,SOCK_STREAM,0,con[id].sock_pair)==-1)
    {
        perror("create socket with child error");
        return -1;
    }else 
    {
        childs[id].id = id;
        pid_t p = fork();
        if(p > 0)
        {
            close(con[id].sock_pair[1]);
            childs[id].sock = con[id].sock_pair[0];
            childs[id].pid = p;

        }else if(p==0)
        {
            close(con[id].sock_pair[0]);
            do_child_work(id);        

        }else
        {
            perror("create child  error");
            return -1;
        }
    }
    return 0;
}

int main()
{
    int ls_sock;
    int child_use=0;
    struct pollfd set[1];
    struct sockaddr_in saddr;
    bzero(&saddr,sizeof(saddr));
    saddr.sin_family= AF_INET;
    saddr.sin_addr.s_addr=htonl(INADDR_ANY);
    saddr.sin_port = htons(PORT);
    if((ls_sock = socket(AF_INET,SOCK_STREAM,0))==-1)
    {
        perror("create socket error");
        exit(EXIT_FAILURE);
    }
    if(bind(ls_sock,(const struct sockaddr *)&saddr,sizeof(saddr))== -1)
    {
        perror("bind socket error");
        exit(EXIT_FAILURE);
    }
    int i;
    for (i=0;i<CHILD_NUM;i++)
    {
        make_child(i);
    }
    if(listen(ls_sock,200)==-1)
    {
        perror("listen socket error");
        exit(EXIT_FAILURE);
    }     
    struct pollfd pfd;
    bzero(&pfd,sizeof(pfd));
    pfd.fd =  ls_sock;
    pfd.events |= POLLIN;
    set[0]=pfd; 
    while(1)
    {
        int selected;
        if((selected = poll(set,1,-1))==-1)
        {
            perror("select error");
            exit(EXIT_FAILURE);
        }
        if(set[0].revents&POLLIN)
        {
            int a_sock;
            socklen_t addrlen;
            struct sockaddr saddr;
            if((a_sock= accept(ls_sock,&saddr,&addrlen))== -1)
            {
                perror("accept socket error");
                exit(EXIT_FAILURE);
            }else
            {
                printf(" a client connected\n");
                if(child_use<CHILD_NUM)
                {
                    write(con[child_use].sock_pair[0],(void*)(&a_sock),sizeof(a_sock));
                    child_use++;
                }else
                {
                    break;
                }
            }
       }
    }
  int status;
  wait(&status); 
  exit(EXIT_SUCCESS);
  return 0;
}


你可能感兴趣的:(鄙陋的prefork)