Skip to content

Commit a6571a0

Browse files
committed
Ruby: Include send example in qhelp
1 parent d3812f5 commit a6571a0

File tree

3 files changed

+14
-8
lines changed

3 files changed

+14
-8
lines changed

ruby/ql/src/queries/security/cwe-094/UnsafeCodeConstruction.qhelp

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ to define the getter method.
6969
<example>
7070
<p>
7171
This example dynamically registers a method on another class which
72-
forwards its arguments to the registering module. This approach uses
72+
forwards its arguments to a target class. This approach uses
7373
<code>module_eval</code> and string interpolation to construct class variables
7474
and methods.
7575
</p>
@@ -81,6 +81,12 @@ A safer approach is to use <code>class_variable_set</code> and
8181
<code>class_variable_get</code> along with <code>define_method</code>. String
8282
interpolation is still used to construct the class variable name, but this is
8383
safe because <code>class_variable_set<code> is not susceptible to code injection.
84+
To construct a dynamic method call we use <code>send</code>, which is ulnerable
85+
to code injection: if an attacker can control the first argument, they can call
86+
any method on the receiver. However this is less powerful than being able to run
87+
arbitrary Ruby code, so it is an improvement in security. We also document to
88+
callers that they should not pass arbitrary user data to the <code>name</code>
89+
parameter.
8490
</p>
8591

8692
<sample src="examples/UnsafeCodeConstruction3Safe.rb" />

ruby/ql/src/queries/security/cwe-094/examples/UnsafeCodeConstruction3.rb

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,10 @@
11
module Invoker
2-
def attach(klass, name)
3-
invoker = self
2+
def attach(klass, name, target)
43
klass.module_eval <<-CODE
5-
@@#{name} = invoker
4+
@@#{name} = target
65
76
def #{name}(*args)
8-
@@#{name}.call(*args)
7+
@@#{name}.#{name}(*args)
98
end
109
CODE
1110
end
Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
module Invoker
2-
def attach(klass, name)
2+
# Do not pass arbitrary user input to +name+.
3+
def attach(klass, name, target)
34
var = :"@@#{name}"
4-
klass.class_variable_set(var, self)
5+
klass.class_variable_set(var, target)
56
klass.define_method(name) do |*args|
6-
self.class.class_variable_get(var).call(*args)
7+
self.class.class_variable_get(var).send(name, *args)
78
end
89
end
910
end

0 commit comments

Comments
 (0)