Monday, 3 August 2015

Unix - Getting Address'd

As part of a build document, I wanted to script the extraction of a host's IP address, in order that I could programmatically update the hosts file.

This is what I typed into Google ( where the world goes for answers ): -

ifconfig parse ip address

and this is what I got: -


This is what I ended up doing, using the above for inspiration: -

echo `/sbin/ifconfig eth0 | grep 'inet addr:' | cut -d: -f2 | awk '{ print $1}' ` `hostname` >> /etc/hosts

which returns: -

cat /etc/hosts

127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6
192.168.33.136 localhost.localdomain


4 comments:

Stevan Bajić said...

This will not work on my system. I get the following output by ifconfig (changed the IP to protect the innocent):
eth0: flags=4163 mtu 1500
inet 111.222.111.69 netmask 255.255.255.240 broadcast 111.222.111.79
ether aa:bb:cc:dd:ee:ff txqueuelen 1000 (Ethernet)
RX packets 48921994 bytes 111046863242 (103.4 GiB)
RX errors 0 dropped 3155 overruns 0 frame 0
TX packets 49369981 bytes 13592375586 (12.6 GiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0


While ip produces the following output (again changed the IP to protect the innocent):
2: eth0: mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether aa:bb:cc:dd:ee:ff brd ff:ff:ff:ff:ff:ff
inet 111.222.111.69/28 brd 111.222.111.79 scope global eth0
valid_lft forever preferred_lft forever


IMHO it is way easier to use just one helper application than using three (grep, cut, awk). For example with SED:

ip addr show eth0 | sed -n "s:^[\t ]*inet[\t ]\([^\t /]*\).*:\1\t`hostname -f` `hostname -s`:p"

ifconfig eth0 | sed -n "s:^[\t ]*inet[\t ]\([^\t /]*\).*:\1\t`hostname -f` `hostname -s`:p"

Or both combined:
( ifconfig eth0 || ip addr show eth0 ) | sed -n "s:^[\t ]*inet[\t ]\([^\t /]*\).*:\1\t`hostname -f` `hostname -s`:p"

Or if you prefer using AWK then you could run this here:
( ifconfig eth0 || ip addr show eth0 ) | awk -v hf="$(hostname -f)" -v hs="$(hostname -s)" '{if ($1 ~ /^inet$/ && $2 ~ /^addr\:$/) myip = $3; else if ($1 ~ /^inet$/) myip = $2}; END {sub(/\/[0-9]*$/,"",myip); print myip"\t"hf" "hs}'


Cheers,

Steve

Dave Hay said...

Steve, thanks for this, much obliged. My particular command works OK on CentOS 6.6 and Red Hat Enterprise Linux 6.6, but it's good to have alternatives :-)

Stevan Bajić said...

Hello Dave,

it will however fail on CentOS 7.1 and Red Hat EL 7.1 because there is no "inet addr:" line in the output of /sbin/ifconfig:
[root@zh-virt01 /]# /sbin/ifconfig lo
lo: flags=73 mtu 65536
inet 127.0.0.1 netmask 255.0.0.0
loop txqueuelen 0 (Local Loopback)
RX packets 1776088 bytes 233112405 (222.3 MiB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 1776088 bytes 233112405 (222.3 MiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

[root@zh-virt01 /]# /sbin/ifconfig br0
br0: flags=4163 mtu 1500
inet 192.168.10.142 netmask 255.255.255.0 broadcast 192.168.10.255
ether 00:25:90:4c:7b:34 txqueuelen 0 (Ethernet)
RX packets 21644355 bytes 11852994489 (11.0 GiB)
RX errors 0 dropped 143142 overruns 0 frame 0
TX packets 18567665 bytes 12713449047 (11.8 GiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0

[root@zh-virt01 /]# /sbin/ifconfig --version
net-tools 2.10-alpha
[root@zh-virt01 /]# rpm -qf /sbin/ifconfig
net-tools-2.0-0.17.20131004git.el7.x86_64
[root@zh-virt01 /]# cat /etc/redhat-release
CentOS Linux release 7.1.1503 (Core)
[root@zh-virt01 /]#



Cheers,

Steve

Dave Hay said...

Steve

Ah, that explains it. I've not used RHEL / CentOS 7 yet, because some of our IBM middleware isn't formally supported on it ( yes, I know that's also true for CentOS but that's not important right now !! ).

Thanks again, Dave