brakeman-lib 4.1.1 → 4.2.0

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
- SHA1:
3
- metadata.gz: 52f1866bbb46d9c31465b38923c8b3af801b3d13
4
- data.tar.gz: ba9389b8a21a103ca0a68b237e642ad0a7638074
2
+ SHA256:
3
+ metadata.gz: 1a02aad3664741bec5ac0228bb7010df63d372fe2720fa3dde272aed8e92c070
4
+ data.tar.gz: d882ea01bc6b151920763b3c9f8ca9220c0abfbd6c443c41d72ef447014c6bfa
5
5
  SHA512:
6
- metadata.gz: 55209544e41fadfc1d042116fa93d5cd583ce08913401003d05d58f6e9975f8b75b9f541e200a7dcc29ae78ae6b60c43457317222292bf7c78e29c5c1d05c543
7
- data.tar.gz: 68934d7abc0916646abf934d2f329b5157c0f92df6b588b501611e98c3f5c1c45405d6329b56fd9aa5338df66daae98011104469af0da0f6e4a203a88afe15dd
6
+ metadata.gz: bdce57e4ee118d55722a174c0f411dc19d3cc9a7f636c080124a2ebdc954e8f063e6022460d989c59cf265a7f5ef58978191a06057fb37c5f02e29d120d5b348
7
+ data.tar.gz: 1ac676aaefc2a521af60b0bf12f9f3dc94df6e0b1925dc0918e41542b2f8f7f79d8d621e00dd3486b3a1205e1992358aa7173dfddd88e0db3bf713f2e13ee3c3
data/CHANGES.md CHANGED
@@ -1,3 +1,16 @@
1
+ # 4.2.0
2
+
3
+ * Avoid warning about symbol DoS on `Model#attributes`
4
+ * Avoid warning about open redirects with model methods ending with `_path`
5
+ * Avoid warning about command injection with `Shellwords.escape`
6
+ * Use ivars from `initialize` in libraries
7
+ * `Sexp#body=` can accept `:rlist` from `Sexp#body_list`
8
+ * Update RubyParser to 3.11.0
9
+ * Fix multiple assignment of globals
10
+ * Warn about SQL injection in `not`
11
+ * Exclude template folders in `lib/` (kru0096)
12
+ * Handle ERb use of `String#<<` method for Ruby 2.5 (Pocke)
13
+
1
14
  # 4.1.1
2
15
 
3
16
  * Remove check for use of `permit` with `*_id` keys
@@ -110,7 +110,7 @@ module Brakeman
110
110
  end
111
111
 
112
112
  def lib_paths
113
- @lib_files ||= find_paths("lib").reject { |path| path.include? "/generators/" or path.include? "lib/tasks/" } +
113
+ @lib_files ||= find_paths("lib").reject { |path| path.include? "/generators/" or path.include? "lib/tasks/" or path.include? "lib/templates/" } +
114
114
  find_additional_lib_paths +
115
115
  find_helper_paths
116
116
  end
@@ -62,12 +62,8 @@ class Brakeman::BaseCheck < Brakeman::SexpProcessor
62
62
  #Default Sexp processing. Iterates over each value in the Sexp
63
63
  #and processes them if they are also Sexps.
64
64
  def process_default exp
65
- exp.each_with_index do |e, _i|
66
- if sexp? e
67
- process e
68
- else
69
- e
70
- end
65
+ exp.each do |e|
66
+ process e if sexp? e
71
67
  end
72
68
 
73
69
  exp
@@ -17,6 +17,10 @@ class Brakeman::CheckExecute < Brakeman::BaseCheck
17
17
  s(:call, s(:const, :Rails), :root),
18
18
  s(:call, s(:const, :Rails), :env)]
19
19
 
20
+ SHELL_ESCAPES = [:escape, :shellescape, :join]
21
+
22
+ SHELLWORDS = s(:const, :Shellwords)
23
+
20
24
  #Check models, controllers, and views for command injection.
21
25
  def run_check
22
26
  Brakeman.debug "Finding system calls using ``"
@@ -127,15 +131,17 @@ class Brakeman::CheckExecute < Brakeman::BaseCheck
127
131
  :confidence => confidence
128
132
  end
129
133
 
134
+ # This method expects a :dstr or :evstr node
130
135
  def dangerous? exp
131
136
  exp.each_sexp do |e|
132
- next if node_type? e, :lit, :str
133
- next if SAFE_VALUES.include? e
134
-
135
137
  if call? e and e.method == :to_s
136
138
  e = e.target
137
139
  end
138
140
 
141
+ next if node_type? e, :lit, :str
142
+ next if SAFE_VALUES.include? e
143
+ next if shell_escape? e
144
+
139
145
  if node_type? e, :or, :evstr, :dstr
140
146
  if res = dangerous?(e)
141
147
  return res
@@ -161,4 +167,16 @@ class Brakeman::CheckExecute < Brakeman::BaseCheck
161
167
 
162
168
  false
163
169
  end
170
+
171
+ def shell_escape? exp
172
+ return false unless call? exp
173
+
174
+ if exp.target == SHELLWORDS and SHELL_ESCAPES.include? exp.method
175
+ true
176
+ elsif exp.method == :shelljoin
177
+ true
178
+ else
179
+ false
180
+ end
181
+ end
164
182
  end
@@ -79,7 +79,9 @@ class Brakeman::CheckRedirect < Brakeman::BaseCheck
79
79
  end
80
80
 
81
81
  if res = has_immediate_model?(arg)
82
- return Match.new(immediate, res)
82
+ unless call? arg and arg.method.to_s =~ /_path/
83
+ return Match.new(immediate, res)
84
+ end
83
85
  elsif call? arg
84
86
  if request_value? arg
85
87
  return Match.new(immediate, arg)
@@ -19,7 +19,7 @@ class Brakeman::CheckSQL < Brakeman::BaseCheck
19
19
  @sql_targets = [:average, :calculate, :count, :count_by_sql, :delete_all, :destroy_all,
20
20
  :find_by_sql, :maximum, :minimum, :pluck, :sum, :update_all]
21
21
  @sql_targets.concat [:from, :group, :having, :joins, :lock, :order, :reorder, :where] if tracker.options[:rails3]
22
- @sql_targets << :find_by << :find_by! if tracker.options[:rails4]
22
+ @sql_targets << :find_by << :find_by! << :not if tracker.options[:rails4]
23
23
 
24
24
  if version_between?("2.0.0", "3.9.9") or tracker.config.rails_version.nil?
25
25
  @sql_targets << :first << :last << :all
@@ -184,7 +184,7 @@ class Brakeman::CheckSQL < Brakeman::BaseCheck
184
184
  else
185
185
  check_find_arguments call.last_arg
186
186
  end
187
- when :where, :having, :find_by, :find_by!
187
+ when :where, :having, :find_by, :find_by!, :not
188
188
  check_query_arguments call.arglist
189
189
  when :order, :group, :reorder
190
190
  check_order_arguments call.arglist
@@ -33,8 +33,10 @@ class Brakeman::CheckSymbolDoS < Brakeman::BaseCheck
33
33
  confidence = :medium
34
34
  end
35
35
 
36
+
36
37
  if confidence
37
38
  return if safe_parameter? input.match
39
+ return if symbolizing_attributes? input
38
40
 
39
41
  message = "Symbol conversion from unsafe string (#{friendly_type_of input})"
40
42
 
@@ -60,4 +62,10 @@ class Brakeman::CheckSymbolDoS < Brakeman::BaseCheck
60
62
  false
61
63
  end
62
64
  end
65
+
66
+ def symbolizing_attributes? input
67
+ input.type == :model and
68
+ call? input.match and
69
+ input.match.method == :attributes
70
+ end
63
71
  end
@@ -10,7 +10,11 @@ class Brakeman::CheckUnscopedFind < Brakeman::BaseCheck
10
10
  Brakeman.debug("Finding instances of #find on models with associations")
11
11
 
12
12
  associated_model_names = active_record_models.keys.select do |name|
13
- active_record_models[name].associations[:belongs_to]
13
+ if belongs_to = active_record_models[name].associations[:belongs_to]
14
+ not optional_belongs_to? belongs_to
15
+ else
16
+ false
17
+ end
14
18
  end
15
19
 
16
20
  calls = tracker.find_call :method => [:find, :find_by_id, :find_by_id!],
@@ -38,4 +42,16 @@ class Brakeman::CheckUnscopedFind < Brakeman::BaseCheck
38
42
  :confidence => :weak,
39
43
  :user_input => input
40
44
  end
45
+
46
+ def optional_belongs_to? exp
47
+ return false unless exp.is_a? Array
48
+
49
+ exp.each do |e|
50
+ if hash? e and true? hash_access(e, :optional)
51
+ return true
52
+ end
53
+ end
54
+
55
+ false
56
+ end
41
57
  end
@@ -431,9 +431,12 @@ class Brakeman::AliasProcessor < Brakeman::SexpProcessor
431
431
  match = Sexp.new(:gvar, exp.lhs)
432
432
  exp.rhs = process(exp.rhs)
433
433
  value = get_rhs(exp)
434
- value.line = exp.line
435
434
 
436
- set_value match, value
435
+ if value
436
+ value.line = exp.line
437
+
438
+ set_value match, value
439
+ end
437
440
 
438
441
  exp
439
442
  end
@@ -37,11 +37,7 @@ class Brakeman::BaseProcessor < Brakeman::SexpProcessor
37
37
  exp = exp.dup
38
38
 
39
39
  exp.each_with_index do |e, i|
40
- if sexp? e and not e.empty?
41
- exp[i] = process e
42
- else
43
- e
44
- end
40
+ exp[i] = process e if sexp? e and not e.empty?
45
41
  end
46
42
 
47
43
  exp
@@ -14,7 +14,7 @@ class Brakeman::ErbTemplateProcessor < Brakeman::TemplateProcessor
14
14
 
15
15
  #_erbout is the default output variable for erb
16
16
  if node_type? target, :lvar and target.value == :_erbout
17
- if method == :concat
17
+ if method == :concat or method == :<<
18
18
  @inside_concat = true
19
19
  exp.arglist = process(exp.arglist)
20
20
  @inside_concat = false
@@ -13,6 +13,7 @@ class Brakeman::LibraryProcessor < Brakeman::BaseProcessor
13
13
  @alias_processor = Brakeman::AliasProcessor.new tracker
14
14
  @current_module = nil
15
15
  @current_class = nil
16
+ @intializer_env = nil
16
17
  end
17
18
 
18
19
  def process_library src, file_name = nil
@@ -29,7 +30,14 @@ class Brakeman::LibraryProcessor < Brakeman::BaseProcessor
29
30
  end
30
31
 
31
32
  def process_defn exp
32
- exp = @alias_processor.process exp
33
+ if exp.method_name == :initialize
34
+ @alias_processor.process_safely exp.body_list
35
+ @initializer_env = @alias_processor.only_ivars
36
+ elsif node_type? exp, :defn
37
+ exp = @alias_processor.process_safely exp, @initializer_env
38
+ else
39
+ exp = @alias_processor.process exp
40
+ end
33
41
 
34
42
  if @current_class
35
43
  exp.body = process_all! exp.body
@@ -1,3 +1,3 @@
1
1
  module Brakeman
2
- Version = "4.1.1"
2
+ Version = "4.2.0"
3
3
  end
@@ -506,6 +506,10 @@ class Sexp
506
506
 
507
507
  self.slice!(index..-1) #Remove old body
508
508
 
509
+ if exp.first == :rlist
510
+ exp = exp[1..-1]
511
+ end
512
+
509
513
  #Insert new body
510
514
  exp.each do |e|
511
515
  self[index] = e
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: brakeman-lib
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.1.1
4
+ version: 4.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Justin Collins
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain:
11
11
  - brakeman-public_cert.pem
12
- date: 2017-12-19 00:00:00.000000000 Z
12
+ date: 2018-02-22 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: minitest
@@ -31,14 +31,14 @@ dependencies:
31
31
  requirements:
32
32
  - - "~>"
33
33
  - !ruby/object:Gem::Version
34
- version: 3.10.0
34
+ version: 3.11.0
35
35
  type: :runtime
36
36
  prerelease: false
37
37
  version_requirements: !ruby/object:Gem::Requirement
38
38
  requirements:
39
39
  - - "~>"
40
40
  - !ruby/object:Gem::Version
41
- version: 3.10.0
41
+ version: 3.11.0
42
42
  - !ruby/object:Gem::Dependency
43
43
  name: sexp_processor
44
44
  requirement: !ruby/object:Gem::Requirement
@@ -380,7 +380,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
380
380
  version: '0'
381
381
  requirements: []
382
382
  rubyforge_project:
383
- rubygems_version: 2.4.8
383
+ rubygems_version: 2.7.6
384
384
  signing_key:
385
385
  specification_version: 4
386
386
  summary: Security vulnerability scanner for Ruby on Rails.