@@ -57,33 +57,51 @@ module ModificationOfParameterWithDefault {
57
57
MutableDefaultValue ( ) { nonEmpty = mutableDefaultValue ( this .asCfgNode ( ) .( NameNode ) .getNode ( ) ) }
58
58
}
59
59
60
- predicate safe_method ( string name ) {
61
- name = "count" or
62
- name = "index" or
63
- name = "copy" or
64
- name = "get" or
65
- name = "has_key" or
66
- name = "items" or
67
- name = "keys" or
68
- name = "values" or
69
- name = "iteritems" or
70
- name = "iterkeys" or
71
- name = "itervalues" or
72
- name = "__contains__" or
73
- name = "__getitem__" or
74
- name = "__getattribute__"
60
+ /**
61
+ * A name of a list function that modifies the list.
62
+ * See https://docs.python.org/3/tutorial/datastructures.html#more-on-lists
63
+ */
64
+ string list_modifying_method ( ) {
65
+ result in [ "append" , "extend" , "insert" , "remove" , "pop" , "clear" , "sort" , "reverse" ]
75
66
}
76
67
77
68
/**
78
- * A mutation is considered a flow sink.
69
+ * A name of a dict function that modifies the dict.
70
+ * See https://docs.python.org/3/library/stdtypes.html#dict
71
+ */
72
+ string dict_modifying_method ( ) { result in [ "clear" , "pop" , "popitem" , "setdefault" , "update" ] }
73
+
74
+ /**
75
+ * A mutation of the default value is a flow sink.
76
+ *
77
+ * Syntactic constructs that modify a list are:
78
+ * - s[i] = x
79
+ * - s[i:j] = t
80
+ * - del s[i:j]
81
+ * - s[i:j:k] = t
82
+ * - del s[i:j:k]
83
+ * - s += t
84
+ * - s *= n
85
+ * See https://docs.python.org/3/library/stdtypes.html#mutable-sequence-types
86
+ *
87
+ * Syntactic constructs that modify a dictionary are:
88
+ * - d[key] = value
89
+ * - del d[key]
90
+ * - d |= other
91
+ * See https://docs.python.org/3/library/stdtypes.html#dict
92
+ *
93
+ * These are all covered by:
94
+ * - assignment to a subscript (includes slices)
95
+ * - deletion of a subscript
96
+ * - augmented assignment to the value
79
97
*/
80
98
class Mutation extends Sink {
81
99
Mutation ( ) {
82
100
exists ( AugAssign a | a .getTarget ( ) .getAFlowNode ( ) = this .asCfgNode ( ) )
83
101
or
84
- exists ( Call c , Attribute a | c .getFunc ( ) = a |
85
- a .getObject ( ) . getAFlowNode ( ) = this . asCfgNode ( ) and
86
- not safe_method ( a . getName ( ) )
102
+ exists ( DataFlow :: CallCfgNode c , DataFlow :: AttrRead a | c .getFunction ( ) = a |
103
+ a .getObject ( ) = this and
104
+ a . getAttributeName ( ) in [ list_modifying_method ( ) , dict_modifying_method ( ) ]
87
105
)
88
106
}
89
107
}
0 commit comments