1
module Facter::IPAddress
1
# A base module for collecting IP-related
2
# information from all kinds of platforms.
3
module Facter::Util::IP
4
# A map of all the different regexes that work for
5
# a given platform or set of platforms.
8
:ipaddress => /inet addr:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/,
9
:macaddress => /(?:ether|HWaddr)\s+(\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2})/,
10
:netmask => /Mask:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
13
:aliases => [:openbsd, :netbsd, :freebsd, :darwin],
14
:ipaddress => /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/,
15
:macaddress => /(?:ether|lladdr)\s+(\w\w:\w\w:\w\w:\w\w:\w\w:\w\w)/,
16
:netmask => /netmask\s+0x(\w{8})/
19
:addr => /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/,
20
:macaddress => /(?:ether|lladdr)\s+(\w?\w:\w?\w:\w?\w:\w?\w:\w?\w:\w?\w)/,
21
:netmask => /netmask\s+(\w{8})/
25
# Convert an interface name into purely alpha characters.
26
def self.alphafy(interface)
27
interface.gsub(/[:.]/, '_')
30
def self.convert_from_hex?(kernel)
31
kernels_to_convert = [:sunos, :openbsd, :netbsd, :freebsd, :darwin]
32
kernels_to_convert.include?(kernel)
35
def self.supported_platforms
36
REGEX_MAP.inject([]) do |result, tmp|
39
result += map[:aliases]
3
47
def self.get_interfaces
7
output = Facter::IPAddress.get_all_interface_output()
9
# We get lots of warnings on platforms that don't get an output
12
int = output.scan(/^\w+[.:]?\d+/)
50
output = Facter::Util::IP.get_all_interface_output()
52
# We get lots of warnings on platforms that don't get an output
55
int = output.scan(/^\w+[.:]?\d+/)
19
61
def self.get_all_interface_output
20
62
case Facter.value(:kernel)
21
when 'Linux', 'OpenBSD', 'NetBSD', 'FreeBSD'
22
output = %x{/sbin/ifconfig -a}
24
output = %x{/usr/sbin/ifconfig -a}
63
when 'Linux', 'OpenBSD', 'NetBSD', 'FreeBSD', 'Darwin'
64
output = %x{/sbin/ifconfig -a}
66
output = %x{/usr/sbin/ifconfig -a}
29
71
def self.get_single_interface_output(interface)
31
73
case Facter.value(:kernel)
32
when 'Linux', 'OpenBSD', 'NetBSD', 'FreeBSD'
33
output = %x{/sbin/ifconfig #{interface}}
74
when 'Linux', 'OpenBSD', 'NetBSD', 'FreeBSD', 'Darwin'
75
output = %x{/sbin/ifconfig #{interface}}
35
77
output = %x{/usr/sbin/ifconfig #{interface}}
82
def self.get_bonding_master(interface)
83
if Facter.value(:kernel) != 'Linux'
86
# We need ip instead of ifconfig because it will show us
87
# the bonding master device.
88
if not FileTest.executable?("/sbin/ip")
91
regex = /SLAVE[,>].* (bond[0-9]+)/
92
ethbond = regex.match(%x{/sbin/ip link show #{interface}})
41
102
def self.get_interface_value(interface, label)
45
case Facter.value(:kernel)
47
addr = /inet addr:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
48
mac = /(?:ether|HWaddr)\s+(\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2})/
49
mask = /Mask:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
50
when 'OpenBSD', 'NetBSD', 'FreeBSD'
51
addr = /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
52
mac = /(?:ether|lladdr)\s+(\w\w:\w\w:\w\w:\w\w:\w\w:\w\w)/
53
mask = /netmask\s+(\w{10})/
55
addr = /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
56
mac = /(?:ether|lladdr)\s+(\w?\w:\w?\w:\w?\w:\w?\w:\w?\w:\w?\w)/
57
mask = /netmask\s+(\w{8})/
69
output_int = get_single_interface_output(interface)
71
if interface != "lo" && interface != "lo0"
75
if label == 'netmask' && Facter.value(:kernel) == "SunOS"
76
value = value.scan(/../).collect do |byte| byte.to_i(16) end.join('.')
105
kernel = Facter.value(:kernel).downcase.to_sym
107
# If it's not directly in the map or aliased in the map, then we don't know how to deal with it.
108
unless map = REGEX_MAP[kernel] || REGEX_MAP.values.find { |tmp| tmp[:aliases] and tmp[:aliases].include?(kernel) }
112
# Pull the correct regex out of the map.
113
regex = map[label.to_sym]
115
# Linux changes the MAC address reported via ifconfig when an ethernet interface
116
# becomes a slave of a bonding device to the master MAC address.
117
# We have to dig a bit to get the original/real MAC address of the interface.
118
bonddev = get_bonding_master(interface)
119
if label == 'macaddress' and bonddev
120
bondinfo = IO.readlines("/proc/net/bonding/#{bonddev}")
121
hwaddrre = /^Slave Interface: #{interface}\n[^\n].+?\nPermanent HW addr: (([0-9a-fA-F]{2}:?)*)$/m
122
value = hwaddrre.match(bondinfo.to_s)[1].upcase
124
output_int = get_single_interface_output(interface)
126
if interface != /^lo[0:]?\d?/
127
output_int.each do |s|
130
if label == 'netmask' && convert_from_hex?(kernel)
131
value = value.scan(/../).collect do |byte| byte.to_i(16) end.join('.')
144
def self.get_network_value(interface)
147
ipaddress = get_interface_value(interface, "ipaddress")
148
netmask = get_interface_value(interface, "netmask")
150
if ipaddress && netmask
151
ip = IPAddr.new(ipaddress, Socket::AF_INET)
152
subnet = IPAddr.new(netmask, Socket::AF_INET)
153
network = ip.mask(subnet.to_s).to_s