Thread: client server query

  1. #1
    Registered User
    Join Date
    Nov 2008
    Posts
    216

    Thumbs up client server query

    I need to create client server socket and server must be able to support atleast 20 incoming connections from client at a time. once it exceeds the limit, it must block other requests for connection, by sending server busy message to other clients. tried with below socket code, but it doesnt seem to work. please provide inputs.

    Code:
    #include <sys/socket.h>
    #include <sys/types.h>
    #include <netinet/in.h>  
    #include <arpa/inet.h>
    #include <stdio.h>
     #include<stdlib.h>
    #define PORT 3800
    main()
    {
        int sock1,sock2, clength;
        FILE *ptr;
        char c;
        char ip[40];
        sock1 =  socket(AF_INET,SOCK_STREAM,0);
        struct sockaddr_in serv,cli;
        printf("Waiting for client\n");
        serv.sin_family = AF_INET;
        serv.sin_port = htons(PORT);
        serv.sin_addr.s_addr = htonl(INADDR_ANY);
        bind(sock1,(struct sockaddr *)&serv, sizeof(serv));
        listen(sock1,20);
        clength = sizeof(cli);
        sock2 = accept(sock1,(struct sockaddr *)&cli,&clength);
        printf("\n Client Connected\n");
        inet_ntop(AF_INET,(void *)&(cli.sin_addr),ip,clength);
        printf("\nClient IP :%s ",ip);
        inet_ntop(AF_INET,(void *)&(serv.sin_addr),ip,sizeof(serv));
        printf("\nServer IP :%s ",ip);
        while(1)
        {
            printf("\nEnter char : ");
            scanf("%c",&c);
            printf("%c",c);
            write(sock2,&c,1);
            if(c=='`')
                break;
        }
        close(sock2);
        close(sock1);
        return 0;
    }

  2. #2
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    38,799
    > sock2 = accept(sock1,(struct sockaddr *)&cli,&clength);
    Your while loop needs to be around this, and you need some kind of array to store up to 20 concurrent connections.

    You need to keep track of when each sock[i] (of the 20, not sock1 which is solely used to accept new connections) gets closed, so that a new one can be opened through accept.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  3. #3
    Registered User
    Join Date
    Nov 2008
    Posts
    216
    I have modified the code, but server still accepts connections even after its exceeds maximum limit..please help me.

    Code:
    #include <sys/socket.h>
    #include <sys/types.h>
    #include <netinet/in.h>  
    #include <arpa/inet.h>
    #include <stdio.h>
     #include<stdlib.h>
    #define PORT 3800
    #define MAXCLIENTS 20
    static int client_count = 0; /* Number of clients currently running */ 
    main()
    {
        int sock1,sock2, clength;
        FILE *ptr;
        char c;
        char ip[40];
        sock1 =  socket(AF_INET,SOCK_STREAM,0);
        struct sockaddr_in serv,cli;
        printf("Waiting for client\n");
        serv.sin_family = AF_INET;
        serv.sin_port = htons(PORT);
        serv.sin_addr.s_addr = htonl(INADDR_ANY);
        bind(sock1,(struct sockaddr *)&serv, sizeof(serv));
        listen(sock1,20);
        clength = sizeof(cli);
         /* Main server loop - accept and handle clients requests */
        for (;;) {
        while (client_count >= MAXCLIENTS) {pause();}
    
        if ((sock2 = accept(sock1,(struct sockaddr *)&cli,&clength) <0)
        {
        printf("\n Client Connected\n");
        inet_ntop(AF_INET,(void *)&(cli.sin_addr),ip,clength);
        printf("\nClient IP :%s ",ip);
        inet_ntop(AF_INET,(void *)&(serv.sin_addr),ip,sizeof(serv));
        printf("\nServer IP :%s ",ip);
        while(1)
        {
            printf("\nEnter char : ");
            scanf("%c",&c);
            printf("%c",c);
            write(sock2,&c,1);
            if(c=='`')
                break;
        }
        close(sock2);
        close(sock1);
        return 0;
    }
    }

  4. #4
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    38,799
    It never accepts more than one connection at once.

    It's so badly indented, that it doesn't even accept more than one connection (or even compile).
    Code:
    #include <sys/socket.h>
    #include <sys/types.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #include <stdio.h>
    #include<stdlib.h>
    #define PORT 3800
    #define MAXCLIENTS 20
    static int client_count = 0;    /* Number of clients currently running */
    main()
    {
      int sock1, sock2, clength;
      FILE *ptr;
      char c;
      char ip[40];
      sock1 = socket(AF_INET, SOCK_STREAM, 0);
      struct sockaddr_in serv, cli;
      printf("Waiting for client\n");
      serv.sin_family = AF_INET;
      serv.sin_port = htons(PORT);
      serv.sin_addr.s_addr = htonl(INADDR_ANY);
      bind(sock1, (struct sockaddr *) &serv, sizeof(serv));
      listen(sock1, 20);
      clength = sizeof(cli);
      /* Main server loop - accept and handle clients requests */
      for (;;) {
        while (client_count >= MAXCLIENTS) {
          pause();
        }
        if ((sock2 = accept(sock1, (struct sockaddr *) &cli, &clength) < 0)) {
          printf("\n Client Connected\n");
          inet_ntop(AF_INET, (void *) &(cli.sin_addr), ip, clength);
          printf("\nClient IP :%s ", ip);
          inet_ntop(AF_INET, (void *) &(serv.sin_addr), ip, sizeof(serv));
          printf("\nServer IP :%s ", ip);
          while (1) {
            printf("\nEnter char : ");
            scanf("%c", &c);
            printf("%c", c);
            write(sock2, &c, 1);
            if (c == '`')
              break;
          }
          close(sock2);
          close(sock1);
          return 0;
        }
      }
    }
    The two close calls and return are inside the first accept.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  5. #5
    Registered User
    Join Date
    Nov 2008
    Posts
    216
    are you saying to close those sockets inside first accept loop?

  6. #6
    Registered User
    Join Date
    Sep 2014
    Posts
    364
    The problem is, that there are a few functions that will block.
    accept will block the execution until a connection is received.
    This doesn't matter the first connection, but if you wait for a second connection, you can not receive messages from the first one, because accept blocks.
    Also, at line 38 is a scanf, this will also block until you hit return.
    Normaly, a server will fork to background and work autonomically.
    The server should automatically act if there a inbound message and eventually send out answers.

    Case 1 (single process):
    In your main-loop there should be:
    accept new connections as non-blocking!
    check non-blocking if a client has send anything!
    send messages non-blocking to clients!

    Case 2 (multi process):
    You can fork childs for every client.
    A child process can block, because it is only there for one client.
    For other clients, there are other childs.
    If a client quit, the child should also quit (rise signal SIGCHLD in main process).
    The main process should not block, because they should keep track of the childs.
    If a child quit, the main process receive the signal SIGCHLD.

    I don't know if this is a homework or a private project, so i will not provide code now.
    Search for function 'select', 'fcntl' and options 'MSG_DONTWAIT' and 'O_NONBLOCK'.
    Last edited by WoodSTokk; 05-05-2016 at 06:28 AM.
    Other have classes, we are class

  7. #7
    Registered User
    Join Date
    Nov 2008
    Posts
    216
    I have modified code as per your comments..please check if its fine now.

    Code:
    #include <sys/socket.h>
    #include <sys/types.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #include <stdio.h>
    #include<stdlib.h>
    #define PORT 3800
    #define MAXCLIENTS 20
    static int client_count = 0;    /* Number of clients currently running */
    main()
    {
      int sock1, sock2, clength;
      FILE *ptr;
      char c;
      char ip[40];
      sock1 = socket(AF_INET, SOCK_STREAM, 0);
      struct sockaddr_in serv, cli;
      printf("Waiting for client\n");
      serv.sin_family = AF_INET;
      serv.sin_port = htons(PORT);
      serv.sin_addr.s_addr = htonl(INADDR_ANY);
      bind(sock1, (struct sockaddr *) &serv, sizeof(serv));
      listen(sock1, 20);
      clength = sizeof(cli);
      /* Main server loop - accept and handle clients requests */
      for (;;) {
        while (client_count >= MAXCLIENTS) {
          pause();
        }
        /* accept incoming connections*/
        if ((sock2 = accept(sock1, (struct sockaddr *) &cli, &clength) < 0)) {
          printf("\n Client Connected\n");
          inet_ntop(AF_INET, (void *) &(cli.sin_addr), ip, clength);
          printf("\nClient IP :%s ", ip);
          inet_ntop(AF_INET, (void *) &(serv.sin_addr), ip, sizeof(serv));
          printf("\nServer IP :%s ", ip);
          //read from client
         if((n = read(sock2,response, BUF_SIZE-1)) < 0){
         perror("read");
         exit(1);
         }
         response[n] = '\0'; //NULL terminate string
    
         printf("Read from client: %s", response);
         //send response
        if(write(sock2, response, strlen(response)) < 0){
        perror("write");
        exit(1);
       
    
    }
          while (1) {
            printf("\nEnter char : ");
            scanf("%c", &c);
            printf("%c", c);
            write(sock2, &c, 1);
            if (c == '`')
              break;
          }
          close(sock2);
          close(sock1);
          return 0;
        }
      }
    }

  8. #8
    Registered User
    Join Date
    Nov 2008
    Posts
    216
    I have modified the code as per your comments..please check if its fine now?

    Code:
    #include <sys/socket.h>
    #include <sys/types.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #include <stdio.h>
    #include<stdlib.h>
    #define PORT 3800
    #define MAXCLIENTS 20
    static int client_count = 0;    /* Number of clients currently running */
    main()
    {
      int sock1, sock2, clength;
      FILE *ptr;
      char c;
      char ip[40];
      sock1 = socket(AF_INET, SOCK_STREAM, 0);
      struct sockaddr_in serv, cli;
      printf("Waiting for client\n");
      serv.sin_family = AF_INET;
      serv.sin_port = htons(PORT);
      serv.sin_addr.s_addr = htonl(INADDR_ANY);
      bind(sock1, (struct sockaddr *) &serv, sizeof(serv));
      listen(sock1, 20);
      clength = sizeof(cli);
      /* Main server loop - accept and handle clients requests */
      for (;;) {
        while (client_count >= MAXCLIENTS) {
          pause();
        }
        /* accept incoming connections*/
        while ((sock2 = accept(sock1, (struct sockaddr *) &cli, &clength) < 0)) {
          printf("\n Client Connected\n");
          inet_ntop(AF_INET, (void *) &(cli.sin_addr), ip, clength);
          printf("\nClient IP :%s ", ip);
          inet_ntop(AF_INET, (void *) &(serv.sin_addr), ip, sizeof(serv));
          printf("\nServer IP :%s ", ip);
          //read from client
         while((n = read(sock2,response, BUF_SIZE-1)) < 0){
         response[n] = '\0'; //NULL terminate string
         printf("Received From: %s:%d (%d): %s\n",  //LOGGING
                inet_ntoa(client_saddr_in.sin_addr), 
                ntohs(client_saddr_in.sin_port), 
                sock2, 
                response);
       
         //send response
        if(write(sock2, response, n) < 0){
        perror("write");
        exit(1);
       
    
    }
    }
     if( n < 0){
         perror("read");
       }
         printf("Client Closed: %s:%d (%d)\n",    //LOGGING
              inet_ntoa(client_saddr_in.sin_addr), 
              ntohs(client_saddr_in.sin_port), 
              sock2);
          close(sock2);
          close(sock1);
          //reset socket len in case
       saddr_len = sizeof(struct sockaddr_in); //length of address
    
     }
          return 0;
        }
      }
    }

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Client/server problem; server either stops receiving data or client stops sending
    By robot-ic in forum Networking/Device Communication
    Replies: 10
    Last Post: 02-16-2009, 11:45 AM
  2. How to let a client pc response to a query
    By DV64h in forum Windows Programming
    Replies: 2
    Last Post: 07-28-2006, 03:13 PM
  3. Run time error at client side query?
    By dp_76 in forum Networking/Device Communication
    Replies: 0
    Last Post: 07-01-2005, 03:02 AM
  4. Unicode vurses Non Unicode client server application with winsock2 query?
    By dp_76 in forum Networking/Device Communication
    Replies: 0
    Last Post: 05-16-2005, 07:26 AM
  5. Web Server Query
    By jinx in forum Tech Board
    Replies: 5
    Last Post: 05-11-2004, 06:14 AM