facter 1.3.8 → 1.5

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of facter might be problematic. Click here for more details.

Files changed (46) hide show
  1. data/CHANGELOG +68 -0
  2. data/README +1 -1
  3. data/Rakefile +2 -1
  4. data/bin/facter +16 -11
  5. data/lib/facter.rb +55 -1001
  6. data/lib/facter/Cfkey.rb +42 -0
  7. data/lib/facter/architecture.rb +14 -0
  8. data/lib/facter/domain.rb +64 -0
  9. data/lib/facter/facterversion.rb +3 -0
  10. data/lib/facter/fqdn.rb +10 -0
  11. data/lib/facter/hardwareisa.rb +4 -0
  12. data/lib/facter/hardwaremodel.rb +13 -0
  13. data/lib/facter/hostname.rb +25 -0
  14. data/lib/facter/id.rb +4 -0
  15. data/lib/facter/ipaddress.rb +151 -0
  16. data/lib/facter/iphostnumber.rb +18 -0
  17. data/lib/facter/ipmess.rb +64 -74
  18. data/lib/facter/kernel.rb +3 -0
  19. data/lib/facter/kernelrelease.rb +8 -0
  20. data/lib/facter/lsb.rb +37 -0
  21. data/lib/facter/lsbmajdistrelease.rb +15 -0
  22. data/lib/facter/macaddress.rb +65 -0
  23. data/lib/facter/macosx.rb +25 -55
  24. data/lib/facter/manufacturer.rb +7 -45
  25. data/lib/facter/memory.rb +26 -49
  26. data/lib/facter/netmask.rb +17 -0
  27. data/lib/facter/operatingsystem.rb +37 -0
  28. data/lib/facter/operatingsystemrelease.rb +63 -0
  29. data/lib/facter/processor.rb +36 -14
  30. data/lib/facter/ps.rb +8 -0
  31. data/lib/facter/puppetversion.rb +10 -0
  32. data/lib/facter/rubysitedir.rb +8 -0
  33. data/lib/facter/rubyversion.rb +3 -0
  34. data/lib/facter/ssh.rb +33 -0
  35. data/lib/facter/uniqueid.rb +4 -0
  36. data/lib/facter/util/collection.rb +126 -0
  37. data/lib/facter/util/confine.rb +41 -0
  38. data/lib/facter/util/fact.rb +122 -0
  39. data/lib/facter/util/ip.rb +98 -0
  40. data/lib/facter/util/loader.rb +96 -0
  41. data/lib/facter/util/macosx.rb +50 -0
  42. data/lib/facter/util/manufacturer.rb +39 -0
  43. data/lib/facter/util/memory.rb +54 -0
  44. data/lib/facter/util/netmask.rb +36 -0
  45. data/lib/facter/util/resolution.rb +125 -0
  46. metadata +76 -34
@@ -1,26 +1,13 @@
1
- #
2
1
  # processor.rb
3
2
  # Additional Facts about the machine's CPUs
4
3
  #
5
4
  # Copyright (C) 2006 Mooter Media Ltd
6
5
  # Author: Matthew Palmer <matt@solutionsfirst.com.au>
7
6
  #
8
- #
9
- # This program is free software; you can redistribute it and/or
10
- # modify it under the terms of the GNU General Public License
11
- # as published by the Free Software Foundation (version 2 of the License)
12
- # This program is distributed in the hope that it will be useful,
13
- # but WITHOUT ANY WARRANTY; without even the implied warranty of
14
- # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
- # GNU General Public License for more details.
16
- # You should have received a copy of the GNU General Public License
17
- # along with this program; if not, write to the Free Software
18
- # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston MA 02110-1301 USA
19
- #
20
7
 
21
8
  require 'thread'
22
9
 
23
- if Facter.kernel == "Linux"
10
+ if Facter.value(:kernel) == "Linux"
24
11
  processor_num = -1
25
12
  processor_list = []
26
13
  Thread::exclusive do
@@ -50,3 +37,38 @@ if Facter.kernel == "Linux"
50
37
  end
51
38
  end
52
39
  end
40
+
41
+ if Facter.value(:kernel) == "AIX"
42
+ processor_num = -1
43
+ processor_list = {}
44
+ Thread::exclusive do
45
+ procs = Facter::Util::Resolution.exec('lsdev -Cc processor')
46
+ procs.each do |proc|
47
+ if proc =~ /^proc(\d+)/
48
+ processor_num = $1.to_i
49
+ # Not retrieving the frequency since AIX 4.3.3 doesn't support the
50
+ # attribute and some people still use the OS.
51
+ proctype = Facter::Util::Resolution.exec('lsattr -El proc0 -a type')
52
+ if proctype =~ /^type\s+(\S+)\s+/
53
+ processor_list["processor#{processor_num}"] = $1
54
+ end
55
+ end
56
+ end
57
+ end
58
+
59
+ Facter.add("ProcessorCount") do
60
+ confine :kernel => :aix
61
+ setcode do
62
+ processor_list.length.to_s
63
+ end
64
+ end
65
+
66
+ processor_list.each do |proc, desc|
67
+ Facter.add(proc) do
68
+ confine :kernel => :aix
69
+ setcode do
70
+ desc
71
+ end
72
+ end
73
+ end
74
+ end
@@ -0,0 +1,8 @@
1
+ Facter.add(:ps) do
2
+ setcode do 'ps -ef' end
3
+ end
4
+
5
+ Facter.add(:ps) do
6
+ confine :operatingsystem => %w{FreeBSD NetBSD OpenBSD Darwin}
7
+ setcode do 'ps auxwww' end
8
+ end
@@ -0,0 +1,10 @@
1
+ Facter.add(:puppetversion, :timeout => 1.5) do
2
+ setcode {
3
+ begin
4
+ require 'puppet'
5
+ Puppet::PUPPETVERSION.to_s
6
+ rescue LoadError
7
+ nil
8
+ end
9
+ }
10
+ end
@@ -0,0 +1,8 @@
1
+ Facter.add :rubysitedir do
2
+ setcode do
3
+ version = RUBY_VERSION.to_s.sub(/\.\d+$/, '')
4
+ $:.find do |dir|
5
+ dir =~ /#{File.join("site_ruby", version)}$/
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,3 @@
1
+ Facter.add(:rubyversion) do
2
+ setcode { RUBY_VERSION.to_s }
3
+ end
@@ -0,0 +1,33 @@
1
+ ## ssh.rb
2
+ ## Facts related to SSH
3
+ ##
4
+ ## This program is free software; you can redistribute it and/or
5
+ ## modify it under the terms of the GNU General Public License
6
+ ## as published by the Free Software Foundation (version 2 of the License)
7
+ ## This program is distributed in the hope that it will be useful,
8
+ ## but WITHOUT ANY WARRANTY; without even the implied warranty of
9
+ ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10
+ ## GNU General Public License for more details.
11
+ ## You should have received a copy of the GNU General Public License
12
+ ## along with this program; if not, write to the Free Software
13
+ ## Foundation, Inc., 51 Franklin St, Fifth Floor, Boston MA 02110-1301 USA
14
+ ##
15
+
16
+ ["/etc/ssh","/usr/local/etc/ssh","/etc","/usr/local/etc"].each do |dir|
17
+ {"SSHDSAKey" => "ssh_host_dsa_key.pub", "SSHRSAKey" => "ssh_host_rsa_key.pub"}.each do |name,file|
18
+ Facter.add(name) do
19
+ setcode do
20
+ value = nil
21
+ filepath = File.join(dir,file)
22
+ if FileTest.file?(filepath)
23
+ begin
24
+ File.open(filepath) { |f| value = f.read.chomp.split(/\s+/)[1] }
25
+ rescue
26
+ value = nil
27
+ end
28
+ end
29
+ value
30
+ end # end of proc
31
+ end # end of add
32
+ end # end of hash each
33
+ end # end of dir each
@@ -0,0 +1,4 @@
1
+ Facter.add(:uniqueid) do
2
+ setcode 'hostid', '/bin/sh'
3
+ confine :operatingsystem => %w{Solaris Linux Fedora RedHat CentOS SuSE Debian Gentoo AIX}
4
+ end
@@ -0,0 +1,126 @@
1
+ require 'facter'
2
+ require 'facter/util/fact'
3
+ require 'facter/util/loader'
4
+
5
+ # Manage which facts exist and how we access them. Largely just a wrapper
6
+ # around a hash of facts.
7
+ class Facter::Util::Collection
8
+ # Return a fact object by name. If you use this, you still have to call
9
+ # 'value' on it to retrieve the actual value.
10
+ def [](name)
11
+ value(name)
12
+ end
13
+
14
+ # Add a resolution mechanism for a named fact. This does not distinguish
15
+ # between adding a new fact and adding a new way to resolve a fact.
16
+ def add(name, options = {}, &block)
17
+ name = canonize(name)
18
+
19
+ unless fact = @facts[name]
20
+ fact = Facter::Util::Fact.new(name)
21
+
22
+ @facts[name] = fact
23
+ end
24
+
25
+ # Set any fact-appropriate options.
26
+ options.each do |opt, value|
27
+ method = opt.to_s + "="
28
+ if fact.respond_to?(method)
29
+ fact.send(method, value)
30
+ options.delete(opt)
31
+ end
32
+ end
33
+
34
+ if block
35
+ resolve = fact.add(&block)
36
+ # Set any resolve-appropriate options
37
+ options.each do |opt, value|
38
+ method = opt.to_s + "="
39
+ if resolve.respond_to?(method)
40
+ resolve.send(method, value)
41
+ options.delete(opt)
42
+ end
43
+ end
44
+ end
45
+
46
+ unless options.empty?
47
+ raise ArgumentError, "Invalid facter option(s) %s" % options.keys.collect { |k| k.to_s }.join(",")
48
+ end
49
+
50
+ return fact
51
+ end
52
+
53
+ include Enumerable
54
+
55
+ # Iterate across all of the facts.
56
+ def each
57
+ @facts.each do |name, fact|
58
+ value = fact.value
59
+ unless value.nil?
60
+ yield name.to_s, value
61
+ end
62
+ end
63
+ end
64
+
65
+ # Return a fact by name.
66
+ def fact(name)
67
+ name = canonize(name)
68
+
69
+ loader.load(name) unless @facts[name]
70
+
71
+ return @facts[name]
72
+ end
73
+
74
+ # Flush all cached values.
75
+ def flush
76
+ @facts.each { |name, fact| fact.flush }
77
+ end
78
+
79
+ def initialize
80
+ @facts = Hash.new
81
+ end
82
+
83
+ # Return a list of all of the facts.
84
+ def list
85
+ return @facts.keys
86
+ end
87
+
88
+ # Load all known facts.
89
+ def load_all
90
+ loader.load_all
91
+ end
92
+
93
+ # The thing that loads facts if we don't have them.
94
+ def loader
95
+ unless defined?(@loader)
96
+ @loader = Facter::Util::Loader.new
97
+ end
98
+ @loader
99
+ end
100
+
101
+ # Return a hash of all of our facts.
102
+ def to_hash
103
+ @facts.inject({}) do |h, ary|
104
+ value = ary[1].value
105
+ if ! value.nil?
106
+ # For backwards compatibility, convert the fact name to a string.
107
+ h[ary[0].to_s] = value
108
+ end
109
+ h
110
+ end
111
+ end
112
+
113
+ def value(name)
114
+ if fact = fact(name)
115
+ fact.value
116
+ end
117
+ end
118
+
119
+ private
120
+
121
+ # Provide a consistent means of getting the exact same fact name
122
+ # every time.
123
+ def canonize(name)
124
+ name.to_s.downcase.to_sym
125
+ end
126
+ end
@@ -0,0 +1,41 @@
1
+ # A restricting tag for fact resolution mechanisms. The tag must be true
2
+ # for the resolution mechanism to be suitable.
3
+ class Facter::Util::Confine
4
+ attr_accessor :fact, :values
5
+
6
+ # Add the restriction. Requires the fact name, an operator, and the value
7
+ # we're comparing to.
8
+ def initialize(fact, *values)
9
+ raise ArgumentError, "The fact name must be provided" unless fact
10
+ raise ArgumentError, "One or more values must be provided" if values.empty?
11
+ fact = fact.to_s if fact.is_a? Symbol
12
+ @fact = fact
13
+ @values = values.collect do |value|
14
+ if value.is_a? String
15
+ value
16
+ else
17
+ value.to_s
18
+ end
19
+ end
20
+ end
21
+
22
+ def to_s
23
+ return "'%s' '%s'" % [@fact, @values.join(",")]
24
+ end
25
+
26
+ # Evaluate the fact, returning true or false.
27
+ def true?
28
+ unless fact = Facter[@fact]
29
+ Facter.debug "No fact for %s" % @fact
30
+ return false
31
+ end
32
+ value = fact.value
33
+
34
+ return false if value.nil?
35
+
36
+ @values.each { |v|
37
+ return true if value.downcase == v.downcase
38
+ }
39
+ return false
40
+ end
41
+ end
@@ -0,0 +1,122 @@
1
+ require 'facter'
2
+ require 'facter/util/resolution'
3
+
4
+ class Facter::Util::Fact
5
+ TIMEOUT = 5
6
+
7
+ attr_accessor :name, :ldapname
8
+
9
+ # Create a new fact, with no resolution mechanisms.
10
+ def initialize(name, options = {})
11
+ @name = name.to_s.downcase.intern
12
+
13
+ # LAK:NOTE: This is slow for many options, but generally we won't have any and at
14
+ # worst we'll have one. If we add more, this should be made more efficient.
15
+ options.each do |name, value|
16
+ case name
17
+ when :ldapname: self.ldapname = value
18
+ else
19
+ raise ArgumentError, "Invalid fact option '%s'" % name
20
+ end
21
+ end
22
+
23
+ @ldapname ||= @name.to_s
24
+
25
+ @resolves = []
26
+ @searching = false
27
+
28
+ @value = nil
29
+ end
30
+
31
+ # Add a new resolution mechanism. This requires a block, which will then
32
+ # be evaluated in the context of the new mechanism.
33
+ def add(&block)
34
+ raise ArgumentError, "You must pass a block to Fact<instance>.add" unless block_given?
35
+
36
+ resolve = Facter::Util::Resolution.new(@name)
37
+
38
+ resolve.instance_eval(&block)
39
+
40
+ @resolves << resolve
41
+
42
+ # Immediately sort the resolutions, so that we always have
43
+ # a sorted list for looking up values.
44
+ # We always want to look them up in the order of number of
45
+ # confines, so the most restricted resolution always wins.
46
+ @resolves.sort! { |a, b| b.length <=> a.length }
47
+
48
+ return resolve
49
+ end
50
+
51
+ # Flush any cached values.
52
+ def flush
53
+ @value = nil
54
+ @suitable = nil
55
+ end
56
+
57
+ # Return the value for a given fact. Searches through all of the mechanisms
58
+ # and returns either the first value or nil.
59
+ def value
60
+ return @value if @value
61
+
62
+ if @resolves.length == 0
63
+ Facter.debug "No resolves for %s" % @name
64
+ return nil
65
+ end
66
+
67
+ searching do
68
+ @value = nil
69
+
70
+ foundsuits = false
71
+ @value = @resolves.inject(nil) { |result, resolve|
72
+ next unless resolve.suitable?
73
+ foundsuits = true
74
+
75
+ tmp = resolve.value
76
+
77
+ break tmp unless tmp.nil? or tmp == ""
78
+ }
79
+
80
+ unless foundsuits
81
+ Facter.debug "Found no suitable resolves of %s for %s" % [@resolves.length, @name]
82
+ end
83
+ end
84
+
85
+ if @value.nil?
86
+ # nothing
87
+ Facter.debug("value for %s is still nil" % @name)
88
+ return nil
89
+ else
90
+ return @value
91
+ end
92
+ end
93
+
94
+ private
95
+
96
+ # Are we in the midst of a search?
97
+ def searching?
98
+ @searching
99
+ end
100
+
101
+ # Lock our searching process, so we never ge stuck in recursion.
102
+ def searching
103
+ if searching?
104
+ Facter.debug "Caught recursion on %s" % @name
105
+
106
+ # return a cached value if we've got it
107
+ if @value
108
+ return @value
109
+ else
110
+ return nil
111
+ end
112
+ end
113
+
114
+ # If we've gotten this far, we're not already searching, so go ahead and do so.
115
+ @searching = true
116
+ begin
117
+ yield
118
+ ensure
119
+ @searching = false
120
+ end
121
+ end
122
+ end
@@ -0,0 +1,98 @@
1
+ module Facter::IPAddress
2
+
3
+ def self.get_interfaces
4
+
5
+ int = nil
6
+
7
+ case Facter.value(:kernel)
8
+ when 'Linux', 'OpenBSD', 'NetBSD', 'FreeBSD'
9
+ output = %x{/sbin/ifconfig -a}
10
+ when 'SunOS'
11
+ output = %x{/usr/sbin/ifconfig -a}
12
+ end
13
+
14
+ # We get lots of warnings on platforms that don't get an output
15
+ # made.
16
+ if output
17
+ int = output.scan(/^\w+[.:]?\d+/)
18
+ else
19
+ []
20
+ end
21
+
22
+ end
23
+
24
+ def self.get_interface_value_nonbsd(interface, label)
25
+
26
+ tmp1 = nil
27
+
28
+ case Facter.value(:kernel)
29
+ when 'Linux'
30
+ output_int = %x{/sbin/ifconfig #{interface}}
31
+ addr = /inet addr:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
32
+ mac = /(?:ether|HWaddr)\s+(\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2}:\w{1,2})/
33
+ mask = /Mask:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
34
+ when 'OpenBSD', 'NetBSD', 'FreeBSD'
35
+ output_int = %x{/sbin/ifconfig #{interface}}
36
+ addr = /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
37
+ mac = /(?:ether|lladdr)\s+(\w\w:\w\w:\w\w:\w\w:\w\w:\w\w)/
38
+ mask = /netmask\s+(\w{10})/
39
+ when 'SunOS'
40
+ output_int = %x{/usr/sbin/ifconfig #{interface}}
41
+ addr = /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
42
+ mac = /(?:ether|lladdr)\s+(\w?\w:\w?\w:\w?\w:\w?\w:\w?\w:\w?\w)/
43
+ mask = /netmask\s+(\w{8})/
44
+ end
45
+
46
+ case label
47
+ when 'ipaddress'
48
+ regex = addr
49
+ when 'macaddress'
50
+ regex = mac
51
+ when 'netmask'
52
+ regex = mask
53
+ end
54
+
55
+ if interface != "lo" && interface != "lo0"
56
+ output_int.each { |s|
57
+ tmp1 = $1 if s =~ regex
58
+ }
59
+ end
60
+
61
+ if tmp1
62
+ value = tmp1
63
+ end
64
+
65
+ end
66
+
67
+ def self.get_interface_value_bsd(interface, label)
68
+
69
+ tmp1 = []
70
+
71
+ int_hash = {}
72
+ output_int = %x{/sbin/ifconfig #{interface}}
73
+ addr = /inet\s+([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)/
74
+ mac = /(?:ether|lladdr)\s+(\w\w:\w\w:\w\w:\w\w:\w\w:\w\w)/
75
+ mask = /netmask\s+(\w{10})/
76
+
77
+ case label
78
+ when 'ipaddress'
79
+ regex = addr
80
+ when 'macaddress'
81
+ regex = mac
82
+ when 'netmask'
83
+ regex = mask
84
+ end
85
+
86
+ if interface != "lo" && interface != "lo0"
87
+ output_int.each { |s|
88
+ tmp1.push($1) if s =~ regex
89
+ }
90
+ end
91
+
92
+ if tmp1
93
+ value = tmp1.shift
94
+ end
95
+
96
+ end
97
+ end
98
+