kchecker: Fix --outfile handling
[smatch.git] / check_mixing_irq_and_irqsave.c
blob210e870e1386f199da4ef4dc003c643ac6516931
1 /*
2 * Copyright (C) 2022 Oracle.
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License
6 * as published by the Free Software Foundation; either version 2
7 * of the License, or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, see http://www.gnu.org/copyleft/gpl.txt
18 #include "smatch.h"
19 #include "smatch_slist.h"
21 static int my_id;
23 static unsigned long warned;
24 static unsigned long irq;
25 static unsigned long irq_save;
27 static const char *irq_funcs[] = {
28 "spin_lock_irq",
29 "spin_unlock_irq",
30 "_spin_lock_irq",
31 "_spin_unlock_irq",
32 "__spin_lock_irq",
33 "__spin_unlock_irq",
34 "_raw_spin_lock_irq",
35 "_raw_spin_unlock_irq",
36 "__raw_spin_unlock_irq",
37 "spin_trylock_irq",
38 "read_lock_irq",
39 "read_unlock_irq",
40 "_read_lock_irq",
41 "_read_unlock_irq",
42 "__read_lock_irq",
43 "__read_unlock_irq",
44 "_raw_read_unlock_irq",
45 "_raw_read_lock_irq",
46 "__raw_write_unlock_irq",
47 "__raw_write_unlock_irq",
48 "write_lock_irq",
49 "write_unlock_irq",
50 "_write_lock_irq",
51 "_write_unlock_irq",
52 "__write_lock_irq",
53 "__write_unlock_irq",
54 "_raw_write_unlock_irq",
55 "_raw_write_lock_irq",
56 "raw_local_irq_disable",
57 "raw_local_irq_enable",
58 "spin_lock_irq",
59 "spin_unlock_irq",
60 "_spin_lock_irq",
61 "_spin_unlock_irq",
62 "__spin_lock_irq",
63 "__spin_unlock_irq",
64 "_raw_spin_lock_irq",
65 "_raw_spin_unlock_irq",
66 "__raw_spin_unlock_irq",
67 "spin_trylock_irq",
68 "read_lock_irq",
69 "read_unlock_irq",
70 "_read_lock_irq",
71 "_read_unlock_irq",
72 "__read_lock_irq",
73 "_raw_read_lock_irq",
74 "__read_unlock_irq",
75 "_raw_read_unlock_irq",
76 "write_lock_irq",
77 "write_unlock_irq",
78 "_write_lock_irq",
79 "_write_unlock_irq",
80 "__write_lock_irq",
81 "__write_unlock_irq",
82 "_raw_write_lock_irq",
83 "_raw_write_unlock_irq",
86 static const char *irqsave_funcs[] = {
87 "spin_lock_irqsave",
88 "_spin_lock_irqsave",
89 "__spin_lock_irqsave",
90 "_raw_spin_lock_irqsave",
91 "__raw_spin_lock_irqsave",
92 "spin_lock_irqsave_nested",
93 "_spin_lock_irqsave_nested",
94 "__spin_lock_irqsave_nested",
95 "_raw_spin_lock_irqsave_nested",
96 "spin_trylock_irqsave",
97 "read_lock_irqsave",
98 "_read_lock_irqsave",
99 "__read_lock_irqsave",
100 "_raw_read_lock_irqsave",
101 "_raw_read_lock_irqsave",
102 "_raw_write_lock_irqsave",
103 "_raw_write_lock_irqsave",
104 "write_lock_irqsave",
105 "_write_lock_irqsave",
106 "__write_lock_irqsave",
107 "arch_local_irq_save",
108 "__raw_local_irq_save",
109 "spin_lock_irqsave_nested",
110 "spin_lock_irqsave",
111 "_spin_lock_irqsave_nested",
112 "_spin_lock_irqsave",
113 "_spin_lock_irqsave",
114 "__spin_lock_irqsave_nested",
115 "__spin_lock_irqsave",
116 "_raw_spin_lock_irqsave",
117 "_raw_spin_lock_irqsave",
118 "__raw_spin_lock_irqsave",
119 "_raw_spin_lock_irqsave_nested",
120 "spin_trylock_irqsave",
121 "read_lock_irqsave",
122 "read_lock_irqsave",
123 "_read_lock_irqsave",
124 "_read_lock_irqsave",
125 "__read_lock_irqsave",
126 "write_lock_irqsave",
127 "write_lock_irqsave",
128 "_write_lock_irqsave",
129 "_write_lock_irqsave",
130 "__write_lock_irqsave",
131 "spin_unlock_irqrestore",
132 "_spin_unlock_irqrestore",
133 "__spin_unlock_irqrestore",
134 "_raw_spin_unlock_irqrestore",
135 "__raw_spin_unlock_irqrestore",
136 "read_unlock_irqrestore",
137 "_read_unlock_irqrestore",
138 "__read_unlock_irqrestore",
139 "_raw_read_unlock_irqrestore",
140 "_raw_write_unlock_irqrestore",
141 "__raw_write_unlock_irqrestore",
142 "write_unlock_irqrestore",
143 "_write_unlock_irqrestore",
144 "__write_unlock_irqrestore",
147 static void irq_hook(const char *fn, struct expression *expr, void *_param)
149 if (warned)
150 return;
151 if (irq_save) {
152 sm_warning("mixing irqsave and irq");
153 warned = true;
155 irq = true;
158 static void irqsave_hook(const char *fn, struct expression *expr, void *_param)
160 char *macro;
162 if (warned)
163 return;
164 macro = get_macro_name(expr->pos);
165 if (macro && !strstr(macro, "irq"))
166 return;
167 if (irq) {
168 sm_warning("mixing irq and irqsave");
169 warned = true;
171 irq_save = true;
174 void check_mixing_irq_and_irqsave(int id)
176 int i;
178 my_id = id;
180 if (option_project != PROJ_KERNEL)
181 return;
183 add_function_data(&warned);
184 add_function_data(&irq);
185 add_function_data(&irq_save);
187 for (i = 0; i < ARRAY_SIZE(irq_funcs); i++)
188 add_function_hook(irq_funcs[i], irq_hook, NULL);
190 for (i = 0; i < ARRAY_SIZE(irqsave_funcs); i++)
191 add_function_hook(irqsave_funcs[i], irqsave_hook, NULL);