Commit 5fe3af119bed58d240e2097fe76f322ab51902d7

Authored by Andy Whitcroft
Committed by Linus Torvalds
1 parent 383099fd63

checkpatch: __weak is an official attribute

Add __weak as an official attribute.  This tends to be used in a location
where the automated attribute detector misses it.

Signed-off-by: Andy Whitcroft <apw@shadowen.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>

Showing 1 changed file with 2 additions and 1 deletions Inline Diff

scripts/checkpatch.pl
1 #!/usr/bin/perl -w 1 #!/usr/bin/perl -w
2 # (c) 2001, Dave Jones. <davej@redhat.com> (the file handling bit) 2 # (c) 2001, Dave Jones. <davej@redhat.com> (the file handling bit)
3 # (c) 2005, Joel Schopp <jschopp@austin.ibm.com> (the ugly bit) 3 # (c) 2005, Joel Schopp <jschopp@austin.ibm.com> (the ugly bit)
4 # (c) 2007, Andy Whitcroft <apw@uk.ibm.com> (new conditions, test suite, etc) 4 # (c) 2007, Andy Whitcroft <apw@uk.ibm.com> (new conditions, test suite, etc)
5 # Licensed under the terms of the GNU GPL License version 2 5 # Licensed under the terms of the GNU GPL License version 2
6 6
7 use strict; 7 use strict;
8 8
9 my $P = $0; 9 my $P = $0;
10 $P =~ s@.*/@@g; 10 $P =~ s@.*/@@g;
11 11
12 my $V = '0.24'; 12 my $V = '0.24';
13 13
14 use Getopt::Long qw(:config no_auto_abbrev); 14 use Getopt::Long qw(:config no_auto_abbrev);
15 15
16 my $quiet = 0; 16 my $quiet = 0;
17 my $tree = 1; 17 my $tree = 1;
18 my $chk_signoff = 1; 18 my $chk_signoff = 1;
19 my $chk_patch = 1; 19 my $chk_patch = 1;
20 my $tst_only; 20 my $tst_only;
21 my $emacs = 0; 21 my $emacs = 0;
22 my $terse = 0; 22 my $terse = 0;
23 my $file = 0; 23 my $file = 0;
24 my $check = 0; 24 my $check = 0;
25 my $summary = 1; 25 my $summary = 1;
26 my $mailback = 0; 26 my $mailback = 0;
27 my $summary_file = 0; 27 my $summary_file = 0;
28 my $root; 28 my $root;
29 my %debug; 29 my %debug;
30 GetOptions( 30 GetOptions(
31 'q|quiet+' => \$quiet, 31 'q|quiet+' => \$quiet,
32 'tree!' => \$tree, 32 'tree!' => \$tree,
33 'signoff!' => \$chk_signoff, 33 'signoff!' => \$chk_signoff,
34 'patch!' => \$chk_patch, 34 'patch!' => \$chk_patch,
35 'emacs!' => \$emacs, 35 'emacs!' => \$emacs,
36 'terse!' => \$terse, 36 'terse!' => \$terse,
37 'file!' => \$file, 37 'file!' => \$file,
38 'subjective!' => \$check, 38 'subjective!' => \$check,
39 'strict!' => \$check, 39 'strict!' => \$check,
40 'root=s' => \$root, 40 'root=s' => \$root,
41 'summary!' => \$summary, 41 'summary!' => \$summary,
42 'mailback!' => \$mailback, 42 'mailback!' => \$mailback,
43 'summary-file!' => \$summary_file, 43 'summary-file!' => \$summary_file,
44 44
45 'debug=s' => \%debug, 45 'debug=s' => \%debug,
46 'test-only=s' => \$tst_only, 46 'test-only=s' => \$tst_only,
47 ) or exit; 47 ) or exit;
48 48
49 my $exit = 0; 49 my $exit = 0;
50 50
51 if ($#ARGV < 0) { 51 if ($#ARGV < 0) {
52 print "usage: $P [options] patchfile\n"; 52 print "usage: $P [options] patchfile\n";
53 print "version: $V\n"; 53 print "version: $V\n";
54 print "options: -q => quiet\n"; 54 print "options: -q => quiet\n";
55 print " --no-tree => run without a kernel tree\n"; 55 print " --no-tree => run without a kernel tree\n";
56 print " --terse => one line per report\n"; 56 print " --terse => one line per report\n";
57 print " --emacs => emacs compile window format\n"; 57 print " --emacs => emacs compile window format\n";
58 print " --file => check a source file\n"; 58 print " --file => check a source file\n";
59 print " --strict => enable more subjective tests\n"; 59 print " --strict => enable more subjective tests\n";
60 print " --root => path to the kernel tree root\n"; 60 print " --root => path to the kernel tree root\n";
61 print " --no-summary => suppress the per-file summary\n"; 61 print " --no-summary => suppress the per-file summary\n";
62 print " --summary-file => include the filename in summary\n"; 62 print " --summary-file => include the filename in summary\n";
63 exit(1); 63 exit(1);
64 } 64 }
65 65
66 my $dbg_values = 0; 66 my $dbg_values = 0;
67 my $dbg_possible = 0; 67 my $dbg_possible = 0;
68 my $dbg_type = 0; 68 my $dbg_type = 0;
69 my $dbg_attr = 0; 69 my $dbg_attr = 0;
70 for my $key (keys %debug) { 70 for my $key (keys %debug) {
71 eval "\${dbg_$key} = '$debug{$key}';" 71 eval "\${dbg_$key} = '$debug{$key}';"
72 } 72 }
73 73
74 if ($terse) { 74 if ($terse) {
75 $emacs = 1; 75 $emacs = 1;
76 $quiet++; 76 $quiet++;
77 } 77 }
78 78
79 if ($tree) { 79 if ($tree) {
80 if (defined $root) { 80 if (defined $root) {
81 if (!top_of_kernel_tree($root)) { 81 if (!top_of_kernel_tree($root)) {
82 die "$P: $root: --root does not point at a valid tree\n"; 82 die "$P: $root: --root does not point at a valid tree\n";
83 } 83 }
84 } else { 84 } else {
85 if (top_of_kernel_tree('.')) { 85 if (top_of_kernel_tree('.')) {
86 $root = '.'; 86 $root = '.';
87 } elsif ($0 =~ m@(.*)/scripts/[^/]*$@ && 87 } elsif ($0 =~ m@(.*)/scripts/[^/]*$@ &&
88 top_of_kernel_tree($1)) { 88 top_of_kernel_tree($1)) {
89 $root = $1; 89 $root = $1;
90 } 90 }
91 } 91 }
92 92
93 if (!defined $root) { 93 if (!defined $root) {
94 print "Must be run from the top-level dir. of a kernel tree\n"; 94 print "Must be run from the top-level dir. of a kernel tree\n";
95 exit(2); 95 exit(2);
96 } 96 }
97 } 97 }
98 98
99 my $emitted_corrupt = 0; 99 my $emitted_corrupt = 0;
100 100
101 our $Ident = qr{[A-Za-z_][A-Za-z\d_]*}; 101 our $Ident = qr{[A-Za-z_][A-Za-z\d_]*};
102 our $Storage = qr{extern|static|asmlinkage}; 102 our $Storage = qr{extern|static|asmlinkage};
103 our $Sparse = qr{ 103 our $Sparse = qr{
104 __user| 104 __user|
105 __kernel| 105 __kernel|
106 __force| 106 __force|
107 __iomem| 107 __iomem|
108 __must_check| 108 __must_check|
109 __init_refok| 109 __init_refok|
110 __kprobes 110 __kprobes
111 }x; 111 }x;
112 our $Attribute = qr{ 112 our $Attribute = qr{
113 const| 113 const|
114 __read_mostly| 114 __read_mostly|
115 __kprobes| 115 __kprobes|
116 __(?:mem|cpu|dev|)(?:initdata|init)| 116 __(?:mem|cpu|dev|)(?:initdata|init)|
117 ____cacheline_aligned| 117 ____cacheline_aligned|
118 ____cacheline_aligned_in_smp| 118 ____cacheline_aligned_in_smp|
119 ____cacheline_internodealigned_in_smp 119 ____cacheline_internodealigned_in_smp|
120 __weak
120 }x; 121 }x;
121 our $Modifier; 122 our $Modifier;
122 our $Inline = qr{inline|__always_inline|noinline}; 123 our $Inline = qr{inline|__always_inline|noinline};
123 our $Member = qr{->$Ident|\.$Ident|\[[^]]*\]}; 124 our $Member = qr{->$Ident|\.$Ident|\[[^]]*\]};
124 our $Lval = qr{$Ident(?:$Member)*}; 125 our $Lval = qr{$Ident(?:$Member)*};
125 126
126 our $Constant = qr{(?:[0-9]+|0x[0-9a-fA-F]+)[UL]*}; 127 our $Constant = qr{(?:[0-9]+|0x[0-9a-fA-F]+)[UL]*};
127 our $Assignment = qr{(?:\*\=|/=|%=|\+=|-=|<<=|>>=|&=|\^=|\|=|=)}; 128 our $Assignment = qr{(?:\*\=|/=|%=|\+=|-=|<<=|>>=|&=|\^=|\|=|=)};
128 our $Operators = qr{ 129 our $Operators = qr{
129 <=|>=|==|!=| 130 <=|>=|==|!=|
130 =>|->|<<|>>|<|>|!|~| 131 =>|->|<<|>>|<|>|!|~|
131 &&|\|\||,|\^|\+\+|--|&|\||\+|-|\*|\/|% 132 &&|\|\||,|\^|\+\+|--|&|\||\+|-|\*|\/|%
132 }x; 133 }x;
133 134
134 our $NonptrType; 135 our $NonptrType;
135 our $Type; 136 our $Type;
136 our $Declare; 137 our $Declare;
137 138
138 our $UTF8 = qr { 139 our $UTF8 = qr {
139 [\x09\x0A\x0D\x20-\x7E] # ASCII 140 [\x09\x0A\x0D\x20-\x7E] # ASCII
140 | [\xC2-\xDF][\x80-\xBF] # non-overlong 2-byte 141 | [\xC2-\xDF][\x80-\xBF] # non-overlong 2-byte
141 | \xE0[\xA0-\xBF][\x80-\xBF] # excluding overlongs 142 | \xE0[\xA0-\xBF][\x80-\xBF] # excluding overlongs
142 | [\xE1-\xEC\xEE\xEF][\x80-\xBF]{2} # straight 3-byte 143 | [\xE1-\xEC\xEE\xEF][\x80-\xBF]{2} # straight 3-byte
143 | \xED[\x80-\x9F][\x80-\xBF] # excluding surrogates 144 | \xED[\x80-\x9F][\x80-\xBF] # excluding surrogates
144 | \xF0[\x90-\xBF][\x80-\xBF]{2} # planes 1-3 145 | \xF0[\x90-\xBF][\x80-\xBF]{2} # planes 1-3
145 | [\xF1-\xF3][\x80-\xBF]{3} # planes 4-15 146 | [\xF1-\xF3][\x80-\xBF]{3} # planes 4-15
146 | \xF4[\x80-\x8F][\x80-\xBF]{2} # plane 16 147 | \xF4[\x80-\x8F][\x80-\xBF]{2} # plane 16
147 }x; 148 }x;
148 149
149 our $typeTypedefs = qr{(?x: 150 our $typeTypedefs = qr{(?x:
150 (?:__)?(?:u|s|be|le)(?:\d|\d\d)| 151 (?:__)?(?:u|s|be|le)(?:\d|\d\d)|
151 atomic_t 152 atomic_t
152 )}; 153 )};
153 154
154 our @typeList = ( 155 our @typeList = (
155 qr{void}, 156 qr{void},
156 qr{(?:unsigned\s+)?char}, 157 qr{(?:unsigned\s+)?char},
157 qr{(?:unsigned\s+)?short}, 158 qr{(?:unsigned\s+)?short},
158 qr{(?:unsigned\s+)?int}, 159 qr{(?:unsigned\s+)?int},
159 qr{(?:unsigned\s+)?long}, 160 qr{(?:unsigned\s+)?long},
160 qr{(?:unsigned\s+)?long\s+int}, 161 qr{(?:unsigned\s+)?long\s+int},
161 qr{(?:unsigned\s+)?long\s+long}, 162 qr{(?:unsigned\s+)?long\s+long},
162 qr{(?:unsigned\s+)?long\s+long\s+int}, 163 qr{(?:unsigned\s+)?long\s+long\s+int},
163 qr{unsigned}, 164 qr{unsigned},
164 qr{float}, 165 qr{float},
165 qr{double}, 166 qr{double},
166 qr{bool}, 167 qr{bool},
167 qr{struct\s+$Ident}, 168 qr{struct\s+$Ident},
168 qr{union\s+$Ident}, 169 qr{union\s+$Ident},
169 qr{enum\s+$Ident}, 170 qr{enum\s+$Ident},
170 qr{${Ident}_t}, 171 qr{${Ident}_t},
171 qr{${Ident}_handler}, 172 qr{${Ident}_handler},
172 qr{${Ident}_handler_fn}, 173 qr{${Ident}_handler_fn},
173 ); 174 );
174 our @modifierList = ( 175 our @modifierList = (
175 qr{fastcall}, 176 qr{fastcall},
176 ); 177 );
177 178
178 sub build_types { 179 sub build_types {
179 my $mods = "(?x: \n" . join("|\n ", @modifierList) . "\n)"; 180 my $mods = "(?x: \n" . join("|\n ", @modifierList) . "\n)";
180 my $all = "(?x: \n" . join("|\n ", @typeList) . "\n)"; 181 my $all = "(?x: \n" . join("|\n ", @typeList) . "\n)";
181 $Modifier = qr{(?:$Attribute|$Sparse|$mods)}; 182 $Modifier = qr{(?:$Attribute|$Sparse|$mods)};
182 $NonptrType = qr{ 183 $NonptrType = qr{
183 (?:$Modifier\s+|const\s+)* 184 (?:$Modifier\s+|const\s+)*
184 (?: 185 (?:
185 (?:typeof|__typeof__)\s*\(\s*\**\s*$Ident\s*\)| 186 (?:typeof|__typeof__)\s*\(\s*\**\s*$Ident\s*\)|
186 (?:$typeTypedefs\b)| 187 (?:$typeTypedefs\b)|
187 (?:${all}\b) 188 (?:${all}\b)
188 ) 189 )
189 (?:\s+$Modifier|\s+const)* 190 (?:\s+$Modifier|\s+const)*
190 }x; 191 }x;
191 $Type = qr{ 192 $Type = qr{
192 $NonptrType 193 $NonptrType
193 (?:\s*\*+\s*const|\s*\*+|(?:\s*\[\s*\])+)? 194 (?:\s*\*+\s*const|\s*\*+|(?:\s*\[\s*\])+)?
194 (?:\s+$Inline|\s+$Modifier)* 195 (?:\s+$Inline|\s+$Modifier)*
195 }x; 196 }x;
196 $Declare = qr{(?:$Storage\s+)?$Type}; 197 $Declare = qr{(?:$Storage\s+)?$Type};
197 } 198 }
198 build_types(); 199 build_types();
199 200
200 $chk_signoff = 0 if ($file); 201 $chk_signoff = 0 if ($file);
201 202
202 my @dep_includes = (); 203 my @dep_includes = ();
203 my @dep_functions = (); 204 my @dep_functions = ();
204 my $removal = "Documentation/feature-removal-schedule.txt"; 205 my $removal = "Documentation/feature-removal-schedule.txt";
205 if ($tree && -f "$root/$removal") { 206 if ($tree && -f "$root/$removal") {
206 open(REMOVE, "<$root/$removal") || 207 open(REMOVE, "<$root/$removal") ||
207 die "$P: $removal: open failed - $!\n"; 208 die "$P: $removal: open failed - $!\n";
208 while (<REMOVE>) { 209 while (<REMOVE>) {
209 if (/^Check:\s+(.*\S)/) { 210 if (/^Check:\s+(.*\S)/) {
210 for my $entry (split(/[, ]+/, $1)) { 211 for my $entry (split(/[, ]+/, $1)) {
211 if ($entry =~ m@include/(.*)@) { 212 if ($entry =~ m@include/(.*)@) {
212 push(@dep_includes, $1); 213 push(@dep_includes, $1);
213 214
214 } elsif ($entry !~ m@/@) { 215 } elsif ($entry !~ m@/@) {
215 push(@dep_functions, $entry); 216 push(@dep_functions, $entry);
216 } 217 }
217 } 218 }
218 } 219 }
219 } 220 }
220 } 221 }
221 222
222 my @rawlines = (); 223 my @rawlines = ();
223 my @lines = (); 224 my @lines = ();
224 my $vname; 225 my $vname;
225 for my $filename (@ARGV) { 226 for my $filename (@ARGV) {
226 if ($file) { 227 if ($file) {
227 open(FILE, "diff -u /dev/null $filename|") || 228 open(FILE, "diff -u /dev/null $filename|") ||
228 die "$P: $filename: diff failed - $!\n"; 229 die "$P: $filename: diff failed - $!\n";
229 } else { 230 } else {
230 open(FILE, "<$filename") || 231 open(FILE, "<$filename") ||
231 die "$P: $filename: open failed - $!\n"; 232 die "$P: $filename: open failed - $!\n";
232 } 233 }
233 if ($filename eq '-') { 234 if ($filename eq '-') {
234 $vname = 'Your patch'; 235 $vname = 'Your patch';
235 } else { 236 } else {
236 $vname = $filename; 237 $vname = $filename;
237 } 238 }
238 while (<FILE>) { 239 while (<FILE>) {
239 chomp; 240 chomp;
240 push(@rawlines, $_); 241 push(@rawlines, $_);
241 } 242 }
242 close(FILE); 243 close(FILE);
243 if (!process($filename)) { 244 if (!process($filename)) {
244 $exit = 1; 245 $exit = 1;
245 } 246 }
246 @rawlines = (); 247 @rawlines = ();
247 @lines = (); 248 @lines = ();
248 } 249 }
249 250
250 exit($exit); 251 exit($exit);
251 252
252 sub top_of_kernel_tree { 253 sub top_of_kernel_tree {
253 my ($root) = @_; 254 my ($root) = @_;
254 255
255 my @tree_check = ( 256 my @tree_check = (
256 "COPYING", "CREDITS", "Kbuild", "MAINTAINERS", "Makefile", 257 "COPYING", "CREDITS", "Kbuild", "MAINTAINERS", "Makefile",
257 "README", "Documentation", "arch", "include", "drivers", 258 "README", "Documentation", "arch", "include", "drivers",
258 "fs", "init", "ipc", "kernel", "lib", "scripts", 259 "fs", "init", "ipc", "kernel", "lib", "scripts",
259 ); 260 );
260 261
261 foreach my $check (@tree_check) { 262 foreach my $check (@tree_check) {
262 if (! -e $root . '/' . $check) { 263 if (! -e $root . '/' . $check) {
263 return 0; 264 return 0;
264 } 265 }
265 } 266 }
266 return 1; 267 return 1;
267 } 268 }
268 269
269 sub expand_tabs { 270 sub expand_tabs {
270 my ($str) = @_; 271 my ($str) = @_;
271 272
272 my $res = ''; 273 my $res = '';
273 my $n = 0; 274 my $n = 0;
274 for my $c (split(//, $str)) { 275 for my $c (split(//, $str)) {
275 if ($c eq "\t") { 276 if ($c eq "\t") {
276 $res .= ' '; 277 $res .= ' ';
277 $n++; 278 $n++;
278 for (; ($n % 8) != 0; $n++) { 279 for (; ($n % 8) != 0; $n++) {
279 $res .= ' '; 280 $res .= ' ';
280 } 281 }
281 next; 282 next;
282 } 283 }
283 $res .= $c; 284 $res .= $c;
284 $n++; 285 $n++;
285 } 286 }
286 287
287 return $res; 288 return $res;
288 } 289 }
289 sub copy_spacing { 290 sub copy_spacing {
290 (my $res = shift) =~ tr/\t/ /c; 291 (my $res = shift) =~ tr/\t/ /c;
291 return $res; 292 return $res;
292 } 293 }
293 294
294 sub line_stats { 295 sub line_stats {
295 my ($line) = @_; 296 my ($line) = @_;
296 297
297 # Drop the diff line leader and expand tabs 298 # Drop the diff line leader and expand tabs
298 $line =~ s/^.//; 299 $line =~ s/^.//;
299 $line = expand_tabs($line); 300 $line = expand_tabs($line);
300 301
301 # Pick the indent from the front of the line. 302 # Pick the indent from the front of the line.
302 my ($white) = ($line =~ /^(\s*)/); 303 my ($white) = ($line =~ /^(\s*)/);
303 304
304 return (length($line), length($white)); 305 return (length($line), length($white));
305 } 306 }
306 307
307 my $sanitise_quote = ''; 308 my $sanitise_quote = '';
308 309
309 sub sanitise_line_reset { 310 sub sanitise_line_reset {
310 my ($in_comment) = @_; 311 my ($in_comment) = @_;
311 312
312 if ($in_comment) { 313 if ($in_comment) {
313 $sanitise_quote = '*/'; 314 $sanitise_quote = '*/';
314 } else { 315 } else {
315 $sanitise_quote = ''; 316 $sanitise_quote = '';
316 } 317 }
317 } 318 }
318 sub sanitise_line { 319 sub sanitise_line {
319 my ($line) = @_; 320 my ($line) = @_;
320 321
321 my $res = ''; 322 my $res = '';
322 my $l = ''; 323 my $l = '';
323 324
324 my $qlen = 0; 325 my $qlen = 0;
325 my $off = 0; 326 my $off = 0;
326 my $c; 327 my $c;
327 328
328 # Always copy over the diff marker. 329 # Always copy over the diff marker.
329 $res = substr($line, 0, 1); 330 $res = substr($line, 0, 1);
330 331
331 for ($off = 1; $off < length($line); $off++) { 332 for ($off = 1; $off < length($line); $off++) {
332 $c = substr($line, $off, 1); 333 $c = substr($line, $off, 1);
333 334
334 # Comments we are wacking completly including the begin 335 # Comments we are wacking completly including the begin
335 # and end, all to $;. 336 # and end, all to $;.
336 if ($sanitise_quote eq '' && substr($line, $off, 2) eq '/*') { 337 if ($sanitise_quote eq '' && substr($line, $off, 2) eq '/*') {
337 $sanitise_quote = '*/'; 338 $sanitise_quote = '*/';
338 339
339 substr($res, $off, 2, "$;$;"); 340 substr($res, $off, 2, "$;$;");
340 $off++; 341 $off++;
341 next; 342 next;
342 } 343 }
343 if ($sanitise_quote eq '*/' && substr($line, $off, 2) eq '*/') { 344 if ($sanitise_quote eq '*/' && substr($line, $off, 2) eq '*/') {
344 $sanitise_quote = ''; 345 $sanitise_quote = '';
345 substr($res, $off, 2, "$;$;"); 346 substr($res, $off, 2, "$;$;");
346 $off++; 347 $off++;
347 next; 348 next;
348 } 349 }
349 350
350 # A \ in a string means ignore the next character. 351 # A \ in a string means ignore the next character.
351 if (($sanitise_quote eq "'" || $sanitise_quote eq '"') && 352 if (($sanitise_quote eq "'" || $sanitise_quote eq '"') &&
352 $c eq "\\") { 353 $c eq "\\") {
353 substr($res, $off, 2, 'XX'); 354 substr($res, $off, 2, 'XX');
354 $off++; 355 $off++;
355 next; 356 next;
356 } 357 }
357 # Regular quotes. 358 # Regular quotes.
358 if ($c eq "'" || $c eq '"') { 359 if ($c eq "'" || $c eq '"') {
359 if ($sanitise_quote eq '') { 360 if ($sanitise_quote eq '') {
360 $sanitise_quote = $c; 361 $sanitise_quote = $c;
361 362
362 substr($res, $off, 1, $c); 363 substr($res, $off, 1, $c);
363 next; 364 next;
364 } elsif ($sanitise_quote eq $c) { 365 } elsif ($sanitise_quote eq $c) {
365 $sanitise_quote = ''; 366 $sanitise_quote = '';
366 } 367 }
367 } 368 }
368 369
369 #print "SQ:$sanitise_quote\n"; 370 #print "SQ:$sanitise_quote\n";
370 if ($off != 0 && $sanitise_quote eq '*/' && $c ne "\t") { 371 if ($off != 0 && $sanitise_quote eq '*/' && $c ne "\t") {
371 substr($res, $off, 1, $;); 372 substr($res, $off, 1, $;);
372 } elsif ($off != 0 && $sanitise_quote && $c ne "\t") { 373 } elsif ($off != 0 && $sanitise_quote && $c ne "\t") {
373 substr($res, $off, 1, 'X'); 374 substr($res, $off, 1, 'X');
374 } else { 375 } else {
375 substr($res, $off, 1, $c); 376 substr($res, $off, 1, $c);
376 } 377 }
377 } 378 }
378 379
379 # The pathname on a #include may be surrounded by '<' and '>'. 380 # The pathname on a #include may be surrounded by '<' and '>'.
380 if ($res =~ /^.\s*\#\s*include\s+\<(.*)\>/) { 381 if ($res =~ /^.\s*\#\s*include\s+\<(.*)\>/) {
381 my $clean = 'X' x length($1); 382 my $clean = 'X' x length($1);
382 $res =~ s@\<.*\>@<$clean>@; 383 $res =~ s@\<.*\>@<$clean>@;
383 384
384 # The whole of a #error is a string. 385 # The whole of a #error is a string.
385 } elsif ($res =~ /^.\s*\#\s*(?:error|warning)\s+(.*)\b/) { 386 } elsif ($res =~ /^.\s*\#\s*(?:error|warning)\s+(.*)\b/) {
386 my $clean = 'X' x length($1); 387 my $clean = 'X' x length($1);
387 $res =~ s@(\#\s*(?:error|warning)\s+).*@$1$clean@; 388 $res =~ s@(\#\s*(?:error|warning)\s+).*@$1$clean@;
388 } 389 }
389 390
390 return $res; 391 return $res;
391 } 392 }
392 393
393 sub ctx_statement_block { 394 sub ctx_statement_block {
394 my ($linenr, $remain, $off) = @_; 395 my ($linenr, $remain, $off) = @_;
395 my $line = $linenr - 1; 396 my $line = $linenr - 1;
396 my $blk = ''; 397 my $blk = '';
397 my $soff = $off; 398 my $soff = $off;
398 my $coff = $off - 1; 399 my $coff = $off - 1;
399 my $coff_set = 0; 400 my $coff_set = 0;
400 401
401 my $loff = 0; 402 my $loff = 0;
402 403
403 my $type = ''; 404 my $type = '';
404 my $level = 0; 405 my $level = 0;
405 my $p; 406 my $p;
406 my $c; 407 my $c;
407 my $len = 0; 408 my $len = 0;
408 409
409 my $remainder; 410 my $remainder;
410 while (1) { 411 while (1) {
411 #warn "CSB: blk<$blk> remain<$remain>\n"; 412 #warn "CSB: blk<$blk> remain<$remain>\n";
412 # If we are about to drop off the end, pull in more 413 # If we are about to drop off the end, pull in more
413 # context. 414 # context.
414 if ($off >= $len) { 415 if ($off >= $len) {
415 for (; $remain > 0; $line++) { 416 for (; $remain > 0; $line++) {
416 last if (!defined $lines[$line]); 417 last if (!defined $lines[$line]);
417 next if ($lines[$line] =~ /^-/); 418 next if ($lines[$line] =~ /^-/);
418 $remain--; 419 $remain--;
419 $loff = $len; 420 $loff = $len;
420 $blk .= $lines[$line] . "\n"; 421 $blk .= $lines[$line] . "\n";
421 $len = length($blk); 422 $len = length($blk);
422 $line++; 423 $line++;
423 last; 424 last;
424 } 425 }
425 # Bail if there is no further context. 426 # Bail if there is no further context.
426 #warn "CSB: blk<$blk> off<$off> len<$len>\n"; 427 #warn "CSB: blk<$blk> off<$off> len<$len>\n";
427 if ($off >= $len) { 428 if ($off >= $len) {
428 last; 429 last;
429 } 430 }
430 } 431 }
431 $p = $c; 432 $p = $c;
432 $c = substr($blk, $off, 1); 433 $c = substr($blk, $off, 1);
433 $remainder = substr($blk, $off); 434 $remainder = substr($blk, $off);
434 435
435 #warn "CSB: c<$c> type<$type> level<$level> remainder<$remainder> coff_set<$coff_set>\n"; 436 #warn "CSB: c<$c> type<$type> level<$level> remainder<$remainder> coff_set<$coff_set>\n";
436 # Statement ends at the ';' or a close '}' at the 437 # Statement ends at the ';' or a close '}' at the
437 # outermost level. 438 # outermost level.
438 if ($level == 0 && $c eq ';') { 439 if ($level == 0 && $c eq ';') {
439 last; 440 last;
440 } 441 }
441 442
442 # An else is really a conditional as long as its not else if 443 # An else is really a conditional as long as its not else if
443 if ($level == 0 && $coff_set == 0 && 444 if ($level == 0 && $coff_set == 0 &&
444 (!defined($p) || $p =~ /(?:\s|\}|\+)/) && 445 (!defined($p) || $p =~ /(?:\s|\}|\+)/) &&
445 $remainder =~ /^(else)(?:\s|{)/ && 446 $remainder =~ /^(else)(?:\s|{)/ &&
446 $remainder !~ /^else\s+if\b/) { 447 $remainder !~ /^else\s+if\b/) {
447 $coff = $off + length($1) - 1; 448 $coff = $off + length($1) - 1;
448 $coff_set = 1; 449 $coff_set = 1;
449 #warn "CSB: mark coff<$coff> soff<$soff> 1<$1>\n"; 450 #warn "CSB: mark coff<$coff> soff<$soff> 1<$1>\n";
450 #warn "[" . substr($blk, $soff, $coff - $soff + 1) . "]\n"; 451 #warn "[" . substr($blk, $soff, $coff - $soff + 1) . "]\n";
451 } 452 }
452 453
453 if (($type eq '' || $type eq '(') && $c eq '(') { 454 if (($type eq '' || $type eq '(') && $c eq '(') {
454 $level++; 455 $level++;
455 $type = '('; 456 $type = '(';
456 } 457 }
457 if ($type eq '(' && $c eq ')') { 458 if ($type eq '(' && $c eq ')') {
458 $level--; 459 $level--;
459 $type = ($level != 0)? '(' : ''; 460 $type = ($level != 0)? '(' : '';
460 461
461 if ($level == 0 && $coff < $soff) { 462 if ($level == 0 && $coff < $soff) {
462 $coff = $off; 463 $coff = $off;
463 $coff_set = 1; 464 $coff_set = 1;
464 #warn "CSB: mark coff<$coff>\n"; 465 #warn "CSB: mark coff<$coff>\n";
465 } 466 }
466 } 467 }
467 if (($type eq '' || $type eq '{') && $c eq '{') { 468 if (($type eq '' || $type eq '{') && $c eq '{') {
468 $level++; 469 $level++;
469 $type = '{'; 470 $type = '{';
470 } 471 }
471 if ($type eq '{' && $c eq '}') { 472 if ($type eq '{' && $c eq '}') {
472 $level--; 473 $level--;
473 $type = ($level != 0)? '{' : ''; 474 $type = ($level != 0)? '{' : '';
474 475
475 if ($level == 0) { 476 if ($level == 0) {
476 last; 477 last;
477 } 478 }
478 } 479 }
479 $off++; 480 $off++;
480 } 481 }
481 # We are truly at the end, so shuffle to the next line. 482 # We are truly at the end, so shuffle to the next line.
482 if ($off == $len) { 483 if ($off == $len) {
483 $loff = $len + 1; 484 $loff = $len + 1;
484 $line++; 485 $line++;
485 $remain--; 486 $remain--;
486 } 487 }
487 488
488 my $statement = substr($blk, $soff, $off - $soff + 1); 489 my $statement = substr($blk, $soff, $off - $soff + 1);
489 my $condition = substr($blk, $soff, $coff - $soff + 1); 490 my $condition = substr($blk, $soff, $coff - $soff + 1);
490 491
491 #warn "STATEMENT<$statement>\n"; 492 #warn "STATEMENT<$statement>\n";
492 #warn "CONDITION<$condition>\n"; 493 #warn "CONDITION<$condition>\n";
493 494
494 #print "coff<$coff> soff<$off> loff<$loff>\n"; 495 #print "coff<$coff> soff<$off> loff<$loff>\n";
495 496
496 return ($statement, $condition, 497 return ($statement, $condition,
497 $line, $remain + 1, $off - $loff + 1, $level); 498 $line, $remain + 1, $off - $loff + 1, $level);
498 } 499 }
499 500
500 sub statement_lines { 501 sub statement_lines {
501 my ($stmt) = @_; 502 my ($stmt) = @_;
502 503
503 # Strip the diff line prefixes and rip blank lines at start and end. 504 # Strip the diff line prefixes and rip blank lines at start and end.
504 $stmt =~ s/(^|\n)./$1/g; 505 $stmt =~ s/(^|\n)./$1/g;
505 $stmt =~ s/^\s*//; 506 $stmt =~ s/^\s*//;
506 $stmt =~ s/\s*$//; 507 $stmt =~ s/\s*$//;
507 508
508 my @stmt_lines = ($stmt =~ /\n/g); 509 my @stmt_lines = ($stmt =~ /\n/g);
509 510
510 return $#stmt_lines + 2; 511 return $#stmt_lines + 2;
511 } 512 }
512 513
513 sub statement_rawlines { 514 sub statement_rawlines {
514 my ($stmt) = @_; 515 my ($stmt) = @_;
515 516
516 my @stmt_lines = ($stmt =~ /\n/g); 517 my @stmt_lines = ($stmt =~ /\n/g);
517 518
518 return $#stmt_lines + 2; 519 return $#stmt_lines + 2;
519 } 520 }
520 521
521 sub statement_block_size { 522 sub statement_block_size {
522 my ($stmt) = @_; 523 my ($stmt) = @_;
523 524
524 $stmt =~ s/(^|\n)./$1/g; 525 $stmt =~ s/(^|\n)./$1/g;
525 $stmt =~ s/^\s*{//; 526 $stmt =~ s/^\s*{//;
526 $stmt =~ s/}\s*$//; 527 $stmt =~ s/}\s*$//;
527 $stmt =~ s/^\s*//; 528 $stmt =~ s/^\s*//;
528 $stmt =~ s/\s*$//; 529 $stmt =~ s/\s*$//;
529 530
530 my @stmt_lines = ($stmt =~ /\n/g); 531 my @stmt_lines = ($stmt =~ /\n/g);
531 my @stmt_statements = ($stmt =~ /;/g); 532 my @stmt_statements = ($stmt =~ /;/g);
532 533
533 my $stmt_lines = $#stmt_lines + 2; 534 my $stmt_lines = $#stmt_lines + 2;
534 my $stmt_statements = $#stmt_statements + 1; 535 my $stmt_statements = $#stmt_statements + 1;
535 536
536 if ($stmt_lines > $stmt_statements) { 537 if ($stmt_lines > $stmt_statements) {
537 return $stmt_lines; 538 return $stmt_lines;
538 } else { 539 } else {
539 return $stmt_statements; 540 return $stmt_statements;
540 } 541 }
541 } 542 }
542 543
543 sub ctx_statement_full { 544 sub ctx_statement_full {
544 my ($linenr, $remain, $off) = @_; 545 my ($linenr, $remain, $off) = @_;
545 my ($statement, $condition, $level); 546 my ($statement, $condition, $level);
546 547
547 my (@chunks); 548 my (@chunks);
548 549
549 # Grab the first conditional/block pair. 550 # Grab the first conditional/block pair.
550 ($statement, $condition, $linenr, $remain, $off, $level) = 551 ($statement, $condition, $linenr, $remain, $off, $level) =
551 ctx_statement_block($linenr, $remain, $off); 552 ctx_statement_block($linenr, $remain, $off);
552 #print "F: c<$condition> s<$statement> remain<$remain>\n"; 553 #print "F: c<$condition> s<$statement> remain<$remain>\n";
553 push(@chunks, [ $condition, $statement ]); 554 push(@chunks, [ $condition, $statement ]);
554 if (!($remain > 0 && $condition =~ /^\s*(?:\n[+-])?\s*(?:if|else|do)\b/s)) { 555 if (!($remain > 0 && $condition =~ /^\s*(?:\n[+-])?\s*(?:if|else|do)\b/s)) {
555 return ($level, $linenr, @chunks); 556 return ($level, $linenr, @chunks);
556 } 557 }
557 558
558 # Pull in the following conditional/block pairs and see if they 559 # Pull in the following conditional/block pairs and see if they
559 # could continue the statement. 560 # could continue the statement.
560 for (;;) { 561 for (;;) {
561 ($statement, $condition, $linenr, $remain, $off, $level) = 562 ($statement, $condition, $linenr, $remain, $off, $level) =
562 ctx_statement_block($linenr, $remain, $off); 563 ctx_statement_block($linenr, $remain, $off);
563 #print "C: c<$condition> s<$statement> remain<$remain>\n"; 564 #print "C: c<$condition> s<$statement> remain<$remain>\n";
564 last if (!($remain > 0 && $condition =~ /^(?:\s*\n[+-])*\s*(?:else|do)\b/s)); 565 last if (!($remain > 0 && $condition =~ /^(?:\s*\n[+-])*\s*(?:else|do)\b/s));
565 #print "C: push\n"; 566 #print "C: push\n";
566 push(@chunks, [ $condition, $statement ]); 567 push(@chunks, [ $condition, $statement ]);
567 } 568 }
568 569
569 return ($level, $linenr, @chunks); 570 return ($level, $linenr, @chunks);
570 } 571 }
571 572
572 sub ctx_block_get { 573 sub ctx_block_get {
573 my ($linenr, $remain, $outer, $open, $close, $off) = @_; 574 my ($linenr, $remain, $outer, $open, $close, $off) = @_;
574 my $line; 575 my $line;
575 my $start = $linenr - 1; 576 my $start = $linenr - 1;
576 my $blk = ''; 577 my $blk = '';
577 my @o; 578 my @o;
578 my @c; 579 my @c;
579 my @res = (); 580 my @res = ();
580 581
581 my $level = 0; 582 my $level = 0;
582 for ($line = $start; $remain > 0; $line++) { 583 for ($line = $start; $remain > 0; $line++) {
583 next if ($rawlines[$line] =~ /^-/); 584 next if ($rawlines[$line] =~ /^-/);
584 $remain--; 585 $remain--;
585 586
586 $blk .= $rawlines[$line]; 587 $blk .= $rawlines[$line];
587 foreach my $c (split(//, $rawlines[$line])) { 588 foreach my $c (split(//, $rawlines[$line])) {
588 ##print "C<$c>L<$level><$open$close>O<$off>\n"; 589 ##print "C<$c>L<$level><$open$close>O<$off>\n";
589 if ($off > 0) { 590 if ($off > 0) {
590 $off--; 591 $off--;
591 next; 592 next;
592 } 593 }
593 594
594 if ($c eq $close && $level > 0) { 595 if ($c eq $close && $level > 0) {
595 $level--; 596 $level--;
596 last if ($level == 0); 597 last if ($level == 0);
597 } elsif ($c eq $open) { 598 } elsif ($c eq $open) {
598 $level++; 599 $level++;
599 } 600 }
600 } 601 }
601 602
602 if (!$outer || $level <= 1) { 603 if (!$outer || $level <= 1) {
603 push(@res, $rawlines[$line]); 604 push(@res, $rawlines[$line]);
604 } 605 }
605 606
606 last if ($level == 0); 607 last if ($level == 0);
607 } 608 }
608 609
609 return ($level, @res); 610 return ($level, @res);
610 } 611 }
611 sub ctx_block_outer { 612 sub ctx_block_outer {
612 my ($linenr, $remain) = @_; 613 my ($linenr, $remain) = @_;
613 614
614 my ($level, @r) = ctx_block_get($linenr, $remain, 1, '{', '}', 0); 615 my ($level, @r) = ctx_block_get($linenr, $remain, 1, '{', '}', 0);
615 return @r; 616 return @r;
616 } 617 }
617 sub ctx_block { 618 sub ctx_block {
618 my ($linenr, $remain) = @_; 619 my ($linenr, $remain) = @_;
619 620
620 my ($level, @r) = ctx_block_get($linenr, $remain, 0, '{', '}', 0); 621 my ($level, @r) = ctx_block_get($linenr, $remain, 0, '{', '}', 0);
621 return @r; 622 return @r;
622 } 623 }
623 sub ctx_statement { 624 sub ctx_statement {
624 my ($linenr, $remain, $off) = @_; 625 my ($linenr, $remain, $off) = @_;
625 626
626 my ($level, @r) = ctx_block_get($linenr, $remain, 0, '(', ')', $off); 627 my ($level, @r) = ctx_block_get($linenr, $remain, 0, '(', ')', $off);
627 return @r; 628 return @r;
628 } 629 }
629 sub ctx_block_level { 630 sub ctx_block_level {
630 my ($linenr, $remain) = @_; 631 my ($linenr, $remain) = @_;
631 632
632 return ctx_block_get($linenr, $remain, 0, '{', '}', 0); 633 return ctx_block_get($linenr, $remain, 0, '{', '}', 0);
633 } 634 }
634 sub ctx_statement_level { 635 sub ctx_statement_level {
635 my ($linenr, $remain, $off) = @_; 636 my ($linenr, $remain, $off) = @_;
636 637
637 return ctx_block_get($linenr, $remain, 0, '(', ')', $off); 638 return ctx_block_get($linenr, $remain, 0, '(', ')', $off);
638 } 639 }
639 640
640 sub ctx_locate_comment { 641 sub ctx_locate_comment {
641 my ($first_line, $end_line) = @_; 642 my ($first_line, $end_line) = @_;
642 643
643 # Catch a comment on the end of the line itself. 644 # Catch a comment on the end of the line itself.
644 my ($current_comment) = ($rawlines[$end_line - 1] =~ m@.*(/\*.*\*/)\s*(?:\\\s*)?$@); 645 my ($current_comment) = ($rawlines[$end_line - 1] =~ m@.*(/\*.*\*/)\s*(?:\\\s*)?$@);
645 return $current_comment if (defined $current_comment); 646 return $current_comment if (defined $current_comment);
646 647
647 # Look through the context and try and figure out if there is a 648 # Look through the context and try and figure out if there is a
648 # comment. 649 # comment.
649 my $in_comment = 0; 650 my $in_comment = 0;
650 $current_comment = ''; 651 $current_comment = '';
651 for (my $linenr = $first_line; $linenr < $end_line; $linenr++) { 652 for (my $linenr = $first_line; $linenr < $end_line; $linenr++) {
652 my $line = $rawlines[$linenr - 1]; 653 my $line = $rawlines[$linenr - 1];
653 #warn " $line\n"; 654 #warn " $line\n";
654 if ($linenr == $first_line and $line =~ m@^.\s*\*@) { 655 if ($linenr == $first_line and $line =~ m@^.\s*\*@) {
655 $in_comment = 1; 656 $in_comment = 1;
656 } 657 }
657 if ($line =~ m@/\*@) { 658 if ($line =~ m@/\*@) {
658 $in_comment = 1; 659 $in_comment = 1;
659 } 660 }
660 if (!$in_comment && $current_comment ne '') { 661 if (!$in_comment && $current_comment ne '') {
661 $current_comment = ''; 662 $current_comment = '';
662 } 663 }
663 $current_comment .= $line . "\n" if ($in_comment); 664 $current_comment .= $line . "\n" if ($in_comment);
664 if ($line =~ m@\*/@) { 665 if ($line =~ m@\*/@) {
665 $in_comment = 0; 666 $in_comment = 0;
666 } 667 }
667 } 668 }
668 669
669 chomp($current_comment); 670 chomp($current_comment);
670 return($current_comment); 671 return($current_comment);
671 } 672 }
672 sub ctx_has_comment { 673 sub ctx_has_comment {
673 my ($first_line, $end_line) = @_; 674 my ($first_line, $end_line) = @_;
674 my $cmt = ctx_locate_comment($first_line, $end_line); 675 my $cmt = ctx_locate_comment($first_line, $end_line);
675 676
676 ##print "LINE: $rawlines[$end_line - 1 ]\n"; 677 ##print "LINE: $rawlines[$end_line - 1 ]\n";
677 ##print "CMMT: $cmt\n"; 678 ##print "CMMT: $cmt\n";
678 679
679 return ($cmt ne ''); 680 return ($cmt ne '');
680 } 681 }
681 682
682 sub raw_line { 683 sub raw_line {
683 my ($linenr, $cnt) = @_; 684 my ($linenr, $cnt) = @_;
684 685
685 my $offset = $linenr - 1; 686 my $offset = $linenr - 1;
686 $cnt++; 687 $cnt++;
687 688
688 my $line; 689 my $line;
689 while ($cnt) { 690 while ($cnt) {
690 $line = $rawlines[$offset++]; 691 $line = $rawlines[$offset++];
691 next if (defined($line) && $line =~ /^-/); 692 next if (defined($line) && $line =~ /^-/);
692 $cnt--; 693 $cnt--;
693 } 694 }
694 695
695 return $line; 696 return $line;
696 } 697 }
697 698
698 sub cat_vet { 699 sub cat_vet {
699 my ($vet) = @_; 700 my ($vet) = @_;
700 my ($res, $coded); 701 my ($res, $coded);
701 702
702 $res = ''; 703 $res = '';
703 while ($vet =~ /([^[:cntrl:]]*)([[:cntrl:]]|$)/g) { 704 while ($vet =~ /([^[:cntrl:]]*)([[:cntrl:]]|$)/g) {
704 $res .= $1; 705 $res .= $1;
705 if ($2 ne '') { 706 if ($2 ne '') {
706 $coded = sprintf("^%c", unpack('C', $2) + 64); 707 $coded = sprintf("^%c", unpack('C', $2) + 64);
707 $res .= $coded; 708 $res .= $coded;
708 } 709 }
709 } 710 }
710 $res =~ s/$/\$/; 711 $res =~ s/$/\$/;
711 712
712 return $res; 713 return $res;
713 } 714 }
714 715
715 my $av_preprocessor = 0; 716 my $av_preprocessor = 0;
716 my $av_pending; 717 my $av_pending;
717 my @av_paren_type; 718 my @av_paren_type;
718 my $av_pend_colon; 719 my $av_pend_colon;
719 720
720 sub annotate_reset { 721 sub annotate_reset {
721 $av_preprocessor = 0; 722 $av_preprocessor = 0;
722 $av_pending = '_'; 723 $av_pending = '_';
723 @av_paren_type = ('E'); 724 @av_paren_type = ('E');
724 $av_pend_colon = 'O'; 725 $av_pend_colon = 'O';
725 } 726 }
726 727
727 sub annotate_values { 728 sub annotate_values {
728 my ($stream, $type) = @_; 729 my ($stream, $type) = @_;
729 730
730 my $res; 731 my $res;
731 my $var = '_' x length($stream); 732 my $var = '_' x length($stream);
732 my $cur = $stream; 733 my $cur = $stream;
733 734
734 print "$stream\n" if ($dbg_values > 1); 735 print "$stream\n" if ($dbg_values > 1);
735 736
736 while (length($cur)) { 737 while (length($cur)) {
737 @av_paren_type = ('E') if ($#av_paren_type < 0); 738 @av_paren_type = ('E') if ($#av_paren_type < 0);
738 print " <" . join('', @av_paren_type) . 739 print " <" . join('', @av_paren_type) .
739 "> <$type> <$av_pending>" if ($dbg_values > 1); 740 "> <$type> <$av_pending>" if ($dbg_values > 1);
740 if ($cur =~ /^(\s+)/o) { 741 if ($cur =~ /^(\s+)/o) {
741 print "WS($1)\n" if ($dbg_values > 1); 742 print "WS($1)\n" if ($dbg_values > 1);
742 if ($1 =~ /\n/ && $av_preprocessor) { 743 if ($1 =~ /\n/ && $av_preprocessor) {
743 $type = pop(@av_paren_type); 744 $type = pop(@av_paren_type);
744 $av_preprocessor = 0; 745 $av_preprocessor = 0;
745 } 746 }
746 747
747 } elsif ($cur =~ /^($Type)\s*(?:$Ident|,|\)|\()/) { 748 } elsif ($cur =~ /^($Type)\s*(?:$Ident|,|\)|\()/) {
748 print "DECLARE($1)\n" if ($dbg_values > 1); 749 print "DECLARE($1)\n" if ($dbg_values > 1);
749 $type = 'T'; 750 $type = 'T';
750 751
751 } elsif ($cur =~ /^($Modifier)\s*/) { 752 } elsif ($cur =~ /^($Modifier)\s*/) {
752 print "MODIFIER($1)\n" if ($dbg_values > 1); 753 print "MODIFIER($1)\n" if ($dbg_values > 1);
753 $type = 'T'; 754 $type = 'T';
754 755
755 } elsif ($cur =~ /^(\#\s*define\s*$Ident)(\(?)/o) { 756 } elsif ($cur =~ /^(\#\s*define\s*$Ident)(\(?)/o) {
756 print "DEFINE($1,$2)\n" if ($dbg_values > 1); 757 print "DEFINE($1,$2)\n" if ($dbg_values > 1);
757 $av_preprocessor = 1; 758 $av_preprocessor = 1;
758 push(@av_paren_type, $type); 759 push(@av_paren_type, $type);
759 if ($2 ne '') { 760 if ($2 ne '') {
760 $av_pending = 'N'; 761 $av_pending = 'N';
761 } 762 }
762 $type = 'E'; 763 $type = 'E';
763 764
764 } elsif ($cur =~ /^(\#\s*(?:undef\s*$Ident|include\b))/o) { 765 } elsif ($cur =~ /^(\#\s*(?:undef\s*$Ident|include\b))/o) {
765 print "UNDEF($1)\n" if ($dbg_values > 1); 766 print "UNDEF($1)\n" if ($dbg_values > 1);
766 $av_preprocessor = 1; 767 $av_preprocessor = 1;
767 push(@av_paren_type, $type); 768 push(@av_paren_type, $type);
768 769
769 } elsif ($cur =~ /^(\#\s*(?:ifdef|ifndef|if))/o) { 770 } elsif ($cur =~ /^(\#\s*(?:ifdef|ifndef|if))/o) {
770 print "PRE_START($1)\n" if ($dbg_values > 1); 771 print "PRE_START($1)\n" if ($dbg_values > 1);
771 $av_preprocessor = 1; 772 $av_preprocessor = 1;
772 773
773 push(@av_paren_type, $type); 774 push(@av_paren_type, $type);
774 push(@av_paren_type, $type); 775 push(@av_paren_type, $type);
775 $type = 'E'; 776 $type = 'E';
776 777
777 } elsif ($cur =~ /^(\#\s*(?:else|elif))/o) { 778 } elsif ($cur =~ /^(\#\s*(?:else|elif))/o) {
778 print "PRE_RESTART($1)\n" if ($dbg_values > 1); 779 print "PRE_RESTART($1)\n" if ($dbg_values > 1);
779 $av_preprocessor = 1; 780 $av_preprocessor = 1;
780 781
781 push(@av_paren_type, $av_paren_type[$#av_paren_type]); 782 push(@av_paren_type, $av_paren_type[$#av_paren_type]);
782 783
783 $type = 'E'; 784 $type = 'E';
784 785
785 } elsif ($cur =~ /^(\#\s*(?:endif))/o) { 786 } elsif ($cur =~ /^(\#\s*(?:endif))/o) {
786 print "PRE_END($1)\n" if ($dbg_values > 1); 787 print "PRE_END($1)\n" if ($dbg_values > 1);
787 788
788 $av_preprocessor = 1; 789 $av_preprocessor = 1;
789 790
790 # Assume all arms of the conditional end as this 791 # Assume all arms of the conditional end as this
791 # one does, and continue as if the #endif was not here. 792 # one does, and continue as if the #endif was not here.
792 pop(@av_paren_type); 793 pop(@av_paren_type);
793 push(@av_paren_type, $type); 794 push(@av_paren_type, $type);
794 $type = 'E'; 795 $type = 'E';
795 796
796 } elsif ($cur =~ /^(\\\n)/o) { 797 } elsif ($cur =~ /^(\\\n)/o) {
797 print "PRECONT($1)\n" if ($dbg_values > 1); 798 print "PRECONT($1)\n" if ($dbg_values > 1);
798 799
799 } elsif ($cur =~ /^(__attribute__)\s*\(?/o) { 800 } elsif ($cur =~ /^(__attribute__)\s*\(?/o) {
800 print "ATTR($1)\n" if ($dbg_values > 1); 801 print "ATTR($1)\n" if ($dbg_values > 1);
801 $av_pending = $type; 802 $av_pending = $type;
802 $type = 'N'; 803 $type = 'N';
803 804
804 } elsif ($cur =~ /^(sizeof)\s*(\()?/o) { 805 } elsif ($cur =~ /^(sizeof)\s*(\()?/o) {
805 print "SIZEOF($1)\n" if ($dbg_values > 1); 806 print "SIZEOF($1)\n" if ($dbg_values > 1);
806 if (defined $2) { 807 if (defined $2) {
807 $av_pending = 'V'; 808 $av_pending = 'V';
808 } 809 }
809 $type = 'N'; 810 $type = 'N';
810 811
811 } elsif ($cur =~ /^(if|while|for)\b/o) { 812 } elsif ($cur =~ /^(if|while|for)\b/o) {
812 print "COND($1)\n" if ($dbg_values > 1); 813 print "COND($1)\n" if ($dbg_values > 1);
813 $av_pending = 'E'; 814 $av_pending = 'E';
814 $type = 'N'; 815 $type = 'N';
815 816
816 } elsif ($cur =~/^(case)/o) { 817 } elsif ($cur =~/^(case)/o) {
817 print "CASE($1)\n" if ($dbg_values > 1); 818 print "CASE($1)\n" if ($dbg_values > 1);
818 $av_pend_colon = 'C'; 819 $av_pend_colon = 'C';
819 $type = 'N'; 820 $type = 'N';
820 821
821 } elsif ($cur =~/^(return|else|goto|typeof|__typeof__)\b/o) { 822 } elsif ($cur =~/^(return|else|goto|typeof|__typeof__)\b/o) {
822 print "KEYWORD($1)\n" if ($dbg_values > 1); 823 print "KEYWORD($1)\n" if ($dbg_values > 1);
823 $type = 'N'; 824 $type = 'N';
824 825
825 } elsif ($cur =~ /^(\()/o) { 826 } elsif ($cur =~ /^(\()/o) {
826 print "PAREN('$1')\n" if ($dbg_values > 1); 827 print "PAREN('$1')\n" if ($dbg_values > 1);
827 push(@av_paren_type, $av_pending); 828 push(@av_paren_type, $av_pending);
828 $av_pending = '_'; 829 $av_pending = '_';
829 $type = 'N'; 830 $type = 'N';
830 831
831 } elsif ($cur =~ /^(\))/o) { 832 } elsif ($cur =~ /^(\))/o) {
832 my $new_type = pop(@av_paren_type); 833 my $new_type = pop(@av_paren_type);
833 if ($new_type ne '_') { 834 if ($new_type ne '_') {
834 $type = $new_type; 835 $type = $new_type;
835 print "PAREN('$1') -> $type\n" 836 print "PAREN('$1') -> $type\n"
836 if ($dbg_values > 1); 837 if ($dbg_values > 1);
837 } else { 838 } else {
838 print "PAREN('$1')\n" if ($dbg_values > 1); 839 print "PAREN('$1')\n" if ($dbg_values > 1);
839 } 840 }
840 841
841 } elsif ($cur =~ /^($Ident)\s*\(/o) { 842 } elsif ($cur =~ /^($Ident)\s*\(/o) {
842 print "FUNC($1)\n" if ($dbg_values > 1); 843 print "FUNC($1)\n" if ($dbg_values > 1);
843 $type = 'V'; 844 $type = 'V';
844 $av_pending = 'V'; 845 $av_pending = 'V';
845 846
846 } elsif ($cur =~ /^($Ident\s*):/) { 847 } elsif ($cur =~ /^($Ident\s*):/) {
847 if ($type eq 'E') { 848 if ($type eq 'E') {
848 $av_pend_colon = 'L'; 849 $av_pend_colon = 'L';
849 } elsif ($type eq 'T') { 850 } elsif ($type eq 'T') {
850 $av_pend_colon = 'B'; 851 $av_pend_colon = 'B';
851 } 852 }
852 print "IDENT_COLON($1,$type>$av_pend_colon)\n" if ($dbg_values > 1); 853 print "IDENT_COLON($1,$type>$av_pend_colon)\n" if ($dbg_values > 1);
853 $type = 'V'; 854 $type = 'V';
854 855
855 } elsif ($cur =~ /^($Ident|$Constant)/o) { 856 } elsif ($cur =~ /^($Ident|$Constant)/o) {
856 print "IDENT($1)\n" if ($dbg_values > 1); 857 print "IDENT($1)\n" if ($dbg_values > 1);
857 $type = 'V'; 858 $type = 'V';
858 859
859 } elsif ($cur =~ /^($Assignment)/o) { 860 } elsif ($cur =~ /^($Assignment)/o) {
860 print "ASSIGN($1)\n" if ($dbg_values > 1); 861 print "ASSIGN($1)\n" if ($dbg_values > 1);
861 $type = 'N'; 862 $type = 'N';
862 863
863 } elsif ($cur =~/^(;|{|})/) { 864 } elsif ($cur =~/^(;|{|})/) {
864 print "END($1)\n" if ($dbg_values > 1); 865 print "END($1)\n" if ($dbg_values > 1);
865 $type = 'E'; 866 $type = 'E';
866 $av_pend_colon = 'O'; 867 $av_pend_colon = 'O';
867 868
868 } elsif ($cur =~ /^(\?)/o) { 869 } elsif ($cur =~ /^(\?)/o) {
869 print "QUESTION($1)\n" if ($dbg_values > 1); 870 print "QUESTION($1)\n" if ($dbg_values > 1);
870 $type = 'N'; 871 $type = 'N';
871 872
872 } elsif ($cur =~ /^(:)/o) { 873 } elsif ($cur =~ /^(:)/o) {
873 print "COLON($1,$av_pend_colon)\n" if ($dbg_values > 1); 874 print "COLON($1,$av_pend_colon)\n" if ($dbg_values > 1);
874 875
875 substr($var, length($res), 1, $av_pend_colon); 876 substr($var, length($res), 1, $av_pend_colon);
876 if ($av_pend_colon eq 'C' || $av_pend_colon eq 'L') { 877 if ($av_pend_colon eq 'C' || $av_pend_colon eq 'L') {
877 $type = 'E'; 878 $type = 'E';
878 } else { 879 } else {
879 $type = 'N'; 880 $type = 'N';
880 } 881 }
881 $av_pend_colon = 'O'; 882 $av_pend_colon = 'O';
882 883
883 } elsif ($cur =~ /^(;|\[)/o) { 884 } elsif ($cur =~ /^(;|\[)/o) {
884 print "CLOSE($1)\n" if ($dbg_values > 1); 885 print "CLOSE($1)\n" if ($dbg_values > 1);
885 $type = 'N'; 886 $type = 'N';
886 887
887 } elsif ($cur =~ /^(-(?![->])|\+(?!\+)|\*|\&\&|\&)/o) { 888 } elsif ($cur =~ /^(-(?![->])|\+(?!\+)|\*|\&\&|\&)/o) {
888 my $variant; 889 my $variant;
889 890
890 print "OPV($1)\n" if ($dbg_values > 1); 891 print "OPV($1)\n" if ($dbg_values > 1);
891 if ($type eq 'V') { 892 if ($type eq 'V') {
892 $variant = 'B'; 893 $variant = 'B';
893 } else { 894 } else {
894 $variant = 'U'; 895 $variant = 'U';
895 } 896 }
896 897
897 substr($var, length($res), 1, $variant); 898 substr($var, length($res), 1, $variant);
898 $type = 'N'; 899 $type = 'N';
899 900
900 } elsif ($cur =~ /^($Operators)/o) { 901 } elsif ($cur =~ /^($Operators)/o) {
901 print "OP($1)\n" if ($dbg_values > 1); 902 print "OP($1)\n" if ($dbg_values > 1);
902 if ($1 ne '++' && $1 ne '--') { 903 if ($1 ne '++' && $1 ne '--') {
903 $type = 'N'; 904 $type = 'N';
904 } 905 }
905 906
906 } elsif ($cur =~ /(^.)/o) { 907 } elsif ($cur =~ /(^.)/o) {
907 print "C($1)\n" if ($dbg_values > 1); 908 print "C($1)\n" if ($dbg_values > 1);
908 } 909 }
909 if (defined $1) { 910 if (defined $1) {
910 $cur = substr($cur, length($1)); 911 $cur = substr($cur, length($1));
911 $res .= $type x length($1); 912 $res .= $type x length($1);
912 } 913 }
913 } 914 }
914 915
915 return ($res, $var); 916 return ($res, $var);
916 } 917 }
917 918
918 sub possible { 919 sub possible {
919 my ($possible, $line) = @_; 920 my ($possible, $line) = @_;
920 921
921 print "CHECK<$possible> ($line)\n" if ($dbg_possible > 2); 922 print "CHECK<$possible> ($line)\n" if ($dbg_possible > 2);
922 if ($possible !~ /(?: 923 if ($possible !~ /(?:
923 ^(?: 924 ^(?:
924 $Modifier| 925 $Modifier|
925 $Storage| 926 $Storage|
926 $Type| 927 $Type|
927 DEFINE_\S+| 928 DEFINE_\S+|
928 goto| 929 goto|
929 return| 930 return|
930 case| 931 case|
931 else| 932 else|
932 asm|__asm__| 933 asm|__asm__|
933 do 934 do
934 )$| 935 )$|
935 ^(?:typedef|struct|enum)\b 936 ^(?:typedef|struct|enum)\b
936 )/x) { 937 )/x) {
937 # Check for modifiers. 938 # Check for modifiers.
938 $possible =~ s/\s*$Storage\s*//g; 939 $possible =~ s/\s*$Storage\s*//g;
939 $possible =~ s/\s*$Sparse\s*//g; 940 $possible =~ s/\s*$Sparse\s*//g;
940 if ($possible =~ /^\s*$/) { 941 if ($possible =~ /^\s*$/) {
941 942
942 } elsif ($possible =~ /\s/) { 943 } elsif ($possible =~ /\s/) {
943 $possible =~ s/\s*$Type\s*//g; 944 $possible =~ s/\s*$Type\s*//g;
944 for my $modifier (split(' ', $possible)) { 945 for my $modifier (split(' ', $possible)) {
945 warn "MODIFIER: $modifier ($possible) ($line)\n" if ($dbg_possible); 946 warn "MODIFIER: $modifier ($possible) ($line)\n" if ($dbg_possible);
946 push(@modifierList, $modifier); 947 push(@modifierList, $modifier);
947 } 948 }
948 949
949 } else { 950 } else {
950 warn "POSSIBLE: $possible ($line)\n" if ($dbg_possible); 951 warn "POSSIBLE: $possible ($line)\n" if ($dbg_possible);
951 push(@typeList, $possible); 952 push(@typeList, $possible);
952 } 953 }
953 build_types(); 954 build_types();
954 } else { 955 } else {
955 warn "NOTPOSS: $possible ($line)\n" if ($dbg_possible > 1); 956 warn "NOTPOSS: $possible ($line)\n" if ($dbg_possible > 1);
956 } 957 }
957 } 958 }
958 959
959 my $prefix = ''; 960 my $prefix = '';
960 961
961 sub report { 962 sub report {
962 if (defined $tst_only && $_[0] !~ /\Q$tst_only\E/) { 963 if (defined $tst_only && $_[0] !~ /\Q$tst_only\E/) {
963 return 0; 964 return 0;
964 } 965 }
965 my $line = $prefix . $_[0]; 966 my $line = $prefix . $_[0];
966 967
967 $line = (split('\n', $line))[0] . "\n" if ($terse); 968 $line = (split('\n', $line))[0] . "\n" if ($terse);
968 969
969 push(our @report, $line); 970 push(our @report, $line);
970 971
971 return 1; 972 return 1;
972 } 973 }
973 sub report_dump { 974 sub report_dump {
974 our @report; 975 our @report;
975 } 976 }
976 sub ERROR { 977 sub ERROR {
977 if (report("ERROR: $_[0]\n")) { 978 if (report("ERROR: $_[0]\n")) {
978 our $clean = 0; 979 our $clean = 0;
979 our $cnt_error++; 980 our $cnt_error++;
980 } 981 }
981 } 982 }
982 sub WARN { 983 sub WARN {
983 if (report("WARNING: $_[0]\n")) { 984 if (report("WARNING: $_[0]\n")) {
984 our $clean = 0; 985 our $clean = 0;
985 our $cnt_warn++; 986 our $cnt_warn++;
986 } 987 }
987 } 988 }
988 sub CHK { 989 sub CHK {
989 if ($check && report("CHECK: $_[0]\n")) { 990 if ($check && report("CHECK: $_[0]\n")) {
990 our $clean = 0; 991 our $clean = 0;
991 our $cnt_chk++; 992 our $cnt_chk++;
992 } 993 }
993 } 994 }
994 995
995 sub check_absolute_file { 996 sub check_absolute_file {
996 my ($absolute, $herecurr) = @_; 997 my ($absolute, $herecurr) = @_;
997 my $file = $absolute; 998 my $file = $absolute;
998 999
999 ##print "absolute<$absolute>\n"; 1000 ##print "absolute<$absolute>\n";
1000 1001
1001 # See if any suffix of this path is a path within the tree. 1002 # See if any suffix of this path is a path within the tree.
1002 while ($file =~ s@^[^/]*/@@) { 1003 while ($file =~ s@^[^/]*/@@) {
1003 if (-f "$root/$file") { 1004 if (-f "$root/$file") {
1004 ##print "file<$file>\n"; 1005 ##print "file<$file>\n";
1005 last; 1006 last;
1006 } 1007 }
1007 } 1008 }
1008 if (! -f _) { 1009 if (! -f _) {
1009 return 0; 1010 return 0;
1010 } 1011 }
1011 1012
1012 # It is, so see if the prefix is acceptable. 1013 # It is, so see if the prefix is acceptable.
1013 my $prefix = $absolute; 1014 my $prefix = $absolute;
1014 substr($prefix, -length($file)) = ''; 1015 substr($prefix, -length($file)) = '';
1015 1016
1016 ##print "prefix<$prefix>\n"; 1017 ##print "prefix<$prefix>\n";
1017 if ($prefix ne ".../") { 1018 if ($prefix ne ".../") {
1018 WARN("use relative pathname instead of absolute in changelog text\n" . $herecurr); 1019 WARN("use relative pathname instead of absolute in changelog text\n" . $herecurr);
1019 } 1020 }
1020 } 1021 }
1021 1022
1022 sub process { 1023 sub process {
1023 my $filename = shift; 1024 my $filename = shift;
1024 1025
1025 my $linenr=0; 1026 my $linenr=0;
1026 my $prevline=""; 1027 my $prevline="";
1027 my $prevrawline=""; 1028 my $prevrawline="";
1028 my $stashline=""; 1029 my $stashline="";
1029 my $stashrawline=""; 1030 my $stashrawline="";
1030 1031
1031 my $length; 1032 my $length;
1032 my $indent; 1033 my $indent;
1033 my $previndent=0; 1034 my $previndent=0;
1034 my $stashindent=0; 1035 my $stashindent=0;
1035 1036
1036 our $clean = 1; 1037 our $clean = 1;
1037 my $signoff = 0; 1038 my $signoff = 0;
1038 my $is_patch = 0; 1039 my $is_patch = 0;
1039 1040
1040 our @report = (); 1041 our @report = ();
1041 our $cnt_lines = 0; 1042 our $cnt_lines = 0;
1042 our $cnt_error = 0; 1043 our $cnt_error = 0;
1043 our $cnt_warn = 0; 1044 our $cnt_warn = 0;
1044 our $cnt_chk = 0; 1045 our $cnt_chk = 0;
1045 1046
1046 # Trace the real file/line as we go. 1047 # Trace the real file/line as we go.
1047 my $realfile = ''; 1048 my $realfile = '';
1048 my $realline = 0; 1049 my $realline = 0;
1049 my $realcnt = 0; 1050 my $realcnt = 0;
1050 my $here = ''; 1051 my $here = '';
1051 my $in_comment = 0; 1052 my $in_comment = 0;
1052 my $comment_edge = 0; 1053 my $comment_edge = 0;
1053 my $first_line = 0; 1054 my $first_line = 0;
1054 1055
1055 my $prev_values = 'E'; 1056 my $prev_values = 'E';
1056 1057
1057 # suppression flags 1058 # suppression flags
1058 my %suppress_ifbraces; 1059 my %suppress_ifbraces;
1059 my %suppress_whiletrailers; 1060 my %suppress_whiletrailers;
1060 1061
1061 # Pre-scan the patch sanitizing the lines. 1062 # Pre-scan the patch sanitizing the lines.
1062 # Pre-scan the patch looking for any __setup documentation. 1063 # Pre-scan the patch looking for any __setup documentation.
1063 # 1064 #
1064 my @setup_docs = (); 1065 my @setup_docs = ();
1065 my $setup_docs = 0; 1066 my $setup_docs = 0;
1066 1067
1067 sanitise_line_reset(); 1068 sanitise_line_reset();
1068 my $line; 1069 my $line;
1069 foreach my $rawline (@rawlines) { 1070 foreach my $rawline (@rawlines) {
1070 $linenr++; 1071 $linenr++;
1071 $line = $rawline; 1072 $line = $rawline;
1072 1073
1073 if ($rawline=~/^\+\+\+\s+(\S+)/) { 1074 if ($rawline=~/^\+\+\+\s+(\S+)/) {
1074 $setup_docs = 0; 1075 $setup_docs = 0;
1075 if ($1 =~ m@Documentation/kernel-parameters.txt$@) { 1076 if ($1 =~ m@Documentation/kernel-parameters.txt$@) {
1076 $setup_docs = 1; 1077 $setup_docs = 1;
1077 } 1078 }
1078 #next; 1079 #next;
1079 } 1080 }
1080 if ($rawline=~/^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@/) { 1081 if ($rawline=~/^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@/) {
1081 $realline=$1-1; 1082 $realline=$1-1;
1082 if (defined $2) { 1083 if (defined $2) {
1083 $realcnt=$3+1; 1084 $realcnt=$3+1;
1084 } else { 1085 } else {
1085 $realcnt=1+1; 1086 $realcnt=1+1;
1086 } 1087 }
1087 $in_comment = 0; 1088 $in_comment = 0;
1088 1089
1089 # Guestimate if this is a continuing comment. Run 1090 # Guestimate if this is a continuing comment. Run
1090 # the context looking for a comment "edge". If this 1091 # the context looking for a comment "edge". If this
1091 # edge is a close comment then we must be in a comment 1092 # edge is a close comment then we must be in a comment
1092 # at context start. 1093 # at context start.
1093 my $edge; 1094 my $edge;
1094 my $cnt = $realcnt; 1095 my $cnt = $realcnt;
1095 for (my $ln = $linenr + 1; $cnt > 0; $ln++) { 1096 for (my $ln = $linenr + 1; $cnt > 0; $ln++) {
1096 next if (defined $rawlines[$ln - 1] && 1097 next if (defined $rawlines[$ln - 1] &&
1097 $rawlines[$ln - 1] =~ /^-/); 1098 $rawlines[$ln - 1] =~ /^-/);
1098 $cnt--; 1099 $cnt--;
1099 #print "RAW<$rawlines[$ln - 1]>\n"; 1100 #print "RAW<$rawlines[$ln - 1]>\n";
1100 last if (!defined $rawlines[$ln - 1]); 1101 last if (!defined $rawlines[$ln - 1]);
1101 ($edge) = ($rawlines[$ln - 1] =~ m@(/\*|\*/)@); 1102 ($edge) = ($rawlines[$ln - 1] =~ m@(/\*|\*/)@);
1102 last if (defined $edge); 1103 last if (defined $edge);
1103 } 1104 }
1104 if (defined $edge && $edge eq '*/') { 1105 if (defined $edge && $edge eq '*/') {
1105 $in_comment = 1; 1106 $in_comment = 1;
1106 } 1107 }
1107 1108
1108 # Guestimate if this is a continuing comment. If this 1109 # Guestimate if this is a continuing comment. If this
1109 # is the start of a diff block and this line starts 1110 # is the start of a diff block and this line starts
1110 # ' *' then it is very likely a comment. 1111 # ' *' then it is very likely a comment.
1111 if (!defined $edge && 1112 if (!defined $edge &&
1112 $rawlines[$linenr] =~ m@^.\s*(?:\*\*+| \*)(?:\s|$)@) 1113 $rawlines[$linenr] =~ m@^.\s*(?:\*\*+| \*)(?:\s|$)@)
1113 { 1114 {
1114 $in_comment = 1; 1115 $in_comment = 1;
1115 } 1116 }
1116 1117
1117 ##print "COMMENT:$in_comment edge<$edge> $rawline\n"; 1118 ##print "COMMENT:$in_comment edge<$edge> $rawline\n";
1118 sanitise_line_reset($in_comment); 1119 sanitise_line_reset($in_comment);
1119 1120
1120 } elsif ($realcnt && $rawline =~ /^(?:\+| |$)/) { 1121 } elsif ($realcnt && $rawline =~ /^(?:\+| |$)/) {
1121 # Standardise the strings and chars within the input to 1122 # Standardise the strings and chars within the input to
1122 # simplify matching -- only bother with positive lines. 1123 # simplify matching -- only bother with positive lines.
1123 $line = sanitise_line($rawline); 1124 $line = sanitise_line($rawline);
1124 } 1125 }
1125 push(@lines, $line); 1126 push(@lines, $line);
1126 1127
1127 if ($realcnt > 1) { 1128 if ($realcnt > 1) {
1128 $realcnt-- if ($line =~ /^(?:\+| |$)/); 1129 $realcnt-- if ($line =~ /^(?:\+| |$)/);
1129 } else { 1130 } else {
1130 $realcnt = 0; 1131 $realcnt = 0;
1131 } 1132 }
1132 1133
1133 #print "==>$rawline\n"; 1134 #print "==>$rawline\n";
1134 #print "-->$line\n"; 1135 #print "-->$line\n";
1135 1136
1136 if ($setup_docs && $line =~ /^\+/) { 1137 if ($setup_docs && $line =~ /^\+/) {
1137 push(@setup_docs, $line); 1138 push(@setup_docs, $line);
1138 } 1139 }
1139 } 1140 }
1140 1141
1141 $prefix = ''; 1142 $prefix = '';
1142 1143
1143 $realcnt = 0; 1144 $realcnt = 0;
1144 $linenr = 0; 1145 $linenr = 0;
1145 foreach my $line (@lines) { 1146 foreach my $line (@lines) {
1146 $linenr++; 1147 $linenr++;
1147 1148
1148 my $rawline = $rawlines[$linenr - 1]; 1149 my $rawline = $rawlines[$linenr - 1];
1149 my $hunk_line = ($realcnt != 0); 1150 my $hunk_line = ($realcnt != 0);
1150 1151
1151 #extract the line range in the file after the patch is applied 1152 #extract the line range in the file after the patch is applied
1152 if ($line=~/^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@/) { 1153 if ($line=~/^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@/) {
1153 $is_patch = 1; 1154 $is_patch = 1;
1154 $first_line = $linenr + 1; 1155 $first_line = $linenr + 1;
1155 $realline=$1-1; 1156 $realline=$1-1;
1156 if (defined $2) { 1157 if (defined $2) {
1157 $realcnt=$3+1; 1158 $realcnt=$3+1;
1158 } else { 1159 } else {
1159 $realcnt=1+1; 1160 $realcnt=1+1;
1160 } 1161 }
1161 annotate_reset(); 1162 annotate_reset();
1162 $prev_values = 'E'; 1163 $prev_values = 'E';
1163 1164
1164 %suppress_ifbraces = (); 1165 %suppress_ifbraces = ();
1165 %suppress_whiletrailers = (); 1166 %suppress_whiletrailers = ();
1166 next; 1167 next;
1167 1168
1168 # track the line number as we move through the hunk, note that 1169 # track the line number as we move through the hunk, note that
1169 # new versions of GNU diff omit the leading space on completely 1170 # new versions of GNU diff omit the leading space on completely
1170 # blank context lines so we need to count that too. 1171 # blank context lines so we need to count that too.
1171 } elsif ($line =~ /^( |\+|$)/) { 1172 } elsif ($line =~ /^( |\+|$)/) {
1172 $realline++; 1173 $realline++;
1173 $realcnt-- if ($realcnt != 0); 1174 $realcnt-- if ($realcnt != 0);
1174 1175
1175 # Measure the line length and indent. 1176 # Measure the line length and indent.
1176 ($length, $indent) = line_stats($rawline); 1177 ($length, $indent) = line_stats($rawline);
1177 1178
1178 # Track the previous line. 1179 # Track the previous line.
1179 ($prevline, $stashline) = ($stashline, $line); 1180 ($prevline, $stashline) = ($stashline, $line);
1180 ($previndent, $stashindent) = ($stashindent, $indent); 1181 ($previndent, $stashindent) = ($stashindent, $indent);
1181 ($prevrawline, $stashrawline) = ($stashrawline, $rawline); 1182 ($prevrawline, $stashrawline) = ($stashrawline, $rawline);
1182 1183
1183 #warn "line<$line>\n"; 1184 #warn "line<$line>\n";
1184 1185
1185 } elsif ($realcnt == 1) { 1186 } elsif ($realcnt == 1) {
1186 $realcnt--; 1187 $realcnt--;
1187 } 1188 }
1188 1189
1189 #make up the handle for any error we report on this line 1190 #make up the handle for any error we report on this line
1190 $prefix = "$filename:$realline: " if ($emacs && $file); 1191 $prefix = "$filename:$realline: " if ($emacs && $file);
1191 $prefix = "$filename:$linenr: " if ($emacs && !$file); 1192 $prefix = "$filename:$linenr: " if ($emacs && !$file);
1192 1193
1193 $here = "#$linenr: " if (!$file); 1194 $here = "#$linenr: " if (!$file);
1194 $here = "#$realline: " if ($file); 1195 $here = "#$realline: " if ($file);
1195 1196
1196 # extract the filename as it passes 1197 # extract the filename as it passes
1197 if ($line=~/^\+\+\+\s+(\S+)/) { 1198 if ($line=~/^\+\+\+\s+(\S+)/) {
1198 $realfile = $1; 1199 $realfile = $1;
1199 $realfile =~ s@^[^/]*/@@; 1200 $realfile =~ s@^[^/]*/@@;
1200 1201
1201 if ($realfile =~ m@^include/asm/@) { 1202 if ($realfile =~ m@^include/asm/@) {
1202 ERROR("do not modify files in include/asm, change architecture specific files in include/asm-<architecture>\n" . "$here$rawline\n"); 1203 ERROR("do not modify files in include/asm, change architecture specific files in include/asm-<architecture>\n" . "$here$rawline\n");
1203 } 1204 }
1204 next; 1205 next;
1205 } 1206 }
1206 1207
1207 $here .= "FILE: $realfile:$realline:" if ($realcnt != 0); 1208 $here .= "FILE: $realfile:$realline:" if ($realcnt != 0);
1208 1209
1209 my $hereline = "$here\n$rawline\n"; 1210 my $hereline = "$here\n$rawline\n";
1210 my $herecurr = "$here\n$rawline\n"; 1211 my $herecurr = "$here\n$rawline\n";
1211 my $hereprev = "$here\n$prevrawline\n$rawline\n"; 1212 my $hereprev = "$here\n$prevrawline\n$rawline\n";
1212 1213
1213 $cnt_lines++ if ($realcnt != 0); 1214 $cnt_lines++ if ($realcnt != 0);
1214 1215
1215 #check the patch for a signoff: 1216 #check the patch for a signoff:
1216 if ($line =~ /^\s*signed-off-by:/i) { 1217 if ($line =~ /^\s*signed-off-by:/i) {
1217 # This is a signoff, if ugly, so do not double report. 1218 # This is a signoff, if ugly, so do not double report.
1218 $signoff++; 1219 $signoff++;
1219 if (!($line =~ /^\s*Signed-off-by:/)) { 1220 if (!($line =~ /^\s*Signed-off-by:/)) {
1220 WARN("Signed-off-by: is the preferred form\n" . 1221 WARN("Signed-off-by: is the preferred form\n" .
1221 $herecurr); 1222 $herecurr);
1222 } 1223 }
1223 if ($line =~ /^\s*signed-off-by:\S/i) { 1224 if ($line =~ /^\s*signed-off-by:\S/i) {
1224 WARN("space required after Signed-off-by:\n" . 1225 WARN("space required after Signed-off-by:\n" .
1225 $herecurr); 1226 $herecurr);
1226 } 1227 }
1227 } 1228 }
1228 1229
1229 # Check for wrappage within a valid hunk of the file 1230 # Check for wrappage within a valid hunk of the file
1230 if ($realcnt != 0 && $line !~ m{^(?:\+|-| |\\ No newline|$)}) { 1231 if ($realcnt != 0 && $line !~ m{^(?:\+|-| |\\ No newline|$)}) {
1231 ERROR("patch seems to be corrupt (line wrapped?)\n" . 1232 ERROR("patch seems to be corrupt (line wrapped?)\n" .
1232 $herecurr) if (!$emitted_corrupt++); 1233 $herecurr) if (!$emitted_corrupt++);
1233 } 1234 }
1234 1235
1235 # Check for absolute kernel paths. 1236 # Check for absolute kernel paths.
1236 if ($tree) { 1237 if ($tree) {
1237 while ($line =~ m{(?:^|\s)(/\S*)}g) { 1238 while ($line =~ m{(?:^|\s)(/\S*)}g) {
1238 my $file = $1; 1239 my $file = $1;
1239 1240
1240 if ($file =~ m{^(.*?)(?::\d+)+:?$} && 1241 if ($file =~ m{^(.*?)(?::\d+)+:?$} &&
1241 check_absolute_file($1, $herecurr)) { 1242 check_absolute_file($1, $herecurr)) {
1242 # 1243 #
1243 } else { 1244 } else {
1244 check_absolute_file($file, $herecurr); 1245 check_absolute_file($file, $herecurr);
1245 } 1246 }
1246 } 1247 }
1247 } 1248 }
1248 1249
1249 # UTF-8 regex found at http://www.w3.org/International/questions/qa-forms-utf-8.en.php 1250 # UTF-8 regex found at http://www.w3.org/International/questions/qa-forms-utf-8.en.php
1250 if (($realfile =~ /^$/ || $line =~ /^\+/) && 1251 if (($realfile =~ /^$/ || $line =~ /^\+/) &&
1251 $rawline !~ m/^$UTF8*$/) { 1252 $rawline !~ m/^$UTF8*$/) {
1252 my ($utf8_prefix) = ($rawline =~ /^($UTF8*)/); 1253 my ($utf8_prefix) = ($rawline =~ /^($UTF8*)/);
1253 1254
1254 my $blank = copy_spacing($rawline); 1255 my $blank = copy_spacing($rawline);
1255 my $ptr = substr($blank, 0, length($utf8_prefix)) . "^"; 1256 my $ptr = substr($blank, 0, length($utf8_prefix)) . "^";
1256 my $hereptr = "$hereline$ptr\n"; 1257 my $hereptr = "$hereline$ptr\n";
1257 1258
1258 ERROR("Invalid UTF-8, patch and commit message should be encoded in UTF-8\n" . $hereptr); 1259 ERROR("Invalid UTF-8, patch and commit message should be encoded in UTF-8\n" . $hereptr);
1259 } 1260 }
1260 1261
1261 # ignore non-hunk lines and lines being removed 1262 # ignore non-hunk lines and lines being removed
1262 next if (!$hunk_line || $line =~ /^-/); 1263 next if (!$hunk_line || $line =~ /^-/);
1263 1264
1264 #trailing whitespace 1265 #trailing whitespace
1265 if ($line =~ /^\+.*\015/) { 1266 if ($line =~ /^\+.*\015/) {
1266 my $herevet = "$here\n" . cat_vet($rawline) . "\n"; 1267 my $herevet = "$here\n" . cat_vet($rawline) . "\n";
1267 ERROR("DOS line endings\n" . $herevet); 1268 ERROR("DOS line endings\n" . $herevet);
1268 1269
1269 } elsif ($rawline =~ /^\+.*\S\s+$/ || $rawline =~ /^\+\s+$/) { 1270 } elsif ($rawline =~ /^\+.*\S\s+$/ || $rawline =~ /^\+\s+$/) {
1270 my $herevet = "$here\n" . cat_vet($rawline) . "\n"; 1271 my $herevet = "$here\n" . cat_vet($rawline) . "\n";
1271 ERROR("trailing whitespace\n" . $herevet); 1272 ERROR("trailing whitespace\n" . $herevet);
1272 } 1273 }
1273 1274
1274 # check we are in a valid source file if not then ignore this hunk 1275 # check we are in a valid source file if not then ignore this hunk
1275 next if ($realfile !~ /\.(h|c|s|S|pl|sh)$/); 1276 next if ($realfile !~ /\.(h|c|s|S|pl|sh)$/);
1276 1277
1277 #80 column limit 1278 #80 column limit
1278 if ($line =~ /^\+/ && $prevrawline !~ /\/\*\*/ && 1279 if ($line =~ /^\+/ && $prevrawline !~ /\/\*\*/ &&
1279 $rawline !~ /^.\s*\*\s*\@$Ident\s/ && 1280 $rawline !~ /^.\s*\*\s*\@$Ident\s/ &&
1280 $line !~ /^\+\s*printk\s*\(\s*(?:KERN_\S+\s*)?"[X\t]*"\s*(?:,|\)\s*;)\s*$/ && 1281 $line !~ /^\+\s*printk\s*\(\s*(?:KERN_\S+\s*)?"[X\t]*"\s*(?:,|\)\s*;)\s*$/ &&
1281 $length > 80) 1282 $length > 80)
1282 { 1283 {
1283 WARN("line over 80 characters\n" . $herecurr); 1284 WARN("line over 80 characters\n" . $herecurr);
1284 } 1285 }
1285 1286
1286 # check for adding lines without a newline. 1287 # check for adding lines without a newline.
1287 if ($line =~ /^\+/ && defined $lines[$linenr] && $lines[$linenr] =~ /^\\ No newline at end of file/) { 1288 if ($line =~ /^\+/ && defined $lines[$linenr] && $lines[$linenr] =~ /^\\ No newline at end of file/) {
1288 WARN("adding a line without newline at end of file\n" . $herecurr); 1289 WARN("adding a line without newline at end of file\n" . $herecurr);
1289 } 1290 }
1290 1291
1291 # check we are in a valid source file C or perl if not then ignore this hunk 1292 # check we are in a valid source file C or perl if not then ignore this hunk
1292 next if ($realfile !~ /\.(h|c|pl)$/); 1293 next if ($realfile !~ /\.(h|c|pl)$/);
1293 1294
1294 # at the beginning of a line any tabs must come first and anything 1295 # at the beginning of a line any tabs must come first and anything
1295 # more than 8 must use tabs. 1296 # more than 8 must use tabs.
1296 if ($rawline =~ /^\+\s* \t\s*\S/ || 1297 if ($rawline =~ /^\+\s* \t\s*\S/ ||
1297 $rawline =~ /^\+\s* \s*/) { 1298 $rawline =~ /^\+\s* \s*/) {
1298 my $herevet = "$here\n" . cat_vet($rawline) . "\n"; 1299 my $herevet = "$here\n" . cat_vet($rawline) . "\n";
1299 ERROR("code indent should use tabs where possible\n" . $herevet); 1300 ERROR("code indent should use tabs where possible\n" . $herevet);
1300 } 1301 }
1301 1302
1302 # check we are in a valid C source file if not then ignore this hunk 1303 # check we are in a valid C source file if not then ignore this hunk
1303 next if ($realfile !~ /\.(h|c)$/); 1304 next if ($realfile !~ /\.(h|c)$/);
1304 1305
1305 # check for RCS/CVS revision markers 1306 # check for RCS/CVS revision markers
1306 if ($rawline =~ /^\+.*\$(Revision|Log|Id)(?:\$|)/) { 1307 if ($rawline =~ /^\+.*\$(Revision|Log|Id)(?:\$|)/) {
1307 WARN("CVS style keyword markers, these will _not_ be updated\n". $herecurr); 1308 WARN("CVS style keyword markers, these will _not_ be updated\n". $herecurr);
1308 } 1309 }
1309 1310
1310 # Check for potential 'bare' types 1311 # Check for potential 'bare' types
1311 my ($stat, $cond, $line_nr_next, $remain_next, $off_next); 1312 my ($stat, $cond, $line_nr_next, $remain_next, $off_next);
1312 if ($realcnt && $line =~ /.\s*\S/) { 1313 if ($realcnt && $line =~ /.\s*\S/) {
1313 ($stat, $cond, $line_nr_next, $remain_next, $off_next) = 1314 ($stat, $cond, $line_nr_next, $remain_next, $off_next) =
1314 ctx_statement_block($linenr, $realcnt, 0); 1315 ctx_statement_block($linenr, $realcnt, 0);
1315 $stat =~ s/\n./\n /g; 1316 $stat =~ s/\n./\n /g;
1316 $cond =~ s/\n./\n /g; 1317 $cond =~ s/\n./\n /g;
1317 1318
1318 my $s = $stat; 1319 my $s = $stat;
1319 $s =~ s/{.*$//s; 1320 $s =~ s/{.*$//s;
1320 1321
1321 # Ignore goto labels. 1322 # Ignore goto labels.
1322 if ($s =~ /$Ident:\*$/s) { 1323 if ($s =~ /$Ident:\*$/s) {
1323 1324
1324 # Ignore functions being called 1325 # Ignore functions being called
1325 } elsif ($s =~ /^.\s*$Ident\s*\(/s) { 1326 } elsif ($s =~ /^.\s*$Ident\s*\(/s) {
1326 1327
1327 # declarations always start with types 1328 # declarations always start with types
1328 } elsif ($prev_values eq 'E' && $s =~ /^.\s*(?:$Storage\s+)?(?:$Inline\s+)?(?:const\s+)?((?:\s*$Ident)+?)\b(?:\s+$Sparse)?\s*\**\s*(?:$Ident|\(\*[^\)]*\))(?:\s*$Modifier)?\s*(?:;|=|,|\()/s) { 1329 } elsif ($prev_values eq 'E' && $s =~ /^.\s*(?:$Storage\s+)?(?:$Inline\s+)?(?:const\s+)?((?:\s*$Ident)+?)\b(?:\s+$Sparse)?\s*\**\s*(?:$Ident|\(\*[^\)]*\))(?:\s*$Modifier)?\s*(?:;|=|,|\()/s) {
1329 my $type = $1; 1330 my $type = $1;
1330 $type =~ s/\s+/ /g; 1331 $type =~ s/\s+/ /g;
1331 possible($type, "A:" . $s); 1332 possible($type, "A:" . $s);
1332 1333
1333 # definitions in global scope can only start with types 1334 # definitions in global scope can only start with types
1334 } elsif ($s =~ /^.(?:$Storage\s+)?(?:$Inline\s+)?(?:const\s+)?($Ident)\b\s*(?!:)/s) { 1335 } elsif ($s =~ /^.(?:$Storage\s+)?(?:$Inline\s+)?(?:const\s+)?($Ident)\b\s*(?!:)/s) {
1335 possible($1, "B:" . $s); 1336 possible($1, "B:" . $s);
1336 } 1337 }
1337 1338
1338 # any (foo ... *) is a pointer cast, and foo is a type 1339 # any (foo ... *) is a pointer cast, and foo is a type
1339 while ($s =~ /\(($Ident)(?:\s+$Sparse)*\s*\*+\s*\)/sg) { 1340 while ($s =~ /\(($Ident)(?:\s+$Sparse)*\s*\*+\s*\)/sg) {
1340 possible($1, "C:" . $s); 1341 possible($1, "C:" . $s);
1341 } 1342 }
1342 1343
1343 # Check for any sort of function declaration. 1344 # Check for any sort of function declaration.
1344 # int foo(something bar, other baz); 1345 # int foo(something bar, other baz);
1345 # void (*store_gdt)(x86_descr_ptr *); 1346 # void (*store_gdt)(x86_descr_ptr *);
1346 if ($prev_values eq 'E' && $s =~ /^(.(?:typedef\s*)?(?:(?:$Storage|$Inline)\s*)*\s*$Type\s*(?:\b$Ident|\(\*\s*$Ident\))\s*)\(/s) { 1347 if ($prev_values eq 'E' && $s =~ /^(.(?:typedef\s*)?(?:(?:$Storage|$Inline)\s*)*\s*$Type\s*(?:\b$Ident|\(\*\s*$Ident\))\s*)\(/s) {
1347 my ($name_len) = length($1); 1348 my ($name_len) = length($1);
1348 1349
1349 my $ctx = $s; 1350 my $ctx = $s;
1350 substr($ctx, 0, $name_len + 1, ''); 1351 substr($ctx, 0, $name_len + 1, '');
1351 $ctx =~ s/\)[^\)]*$//; 1352 $ctx =~ s/\)[^\)]*$//;
1352 1353
1353 for my $arg (split(/\s*,\s*/, $ctx)) { 1354 for my $arg (split(/\s*,\s*/, $ctx)) {
1354 if ($arg =~ /^(?:const\s+)?($Ident)(?:\s+$Sparse)*\s*\**\s*(:?\b$Ident)?$/s || $arg =~ /^($Ident)$/s) { 1355 if ($arg =~ /^(?:const\s+)?($Ident)(?:\s+$Sparse)*\s*\**\s*(:?\b$Ident)?$/s || $arg =~ /^($Ident)$/s) {
1355 1356
1356 possible($1, "D:" . $s); 1357 possible($1, "D:" . $s);
1357 } 1358 }
1358 } 1359 }
1359 } 1360 }
1360 1361
1361 } 1362 }
1362 1363
1363 # 1364 #
1364 # Checks which may be anchored in the context. 1365 # Checks which may be anchored in the context.
1365 # 1366 #
1366 1367
1367 # Check for switch () and associated case and default 1368 # Check for switch () and associated case and default
1368 # statements should be at the same indent. 1369 # statements should be at the same indent.
1369 if ($line=~/\bswitch\s*\(.*\)/) { 1370 if ($line=~/\bswitch\s*\(.*\)/) {
1370 my $err = ''; 1371 my $err = '';
1371 my $sep = ''; 1372 my $sep = '';
1372 my @ctx = ctx_block_outer($linenr, $realcnt); 1373 my @ctx = ctx_block_outer($linenr, $realcnt);
1373 shift(@ctx); 1374 shift(@ctx);
1374 for my $ctx (@ctx) { 1375 for my $ctx (@ctx) {
1375 my ($clen, $cindent) = line_stats($ctx); 1376 my ($clen, $cindent) = line_stats($ctx);
1376 if ($ctx =~ /^\+\s*(case\s+|default:)/ && 1377 if ($ctx =~ /^\+\s*(case\s+|default:)/ &&
1377 $indent != $cindent) { 1378 $indent != $cindent) {
1378 $err .= "$sep$ctx\n"; 1379 $err .= "$sep$ctx\n";
1379 $sep = ''; 1380 $sep = '';
1380 } else { 1381 } else {
1381 $sep = "[...]\n"; 1382 $sep = "[...]\n";
1382 } 1383 }
1383 } 1384 }
1384 if ($err ne '') { 1385 if ($err ne '') {
1385 ERROR("switch and case should be at the same indent\n$hereline$err"); 1386 ERROR("switch and case should be at the same indent\n$hereline$err");
1386 } 1387 }
1387 } 1388 }
1388 1389
1389 # if/while/etc brace do not go on next line, unless defining a do while loop, 1390 # if/while/etc brace do not go on next line, unless defining a do while loop,
1390 # or if that brace on the next line is for something else 1391 # or if that brace on the next line is for something else
1391 if ($line =~ /(.*)\b((?:if|while|for|switch)\s*\(|do\b|else\b)/ && $line !~ /^.\s*\#/) { 1392 if ($line =~ /(.*)\b((?:if|while|for|switch)\s*\(|do\b|else\b)/ && $line !~ /^.\s*\#/) {
1392 my $pre_ctx = "$1$2"; 1393 my $pre_ctx = "$1$2";
1393 1394
1394 my ($level, @ctx) = ctx_statement_level($linenr, $realcnt, 0); 1395 my ($level, @ctx) = ctx_statement_level($linenr, $realcnt, 0);
1395 my $ctx_cnt = $realcnt - $#ctx - 1; 1396 my $ctx_cnt = $realcnt - $#ctx - 1;
1396 my $ctx = join("\n", @ctx); 1397 my $ctx = join("\n", @ctx);
1397 1398
1398 my $ctx_ln = $linenr; 1399 my $ctx_ln = $linenr;
1399 my $ctx_skip = $realcnt; 1400 my $ctx_skip = $realcnt;
1400 1401
1401 while ($ctx_skip > $ctx_cnt || ($ctx_skip == $ctx_cnt && 1402 while ($ctx_skip > $ctx_cnt || ($ctx_skip == $ctx_cnt &&
1402 defined $lines[$ctx_ln - 1] && 1403 defined $lines[$ctx_ln - 1] &&
1403 $lines[$ctx_ln - 1] =~ /^-/)) { 1404 $lines[$ctx_ln - 1] =~ /^-/)) {
1404 ##print "SKIP<$ctx_skip> CNT<$ctx_cnt>\n"; 1405 ##print "SKIP<$ctx_skip> CNT<$ctx_cnt>\n";
1405 $ctx_skip-- if (!defined $lines[$ctx_ln - 1] || $lines[$ctx_ln - 1] !~ /^-/); 1406 $ctx_skip-- if (!defined $lines[$ctx_ln - 1] || $lines[$ctx_ln - 1] !~ /^-/);
1406 $ctx_ln++; 1407 $ctx_ln++;
1407 } 1408 }
1408 1409
1409 #print "realcnt<$realcnt> ctx_cnt<$ctx_cnt>\n"; 1410 #print "realcnt<$realcnt> ctx_cnt<$ctx_cnt>\n";
1410 #print "pre<$pre_ctx>\nline<$line>\nctx<$ctx>\nnext<$lines[$ctx_ln - 1]>\n"; 1411 #print "pre<$pre_ctx>\nline<$line>\nctx<$ctx>\nnext<$lines[$ctx_ln - 1]>\n";
1411 1412
1412 if ($ctx !~ /{\s*/ && defined($lines[$ctx_ln -1]) && $lines[$ctx_ln - 1] =~ /^\+\s*{/) { 1413 if ($ctx !~ /{\s*/ && defined($lines[$ctx_ln -1]) && $lines[$ctx_ln - 1] =~ /^\+\s*{/) {
1413 ERROR("that open brace { should be on the previous line\n" . 1414 ERROR("that open brace { should be on the previous line\n" .
1414 "$here\n$ctx\n$lines[$ctx_ln - 1]\n"); 1415 "$here\n$ctx\n$lines[$ctx_ln - 1]\n");
1415 } 1416 }
1416 if ($level == 0 && $pre_ctx !~ /}\s*while\s*\($/ && 1417 if ($level == 0 && $pre_ctx !~ /}\s*while\s*\($/ &&
1417 $ctx =~ /\)\s*\;\s*$/ && 1418 $ctx =~ /\)\s*\;\s*$/ &&
1418 defined $lines[$ctx_ln - 1]) 1419 defined $lines[$ctx_ln - 1])
1419 { 1420 {
1420 my ($nlength, $nindent) = line_stats($lines[$ctx_ln - 1]); 1421 my ($nlength, $nindent) = line_stats($lines[$ctx_ln - 1]);
1421 if ($nindent > $indent) { 1422 if ($nindent > $indent) {
1422 WARN("trailing semicolon indicates no statements, indent implies otherwise\n" . 1423 WARN("trailing semicolon indicates no statements, indent implies otherwise\n" .
1423 "$here\n$ctx\n$lines[$ctx_ln - 1]\n"); 1424 "$here\n$ctx\n$lines[$ctx_ln - 1]\n");
1424 } 1425 }
1425 } 1426 }
1426 } 1427 }
1427 1428
1428 # Check relative indent for conditionals and blocks. 1429 # Check relative indent for conditionals and blocks.
1429 if ($line =~ /\b(?:(?:if|while|for)\s*\(|do\b)/ && $line !~ /^.\s*#/ && $line !~ /\}\s*while\s*/) { 1430 if ($line =~ /\b(?:(?:if|while|for)\s*\(|do\b)/ && $line !~ /^.\s*#/ && $line !~ /\}\s*while\s*/) {
1430 my ($s, $c) = ($stat, $cond); 1431 my ($s, $c) = ($stat, $cond);
1431 1432
1432 substr($s, 0, length($c), ''); 1433 substr($s, 0, length($c), '');
1433 1434
1434 # Make sure we remove the line prefixes as we have 1435 # Make sure we remove the line prefixes as we have
1435 # none on the first line, and are going to readd them 1436 # none on the first line, and are going to readd them
1436 # where necessary. 1437 # where necessary.
1437 $s =~ s/\n./\n/gs; 1438 $s =~ s/\n./\n/gs;
1438 1439
1439 # Find out how long the conditional actually is. 1440 # Find out how long the conditional actually is.
1440 my @newlines = ($c =~ /\n/gs); 1441 my @newlines = ($c =~ /\n/gs);
1441 my $cond_lines = 1 + $#newlines; 1442 my $cond_lines = 1 + $#newlines;
1442 1443
1443 # We want to check the first line inside the block 1444 # We want to check the first line inside the block
1444 # starting at the end of the conditional, so remove: 1445 # starting at the end of the conditional, so remove:
1445 # 1) any blank line termination 1446 # 1) any blank line termination
1446 # 2) any opening brace { on end of the line 1447 # 2) any opening brace { on end of the line
1447 # 3) any do (...) { 1448 # 3) any do (...) {
1448 my $continuation = 0; 1449 my $continuation = 0;
1449 my $check = 0; 1450 my $check = 0;
1450 $s =~ s/^.*\bdo\b//; 1451 $s =~ s/^.*\bdo\b//;
1451 $s =~ s/^\s*{//; 1452 $s =~ s/^\s*{//;
1452 if ($s =~ s/^\s*\\//) { 1453 if ($s =~ s/^\s*\\//) {
1453 $continuation = 1; 1454 $continuation = 1;
1454 } 1455 }
1455 if ($s =~ s/^\s*?\n//) { 1456 if ($s =~ s/^\s*?\n//) {
1456 $check = 1; 1457 $check = 1;
1457 $cond_lines++; 1458 $cond_lines++;
1458 } 1459 }
1459 1460
1460 # Also ignore a loop construct at the end of a 1461 # Also ignore a loop construct at the end of a
1461 # preprocessor statement. 1462 # preprocessor statement.
1462 if (($prevline =~ /^.\s*#\s*define\s/ || 1463 if (($prevline =~ /^.\s*#\s*define\s/ ||
1463 $prevline =~ /\\\s*$/) && $continuation == 0) { 1464 $prevline =~ /\\\s*$/) && $continuation == 0) {
1464 $check = 0; 1465 $check = 0;
1465 } 1466 }
1466 1467
1467 my $cond_ptr = -1; 1468 my $cond_ptr = -1;
1468 $continuation = 0; 1469 $continuation = 0;
1469 while ($cond_ptr != $cond_lines) { 1470 while ($cond_ptr != $cond_lines) {
1470 $cond_ptr = $cond_lines; 1471 $cond_ptr = $cond_lines;
1471 1472
1472 # If we see an #else/#elif then the code 1473 # If we see an #else/#elif then the code
1473 # is not linear. 1474 # is not linear.
1474 if ($s =~ /^\s*\#\s*(?:else|elif)/) { 1475 if ($s =~ /^\s*\#\s*(?:else|elif)/) {
1475 $check = 0; 1476 $check = 0;
1476 } 1477 }
1477 1478
1478 # Ignore: 1479 # Ignore:
1479 # 1) blank lines, they should be at 0, 1480 # 1) blank lines, they should be at 0,
1480 # 2) preprocessor lines, and 1481 # 2) preprocessor lines, and
1481 # 3) labels. 1482 # 3) labels.
1482 if ($continuation || 1483 if ($continuation ||
1483 $s =~ /^\s*?\n/ || 1484 $s =~ /^\s*?\n/ ||
1484 $s =~ /^\s*#\s*?/ || 1485 $s =~ /^\s*#\s*?/ ||
1485 $s =~ /^\s*$Ident\s*:/) { 1486 $s =~ /^\s*$Ident\s*:/) {
1486 $continuation = ($s =~ /^.*?\\\n/) ? 1 : 0; 1487 $continuation = ($s =~ /^.*?\\\n/) ? 1 : 0;
1487 $s =~ s/^.*?\n//; 1488 $s =~ s/^.*?\n//;
1488 $cond_lines++; 1489 $cond_lines++;
1489 } 1490 }
1490 } 1491 }
1491 1492
1492 my (undef, $sindent) = line_stats("+" . $s); 1493 my (undef, $sindent) = line_stats("+" . $s);
1493 my $stat_real = raw_line($linenr, $cond_lines); 1494 my $stat_real = raw_line($linenr, $cond_lines);
1494 1495
1495 # Check if either of these lines are modified, else 1496 # Check if either of these lines are modified, else
1496 # this is not this patch's fault. 1497 # this is not this patch's fault.
1497 if (!defined($stat_real) || 1498 if (!defined($stat_real) ||
1498 $stat !~ /^\+/ && $stat_real !~ /^\+/) { 1499 $stat !~ /^\+/ && $stat_real !~ /^\+/) {
1499 $check = 0; 1500 $check = 0;
1500 } 1501 }
1501 if (defined($stat_real) && $cond_lines > 1) { 1502 if (defined($stat_real) && $cond_lines > 1) {
1502 $stat_real = "[...]\n$stat_real"; 1503 $stat_real = "[...]\n$stat_real";
1503 } 1504 }
1504 1505
1505 #print "line<$line> prevline<$prevline> indent<$indent> sindent<$sindent> check<$check> continuation<$continuation> s<$s> cond_lines<$cond_lines> stat_real<$stat_real> stat<$stat>\n"; 1506 #print "line<$line> prevline<$prevline> indent<$indent> sindent<$sindent> check<$check> continuation<$continuation> s<$s> cond_lines<$cond_lines> stat_real<$stat_real> stat<$stat>\n";
1506 1507
1507 if ($check && (($sindent % 8) != 0 || 1508 if ($check && (($sindent % 8) != 0 ||
1508 ($sindent <= $indent && $s ne ''))) { 1509 ($sindent <= $indent && $s ne ''))) {
1509 WARN("suspect code indent for conditional statements ($indent, $sindent)\n" . $herecurr . "$stat_real\n"); 1510 WARN("suspect code indent for conditional statements ($indent, $sindent)\n" . $herecurr . "$stat_real\n");
1510 } 1511 }
1511 } 1512 }
1512 1513
1513 # Track the 'values' across context and added lines. 1514 # Track the 'values' across context and added lines.
1514 my $opline = $line; $opline =~ s/^./ /; 1515 my $opline = $line; $opline =~ s/^./ /;
1515 my ($curr_values, $curr_vars) = 1516 my ($curr_values, $curr_vars) =
1516 annotate_values($opline . "\n", $prev_values); 1517 annotate_values($opline . "\n", $prev_values);
1517 $curr_values = $prev_values . $curr_values; 1518 $curr_values = $prev_values . $curr_values;
1518 if ($dbg_values) { 1519 if ($dbg_values) {
1519 my $outline = $opline; $outline =~ s/\t/ /g; 1520 my $outline = $opline; $outline =~ s/\t/ /g;
1520 print "$linenr > .$outline\n"; 1521 print "$linenr > .$outline\n";
1521 print "$linenr > $curr_values\n"; 1522 print "$linenr > $curr_values\n";
1522 print "$linenr > $curr_vars\n"; 1523 print "$linenr > $curr_vars\n";
1523 } 1524 }
1524 $prev_values = substr($curr_values, -1); 1525 $prev_values = substr($curr_values, -1);
1525 1526
1526 #ignore lines not being added 1527 #ignore lines not being added
1527 if ($line=~/^[^\+]/) {next;} 1528 if ($line=~/^[^\+]/) {next;}
1528 1529
1529 # TEST: allow direct testing of the type matcher. 1530 # TEST: allow direct testing of the type matcher.
1530 if ($dbg_type) { 1531 if ($dbg_type) {
1531 if ($line =~ /^.\s*$Declare\s*$/) { 1532 if ($line =~ /^.\s*$Declare\s*$/) {
1532 ERROR("TEST: is type\n" . $herecurr); 1533 ERROR("TEST: is type\n" . $herecurr);
1533 } elsif ($dbg_type > 1 && $line =~ /^.+($Declare)/) { 1534 } elsif ($dbg_type > 1 && $line =~ /^.+($Declare)/) {
1534 ERROR("TEST: is not type ($1 is)\n". $herecurr); 1535 ERROR("TEST: is not type ($1 is)\n". $herecurr);
1535 } 1536 }
1536 next; 1537 next;
1537 } 1538 }
1538 # TEST: allow direct testing of the attribute matcher. 1539 # TEST: allow direct testing of the attribute matcher.
1539 if ($dbg_attr) { 1540 if ($dbg_attr) {
1540 if ($line =~ /^.\s*$Attribute\s*$/) { 1541 if ($line =~ /^.\s*$Attribute\s*$/) {
1541 ERROR("TEST: is attr\n" . $herecurr); 1542 ERROR("TEST: is attr\n" . $herecurr);
1542 } elsif ($dbg_attr > 1 && $line =~ /^.+($Attribute)/) { 1543 } elsif ($dbg_attr > 1 && $line =~ /^.+($Attribute)/) {
1543 ERROR("TEST: is not attr ($1 is)\n". $herecurr); 1544 ERROR("TEST: is not attr ($1 is)\n". $herecurr);
1544 } 1545 }
1545 next; 1546 next;
1546 } 1547 }
1547 1548
1548 # check for initialisation to aggregates open brace on the next line 1549 # check for initialisation to aggregates open brace on the next line
1549 if ($prevline =~ /$Declare\s*$Ident\s*=\s*$/ && 1550 if ($prevline =~ /$Declare\s*$Ident\s*=\s*$/ &&
1550 $line =~ /^.\s*{/) { 1551 $line =~ /^.\s*{/) {
1551 ERROR("that open brace { should be on the previous line\n" . $hereprev); 1552 ERROR("that open brace { should be on the previous line\n" . $hereprev);
1552 } 1553 }
1553 1554
1554 # 1555 #
1555 # Checks which are anchored on the added line. 1556 # Checks which are anchored on the added line.
1556 # 1557 #
1557 1558
1558 # check for malformed paths in #include statements (uses RAW line) 1559 # check for malformed paths in #include statements (uses RAW line)
1559 if ($rawline =~ m{^.\s*\#\s*include\s+[<"](.*)[">]}) { 1560 if ($rawline =~ m{^.\s*\#\s*include\s+[<"](.*)[">]}) {
1560 my $path = $1; 1561 my $path = $1;
1561 if ($path =~ m{//}) { 1562 if ($path =~ m{//}) {
1562 ERROR("malformed #include filename\n" . 1563 ERROR("malformed #include filename\n" .
1563 $herecurr); 1564 $herecurr);
1564 } 1565 }
1565 } 1566 }
1566 1567
1567 # no C99 // comments 1568 # no C99 // comments
1568 if ($line =~ m{//}) { 1569 if ($line =~ m{//}) {
1569 ERROR("do not use C99 // comments\n" . $herecurr); 1570 ERROR("do not use C99 // comments\n" . $herecurr);
1570 } 1571 }
1571 # Remove C99 comments. 1572 # Remove C99 comments.
1572 $line =~ s@//.*@@; 1573 $line =~ s@//.*@@;
1573 $opline =~ s@//.*@@; 1574 $opline =~ s@//.*@@;
1574 1575
1575 #EXPORT_SYMBOL should immediately follow its function closing }. 1576 #EXPORT_SYMBOL should immediately follow its function closing }.
1576 if (($line =~ /EXPORT_SYMBOL.*\((.*)\)/) || 1577 if (($line =~ /EXPORT_SYMBOL.*\((.*)\)/) ||
1577 ($line =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) { 1578 ($line =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) {
1578 my $name = $1; 1579 my $name = $1;
1579 if ($prevline !~ /(?: 1580 if ($prevline !~ /(?:
1580 ^.}| 1581 ^.}|
1581 ^.DEFINE_$Ident\(\Q$name\E\)| 1582 ^.DEFINE_$Ident\(\Q$name\E\)|
1582 ^.DECLARE_$Ident\(\Q$name\E\)| 1583 ^.DECLARE_$Ident\(\Q$name\E\)|
1583 ^.LIST_HEAD\(\Q$name\E\)| 1584 ^.LIST_HEAD\(\Q$name\E\)|
1584 ^.$Type\s*\(\s*\*\s*\Q$name\E\s*\)\s*\(| 1585 ^.$Type\s*\(\s*\*\s*\Q$name\E\s*\)\s*\(|
1585 \b\Q$name\E(?:\s+$Attribute)?\s*(?:;|=|\[) 1586 \b\Q$name\E(?:\s+$Attribute)?\s*(?:;|=|\[)
1586 )/x) { 1587 )/x) {
1587 WARN("EXPORT_SYMBOL(foo); should immediately follow its function/variable\n" . $herecurr); 1588 WARN("EXPORT_SYMBOL(foo); should immediately follow its function/variable\n" . $herecurr);
1588 } 1589 }
1589 } 1590 }
1590 1591
1591 # check for external initialisers. 1592 # check for external initialisers.
1592 if ($line =~ /^.$Type\s*$Ident\s*(?:\s+$Modifier)*\s*=\s*(0|NULL|false)\s*;/) { 1593 if ($line =~ /^.$Type\s*$Ident\s*(?:\s+$Modifier)*\s*=\s*(0|NULL|false)\s*;/) {
1593 ERROR("do not initialise externals to 0 or NULL\n" . 1594 ERROR("do not initialise externals to 0 or NULL\n" .
1594 $herecurr); 1595 $herecurr);
1595 } 1596 }
1596 # check for static initialisers. 1597 # check for static initialisers.
1597 if ($line =~ /\s*static\s.*=\s*(0|NULL|false)\s*;/) { 1598 if ($line =~ /\s*static\s.*=\s*(0|NULL|false)\s*;/) {
1598 ERROR("do not initialise statics to 0 or NULL\n" . 1599 ERROR("do not initialise statics to 0 or NULL\n" .
1599 $herecurr); 1600 $herecurr);
1600 } 1601 }
1601 1602
1602 # check for new typedefs, only function parameters and sparse annotations 1603 # check for new typedefs, only function parameters and sparse annotations
1603 # make sense. 1604 # make sense.
1604 if ($line =~ /\btypedef\s/ && 1605 if ($line =~ /\btypedef\s/ &&
1605 $line !~ /\btypedef\s+$Type\s+\(\s*\*?$Ident\s*\)\s*\(/ && 1606 $line !~ /\btypedef\s+$Type\s+\(\s*\*?$Ident\s*\)\s*\(/ &&
1606 $line !~ /\btypedef\s+$Type\s+$Ident\s*\(/ && 1607 $line !~ /\btypedef\s+$Type\s+$Ident\s*\(/ &&
1607 $line !~ /\b$typeTypedefs\b/ && 1608 $line !~ /\b$typeTypedefs\b/ &&
1608 $line !~ /\b__bitwise(?:__|)\b/) { 1609 $line !~ /\b__bitwise(?:__|)\b/) {
1609 WARN("do not add new typedefs\n" . $herecurr); 1610 WARN("do not add new typedefs\n" . $herecurr);
1610 } 1611 }
1611 1612
1612 # * goes on variable not on type 1613 # * goes on variable not on type
1613 if ($line =~ m{\($NonptrType(\*+)(?:\s+const)?\)}) { 1614 if ($line =~ m{\($NonptrType(\*+)(?:\s+const)?\)}) {
1614 ERROR("\"(foo$1)\" should be \"(foo $1)\"\n" . 1615 ERROR("\"(foo$1)\" should be \"(foo $1)\"\n" .
1615 $herecurr); 1616 $herecurr);
1616 1617
1617 } elsif ($line =~ m{\($NonptrType\s+(\*+)(?!\s+const)\s+\)}) { 1618 } elsif ($line =~ m{\($NonptrType\s+(\*+)(?!\s+const)\s+\)}) {
1618 ERROR("\"(foo $1 )\" should be \"(foo $1)\"\n" . 1619 ERROR("\"(foo $1 )\" should be \"(foo $1)\"\n" .
1619 $herecurr); 1620 $herecurr);
1620 1621
1621 } elsif ($line =~ m{\b$NonptrType(\*+)(?:\s+(?:$Attribute|$Sparse))?\s+[A-Za-z\d_]+}) { 1622 } elsif ($line =~ m{\b$NonptrType(\*+)(?:\s+(?:$Attribute|$Sparse))?\s+[A-Za-z\d_]+}) {
1622 ERROR("\"foo$1 bar\" should be \"foo $1bar\"\n" . 1623 ERROR("\"foo$1 bar\" should be \"foo $1bar\"\n" .
1623 $herecurr); 1624 $herecurr);
1624 1625
1625 } elsif ($line =~ m{\b$NonptrType\s+(\*+)(?!\s+(?:$Attribute|$Sparse))\s+[A-Za-z\d_]+}) { 1626 } elsif ($line =~ m{\b$NonptrType\s+(\*+)(?!\s+(?:$Attribute|$Sparse))\s+[A-Za-z\d_]+}) {
1626 ERROR("\"foo $1 bar\" should be \"foo $1bar\"\n" . 1627 ERROR("\"foo $1 bar\" should be \"foo $1bar\"\n" .
1627 $herecurr); 1628 $herecurr);
1628 } 1629 }
1629 1630
1630 # # no BUG() or BUG_ON() 1631 # # no BUG() or BUG_ON()
1631 # if ($line =~ /\b(BUG|BUG_ON)\b/) { 1632 # if ($line =~ /\b(BUG|BUG_ON)\b/) {
1632 # print "Try to use WARN_ON & Recovery code rather than BUG() or BUG_ON()\n"; 1633 # print "Try to use WARN_ON & Recovery code rather than BUG() or BUG_ON()\n";
1633 # print "$herecurr"; 1634 # print "$herecurr";
1634 # $clean = 0; 1635 # $clean = 0;
1635 # } 1636 # }
1636 1637
1637 if ($line =~ /\bLINUX_VERSION_CODE\b/) { 1638 if ($line =~ /\bLINUX_VERSION_CODE\b/) {
1638 WARN("LINUX_VERSION_CODE should be avoided, code should be for the version to which it is merged\n" . $herecurr); 1639 WARN("LINUX_VERSION_CODE should be avoided, code should be for the version to which it is merged\n" . $herecurr);
1639 } 1640 }
1640 1641
1641 # printk should use KERN_* levels. Note that follow on printk's on the 1642 # printk should use KERN_* levels. Note that follow on printk's on the
1642 # same line do not need a level, so we use the current block context 1643 # same line do not need a level, so we use the current block context
1643 # to try and find and validate the current printk. In summary the current 1644 # to try and find and validate the current printk. In summary the current
1644 # printk includes all preceeding printk's which have no newline on the end. 1645 # printk includes all preceeding printk's which have no newline on the end.
1645 # we assume the first bad printk is the one to report. 1646 # we assume the first bad printk is the one to report.
1646 if ($line =~ /\bprintk\((?!KERN_)\s*"/) { 1647 if ($line =~ /\bprintk\((?!KERN_)\s*"/) {
1647 my $ok = 0; 1648 my $ok = 0;
1648 for (my $ln = $linenr - 1; $ln >= $first_line; $ln--) { 1649 for (my $ln = $linenr - 1; $ln >= $first_line; $ln--) {
1649 #print "CHECK<$lines[$ln - 1]\n"; 1650 #print "CHECK<$lines[$ln - 1]\n";
1650 # we have a preceeding printk if it ends 1651 # we have a preceeding printk if it ends
1651 # with "\n" ignore it, else it is to blame 1652 # with "\n" ignore it, else it is to blame
1652 if ($lines[$ln - 1] =~ m{\bprintk\(}) { 1653 if ($lines[$ln - 1] =~ m{\bprintk\(}) {
1653 if ($rawlines[$ln - 1] !~ m{\\n"}) { 1654 if ($rawlines[$ln - 1] !~ m{\\n"}) {
1654 $ok = 1; 1655 $ok = 1;
1655 } 1656 }
1656 last; 1657 last;
1657 } 1658 }
1658 } 1659 }
1659 if ($ok == 0) { 1660 if ($ok == 0) {
1660 WARN("printk() should include KERN_ facility level\n" . $herecurr); 1661 WARN("printk() should include KERN_ facility level\n" . $herecurr);
1661 } 1662 }
1662 } 1663 }
1663 1664
1664 # function brace can't be on same line, except for #defines of do while, 1665 # function brace can't be on same line, except for #defines of do while,
1665 # or if closed on same line 1666 # or if closed on same line
1666 if (($line=~/$Type\s*$Ident\(.*\).*\s{/) and 1667 if (($line=~/$Type\s*$Ident\(.*\).*\s{/) and
1667 !($line=~/\#\s*define.*do\s{/) and !($line=~/}/)) { 1668 !($line=~/\#\s*define.*do\s{/) and !($line=~/}/)) {
1668 ERROR("open brace '{' following function declarations go on the next line\n" . $herecurr); 1669 ERROR("open brace '{' following function declarations go on the next line\n" . $herecurr);
1669 } 1670 }
1670 1671
1671 # open braces for enum, union and struct go on the same line. 1672 # open braces for enum, union and struct go on the same line.
1672 if ($line =~ /^.\s*{/ && 1673 if ($line =~ /^.\s*{/ &&
1673 $prevline =~ /^.\s*(?:typedef\s+)?(enum|union|struct)(?:\s+$Ident)?\s*$/) { 1674 $prevline =~ /^.\s*(?:typedef\s+)?(enum|union|struct)(?:\s+$Ident)?\s*$/) {
1674 ERROR("open brace '{' following $1 go on the same line\n" . $hereprev); 1675 ERROR("open brace '{' following $1 go on the same line\n" . $hereprev);
1675 } 1676 }
1676 1677
1677 # check for spacing round square brackets; allowed: 1678 # check for spacing round square brackets; allowed:
1678 # 1. with a type on the left -- int [] a; 1679 # 1. with a type on the left -- int [] a;
1679 # 2. at the beginning of a line for slice initialisers -- [0...10] = 5, 1680 # 2. at the beginning of a line for slice initialisers -- [0...10] = 5,
1680 # 3. inside a curly brace -- = { [0...10] = 5 } 1681 # 3. inside a curly brace -- = { [0...10] = 5 }
1681 while ($line =~ /(.*?\s)\[/g) { 1682 while ($line =~ /(.*?\s)\[/g) {
1682 my ($where, $prefix) = ($-[1], $1); 1683 my ($where, $prefix) = ($-[1], $1);
1683 if ($prefix !~ /$Type\s+$/ && 1684 if ($prefix !~ /$Type\s+$/ &&
1684 ($where != 0 || $prefix !~ /^.\s+$/) && 1685 ($where != 0 || $prefix !~ /^.\s+$/) &&
1685 $prefix !~ /{\s+$/) { 1686 $prefix !~ /{\s+$/) {
1686 ERROR("space prohibited before open square bracket '['\n" . $herecurr); 1687 ERROR("space prohibited before open square bracket '['\n" . $herecurr);
1687 } 1688 }
1688 } 1689 }
1689 1690
1690 # check for spaces between functions and their parentheses. 1691 # check for spaces between functions and their parentheses.
1691 while ($line =~ /($Ident)\s+\(/g) { 1692 while ($line =~ /($Ident)\s+\(/g) {
1692 my $name = $1; 1693 my $name = $1;
1693 my $ctx_before = substr($line, 0, $-[1]); 1694 my $ctx_before = substr($line, 0, $-[1]);
1694 my $ctx = "$ctx_before$name"; 1695 my $ctx = "$ctx_before$name";
1695 1696
1696 # Ignore those directives where spaces _are_ permitted. 1697 # Ignore those directives where spaces _are_ permitted.
1697 if ($name =~ /^(?: 1698 if ($name =~ /^(?:
1698 if|for|while|switch|return|case| 1699 if|for|while|switch|return|case|
1699 volatile|__volatile__| 1700 volatile|__volatile__|
1700 __attribute__|format|__extension__| 1701 __attribute__|format|__extension__|
1701 asm|__asm__)$/x) 1702 asm|__asm__)$/x)
1702 { 1703 {
1703 1704
1704 # cpp #define statements have non-optional spaces, ie 1705 # cpp #define statements have non-optional spaces, ie
1705 # if there is a space between the name and the open 1706 # if there is a space between the name and the open
1706 # parenthesis it is simply not a parameter group. 1707 # parenthesis it is simply not a parameter group.
1707 } elsif ($ctx_before =~ /^.\s*\#\s*define\s*$/) { 1708 } elsif ($ctx_before =~ /^.\s*\#\s*define\s*$/) {
1708 1709
1709 # cpp #elif statement condition may start with a ( 1710 # cpp #elif statement condition may start with a (
1710 } elsif ($ctx =~ /^.\s*\#\s*elif\s*$/) { 1711 } elsif ($ctx =~ /^.\s*\#\s*elif\s*$/) {
1711 1712
1712 # If this whole things ends with a type its most 1713 # If this whole things ends with a type its most
1713 # likely a typedef for a function. 1714 # likely a typedef for a function.
1714 } elsif ($ctx =~ /$Type$/) { 1715 } elsif ($ctx =~ /$Type$/) {
1715 1716
1716 } else { 1717 } else {
1717 WARN("space prohibited between function name and open parenthesis '('\n" . $herecurr); 1718 WARN("space prohibited between function name and open parenthesis '('\n" . $herecurr);
1718 } 1719 }
1719 } 1720 }
1720 # Check operator spacing. 1721 # Check operator spacing.
1721 if (!($line=~/\#\s*include/)) { 1722 if (!($line=~/\#\s*include/)) {
1722 my $ops = qr{ 1723 my $ops = qr{
1723 <<=|>>=|<=|>=|==|!=| 1724 <<=|>>=|<=|>=|==|!=|
1724 \+=|-=|\*=|\/=|%=|\^=|\|=|&=| 1725 \+=|-=|\*=|\/=|%=|\^=|\|=|&=|
1725 =>|->|<<|>>|<|>|=|!|~| 1726 =>|->|<<|>>|<|>|=|!|~|
1726 &&|\|\||,|\^|\+\+|--|&|\||\+|-|\*|\/|%| 1727 &&|\|\||,|\^|\+\+|--|&|\||\+|-|\*|\/|%|
1727 \?|: 1728 \?|:
1728 }x; 1729 }x;
1729 my @elements = split(/($ops|;)/, $opline); 1730 my @elements = split(/($ops|;)/, $opline);
1730 my $off = 0; 1731 my $off = 0;
1731 1732
1732 my $blank = copy_spacing($opline); 1733 my $blank = copy_spacing($opline);
1733 1734
1734 for (my $n = 0; $n < $#elements; $n += 2) { 1735 for (my $n = 0; $n < $#elements; $n += 2) {
1735 $off += length($elements[$n]); 1736 $off += length($elements[$n]);
1736 1737
1737 # Pick up the preceeding and succeeding characters. 1738 # Pick up the preceeding and succeeding characters.
1738 my $ca = substr($opline, 0, $off); 1739 my $ca = substr($opline, 0, $off);
1739 my $cc = ''; 1740 my $cc = '';
1740 if (length($opline) >= ($off + length($elements[$n + 1]))) { 1741 if (length($opline) >= ($off + length($elements[$n + 1]))) {
1741 $cc = substr($opline, $off + length($elements[$n + 1])); 1742 $cc = substr($opline, $off + length($elements[$n + 1]));
1742 } 1743 }
1743 my $cb = "$ca$;$cc"; 1744 my $cb = "$ca$;$cc";
1744 1745
1745 my $a = ''; 1746 my $a = '';
1746 $a = 'V' if ($elements[$n] ne ''); 1747 $a = 'V' if ($elements[$n] ne '');
1747 $a = 'W' if ($elements[$n] =~ /\s$/); 1748 $a = 'W' if ($elements[$n] =~ /\s$/);
1748 $a = 'C' if ($elements[$n] =~ /$;$/); 1749 $a = 'C' if ($elements[$n] =~ /$;$/);
1749 $a = 'B' if ($elements[$n] =~ /(\[|\()$/); 1750 $a = 'B' if ($elements[$n] =~ /(\[|\()$/);
1750 $a = 'O' if ($elements[$n] eq ''); 1751 $a = 'O' if ($elements[$n] eq '');
1751 $a = 'E' if ($ca =~ /^\s*$/); 1752 $a = 'E' if ($ca =~ /^\s*$/);
1752 1753
1753 my $op = $elements[$n + 1]; 1754 my $op = $elements[$n + 1];
1754 1755
1755 my $c = ''; 1756 my $c = '';
1756 if (defined $elements[$n + 2]) { 1757 if (defined $elements[$n + 2]) {
1757 $c = 'V' if ($elements[$n + 2] ne ''); 1758 $c = 'V' if ($elements[$n + 2] ne '');
1758 $c = 'W' if ($elements[$n + 2] =~ /^\s/); 1759 $c = 'W' if ($elements[$n + 2] =~ /^\s/);
1759 $c = 'C' if ($elements[$n + 2] =~ /^$;/); 1760 $c = 'C' if ($elements[$n + 2] =~ /^$;/);
1760 $c = 'B' if ($elements[$n + 2] =~ /^(\)|\]|;)/); 1761 $c = 'B' if ($elements[$n + 2] =~ /^(\)|\]|;)/);
1761 $c = 'O' if ($elements[$n + 2] eq ''); 1762 $c = 'O' if ($elements[$n + 2] eq '');
1762 $c = 'E' if ($elements[$n + 2] =~ /\s*\\$/); 1763 $c = 'E' if ($elements[$n + 2] =~ /\s*\\$/);
1763 } else { 1764 } else {
1764 $c = 'E'; 1765 $c = 'E';
1765 } 1766 }
1766 1767
1767 my $ctx = "${a}x${c}"; 1768 my $ctx = "${a}x${c}";
1768 1769
1769 my $at = "(ctx:$ctx)"; 1770 my $at = "(ctx:$ctx)";
1770 1771
1771 my $ptr = substr($blank, 0, $off) . "^"; 1772 my $ptr = substr($blank, 0, $off) . "^";
1772 my $hereptr = "$hereline$ptr\n"; 1773 my $hereptr = "$hereline$ptr\n";
1773 1774
1774 # Pull out the value of this operator. 1775 # Pull out the value of this operator.
1775 my $op_type = substr($curr_values, $off + 1, 1); 1776 my $op_type = substr($curr_values, $off + 1, 1);
1776 1777
1777 # Get the full operator variant. 1778 # Get the full operator variant.
1778 my $opv = $op . substr($curr_vars, $off, 1); 1779 my $opv = $op . substr($curr_vars, $off, 1);
1779 1780
1780 # Ignore operators passed as parameters. 1781 # Ignore operators passed as parameters.
1781 if ($op_type ne 'V' && 1782 if ($op_type ne 'V' &&
1782 $ca =~ /\s$/ && $cc =~ /^\s*,/) { 1783 $ca =~ /\s$/ && $cc =~ /^\s*,/) {
1783 1784
1784 # # Ignore comments 1785 # # Ignore comments
1785 # } elsif ($op =~ /^$;+$/) { 1786 # } elsif ($op =~ /^$;+$/) {
1786 1787
1787 # ; should have either the end of line or a space or \ after it 1788 # ; should have either the end of line or a space or \ after it
1788 } elsif ($op eq ';') { 1789 } elsif ($op eq ';') {
1789 if ($ctx !~ /.x[WEBC]/ && 1790 if ($ctx !~ /.x[WEBC]/ &&
1790 $cc !~ /^\\/ && $cc !~ /^;/) { 1791 $cc !~ /^\\/ && $cc !~ /^;/) {
1791 ERROR("space required after that '$op' $at\n" . $hereptr); 1792 ERROR("space required after that '$op' $at\n" . $hereptr);
1792 } 1793 }
1793 1794
1794 # // is a comment 1795 # // is a comment
1795 } elsif ($op eq '//') { 1796 } elsif ($op eq '//') {
1796 1797
1797 # No spaces for: 1798 # No spaces for:
1798 # -> 1799 # ->
1799 # : when part of a bitfield 1800 # : when part of a bitfield
1800 } elsif ($op eq '->' || $opv eq ':B') { 1801 } elsif ($op eq '->' || $opv eq ':B') {
1801 if ($ctx =~ /Wx.|.xW/) { 1802 if ($ctx =~ /Wx.|.xW/) {
1802 ERROR("spaces prohibited around that '$op' $at\n" . $hereptr); 1803 ERROR("spaces prohibited around that '$op' $at\n" . $hereptr);
1803 } 1804 }
1804 1805
1805 # , must have a space on the right. 1806 # , must have a space on the right.
1806 } elsif ($op eq ',') { 1807 } elsif ($op eq ',') {
1807 if ($ctx !~ /.x[WEC]/ && $cc !~ /^}/) { 1808 if ($ctx !~ /.x[WEC]/ && $cc !~ /^}/) {
1808 ERROR("space required after that '$op' $at\n" . $hereptr); 1809 ERROR("space required after that '$op' $at\n" . $hereptr);
1809 } 1810 }
1810 1811
1811 # '*' as part of a type definition -- reported already. 1812 # '*' as part of a type definition -- reported already.
1812 } elsif ($opv eq '*_') { 1813 } elsif ($opv eq '*_') {
1813 #warn "'*' is part of type\n"; 1814 #warn "'*' is part of type\n";
1814 1815
1815 # unary operators should have a space before and 1816 # unary operators should have a space before and
1816 # none after. May be left adjacent to another 1817 # none after. May be left adjacent to another
1817 # unary operator, or a cast 1818 # unary operator, or a cast
1818 } elsif ($op eq '!' || $op eq '~' || 1819 } elsif ($op eq '!' || $op eq '~' ||
1819 $opv eq '*U' || $opv eq '-U' || 1820 $opv eq '*U' || $opv eq '-U' ||
1820 $opv eq '&U' || $opv eq '&&U') { 1821 $opv eq '&U' || $opv eq '&&U') {
1821 if ($ctx !~ /[WEBC]x./ && $ca !~ /(?:\)|!|~|\*|-|\&|\||\+\+|\-\-|\{)$/) { 1822 if ($ctx !~ /[WEBC]x./ && $ca !~ /(?:\)|!|~|\*|-|\&|\||\+\+|\-\-|\{)$/) {
1822 ERROR("space required before that '$op' $at\n" . $hereptr); 1823 ERROR("space required before that '$op' $at\n" . $hereptr);
1823 } 1824 }
1824 if ($op eq '*' && $cc =~/\s*const\b/) { 1825 if ($op eq '*' && $cc =~/\s*const\b/) {
1825 # A unary '*' may be const 1826 # A unary '*' may be const
1826 1827
1827 } elsif ($ctx =~ /.xW/) { 1828 } elsif ($ctx =~ /.xW/) {
1828 ERROR("space prohibited after that '$op' $at\n" . $hereptr); 1829 ERROR("space prohibited after that '$op' $at\n" . $hereptr);
1829 } 1830 }
1830 1831
1831 # unary ++ and unary -- are allowed no space on one side. 1832 # unary ++ and unary -- are allowed no space on one side.
1832 } elsif ($op eq '++' or $op eq '--') { 1833 } elsif ($op eq '++' or $op eq '--') {
1833 if ($ctx !~ /[WEOBC]x[^W]/ && $ctx !~ /[^W]x[WOBEC]/) { 1834 if ($ctx !~ /[WEOBC]x[^W]/ && $ctx !~ /[^W]x[WOBEC]/) {
1834 ERROR("space required one side of that '$op' $at\n" . $hereptr); 1835 ERROR("space required one side of that '$op' $at\n" . $hereptr);
1835 } 1836 }
1836 if ($ctx =~ /Wx[BE]/ || 1837 if ($ctx =~ /Wx[BE]/ ||
1837 ($ctx =~ /Wx./ && $cc =~ /^;/)) { 1838 ($ctx =~ /Wx./ && $cc =~ /^;/)) {
1838 ERROR("space prohibited before that '$op' $at\n" . $hereptr); 1839 ERROR("space prohibited before that '$op' $at\n" . $hereptr);
1839 } 1840 }
1840 if ($ctx =~ /ExW/) { 1841 if ($ctx =~ /ExW/) {
1841 ERROR("space prohibited after that '$op' $at\n" . $hereptr); 1842 ERROR("space prohibited after that '$op' $at\n" . $hereptr);
1842 } 1843 }
1843 1844
1844 1845
1845 # << and >> may either have or not have spaces both sides 1846 # << and >> may either have or not have spaces both sides
1846 } elsif ($op eq '<<' or $op eq '>>' or 1847 } elsif ($op eq '<<' or $op eq '>>' or
1847 $op eq '&' or $op eq '^' or $op eq '|' or 1848 $op eq '&' or $op eq '^' or $op eq '|' or
1848 $op eq '+' or $op eq '-' or 1849 $op eq '+' or $op eq '-' or
1849 $op eq '*' or $op eq '/' or 1850 $op eq '*' or $op eq '/' or
1850 $op eq '%') 1851 $op eq '%')
1851 { 1852 {
1852 if ($ctx =~ /Wx[^WCE]|[^WCE]xW/) { 1853 if ($ctx =~ /Wx[^WCE]|[^WCE]xW/) {
1853 ERROR("need consistent spacing around '$op' $at\n" . 1854 ERROR("need consistent spacing around '$op' $at\n" .
1854 $hereptr); 1855 $hereptr);
1855 } 1856 }
1856 1857
1857 # A colon needs no spaces before when it is 1858 # A colon needs no spaces before when it is
1858 # terminating a case value or a label. 1859 # terminating a case value or a label.
1859 } elsif ($opv eq ':C' || $opv eq ':L') { 1860 } elsif ($opv eq ':C' || $opv eq ':L') {
1860 if ($ctx =~ /Wx./) { 1861 if ($ctx =~ /Wx./) {
1861 ERROR("space prohibited before that '$op' $at\n" . $hereptr); 1862 ERROR("space prohibited before that '$op' $at\n" . $hereptr);
1862 } 1863 }
1863 1864
1864 # All the others need spaces both sides. 1865 # All the others need spaces both sides.
1865 } elsif ($ctx !~ /[EWC]x[CWE]/) { 1866 } elsif ($ctx !~ /[EWC]x[CWE]/) {
1866 my $ok = 0; 1867 my $ok = 0;
1867 1868
1868 # Ignore email addresses <foo@bar> 1869 # Ignore email addresses <foo@bar>
1869 if (($op eq '<' && 1870 if (($op eq '<' &&
1870 $cc =~ /^\S+\@\S+>/) || 1871 $cc =~ /^\S+\@\S+>/) ||
1871 ($op eq '>' && 1872 ($op eq '>' &&
1872 $ca =~ /<\S+\@\S+$/)) 1873 $ca =~ /<\S+\@\S+$/))
1873 { 1874 {
1874 $ok = 1; 1875 $ok = 1;
1875 } 1876 }
1876 1877
1877 # Ignore ?: 1878 # Ignore ?:
1878 if (($opv eq ':O' && $ca =~ /\?$/) || 1879 if (($opv eq ':O' && $ca =~ /\?$/) ||
1879 ($op eq '?' && $cc =~ /^:/)) { 1880 ($op eq '?' && $cc =~ /^:/)) {
1880 $ok = 1; 1881 $ok = 1;
1881 } 1882 }
1882 1883
1883 if ($ok == 0) { 1884 if ($ok == 0) {
1884 ERROR("spaces required around that '$op' $at\n" . $hereptr); 1885 ERROR("spaces required around that '$op' $at\n" . $hereptr);
1885 } 1886 }
1886 } 1887 }
1887 $off += length($elements[$n + 1]); 1888 $off += length($elements[$n + 1]);
1888 } 1889 }
1889 } 1890 }
1890 1891
1891 # check for multiple assignments 1892 # check for multiple assignments
1892 if ($line =~ /^.\s*$Lval\s*=\s*$Lval\s*=(?!=)/) { 1893 if ($line =~ /^.\s*$Lval\s*=\s*$Lval\s*=(?!=)/) {
1893 CHK("multiple assignments should be avoided\n" . $herecurr); 1894 CHK("multiple assignments should be avoided\n" . $herecurr);
1894 } 1895 }
1895 1896
1896 ## # check for multiple declarations, allowing for a function declaration 1897 ## # check for multiple declarations, allowing for a function declaration
1897 ## # continuation. 1898 ## # continuation.
1898 ## if ($line =~ /^.\s*$Type\s+$Ident(?:\s*=[^,{]*)?\s*,\s*$Ident.*/ && 1899 ## if ($line =~ /^.\s*$Type\s+$Ident(?:\s*=[^,{]*)?\s*,\s*$Ident.*/ &&
1899 ## $line !~ /^.\s*$Type\s+$Ident(?:\s*=[^,{]*)?\s*,\s*$Type\s*$Ident.*/) { 1900 ## $line !~ /^.\s*$Type\s+$Ident(?:\s*=[^,{]*)?\s*,\s*$Type\s*$Ident.*/) {
1900 ## 1901 ##
1901 ## # Remove any bracketed sections to ensure we do not 1902 ## # Remove any bracketed sections to ensure we do not
1902 ## # falsly report the parameters of functions. 1903 ## # falsly report the parameters of functions.
1903 ## my $ln = $line; 1904 ## my $ln = $line;
1904 ## while ($ln =~ s/\([^\(\)]*\)//g) { 1905 ## while ($ln =~ s/\([^\(\)]*\)//g) {
1905 ## } 1906 ## }
1906 ## if ($ln =~ /,/) { 1907 ## if ($ln =~ /,/) {
1907 ## WARN("declaring multiple variables together should be avoided\n" . $herecurr); 1908 ## WARN("declaring multiple variables together should be avoided\n" . $herecurr);
1908 ## } 1909 ## }
1909 ## } 1910 ## }
1910 1911
1911 #need space before brace following if, while, etc 1912 #need space before brace following if, while, etc
1912 if (($line =~ /\(.*\){/ && $line !~ /\($Type\){/) || 1913 if (($line =~ /\(.*\){/ && $line !~ /\($Type\){/) ||
1913 $line =~ /do{/) { 1914 $line =~ /do{/) {
1914 ERROR("space required before the open brace '{'\n" . $herecurr); 1915 ERROR("space required before the open brace '{'\n" . $herecurr);
1915 } 1916 }
1916 1917
1917 # closing brace should have a space following it when it has anything 1918 # closing brace should have a space following it when it has anything
1918 # on the line 1919 # on the line
1919 if ($line =~ /}(?!(?:,|;|\)))\S/) { 1920 if ($line =~ /}(?!(?:,|;|\)))\S/) {
1920 ERROR("space required after that close brace '}'\n" . $herecurr); 1921 ERROR("space required after that close brace '}'\n" . $herecurr);
1921 } 1922 }
1922 1923
1923 # check spacing on square brackets 1924 # check spacing on square brackets
1924 if ($line =~ /\[\s/ && $line !~ /\[\s*$/) { 1925 if ($line =~ /\[\s/ && $line !~ /\[\s*$/) {
1925 ERROR("space prohibited after that open square bracket '['\n" . $herecurr); 1926 ERROR("space prohibited after that open square bracket '['\n" . $herecurr);
1926 } 1927 }
1927 if ($line =~ /\s\]/) { 1928 if ($line =~ /\s\]/) {
1928 ERROR("space prohibited before that close square bracket ']'\n" . $herecurr); 1929 ERROR("space prohibited before that close square bracket ']'\n" . $herecurr);
1929 } 1930 }
1930 1931
1931 # check spacing on parentheses 1932 # check spacing on parentheses
1932 if ($line =~ /\(\s/ && $line !~ /\(\s*(?:\\)?$/ && 1933 if ($line =~ /\(\s/ && $line !~ /\(\s*(?:\\)?$/ &&
1933 $line !~ /for\s*\(\s+;/) { 1934 $line !~ /for\s*\(\s+;/) {
1934 ERROR("space prohibited after that open parenthesis '('\n" . $herecurr); 1935 ERROR("space prohibited after that open parenthesis '('\n" . $herecurr);
1935 } 1936 }
1936 if ($line =~ /(\s+)\)/ && $line !~ /^.\s*\)/ && 1937 if ($line =~ /(\s+)\)/ && $line !~ /^.\s*\)/ &&
1937 $line !~ /for\s*\(.*;\s+\)/ && 1938 $line !~ /for\s*\(.*;\s+\)/ &&
1938 $line !~ /:\s+\)/) { 1939 $line !~ /:\s+\)/) {
1939 ERROR("space prohibited before that close parenthesis ')'\n" . $herecurr); 1940 ERROR("space prohibited before that close parenthesis ')'\n" . $herecurr);
1940 } 1941 }
1941 1942
1942 #goto labels aren't indented, allow a single space however 1943 #goto labels aren't indented, allow a single space however
1943 if ($line=~/^.\s+[A-Za-z\d_]+:(?![0-9]+)/ and 1944 if ($line=~/^.\s+[A-Za-z\d_]+:(?![0-9]+)/ and
1944 !($line=~/^. [A-Za-z\d_]+:/) and !($line=~/^.\s+default:/)) { 1945 !($line=~/^. [A-Za-z\d_]+:/) and !($line=~/^.\s+default:/)) {
1945 WARN("labels should not be indented\n" . $herecurr); 1946 WARN("labels should not be indented\n" . $herecurr);
1946 } 1947 }
1947 1948
1948 # Return is not a function. 1949 # Return is not a function.
1949 if (defined($stat) && $stat =~ /^.\s*return(\s*)(\(.*);/s) { 1950 if (defined($stat) && $stat =~ /^.\s*return(\s*)(\(.*);/s) {
1950 my $spacing = $1; 1951 my $spacing = $1;
1951 my $value = $2; 1952 my $value = $2;
1952 1953
1953 # Flatten any parentheses and braces 1954 # Flatten any parentheses and braces
1954 $value =~ s/\)\(/\) \(/g; 1955 $value =~ s/\)\(/\) \(/g;
1955 while ($value =~ s/\([^\(\)]*\)/1/) { 1956 while ($value =~ s/\([^\(\)]*\)/1/) {
1956 } 1957 }
1957 1958
1958 if ($value =~ /^(?:$Ident|-?$Constant)$/) { 1959 if ($value =~ /^(?:$Ident|-?$Constant)$/) {
1959 ERROR("return is not a function, parentheses are not required\n" . $herecurr); 1960 ERROR("return is not a function, parentheses are not required\n" . $herecurr);
1960 1961
1961 } elsif ($spacing !~ /\s+/) { 1962 } elsif ($spacing !~ /\s+/) {
1962 ERROR("space required before the open parenthesis '('\n" . $herecurr); 1963 ERROR("space required before the open parenthesis '('\n" . $herecurr);
1963 } 1964 }
1964 } 1965 }
1965 1966
1966 # Need a space before open parenthesis after if, while etc 1967 # Need a space before open parenthesis after if, while etc
1967 if ($line=~/\b(if|while|for|switch)\(/) { 1968 if ($line=~/\b(if|while|for|switch)\(/) {
1968 ERROR("space required before the open parenthesis '('\n" . $herecurr); 1969 ERROR("space required before the open parenthesis '('\n" . $herecurr);
1969 } 1970 }
1970 1971
1971 # Check for illegal assignment in if conditional -- and check for trailing 1972 # Check for illegal assignment in if conditional -- and check for trailing
1972 # statements after the conditional. 1973 # statements after the conditional.
1973 if ($line =~ /do\s*(?!{)/) { 1974 if ($line =~ /do\s*(?!{)/) {
1974 my ($stat_next) = ctx_statement_block($line_nr_next, 1975 my ($stat_next) = ctx_statement_block($line_nr_next,
1975 $remain_next, $off_next); 1976 $remain_next, $off_next);
1976 $stat_next =~ s/\n./\n /g; 1977 $stat_next =~ s/\n./\n /g;
1977 ##print "stat<$stat> stat_next<$stat_next>\n"; 1978 ##print "stat<$stat> stat_next<$stat_next>\n";
1978 1979
1979 if ($stat_next =~ /^\s*while\b/) { 1980 if ($stat_next =~ /^\s*while\b/) {
1980 # If the statement carries leading newlines, 1981 # If the statement carries leading newlines,
1981 # then count those as offsets. 1982 # then count those as offsets.
1982 my ($whitespace) = 1983 my ($whitespace) =
1983 ($stat_next =~ /^((?:\s*\n[+-])*\s*)/s); 1984 ($stat_next =~ /^((?:\s*\n[+-])*\s*)/s);
1984 my $offset = 1985 my $offset =
1985 statement_rawlines($whitespace) - 1; 1986 statement_rawlines($whitespace) - 1;
1986 1987
1987 $suppress_whiletrailers{$line_nr_next + 1988 $suppress_whiletrailers{$line_nr_next +
1988 $offset} = 1; 1989 $offset} = 1;
1989 } 1990 }
1990 } 1991 }
1991 if (!defined $suppress_whiletrailers{$linenr} && 1992 if (!defined $suppress_whiletrailers{$linenr} &&
1992 $line =~ /\b(?:if|while|for)\s*\(/ && $line !~ /^.\s*#/) { 1993 $line =~ /\b(?:if|while|for)\s*\(/ && $line !~ /^.\s*#/) {
1993 my ($s, $c) = ($stat, $cond); 1994 my ($s, $c) = ($stat, $cond);
1994 1995
1995 if ($c =~ /\bif\s*\(.*[^<>!=]=[^=].*/) { 1996 if ($c =~ /\bif\s*\(.*[^<>!=]=[^=].*/) {
1996 ERROR("do not use assignment in if condition\n" . $herecurr); 1997 ERROR("do not use assignment in if condition\n" . $herecurr);
1997 } 1998 }
1998 1999
1999 # Find out what is on the end of the line after the 2000 # Find out what is on the end of the line after the
2000 # conditional. 2001 # conditional.
2001 substr($s, 0, length($c), ''); 2002 substr($s, 0, length($c), '');
2002 $s =~ s/\n.*//g; 2003 $s =~ s/\n.*//g;
2003 $s =~ s/$;//g; # Remove any comments 2004 $s =~ s/$;//g; # Remove any comments
2004 if (length($c) && $s !~ /^\s*{?\s*\\*\s*$/ && 2005 if (length($c) && $s !~ /^\s*{?\s*\\*\s*$/ &&
2005 $c !~ /}\s*while\s*/) 2006 $c !~ /}\s*while\s*/)
2006 { 2007 {
2007 # Find out how long the conditional actually is. 2008 # Find out how long the conditional actually is.
2008 my @newlines = ($c =~ /\n/gs); 2009 my @newlines = ($c =~ /\n/gs);
2009 my $cond_lines = 1 + $#newlines; 2010 my $cond_lines = 1 + $#newlines;
2010 2011
2011 my $stat_real = raw_line($linenr, $cond_lines); 2012 my $stat_real = raw_line($linenr, $cond_lines);
2012 if (defined($stat_real) && $cond_lines > 1) { 2013 if (defined($stat_real) && $cond_lines > 1) {
2013 $stat_real = "[...]\n$stat_real"; 2014 $stat_real = "[...]\n$stat_real";
2014 } 2015 }
2015 2016
2016 ERROR("trailing statements should be on next line\n" . $herecurr . $stat_real); 2017 ERROR("trailing statements should be on next line\n" . $herecurr . $stat_real);
2017 } 2018 }
2018 } 2019 }
2019 2020
2020 # Check for bitwise tests written as boolean 2021 # Check for bitwise tests written as boolean
2021 if ($line =~ / 2022 if ($line =~ /
2022 (?: 2023 (?:
2023 (?:\[|\(|\&\&|\|\|) 2024 (?:\[|\(|\&\&|\|\|)
2024 \s*0[xX][0-9]+\s* 2025 \s*0[xX][0-9]+\s*
2025 (?:\&\&|\|\|) 2026 (?:\&\&|\|\|)
2026 | 2027 |
2027 (?:\&\&|\|\|) 2028 (?:\&\&|\|\|)
2028 \s*0[xX][0-9]+\s* 2029 \s*0[xX][0-9]+\s*
2029 (?:\&\&|\|\||\)|\]) 2030 (?:\&\&|\|\||\)|\])
2030 )/x) 2031 )/x)
2031 { 2032 {
2032 WARN("boolean test with hexadecimal, perhaps just 1 \& or \|?\n" . $herecurr); 2033 WARN("boolean test with hexadecimal, perhaps just 1 \& or \|?\n" . $herecurr);
2033 } 2034 }
2034 2035
2035 # if and else should not have general statements after it 2036 # if and else should not have general statements after it
2036 if ($line =~ /^.\s*(?:}\s*)?else\b(.*)/) { 2037 if ($line =~ /^.\s*(?:}\s*)?else\b(.*)/) {
2037 my $s = $1; 2038 my $s = $1;
2038 $s =~ s/$;//g; # Remove any comments 2039 $s =~ s/$;//g; # Remove any comments
2039 if ($s !~ /^\s*(?:\sif|(?:{|)\s*\\?\s*$)/) { 2040 if ($s !~ /^\s*(?:\sif|(?:{|)\s*\\?\s*$)/) {
2040 ERROR("trailing statements should be on next line\n" . $herecurr); 2041 ERROR("trailing statements should be on next line\n" . $herecurr);
2041 } 2042 }
2042 } 2043 }
2043 # case and default should not have general statements after them 2044 # case and default should not have general statements after them
2044 if ($line =~ /^.\s*(?:case\s*.*|default\s*):/g && 2045 if ($line =~ /^.\s*(?:case\s*.*|default\s*):/g &&
2045 $line !~ /\G(?: 2046 $line !~ /\G(?:
2046 (?:\s*$;*)(?:\s*{)?(?:\s*$;*)(?:\s*\\)?\s*$| 2047 (?:\s*$;*)(?:\s*{)?(?:\s*$;*)(?:\s*\\)?\s*$|
2047 \s*return\s+ 2048 \s*return\s+
2048 )/xg) 2049 )/xg)
2049 { 2050 {
2050 ERROR("trailing statements should be on next line\n" . $herecurr); 2051 ERROR("trailing statements should be on next line\n" . $herecurr);
2051 } 2052 }
2052 2053
2053 # Check for }<nl>else {, these must be at the same 2054 # Check for }<nl>else {, these must be at the same
2054 # indent level to be relevant to each other. 2055 # indent level to be relevant to each other.
2055 if ($prevline=~/}\s*$/ and $line=~/^.\s*else\s*/ and 2056 if ($prevline=~/}\s*$/ and $line=~/^.\s*else\s*/ and
2056 $previndent == $indent) { 2057 $previndent == $indent) {
2057 ERROR("else should follow close brace '}'\n" . $hereprev); 2058 ERROR("else should follow close brace '}'\n" . $hereprev);
2058 } 2059 }
2059 2060
2060 if ($prevline=~/}\s*$/ and $line=~/^.\s*while\s*/ and 2061 if ($prevline=~/}\s*$/ and $line=~/^.\s*while\s*/ and
2061 $previndent == $indent) { 2062 $previndent == $indent) {
2062 my ($s, $c) = ctx_statement_block($linenr, $realcnt, 0); 2063 my ($s, $c) = ctx_statement_block($linenr, $realcnt, 0);
2063 2064
2064 # Find out what is on the end of the line after the 2065 # Find out what is on the end of the line after the
2065 # conditional. 2066 # conditional.
2066 substr($s, 0, length($c), ''); 2067 substr($s, 0, length($c), '');
2067 $s =~ s/\n.*//g; 2068 $s =~ s/\n.*//g;
2068 2069
2069 if ($s =~ /^\s*;/) { 2070 if ($s =~ /^\s*;/) {
2070 ERROR("while should follow close brace '}'\n" . $hereprev); 2071 ERROR("while should follow close brace '}'\n" . $hereprev);
2071 } 2072 }
2072 } 2073 }
2073 2074
2074 #studly caps, commented out until figure out how to distinguish between use of existing and adding new 2075 #studly caps, commented out until figure out how to distinguish between use of existing and adding new
2075 # if (($line=~/[\w_][a-z\d]+[A-Z]/) and !($line=~/print/)) { 2076 # if (($line=~/[\w_][a-z\d]+[A-Z]/) and !($line=~/print/)) {
2076 # print "No studly caps, use _\n"; 2077 # print "No studly caps, use _\n";
2077 # print "$herecurr"; 2078 # print "$herecurr";
2078 # $clean = 0; 2079 # $clean = 0;
2079 # } 2080 # }
2080 2081
2081 #no spaces allowed after \ in define 2082 #no spaces allowed after \ in define
2082 if ($line=~/\#\s*define.*\\\s$/) { 2083 if ($line=~/\#\s*define.*\\\s$/) {
2083 WARN("Whitepspace after \\ makes next lines useless\n" . $herecurr); 2084 WARN("Whitepspace after \\ makes next lines useless\n" . $herecurr);
2084 } 2085 }
2085 2086
2086 #warn if <asm/foo.h> is #included and <linux/foo.h> is available (uses RAW line) 2087 #warn if <asm/foo.h> is #included and <linux/foo.h> is available (uses RAW line)
2087 if ($tree && $rawline =~ m{^.\s*\#\s*include\s*\<asm\/(.*)\.h\>}) { 2088 if ($tree && $rawline =~ m{^.\s*\#\s*include\s*\<asm\/(.*)\.h\>}) {
2088 my $file = "$1.h"; 2089 my $file = "$1.h";
2089 my $checkfile = "include/linux/$file"; 2090 my $checkfile = "include/linux/$file";
2090 if (-f "$root/$checkfile" && 2091 if (-f "$root/$checkfile" &&
2091 $realfile ne $checkfile && 2092 $realfile ne $checkfile &&
2092 $1 ne 'irq') 2093 $1 ne 'irq')
2093 { 2094 {
2094 if ($realfile =~ m{^arch/}) { 2095 if ($realfile =~ m{^arch/}) {
2095 CHK("Consider using #include <linux/$file> instead of <asm/$file>\n" . $herecurr); 2096 CHK("Consider using #include <linux/$file> instead of <asm/$file>\n" . $herecurr);
2096 } else { 2097 } else {
2097 WARN("Use #include <linux/$file> instead of <asm/$file>\n" . $herecurr); 2098 WARN("Use #include <linux/$file> instead of <asm/$file>\n" . $herecurr);
2098 } 2099 }
2099 } 2100 }
2100 } 2101 }
2101 2102
2102 # multi-statement macros should be enclosed in a do while loop, grab the 2103 # multi-statement macros should be enclosed in a do while loop, grab the
2103 # first statement and ensure its the whole macro if its not enclosed 2104 # first statement and ensure its the whole macro if its not enclosed
2104 # in a known good container 2105 # in a known good container
2105 if ($realfile !~ m@/vmlinux.lds.h$@ && 2106 if ($realfile !~ m@/vmlinux.lds.h$@ &&
2106 $line =~ /^.\s*\#\s*define\s*$Ident(\()?/) { 2107 $line =~ /^.\s*\#\s*define\s*$Ident(\()?/) {
2107 my $ln = $linenr; 2108 my $ln = $linenr;
2108 my $cnt = $realcnt; 2109 my $cnt = $realcnt;
2109 my ($off, $dstat, $dcond, $rest); 2110 my ($off, $dstat, $dcond, $rest);
2110 my $ctx = ''; 2111 my $ctx = '';
2111 2112
2112 my $args = defined($1); 2113 my $args = defined($1);
2113 2114
2114 # Find the end of the macro and limit our statement 2115 # Find the end of the macro and limit our statement
2115 # search to that. 2116 # search to that.
2116 while ($cnt > 0 && defined $lines[$ln - 1] && 2117 while ($cnt > 0 && defined $lines[$ln - 1] &&
2117 $lines[$ln - 1] =~ /^(?:-|..*\\$)/) 2118 $lines[$ln - 1] =~ /^(?:-|..*\\$)/)
2118 { 2119 {
2119 $ctx .= $rawlines[$ln - 1] . "\n"; 2120 $ctx .= $rawlines[$ln - 1] . "\n";
2120 $cnt-- if ($lines[$ln - 1] !~ /^-/); 2121 $cnt-- if ($lines[$ln - 1] !~ /^-/);
2121 $ln++; 2122 $ln++;
2122 } 2123 }
2123 $ctx .= $rawlines[$ln - 1]; 2124 $ctx .= $rawlines[$ln - 1];
2124 2125
2125 ($dstat, $dcond, $ln, $cnt, $off) = 2126 ($dstat, $dcond, $ln, $cnt, $off) =
2126 ctx_statement_block($linenr, $ln - $linenr + 1, 0); 2127 ctx_statement_block($linenr, $ln - $linenr + 1, 0);
2127 #print "dstat<$dstat> dcond<$dcond> cnt<$cnt> off<$off>\n"; 2128 #print "dstat<$dstat> dcond<$dcond> cnt<$cnt> off<$off>\n";
2128 #print "LINE<$lines[$ln-1]> len<" . length($lines[$ln-1]) . "\n"; 2129 #print "LINE<$lines[$ln-1]> len<" . length($lines[$ln-1]) . "\n";
2129 2130
2130 # Extract the remainder of the define (if any) and 2131 # Extract the remainder of the define (if any) and
2131 # rip off surrounding spaces, and trailing \'s. 2132 # rip off surrounding spaces, and trailing \'s.
2132 $rest = ''; 2133 $rest = '';
2133 while ($off != 0 || ($cnt > 0 && $rest =~ /\\\s*$/)) { 2134 while ($off != 0 || ($cnt > 0 && $rest =~ /\\\s*$/)) {
2134 #print "ADDING cnt<$cnt> $off <" . substr($lines[$ln - 1], $off) . "> rest<$rest>\n"; 2135 #print "ADDING cnt<$cnt> $off <" . substr($lines[$ln - 1], $off) . "> rest<$rest>\n";
2135 if ($off != 0 || $lines[$ln - 1] !~ /^-/) { 2136 if ($off != 0 || $lines[$ln - 1] !~ /^-/) {
2136 $rest .= substr($lines[$ln - 1], $off) . "\n"; 2137 $rest .= substr($lines[$ln - 1], $off) . "\n";
2137 $cnt--; 2138 $cnt--;
2138 } 2139 }
2139 $ln++; 2140 $ln++;
2140 $off = 0; 2141 $off = 0;
2141 } 2142 }
2142 $rest =~ s/\\\n.//g; 2143 $rest =~ s/\\\n.//g;
2143 $rest =~ s/^\s*//s; 2144 $rest =~ s/^\s*//s;
2144 $rest =~ s/\s*$//s; 2145 $rest =~ s/\s*$//s;
2145 2146
2146 # Clean up the original statement. 2147 # Clean up the original statement.
2147 if ($args) { 2148 if ($args) {
2148 substr($dstat, 0, length($dcond), ''); 2149 substr($dstat, 0, length($dcond), '');
2149 } else { 2150 } else {
2150 $dstat =~ s/^.\s*\#\s*define\s+$Ident\s*//; 2151 $dstat =~ s/^.\s*\#\s*define\s+$Ident\s*//;
2151 } 2152 }
2152 $dstat =~ s/$;//g; 2153 $dstat =~ s/$;//g;
2153 $dstat =~ s/\\\n.//g; 2154 $dstat =~ s/\\\n.//g;
2154 $dstat =~ s/^\s*//s; 2155 $dstat =~ s/^\s*//s;
2155 $dstat =~ s/\s*$//s; 2156 $dstat =~ s/\s*$//s;
2156 2157
2157 # Flatten any parentheses and braces 2158 # Flatten any parentheses and braces
2158 while ($dstat =~ s/\([^\(\)]*\)/1/ || 2159 while ($dstat =~ s/\([^\(\)]*\)/1/ ||
2159 $dstat =~ s/\{[^\{\}]*\}/1/ || 2160 $dstat =~ s/\{[^\{\}]*\}/1/ ||
2160 $dstat =~ s/\[[^\{\}]*\]/1/) 2161 $dstat =~ s/\[[^\{\}]*\]/1/)
2161 { 2162 {
2162 } 2163 }
2163 2164
2164 my $exceptions = qr{ 2165 my $exceptions = qr{
2165 $Declare| 2166 $Declare|
2166 module_param_named| 2167 module_param_named|
2167 MODULE_PARAM_DESC| 2168 MODULE_PARAM_DESC|
2168 DECLARE_PER_CPU| 2169 DECLARE_PER_CPU|
2169 DEFINE_PER_CPU| 2170 DEFINE_PER_CPU|
2170 __typeof__\(| 2171 __typeof__\(|
2171 \.$Ident\s*=\s* 2172 \.$Ident\s*=\s*
2172 }x; 2173 }x;
2173 #print "REST<$rest> dstat<$dstat>\n"; 2174 #print "REST<$rest> dstat<$dstat>\n";
2174 if ($rest ne '') { 2175 if ($rest ne '') {
2175 if ($rest !~ /while\s*\(/ && 2176 if ($rest !~ /while\s*\(/ &&
2176 $dstat !~ /$exceptions/) 2177 $dstat !~ /$exceptions/)
2177 { 2178 {
2178 ERROR("Macros with multiple statements should be enclosed in a do - while loop\n" . "$here\n$ctx\n"); 2179 ERROR("Macros with multiple statements should be enclosed in a do - while loop\n" . "$here\n$ctx\n");
2179 } 2180 }
2180 2181
2181 } elsif ($ctx !~ /;/) { 2182 } elsif ($ctx !~ /;/) {
2182 if ($dstat ne '' && 2183 if ($dstat ne '' &&
2183 $dstat !~ /^(?:$Ident|-?$Constant)$/ && 2184 $dstat !~ /^(?:$Ident|-?$Constant)$/ &&
2184 $dstat !~ /$exceptions/ && 2185 $dstat !~ /$exceptions/ &&
2185 $dstat !~ /^\.$Ident\s*=/ && 2186 $dstat !~ /^\.$Ident\s*=/ &&
2186 $dstat =~ /$Operators/) 2187 $dstat =~ /$Operators/)
2187 { 2188 {
2188 ERROR("Macros with complex values should be enclosed in parenthesis\n" . "$here\n$ctx\n"); 2189 ERROR("Macros with complex values should be enclosed in parenthesis\n" . "$here\n$ctx\n");
2189 } 2190 }
2190 } 2191 }
2191 } 2192 }
2192 2193
2193 # check for redundant bracing round if etc 2194 # check for redundant bracing round if etc
2194 if ($line =~ /(^.*)\bif\b/ && $1 !~ /else\s*$/) { 2195 if ($line =~ /(^.*)\bif\b/ && $1 !~ /else\s*$/) {
2195 my ($level, $endln, @chunks) = 2196 my ($level, $endln, @chunks) =
2196 ctx_statement_full($linenr, $realcnt, 1); 2197 ctx_statement_full($linenr, $realcnt, 1);
2197 #print "chunks<$#chunks> linenr<$linenr> endln<$endln> level<$level>\n"; 2198 #print "chunks<$#chunks> linenr<$linenr> endln<$endln> level<$level>\n";
2198 #print "APW: <<$chunks[1][0]>><<$chunks[1][1]>>\n"; 2199 #print "APW: <<$chunks[1][0]>><<$chunks[1][1]>>\n";
2199 if ($#chunks > 0 && $level == 0) { 2200 if ($#chunks > 0 && $level == 0) {
2200 my $allowed = 0; 2201 my $allowed = 0;
2201 my $seen = 0; 2202 my $seen = 0;
2202 my $herectx = $here . "\n"; 2203 my $herectx = $here . "\n";
2203 my $ln = $linenr - 1; 2204 my $ln = $linenr - 1;
2204 for my $chunk (@chunks) { 2205 for my $chunk (@chunks) {
2205 my ($cond, $block) = @{$chunk}; 2206 my ($cond, $block) = @{$chunk};
2206 2207
2207 # If the condition carries leading newlines, then count those as offsets. 2208 # If the condition carries leading newlines, then count those as offsets.
2208 my ($whitespace) = ($cond =~ /^((?:\s*\n[+-])*\s*)/s); 2209 my ($whitespace) = ($cond =~ /^((?:\s*\n[+-])*\s*)/s);
2209 my $offset = statement_rawlines($whitespace) - 1; 2210 my $offset = statement_rawlines($whitespace) - 1;
2210 2211
2211 #print "COND<$cond> whitespace<$whitespace> offset<$offset>\n"; 2212 #print "COND<$cond> whitespace<$whitespace> offset<$offset>\n";
2212 2213
2213 # We have looked at and allowed this specific line. 2214 # We have looked at and allowed this specific line.
2214 $suppress_ifbraces{$ln + $offset} = 1; 2215 $suppress_ifbraces{$ln + $offset} = 1;
2215 2216
2216 $herectx .= "$rawlines[$ln + $offset]\n[...]\n"; 2217 $herectx .= "$rawlines[$ln + $offset]\n[...]\n";
2217 $ln += statement_rawlines($block) - 1; 2218 $ln += statement_rawlines($block) - 1;
2218 2219
2219 substr($block, 0, length($cond), ''); 2220 substr($block, 0, length($cond), '');
2220 2221
2221 $seen++ if ($block =~ /^\s*{/); 2222 $seen++ if ($block =~ /^\s*{/);
2222 2223
2223 #print "cond<$cond> block<$block> allowed<$allowed>\n"; 2224 #print "cond<$cond> block<$block> allowed<$allowed>\n";
2224 if (statement_lines($cond) > 1) { 2225 if (statement_lines($cond) > 1) {
2225 #print "APW: ALLOWED: cond<$cond>\n"; 2226 #print "APW: ALLOWED: cond<$cond>\n";
2226 $allowed = 1; 2227 $allowed = 1;
2227 } 2228 }
2228 if ($block =~/\b(?:if|for|while)\b/) { 2229 if ($block =~/\b(?:if|for|while)\b/) {
2229 #print "APW: ALLOWED: block<$block>\n"; 2230 #print "APW: ALLOWED: block<$block>\n";
2230 $allowed = 1; 2231 $allowed = 1;
2231 } 2232 }
2232 if (statement_block_size($block) > 1) { 2233 if (statement_block_size($block) > 1) {
2233 #print "APW: ALLOWED: lines block<$block>\n"; 2234 #print "APW: ALLOWED: lines block<$block>\n";
2234 $allowed = 1; 2235 $allowed = 1;
2235 } 2236 }
2236 } 2237 }
2237 if ($seen && !$allowed) { 2238 if ($seen && !$allowed) {
2238 WARN("braces {} are not necessary for any arm of this statement\n" . $herectx); 2239 WARN("braces {} are not necessary for any arm of this statement\n" . $herectx);
2239 } 2240 }
2240 } 2241 }
2241 } 2242 }
2242 if (!defined $suppress_ifbraces{$linenr - 1} && 2243 if (!defined $suppress_ifbraces{$linenr - 1} &&
2243 $line =~ /\b(if|while|for|else)\b/) { 2244 $line =~ /\b(if|while|for|else)\b/) {
2244 my $allowed = 0; 2245 my $allowed = 0;
2245 2246
2246 # Check the pre-context. 2247 # Check the pre-context.
2247 if (substr($line, 0, $-[0]) =~ /(\}\s*)$/) { 2248 if (substr($line, 0, $-[0]) =~ /(\}\s*)$/) {
2248 #print "APW: ALLOWED: pre<$1>\n"; 2249 #print "APW: ALLOWED: pre<$1>\n";
2249 $allowed = 1; 2250 $allowed = 1;
2250 } 2251 }
2251 2252
2252 my ($level, $endln, @chunks) = 2253 my ($level, $endln, @chunks) =
2253 ctx_statement_full($linenr, $realcnt, $-[0]); 2254 ctx_statement_full($linenr, $realcnt, $-[0]);
2254 2255
2255 # Check the condition. 2256 # Check the condition.
2256 my ($cond, $block) = @{$chunks[0]}; 2257 my ($cond, $block) = @{$chunks[0]};
2257 #print "CHECKING<$linenr> cond<$cond> block<$block>\n"; 2258 #print "CHECKING<$linenr> cond<$cond> block<$block>\n";
2258 if (defined $cond) { 2259 if (defined $cond) {
2259 substr($block, 0, length($cond), ''); 2260 substr($block, 0, length($cond), '');
2260 } 2261 }
2261 if (statement_lines($cond) > 1) { 2262 if (statement_lines($cond) > 1) {
2262 #print "APW: ALLOWED: cond<$cond>\n"; 2263 #print "APW: ALLOWED: cond<$cond>\n";
2263 $allowed = 1; 2264 $allowed = 1;
2264 } 2265 }
2265 if ($block =~/\b(?:if|for|while)\b/) { 2266 if ($block =~/\b(?:if|for|while)\b/) {
2266 #print "APW: ALLOWED: block<$block>\n"; 2267 #print "APW: ALLOWED: block<$block>\n";
2267 $allowed = 1; 2268 $allowed = 1;
2268 } 2269 }
2269 if (statement_block_size($block) > 1) { 2270 if (statement_block_size($block) > 1) {
2270 #print "APW: ALLOWED: lines block<$block>\n"; 2271 #print "APW: ALLOWED: lines block<$block>\n";
2271 $allowed = 1; 2272 $allowed = 1;
2272 } 2273 }
2273 # Check the post-context. 2274 # Check the post-context.
2274 if (defined $chunks[1]) { 2275 if (defined $chunks[1]) {
2275 my ($cond, $block) = @{$chunks[1]}; 2276 my ($cond, $block) = @{$chunks[1]};
2276 if (defined $cond) { 2277 if (defined $cond) {
2277 substr($block, 0, length($cond), ''); 2278 substr($block, 0, length($cond), '');
2278 } 2279 }
2279 if ($block =~ /^\s*\{/) { 2280 if ($block =~ /^\s*\{/) {
2280 #print "APW: ALLOWED: chunk-1 block<$block>\n"; 2281 #print "APW: ALLOWED: chunk-1 block<$block>\n";
2281 $allowed = 1; 2282 $allowed = 1;
2282 } 2283 }
2283 } 2284 }
2284 if ($level == 0 && $block =~ /^\s*\{/ && !$allowed) { 2285 if ($level == 0 && $block =~ /^\s*\{/ && !$allowed) {
2285 my $herectx = $here . "\n";; 2286 my $herectx = $here . "\n";;
2286 my $cnt = statement_rawlines($block); 2287 my $cnt = statement_rawlines($block);
2287 2288
2288 for (my $n = 0; $n < $cnt; $n++) { 2289 for (my $n = 0; $n < $cnt; $n++) {
2289 $herectx .= raw_line($linenr, $n) . "\n";; 2290 $herectx .= raw_line($linenr, $n) . "\n";;
2290 } 2291 }
2291 2292
2292 WARN("braces {} are not necessary for single statement blocks\n" . $herectx); 2293 WARN("braces {} are not necessary for single statement blocks\n" . $herectx);
2293 } 2294 }
2294 } 2295 }
2295 2296
2296 # don't include deprecated include files (uses RAW line) 2297 # don't include deprecated include files (uses RAW line)
2297 for my $inc (@dep_includes) { 2298 for my $inc (@dep_includes) {
2298 if ($rawline =~ m@^.\s*\#\s*include\s*\<$inc>@) { 2299 if ($rawline =~ m@^.\s*\#\s*include\s*\<$inc>@) {
2299 ERROR("Don't use <$inc>: see Documentation/feature-removal-schedule.txt\n" . $herecurr); 2300 ERROR("Don't use <$inc>: see Documentation/feature-removal-schedule.txt\n" . $herecurr);
2300 } 2301 }
2301 } 2302 }
2302 2303
2303 # don't use deprecated functions 2304 # don't use deprecated functions
2304 for my $func (@dep_functions) { 2305 for my $func (@dep_functions) {
2305 if ($line =~ /\b$func\b/) { 2306 if ($line =~ /\b$func\b/) {
2306 ERROR("Don't use $func(): see Documentation/feature-removal-schedule.txt\n" . $herecurr); 2307 ERROR("Don't use $func(): see Documentation/feature-removal-schedule.txt\n" . $herecurr);
2307 } 2308 }
2308 } 2309 }
2309 2310
2310 # no volatiles please 2311 # no volatiles please
2311 my $asm_volatile = qr{\b(__asm__|asm)\s+(__volatile__|volatile)\b}; 2312 my $asm_volatile = qr{\b(__asm__|asm)\s+(__volatile__|volatile)\b};
2312 if ($line =~ /\bvolatile\b/ && $line !~ /$asm_volatile/) { 2313 if ($line =~ /\bvolatile\b/ && $line !~ /$asm_volatile/) {
2313 WARN("Use of volatile is usually wrong: see Documentation/volatile-considered-harmful.txt\n" . $herecurr); 2314 WARN("Use of volatile is usually wrong: see Documentation/volatile-considered-harmful.txt\n" . $herecurr);
2314 } 2315 }
2315 2316
2316 # SPIN_LOCK_UNLOCKED & RW_LOCK_UNLOCKED are deprecated 2317 # SPIN_LOCK_UNLOCKED & RW_LOCK_UNLOCKED are deprecated
2317 if ($line =~ /\b(SPIN_LOCK_UNLOCKED|RW_LOCK_UNLOCKED)/) { 2318 if ($line =~ /\b(SPIN_LOCK_UNLOCKED|RW_LOCK_UNLOCKED)/) {
2318 ERROR("Use of $1 is deprecated: see Documentation/spinlocks.txt\n" . $herecurr); 2319 ERROR("Use of $1 is deprecated: see Documentation/spinlocks.txt\n" . $herecurr);
2319 } 2320 }
2320 2321
2321 # warn about #if 0 2322 # warn about #if 0
2322 if ($line =~ /^.\s*\#\s*if\s+0\b/) { 2323 if ($line =~ /^.\s*\#\s*if\s+0\b/) {
2323 CHK("if this code is redundant consider removing it\n" . 2324 CHK("if this code is redundant consider removing it\n" .
2324 $herecurr); 2325 $herecurr);
2325 } 2326 }
2326 2327
2327 # check for needless kfree() checks 2328 # check for needless kfree() checks
2328 if ($prevline =~ /\bif\s*\(([^\)]*)\)/) { 2329 if ($prevline =~ /\bif\s*\(([^\)]*)\)/) {
2329 my $expr = $1; 2330 my $expr = $1;
2330 if ($line =~ /\bkfree\(\Q$expr\E\);/) { 2331 if ($line =~ /\bkfree\(\Q$expr\E\);/) {
2331 WARN("kfree(NULL) is safe this check is probably not required\n" . $hereprev); 2332 WARN("kfree(NULL) is safe this check is probably not required\n" . $hereprev);
2332 } 2333 }
2333 } 2334 }
2334 # check for needless usb_free_urb() checks 2335 # check for needless usb_free_urb() checks
2335 if ($prevline =~ /\bif\s*\(([^\)]*)\)/) { 2336 if ($prevline =~ /\bif\s*\(([^\)]*)\)/) {
2336 my $expr = $1; 2337 my $expr = $1;
2337 if ($line =~ /\busb_free_urb\(\Q$expr\E\);/) { 2338 if ($line =~ /\busb_free_urb\(\Q$expr\E\);/) {
2338 WARN("usb_free_urb(NULL) is safe this check is probably not required\n" . $hereprev); 2339 WARN("usb_free_urb(NULL) is safe this check is probably not required\n" . $hereprev);
2339 } 2340 }
2340 } 2341 }
2341 2342
2342 # warn about #ifdefs in C files 2343 # warn about #ifdefs in C files
2343 # if ($line =~ /^.\s*\#\s*if(|n)def/ && ($realfile =~ /\.c$/)) { 2344 # if ($line =~ /^.\s*\#\s*if(|n)def/ && ($realfile =~ /\.c$/)) {
2344 # print "#ifdef in C files should be avoided\n"; 2345 # print "#ifdef in C files should be avoided\n";
2345 # print "$herecurr"; 2346 # print "$herecurr";
2346 # $clean = 0; 2347 # $clean = 0;
2347 # } 2348 # }
2348 2349
2349 # warn about spacing in #ifdefs 2350 # warn about spacing in #ifdefs
2350 if ($line =~ /^.\s*\#\s*(ifdef|ifndef|elif)\s\s+/) { 2351 if ($line =~ /^.\s*\#\s*(ifdef|ifndef|elif)\s\s+/) {
2351 ERROR("exactly one space required after that #$1\n" . $herecurr); 2352 ERROR("exactly one space required after that #$1\n" . $herecurr);
2352 } 2353 }
2353 2354
2354 # check for spinlock_t definitions without a comment. 2355 # check for spinlock_t definitions without a comment.
2355 if ($line =~ /^.\s*(struct\s+mutex|spinlock_t)\s+\S+;/ || 2356 if ($line =~ /^.\s*(struct\s+mutex|spinlock_t)\s+\S+;/ ||
2356 $line =~ /^.\s*(DEFINE_MUTEX)\s*\(/) { 2357 $line =~ /^.\s*(DEFINE_MUTEX)\s*\(/) {
2357 my $which = $1; 2358 my $which = $1;
2358 if (!ctx_has_comment($first_line, $linenr)) { 2359 if (!ctx_has_comment($first_line, $linenr)) {
2359 CHK("$1 definition without comment\n" . $herecurr); 2360 CHK("$1 definition without comment\n" . $herecurr);
2360 } 2361 }
2361 } 2362 }
2362 # check for memory barriers without a comment. 2363 # check for memory barriers without a comment.
2363 if ($line =~ /\b(mb|rmb|wmb|read_barrier_depends|smp_mb|smp_rmb|smp_wmb|smp_read_barrier_depends)\(/) { 2364 if ($line =~ /\b(mb|rmb|wmb|read_barrier_depends|smp_mb|smp_rmb|smp_wmb|smp_read_barrier_depends)\(/) {
2364 if (!ctx_has_comment($first_line, $linenr)) { 2365 if (!ctx_has_comment($first_line, $linenr)) {
2365 CHK("memory barrier without comment\n" . $herecurr); 2366 CHK("memory barrier without comment\n" . $herecurr);
2366 } 2367 }
2367 } 2368 }
2368 # check of hardware specific defines 2369 # check of hardware specific defines
2369 if ($line =~ m@^.\s*\#\s*if.*\b(__i386__|__powerpc64__|__sun__|__s390x__)\b@ && $realfile !~ m@include/asm-@) { 2370 if ($line =~ m@^.\s*\#\s*if.*\b(__i386__|__powerpc64__|__sun__|__s390x__)\b@ && $realfile !~ m@include/asm-@) {
2370 CHK("architecture specific defines should be avoided\n" . $herecurr); 2371 CHK("architecture specific defines should be avoided\n" . $herecurr);
2371 } 2372 }
2372 2373
2373 # check the location of the inline attribute, that it is between 2374 # check the location of the inline attribute, that it is between
2374 # storage class and type. 2375 # storage class and type.
2375 if ($line =~ /\b$Type\s+$Inline\b/ || 2376 if ($line =~ /\b$Type\s+$Inline\b/ ||
2376 $line =~ /\b$Inline\s+$Storage\b/) { 2377 $line =~ /\b$Inline\s+$Storage\b/) {
2377 ERROR("inline keyword should sit between storage class and type\n" . $herecurr); 2378 ERROR("inline keyword should sit between storage class and type\n" . $herecurr);
2378 } 2379 }
2379 2380
2380 # Check for __inline__ and __inline, prefer inline 2381 # Check for __inline__ and __inline, prefer inline
2381 if ($line =~ /\b(__inline__|__inline)\b/) { 2382 if ($line =~ /\b(__inline__|__inline)\b/) {
2382 WARN("plain inline is preferred over $1\n" . $herecurr); 2383 WARN("plain inline is preferred over $1\n" . $herecurr);
2383 } 2384 }
2384 2385
2385 # check for new externs in .c files. 2386 # check for new externs in .c files.
2386 if ($realfile =~ /\.c$/ && defined $stat && 2387 if ($realfile =~ /\.c$/ && defined $stat &&
2387 $stat =~ /^.\s*(?:extern\s+)?$Type\s+($Ident)(\s*)\(/s) 2388 $stat =~ /^.\s*(?:extern\s+)?$Type\s+($Ident)(\s*)\(/s)
2388 { 2389 {
2389 my $function_name = $1; 2390 my $function_name = $1;
2390 my $paren_space = $2; 2391 my $paren_space = $2;
2391 2392
2392 my $s = $stat; 2393 my $s = $stat;
2393 if (defined $cond) { 2394 if (defined $cond) {
2394 substr($s, 0, length($cond), ''); 2395 substr($s, 0, length($cond), '');
2395 } 2396 }
2396 if ($s =~ /^\s*;/ && 2397 if ($s =~ /^\s*;/ &&
2397 $function_name ne 'uninitialized_var') 2398 $function_name ne 'uninitialized_var')
2398 { 2399 {
2399 WARN("externs should be avoided in .c files\n" . $herecurr); 2400 WARN("externs should be avoided in .c files\n" . $herecurr);
2400 } 2401 }
2401 2402
2402 if ($paren_space =~ /\n/) { 2403 if ($paren_space =~ /\n/) {
2403 WARN("arguments for function declarations should follow identifier\n" . $herecurr); 2404 WARN("arguments for function declarations should follow identifier\n" . $herecurr);
2404 } 2405 }
2405 2406
2406 } elsif ($realfile =~ /\.c$/ && defined $stat && 2407 } elsif ($realfile =~ /\.c$/ && defined $stat &&
2407 $stat =~ /^.\s*extern\s+/) 2408 $stat =~ /^.\s*extern\s+/)
2408 { 2409 {
2409 WARN("externs should be avoided in .c files\n" . $herecurr); 2410 WARN("externs should be avoided in .c files\n" . $herecurr);
2410 } 2411 }
2411 2412
2412 # checks for new __setup's 2413 # checks for new __setup's
2413 if ($rawline =~ /\b__setup\("([^"]*)"/) { 2414 if ($rawline =~ /\b__setup\("([^"]*)"/) {
2414 my $name = $1; 2415 my $name = $1;
2415 2416
2416 if (!grep(/$name/, @setup_docs)) { 2417 if (!grep(/$name/, @setup_docs)) {
2417 CHK("__setup appears un-documented -- check Documentation/kernel-parameters.txt\n" . $herecurr); 2418 CHK("__setup appears un-documented -- check Documentation/kernel-parameters.txt\n" . $herecurr);
2418 } 2419 }
2419 } 2420 }
2420 2421
2421 # check for pointless casting of kmalloc return 2422 # check for pointless casting of kmalloc return
2422 if ($line =~ /\*\s*\)\s*k[czm]alloc\b/) { 2423 if ($line =~ /\*\s*\)\s*k[czm]alloc\b/) {
2423 WARN("unnecessary cast may hide bugs, see http://c-faq.com/malloc/mallocnocast.html\n" . $herecurr); 2424 WARN("unnecessary cast may hide bugs, see http://c-faq.com/malloc/mallocnocast.html\n" . $herecurr);
2424 } 2425 }
2425 2426
2426 # check for gcc specific __FUNCTION__ 2427 # check for gcc specific __FUNCTION__
2427 if ($line =~ /__FUNCTION__/) { 2428 if ($line =~ /__FUNCTION__/) {
2428 WARN("__func__ should be used instead of gcc specific __FUNCTION__\n" . $herecurr); 2429 WARN("__func__ should be used instead of gcc specific __FUNCTION__\n" . $herecurr);
2429 } 2430 }
2430 2431
2431 # check for semaphores used as mutexes 2432 # check for semaphores used as mutexes
2432 if ($line =~ /^.\s*(DECLARE_MUTEX|init_MUTEX)\s*\(/) { 2433 if ($line =~ /^.\s*(DECLARE_MUTEX|init_MUTEX)\s*\(/) {
2433 WARN("mutexes are preferred for single holder semaphores\n" . $herecurr); 2434 WARN("mutexes are preferred for single holder semaphores\n" . $herecurr);
2434 } 2435 }
2435 # check for semaphores used as mutexes 2436 # check for semaphores used as mutexes
2436 if ($line =~ /^.\s*init_MUTEX_LOCKED\s*\(/) { 2437 if ($line =~ /^.\s*init_MUTEX_LOCKED\s*\(/) {
2437 WARN("consider using a completion\n" . $herecurr); 2438 WARN("consider using a completion\n" . $herecurr);
2438 } 2439 }
2439 # recommend strict_strto* over simple_strto* 2440 # recommend strict_strto* over simple_strto*
2440 if ($line =~ /\bsimple_(strto.*?)\s*\(/) { 2441 if ($line =~ /\bsimple_(strto.*?)\s*\(/) {
2441 WARN("consider using strict_$1 in preference to simple_$1\n" . $herecurr); 2442 WARN("consider using strict_$1 in preference to simple_$1\n" . $herecurr);
2442 } 2443 }
2443 # check for __initcall(), use device_initcall() explicitly please 2444 # check for __initcall(), use device_initcall() explicitly please
2444 if ($line =~ /^.\s*__initcall\s*\(/) { 2445 if ($line =~ /^.\s*__initcall\s*\(/) {
2445 WARN("please use device_initcall() instead of __initcall()\n" . $herecurr); 2446 WARN("please use device_initcall() instead of __initcall()\n" . $herecurr);
2446 } 2447 }
2447 2448
2448 # use of NR_CPUS is usually wrong 2449 # use of NR_CPUS is usually wrong
2449 # ignore definitions of NR_CPUS and usage to define arrays as likely right 2450 # ignore definitions of NR_CPUS and usage to define arrays as likely right
2450 if ($line =~ /\bNR_CPUS\b/ && 2451 if ($line =~ /\bNR_CPUS\b/ &&
2451 $line !~ /^.\s*\s*#\s*if\b.*\bNR_CPUS\b/ && 2452 $line !~ /^.\s*\s*#\s*if\b.*\bNR_CPUS\b/ &&
2452 $line !~ /^.\s*\s*#\s*define\b.*\bNR_CPUS\b/ && 2453 $line !~ /^.\s*\s*#\s*define\b.*\bNR_CPUS\b/ &&
2453 $line !~ /^.\s*$Declare\s.*\[[^\]]*NR_CPUS[^\]]*\]/ && 2454 $line !~ /^.\s*$Declare\s.*\[[^\]]*NR_CPUS[^\]]*\]/ &&
2454 $line !~ /\[[^\]]*\.\.\.[^\]]*NR_CPUS[^\]]*\]/ && 2455 $line !~ /\[[^\]]*\.\.\.[^\]]*NR_CPUS[^\]]*\]/ &&
2455 $line !~ /\[[^\]]*NR_CPUS[^\]]*\.\.\.[^\]]*\]/) 2456 $line !~ /\[[^\]]*NR_CPUS[^\]]*\.\.\.[^\]]*\]/)
2456 { 2457 {
2457 WARN("usage of NR_CPUS is often wrong - consider using cpu_possible(), num_possible_cpus(), for_each_possible_cpu(), etc\n" . $herecurr); 2458 WARN("usage of NR_CPUS is often wrong - consider using cpu_possible(), num_possible_cpus(), for_each_possible_cpu(), etc\n" . $herecurr);
2458 } 2459 }
2459 2460
2460 # check for %L{u,d,i} in strings 2461 # check for %L{u,d,i} in strings
2461 my $string; 2462 my $string;
2462 while ($line =~ /(?:^|")([X\t]*)(?:"|$)/g) { 2463 while ($line =~ /(?:^|")([X\t]*)(?:"|$)/g) {
2463 $string = substr($rawline, $-[1], $+[1] - $-[1]); 2464 $string = substr($rawline, $-[1], $+[1] - $-[1]);
2464 $string =~ s/%%/__/g; 2465 $string =~ s/%%/__/g;
2465 if ($string =~ /(?<!%)%L[udi]/) { 2466 if ($string =~ /(?<!%)%L[udi]/) {
2466 WARN("\%Ld/%Lu are not-standard C, use %lld/%llu\n" . $herecurr); 2467 WARN("\%Ld/%Lu are not-standard C, use %lld/%llu\n" . $herecurr);
2467 last; 2468 last;
2468 } 2469 }
2469 } 2470 }
2470 2471
2471 # whine mightly about in_atomic 2472 # whine mightly about in_atomic
2472 if ($line =~ /\bin_atomic\s*\(/) { 2473 if ($line =~ /\bin_atomic\s*\(/) {
2473 if ($realfile =~ m@^drivers/@) { 2474 if ($realfile =~ m@^drivers/@) {
2474 ERROR("do not use in_atomic in drivers\n" . $herecurr); 2475 ERROR("do not use in_atomic in drivers\n" . $herecurr);
2475 } else { 2476 } else {
2476 WARN("use of in_atomic() is incorrect outside core kernel code\n" . $herecurr); 2477 WARN("use of in_atomic() is incorrect outside core kernel code\n" . $herecurr);
2477 } 2478 }
2478 } 2479 }
2479 } 2480 }
2480 2481
2481 # If we have no input at all, then there is nothing to report on 2482 # If we have no input at all, then there is nothing to report on
2482 # so just keep quiet. 2483 # so just keep quiet.
2483 if ($#rawlines == -1) { 2484 if ($#rawlines == -1) {
2484 exit(0); 2485 exit(0);
2485 } 2486 }
2486 2487
2487 # In mailback mode only produce a report in the negative, for 2488 # In mailback mode only produce a report in the negative, for
2488 # things that appear to be patches. 2489 # things that appear to be patches.
2489 if ($mailback && ($clean == 1 || !$is_patch)) { 2490 if ($mailback && ($clean == 1 || !$is_patch)) {
2490 exit(0); 2491 exit(0);
2491 } 2492 }
2492 2493
2493 # This is not a patch, and we are are in 'no-patch' mode so 2494 # This is not a patch, and we are are in 'no-patch' mode so
2494 # just keep quiet. 2495 # just keep quiet.
2495 if (!$chk_patch && !$is_patch) { 2496 if (!$chk_patch && !$is_patch) {
2496 exit(0); 2497 exit(0);
2497 } 2498 }
2498 2499
2499 if (!$is_patch) { 2500 if (!$is_patch) {
2500 ERROR("Does not appear to be a unified-diff format patch\n"); 2501 ERROR("Does not appear to be a unified-diff format patch\n");
2501 } 2502 }
2502 if ($is_patch && $chk_signoff && $signoff == 0) { 2503 if ($is_patch && $chk_signoff && $signoff == 0) {
2503 ERROR("Missing Signed-off-by: line(s)\n"); 2504 ERROR("Missing Signed-off-by: line(s)\n");
2504 } 2505 }
2505 2506
2506 print report_dump(); 2507 print report_dump();
2507 if ($summary && !($clean == 1 && $quiet == 1)) { 2508 if ($summary && !($clean == 1 && $quiet == 1)) {
2508 print "$filename " if ($summary_file); 2509 print "$filename " if ($summary_file);
2509 print "total: $cnt_error errors, $cnt_warn warnings, " . 2510 print "total: $cnt_error errors, $cnt_warn warnings, " .
2510 (($check)? "$cnt_chk checks, " : "") . 2511 (($check)? "$cnt_chk checks, " : "") .
2511 "$cnt_lines lines checked\n"; 2512 "$cnt_lines lines checked\n";
2512 print "\n" if ($quiet == 0); 2513 print "\n" if ($quiet == 0);
2513 } 2514 }
2514 2515
2515 if ($clean == 1 && $quiet == 0) { 2516 if ($clean == 1 && $quiet == 0) {
2516 print "$vname has no obvious style problems and is ready for submission.\n" 2517 print "$vname has no obvious style problems and is ready for submission.\n"
2517 } 2518 }
2518 if ($clean == 0 && $quiet == 0) { 2519 if ($clean == 0 && $quiet == 0) {
2519 print "$vname has style problems, please review. If any of these errors\n"; 2520 print "$vname has style problems, please review. If any of these errors\n";
2520 print "are false positives report them to the maintainer, see\n"; 2521 print "are false positives report them to the maintainer, see\n";
2521 print "CHECKPATCH in MAINTAINERS.\n"; 2522 print "CHECKPATCH in MAINTAINERS.\n";
2522 } 2523 }
2523 2524
2524 return $clean; 2525 return $clean;
2525 } 2526 }
2526 2527