Extract IP from connection that listen and accept in socket programming in Linux in c
In the following code I would like to extract the IP address of the connected client after accepting an incoming connection. What should I do after the accept()
to achieve it?
int sockfd, newsockfd, portno, clilen;
portno = 8090;
clilen = 0;
pthread_t serverIn;
struct sockaddr_in serv_addr, cli_addr;
sockfd = socket(AF_INET, SOCK_STREAM, 0);
if (sockfd < 0)
{
perror("ERROR opening socket");
}
bzero((char *) & serv_addr, sizeof (serv_addr));
serv_addr.sin_family = AF_INET;
serv_addr.sin_port = htons(portno);
s开发者_Go百科erv_addr.sin_addr.s_addr = INADDR_ANY;
if (bind(sockfd, (struct sockaddr *) & serv_addr, sizeof (serv_addr)) < 0)
{
perror("ERROR on binding");
}
listen(sockfd, 5);
clilen = sizeof (cli_addr);
newsockfd = accept(sockfd, (struct sockaddr *) & cli_addr, &clilen);
Your cli_addr
already contains the IP address and port of the connected client after accept()
returns successfully, in the same format as your serv_addr
variable. Use inet_ntop
to convert IP to a string.
getpeername()
See the helpful description of how to use it over at the indispensable Beej's Guide to Network Programming.
You can follow this example :
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <stdio.h>
{
int s;
struct sockaddr_in peer;
int peer_len;
.
.
.
/* We must put the length in a variable. */
peer_len = sizeof(peer);
/* Ask getpeername to fill in peer's socket address. */
if (getpeername(s, &peer, &peer_len) == -1) {
perror("getpeername() failed");
return -1;
}
/* Print it. The IP address is often zero because */
/* sockets are seldom bound to a specific local */
/* interface. */
printf("Peer's IP address is: %s\n", inet_ntoa(peer.sin_addr));
printf("Peer's port is: %d\n", (int) ntohs(peer.sin_port));
.
.
.
}
I think getpeername()
is not needed - the client address is already filled into cli_addr
by the accept()
call.
You only need to use inet_ntop()
, getnameinfo()
, or gethostbyaddr()
to print or get more information.
The API is described in the manual pages. You can either browse them from the console, starting with man socket
and follow references to man getpeername
or use Konqueror, which renders it nicely with links, if you ask for #socket
address. In my case on Kubuntu it was necessary to install manpages-dev
package.
精彩评论