Re: C code to find interface IP address
Hello and thanks for answering.
By doing the following, according to your code for the broadcast
addresses, I did what I wanted.
(I also had to declare srv_addr as struct in_addr)
if (ioctl(sd,SIOCGIFFLAGS,devptr) < 0)
{
fprintf(stderr,"Error: Unable to get device interface
flags.\n");
perror("ioctl");
close(sd);
return -1;
}
else
{
printf("Interface name: %s", devptr->ifr_name);
printf("\n");
srv_addr.s_addr
= ((struct sockaddr_in
*)&devptr->ifr_addr)->sin_addr.s_addr;
printf("Interface long int addr: %d", srv_addr.s_addr);
printf("\n");
printf("Interface IP addr: %s", inet_ntoa(srv_addr));
printf("\n");
}
I want to "lock" the executable with the machine IP.
many many thanks,
Mihalis.
On Wed, 19 Mar 2003, Bob Proulx wrote:
> Date: Wed, 19 Mar 2003 11:58:51 -0700
> From: Bob Proulx <bob@proulx.com>
> To: debian-user@lists.debian.org
> Subject: Re: C code to find interface IP address
> Resent-Date: Wed, 19 Mar 2003 13:15:49 -0600 (CST)
> Resent-From: debian-user@lists.debian.org
>
> mtsouk@freemail.gr wrote:
> > I am looking for C code in order to find the IP address of each ethX
> > interface in a Linux machine.
>
> Curious as to why you need that information. Very few programs ever
> need to tread there.
>
> Note that network devices can be configured or unconfigured at any
> time. Which means you need to check ever so often to see if the list
> has changed. Be ready for a device to drop out at any time. People
> routinely up and down interfaces at their own whims.
>
> Here are some snippets which might help you. This is from one of my
> own programs. It is getting a list of broadcast addresses. Putting
> in the error checking is left as an exercise to the reader. I
> probably broken it splitting it out of its working environment. YMMV.
>
> Bob Proulx
>
> #include <sys/types.h>
> #include <sys/socket.h>
> #include <sys/ioctl.h>
> #include <net/if.h>
> #include <netinet/in.h>
> #include <netdb.h>
> #include <stdio.h>
> #include <stdlib.h>
> #include <unistd.h>
> #include <fcntl.h>
> #include <ctype.h>
>
> enum { ADDRS_SIZE = 8 }; /* Plenty of initial broadcast addresses. */
>
> static struct in_addr bcast_arr[ADDRS_SIZE];
> static int numbaddrs; /* The actual number. */
>
> /******************************************************************/
> /*
> * Get the interface device list, walk through it and deduce those
> * interfaces which can broadcast.
> */
> static int get_device_info(void)
> {
> int i, sd, numdevs;
> struct ifconf ifc_conf;
> char ifc_conf_buf[BUFSIZ]; /* 1024/32 == space for 32 interfaces */
> struct ifreq *devptr;
> int ifc_conf_buf_size;
>
> numbaddrs = 0;
>
> /*
> * Open a socket, any type will do so we choose UDP, and ask it with
> * an ioctl call what devices are behind it.
> */
> if ((sd = socket(AF_INET,SOCK_DGRAM,0)) < 0)
> {
> fprintf(stderr,"Error: Unable to create socket\n");
> perror("socket");
> return -1;
> }
>
> /*
> * Fill the buffer with our static buffer, probably big enough, and get
> * the interface configuration.
> */
> ifc_conf_buf_size = sizeof ifc_conf_buf;
> ifc_conf.ifc_len = ifc_conf_buf_size;
> ifc_conf.ifc_buf = ifc_conf_buf;
> if (ioctl(sd,SIOCGIFCONF,&ifc_conf) < 0)
> {
> fprintf(stderr,"Error: Unable to get network interface conf\n");
> perror("ioctl");
> close(sd);
> return -1;
> }
> if ((sizeof ifc_conf_buf - ifc_conf.ifc_len) <= sizeof (struct ifreq))
> fprintf(stderr,"Info: More interfaces then we anticipated.\n");
>
> /*
> * Excess space should be larger than one ifreq or we need more. If
> * the buffer was not big enough then we need to malloc a larger space
> * and try again. There is no number of retries. We either get them
> * all or we run out of memory.
> */
> while ((sizeof ifc_conf_buf - ifc_conf.ifc_len) <= sizeof (struct ifreq))
> {
> if (ifc_conf_buf_size != sizeof ifc_conf_buf)
> free(ifc_conf.ifc_buf); /* We allocated it last time around. */
> ifc_conf_buf_size *= 2;
> ifc_conf.ifc_len = ifc_conf_buf_size;
> if ((ifc_conf.ifc_buf = malloc(ifc_conf_buf_size)) == 0)
> {
> fprintf(stderr,"Error: Out of memory allocating interfaces.\n");
> close(sd);
> return -1;
> }
> if (ioctl(sd,SIOCGIFCONF,&ifc_conf) < 0)
> {
> fprintf(stderr,"Error: Unable to get network interface conf\n");
> perror("ioctl");
> close(sd);
> return -1;
> }
> }
>
> /*
> * An array of devices were returned. Which ones are up right now and
> * have broadcast capability?
> */
> numdevs = ifc_conf.ifc_len / sizeof (struct ifreq);
> for (i = 0; i < numdevs; i++)
> {
> /* devptr points into an array of ifreq structs. */
> devptr = &ifc_conf.ifc_req[i];
>
> if (devptr->ifr_addr.sa_family != AF_INET)
> continue;
>
> if (ioctl(sd,SIOCGIFFLAGS,devptr) < 0)
> {
> fprintf(stderr,"Error: Unable to get device interface flags.\n");
> perror("ioctl");
> close(sd);
> return -1;
> }
>
> if ((devptr->ifr_flags & IFF_LOOPBACK) != 0)
> continue;
>
> if ((devptr->ifr_flags & IFF_UP) == 0)
> continue;
>
> if ((devptr->ifr_flags & IFF_BROADCAST) == 0)
> continue;
>
> /* Get the broadcast address. */
> if (ioctl(sd,SIOCGIFBRDADDR,devptr) < 0)
> {
> fprintf(stderr,"%s: Error: Unable to get broadcast address.\n",
> devptr->ifr_name);
> perror("ioctl");
> close(sd);
> return -1;
> }
> bcast_arr[numbaddrs].s_addr
> = ((struct sockaddr_in *)&devptr->ifr_broadaddr)->sin_addr.s_addr;
>
> /* FIXME: should dynamically allocate more space. */
> if (++numbaddrs > ADDRS_SIZE)
> {
> fprintf(stderr,"Warning: More broadcast devs than anticipated.\n");
> break;
> }
> }
>
> close(sd);
>
> return 0;
> }
-----
:wq
Reply to: