ruby-nmap 0.6.0 → 0.7.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (58) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +3 -0
  3. data/.travis.yml +13 -0
  4. data/ChangeLog.md +24 -0
  5. data/Gemfile +12 -0
  6. data/LICENSE.txt +1 -1
  7. data/README.md +11 -9
  8. data/Rakefile +20 -24
  9. data/gemspec.yml +1 -3
  10. data/lib/nmap/cpe.rb +2 -0
  11. data/lib/nmap/cpe/cpe.rb +45 -0
  12. data/lib/nmap/cpe/url.rb +78 -0
  13. data/lib/nmap/hop.rb +20 -0
  14. data/lib/nmap/host.rb +69 -15
  15. data/lib/nmap/hostname.rb +20 -0
  16. data/lib/nmap/os.rb +2 -17
  17. data/lib/nmap/os_class.rb +65 -1
  18. data/lib/nmap/port.rb +10 -0
  19. data/lib/nmap/run_stat.rb +20 -0
  20. data/lib/nmap/scan_task.rb +4 -19
  21. data/lib/nmap/sequence.rb +6 -18
  22. data/lib/nmap/service.rb +76 -0
  23. data/lib/nmap/tcp_sequence.rb +1 -1
  24. data/lib/nmap/traceroute.rb +67 -0
  25. data/lib/nmap/uptime.rb +20 -0
  26. data/lib/nmap/version.rb +1 -1
  27. data/lib/nmap/xml.rb +134 -17
  28. data/spec/address_spec.rb +14 -0
  29. data/spec/cpe/url_spec.rb +99 -0
  30. data/spec/cpe_examples.rb +11 -0
  31. data/spec/hop_spec.rb +14 -0
  32. data/spec/host_spec.rb +138 -55
  33. data/spec/hostname_spec.rb +15 -0
  34. data/spec/ip_id_sequence_spec.rb +24 -10
  35. data/spec/os_class_spec.rb +31 -0
  36. data/spec/os_match_spec.rb +15 -0
  37. data/spec/os_spec.rb +23 -20
  38. data/spec/port_spec.rb +14 -15
  39. data/spec/run_stat_spec.rb +21 -0
  40. data/spec/scan.xml +137 -0
  41. data/spec/scan_spec.rb +28 -0
  42. data/spec/scan_task_spec.rb +35 -0
  43. data/spec/scanner_spec.rb +24 -0
  44. data/spec/scripts_examples.rb +10 -0
  45. data/spec/sequence_examples.rb +10 -0
  46. data/spec/service_spec.rb +55 -18
  47. data/spec/spec_helper.rb +30 -3
  48. data/spec/status_spec.rb +15 -0
  49. data/spec/tcp_sequence_spec.rb +32 -19
  50. data/spec/tcp_ts_sequence_spec.rb +24 -10
  51. data/spec/traceroute_spec.rb +31 -0
  52. data/spec/uptime_spec.rb +15 -0
  53. data/spec/xml_spec.rb +172 -31
  54. metadata +50 -54
  55. data/.gemtest +0 -0
  56. data/spec/helpers/nse.xml +0 -94
  57. data/spec/helpers/scan.xml +0 -241
  58. data/spec/helpers/xml.rb +0 -5
@@ -0,0 +1,20 @@
1
+ module Nmap
2
+ #
3
+ # Represents a hostname.
4
+ #
5
+ # @since 0.7.0
6
+ #
7
+ class Hostname < Struct.new(:type, :name)
8
+
9
+ #
10
+ # Converts the hostname to a String.
11
+ #
12
+ # @return [String]
13
+ # The name of the host.
14
+ #
15
+ def to_s
16
+ self.name.to_s
17
+ end
18
+
19
+ end
20
+ end
@@ -15,16 +15,8 @@ module Nmap
15
15
  # @param [Nokogiri::XML::Node] node
16
16
  # The node that contains the OS guessing information.
17
17
  #
18
- # @yield [os]
19
- # If a block is given, it will passed the newly created OS object.
20
- #
21
- # @yieldparam [OS] os
22
- # The newly created OS object.
23
- #
24
18
  def initialize(node)
25
19
  @node = node
26
-
27
- yield self if block_given?
28
20
  end
29
21
 
30
22
  #
@@ -43,15 +35,8 @@ module Nmap
43
35
  def each_class
44
36
  return enum_for(__method__) unless block_given?
45
37
 
46
- @node.xpath("osclass").map do |osclass|
47
- os_class = OSClass.new(
48
- osclass['type'].to_sym,
49
- osclass['vendor'],
50
- osclass['osfamily'].to_sym,
51
- osclass['accuracy'].to_i
52
- )
53
-
54
- yield os_class
38
+ @node.xpath("osmatch/osclass").each do |osclass|
39
+ yield OSClass.new(osclass)
55
40
  end
56
41
 
57
42
  return self
@@ -1,8 +1,72 @@
1
+ require 'nmap/cpe'
2
+
1
3
  module Nmap
2
4
  #
3
5
  # Represents an {OS} class.
4
6
  #
5
- class OSClass < Struct.new(:type, :vendor, :family, :accuracy)
7
+ class OSClass
8
+
9
+ include CPE
10
+
11
+ #
12
+ # Initializes the os class.
13
+ #
14
+ # @param [Nokogiri::XML::Node] node
15
+ # The node that contains the OS Class information.
16
+ #
17
+ def initialize(node)
18
+ @node = node
19
+ end
20
+
21
+ #
22
+ # The OS type.
23
+ #
24
+ # @return [String]
25
+ #
26
+ def type
27
+ @type ||= if @node['type']
28
+ @node['type'].to_sym
29
+ end
30
+ end
31
+
32
+ #
33
+ # The OS vendor.
34
+ #
35
+ # @return [String]
36
+ #
37
+ def vendor
38
+ @vendor ||= @node.get_attribute('vendor')
39
+ end
40
+
41
+ #
42
+ # The OS family.
43
+ #
44
+ # @return [Symbol, nil]
45
+ #
46
+ def family
47
+ @family ||= @node.get_attribute('osfamily').to_sym
48
+ end
49
+
50
+ #
51
+ # The OS generation.
52
+ #
53
+ # @return [Symbol, nil]
54
+ #
55
+ def gen
56
+ @gen ||= if @node['osgen']
57
+ @node['osgen'].to_sym
58
+ end
59
+ end
60
+
61
+ #
62
+ # The accuracy of the OS class information.
63
+ #
64
+ # @return [Integer]
65
+ # Returns a number between 0 and 10.
66
+ #
67
+ def accuracy
68
+ @accuracy ||= @node.get_attribute('accuracy').to_i
69
+ end
6
70
 
7
71
  #
8
72
  # Converts the OS class to a String.
@@ -102,5 +102,15 @@ module Nmap
102
102
  number.to_s
103
103
  end
104
104
 
105
+ #
106
+ # Inspects the port.
107
+ #
108
+ # @return [String]
109
+ # The inspected port.
110
+ #
111
+ def inspect
112
+ "#<#{self.class}: #{self}>"
113
+ end
114
+
105
115
  end
106
116
  end
@@ -0,0 +1,20 @@
1
+ module Nmap
2
+ #
3
+ # Represents the runstats of a scan.
4
+ #
5
+ # @since 0.7.0
6
+ #
7
+ class RunStat < Struct.new(:end_time, :elapsed, :summary, :exit_status)
8
+
9
+ #
10
+ # Converts the stats to a String.
11
+ #
12
+ # @return [String]
13
+ # The String form of the scan.
14
+ #
15
+ def to_s
16
+ "#{self.end_time} #{self.elapsed} #{self.exit_status}"
17
+ end
18
+
19
+ end
20
+ end
@@ -1,17 +1,5 @@
1
1
  module Nmap
2
- class ScanTask
3
-
4
- # The name of the scan task
5
- attr_reader :name
6
-
7
- # The time the scan task begun
8
- attr_reader :start_time
9
-
10
- # The time the scan task ended
11
- attr_reader :end_time
12
-
13
- # Extra information on the scan task
14
- attr_reader :extrainfo
2
+ class ScanTask < Struct.new(:name, :start_time, :end_time, :extrainfo)
15
3
 
16
4
  #
17
5
  # Creates a new ScanTask object.
@@ -31,10 +19,7 @@ module Nmap
31
19
  # @since 0.1.2
32
20
  #
33
21
  def initialize(name,start_time,end_time,extrainfo=nil)
34
- @name = name
35
- @start_time = start_time
36
- @end_time = end_time
37
- @extrainfo = extrainfo
22
+ super
38
23
  end
39
24
 
40
25
  #
@@ -46,7 +31,7 @@ module Nmap
46
31
  # @since 0.1.2
47
32
  #
48
33
  def duration
49
- (@end_time - @start_time)
34
+ (self.end_time - self.start_time)
50
35
  end
51
36
 
52
37
  #
@@ -58,7 +43,7 @@ module Nmap
58
43
  # @since 0.1.2
59
44
  #
60
45
  def to_s
61
- "#{@start}: #{@name} (#{@extrainfo})"
46
+ "#{self.start_time}: #{self.name} (#{self.extrainfo})"
62
47
  end
63
48
 
64
49
  end
@@ -12,18 +12,10 @@ module Nmap
12
12
  # @param [Nokogiri::XML::Node] node
13
13
  # The node that contains the sequence information.
14
14
  #
15
- # @yield [sequence]
16
- # If a block is given, it will passed the newly created sequence.
17
- #
18
- # @yieldparam [Sequence] sequence
19
- # The newly created sequence object.
20
- #
21
15
  # @since 0.5.0
22
16
  #
23
17
  def initialize(node)
24
18
  @node = node
25
-
26
- yield self if block_given?
27
19
  end
28
20
 
29
21
  #
@@ -35,7 +27,7 @@ module Nmap
35
27
  # @since 0.5.0
36
28
  #
37
29
  def description
38
- @node['class']
30
+ @description ||= @node['class']
39
31
  end
40
32
 
41
33
  #
@@ -47,15 +39,11 @@ module Nmap
47
39
  # @since 0.5.0
48
40
  #
49
41
  def values
50
- unless @values
51
- @values = []
52
-
53
- if (string = @node['values'])
54
- string.scan(/[^\s,]+/) { |match| @values << match.to_i(16) }
55
- end
56
- end
57
-
58
- return @values
42
+ @values ||= if @node['values']
43
+ @node['values'].split(',').map { |value| value.to_i(16) }
44
+ else
45
+ []
46
+ end
59
47
  end
60
48
 
61
49
  end
@@ -1,3 +1,5 @@
1
+ require 'nmap/cpe'
2
+
1
3
  module Nmap
2
4
  #
3
5
  # Wraps a `service` XML element.
@@ -6,6 +8,8 @@ module Nmap
6
8
  #
7
9
  class Service
8
10
 
11
+ include CPE
12
+
9
13
  #
10
14
  # Creates a new OS object.
11
15
  #
@@ -26,6 +30,30 @@ module Nmap
26
30
  @name ||= @node.get_attribute('name')
27
31
  end
28
32
 
33
+ #
34
+ # Determines if the service requires SSL.
35
+ #
36
+ # @return [Boolean]
37
+ # Checks whether the `tunnel` XML attribute is `ssl`.
38
+ #
39
+ # @since 0.7.0
40
+ #
41
+ def ssl?
42
+ (@ssl ||= @node['tunnel']) == 'ssl'
43
+ end
44
+
45
+ #
46
+ # The application protocol used by the service.
47
+ #
48
+ # @return [String]
49
+ # The `proto` XML attribute.
50
+ #
51
+ # @since 0.7.0
52
+ #
53
+ def protocol
54
+ @protocol ||= @node['proto']
55
+ end
56
+
29
57
  #
30
58
  # The product of the service.
31
59
  #
@@ -46,6 +74,18 @@ module Nmap
46
74
  @version ||= @node.get_attribute('version')
47
75
  end
48
76
 
77
+ #
78
+ # The extra information from the service scan.
79
+ #
80
+ # @return [String]
81
+ # The `extrainfo` XML attribute.
82
+ #
83
+ # @since 0.7.0
84
+ #
85
+ def extra_info
86
+ @extra_info ||= @node['extrainfo']
87
+ end
88
+
49
89
  #
50
90
  # The hostname reported by the service.
51
91
  #
@@ -56,6 +96,30 @@ module Nmap
56
96
  @hostname ||= @node.get_attribute('hostname')
57
97
  end
58
98
 
99
+ #
100
+ # The reported OS type.
101
+ #
102
+ # @return [String]
103
+ # The `ostype` XML attribute.
104
+ #
105
+ # @since 0.7.0
106
+ #
107
+ def os_type
108
+ @os_type ||= @node['ostype']
109
+ end
110
+
111
+ #
112
+ # The reported device type.
113
+ #
114
+ # @return [String]
115
+ # The `devicetype` XML attribute.
116
+ #
117
+ # @since 0.7.0
118
+ #
119
+ def device_type
120
+ @device_type ||= @node['devicetype']
121
+ end
122
+
59
123
  #
60
124
  # The fingerprint method used to identify the service.
61
125
  #
@@ -66,6 +130,18 @@ module Nmap
66
130
  @fingerprint_method ||= @node.get_attribute('method').to_sym
67
131
  end
68
132
 
133
+ #
134
+ # The actual fingerprint
135
+ #
136
+ # @return [String]
137
+ # The fingerprint
138
+ #
139
+ # @since 0.7.0
140
+ #
141
+ def fingerprint
142
+ @fingerprint ||= @node.get_attribute('servicefp')
143
+ end
144
+
69
145
  #
70
146
  # The confidence score of the service fingerprinting.
71
147
  #
@@ -27,7 +27,7 @@ module Nmap
27
27
  # @since 0.5.0
28
28
  #
29
29
  def difficulty
30
- @node['difficulty']
30
+ @difficulty ||= @node['difficulty']
31
31
  end
32
32
 
33
33
  #
@@ -0,0 +1,67 @@
1
+ require 'nmap/hop'
2
+
3
+ module Nmap
4
+ #
5
+ # Wraps the `trace` XML element.
6
+ #
7
+ # @since 0.7.0
8
+ #
9
+ class Traceroute
10
+
11
+ include Enumerable
12
+
13
+ #
14
+ # Creates a new traceroute.
15
+ #
16
+ # @param [Nokogiri::XML::Element] node
17
+ # The `trace` XML element.
18
+ #
19
+ def initialize(node)
20
+ @node = node
21
+ end
22
+
23
+ #
24
+ # The port used for the traceroute.
25
+ #
26
+ # @return [Integer]
27
+ # The `port` XML attribute.
28
+ #
29
+ def port
30
+ @port ||= @node['port'].to_i
31
+ end
32
+
33
+ #
34
+ # The protocol used for the traceroute.
35
+ #
36
+ # @return [Symbol]
37
+ # The `proto` XML element.
38
+ #
39
+ def protocol
40
+ @protocol ||= @node['proto'].to_sym
41
+ end
42
+
43
+ #
44
+ # Parses the traceroute information for the host.
45
+ #
46
+ # @yield [hop]
47
+ # Each hop to the host.
48
+ #
49
+ # @yieldparam [Hop] hop
50
+ # A hop to the host.
51
+ #
52
+ # @return [Traceroute, Enumerator]
53
+ # The traceroute.
54
+ # If no block was given, an enumerator will be returned.
55
+ #
56
+ def each
57
+ return enum_for(__method__) unless block_given?
58
+
59
+ @node.xpath('hop').each do |hop|
60
+ yield Hop.new(hop['ipaddr'],hop['host'],hop['ttl'],hop['rtt'])
61
+ end
62
+
63
+ return self
64
+ end
65
+
66
+ end
67
+ end