mirror of
https://github.com/github/codeql.git
synced 2025-12-17 17:23:36 +01:00
Fixes #1832. In the taint sink, we add an additional check that the given control-flow node can indeed point to a value that is mutable. This takes care of the guard on the type. If and when we get around to adding configurations for all of the taint analyses, we may want to implement this as a barrier instead, pruning any steps that go through a type test where the type is not mutable.
196 lines
3.0 KiB
Python
196 lines
3.0 KiB
Python
|
|
#Consistent Returns
|
|
|
|
__all__ = [ '' ]
|
|
|
|
def ok1(x):
|
|
if x:
|
|
return None
|
|
else:
|
|
return
|
|
|
|
def ok2(x):
|
|
if x:
|
|
return 4
|
|
else:
|
|
return "Hi"
|
|
|
|
def cr1(x):
|
|
if x:
|
|
return 4
|
|
|
|
def cr2(x):
|
|
if x:
|
|
return 4
|
|
else:
|
|
return
|
|
|
|
def ok3(x):
|
|
try:
|
|
return
|
|
finally:
|
|
do_something()
|
|
|
|
#Modification of parameter with default
|
|
|
|
def ok4(x = []):
|
|
return len(x)
|
|
|
|
def mpd(x = []):
|
|
x.append("x")
|
|
|
|
|
|
def use_implicit_return_value(arg):
|
|
x = do_nothing()
|
|
return call_non_callable(arg)
|
|
|
|
#The return in the lambda is OK as it is auto-generated
|
|
y = lambda x : do_nothing()
|
|
|
|
def do_nothing():
|
|
pass
|
|
|
|
|
|
def returns_self(self):
|
|
return self
|
|
|
|
def return_value_ignored():
|
|
ok2()
|
|
ok4()
|
|
sorted([1,2])
|
|
|
|
d = {}
|
|
|
|
def use_return_values():
|
|
x = ok2()
|
|
x = ok2()
|
|
x = ok3()
|
|
x = ok3()
|
|
x = ok4()
|
|
x = ok4()
|
|
x = y()
|
|
x = y()
|
|
x = returns_self()
|
|
x = returns_self()
|
|
x = sorted(x)
|
|
x = sorted(x)
|
|
x = ok2()
|
|
x = ok2()
|
|
x = ok3()
|
|
x = ok3()
|
|
x = ok4()
|
|
x = ok4()
|
|
x = y()
|
|
x = y()
|
|
x = returns_self()
|
|
x = returns_self()
|
|
x = sorted(x)
|
|
x = sorted(x)
|
|
|
|
def ok_to_ignore():
|
|
ok1
|
|
do_nothing()
|
|
returns_self()
|
|
ok3()
|
|
y()
|
|
|
|
class DeprecatedSliceMethods(object):
|
|
|
|
def __getslice__(self, start, stop):
|
|
pass
|
|
|
|
def __setslice__(self, start, stop, value):
|
|
pass
|
|
|
|
def __delslice__(self, start, stop):
|
|
pass
|
|
|
|
|
|
|
|
@decorator
|
|
def nested_call_implicit_return_func_ok(arg):
|
|
do_nothing()
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#Harmless, so we allow it.
|
|
def use_implicit_return_value_ok(arg):
|
|
return do_nothing()
|
|
|
|
def mutli_return(arg):
|
|
if arg:
|
|
return do_something()
|
|
else:
|
|
return do_nothing()
|
|
|
|
#Modification of parameter with default
|
|
|
|
def augassign(x = []):
|
|
x += ["x"]
|
|
|
|
|
|
#ODASA 3658
|
|
from sys import exit
|
|
#Consistent returns
|
|
def ok5():
|
|
try:
|
|
may_raise()
|
|
return 0
|
|
except ValueError as e:
|
|
print(e)
|
|
exit(EXIT_ERROR)
|
|
|
|
|
|
|
|
# indirect modification of parameter with default
|
|
def aug_assign_argument(x):
|
|
x += ['x']
|
|
|
|
def mutate_argument(x):
|
|
x.append('x')
|
|
|
|
def indirect_modification(y = []):
|
|
aug_assign_argument(y)
|
|
mutate_argument(y)
|
|
|
|
def guarded_modification(z=[]):
|
|
if z:
|
|
z.append(0)
|
|
return z
|
|
|
|
def issue1143(expr, param=[]):
|
|
if not param:
|
|
return result
|
|
for i in param:
|
|
param.remove(i) # Mutation here
|
|
|
|
|
|
# Type guarding of modification of parameter with default:
|
|
|
|
def do_stuff_based_on_type(x):
|
|
if isinstance(x, str):
|
|
x = x.split()
|
|
elif isinstance(x, dict):
|
|
x.setdefault('foo', 'bar')
|
|
elif isinstance(x, list):
|
|
x.append(5)
|
|
elif isinstance(x, tuple):
|
|
x = x.unknown_method()
|
|
|
|
def str_default(x="hello world"):
|
|
do_stuff_based_on_type(x)
|
|
|
|
def dict_default(x={'baz':'quux'}):
|
|
do_stuff_based_on_type(x)
|
|
|
|
def list_default(x=[1,2,3,4]):
|
|
do_stuff_based_on_type(x)
|
|
|
|
def tuple_default(x=(1,2)):
|
|
do_stuff_based_on_type(x)
|