8
\$\begingroup\$

I have written some code to establish a client and server. I have managed to get a one way communication from client to server. I have added the code below. Can someone please have a look and see it is the right way to do it? If this is good enough, how can I get two communication to work now?

Client:

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

#define PORT 3490
#define MAXSIZE 1024

int main(int argc, char *argv[])
{
    struct sockaddr_in server_info;
    struct hostent *he;
    int socket_fd,num;
    char buffer[1024];

    char buff[1024];

    if (argc != 2) {
        fprintf(stderr, "Usage: client hostname\n");
        exit(1);
    }

    if ((he = gethostbyname(argv[1]))==NULL) {
        fprintf(stderr, "Cannot get host name\n");
        exit(1);
    }

    if ((socket_fd = socket(AF_INET, SOCK_STREAM, 0))== -1) {
        fprintf(stderr, "Socket Failure!!\n");
        exit(1);
    }

    memset(&server_info, 0, sizeof(server_info));
    server_info.sin_family = AF_INET;
    server_info.sin_port = htons(PORT);
    server_info.sin_addr = *((struct in_addr *)he->h_addr);
    if (connect(socket_fd, (struct sockaddr *)&server_info, sizeof(struct sockaddr))<0) {
        //fprintf(stderr, "Connection Failure\n");
        perror("connect");
        exit(1);
    }

    //buffer = "Hello World!! Lets have fun\n";
    //memset(buffer, 0 , sizeof(buffer));
    while(1) {
        fgets(buffer,MAXSIZE-1,stdin);
        if ((send(socket_fd,buffer, strlen(buffer),0))== -1) {
            fprintf(stderr, "Failure Sending Message\n");
            close(socket_fd);
            exit(1);
        }
        else {
            printf("Message being sent: %s\n",buffer);
        }
    }   

    /*if ((num = recv(socket_fd, buff, 1024,0))== -1) {
            //fprintf(stderr,"Error in receiving message!!\n");
            perror("recv");
            exit(1);
        }   
    //  num = recv(client_fd, buffer, sizeof(buffer),0);
    buff[num] = '\0';
    printf("Message received: %s\nNumber of bytes received: %d\n", buff,num);*/
    close(socket_fd);   

}

Server:

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

#define PORT 3490
#define BACKLOG 10

int main()
{
    struct sockaddr_in server;
    struct sockaddr_in dest;
    int status,socket_fd, client_fd,num;
    socklen_t size;

    char buffer[10241];
    char *buff;
//  memset(buffer,0,sizeof(buffer));
    int yes =1;



    if ((socket_fd = socket(AF_INET, SOCK_STREAM, 0))== -1) {
        fprintf(stderr, "Socket failure!!\n");
        exit(1);
    }

    if (setsockopt(socket_fd, SOL_SOCKET, SO_REUSEADDR, &yes, sizeof(int)) == -1) {
        perror("setsockopt");
        exit(1);
    }
    memset(&server, 0, sizeof(server));
    memset(&dest,0,sizeof(dest));
    server.sin_family = AF_INET;
    server.sin_port = htons(PORT);
    server.sin_addr.s_addr = INADDR_ANY; 
    if ((bind(socket_fd, (struct sockaddr *)&server, sizeof(struct sockaddr )))== -1)    { //sizeof(struct sockaddr) 
        fprintf(stderr, "Binding Failure\n");
        exit(1);
    }

    if ((listen(socket_fd, BACKLOG))== -1){
        fprintf(stderr, "Listening Failure\n");
        exit(1);
    }

    while(1) {
        size = sizeof(struct sockaddr_in);  

        if ((client_fd = accept(socket_fd, (struct sockaddr *)&dest, &size))==-1) {
            //fprintf(stderr,"Accept Failure\n");
            perror("accept");
            exit(1);
        }
        printf("Server got connection from client %s\n", inet_ntoa(dest.sin_addr));
        //buffer = "Hello World!! I am networking!!\n";

        while(1) {
        if ((num = recv(client_fd, buffer, 10240,0))== -1) {
            //fprintf(stderr,"Error in receiving message!!\n");
            perror("recv");
            exit(1);
        }   
        else if (num == 0) {
            printf("Connection closed\n");
            return 0;
        }
    //  num = recv(client_fd, buffer, sizeof(buffer),0);
        buffer[num] = '\0';
        printf("Message received: %s\n", buffer);
        }

    /*  buff = "I am communicating with the client!!\n";

        if ((send(client_fd,buff, strlen(buff),0))== -1) {
        fprintf(stderr, "Failure Sending Message\n");
        close(client_fd);
        exit(1);
    }
    else {
        printf("Message being sent: %s\nNumber of bytes sent: %d\n",buff, strlen(buff));
    }*/

        close(client_fd);   
        close(socket_fd);   
        //return 0;
    }
    //close(client_fd); 
    return 0;
}
\$\endgroup\$
3
  • \$\begingroup\$ what i meant to ask if my code was the right way to establish one way communication?? my more specific ques is how can i establsih 2-way (duplex communication)? \$\endgroup\$
    – ueg1990
    Jul 9, 2012 at 8:00
  • \$\begingroup\$ and thnx for the link!! \$\endgroup\$
    – ueg1990
    Jul 9, 2012 at 8:04
  • \$\begingroup\$ Checkout "A Sample GNU/Linux Application" chapter from "Advanced Linux Programming" book. In this chapter you can find good practices for two-way communication since a simple HTTP web server is implemented. \$\endgroup\$
    – user22912
    Mar 7, 2013 at 20:50

1 Answer 1

8
\$\begingroup\$

You can do a two way data transfer here. I have modified your code to show that. Now the server is echoing back to the client the same string which it has received. Now the client displays the same string, which it receives from the server. Pl. experiment with this.

client main loop

    while(1) {
        printf("Client: Enter Data for Server:\n");
        fgets(buffer,MAXSIZE-1,stdin);
        if ((send(socket_fd,buffer, strlen(buffer),0))== -1) {
                fprintf(stderr, "Failure Sending Message\n");
                close(socket_fd);
                exit(1);
        }
        else {
                printf("Client:Message being sent: %s\n",buffer);
                num = recv(socket_fd, buffer, sizeof(buffer),0);
                if ( num <= 0 )
                {
                        printf("Either Connection Closed or Error\n");
                        //Break from the While
                        break;
                }

                buff[num] = '\0';
                printf("Client:Message Received From Server -  %s\n",buffer);
           }
    }
    close(socket_fd);

}//End of main

Server main loop

    while(1) {

        size = sizeof(struct sockaddr_in);

        if ((client_fd = accept(socket_fd, (struct sockaddr *)&dest, &size))==-1 ) {
            perror("accept");
            exit(1);
        }
        printf("Server got connection from client %s\n", inet_ntoa(dest.sin_addr));

        while(1) {

                if ((num = recv(client_fd, buffer, 1024,0))== -1) {
                        perror("recv");
                        exit(1);
                }
                else if (num == 0) {
                        printf("Connection closed\n");
                        //So I can now wait for another client
                        break;
                }
                buffer[num] = '\0';
                printf("Server:Msg Received %s\n", buffer);
                if ((send(client_fd,buffer, strlen(buffer),0))== -1) 
                {
                     fprintf(stderr, "Failure Sending Message\n");
                     close(client_fd);
                     break;
                }

                printf("Server:Msg being sent: %s\nNumber of bytes sent: %d\n",b
                uffer, strlen(buffer));

        } //End of Inner While...
        //Close Connection Socket
        close(client_fd);
    } //Outer While

    close(socket_fd);
    return 0;
} //End of main
\$\endgroup\$
9
  • \$\begingroup\$ thank you. i will test it out!! so this 2way communication is sufficient to be considered as chat messaging btw two machines??? \$\endgroup\$
    – ueg1990
    Jul 9, 2012 at 17:04
  • \$\begingroup\$ Since you are using TCP, this is having some limitations. TCP is a byte oriented protocol. So ideally you cannot expect to get all the data in a single "recv". You need to run recv in loop even to grab all the data in a line, if the line is arbitrarily large. Anyway this code should work for normal user inputs, which may not be that large. I would suggest, you may also try implementing this using UDP.Also pl. read from the link , faqs.org/faqs/unix-faq/socket to learn more about sockets or from any good book like "Network Programming" byStevens.Pl. let me know if the code worked. \$\endgroup\$ Jul 9, 2012 at 17:13
  • \$\begingroup\$ nope, it is not working!!client is able to send message which server receives, but after that nothing happens!! \$\endgroup\$
    – ueg1990
    Jul 10, 2012 at 4:56
  • \$\begingroup\$ I missed the send function in the server side , which I have updated.The character array buffer is populated by the recv function and the same array "buffer" is used to send data.I hope you are not using the "buff" as was there in your orginal code. \$\endgroup\$ Jul 10, 2012 at 6:04
  • \$\begingroup\$ hey, i made a mistake!! ur modifications worked!! but now i want to implement a continuous 2 way communication whereby a server can also send messages to the client, can u help me how? i cannot find much on google also, how do i check in recv function if all the data has been actually received?? thnx again for ur help!! \$\endgroup\$
    – ueg1990
    Jul 10, 2012 at 6:05

Not the answer you're looking for? Browse other questions tagged or ask your own question.