]>
Commit | Line | Data |
---|---|---|
44d8870f DE |
1 | // SPDX-License-Identifier: GPL-2.0-only |
2 | /// | |
3 | /// Find if/else condition with kmalloc/vmalloc calls. | |
4 | /// Suggest to use kvmalloc instead. Same for kvfree. | |
5 | /// | |
6 | // Confidence: High | |
7 | // Copyright: (C) 2020 Denis Efremov ISPRAS | |
8 | // Options: --no-includes --include-headers | |
9 | // | |
10 | ||
11 | virtual patch | |
12 | virtual report | |
13 | virtual org | |
14 | virtual context | |
15 | ||
16 | @initialize:python@ | |
17 | @@ | |
18 | filter = frozenset(['kvfree']) | |
19 | ||
20 | def relevant(p): | |
21 | return not (filter & {el.current_element for el in p}) | |
22 | ||
23 | @kvmalloc depends on !patch@ | |
24 | expression E, E1, size; | |
25 | identifier flags; | |
26 | binary operator cmp = {<=, <, ==, >, >=}; | |
27 | identifier x; | |
28 | type T; | |
29 | position p; | |
30 | @@ | |
31 | ||
32 | ( | |
33 | * if (size cmp E1 || ...)@p { | |
34 | ... | |
35 | * E = \(kmalloc\|kzalloc\|kcalloc\|kmalloc_node\|kzalloc_node\| | |
36 | * kmalloc_array\|kmalloc_array_node\|kcalloc_node\) | |
37 | * (..., size, \(flags\|GFP_KERNEL\|\(GFP_KERNEL\|flags\)|__GFP_NOWARN\), ...) | |
38 | ... | |
39 | } else { | |
40 | ... | |
41 | * E = \(vmalloc\|vzalloc\|vmalloc_node\|vzalloc_node\)(..., size, ...) | |
42 | ... | |
43 | } | |
44 | | | |
45 | * E = \(kmalloc\|kzalloc\|kcalloc\|kmalloc_node\|kzalloc_node\| | |
46 | * kmalloc_array\|kmalloc_array_node\|kcalloc_node\) | |
47 | * (..., size, \(flags\|GFP_KERNEL\|\(GFP_KERNEL\|flags\)|__GFP_NOWARN\), ...) | |
48 | ... when != E = E1 | |
49 | when != size = E1 | |
50 | when any | |
51 | * if (E == NULL)@p { | |
52 | ... | |
53 | * E = \(vmalloc\|vzalloc\|vmalloc_node\|vzalloc_node\)(..., size, ...) | |
54 | ... | |
55 | } | |
56 | | | |
57 | * T x = \(kmalloc\|kzalloc\|kcalloc\|kmalloc_node\|kzalloc_node\| | |
58 | * kmalloc_array\|kmalloc_array_node\|kcalloc_node\) | |
59 | * (..., size, \(flags\|GFP_KERNEL\|\(GFP_KERNEL\|flags\)|__GFP_NOWARN\), ...); | |
60 | ... when != x = E1 | |
61 | when != size = E1 | |
62 | when any | |
63 | * if (x == NULL)@p { | |
64 | ... | |
65 | * x = \(vmalloc\|vzalloc\|vmalloc_node\|vzalloc_node\)(..., size, ...) | |
66 | ... | |
67 | } | |
68 | ) | |
69 | ||
70 | @kvfree depends on !patch@ | |
71 | expression E; | |
72 | position p : script:python() { relevant(p) }; | |
73 | @@ | |
74 | ||
75 | * if (is_vmalloc_addr(E))@p { | |
76 | ... | |
77 | * vfree(E) | |
78 | ... | |
79 | } else { | |
80 | ... when != krealloc(E, ...) | |
81 | when any | |
9eec0792 | 82 | * \(kfree\|kfree_sensitive\)(E) |
44d8870f DE |
83 | ... |
84 | } | |
85 | ||
86 | @depends on patch@ | |
87 | expression E, E1, size, node; | |
88 | binary operator cmp = {<=, <, ==, >, >=}; | |
89 | identifier flags, x; | |
90 | type T; | |
91 | @@ | |
92 | ||
93 | ( | |
94 | - if (size cmp E1) | |
95 | - E = kmalloc(size, flags); | |
96 | - else | |
97 | - E = vmalloc(size); | |
98 | + E = kvmalloc(size, flags); | |
99 | | | |
100 | - if (size cmp E1) | |
101 | - E = kmalloc(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\)); | |
102 | - else | |
103 | - E = vmalloc(size); | |
104 | + E = kvmalloc(size, GFP_KERNEL); | |
105 | | | |
106 | - E = kmalloc(size, flags | __GFP_NOWARN); | |
107 | - if (E == NULL) | |
108 | - E = vmalloc(size); | |
109 | + E = kvmalloc(size, flags); | |
110 | | | |
111 | - E = kmalloc(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\)); | |
112 | - if (E == NULL) | |
113 | - E = vmalloc(size); | |
114 | + E = kvmalloc(size, GFP_KERNEL); | |
115 | | | |
116 | - T x = kmalloc(size, flags | __GFP_NOWARN); | |
117 | - if (x == NULL) | |
118 | - x = vmalloc(size); | |
119 | + T x = kvmalloc(size, flags); | |
120 | | | |
121 | - T x = kmalloc(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\)); | |
122 | - if (x == NULL) | |
123 | - x = vmalloc(size); | |
124 | + T x = kvmalloc(size, GFP_KERNEL); | |
125 | | | |
126 | - if (size cmp E1) | |
127 | - E = kzalloc(size, flags); | |
128 | - else | |
129 | - E = vzalloc(size); | |
130 | + E = kvzalloc(size, flags); | |
131 | | | |
132 | - if (size cmp E1) | |
133 | - E = kzalloc(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\)); | |
134 | - else | |
135 | - E = vzalloc(size); | |
136 | + E = kvzalloc(size, GFP_KERNEL); | |
137 | | | |
138 | - E = kzalloc(size, flags | __GFP_NOWARN); | |
139 | - if (E == NULL) | |
140 | - E = vzalloc(size); | |
141 | + E = kvzalloc(size, flags); | |
142 | | | |
143 | - E = kzalloc(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\)); | |
144 | - if (E == NULL) | |
145 | - E = vzalloc(size); | |
146 | + E = kvzalloc(size, GFP_KERNEL); | |
147 | | | |
148 | - T x = kzalloc(size, flags | __GFP_NOWARN); | |
149 | - if (x == NULL) | |
150 | - x = vzalloc(size); | |
151 | + T x = kvzalloc(size, flags); | |
152 | | | |
153 | - T x = kzalloc(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\)); | |
154 | - if (x == NULL) | |
155 | - x = vzalloc(size); | |
156 | + T x = kvzalloc(size, GFP_KERNEL); | |
157 | | | |
158 | - if (size cmp E1) | |
159 | - E = kmalloc_node(size, flags, node); | |
160 | - else | |
161 | - E = vmalloc_node(size, node); | |
162 | + E = kvmalloc_node(size, flags, node); | |
163 | | | |
164 | - if (size cmp E1) | |
165 | - E = kmalloc_node(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\), node); | |
166 | - else | |
167 | - E = vmalloc_node(size, node); | |
168 | + E = kvmalloc_node(size, GFP_KERNEL, node); | |
169 | | | |
170 | - E = kmalloc_node(size, flags | __GFP_NOWARN, node); | |
171 | - if (E == NULL) | |
172 | - E = vmalloc_node(size, node); | |
173 | + E = kvmalloc_node(size, flags, node); | |
174 | | | |
175 | - E = kmalloc_node(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\), node); | |
176 | - if (E == NULL) | |
177 | - E = vmalloc_node(size, node); | |
178 | + E = kvmalloc_node(size, GFP_KERNEL, node); | |
179 | | | |
180 | - T x = kmalloc_node(size, flags | __GFP_NOWARN, node); | |
181 | - if (x == NULL) | |
182 | - x = vmalloc_node(size, node); | |
183 | + T x = kvmalloc_node(size, flags, node); | |
184 | | | |
185 | - T x = kmalloc_node(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\), node); | |
186 | - if (x == NULL) | |
187 | - x = vmalloc_node(size, node); | |
188 | + T x = kvmalloc_node(size, GFP_KERNEL, node); | |
189 | | | |
190 | - if (size cmp E1) | |
191 | - E = kvzalloc_node(size, flags, node); | |
192 | - else | |
193 | - E = vzalloc_node(size, node); | |
194 | + E = kvzalloc_node(size, flags, node); | |
195 | | | |
196 | - if (size cmp E1) | |
197 | - E = kvzalloc_node(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\), node); | |
198 | - else | |
199 | - E = vzalloc_node(size, node); | |
200 | + E = kvzalloc_node(size, GFP_KERNEL, node); | |
201 | | | |
202 | - E = kvzalloc_node(size, flags | __GFP_NOWARN, node); | |
203 | - if (E == NULL) | |
204 | - E = vzalloc_node(size, node); | |
205 | + E = kvzalloc_node(size, flags, node); | |
206 | | | |
207 | - E = kvzalloc_node(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\), node); | |
208 | - if (E == NULL) | |
209 | - E = vzalloc_node(size, node); | |
210 | + E = kvzalloc_node(size, GFP_KERNEL, node); | |
211 | | | |
212 | - T x = kvzalloc_node(size, flags | __GFP_NOWARN, node); | |
213 | - if (x == NULL) | |
214 | - x = vzalloc_node(size, node); | |
215 | + T x = kvzalloc_node(size, flags, node); | |
216 | | | |
217 | - T x = kvzalloc_node(size, \(GFP_KERNEL\|GFP_KERNEL|__GFP_NOWARN\), node); | |
218 | - if (x == NULL) | |
219 | - x = vzalloc_node(size, node); | |
220 | + T x = kvzalloc_node(size, GFP_KERNEL, node); | |
221 | ) | |
222 | ||
223 | @depends on patch@ | |
224 | expression E; | |
225 | position p : script:python() { relevant(p) }; | |
226 | @@ | |
227 | ||
228 | - if (is_vmalloc_addr(E))@p | |
229 | - vfree(E); | |
230 | - else | |
231 | - kfree(E); | |
232 | + kvfree(E); | |
233 | ||
234 | @script: python depends on report@ | |
235 | p << kvmalloc.p; | |
236 | @@ | |
237 | ||
238 | coccilib.report.print_report(p[0], "WARNING opportunity for kvmalloc") | |
239 | ||
240 | @script: python depends on org@ | |
241 | p << kvmalloc.p; | |
242 | @@ | |
243 | ||
244 | coccilib.org.print_todo(p[0], "WARNING opportunity for kvmalloc") | |
245 | ||
246 | @script: python depends on report@ | |
247 | p << kvfree.p; | |
248 | @@ | |
249 | ||
250 | coccilib.report.print_report(p[0], "WARNING opportunity for kvfree") | |
251 | ||
252 | @script: python depends on org@ | |
253 | p << kvfree.p; | |
254 | @@ | |
255 | ||
256 | coccilib.org.print_todo(p[0], "WARNING opportunity for kvfree") |