cfn-nag 0.1.7 → 0.1.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 6fc49caae80b7af90674e5242e1011d57c8228b1
4
- data.tar.gz: 4d26ed8e76161e9ec08800b52cebb9e4badb4731
3
+ metadata.gz: bd5906c9788032280ede5ed4140f22b9654044a2
4
+ data.tar.gz: 1afc86b72e29a99ec4a91566b00ff2ee5b973078
5
5
  SHA512:
6
- metadata.gz: 2ae12235c935e1b91bdfd71aa63a6d44294c7ae7aec66cf4cd80a58fef9ffcff793ce680ee05588c8e333463fb84357b7e62b25879427b768f29e9d666cae31d
7
- data.tar.gz: 1a4c37d8de9926839b445dc35bd92421191d4f61540bd34a0aaabc13a1b657e7c032d24d08b4b306b6ee248eeb6d3ffef0625cf25e32c355eefbc6eb84364cca
6
+ metadata.gz: e4bbe81af76602d8c5bdb0705bf5fd92b898bf5a11d630a644d97f557ba5cf772272649483aaadbc58f9e4872bee768a6e919b38f2c0681f0f9e0dd4e7cd5eba
7
+ data.tar.gz: c5b85b35db56051f6196ab02a60c665592768ae2e15f5ef3d49440c6a1bf0232789b603f58b048394d9d73ce3c01d659c01c2853b55de0b9329a8112bbcfd980
@@ -1,7 +1,9 @@
1
1
  require 'cfn-nag/violation'
2
2
  require_relative 'base'
3
+ require 'cfn-nag/ip_addr'
3
4
 
4
5
  class SecurityGroupEgressOpenToWorldRule < BaseRule
6
+ include IpAddr
5
7
 
6
8
  def rule_text
7
9
  'Security Groups found with cidr open to world on egress'
@@ -21,8 +23,7 @@ class SecurityGroupEgressOpenToWorldRule < BaseRule
21
23
  logical_resource_ids = []
22
24
  cfn_model.security_groups.each do |security_group|
23
25
  violating_egresses = security_group.securityGroupEgress.select do |egress|
24
- # only care about literals. if a Hash/Ref not going to chase it down given likely a Parameter with external val
25
- egress.cidrIp.is_a?(String) && egress.cidrIp == '0.0.0.0/0'
26
+ ip4_open?(egress) || ip6_open?(egress)
26
27
  end
27
28
 
28
29
  unless violating_egresses.empty?
@@ -31,7 +32,7 @@ class SecurityGroupEgressOpenToWorldRule < BaseRule
31
32
  end
32
33
 
33
34
  violating_egresses = cfn_model.standalone_egress.select do |standalone_egress|
34
- standalone_egress.cidrIp.is_a?(String) && standalone_egress.cidrIp == '0.0.0.0/0'
35
+ ip4_open?(standalone_egress) || ip6_open?(standalone_egress)
35
36
  end
36
37
 
37
38
  logical_resource_ids + violating_egresses.map { |egress| egress.logical_resource_id}
@@ -1,7 +1,9 @@
1
1
  require 'cfn-nag/violation'
2
2
  require_relative 'base'
3
+ require 'cfn-nag/ip_addr'
3
4
 
4
5
  class SecurityGroupIngressCidrNon32Rule < BaseRule
6
+ include IpAddr
5
7
 
6
8
  def rule_text
7
9
  'Security Groups found with ingress cidr that is not /32'
@@ -21,8 +23,7 @@ class SecurityGroupIngressCidrNon32Rule < BaseRule
21
23
  logical_resource_ids = []
22
24
  cfn_model.security_groups.each do |security_group|
23
25
  violating_ingresses = security_group.securityGroupIngress.select do |ingress|
24
- # only care about literals. if a Hash/Ref not going to chase it down given likely a Parameter with external val
25
- ingress.cidrIp.is_a?(String) && !ingress.cidrIp.end_with?('/32')
26
+ ip4_cidr_range?(ingress) || ip6_cidr_range?(ingress)
26
27
  end
27
28
 
28
29
  unless violating_ingresses.empty?
@@ -31,7 +32,7 @@ class SecurityGroupIngressCidrNon32Rule < BaseRule
31
32
  end
32
33
 
33
34
  violating_ingresses = cfn_model.standalone_ingress.select do |standalone_ingress|
34
- standalone_ingress.cidrIp.is_a?(String) && !standalone_ingress.cidrIp.end_with?('/32')
35
+ ip4_cidr_range?(standalone_ingress) || ip6_cidr_range?(standalone_ingress)
35
36
  end
36
37
 
37
38
  logical_resource_ids + violating_ingresses.map { |ingress| ingress.logical_resource_id}
@@ -1,8 +1,10 @@
1
1
  require 'cfn-nag/violation'
2
2
  require_relative 'base'
3
+ require 'cfn-nag/ip_addr'
3
4
 
4
5
  class SecurityGroupIngressOpenToWorldRule < BaseRule
5
-
6
+ include IpAddr
7
+
6
8
  def rule_text
7
9
  'Security Groups found with cidr open to world on ingress. This should never be true on instance. Permissible on ELB'
8
10
  end
@@ -21,8 +23,7 @@ class SecurityGroupIngressOpenToWorldRule < BaseRule
21
23
  logical_resource_ids = []
22
24
  cfn_model.security_groups.each do |security_group|
23
25
  violating_ingresses = security_group.securityGroupIngress.select do |ingress|
24
- # only care about literals. if a Hash/Ref not going to chase it down given likely a Parameter with external val
25
- ingress.cidrIp.is_a?(String) && ingress.cidrIp == '0.0.0.0/0'
26
+ ip4_open?(ingress) || ip6_open?(ingress)
26
27
  end
27
28
 
28
29
  unless violating_ingresses.empty?
@@ -31,7 +32,7 @@ class SecurityGroupIngressOpenToWorldRule < BaseRule
31
32
  end
32
33
 
33
34
  violating_ingresses = cfn_model.standalone_ingress.select do |standalone_ingress|
34
- standalone_ingress.cidrIp.is_a?(String) && standalone_ingress.cidrIp == '0.0.0.0/0'
35
+ ip4_open?(standalone_ingress) || ip6_open?(standalone_ingress)
35
36
  end
36
37
 
37
38
  logical_resource_ids + violating_ingresses.map { |ingress| ingress.logical_resource_id}
@@ -0,0 +1,44 @@
1
+ require 'netaddr'
2
+
3
+ module IpAddr
4
+ def ip4_open?(ingress)
5
+ # only care about literals. if a Hash/Ref not going to chase it down given likely a Parameter with external val
6
+ ingress.cidrIp.is_a?(String) && ingress.cidrIp == '0.0.0.0/0'
7
+ end
8
+
9
+
10
+ def ip6_open?(ingress)
11
+ normalized_cidr_ip6 = normalize_cidr_ip6(ingress)
12
+ return false if normalized_cidr_ip6.nil?
13
+
14
+ # only care about literals. if a Hash/Ref not going to chase it down given likely a Parameter with external val
15
+ (NetAddr::CIDRv6.create(normalized_cidr_ip6) == NetAddr::CIDRv6.create('::/0'))
16
+ end
17
+
18
+ def ip4_cidr_range?(ingress)
19
+ ingress.cidrIp.is_a?(String) && !ingress.cidrIp.end_with?('/32')
20
+ end
21
+
22
+ def ip6_cidr_range?(ingress)
23
+ normalized_cidr_ip6 = normalize_cidr_ip6(ingress)
24
+ return false if normalized_cidr_ip6.nil?
25
+
26
+ # only care about literals. if a Hash/Ref not going to chase it down given likely a Parameter with external val
27
+ !NetAddr::CIDRv6.create(normalized_cidr_ip6).to_s.end_with?('/128')
28
+ end
29
+
30
+ ##
31
+ # If it's a string, just pass through
32
+ # If it's a symbol - probably because the YAML.load call treats an unquoted ::/0 as a the symbol :':/0'
33
+ # Otherwise it's probably a Ref or whatever and we aren't going to do anything with it
34
+ #
35
+ def normalize_cidr_ip6(ingress)
36
+ if ingress.cidrIpv6.is_a?(Symbol)
37
+ ":#{ingress.cidrIpv6.to_s}"
38
+ elsif ingress.cidrIpv6.is_a?(String)
39
+ ingress.cidrIpv6
40
+ else
41
+ nil
42
+ end
43
+ end
44
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cfn-nag
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.7
4
+ version: 0.1.8
5
5
  platform: ruby
6
6
  authors:
7
7
  - Eric Kascic
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-07-17 00:00:00.000000000 Z
11
+ date: 2017-07-19 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: logging
@@ -66,6 +66,20 @@ dependencies:
66
66
  - - '='
67
67
  - !ruby/object:Gem::Version
68
68
  version: 1.3.1
69
+ - !ruby/object:Gem::Dependency
70
+ name: netaddr
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - '='
74
+ - !ruby/object:Gem::Version
75
+ version: 1.5.1
76
+ type: :runtime
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - '='
81
+ - !ruby/object:Gem::Version
82
+ version: 1.5.1
69
83
  description: Auditing tool for CloudFormation templates
70
84
  email:
71
85
  executables:
@@ -129,6 +143,7 @@ files:
129
143
  - lib/cfn-nag/custom_rules/base.rb
130
144
  - lib/cfn-nag/custom_rules/ebs_volumes_jmespath.rb
131
145
  - lib/cfn-nag/custom_rules/unencrypted_s3_put_allowed.rb
146
+ - lib/cfn-nag/ip_addr.rb
132
147
  - lib/cfn-nag/jmes_path_discovery.rb
133
148
  - lib/cfn-nag/jmes_path_evaluator.rb
134
149
  - lib/cfn-nag/profile.rb