Thread: same file descriptors of all client connections. How to differentiate clients ?

  1. #1
    Registered User
    Join Date
    Feb 2011
    Location
    gandhinagar
    Posts
    7

    Post same file descriptors of all client connections. How to differentiate clients ?

    I want to send diff client diff reply from other child process of server
    For that I use fd of client.
    Every forked child process of server replies to particular client (child created on that client connection) even if fd is same.

    But different processes(other children of server i.e. exec) couldn't identify that client with same fd in used in forked child.

    How can I differentiate client on other processes ??

    Code:
    /* server process */ 
    #include <ctype.h> 
    #include <sys/types.h> 
    #include <sys/socket.h> 
    #include<stdlib.h>
    #include<stdio.h>
    #include <netinet/in.h> 
    #include <signal.h> 
    #define SIZE sizeof(struct sockaddr_in) 
    void catcher(int sig); 
    int newsockfd; 
    int main(void) 
    { 
    	int sockfd; 
    	char c;
    	struct sockaddr_in server = {AF_INET, 7000, INADDR_ANY}; 
    	static struct sigaction act; 
    	act.sa_handler = catcher; 
    	sigfillset(&(act.sa_mask)); 
    	sigaction(SIGPIPE, &act, NULL); 
    	/* set up the transport end point */ 
    	if ( (sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) 
    	{ 
    		perror("socket call failed"); 
    		exit(1); 
    	} 
    	/* bind an address to the end point */ 
    	if ( bind(sockfd, (struct sockaddr *)&server, SIZE) == -1) 
    	{ 
    		perror("bind call failed"); 
    		exit(1); 
    	}
    	/* start listening for incoming connections */ 
    	if ( listen(sockfd, 5) == -1 ) 
    	{ 
    		perror("listen call failed"); 
    		exit(1) ; 
    	} 
    	for (;;) 
    	{ 
    		/* accept a connection */ 
    		if ( (newsockfd = accept(sockfd, NULL, NULL)) == -1) 
    		{ 
    			perror("accept call failed"); 
    			continue; 
    		} 
    		printf("New connection. File descriptor fd is %d\n",newsockfd);
    		/* spawn a child to deal with the connection */
    		if ( fork() == 0) 
    		{ 
    			while (recv(newsockfd, &c, 1, 0) > 0) 
    			{ 
    				c = toupper(c); 
    				send(newsockfd, &c,1, 0); 
    			} 
    			/* when client is no longer sending information the socket can be closed and the child process terminated */ 
    			close(newsockfd); 
    			exit (0); 
    		} 
    		/* parent doesn't need the newsockfd */ 
    		close(newsockfd); 
    	} 
    } 
    void catcher(int sig) 
    { 
    	close(newsockfd); 
    	exit (0); 
    }
    Code:
    /* client process */ 
    #include <ctype.h> 
    #include <sys/types.h> 
    #include<stdlib.h>
    #include<stdio.h>
    #include <sys/socket.h> 
    #include <netinet/in.h> 
    #define SIZE sizeof(struct sockaddr_in) 
    int main(void) 
    { 
    	int sockfd; 
    	char c, rc; 
    	struct sockaddr_in server = {AF_INET, 7000}; 
    	/* convert and store the server's IP address */ 
    	server.sin_addr.s_addr = inet_addr("127.0.0.1"); 
    	/* set up the transport end point */ 
    	if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) 
    	{ 
    		perror("socket call failed"); 
    		exit(1); 
    	} 
    	/* connect the socket to the server's address */ 
    	if ( connect (sockfd, (struct sockaddr *)&server, SIZE) == -1) 
    	{ 
    		perror("connect call failed"); 
    		exit(1); 
    	} 
    	/* send and receive information with the server */ 
    	for(rc = '\n';;) 
    	{ 
    		if (rc == '\n') 
    			printf("Input a lower case character\n"); 
    		c = getchar(); 
    		send(sockfd, &c, 1, 0); 
    		if (recv(sockfd, &rc, 1, 0) >0) 
    			printf("%c", rc);  
    		else 
    		{
    			printf("server has died\n");
    			close(sockfd);
    			exit(1); 
    		} 
    	} 
    }

  2. #2
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    I'm not totally clear on what you want. It sounds to me like you want something like the following:
    1. Request A comes from client A in to server
    2. Server forks child 1 to handle request A via accept()
    3. Request B comes from client B into server
    4. Server forks child 2 to handle request B via accept()
    5. Child 1 can talk to client A or B.


    Please clarify what exactly you want and why you want to do it or what you are trying to achieve.

    A little note: File descriptors are per-process. Thus, for example, fd 7 in child 1 probably refers to a different file descriptor/socket than fd 7 in child 2. When you fork, the child inherits all the file descriptors of the parent, but you need to close those to be safe, to avoid accidentally using another processes resources. Only use the new socket provided by exec in the children. If two processes could use each other's file descriptors at will, it would be a big security hole. Imagine this on a web server. Somebody could send malicious data to the socket you're using to browse a web page, and send you a virus.

  3. #3
    Registered User
    Join Date
    Feb 2011
    Location
    gandhinagar
    Posts
    7
    Quote Originally Posted by anduril462 View Post
    I'm not totally clear on what you want. It sounds to me like you want something like the following:
    1. Request A comes from client A in to server
    2. Server forks child 1 to handle request A via accept()
    3. Request B comes from client B into server
    4. Server forks child 2 to handle request B via accept()
    5. Child 1 can talk to client A or B.


    Please clarify what exactly you want and why you want to do it or what you are trying to achieve.

    A little note: File descriptors are per-process. Thus, for example, fd 7 in child 1 probably refers to a different file descriptor/socket than fd 7 in child 2. When you fork, the child inherits all the file descriptors of the parent, but you need to close those to be safe, to avoid accidentally using another processes resources. Only use the new socket provided by exec in the children. If two processes could use each other's file descriptors at will, it would be a big security hole. Imagine this on a web server. Somebody could send malicious data to the socket you're using to browse a web page, and send you a virus.
    I want child 3 to be able to send msg to some clients (not all connected).

    server creates child 3 according to client request.

  4. #4
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    Then you need to set up a whole other mechanism for this. It will require some sort of IPC to accomplish this. Sharing a socket between multiple processes is bad. You'll have to have each client open a separate socket to child 3, different from the one it used for the parent server, or child servers 1 or 2. Make sure they're non-blocking, and use select() to determine which sockets are ready for reading/writing.

    Here's some info on IPCs in Linux, and here's a good network programming guide.

  5. #5
    Registered User
    Join Date
    Feb 2011
    Location
    gandhinagar
    Posts
    7
    Quote Originally Posted by anduril462 View Post
    Then you need to set up a whole other mechanism for this. It will require some sort of IPC to accomplish this. Sharing a socket between multiple processes is bad. You'll have to have each client open a separate socket to child 3, different from the one it used for the parent server, or child servers 1 or 2. Make sure they're non-blocking, and use select() to determine which sockets are ready for reading/writing.

    Here's some info on IPCs in Linux, and here's a good network programming guide.
    what if child 3 somehow get pointer to fd returned by accept call ??
    will child 3 be able to send msg to client ??

  6. #6
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    Nope. They have separate memory spaces. Address 0x1234 in child1 refers to a completely different piece of memory/data in child 2 or 3. Seriously...this isn't a trick question with some super simple answer.

  7. #7
    Registered User
    Join Date
    Feb 2011
    Location
    gandhinagar
    Posts
    7
    Quote Originally Posted by anduril462 View Post
    Nope. They have separate memory spaces. Address 0x1234 in child1 refers to a completely different piece of memory/data in child 2 or 3. Seriously...this isn't a trick question with some super simple answer.
    I forgot to specify that I am using shared memory to share array of fd among 2 processes.

    Now tell me if child 3 will be able to send msg to client ??

    Here is the code

    https://github.com/smitpatel24/SChannel

    Note : channel is child 3
    Last edited by smitpatel24; 05-07-2011 at 09:05 AM.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 12
    Last Post: 02-10-2009, 02:14 PM
  2. Testing maximum client connections
    By abachler in forum Networking/Device Communication
    Replies: 6
    Last Post: 05-02-2008, 08:31 AM
  3. Numering of file descriptors
    By Massive in forum C Programming
    Replies: 6
    Last Post: 06-24-2003, 06:49 AM
  4. File descriptors and buffers.
    By ingofrey in forum C Programming
    Replies: 2
    Last Post: 10-17-2002, 09:40 AM
  5. Multiple Client Connections
    By (TNT) in forum Windows Programming
    Replies: 1
    Last Post: 04-06-2002, 11:04 PM

Tags for this Thread