Get Local IP using glib (eth0,eth1)

classic Classic list List threaded Threaded
14 messages Options
Reply | Threaded
Open this post in threaded view
|

Get Local IP using glib (eth0,eth1)

dtouzeau
  Hi

I'm trying to write a function to read the local IP eth0/eth1... using
glibc library...
I found only examples that found the 127.0.0.1 IP but not the real IP :

http://community.freepascal.org:10000/bboards/message?message_id=233776&forum_id=24083
http://lists.freepascal.org/lists/fpc-pascal/2002-March/002932.html

Is someone could help me to find the solution...
Currently i use regex on ifconfig that is a hack!

best regards

--


 

_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

RE: Get Local IP using glib (eth0,eth1)

Jeff Pohlmeyer
> I'm trying to write a function to read the local IP eth0/eth1
> using glibc library...


program ip_addr;
{$MODE OBJFPC}

uses libc;
const
  IP_NAMESIZE = 16;
type
  ipstr = array[0..IP_NAMESIZE-1] of char;


function GetIPAddressOfInterface( if_name:ansistring):ansistring;
var
  ifr : ifreq;
  tmp:ipstr;
  sock : longint;
  p:pChar;

begin
  Result:='0.0.0.0';
  strncpy( ifr.ifr_ifrn.ifrn_name, pChar(if_name), IF_NAMESIZE-1 );
  ifr.ifr_ifru.ifru_addr.sa_family := AF_INET;
  FillChar(tmp[0], IP_NAMESIZE, #0);
  sock := socket(AF_INET, SOCK_DGRAM, IPPROTO_IP);
  if ( sock >= 0 ) then begin
    if ( ioctl( sock, SIOCGIFADDR, @ifr ) >= 0 ) then begin
      p:=inet_ntoa( ifr.ifr_ifru.ifru_addr.sin_addr );
      if ( p <> nil ) then strncpy(tmp, p, IP_NAMESIZE-1);
      if ( tmp[0] <> #0 ) then Result :=  tmp;
    end;
    libc.__close(sock);
  end;
end;




begin
  if (ParamCount=1)
  then WriteLn(GetIPAddressOfInterface(ParamStr(1)))
  else WriteLn('Usage:', ParamStr(0), '<interface-name>')
end.



 - Jeff
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

RE: Get Local IP using glib (eth0,eth1)

Jeff Pohlmeyer
In reply to this post by dtouzeau
> > function to read the local IP eth0/eth1 using glibc library.

> program ip_addr;
>  ...
> end.



Please ignore my last post -
This one is a little cleaner...

program ip_addr;
{$MODE OBJFPC}

uses libc;

function GetIPAddressOfInterface( if_name:ansistring):ansistring;
var
  ifr : ifreq;
  sock : longint;
  p:pChar;

begin
  Result:='0.0.0.0';
  strncpy( ifr.ifr_ifrn.ifrn_name, pChar(if_name), IF_NAMESIZE-1 );
  ifr.ifr_ifru.ifru_addr.sa_family := AF_INET;
  sock := socket(AF_INET, SOCK_DGRAM, IPPROTO_IP);
  if ( sock >= 0 ) then begin
    if ( ioctl( sock, SIOCGIFADDR, @ifr ) >= 0 ) then begin
      p:=inet_ntoa( ifr.ifr_ifru.ifru_addr.sin_addr );
      if ( p <> nil ) then Result :=  p;
    end;
    libc.__close(sock);
  end;
end;



var
  i:LongInt;
begin
  if (ParamCount>0)
  then for i:=1 to ParamCount
       do WriteLn(GetIPAddressOfInterface(ParamStr(i)))
  else WriteLn('Usage:', ParamStr(0), '<interface-name>')
end.
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

Micha Nelissen
Jeff Pohlmeyer wrote:
>> > function to read the local IP eth0/eth1 using glibc library.
>
> This one is a little cleaner...
>
> program ip_addr;
> {$MODE OBJFPC}
>
> uses libc;

It doesn't seem like you're using libc specific functions ? You can also
write a fpc 'native' one using fpsocket and fpioctl in baseunix/unix, I
think.

Micha
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

dtouzeau
In reply to this post by Jeff Pohlmeyer
Many Thanks Jeff and Micha.

This function works perfectly without need to regex ifconfig... And i
use glibc
I develop only on linux system.

Great respects...
Just another question... (this because i came from Windows OS) how can i
list wich interface loaded without need to parse /etc/networks/...?
(wlan0,wlan1,eth0,eth1...)

Best regards...


Jeff Pohlmeyer a écrit :

>> I'm trying to write a function to read the local IP eth0/eth1
>> using glibc library...
>
>
> program ip_addr;
> {$MODE OBJFPC}
>
> uses libc;
> const
>  IP_NAMESIZE = 16;
> type
>  ipstr = array[0..IP_NAMESIZE-1] of char;
>
>
> function GetIPAddressOfInterface( if_name:ansistring):ansistring;
> var
>  ifr : ifreq;
>  tmp:ipstr;
>  sock : longint;
>  p:pChar;
>
> begin
>  Result:='0.0.0.0';
>  strncpy( ifr.ifr_ifrn.ifrn_name, pChar(if_name), IF_NAMESIZE-1 );
>  ifr.ifr_ifru.ifru_addr.sa_family := AF_INET;
>  FillChar(tmp[0], IP_NAMESIZE, #0);
>  sock := socket(AF_INET, SOCK_DGRAM, IPPROTO_IP);
>  if ( sock >= 0 ) then begin
>    if ( ioctl( sock, SIOCGIFADDR, @ifr ) >= 0 ) then begin
>      p:=inet_ntoa( ifr.ifr_ifru.ifru_addr.sin_addr );
>      if ( p <> nil ) then strncpy(tmp, p, IP_NAMESIZE-1);
>      if ( tmp[0] <> #0 ) then Result :=  tmp;
>    end;
>    libc.__close(sock);
>  end;
> end;
>
>
>
>
> begin
>  if (ParamCount=1)
>  then WriteLn(GetIPAddressOfInterface(ParamStr(1)))
>  else WriteLn('Usage:', ParamStr(0), '<interface-name>')
> end.
>
>
>
> - Jeff
> _______________________________________________
> fpc-pascal maillist  -  [hidden email]
> http://lists.freepascal.org/mailman/listinfo/fpc-pascal
>

--

David Touzeau -------------------------- Linux Ubuntu Dapper 6.0.6
FreePascal-Lazarus,perl,delphi,php icq:160018849

_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

Marco van de Voort
 
> This function works perfectly without need to regex ifconfig... And i
> use glibc
> I develop only on linux system.

Note that it is linux/x86 only. No 64-bit, or other platforms.
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

dtouzeau
OK i understand that i using i386 no 64 bits

Marco van de Voort a écrit :

>  
>  
>> This function works perfectly without need to regex ifconfig... And i
>> use glibc
>> I develop only on linux system.
>>    
>
> Note that it is linux/x86 only. No 64-bit, or other platforms.
>
>  

--

David Touzeau -------------------------- Linux Ubuntu Dapper 6.0.6
FreePascal-Lazarus,perl,delphi,php icq:160018849

_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

RE: Get Local IP using glib (eth0,eth1)

Jeff Pohlmeyer
In reply to this post by dtouzeau
> how can i list wich interface loaded without
> need to parse /etc/networks/...?



I would parse /proc/net/dev instead....


program ifnames;
var
  s:shortstring;
  f:text;
  p:LongInt;
begin
  assign(f,'/proc/net/dev');
  reset(f);
  while not eof(f) do begin
    readln(f,s);
    p:=pos(':',s);
    if ( p > 0 ) then begin
      delete(s, p, 255);
      while ( s <> '' ) and (s[1]=#32) do delete(s,1,1);
      writeln(s);
    end;
  end;
  close(f);
end.
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

Marco van de Voort
> I would parse /proc/net/dev instead....

Better, but still Linux only. For a good solution, a resolver unit that
accesses libc should be written that is portable (unlike the libc unit)

_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

dtouzeau
Many Thanks for this way jeff...
/proc/net/dev is more compatible
Impressed it
for your information.
My program will run only on linux system...


Marco van de Voort a écrit :

>> I would parse /proc/net/dev instead....
>>    
>
> Better, but still Linux only. For a good solution, a resolver unit that
> accesses libc should be written that is portable (unlike the libc unit)
>
> _______________________________________________
> fpc-pascal maillist  -  [hidden email]
> http://lists.freepascal.org/mailman/listinfo/fpc-pascal
>
>  

--

David Touzeau -------------------------- Linux Ubuntu Dapper 6.0.6
FreePascal-Lazarus,perl,delphi,php icq:160018849

_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

RE: Get Local IP using glib (eth0,eth1)

Jeff Pohlmeyer
In reply to this post by dtouzeau
> Better, but still Linux only. For a good solution,
> a resolver unit that accesses libc should be
> written that is portable (unlike the libc unit)


If I understood correctly, the OP had two questions:

1. Retrieve a list of interface names on a *linux* system.
2. Return the IP address for a given *linux* interface name.


And the only "good" solution is a portable resolver unit?

How will you resolve "eth0" on Win32 or BSD ?

 -Jeff
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

Graeme Geldenhuys-2
I have these two functions in my .bashrc file.  You only need to run
"ii" for the cool output.  Now back to the question -  If it is for
linux only, why not just use the /sbin/ifconfig output.  After all, it
is accurate and seem much easier than all those libc/library methods.
I pull the IPs and Interfaces available from the /sbin/ifconfig output
and works just fine.  If it was needed on windows, I am sure you could
to the same thing with the 'ipconfig' output.

My 2c worth!  :-)


Regards,
  - Graeme -



------------ .bashrc ---------------------
function my_ip() # get IP adresses
{
    MY_IP=$(/sbin/ifconfig eth0 | awk '/inet/ { print $2 } ' | sed -e s/addr://)
    MY_ISP=$(/sbin/ifconfig ppp0 | awk '/P-t-P/ { print $3 } ' | sed
-e s/P-t-P://)
}

function ii()   # get current host related info
{
    echo -e "\nYou are logged on ${RED}$HOST"
    echo -e "\nAdditionnal information:$NC " ; uname -a
    echo -e "\n${RED}Users logged on:$NC " ; w -h
    echo -e "\n${RED}Current date :$NC " ; date
    echo -e "\n${RED}Machine stats :$NC " ; uptime
    echo -e "\n${RED}Memory stats :$NC " ; free
    my_ip 2>&- ;
    echo -e "\n${RED}Local IP Address :$NC" ; echo ${MY_IP:-"Not connected"}
    echo -e "\n${RED}ISP Address :$NC" ; echo ${MY_ISP:-"Not connected"}
    echo
}
---------------------------------

On 06/10/06, Jeff Pohlmeyer <[hidden email]> wrote:

> > Better, but still Linux only. For a good solution,
> > a resolver unit that accesses libc should be
> > written that is portable (unlike the libc unit)
>
>
> If I understood correctly, the OP had two questions:
>
> 1. Retrieve a list of interface names on a *linux* system.
> 2. Return the IP address for a given *linux* interface name.
>
>
> And the only "good" solution is a portable resolver unit?
>
> How will you resolve "eth0" on Win32 or BSD ?
>
>  -Jeff


--
There's no place like 127.0.0.1
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

Marco van de Voort
In reply to this post by Jeff Pohlmeyer
> > Better, but still Linux only. For a good solution,
> > a resolver unit that accesses libc should be
> > written that is portable (unlike the libc unit)
>
> If I understood correctly, the OP had two questions:
>
> 1. Retrieve a list of interface names on a *linux* system.
> 2. Return the IP address for a given *linux* interface name.

I don't understand that last one. _WHY_ would you want to enumerate and then
still use hardcoded "eth0" What if eth0 is my internal and eth1 my external
interface? The only meaning of the name is order of detection.
 
> And the only "good" solution is a portable resolver unit?
>
> How will you resolve "eth0" on Win32 or BSD ?

Usually you enumerate the interfaces list, till you find the interface with
the "default" (ANY) route, so you have the default gateway, regardless of
name. That is usually the interface you interested in.

IOW names say nothing, routes and masks do.
_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal
Reply | Threaded
Open this post in threaded view
|

Re: RE: Get Local IP using glib (eth0,eth1)

dtouzeau
In reply to this post by Graeme Geldenhuys-2
Many thanks to the community

To reply to Graeme :
why not just use the /sbin/ifconfig output ?
Simply to be more dev compliance... using an external program is slower
and sometime ifconfig doesn't exist or is deleted on target computers.

To reply to Marco :
And the only "good" solution is a portable resolver unit?
How will you resolve "eth0" on Win32 or BSD ?

For WIN32, i d'ont care because the program is only for Linux systems.
Your are true, in BSD the network interface is not the same and i must
detect wich interface is used...

Best regards






Graeme Geldenhuys a écrit :

> I have these two functions in my .bashrc file.  You only need to run
> "ii" for the cool output.  Now back to the question -  If it is for
> linux only, why not just use the /sbin/ifconfig output.  After all, it
> is accurate and seem much easier than all those libc/library methods.
> I pull the IPs and Interfaces available from the /sbin/ifconfig output
> and works just fine.  If it was needed on windows, I am sure you could
> to the same thing with the 'ipconfig' output.
>
> My 2c worth!  :-)
>
>
> Regards,
>  - Graeme -
>
>
>
> ------------ .bashrc ---------------------
> function my_ip() # get IP adresses
> {
>    MY_IP=$(/sbin/ifconfig eth0 | awk '/inet/ { print $2 } ' | sed -e
> s/addr://)
>    MY_ISP=$(/sbin/ifconfig ppp0 | awk '/P-t-P/ { print $3 } ' | sed
> -e s/P-t-P://)
> }
>
> function ii()   # get current host related info
> {
>    echo -e "\nYou are logged on ${RED}$HOST"
>    echo -e "\nAdditionnal information:$NC " ; uname -a
>    echo -e "\n${RED}Users logged on:$NC " ; w -h
>    echo -e "\n${RED}Current date :$NC " ; date
>    echo -e "\n${RED}Machine stats :$NC " ; uptime
>    echo -e "\n${RED}Memory stats :$NC " ; free
>    my_ip 2>&- ;
>    echo -e "\n${RED}Local IP Address :$NC" ; echo ${MY_IP:-"Not
> connected"}
>    echo -e "\n${RED}ISP Address :$NC" ; echo ${MY_ISP:-"Not connected"}
>    echo
> }
> ---------------------------------
>
> On 06/10/06, Jeff Pohlmeyer <[hidden email]> wrote:
>> > Better, but still Linux only. For a good solution,
>> > a resolver unit that accesses libc should be
>> > written that is portable (unlike the libc unit)
>>
>>
>> If I understood correctly, the OP had two questions:
>>
>> 1. Retrieve a list of interface names on a *linux* system.
>> 2. Return the IP address for a given *linux* interface name.
>>
>>
>> And the only "good" solution is a portable resolver unit?
>>
>> How will you resolve "eth0" on Win32 or BSD ?
>>
>>  -Jeff
>
>

--

David Touzeau -------------------------- Linux Ubuntu Dapper 6.0.6
FreePascal-Lazarus,perl,delphi,php icq:160018849

_______________________________________________
fpc-pascal maillist  -  [hidden email]
http://lists.freepascal.org/mailman/listinfo/fpc-pascal