开发者

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.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜