iputil: switch to a scapy-inspired SIOCGIFADDR approach, very linux-specific now

This commit is contained in:
Brian Warner 2007-03-07 20:03:47 -07:00
parent eccb3258ae
commit 751587f376

View File

@ -9,9 +9,55 @@ from twisted.internet import reactor
from twisted.internet.protocol import DatagramProtocol
from twisted.internet.utils import getProcessOutput
from fcntl import ioctl
import struct
SIOCGIFADDR = 0x8915 # linux-specific
# inspired by scapy
def get_if_list():
f = open("/proc/net/dev","r")
f.readline(); f.readline()
names = []
for l in f.readlines():
names.append(l[:l.index(":")].strip())
return names
def get_if_addr(ifname):
try:
s=socket.socket()
ifreq = ioctl(s, SIOCGIFADDR, struct.pack("16s16x", ifname))
s.close()
naddr = ifreq[20:24]
return socket.inet_ntoa(naddr)
except IOError:
return None
def get_local_addresses():
"""Return a Deferred that fires with a list of IPv4 addresses (as
dotted-quad strings) that are currently configured on this host.
"""Return a list of IPv4 addresses (as dotted-quad strings) that are
currently configured on this host.
This will only work under linux, because it uses both a linux-specific
/proc/net/dev devices (to get the interface names) and a SIOCGIFADDR
ioctl (to get their addresses). If the listing-the-interfaces were done
with an ioctl too (and if if you're lucky enough to be using the same
value for the ioctls), then it might work on other forms of unix too.
Windows is right out."""
ifnames = []
for ifname in get_if_list():
addr = get_if_addr(ifname)
if addr:
ifnames.append(addr)
return ifnames
def get_local_addresses_sync():
"""Return a list of IPv4 addresses (as dotted-quad strings) that are
currently configured on this host.
Unfortunately this is not compatible with Twisted: it catches SIGCHLD and
this usually results in errors about 'Interrupted system call'.
This will probably work on both linux and OS-X, but probably not windows.
"""
# eventually I want to use somebody else's cross-platform library for
# this. For right now, I'm running ifconfig and grepping for the 'inet '
@ -34,6 +80,8 @@ def get_local_addresses():
def get_local_addresses_async():
"""Return a Deferred that fires with a list of IPv4 addresses (as
dotted-quad strings) that are currently configured on this host.
This will probably work on both linux and OS-X, but probably not windows.
"""
# eventually I want to use somebody else's cross-platform library for
# this. For right now, I'm running ifconfig and grepping for the 'inet '