Link to home
Start Free TrialLog in
Avatar of perlperl
perlperl

asked on

socket and server ip address

I am creating and binding a socket on my server with the following optons on a clustered environment

	struct addrinfo hints, *start, *results;
	bzero(&hints, sizeof(struct addrinfo));
	hints.ai_flags = AI_PASSIVE; // Use address return by getaddrinfo in bind() return addrinfo will have INADDR_ANY set to IPv4 adress and INADDR6_ANY_INIT for IPv6 address
	hints.ai_family = AF_UNSPEC;  // return both the family AF_INET and AF_INET6 address structures
	hints.ai_socktype = SOCK_STREAM;
	hints.ai_protocol = IPPROTO_TCP;

getaddrinfo(NULL, "4455", &hints, &results);
int fd = socket(results->ai_family, results->ai_socktype, results->ai_protocol);
bind(fd, results->ai_addr, results->ai_addrlen);

Open in new window


The above server is running in background and continously listening for incoming packets.

Once I accept a new request I want to make sure that the client's request came on specific server's IP address only.

I tried two options to get server's IP:

METHOD 1  ---> This prints  Addres = 0.0.0.0
// I believe this is because I have AI_PASSIVE set. 
	struct sockaddr_storage addr;
	len = sizeof (struct sockaddr_storage);
	 getsockname(fd, (struct sockaddr*)&addr, &len );
	struct sockaddr_in *sin = (struct sockaddr_in *)&addr;
	char str[INET_ADDRSTRLEN];
	inet_ntop(AF_INET, &sin->sin_addr, str, INET_ADDRSTRLEN);
	DBG0(" Addres = " << str);    

METHOD 2:  --> This prints  Adress =127.0.0.1
In this method, instead of using "fd", I am using the socket descriptor from "accept" call

Open in new window


0.0.0.0 and 127.0.01 does not help me as client may have initiated a request againt server's ip address say 10.10.20.20
How do I get the specific IP address from either "fd" or "file descriptor from returned accept call"  so that I can make a check that client sent request on this IP only.
Avatar of jkr
jkr
Flag of Germany image

'getsockname()' returns your local connection information. If you want the remote info, use 'getpeername()' (https://www.linux.com/learn/docs/man/3178-getpeername2) instead:

	struct sockaddr_storage addr;
	len = sizeof (struct sockaddr_storage);
	 getpeername(fd, (struct sockaddr*)&addr, &len ); // <---- !
	struct sockaddr_in *sin = (struct sockaddr_in *)&addr;
	char str[INET_ADDRSTRLEN];
	inet_ntop(AF_INET, &sin->sin_addr, str, INET_ADDRSTRLEN);
	DBG0(" Addres = " << str);    

Open in new window

ASKER CERTIFIED SOLUTION
Avatar of perlperl
perlperl

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial