xref: /rk3399_rockchip-uboot/scripts/checkpatch.pl (revision 722c07dd6e0c95e835dfd63314ee58236926fbe8)
17551eb4fSHeinrich Schuchardt#!/usr/bin/env perl
2dd88ab32SMasahiro Yamada# (c) 2001, Dave Jones. (the file handling bit)
3dd88ab32SMasahiro Yamada# (c) 2005, Joel Schopp <jschopp@austin.ibm.com> (the ugly bit)
4dd88ab32SMasahiro Yamada# (c) 2007,2008, Andy Whitcroft <apw@uk.ibm.com> (new conditions, test suite)
5dd88ab32SMasahiro Yamada# (c) 2008-2010 Andy Whitcroft <apw@canonical.com>
6dd88ab32SMasahiro Yamada# Licensed under the terms of the GNU GPL License version 2
7dd88ab32SMasahiro Yamada
8dd88ab32SMasahiro Yamadause strict;
97551eb4fSHeinrich Schuchardtuse warnings;
106b9709d9STom Riniuse POSIX;
11c10e0f5bSDan Murphyuse File::Basename;
12c10e0f5bSDan Murphyuse Cwd 'abs_path';
137551eb4fSHeinrich Schuchardtuse Term::ANSIColor qw(:constants);
14dd88ab32SMasahiro Yamada
15dd88ab32SMasahiro Yamadamy $P = $0;
16c10e0f5bSDan Murphymy $D = dirname(abs_path($P));
17dd88ab32SMasahiro Yamada
18dd88ab32SMasahiro Yamadamy $V = '0.32';
19dd88ab32SMasahiro Yamada
20dd88ab32SMasahiro Yamadause Getopt::Long qw(:config no_auto_abbrev);
21dd88ab32SMasahiro Yamada
22dd88ab32SMasahiro Yamadamy $quiet = 0;
23dd88ab32SMasahiro Yamadamy $tree = 1;
24dd88ab32SMasahiro Yamadamy $chk_signoff = 1;
25dd88ab32SMasahiro Yamadamy $chk_patch = 1;
26dd88ab32SMasahiro Yamadamy $tst_only;
27dd88ab32SMasahiro Yamadamy $emacs = 0;
28dd88ab32SMasahiro Yamadamy $terse = 0;
297551eb4fSHeinrich Schuchardtmy $showfile = 0;
30dd88ab32SMasahiro Yamadamy $file = 0;
317551eb4fSHeinrich Schuchardtmy $git = 0;
327551eb4fSHeinrich Schuchardtmy %git_commits = ();
33dd88ab32SMasahiro Yamadamy $check = 0;
347551eb4fSHeinrich Schuchardtmy $check_orig = 0;
35dd88ab32SMasahiro Yamadamy $summary = 1;
36dd88ab32SMasahiro Yamadamy $mailback = 0;
37dd88ab32SMasahiro Yamadamy $summary_file = 0;
38dd88ab32SMasahiro Yamadamy $show_types = 0;
397551eb4fSHeinrich Schuchardtmy $list_types = 0;
406b9709d9STom Rinimy $fix = 0;
416b9709d9STom Rinimy $fix_inplace = 0;
42dd88ab32SMasahiro Yamadamy $root;
43dd88ab32SMasahiro Yamadamy %debug;
446b9709d9STom Rinimy %camelcase = ();
456b9709d9STom Rinimy %use_type = ();
466b9709d9STom Rinimy @use = ();
47dd88ab32SMasahiro Yamadamy %ignore_type = ();
48dd88ab32SMasahiro Yamadamy @ignore = ();
49dd88ab32SMasahiro Yamadamy $help = 0;
50dd88ab32SMasahiro Yamadamy $configuration_file = ".checkpatch.conf";
51dd88ab32SMasahiro Yamadamy $max_line_length = 80;
526b9709d9STom Rinimy $ignore_perl_version = 0;
536b9709d9STom Rinimy $minimum_perl_version = 5.10.0;
547551eb4fSHeinrich Schuchardtmy $min_conf_desc_length = 4;
55c10e0f5bSDan Murphymy $spelling_file = "$D/spelling.txt";
56c10e0f5bSDan Murphymy $codespell = 0;
57c10e0f5bSDan Murphymy $codespellfile = "/usr/share/codespell/dictionary.txt";
587551eb4fSHeinrich Schuchardtmy $conststructsfile = "$D/const_structs.checkpatch";
597551eb4fSHeinrich Schuchardtmy $typedefsfile = "";
607551eb4fSHeinrich Schuchardtmy $color = "auto";
617551eb4fSHeinrich Schuchardtmy $allow_c99_comments = 1;
62dd88ab32SMasahiro Yamada
63dd88ab32SMasahiro Yamadasub help {
64dd88ab32SMasahiro Yamada	my ($exitcode) = @_;
65dd88ab32SMasahiro Yamada
66dd88ab32SMasahiro Yamada	print << "EOM";
67dd88ab32SMasahiro YamadaUsage: $P [OPTION]... [FILE]...
68dd88ab32SMasahiro YamadaVersion: $V
69dd88ab32SMasahiro Yamada
70dd88ab32SMasahiro YamadaOptions:
71dd88ab32SMasahiro Yamada  -q, --quiet                quiet
72dd88ab32SMasahiro Yamada  --no-tree                  run without a kernel tree
73dd88ab32SMasahiro Yamada  --no-signoff               do not check for 'Signed-off-by' line
74dd88ab32SMasahiro Yamada  --patch                    treat FILE as patchfile (default)
75dd88ab32SMasahiro Yamada  --emacs                    emacs compile window format
76dd88ab32SMasahiro Yamada  --terse                    one line per report
777551eb4fSHeinrich Schuchardt  --showfile                 emit diffed file position, not input file position
787551eb4fSHeinrich Schuchardt  -g, --git                  treat FILE as a single commit or git revision range
797551eb4fSHeinrich Schuchardt                             single git commit with:
807551eb4fSHeinrich Schuchardt                               <rev>
817551eb4fSHeinrich Schuchardt                               <rev>^
827551eb4fSHeinrich Schuchardt                               <rev>~n
837551eb4fSHeinrich Schuchardt                             multiple git commits with:
847551eb4fSHeinrich Schuchardt                               <rev1>..<rev2>
857551eb4fSHeinrich Schuchardt                               <rev1>...<rev2>
867551eb4fSHeinrich Schuchardt                               <rev>-<count>
877551eb4fSHeinrich Schuchardt                             git merges are ignored
88dd88ab32SMasahiro Yamada  -f, --file                 treat FILE as regular source file
89dd88ab32SMasahiro Yamada  --subjective, --strict     enable more subjective tests
907551eb4fSHeinrich Schuchardt  --list-types               list the possible message types
916b9709d9STom Rini  --types TYPE(,TYPE2...)    show only these comma separated message types
92dd88ab32SMasahiro Yamada  --ignore TYPE(,TYPE2...)   ignore various comma separated message types
937551eb4fSHeinrich Schuchardt  --show-types               show the specific message type in the output
94dd88ab32SMasahiro Yamada  --max-line-length=n        set the maximum line length, if exceeded, warn
957551eb4fSHeinrich Schuchardt  --min-conf-desc-length=n   set the min description length, if shorter, warn
96dd88ab32SMasahiro Yamada  --root=PATH                PATH to the kernel tree root
97dd88ab32SMasahiro Yamada  --no-summary               suppress the per-file summary
98dd88ab32SMasahiro Yamada  --mailback                 only produce a report in case of warnings/errors
99dd88ab32SMasahiro Yamada  --summary-file             include the filename in summary
100dd88ab32SMasahiro Yamada  --debug KEY=[0|1]          turn on/off debugging of KEY, where KEY is one of
101dd88ab32SMasahiro Yamada                             'values', 'possible', 'type', and 'attr' (default
102dd88ab32SMasahiro Yamada                             is all off)
103dd88ab32SMasahiro Yamada  --test-only=WORD           report only warnings/errors containing WORD
104dd88ab32SMasahiro Yamada                             literally
1056b9709d9STom Rini  --fix                      EXPERIMENTAL - may create horrible results
1066b9709d9STom Rini                             If correctable single-line errors exist, create
1076b9709d9STom Rini                             "<inputfile>.EXPERIMENTAL-checkpatch-fixes"
1086b9709d9STom Rini                             with potential errors corrected to the preferred
1096b9709d9STom Rini                             checkpatch style
1106b9709d9STom Rini  --fix-inplace              EXPERIMENTAL - may create horrible results
1116b9709d9STom Rini                             Is the same as --fix, but overwrites the input
1126b9709d9STom Rini                             file.  It's your fault if there's no backup or git
1136b9709d9STom Rini  --ignore-perl-version      override checking of perl version.  expect
1146b9709d9STom Rini                             runtime errors.
115c10e0f5bSDan Murphy  --codespell                Use the codespell dictionary for spelling/typos
1167551eb4fSHeinrich Schuchardt                             (default:/usr/share/codespell/dictionary.txt)
117c10e0f5bSDan Murphy  --codespellfile            Use this codespell dictionary
1187551eb4fSHeinrich Schuchardt  --typedefsfile             Read additional types from this file
1197551eb4fSHeinrich Schuchardt  --color[=WHEN]             Use colors 'always', 'never', or only when output
1207551eb4fSHeinrich Schuchardt                             is a terminal ('auto'). Default is 'auto'.
121dd88ab32SMasahiro Yamada  -h, --help, --version      display this help and exit
122dd88ab32SMasahiro Yamada
123dd88ab32SMasahiro YamadaWhen FILE is - read standard input.
124dd88ab32SMasahiro YamadaEOM
125dd88ab32SMasahiro Yamada
126dd88ab32SMasahiro Yamada	exit($exitcode);
127dd88ab32SMasahiro Yamada}
128dd88ab32SMasahiro Yamada
1297551eb4fSHeinrich Schuchardtsub uniq {
1307551eb4fSHeinrich Schuchardt	my %seen;
1317551eb4fSHeinrich Schuchardt	return grep { !$seen{$_}++ } @_;
1327551eb4fSHeinrich Schuchardt}
1337551eb4fSHeinrich Schuchardt
1347551eb4fSHeinrich Schuchardtsub list_types {
1357551eb4fSHeinrich Schuchardt	my ($exitcode) = @_;
1367551eb4fSHeinrich Schuchardt
1377551eb4fSHeinrich Schuchardt	my $count = 0;
1387551eb4fSHeinrich Schuchardt
1397551eb4fSHeinrich Schuchardt	local $/ = undef;
1407551eb4fSHeinrich Schuchardt
1417551eb4fSHeinrich Schuchardt	open(my $script, '<', abs_path($P)) or
1427551eb4fSHeinrich Schuchardt	    die "$P: Can't read '$P' $!\n";
1437551eb4fSHeinrich Schuchardt
1447551eb4fSHeinrich Schuchardt	my $text = <$script>;
1457551eb4fSHeinrich Schuchardt	close($script);
1467551eb4fSHeinrich Schuchardt
1477551eb4fSHeinrich Schuchardt	my @types = ();
1487551eb4fSHeinrich Schuchardt	for ($text =~ /\b(?:(?:CHK|WARN|ERROR)\s*\(\s*"([^"]+)")/g) {
1497551eb4fSHeinrich Schuchardt		push (@types, $_);
1507551eb4fSHeinrich Schuchardt	}
1517551eb4fSHeinrich Schuchardt	@types = sort(uniq(@types));
1527551eb4fSHeinrich Schuchardt	print("#\tMessage type\n\n");
1537551eb4fSHeinrich Schuchardt	foreach my $type (@types) {
1547551eb4fSHeinrich Schuchardt		print(++$count . "\t" . $type . "\n");
1557551eb4fSHeinrich Schuchardt	}
1567551eb4fSHeinrich Schuchardt
1577551eb4fSHeinrich Schuchardt	exit($exitcode);
1587551eb4fSHeinrich Schuchardt}
1597551eb4fSHeinrich Schuchardt
160dd88ab32SMasahiro Yamadamy $conf = which_conf($configuration_file);
161dd88ab32SMasahiro Yamadaif (-f $conf) {
162dd88ab32SMasahiro Yamada	my @conf_args;
163dd88ab32SMasahiro Yamada	open(my $conffile, '<', "$conf")
164dd88ab32SMasahiro Yamada	    or warn "$P: Can't find a readable $configuration_file file $!\n";
165dd88ab32SMasahiro Yamada
166dd88ab32SMasahiro Yamada	while (<$conffile>) {
167dd88ab32SMasahiro Yamada		my $line = $_;
168dd88ab32SMasahiro Yamada
169dd88ab32SMasahiro Yamada		$line =~ s/\s*\n?$//g;
170dd88ab32SMasahiro Yamada		$line =~ s/^\s*//g;
171dd88ab32SMasahiro Yamada		$line =~ s/\s+/ /g;
172dd88ab32SMasahiro Yamada
173dd88ab32SMasahiro Yamada		next if ($line =~ m/^\s*#/);
174dd88ab32SMasahiro Yamada		next if ($line =~ m/^\s*$/);
175dd88ab32SMasahiro Yamada
176dd88ab32SMasahiro Yamada		my @words = split(" ", $line);
177dd88ab32SMasahiro Yamada		foreach my $word (@words) {
178dd88ab32SMasahiro Yamada			last if ($word =~ m/^#/);
179dd88ab32SMasahiro Yamada			push (@conf_args, $word);
180dd88ab32SMasahiro Yamada		}
181dd88ab32SMasahiro Yamada	}
182dd88ab32SMasahiro Yamada	close($conffile);
183dd88ab32SMasahiro Yamada	unshift(@ARGV, @conf_args) if @conf_args;
184dd88ab32SMasahiro Yamada}
185dd88ab32SMasahiro Yamada
1867551eb4fSHeinrich Schuchardt# Perl's Getopt::Long allows options to take optional arguments after a space.
1877551eb4fSHeinrich Schuchardt# Prevent --color by itself from consuming other arguments
1887551eb4fSHeinrich Schuchardtforeach (@ARGV) {
1897551eb4fSHeinrich Schuchardt	if ($_ eq "--color" || $_ eq "-color") {
1907551eb4fSHeinrich Schuchardt		$_ = "--color=$color";
1917551eb4fSHeinrich Schuchardt	}
1927551eb4fSHeinrich Schuchardt}
1937551eb4fSHeinrich Schuchardt
194dd88ab32SMasahiro YamadaGetOptions(
195dd88ab32SMasahiro Yamada	'q|quiet+'	=> \$quiet,
196dd88ab32SMasahiro Yamada	'tree!'		=> \$tree,
197dd88ab32SMasahiro Yamada	'signoff!'	=> \$chk_signoff,
198dd88ab32SMasahiro Yamada	'patch!'	=> \$chk_patch,
199dd88ab32SMasahiro Yamada	'emacs!'	=> \$emacs,
200dd88ab32SMasahiro Yamada	'terse!'	=> \$terse,
2017551eb4fSHeinrich Schuchardt	'showfile!'	=> \$showfile,
202dd88ab32SMasahiro Yamada	'f|file!'	=> \$file,
2037551eb4fSHeinrich Schuchardt	'g|git!'	=> \$git,
204dd88ab32SMasahiro Yamada	'subjective!'	=> \$check,
205dd88ab32SMasahiro Yamada	'strict!'	=> \$check,
206dd88ab32SMasahiro Yamada	'ignore=s'	=> \@ignore,
2076b9709d9STom Rini	'types=s'	=> \@use,
208dd88ab32SMasahiro Yamada	'show-types!'	=> \$show_types,
2097551eb4fSHeinrich Schuchardt	'list-types!'	=> \$list_types,
210dd88ab32SMasahiro Yamada	'max-line-length=i' => \$max_line_length,
2117551eb4fSHeinrich Schuchardt	'min-conf-desc-length=i' => \$min_conf_desc_length,
212dd88ab32SMasahiro Yamada	'root=s'	=> \$root,
213dd88ab32SMasahiro Yamada	'summary!'	=> \$summary,
214dd88ab32SMasahiro Yamada	'mailback!'	=> \$mailback,
215dd88ab32SMasahiro Yamada	'summary-file!'	=> \$summary_file,
2166b9709d9STom Rini	'fix!'		=> \$fix,
2176b9709d9STom Rini	'fix-inplace!'	=> \$fix_inplace,
2186b9709d9STom Rini	'ignore-perl-version!' => \$ignore_perl_version,
219dd88ab32SMasahiro Yamada	'debug=s'	=> \%debug,
220dd88ab32SMasahiro Yamada	'test-only=s'	=> \$tst_only,
221c10e0f5bSDan Murphy	'codespell!'	=> \$codespell,
222c10e0f5bSDan Murphy	'codespellfile=s'	=> \$codespellfile,
2237551eb4fSHeinrich Schuchardt	'typedefsfile=s'	=> \$typedefsfile,
2247551eb4fSHeinrich Schuchardt	'color=s'	=> \$color,
2257551eb4fSHeinrich Schuchardt	'no-color'	=> \$color,	#keep old behaviors of -nocolor
2267551eb4fSHeinrich Schuchardt	'nocolor'	=> \$color,	#keep old behaviors of -nocolor
227dd88ab32SMasahiro Yamada	'h|help'	=> \$help,
228dd88ab32SMasahiro Yamada	'version'	=> \$help
229dd88ab32SMasahiro Yamada) or help(1);
230dd88ab32SMasahiro Yamada
231dd88ab32SMasahiro Yamadahelp(0) if ($help);
232dd88ab32SMasahiro Yamada
2337551eb4fSHeinrich Schuchardtlist_types(0) if ($list_types);
2347551eb4fSHeinrich Schuchardt
2356b9709d9STom Rini$fix = 1 if ($fix_inplace);
2367551eb4fSHeinrich Schuchardt$check_orig = $check;
2376b9709d9STom Rini
238dd88ab32SMasahiro Yamadamy $exit = 0;
239dd88ab32SMasahiro Yamada
2406b9709d9STom Riniif ($^V && $^V lt $minimum_perl_version) {
2416b9709d9STom Rini	printf "$P: requires at least perl version %vd\n", $minimum_perl_version;
2426b9709d9STom Rini	if (!$ignore_perl_version) {
2436b9709d9STom Rini		exit(1);
2446b9709d9STom Rini	}
2456b9709d9STom Rini}
2466b9709d9STom Rini
2477551eb4fSHeinrich Schuchardt#if no filenames are given, push '-' to read patch from stdin
248dd88ab32SMasahiro Yamadaif ($#ARGV < 0) {
2497551eb4fSHeinrich Schuchardt	push(@ARGV, '-');
2507551eb4fSHeinrich Schuchardt}
2517551eb4fSHeinrich Schuchardt
2527551eb4fSHeinrich Schuchardtif ($color =~ /^[01]$/) {
2537551eb4fSHeinrich Schuchardt	$color = !$color;
2547551eb4fSHeinrich Schuchardt} elsif ($color =~ /^always$/i) {
2557551eb4fSHeinrich Schuchardt	$color = 1;
2567551eb4fSHeinrich Schuchardt} elsif ($color =~ /^never$/i) {
2577551eb4fSHeinrich Schuchardt	$color = 0;
2587551eb4fSHeinrich Schuchardt} elsif ($color =~ /^auto$/i) {
2597551eb4fSHeinrich Schuchardt	$color = (-t STDOUT);
2607551eb4fSHeinrich Schuchardt} else {
2617551eb4fSHeinrich Schuchardt	die "Invalid color mode: $color\n";
262dd88ab32SMasahiro Yamada}
263dd88ab32SMasahiro Yamada
2646b9709d9STom Rinisub hash_save_array_words {
2656b9709d9STom Rini	my ($hashRef, $arrayRef) = @_;
2666b9709d9STom Rini
2676b9709d9STom Rini	my @array = split(/,/, join(',', @$arrayRef));
2686b9709d9STom Rini	foreach my $word (@array) {
269dd88ab32SMasahiro Yamada		$word =~ s/\s*\n?$//g;
270dd88ab32SMasahiro Yamada		$word =~ s/^\s*//g;
271dd88ab32SMasahiro Yamada		$word =~ s/\s+/ /g;
272dd88ab32SMasahiro Yamada		$word =~ tr/[a-z]/[A-Z]/;
273dd88ab32SMasahiro Yamada
274dd88ab32SMasahiro Yamada		next if ($word =~ m/^\s*#/);
275dd88ab32SMasahiro Yamada		next if ($word =~ m/^\s*$/);
276dd88ab32SMasahiro Yamada
2776b9709d9STom Rini		$hashRef->{$word}++;
278dd88ab32SMasahiro Yamada	}
2796b9709d9STom Rini}
2806b9709d9STom Rini
2816b9709d9STom Rinisub hash_show_words {
2826b9709d9STom Rini	my ($hashRef, $prefix) = @_;
2836b9709d9STom Rini
2847551eb4fSHeinrich Schuchardt	if (keys %$hashRef) {
2857551eb4fSHeinrich Schuchardt		print "\nNOTE: $prefix message types:";
2866b9709d9STom Rini		foreach my $word (sort keys %$hashRef) {
2876b9709d9STom Rini			print " $word";
2886b9709d9STom Rini		}
2897551eb4fSHeinrich Schuchardt		print "\n";
2906b9709d9STom Rini	}
2916b9709d9STom Rini}
2926b9709d9STom Rini
2936b9709d9STom Rinihash_save_array_words(\%ignore_type, \@ignore);
2946b9709d9STom Rinihash_save_array_words(\%use_type, \@use);
295dd88ab32SMasahiro Yamada
296dd88ab32SMasahiro Yamadamy $dbg_values = 0;
297dd88ab32SMasahiro Yamadamy $dbg_possible = 0;
298dd88ab32SMasahiro Yamadamy $dbg_type = 0;
299dd88ab32SMasahiro Yamadamy $dbg_attr = 0;
300dd88ab32SMasahiro Yamadafor my $key (keys %debug) {
301dd88ab32SMasahiro Yamada	## no critic
302dd88ab32SMasahiro Yamada	eval "\${dbg_$key} = '$debug{$key}';";
303dd88ab32SMasahiro Yamada	die "$@" if ($@);
304dd88ab32SMasahiro Yamada}
305dd88ab32SMasahiro Yamada
306dd88ab32SMasahiro Yamadamy $rpt_cleaners = 0;
307dd88ab32SMasahiro Yamada
308dd88ab32SMasahiro Yamadaif ($terse) {
309dd88ab32SMasahiro Yamada	$emacs = 1;
310dd88ab32SMasahiro Yamada	$quiet++;
311dd88ab32SMasahiro Yamada}
312dd88ab32SMasahiro Yamada
313dd88ab32SMasahiro Yamadaif ($tree) {
314dd88ab32SMasahiro Yamada	if (defined $root) {
315dd88ab32SMasahiro Yamada		if (!top_of_kernel_tree($root)) {
316dd88ab32SMasahiro Yamada			die "$P: $root: --root does not point at a valid tree\n";
317dd88ab32SMasahiro Yamada		}
318dd88ab32SMasahiro Yamada	} else {
319dd88ab32SMasahiro Yamada		if (top_of_kernel_tree('.')) {
320dd88ab32SMasahiro Yamada			$root = '.';
321dd88ab32SMasahiro Yamada		} elsif ($0 =~ m@(.*)/scripts/[^/]*$@ &&
322dd88ab32SMasahiro Yamada						top_of_kernel_tree($1)) {
323dd88ab32SMasahiro Yamada			$root = $1;
324dd88ab32SMasahiro Yamada		}
325dd88ab32SMasahiro Yamada	}
326dd88ab32SMasahiro Yamada
327dd88ab32SMasahiro Yamada	if (!defined $root) {
328dd88ab32SMasahiro Yamada		print "Must be run from the top-level dir. of a kernel tree\n";
329dd88ab32SMasahiro Yamada		exit(2);
330dd88ab32SMasahiro Yamada	}
331dd88ab32SMasahiro Yamada}
332dd88ab32SMasahiro Yamada
333dd88ab32SMasahiro Yamadamy $emitted_corrupt = 0;
334dd88ab32SMasahiro Yamada
335dd88ab32SMasahiro Yamadaour $Ident	= qr{
336dd88ab32SMasahiro Yamada			[A-Za-z_][A-Za-z\d_]*
337dd88ab32SMasahiro Yamada			(?:\s*\#\#\s*[A-Za-z_][A-Za-z\d_]*)*
338dd88ab32SMasahiro Yamada		}x;
339dd88ab32SMasahiro Yamadaour $Storage	= qr{extern|static|asmlinkage};
340dd88ab32SMasahiro Yamadaour $Sparse	= qr{
341dd88ab32SMasahiro Yamada			__user|
342dd88ab32SMasahiro Yamada			__kernel|
343dd88ab32SMasahiro Yamada			__force|
344dd88ab32SMasahiro Yamada			__iomem|
345dd88ab32SMasahiro Yamada			__must_check|
346dd88ab32SMasahiro Yamada			__init_refok|
347dd88ab32SMasahiro Yamada			__kprobes|
348dd88ab32SMasahiro Yamada			__ref|
3497551eb4fSHeinrich Schuchardt			__rcu|
3507551eb4fSHeinrich Schuchardt			__private
351dd88ab32SMasahiro Yamada		}x;
3526b9709d9STom Riniour $InitAttributePrefix = qr{__(?:mem|cpu|dev|net_|)};
3536b9709d9STom Riniour $InitAttributeData = qr{$InitAttributePrefix(?:initdata\b)};
3546b9709d9STom Riniour $InitAttributeConst = qr{$InitAttributePrefix(?:initconst\b)};
3556b9709d9STom Riniour $InitAttributeInit = qr{$InitAttributePrefix(?:init\b)};
3566b9709d9STom Riniour $InitAttribute = qr{$InitAttributeData|$InitAttributeConst|$InitAttributeInit};
357dd88ab32SMasahiro Yamada
358dd88ab32SMasahiro Yamada# Notes to $Attribute:
359dd88ab32SMasahiro Yamada# We need \b after 'init' otherwise 'initconst' will cause a false positive in a check
360dd88ab32SMasahiro Yamadaour $Attribute	= qr{
361dd88ab32SMasahiro Yamada			const|
362dd88ab32SMasahiro Yamada			__percpu|
363dd88ab32SMasahiro Yamada			__nocast|
364dd88ab32SMasahiro Yamada			__safe|
3657551eb4fSHeinrich Schuchardt			__bitwise|
366dd88ab32SMasahiro Yamada			__packed__|
367dd88ab32SMasahiro Yamada			__packed2__|
368dd88ab32SMasahiro Yamada			__naked|
369dd88ab32SMasahiro Yamada			__maybe_unused|
370dd88ab32SMasahiro Yamada			__always_unused|
371dd88ab32SMasahiro Yamada			__noreturn|
372dd88ab32SMasahiro Yamada			__used|
373dd88ab32SMasahiro Yamada			__cold|
3747551eb4fSHeinrich Schuchardt			__pure|
375dd88ab32SMasahiro Yamada			__noclone|
376dd88ab32SMasahiro Yamada			__deprecated|
377dd88ab32SMasahiro Yamada			__read_mostly|
378dd88ab32SMasahiro Yamada			__kprobes|
3796b9709d9STom Rini			$InitAttribute|
380dd88ab32SMasahiro Yamada			____cacheline_aligned|
381dd88ab32SMasahiro Yamada			____cacheline_aligned_in_smp|
382dd88ab32SMasahiro Yamada			____cacheline_internodealigned_in_smp|
383dd88ab32SMasahiro Yamada			__weak
384dd88ab32SMasahiro Yamada		  }x;
385dd88ab32SMasahiro Yamadaour $Modifier;
3867551eb4fSHeinrich Schuchardtour $Inline	= qr{inline|__always_inline|noinline|__inline|__inline__};
387dd88ab32SMasahiro Yamadaour $Member	= qr{->$Ident|\.$Ident|\[[^]]*\]};
388dd88ab32SMasahiro Yamadaour $Lval	= qr{$Ident(?:$Member)*};
389dd88ab32SMasahiro Yamada
3906b9709d9STom Riniour $Int_type	= qr{(?i)llu|ull|ll|lu|ul|l|u};
3916b9709d9STom Riniour $Binary	= qr{(?i)0b[01]+$Int_type?};
3926b9709d9STom Riniour $Hex	= qr{(?i)0x[0-9a-f]+$Int_type?};
3936b9709d9STom Riniour $Int	= qr{[0-9]+$Int_type?};
3947551eb4fSHeinrich Schuchardtour $Octal	= qr{0[0-7]+$Int_type?};
395*722c07ddSHeinrich Schuchardtour $String	= qr{(?:\bL)?"[X\t]*"};
396dd88ab32SMasahiro Yamadaour $Float_hex	= qr{(?i)0x[0-9a-f]+p-?[0-9]+[fl]?};
397dd88ab32SMasahiro Yamadaour $Float_dec	= qr{(?i)(?:[0-9]+\.[0-9]*|[0-9]*\.[0-9]+)(?:e-?[0-9]+)?[fl]?};
398dd88ab32SMasahiro Yamadaour $Float_int	= qr{(?i)[0-9]+e-?[0-9]+[fl]?};
399dd88ab32SMasahiro Yamadaour $Float	= qr{$Float_hex|$Float_dec|$Float_int};
4007551eb4fSHeinrich Schuchardtour $Constant	= qr{$Float|$Binary|$Octal|$Hex|$Int};
401dd88ab32SMasahiro Yamadaour $Assignment	= qr{\*\=|/=|%=|\+=|-=|<<=|>>=|&=|\^=|\|=|=};
4027551eb4fSHeinrich Schuchardtour $Compare    = qr{<=|>=|==|!=|<|(?<!-)>};
4036b9709d9STom Riniour $Arithmetic = qr{\+|-|\*|\/|%};
404dd88ab32SMasahiro Yamadaour $Operators	= qr{
405dd88ab32SMasahiro Yamada			<=|>=|==|!=|
406dd88ab32SMasahiro Yamada			=>|->|<<|>>|<|>|!|~|
4076b9709d9STom Rini			&&|\|\||,|\^|\+\+|--|&|\||$Arithmetic
408dd88ab32SMasahiro Yamada		  }x;
409dd88ab32SMasahiro Yamada
4107551eb4fSHeinrich Schuchardtour $c90_Keywords = qr{do|for|while|if|else|return|goto|continue|switch|default|case|break}x;
4117551eb4fSHeinrich Schuchardt
4127551eb4fSHeinrich Schuchardtour $BasicType;
413dd88ab32SMasahiro Yamadaour $NonptrType;
4147551eb4fSHeinrich Schuchardtour $NonptrTypeMisordered;
4156b9709d9STom Riniour $NonptrTypeWithAttr;
416dd88ab32SMasahiro Yamadaour $Type;
4177551eb4fSHeinrich Schuchardtour $TypeMisordered;
418dd88ab32SMasahiro Yamadaour $Declare;
4197551eb4fSHeinrich Schuchardtour $DeclareMisordered;
420dd88ab32SMasahiro Yamada
421dd88ab32SMasahiro Yamadaour $NON_ASCII_UTF8	= qr{
422dd88ab32SMasahiro Yamada	[\xC2-\xDF][\x80-\xBF]               # non-overlong 2-byte
423dd88ab32SMasahiro Yamada	|  \xE0[\xA0-\xBF][\x80-\xBF]        # excluding overlongs
424dd88ab32SMasahiro Yamada	| [\xE1-\xEC\xEE\xEF][\x80-\xBF]{2}  # straight 3-byte
425dd88ab32SMasahiro Yamada	|  \xED[\x80-\x9F][\x80-\xBF]        # excluding surrogates
426dd88ab32SMasahiro Yamada	|  \xF0[\x90-\xBF][\x80-\xBF]{2}     # planes 1-3
427dd88ab32SMasahiro Yamada	| [\xF1-\xF3][\x80-\xBF]{3}          # planes 4-15
428dd88ab32SMasahiro Yamada	|  \xF4[\x80-\x8F][\x80-\xBF]{2}     # plane 16
429dd88ab32SMasahiro Yamada}x;
430dd88ab32SMasahiro Yamada
431dd88ab32SMasahiro Yamadaour $UTF8	= qr{
432dd88ab32SMasahiro Yamada	[\x09\x0A\x0D\x20-\x7E]              # ASCII
433dd88ab32SMasahiro Yamada	| $NON_ASCII_UTF8
434dd88ab32SMasahiro Yamada}x;
435dd88ab32SMasahiro Yamada
4367551eb4fSHeinrich Schuchardtour $typeC99Typedefs = qr{(?:__)?(?:[us]_?)?int_?(?:8|16|32|64)_t};
4377551eb4fSHeinrich Schuchardtour $typeOtherOSTypedefs = qr{(?x:
4387551eb4fSHeinrich Schuchardt	u_(?:char|short|int|long) |          # bsd
4397551eb4fSHeinrich Schuchardt	u(?:nchar|short|int|long)            # sysv
4407551eb4fSHeinrich Schuchardt)};
4417551eb4fSHeinrich Schuchardtour $typeKernelTypedefs = qr{(?x:
442dd88ab32SMasahiro Yamada	(?:__)?(?:u|s|be|le)(?:8|16|32|64)|
443dd88ab32SMasahiro Yamada	atomic_t
444dd88ab32SMasahiro Yamada)};
4457551eb4fSHeinrich Schuchardtour $typeTypedefs = qr{(?x:
4467551eb4fSHeinrich Schuchardt	$typeC99Typedefs\b|
4477551eb4fSHeinrich Schuchardt	$typeOtherOSTypedefs\b|
4487551eb4fSHeinrich Schuchardt	$typeKernelTypedefs\b
4497551eb4fSHeinrich Schuchardt)};
4507551eb4fSHeinrich Schuchardt
4517551eb4fSHeinrich Schuchardtour $zero_initializer = qr{(?:(?:0[xX])?0+$Int_type?|NULL|false)\b};
452dd88ab32SMasahiro Yamada
453dd88ab32SMasahiro Yamadaour $logFunctions = qr{(?x:
4547551eb4fSHeinrich Schuchardt	printk(?:_ratelimited|_once|_deferred_once|_deferred|)|
4556b9709d9STom Rini	(?:[a-z0-9]+_){1,2}(?:printk|emerg|alert|crit|err|warning|warn|notice|info|debug|dbg|vdbg|devel|cont|WARN)(?:_ratelimited|_once|)|
456dd88ab32SMasahiro Yamada	WARN(?:_RATELIMIT|_ONCE|)|
457dd88ab32SMasahiro Yamada	panic|
4586b9709d9STom Rini	MODULE_[A-Z_]+|
4596b9709d9STom Rini	seq_vprintf|seq_printf|seq_puts
460dd88ab32SMasahiro Yamada)};
461dd88ab32SMasahiro Yamada
462dd88ab32SMasahiro Yamadaour $signature_tags = qr{(?xi:
463dd88ab32SMasahiro Yamada	Signed-off-by:|
464dd88ab32SMasahiro Yamada	Acked-by:|
465dd88ab32SMasahiro Yamada	Tested-by:|
466dd88ab32SMasahiro Yamada	Reviewed-by:|
467dd88ab32SMasahiro Yamada	Reported-by:|
4686b9709d9STom Rini	Suggested-by:|
469dd88ab32SMasahiro Yamada	To:|
470dd88ab32SMasahiro Yamada	Cc:
471dd88ab32SMasahiro Yamada)};
472dd88ab32SMasahiro Yamada
4737551eb4fSHeinrich Schuchardtour @typeListMisordered = (
4747551eb4fSHeinrich Schuchardt	qr{char\s+(?:un)?signed},
4757551eb4fSHeinrich Schuchardt	qr{int\s+(?:(?:un)?signed\s+)?short\s},
4767551eb4fSHeinrich Schuchardt	qr{int\s+short(?:\s+(?:un)?signed)},
4777551eb4fSHeinrich Schuchardt	qr{short\s+int(?:\s+(?:un)?signed)},
4787551eb4fSHeinrich Schuchardt	qr{(?:un)?signed\s+int\s+short},
4797551eb4fSHeinrich Schuchardt	qr{short\s+(?:un)?signed},
4807551eb4fSHeinrich Schuchardt	qr{long\s+int\s+(?:un)?signed},
4817551eb4fSHeinrich Schuchardt	qr{int\s+long\s+(?:un)?signed},
4827551eb4fSHeinrich Schuchardt	qr{long\s+(?:un)?signed\s+int},
4837551eb4fSHeinrich Schuchardt	qr{int\s+(?:un)?signed\s+long},
4847551eb4fSHeinrich Schuchardt	qr{int\s+(?:un)?signed},
4857551eb4fSHeinrich Schuchardt	qr{int\s+long\s+long\s+(?:un)?signed},
4867551eb4fSHeinrich Schuchardt	qr{long\s+long\s+int\s+(?:un)?signed},
4877551eb4fSHeinrich Schuchardt	qr{long\s+long\s+(?:un)?signed\s+int},
4887551eb4fSHeinrich Schuchardt	qr{long\s+long\s+(?:un)?signed},
4897551eb4fSHeinrich Schuchardt	qr{long\s+(?:un)?signed},
4907551eb4fSHeinrich Schuchardt);
4917551eb4fSHeinrich Schuchardt
492dd88ab32SMasahiro Yamadaour @typeList = (
493dd88ab32SMasahiro Yamada	qr{void},
4947551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?char},
4957551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?short\s+int},
4967551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?short},
4977551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?int},
4987551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?long\s+int},
4997551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?long\s+long\s+int},
5007551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?long\s+long},
5017551eb4fSHeinrich Schuchardt	qr{(?:(?:un)?signed\s+)?long},
5027551eb4fSHeinrich Schuchardt	qr{(?:un)?signed},
503dd88ab32SMasahiro Yamada	qr{float},
504dd88ab32SMasahiro Yamada	qr{double},
505dd88ab32SMasahiro Yamada	qr{bool},
506dd88ab32SMasahiro Yamada	qr{struct\s+$Ident},
507dd88ab32SMasahiro Yamada	qr{union\s+$Ident},
508dd88ab32SMasahiro Yamada	qr{enum\s+$Ident},
509dd88ab32SMasahiro Yamada	qr{${Ident}_t},
510dd88ab32SMasahiro Yamada	qr{${Ident}_handler},
511dd88ab32SMasahiro Yamada	qr{${Ident}_handler_fn},
5127551eb4fSHeinrich Schuchardt	@typeListMisordered,
513dd88ab32SMasahiro Yamada);
5147551eb4fSHeinrich Schuchardt
5157551eb4fSHeinrich Schuchardtour $C90_int_types = qr{(?x:
5167551eb4fSHeinrich Schuchardt	long\s+long\s+int\s+(?:un)?signed|
5177551eb4fSHeinrich Schuchardt	long\s+long\s+(?:un)?signed\s+int|
5187551eb4fSHeinrich Schuchardt	long\s+long\s+(?:un)?signed|
5197551eb4fSHeinrich Schuchardt	(?:(?:un)?signed\s+)?long\s+long\s+int|
5207551eb4fSHeinrich Schuchardt	(?:(?:un)?signed\s+)?long\s+long|
5217551eb4fSHeinrich Schuchardt	int\s+long\s+long\s+(?:un)?signed|
5227551eb4fSHeinrich Schuchardt	int\s+(?:(?:un)?signed\s+)?long\s+long|
5237551eb4fSHeinrich Schuchardt
5247551eb4fSHeinrich Schuchardt	long\s+int\s+(?:un)?signed|
5257551eb4fSHeinrich Schuchardt	long\s+(?:un)?signed\s+int|
5267551eb4fSHeinrich Schuchardt	long\s+(?:un)?signed|
5277551eb4fSHeinrich Schuchardt	(?:(?:un)?signed\s+)?long\s+int|
5287551eb4fSHeinrich Schuchardt	(?:(?:un)?signed\s+)?long|
5297551eb4fSHeinrich Schuchardt	int\s+long\s+(?:un)?signed|
5307551eb4fSHeinrich Schuchardt	int\s+(?:(?:un)?signed\s+)?long|
5317551eb4fSHeinrich Schuchardt
5327551eb4fSHeinrich Schuchardt	int\s+(?:un)?signed|
5337551eb4fSHeinrich Schuchardt	(?:(?:un)?signed\s+)?int
5347551eb4fSHeinrich Schuchardt)};
5357551eb4fSHeinrich Schuchardt
5367551eb4fSHeinrich Schuchardtour @typeListFile = ();
5376b9709d9STom Riniour @typeListWithAttr = (
5386b9709d9STom Rini	@typeList,
5396b9709d9STom Rini	qr{struct\s+$InitAttribute\s+$Ident},
5406b9709d9STom Rini	qr{union\s+$InitAttribute\s+$Ident},
5416b9709d9STom Rini);
5426b9709d9STom Rini
543dd88ab32SMasahiro Yamadaour @modifierList = (
544dd88ab32SMasahiro Yamada	qr{fastcall},
545dd88ab32SMasahiro Yamada);
5467551eb4fSHeinrich Schuchardtour @modifierListFile = ();
5477551eb4fSHeinrich Schuchardt
5487551eb4fSHeinrich Schuchardtour @mode_permission_funcs = (
5497551eb4fSHeinrich Schuchardt	["module_param", 3],
5507551eb4fSHeinrich Schuchardt	["module_param_(?:array|named|string)", 4],
5517551eb4fSHeinrich Schuchardt	["module_param_array_named", 5],
5527551eb4fSHeinrich Schuchardt	["debugfs_create_(?:file|u8|u16|u32|u64|x8|x16|x32|x64|size_t|atomic_t|bool|blob|regset32|u32_array)", 2],
5537551eb4fSHeinrich Schuchardt	["proc_create(?:_data|)", 2],
5547551eb4fSHeinrich Schuchardt	["(?:CLASS|DEVICE|SENSOR|SENSOR_DEVICE|IIO_DEVICE)_ATTR", 2],
5557551eb4fSHeinrich Schuchardt	["IIO_DEV_ATTR_[A-Z_]+", 1],
5567551eb4fSHeinrich Schuchardt	["SENSOR_(?:DEVICE_|)ATTR_2", 2],
5577551eb4fSHeinrich Schuchardt	["SENSOR_TEMPLATE(?:_2|)", 3],
5587551eb4fSHeinrich Schuchardt	["__ATTR", 2],
5597551eb4fSHeinrich Schuchardt);
5607551eb4fSHeinrich Schuchardt
5617551eb4fSHeinrich Schuchardt#Create a search pattern for all these functions to speed up a loop below
5627551eb4fSHeinrich Schuchardtour $mode_perms_search = "";
5637551eb4fSHeinrich Schuchardtforeach my $entry (@mode_permission_funcs) {
5647551eb4fSHeinrich Schuchardt	$mode_perms_search .= '|' if ($mode_perms_search ne "");
5657551eb4fSHeinrich Schuchardt	$mode_perms_search .= $entry->[0];
5667551eb4fSHeinrich Schuchardt}
5677551eb4fSHeinrich Schuchardt
5687551eb4fSHeinrich Schuchardtour $mode_perms_world_writable = qr{
5697551eb4fSHeinrich Schuchardt	S_IWUGO		|
5707551eb4fSHeinrich Schuchardt	S_IWOTH		|
5717551eb4fSHeinrich Schuchardt	S_IRWXUGO	|
5727551eb4fSHeinrich Schuchardt	S_IALLUGO	|
5737551eb4fSHeinrich Schuchardt	0[0-7][0-7][2367]
5747551eb4fSHeinrich Schuchardt}x;
5757551eb4fSHeinrich Schuchardt
5767551eb4fSHeinrich Schuchardtour %mode_permission_string_types = (
5777551eb4fSHeinrich Schuchardt	"S_IRWXU" => 0700,
5787551eb4fSHeinrich Schuchardt	"S_IRUSR" => 0400,
5797551eb4fSHeinrich Schuchardt	"S_IWUSR" => 0200,
5807551eb4fSHeinrich Schuchardt	"S_IXUSR" => 0100,
5817551eb4fSHeinrich Schuchardt	"S_IRWXG" => 0070,
5827551eb4fSHeinrich Schuchardt	"S_IRGRP" => 0040,
5837551eb4fSHeinrich Schuchardt	"S_IWGRP" => 0020,
5847551eb4fSHeinrich Schuchardt	"S_IXGRP" => 0010,
5857551eb4fSHeinrich Schuchardt	"S_IRWXO" => 0007,
5867551eb4fSHeinrich Schuchardt	"S_IROTH" => 0004,
5877551eb4fSHeinrich Schuchardt	"S_IWOTH" => 0002,
5887551eb4fSHeinrich Schuchardt	"S_IXOTH" => 0001,
5897551eb4fSHeinrich Schuchardt	"S_IRWXUGO" => 0777,
5907551eb4fSHeinrich Schuchardt	"S_IRUGO" => 0444,
5917551eb4fSHeinrich Schuchardt	"S_IWUGO" => 0222,
5927551eb4fSHeinrich Schuchardt	"S_IXUGO" => 0111,
5937551eb4fSHeinrich Schuchardt);
5947551eb4fSHeinrich Schuchardt
5957551eb4fSHeinrich Schuchardt#Create a search pattern for all these strings to speed up a loop below
5967551eb4fSHeinrich Schuchardtour $mode_perms_string_search = "";
5977551eb4fSHeinrich Schuchardtforeach my $entry (keys %mode_permission_string_types) {
5987551eb4fSHeinrich Schuchardt	$mode_perms_string_search .= '|' if ($mode_perms_string_search ne "");
5997551eb4fSHeinrich Schuchardt	$mode_perms_string_search .= $entry;
6007551eb4fSHeinrich Schuchardt}
601dd88ab32SMasahiro Yamada
602dd88ab32SMasahiro Yamadaour $allowed_asm_includes = qr{(?x:
603dd88ab32SMasahiro Yamada	irq|
6047551eb4fSHeinrich Schuchardt	memory|
6057551eb4fSHeinrich Schuchardt	time|
6067551eb4fSHeinrich Schuchardt	reboot
607dd88ab32SMasahiro Yamada)};
608dd88ab32SMasahiro Yamada# memory.h: ARM has a custom one
609dd88ab32SMasahiro Yamada
610c10e0f5bSDan Murphy# Load common spelling mistakes and build regular expression list.
611c10e0f5bSDan Murphymy $misspellings;
612c10e0f5bSDan Murphymy %spelling_fix;
613c10e0f5bSDan Murphy
614c10e0f5bSDan Murphyif (open(my $spelling, '<', $spelling_file)) {
615c10e0f5bSDan Murphy	while (<$spelling>) {
616c10e0f5bSDan Murphy		my $line = $_;
617c10e0f5bSDan Murphy
618c10e0f5bSDan Murphy		$line =~ s/\s*\n?$//g;
619c10e0f5bSDan Murphy		$line =~ s/^\s*//g;
620c10e0f5bSDan Murphy
621c10e0f5bSDan Murphy		next if ($line =~ m/^\s*#/);
622c10e0f5bSDan Murphy		next if ($line =~ m/^\s*$/);
623c10e0f5bSDan Murphy
624c10e0f5bSDan Murphy		my ($suspect, $fix) = split(/\|\|/, $line);
625c10e0f5bSDan Murphy
626c10e0f5bSDan Murphy		$spelling_fix{$suspect} = $fix;
627c10e0f5bSDan Murphy	}
628c10e0f5bSDan Murphy	close($spelling);
629c10e0f5bSDan Murphy} else {
630c10e0f5bSDan Murphy	warn "No typos will be found - file '$spelling_file': $!\n";
631c10e0f5bSDan Murphy}
632c10e0f5bSDan Murphy
633c10e0f5bSDan Murphyif ($codespell) {
634c10e0f5bSDan Murphy	if (open(my $spelling, '<', $codespellfile)) {
635c10e0f5bSDan Murphy		while (<$spelling>) {
636c10e0f5bSDan Murphy			my $line = $_;
637c10e0f5bSDan Murphy
638c10e0f5bSDan Murphy			$line =~ s/\s*\n?$//g;
639c10e0f5bSDan Murphy			$line =~ s/^\s*//g;
640c10e0f5bSDan Murphy
641c10e0f5bSDan Murphy			next if ($line =~ m/^\s*#/);
642c10e0f5bSDan Murphy			next if ($line =~ m/^\s*$/);
643c10e0f5bSDan Murphy			next if ($line =~ m/, disabled/i);
644c10e0f5bSDan Murphy
645c10e0f5bSDan Murphy			$line =~ s/,.*$//;
646c10e0f5bSDan Murphy
647c10e0f5bSDan Murphy			my ($suspect, $fix) = split(/->/, $line);
648c10e0f5bSDan Murphy
649c10e0f5bSDan Murphy			$spelling_fix{$suspect} = $fix;
650c10e0f5bSDan Murphy		}
651c10e0f5bSDan Murphy		close($spelling);
652c10e0f5bSDan Murphy	} else {
653c10e0f5bSDan Murphy		warn "No codespell typos will be found - file '$codespellfile': $!\n";
654c10e0f5bSDan Murphy	}
655c10e0f5bSDan Murphy}
656c10e0f5bSDan Murphy
657c10e0f5bSDan Murphy$misspellings = join("|", sort keys %spelling_fix) if keys %spelling_fix;
658c10e0f5bSDan Murphy
6597551eb4fSHeinrich Schuchardtsub read_words {
6607551eb4fSHeinrich Schuchardt	my ($wordsRef, $file) = @_;
6617551eb4fSHeinrich Schuchardt
6627551eb4fSHeinrich Schuchardt	if (open(my $words, '<', $file)) {
6637551eb4fSHeinrich Schuchardt		while (<$words>) {
6647551eb4fSHeinrich Schuchardt			my $line = $_;
6657551eb4fSHeinrich Schuchardt
6667551eb4fSHeinrich Schuchardt			$line =~ s/\s*\n?$//g;
6677551eb4fSHeinrich Schuchardt			$line =~ s/^\s*//g;
6687551eb4fSHeinrich Schuchardt
6697551eb4fSHeinrich Schuchardt			next if ($line =~ m/^\s*#/);
6707551eb4fSHeinrich Schuchardt			next if ($line =~ m/^\s*$/);
6717551eb4fSHeinrich Schuchardt			if ($line =~ /\s/) {
6727551eb4fSHeinrich Schuchardt				print("$file: '$line' invalid - ignored\n");
6737551eb4fSHeinrich Schuchardt				next;
6747551eb4fSHeinrich Schuchardt			}
6757551eb4fSHeinrich Schuchardt
6767551eb4fSHeinrich Schuchardt			$$wordsRef .= '|' if ($$wordsRef ne "");
6777551eb4fSHeinrich Schuchardt			$$wordsRef .= $line;
6787551eb4fSHeinrich Schuchardt		}
6797551eb4fSHeinrich Schuchardt		close($file);
6807551eb4fSHeinrich Schuchardt		return 1;
6817551eb4fSHeinrich Schuchardt	}
6827551eb4fSHeinrich Schuchardt
6837551eb4fSHeinrich Schuchardt	return 0;
6847551eb4fSHeinrich Schuchardt}
6857551eb4fSHeinrich Schuchardt
6867551eb4fSHeinrich Schuchardtmy $const_structs = "";
6877551eb4fSHeinrich Schuchardtread_words(\$const_structs, $conststructsfile)
6887551eb4fSHeinrich Schuchardt    or warn "No structs that should be const will be found - file '$conststructsfile': $!\n";
6897551eb4fSHeinrich Schuchardt
6907551eb4fSHeinrich Schuchardtmy $typeOtherTypedefs = "";
6917551eb4fSHeinrich Schuchardtif (length($typedefsfile)) {
6927551eb4fSHeinrich Schuchardt	read_words(\$typeOtherTypedefs, $typedefsfile)
6937551eb4fSHeinrich Schuchardt	    or warn "No additional types will be considered - file '$typedefsfile': $!\n";
6947551eb4fSHeinrich Schuchardt}
6957551eb4fSHeinrich Schuchardt$typeTypedefs .= '|' . $typeOtherTypedefs if ($typeOtherTypedefs ne "");
696c10e0f5bSDan Murphy
697dd88ab32SMasahiro Yamadasub build_types {
6987551eb4fSHeinrich Schuchardt	my $mods = "(?x:  \n" . join("|\n  ", (@modifierList, @modifierListFile)) . "\n)";
6997551eb4fSHeinrich Schuchardt	my $all = "(?x:  \n" . join("|\n  ", (@typeList, @typeListFile)) . "\n)";
7007551eb4fSHeinrich Schuchardt	my $Misordered = "(?x:  \n" . join("|\n  ", @typeListMisordered) . "\n)";
7016b9709d9STom Rini	my $allWithAttr = "(?x:  \n" . join("|\n  ", @typeListWithAttr) . "\n)";
702dd88ab32SMasahiro Yamada	$Modifier	= qr{(?:$Attribute|$Sparse|$mods)};
7037551eb4fSHeinrich Schuchardt	$BasicType	= qr{
7047551eb4fSHeinrich Schuchardt				(?:$typeTypedefs\b)|
7057551eb4fSHeinrich Schuchardt				(?:${all}\b)
7067551eb4fSHeinrich Schuchardt		}x;
707dd88ab32SMasahiro Yamada	$NonptrType	= qr{
708dd88ab32SMasahiro Yamada			(?:$Modifier\s+|const\s+)*
709dd88ab32SMasahiro Yamada			(?:
710dd88ab32SMasahiro Yamada				(?:typeof|__typeof__)\s*\([^\)]*\)|
711dd88ab32SMasahiro Yamada				(?:$typeTypedefs\b)|
712dd88ab32SMasahiro Yamada				(?:${all}\b)
713dd88ab32SMasahiro Yamada			)
714dd88ab32SMasahiro Yamada			(?:\s+$Modifier|\s+const)*
715dd88ab32SMasahiro Yamada		  }x;
7167551eb4fSHeinrich Schuchardt	$NonptrTypeMisordered	= qr{
7177551eb4fSHeinrich Schuchardt			(?:$Modifier\s+|const\s+)*
7187551eb4fSHeinrich Schuchardt			(?:
7197551eb4fSHeinrich Schuchardt				(?:${Misordered}\b)
7207551eb4fSHeinrich Schuchardt			)
7217551eb4fSHeinrich Schuchardt			(?:\s+$Modifier|\s+const)*
7227551eb4fSHeinrich Schuchardt		  }x;
7236b9709d9STom Rini	$NonptrTypeWithAttr	= qr{
7246b9709d9STom Rini			(?:$Modifier\s+|const\s+)*
7256b9709d9STom Rini			(?:
7266b9709d9STom Rini				(?:typeof|__typeof__)\s*\([^\)]*\)|
7276b9709d9STom Rini				(?:$typeTypedefs\b)|
7286b9709d9STom Rini				(?:${allWithAttr}\b)
7296b9709d9STom Rini			)
7306b9709d9STom Rini			(?:\s+$Modifier|\s+const)*
7316b9709d9STom Rini		  }x;
732dd88ab32SMasahiro Yamada	$Type	= qr{
733dd88ab32SMasahiro Yamada			$NonptrType
7347551eb4fSHeinrich Schuchardt			(?:(?:\s|\*|\[\])+\s*const|(?:\s|\*\s*(?:const\s*)?|\[\])+|(?:\s*\[\s*\])+)?
735dd88ab32SMasahiro Yamada			(?:\s+$Inline|\s+$Modifier)*
736dd88ab32SMasahiro Yamada		  }x;
7377551eb4fSHeinrich Schuchardt	$TypeMisordered	= qr{
7387551eb4fSHeinrich Schuchardt			$NonptrTypeMisordered
7397551eb4fSHeinrich Schuchardt			(?:(?:\s|\*|\[\])+\s*const|(?:\s|\*\s*(?:const\s*)?|\[\])+|(?:\s*\[\s*\])+)?
7407551eb4fSHeinrich Schuchardt			(?:\s+$Inline|\s+$Modifier)*
7417551eb4fSHeinrich Schuchardt		  }x;
7427551eb4fSHeinrich Schuchardt	$Declare	= qr{(?:$Storage\s+(?:$Inline\s+)?)?$Type};
7437551eb4fSHeinrich Schuchardt	$DeclareMisordered	= qr{(?:$Storage\s+(?:$Inline\s+)?)?$TypeMisordered};
744dd88ab32SMasahiro Yamada}
745dd88ab32SMasahiro Yamadabuild_types();
746dd88ab32SMasahiro Yamada
747dd88ab32SMasahiro Yamadaour $Typecast	= qr{\s*(\(\s*$NonptrType\s*\)){0,1}\s*};
748dd88ab32SMasahiro Yamada
749dd88ab32SMasahiro Yamada# Using $balanced_parens, $LvalOrFunc, or $FuncArg
750dd88ab32SMasahiro Yamada# requires at least perl version v5.10.0
751dd88ab32SMasahiro Yamada# Any use must be runtime checked with $^V
752dd88ab32SMasahiro Yamada
753dd88ab32SMasahiro Yamadaour $balanced_parens = qr/(\((?:[^\(\)]++|(?-1))*\))/;
7547551eb4fSHeinrich Schuchardtour $LvalOrFunc	= qr{((?:[\&\*]\s*)?$Lval)\s*($balanced_parens{0,1})\s*};
7557551eb4fSHeinrich Schuchardtour $FuncArg = qr{$Typecast{0,1}($LvalOrFunc|$Constant|$String)};
7567551eb4fSHeinrich Schuchardt
7577551eb4fSHeinrich Schuchardtour $declaration_macros = qr{(?x:
7587551eb4fSHeinrich Schuchardt	(?:$Storage\s+)?(?:[A-Z_][A-Z0-9]*_){0,2}(?:DEFINE|DECLARE)(?:_[A-Z0-9]+){1,6}\s*\(|
7597551eb4fSHeinrich Schuchardt	(?:$Storage\s+)?[HLP]?LIST_HEAD\s*\(|
7607551eb4fSHeinrich Schuchardt	(?:$Storage\s+)?${Type}\s+uninitialized_var\s*\(
7617551eb4fSHeinrich Schuchardt)};
762dd88ab32SMasahiro Yamada
763dd88ab32SMasahiro Yamadasub deparenthesize {
764dd88ab32SMasahiro Yamada	my ($string) = @_;
765dd88ab32SMasahiro Yamada	return "" if (!defined($string));
7667551eb4fSHeinrich Schuchardt
7677551eb4fSHeinrich Schuchardt	while ($string =~ /^\s*\(.*\)\s*$/) {
7687551eb4fSHeinrich Schuchardt		$string =~ s@^\s*\(\s*@@;
7697551eb4fSHeinrich Schuchardt		$string =~ s@\s*\)\s*$@@;
7707551eb4fSHeinrich Schuchardt	}
7717551eb4fSHeinrich Schuchardt
772dd88ab32SMasahiro Yamada	$string =~ s@\s+@ @g;
7737551eb4fSHeinrich Schuchardt
774dd88ab32SMasahiro Yamada	return $string;
775dd88ab32SMasahiro Yamada}
776dd88ab32SMasahiro Yamada
7776b9709d9STom Rinisub seed_camelcase_file {
7786b9709d9STom Rini	my ($file) = @_;
7796b9709d9STom Rini
7806b9709d9STom Rini	return if (!(-f $file));
7816b9709d9STom Rini
7826b9709d9STom Rini	local $/;
7836b9709d9STom Rini
7846b9709d9STom Rini	open(my $include_file, '<', "$file")
7856b9709d9STom Rini	    or warn "$P: Can't read '$file' $!\n";
7866b9709d9STom Rini	my $text = <$include_file>;
7876b9709d9STom Rini	close($include_file);
7886b9709d9STom Rini
7896b9709d9STom Rini	my @lines = split('\n', $text);
7906b9709d9STom Rini
7916b9709d9STom Rini	foreach my $line (@lines) {
7926b9709d9STom Rini		next if ($line !~ /(?:[A-Z][a-z]|[a-z][A-Z])/);
7936b9709d9STom Rini		if ($line =~ /^[ \t]*(?:#[ \t]*define|typedef\s+$Type)\s+(\w*(?:[A-Z][a-z]|[a-z][A-Z])\w*)/) {
7946b9709d9STom Rini			$camelcase{$1} = 1;
7956b9709d9STom Rini		} elsif ($line =~ /^\s*$Declare\s+(\w*(?:[A-Z][a-z]|[a-z][A-Z])\w*)\s*[\(\[,;]/) {
7966b9709d9STom Rini			$camelcase{$1} = 1;
7976b9709d9STom Rini		} elsif ($line =~ /^\s*(?:union|struct|enum)\s+(\w*(?:[A-Z][a-z]|[a-z][A-Z])\w*)\s*[;\{]/) {
7986b9709d9STom Rini			$camelcase{$1} = 1;
7996b9709d9STom Rini		}
8006b9709d9STom Rini	}
8016b9709d9STom Rini}
8026b9709d9STom Rini
8037551eb4fSHeinrich Schuchardtsub is_maintained_obsolete {
8047551eb4fSHeinrich Schuchardt	my ($filename) = @_;
8057551eb4fSHeinrich Schuchardt
8067551eb4fSHeinrich Schuchardt	return 0 if (!$tree || !(-e "$root/scripts/get_maintainer.pl"));
8077551eb4fSHeinrich Schuchardt
8087551eb4fSHeinrich Schuchardt	my $status = `perl $root/scripts/get_maintainer.pl --status --nom --nol --nogit --nogit-fallback -f $filename 2>&1`;
8097551eb4fSHeinrich Schuchardt
8107551eb4fSHeinrich Schuchardt	return $status =~ /obsolete/i;
8117551eb4fSHeinrich Schuchardt}
8127551eb4fSHeinrich Schuchardt
8136b9709d9STom Rinimy $camelcase_seeded = 0;
8146b9709d9STom Rinisub seed_camelcase_includes {
8156b9709d9STom Rini	return if ($camelcase_seeded);
8166b9709d9STom Rini
8176b9709d9STom Rini	my $files;
8186b9709d9STom Rini	my $camelcase_cache = "";
8196b9709d9STom Rini	my @include_files = ();
8206b9709d9STom Rini
8216b9709d9STom Rini	$camelcase_seeded = 1;
8226b9709d9STom Rini
8236b9709d9STom Rini	if (-e ".git") {
8246b9709d9STom Rini		my $git_last_include_commit = `git log --no-merges --pretty=format:"%h%n" -1 -- include`;
8256b9709d9STom Rini		chomp $git_last_include_commit;
8266b9709d9STom Rini		$camelcase_cache = ".checkpatch-camelcase.git.$git_last_include_commit";
8276b9709d9STom Rini	} else {
8286b9709d9STom Rini		my $last_mod_date = 0;
8296b9709d9STom Rini		$files = `find $root/include -name "*.h"`;
8306b9709d9STom Rini		@include_files = split('\n', $files);
8316b9709d9STom Rini		foreach my $file (@include_files) {
8326b9709d9STom Rini			my $date = POSIX::strftime("%Y%m%d%H%M",
8336b9709d9STom Rini						   localtime((stat $file)[9]));
8346b9709d9STom Rini			$last_mod_date = $date if ($last_mod_date < $date);
8356b9709d9STom Rini		}
8366b9709d9STom Rini		$camelcase_cache = ".checkpatch-camelcase.date.$last_mod_date";
8376b9709d9STom Rini	}
8386b9709d9STom Rini
8396b9709d9STom Rini	if ($camelcase_cache ne "" && -f $camelcase_cache) {
8406b9709d9STom Rini		open(my $camelcase_file, '<', "$camelcase_cache")
8416b9709d9STom Rini		    or warn "$P: Can't read '$camelcase_cache' $!\n";
8426b9709d9STom Rini		while (<$camelcase_file>) {
8436b9709d9STom Rini			chomp;
8446b9709d9STom Rini			$camelcase{$_} = 1;
8456b9709d9STom Rini		}
8466b9709d9STom Rini		close($camelcase_file);
8476b9709d9STom Rini
8486b9709d9STom Rini		return;
8496b9709d9STom Rini	}
8506b9709d9STom Rini
8516b9709d9STom Rini	if (-e ".git") {
8526b9709d9STom Rini		$files = `git ls-files "include/*.h"`;
8536b9709d9STom Rini		@include_files = split('\n', $files);
8546b9709d9STom Rini	}
8556b9709d9STom Rini
8566b9709d9STom Rini	foreach my $file (@include_files) {
8576b9709d9STom Rini		seed_camelcase_file($file);
8586b9709d9STom Rini	}
8596b9709d9STom Rini
8606b9709d9STom Rini	if ($camelcase_cache ne "") {
8616b9709d9STom Rini		unlink glob ".checkpatch-camelcase.*";
8626b9709d9STom Rini		open(my $camelcase_file, '>', "$camelcase_cache")
8636b9709d9STom Rini		    or warn "$P: Can't write '$camelcase_cache' $!\n";
8646b9709d9STom Rini		foreach (sort { lc($a) cmp lc($b) } keys(%camelcase)) {
8656b9709d9STom Rini			print $camelcase_file ("$_\n");
8666b9709d9STom Rini		}
8676b9709d9STom Rini		close($camelcase_file);
8686b9709d9STom Rini	}
8696b9709d9STom Rini}
8706b9709d9STom Rini
8717551eb4fSHeinrich Schuchardtsub git_commit_info {
8727551eb4fSHeinrich Schuchardt	my ($commit, $id, $desc) = @_;
8737551eb4fSHeinrich Schuchardt
8747551eb4fSHeinrich Schuchardt	return ($id, $desc) if ((which("git") eq "") || !(-e ".git"));
8757551eb4fSHeinrich Schuchardt
8767551eb4fSHeinrich Schuchardt	my $output = `git log --no-color --format='%H %s' -1 $commit 2>&1`;
8777551eb4fSHeinrich Schuchardt	$output =~ s/^\s*//gm;
8787551eb4fSHeinrich Schuchardt	my @lines = split("\n", $output);
8797551eb4fSHeinrich Schuchardt
8807551eb4fSHeinrich Schuchardt	return ($id, $desc) if ($#lines < 0);
8817551eb4fSHeinrich Schuchardt
8827551eb4fSHeinrich Schuchardt	if ($lines[0] =~ /^error: short SHA1 $commit is ambiguous\./) {
8837551eb4fSHeinrich Schuchardt# Maybe one day convert this block of bash into something that returns
8847551eb4fSHeinrich Schuchardt# all matching commit ids, but it's very slow...
8857551eb4fSHeinrich Schuchardt#
8867551eb4fSHeinrich Schuchardt#		echo "checking commits $1..."
8877551eb4fSHeinrich Schuchardt#		git rev-list --remotes | grep -i "^$1" |
8887551eb4fSHeinrich Schuchardt#		while read line ; do
8897551eb4fSHeinrich Schuchardt#		    git log --format='%H %s' -1 $line |
8907551eb4fSHeinrich Schuchardt#		    echo "commit $(cut -c 1-12,41-)"
8917551eb4fSHeinrich Schuchardt#		done
8927551eb4fSHeinrich Schuchardt	} elsif ($lines[0] =~ /^fatal: ambiguous argument '$commit': unknown revision or path not in the working tree\./) {
8937551eb4fSHeinrich Schuchardt		$id = undef;
8947551eb4fSHeinrich Schuchardt	} else {
8957551eb4fSHeinrich Schuchardt		$id = substr($lines[0], 0, 12);
8967551eb4fSHeinrich Schuchardt		$desc = substr($lines[0], 41);
8977551eb4fSHeinrich Schuchardt	}
8987551eb4fSHeinrich Schuchardt
8997551eb4fSHeinrich Schuchardt	return ($id, $desc);
9007551eb4fSHeinrich Schuchardt}
9017551eb4fSHeinrich Schuchardt
902dd88ab32SMasahiro Yamada$chk_signoff = 0 if ($file);
903dd88ab32SMasahiro Yamada
904dd88ab32SMasahiro Yamadamy @rawlines = ();
905dd88ab32SMasahiro Yamadamy @lines = ();
9066b9709d9STom Rinimy @fixed = ();
9077551eb4fSHeinrich Schuchardtmy @fixed_inserted = ();
9087551eb4fSHeinrich Schuchardtmy @fixed_deleted = ();
909c10e0f5bSDan Murphymy $fixlinenr = -1;
910c10e0f5bSDan Murphy
9117551eb4fSHeinrich Schuchardt# If input is git commits, extract all commits from the commit expressions.
9127551eb4fSHeinrich Schuchardt# For example, HEAD-3 means we need check 'HEAD, HEAD~1, HEAD~2'.
9137551eb4fSHeinrich Schuchardtdie "$P: No git repository found\n" if ($git && !-e ".git");
9147551eb4fSHeinrich Schuchardt
9157551eb4fSHeinrich Schuchardtif ($git) {
9167551eb4fSHeinrich Schuchardt	my @commits = ();
9177551eb4fSHeinrich Schuchardt	foreach my $commit_expr (@ARGV) {
9187551eb4fSHeinrich Schuchardt		my $git_range;
9197551eb4fSHeinrich Schuchardt		if ($commit_expr =~ m/^(.*)-(\d+)$/) {
9207551eb4fSHeinrich Schuchardt			$git_range = "-$2 $1";
9217551eb4fSHeinrich Schuchardt		} elsif ($commit_expr =~ m/\.\./) {
9227551eb4fSHeinrich Schuchardt			$git_range = "$commit_expr";
9237551eb4fSHeinrich Schuchardt		} else {
9247551eb4fSHeinrich Schuchardt			$git_range = "-1 $commit_expr";
9257551eb4fSHeinrich Schuchardt		}
9267551eb4fSHeinrich Schuchardt		my $lines = `git log --no-color --no-merges --pretty=format:'%H %s' $git_range`;
9277551eb4fSHeinrich Schuchardt		foreach my $line (split(/\n/, $lines)) {
9287551eb4fSHeinrich Schuchardt			$line =~ /^([0-9a-fA-F]{40,40}) (.*)$/;
9297551eb4fSHeinrich Schuchardt			next if (!defined($1) || !defined($2));
9307551eb4fSHeinrich Schuchardt			my $sha1 = $1;
9317551eb4fSHeinrich Schuchardt			my $subject = $2;
9327551eb4fSHeinrich Schuchardt			unshift(@commits, $sha1);
9337551eb4fSHeinrich Schuchardt			$git_commits{$sha1} = $subject;
9347551eb4fSHeinrich Schuchardt		}
9357551eb4fSHeinrich Schuchardt	}
9367551eb4fSHeinrich Schuchardt	die "$P: no git commits after extraction!\n" if (@commits == 0);
9377551eb4fSHeinrich Schuchardt	@ARGV = @commits;
9387551eb4fSHeinrich Schuchardt}
9397551eb4fSHeinrich Schuchardt
9407551eb4fSHeinrich Schuchardtmy $vname;
941dd88ab32SMasahiro Yamadafor my $filename (@ARGV) {
942dd88ab32SMasahiro Yamada	my $FILE;
9437551eb4fSHeinrich Schuchardt	if ($git) {
9447551eb4fSHeinrich Schuchardt		open($FILE, '-|', "git format-patch -M --stdout -1 $filename") ||
9457551eb4fSHeinrich Schuchardt			die "$P: $filename: git format-patch failed - $!\n";
9467551eb4fSHeinrich Schuchardt	} elsif ($file) {
947dd88ab32SMasahiro Yamada		open($FILE, '-|', "diff -u /dev/null $filename") ||
948dd88ab32SMasahiro Yamada			die "$P: $filename: diff failed - $!\n";
949dd88ab32SMasahiro Yamada	} elsif ($filename eq '-') {
950dd88ab32SMasahiro Yamada		open($FILE, '<&STDIN');
951dd88ab32SMasahiro Yamada	} else {
952dd88ab32SMasahiro Yamada		open($FILE, '<', "$filename") ||
953dd88ab32SMasahiro Yamada			die "$P: $filename: open failed - $!\n";
954dd88ab32SMasahiro Yamada	}
955dd88ab32SMasahiro Yamada	if ($filename eq '-') {
956dd88ab32SMasahiro Yamada		$vname = 'Your patch';
9577551eb4fSHeinrich Schuchardt	} elsif ($git) {
9587551eb4fSHeinrich Schuchardt		$vname = "Commit " . substr($filename, 0, 12) . ' ("' . $git_commits{$filename} . '")';
959dd88ab32SMasahiro Yamada	} else {
960dd88ab32SMasahiro Yamada		$vname = $filename;
961dd88ab32SMasahiro Yamada	}
962dd88ab32SMasahiro Yamada	while (<$FILE>) {
963dd88ab32SMasahiro Yamada		chomp;
964dd88ab32SMasahiro Yamada		push(@rawlines, $_);
965dd88ab32SMasahiro Yamada	}
966dd88ab32SMasahiro Yamada	close($FILE);
9677551eb4fSHeinrich Schuchardt
9687551eb4fSHeinrich Schuchardt	if ($#ARGV > 0 && $quiet == 0) {
9697551eb4fSHeinrich Schuchardt		print '-' x length($vname) . "\n";
9707551eb4fSHeinrich Schuchardt		print "$vname\n";
9717551eb4fSHeinrich Schuchardt		print '-' x length($vname) . "\n";
9727551eb4fSHeinrich Schuchardt	}
9737551eb4fSHeinrich Schuchardt
974dd88ab32SMasahiro Yamada	if (!process($filename)) {
975dd88ab32SMasahiro Yamada		$exit = 1;
976dd88ab32SMasahiro Yamada	}
977dd88ab32SMasahiro Yamada	@rawlines = ();
978dd88ab32SMasahiro Yamada	@lines = ();
9796b9709d9STom Rini	@fixed = ();
9807551eb4fSHeinrich Schuchardt	@fixed_inserted = ();
9817551eb4fSHeinrich Schuchardt	@fixed_deleted = ();
9827551eb4fSHeinrich Schuchardt	$fixlinenr = -1;
9837551eb4fSHeinrich Schuchardt	@modifierListFile = ();
9847551eb4fSHeinrich Schuchardt	@typeListFile = ();
9857551eb4fSHeinrich Schuchardt	build_types();
9867551eb4fSHeinrich Schuchardt}
9877551eb4fSHeinrich Schuchardt
9887551eb4fSHeinrich Schuchardtif (!$quiet) {
9897551eb4fSHeinrich Schuchardt	hash_show_words(\%use_type, "Used");
9907551eb4fSHeinrich Schuchardt	hash_show_words(\%ignore_type, "Ignored");
9917551eb4fSHeinrich Schuchardt
9927551eb4fSHeinrich Schuchardt	if ($^V lt 5.10.0) {
9937551eb4fSHeinrich Schuchardt		print << "EOM"
9947551eb4fSHeinrich Schuchardt
9957551eb4fSHeinrich SchuchardtNOTE: perl $^V is not modern enough to detect all possible issues.
9967551eb4fSHeinrich Schuchardt      An upgrade to at least perl v5.10.0 is suggested.
9977551eb4fSHeinrich SchuchardtEOM
9987551eb4fSHeinrich Schuchardt	}
9997551eb4fSHeinrich Schuchardt	if ($exit) {
10007551eb4fSHeinrich Schuchardt		print << "EOM"
10017551eb4fSHeinrich Schuchardt
10027551eb4fSHeinrich SchuchardtNOTE: If any of the errors are false positives, please report
10037551eb4fSHeinrich Schuchardt      them to the maintainer, see CHECKPATCH in MAINTAINERS.
10047551eb4fSHeinrich SchuchardtEOM
10057551eb4fSHeinrich Schuchardt	}
1006dd88ab32SMasahiro Yamada}
1007dd88ab32SMasahiro Yamada
1008dd88ab32SMasahiro Yamadaexit($exit);
1009dd88ab32SMasahiro Yamada
1010dd88ab32SMasahiro Yamadasub top_of_kernel_tree {
1011dd88ab32SMasahiro Yamada	my ($root) = @_;
1012dd88ab32SMasahiro Yamada
1013dd88ab32SMasahiro Yamada	my @tree_check = (
10146b9709d9STom Rini		"COPYING", "CREDITS", "Kbuild", "MAINTAINERS", "Makefile",
1015dd88ab32SMasahiro Yamada		"README", "Documentation", "arch", "include", "drivers",
1016dd88ab32SMasahiro Yamada		"fs", "init", "ipc", "kernel", "lib", "scripts",
1017dd88ab32SMasahiro Yamada	);
1018dd88ab32SMasahiro Yamada
1019dd88ab32SMasahiro Yamada	foreach my $check (@tree_check) {
1020dd88ab32SMasahiro Yamada		if (! -e $root . '/' . $check) {
1021dd88ab32SMasahiro Yamada			return 0;
1022dd88ab32SMasahiro Yamada		}
1023dd88ab32SMasahiro Yamada	}
1024dd88ab32SMasahiro Yamada	return 1;
1025dd88ab32SMasahiro Yamada}
1026dd88ab32SMasahiro Yamada
1027dd88ab32SMasahiro Yamadasub parse_email {
1028dd88ab32SMasahiro Yamada	my ($formatted_email) = @_;
1029dd88ab32SMasahiro Yamada
1030dd88ab32SMasahiro Yamada	my $name = "";
1031dd88ab32SMasahiro Yamada	my $address = "";
1032dd88ab32SMasahiro Yamada	my $comment = "";
1033dd88ab32SMasahiro Yamada
1034dd88ab32SMasahiro Yamada	if ($formatted_email =~ /^(.*)<(\S+\@\S+)>(.*)$/) {
1035dd88ab32SMasahiro Yamada		$name = $1;
1036dd88ab32SMasahiro Yamada		$address = $2;
1037dd88ab32SMasahiro Yamada		$comment = $3 if defined $3;
1038dd88ab32SMasahiro Yamada	} elsif ($formatted_email =~ /^\s*<(\S+\@\S+)>(.*)$/) {
1039dd88ab32SMasahiro Yamada		$address = $1;
1040dd88ab32SMasahiro Yamada		$comment = $2 if defined $2;
1041dd88ab32SMasahiro Yamada	} elsif ($formatted_email =~ /(\S+\@\S+)(.*)$/) {
1042dd88ab32SMasahiro Yamada		$address = $1;
1043dd88ab32SMasahiro Yamada		$comment = $2 if defined $2;
1044dd88ab32SMasahiro Yamada		$formatted_email =~ s/$address.*$//;
1045dd88ab32SMasahiro Yamada		$name = $formatted_email;
10466b9709d9STom Rini		$name = trim($name);
1047dd88ab32SMasahiro Yamada		$name =~ s/^\"|\"$//g;
1048dd88ab32SMasahiro Yamada		# If there's a name left after stripping spaces and
1049dd88ab32SMasahiro Yamada		# leading quotes, and the address doesn't have both
1050dd88ab32SMasahiro Yamada		# leading and trailing angle brackets, the address
1051dd88ab32SMasahiro Yamada		# is invalid. ie:
1052dd88ab32SMasahiro Yamada		#   "joe smith joe@smith.com" bad
1053dd88ab32SMasahiro Yamada		#   "joe smith <joe@smith.com" bad
1054dd88ab32SMasahiro Yamada		if ($name ne "" && $address !~ /^<[^>]+>$/) {
1055dd88ab32SMasahiro Yamada			$name = "";
1056dd88ab32SMasahiro Yamada			$address = "";
1057dd88ab32SMasahiro Yamada			$comment = "";
1058dd88ab32SMasahiro Yamada		}
1059dd88ab32SMasahiro Yamada	}
1060dd88ab32SMasahiro Yamada
10616b9709d9STom Rini	$name = trim($name);
1062dd88ab32SMasahiro Yamada	$name =~ s/^\"|\"$//g;
10636b9709d9STom Rini	$address = trim($address);
1064dd88ab32SMasahiro Yamada	$address =~ s/^\<|\>$//g;
1065dd88ab32SMasahiro Yamada
1066dd88ab32SMasahiro Yamada	if ($name =~ /[^\w \-]/i) { ##has "must quote" chars
1067dd88ab32SMasahiro Yamada		$name =~ s/(?<!\\)"/\\"/g; ##escape quotes
1068dd88ab32SMasahiro Yamada		$name = "\"$name\"";
1069dd88ab32SMasahiro Yamada	}
1070dd88ab32SMasahiro Yamada
1071dd88ab32SMasahiro Yamada	return ($name, $address, $comment);
1072dd88ab32SMasahiro Yamada}
1073dd88ab32SMasahiro Yamada
1074dd88ab32SMasahiro Yamadasub format_email {
1075dd88ab32SMasahiro Yamada	my ($name, $address) = @_;
1076dd88ab32SMasahiro Yamada
1077dd88ab32SMasahiro Yamada	my $formatted_email;
1078dd88ab32SMasahiro Yamada
10796b9709d9STom Rini	$name = trim($name);
1080dd88ab32SMasahiro Yamada	$name =~ s/^\"|\"$//g;
10816b9709d9STom Rini	$address = trim($address);
1082dd88ab32SMasahiro Yamada
1083dd88ab32SMasahiro Yamada	if ($name =~ /[^\w \-]/i) { ##has "must quote" chars
1084dd88ab32SMasahiro Yamada		$name =~ s/(?<!\\)"/\\"/g; ##escape quotes
1085dd88ab32SMasahiro Yamada		$name = "\"$name\"";
1086dd88ab32SMasahiro Yamada	}
1087dd88ab32SMasahiro Yamada
1088dd88ab32SMasahiro Yamada	if ("$name" eq "") {
1089dd88ab32SMasahiro Yamada		$formatted_email = "$address";
1090dd88ab32SMasahiro Yamada	} else {
1091dd88ab32SMasahiro Yamada		$formatted_email = "$name <$address>";
1092dd88ab32SMasahiro Yamada	}
1093dd88ab32SMasahiro Yamada
1094dd88ab32SMasahiro Yamada	return $formatted_email;
1095dd88ab32SMasahiro Yamada}
1096dd88ab32SMasahiro Yamada
10977551eb4fSHeinrich Schuchardtsub which {
10987551eb4fSHeinrich Schuchardt	my ($bin) = @_;
10997551eb4fSHeinrich Schuchardt
11007551eb4fSHeinrich Schuchardt	foreach my $path (split(/:/, $ENV{PATH})) {
11017551eb4fSHeinrich Schuchardt		if (-e "$path/$bin") {
11027551eb4fSHeinrich Schuchardt			return "$path/$bin";
11037551eb4fSHeinrich Schuchardt		}
11047551eb4fSHeinrich Schuchardt	}
11057551eb4fSHeinrich Schuchardt
11067551eb4fSHeinrich Schuchardt	return "";
11077551eb4fSHeinrich Schuchardt}
11087551eb4fSHeinrich Schuchardt
1109dd88ab32SMasahiro Yamadasub which_conf {
1110dd88ab32SMasahiro Yamada	my ($conf) = @_;
1111dd88ab32SMasahiro Yamada
1112dd88ab32SMasahiro Yamada	foreach my $path (split(/:/, ".:$ENV{HOME}:.scripts")) {
1113dd88ab32SMasahiro Yamada		if (-e "$path/$conf") {
1114dd88ab32SMasahiro Yamada			return "$path/$conf";
1115dd88ab32SMasahiro Yamada		}
1116dd88ab32SMasahiro Yamada	}
1117dd88ab32SMasahiro Yamada
1118dd88ab32SMasahiro Yamada	return "";
1119dd88ab32SMasahiro Yamada}
1120dd88ab32SMasahiro Yamada
1121dd88ab32SMasahiro Yamadasub expand_tabs {
1122dd88ab32SMasahiro Yamada	my ($str) = @_;
1123dd88ab32SMasahiro Yamada
1124dd88ab32SMasahiro Yamada	my $res = '';
1125dd88ab32SMasahiro Yamada	my $n = 0;
1126dd88ab32SMasahiro Yamada	for my $c (split(//, $str)) {
1127dd88ab32SMasahiro Yamada		if ($c eq "\t") {
1128dd88ab32SMasahiro Yamada			$res .= ' ';
1129dd88ab32SMasahiro Yamada			$n++;
1130dd88ab32SMasahiro Yamada			for (; ($n % 8) != 0; $n++) {
1131dd88ab32SMasahiro Yamada				$res .= ' ';
1132dd88ab32SMasahiro Yamada			}
1133dd88ab32SMasahiro Yamada			next;
1134dd88ab32SMasahiro Yamada		}
1135dd88ab32SMasahiro Yamada		$res .= $c;
1136dd88ab32SMasahiro Yamada		$n++;
1137dd88ab32SMasahiro Yamada	}
1138dd88ab32SMasahiro Yamada
1139dd88ab32SMasahiro Yamada	return $res;
1140dd88ab32SMasahiro Yamada}
1141dd88ab32SMasahiro Yamadasub copy_spacing {
1142dd88ab32SMasahiro Yamada	(my $res = shift) =~ tr/\t/ /c;
1143dd88ab32SMasahiro Yamada	return $res;
1144dd88ab32SMasahiro Yamada}
1145dd88ab32SMasahiro Yamada
1146dd88ab32SMasahiro Yamadasub line_stats {
1147dd88ab32SMasahiro Yamada	my ($line) = @_;
1148dd88ab32SMasahiro Yamada
1149dd88ab32SMasahiro Yamada	# Drop the diff line leader and expand tabs
1150dd88ab32SMasahiro Yamada	$line =~ s/^.//;
1151dd88ab32SMasahiro Yamada	$line = expand_tabs($line);
1152dd88ab32SMasahiro Yamada
1153dd88ab32SMasahiro Yamada	# Pick the indent from the front of the line.
1154dd88ab32SMasahiro Yamada	my ($white) = ($line =~ /^(\s*)/);
1155dd88ab32SMasahiro Yamada
1156dd88ab32SMasahiro Yamada	return (length($line), length($white));
1157dd88ab32SMasahiro Yamada}
1158dd88ab32SMasahiro Yamada
1159dd88ab32SMasahiro Yamadamy $sanitise_quote = '';
1160dd88ab32SMasahiro Yamada
1161dd88ab32SMasahiro Yamadasub sanitise_line_reset {
1162dd88ab32SMasahiro Yamada	my ($in_comment) = @_;
1163dd88ab32SMasahiro Yamada
1164dd88ab32SMasahiro Yamada	if ($in_comment) {
1165dd88ab32SMasahiro Yamada		$sanitise_quote = '*/';
1166dd88ab32SMasahiro Yamada	} else {
1167dd88ab32SMasahiro Yamada		$sanitise_quote = '';
1168dd88ab32SMasahiro Yamada	}
1169dd88ab32SMasahiro Yamada}
1170dd88ab32SMasahiro Yamadasub sanitise_line {
1171dd88ab32SMasahiro Yamada	my ($line) = @_;
1172dd88ab32SMasahiro Yamada
1173dd88ab32SMasahiro Yamada	my $res = '';
1174dd88ab32SMasahiro Yamada	my $l = '';
1175dd88ab32SMasahiro Yamada
1176dd88ab32SMasahiro Yamada	my $qlen = 0;
1177dd88ab32SMasahiro Yamada	my $off = 0;
1178dd88ab32SMasahiro Yamada	my $c;
1179dd88ab32SMasahiro Yamada
1180dd88ab32SMasahiro Yamada	# Always copy over the diff marker.
1181dd88ab32SMasahiro Yamada	$res = substr($line, 0, 1);
1182dd88ab32SMasahiro Yamada
1183dd88ab32SMasahiro Yamada	for ($off = 1; $off < length($line); $off++) {
1184dd88ab32SMasahiro Yamada		$c = substr($line, $off, 1);
1185dd88ab32SMasahiro Yamada
1186dd88ab32SMasahiro Yamada		# Comments we are wacking completly including the begin
1187dd88ab32SMasahiro Yamada		# and end, all to $;.
1188dd88ab32SMasahiro Yamada		if ($sanitise_quote eq '' && substr($line, $off, 2) eq '/*') {
1189dd88ab32SMasahiro Yamada			$sanitise_quote = '*/';
1190dd88ab32SMasahiro Yamada
1191dd88ab32SMasahiro Yamada			substr($res, $off, 2, "$;$;");
1192dd88ab32SMasahiro Yamada			$off++;
1193dd88ab32SMasahiro Yamada			next;
1194dd88ab32SMasahiro Yamada		}
1195dd88ab32SMasahiro Yamada		if ($sanitise_quote eq '*/' && substr($line, $off, 2) eq '*/') {
1196dd88ab32SMasahiro Yamada			$sanitise_quote = '';
1197dd88ab32SMasahiro Yamada			substr($res, $off, 2, "$;$;");
1198dd88ab32SMasahiro Yamada			$off++;
1199dd88ab32SMasahiro Yamada			next;
1200dd88ab32SMasahiro Yamada		}
1201dd88ab32SMasahiro Yamada		if ($sanitise_quote eq '' && substr($line, $off, 2) eq '//') {
1202dd88ab32SMasahiro Yamada			$sanitise_quote = '//';
1203dd88ab32SMasahiro Yamada
1204dd88ab32SMasahiro Yamada			substr($res, $off, 2, $sanitise_quote);
1205dd88ab32SMasahiro Yamada			$off++;
1206dd88ab32SMasahiro Yamada			next;
1207dd88ab32SMasahiro Yamada		}
1208dd88ab32SMasahiro Yamada
1209dd88ab32SMasahiro Yamada		# A \ in a string means ignore the next character.
1210dd88ab32SMasahiro Yamada		if (($sanitise_quote eq "'" || $sanitise_quote eq '"') &&
1211dd88ab32SMasahiro Yamada		    $c eq "\\") {
1212dd88ab32SMasahiro Yamada			substr($res, $off, 2, 'XX');
1213dd88ab32SMasahiro Yamada			$off++;
1214dd88ab32SMasahiro Yamada			next;
1215dd88ab32SMasahiro Yamada		}
1216dd88ab32SMasahiro Yamada		# Regular quotes.
1217dd88ab32SMasahiro Yamada		if ($c eq "'" || $c eq '"') {
1218dd88ab32SMasahiro Yamada			if ($sanitise_quote eq '') {
1219dd88ab32SMasahiro Yamada				$sanitise_quote = $c;
1220dd88ab32SMasahiro Yamada
1221dd88ab32SMasahiro Yamada				substr($res, $off, 1, $c);
1222dd88ab32SMasahiro Yamada				next;
1223dd88ab32SMasahiro Yamada			} elsif ($sanitise_quote eq $c) {
1224dd88ab32SMasahiro Yamada				$sanitise_quote = '';
1225dd88ab32SMasahiro Yamada			}
1226dd88ab32SMasahiro Yamada		}
1227dd88ab32SMasahiro Yamada
1228dd88ab32SMasahiro Yamada		#print "c<$c> SQ<$sanitise_quote>\n";
1229dd88ab32SMasahiro Yamada		if ($off != 0 && $sanitise_quote eq '*/' && $c ne "\t") {
1230dd88ab32SMasahiro Yamada			substr($res, $off, 1, $;);
1231dd88ab32SMasahiro Yamada		} elsif ($off != 0 && $sanitise_quote eq '//' && $c ne "\t") {
1232dd88ab32SMasahiro Yamada			substr($res, $off, 1, $;);
1233dd88ab32SMasahiro Yamada		} elsif ($off != 0 && $sanitise_quote && $c ne "\t") {
1234dd88ab32SMasahiro Yamada			substr($res, $off, 1, 'X');
1235dd88ab32SMasahiro Yamada		} else {
1236dd88ab32SMasahiro Yamada			substr($res, $off, 1, $c);
1237dd88ab32SMasahiro Yamada		}
1238dd88ab32SMasahiro Yamada	}
1239dd88ab32SMasahiro Yamada
1240dd88ab32SMasahiro Yamada	if ($sanitise_quote eq '//') {
1241dd88ab32SMasahiro Yamada		$sanitise_quote = '';
1242dd88ab32SMasahiro Yamada	}
1243dd88ab32SMasahiro Yamada
1244dd88ab32SMasahiro Yamada	# The pathname on a #include may be surrounded by '<' and '>'.
1245dd88ab32SMasahiro Yamada	if ($res =~ /^.\s*\#\s*include\s+\<(.*)\>/) {
1246dd88ab32SMasahiro Yamada		my $clean = 'X' x length($1);
1247dd88ab32SMasahiro Yamada		$res =~ s@\<.*\>@<$clean>@;
1248dd88ab32SMasahiro Yamada
1249dd88ab32SMasahiro Yamada	# The whole of a #error is a string.
1250dd88ab32SMasahiro Yamada	} elsif ($res =~ /^.\s*\#\s*(?:error|warning)\s+(.*)\b/) {
1251dd88ab32SMasahiro Yamada		my $clean = 'X' x length($1);
1252dd88ab32SMasahiro Yamada		$res =~ s@(\#\s*(?:error|warning)\s+).*@$1$clean@;
1253dd88ab32SMasahiro Yamada	}
1254dd88ab32SMasahiro Yamada
12557551eb4fSHeinrich Schuchardt	if ($allow_c99_comments && $res =~ m@(//.*$)@) {
12567551eb4fSHeinrich Schuchardt		my $match = $1;
12577551eb4fSHeinrich Schuchardt		$res =~ s/\Q$match\E/"$;" x length($match)/e;
12587551eb4fSHeinrich Schuchardt	}
12597551eb4fSHeinrich Schuchardt
1260dd88ab32SMasahiro Yamada	return $res;
1261dd88ab32SMasahiro Yamada}
1262dd88ab32SMasahiro Yamada
12636b9709d9STom Rinisub get_quoted_string {
12646b9709d9STom Rini	my ($line, $rawline) = @_;
12656b9709d9STom Rini
12667551eb4fSHeinrich Schuchardt	return "" if ($line !~ m/($String)/g);
12676b9709d9STom Rini	return substr($rawline, $-[0], $+[0] - $-[0]);
12686b9709d9STom Rini}
12696b9709d9STom Rini
1270dd88ab32SMasahiro Yamadasub ctx_statement_block {
1271dd88ab32SMasahiro Yamada	my ($linenr, $remain, $off) = @_;
1272dd88ab32SMasahiro Yamada	my $line = $linenr - 1;
1273dd88ab32SMasahiro Yamada	my $blk = '';
1274dd88ab32SMasahiro Yamada	my $soff = $off;
1275dd88ab32SMasahiro Yamada	my $coff = $off - 1;
1276dd88ab32SMasahiro Yamada	my $coff_set = 0;
1277dd88ab32SMasahiro Yamada
1278dd88ab32SMasahiro Yamada	my $loff = 0;
1279dd88ab32SMasahiro Yamada
1280dd88ab32SMasahiro Yamada	my $type = '';
1281dd88ab32SMasahiro Yamada	my $level = 0;
1282dd88ab32SMasahiro Yamada	my @stack = ();
1283dd88ab32SMasahiro Yamada	my $p;
1284dd88ab32SMasahiro Yamada	my $c;
1285dd88ab32SMasahiro Yamada	my $len = 0;
1286dd88ab32SMasahiro Yamada
1287dd88ab32SMasahiro Yamada	my $remainder;
1288dd88ab32SMasahiro Yamada	while (1) {
1289dd88ab32SMasahiro Yamada		@stack = (['', 0]) if ($#stack == -1);
1290dd88ab32SMasahiro Yamada
1291dd88ab32SMasahiro Yamada		#warn "CSB: blk<$blk> remain<$remain>\n";
1292dd88ab32SMasahiro Yamada		# If we are about to drop off the end, pull in more
1293dd88ab32SMasahiro Yamada		# context.
1294dd88ab32SMasahiro Yamada		if ($off >= $len) {
1295dd88ab32SMasahiro Yamada			for (; $remain > 0; $line++) {
1296dd88ab32SMasahiro Yamada				last if (!defined $lines[$line]);
1297dd88ab32SMasahiro Yamada				next if ($lines[$line] =~ /^-/);
1298dd88ab32SMasahiro Yamada				$remain--;
1299dd88ab32SMasahiro Yamada				$loff = $len;
1300dd88ab32SMasahiro Yamada				$blk .= $lines[$line] . "\n";
1301dd88ab32SMasahiro Yamada				$len = length($blk);
1302dd88ab32SMasahiro Yamada				$line++;
1303dd88ab32SMasahiro Yamada				last;
1304dd88ab32SMasahiro Yamada			}
1305dd88ab32SMasahiro Yamada			# Bail if there is no further context.
1306dd88ab32SMasahiro Yamada			#warn "CSB: blk<$blk> off<$off> len<$len>\n";
1307dd88ab32SMasahiro Yamada			if ($off >= $len) {
1308dd88ab32SMasahiro Yamada				last;
1309dd88ab32SMasahiro Yamada			}
1310dd88ab32SMasahiro Yamada			if ($level == 0 && substr($blk, $off) =~ /^.\s*#\s*define/) {
1311dd88ab32SMasahiro Yamada				$level++;
1312dd88ab32SMasahiro Yamada				$type = '#';
1313dd88ab32SMasahiro Yamada			}
1314dd88ab32SMasahiro Yamada		}
1315dd88ab32SMasahiro Yamada		$p = $c;
1316dd88ab32SMasahiro Yamada		$c = substr($blk, $off, 1);
1317dd88ab32SMasahiro Yamada		$remainder = substr($blk, $off);
1318dd88ab32SMasahiro Yamada
1319dd88ab32SMasahiro Yamada		#warn "CSB: c<$c> type<$type> level<$level> remainder<$remainder> coff_set<$coff_set>\n";
1320dd88ab32SMasahiro Yamada
1321dd88ab32SMasahiro Yamada		# Handle nested #if/#else.
1322dd88ab32SMasahiro Yamada		if ($remainder =~ /^#\s*(?:ifndef|ifdef|if)\s/) {
1323dd88ab32SMasahiro Yamada			push(@stack, [ $type, $level ]);
1324dd88ab32SMasahiro Yamada		} elsif ($remainder =~ /^#\s*(?:else|elif)\b/) {
1325dd88ab32SMasahiro Yamada			($type, $level) = @{$stack[$#stack - 1]};
1326dd88ab32SMasahiro Yamada		} elsif ($remainder =~ /^#\s*endif\b/) {
1327dd88ab32SMasahiro Yamada			($type, $level) = @{pop(@stack)};
1328dd88ab32SMasahiro Yamada		}
1329dd88ab32SMasahiro Yamada
1330dd88ab32SMasahiro Yamada		# Statement ends at the ';' or a close '}' at the
1331dd88ab32SMasahiro Yamada		# outermost level.
1332dd88ab32SMasahiro Yamada		if ($level == 0 && $c eq ';') {
1333dd88ab32SMasahiro Yamada			last;
1334dd88ab32SMasahiro Yamada		}
1335dd88ab32SMasahiro Yamada
1336dd88ab32SMasahiro Yamada		# An else is really a conditional as long as its not else if
1337dd88ab32SMasahiro Yamada		if ($level == 0 && $coff_set == 0 &&
1338dd88ab32SMasahiro Yamada				(!defined($p) || $p =~ /(?:\s|\}|\+)/) &&
1339dd88ab32SMasahiro Yamada				$remainder =~ /^(else)(?:\s|{)/ &&
1340dd88ab32SMasahiro Yamada				$remainder !~ /^else\s+if\b/) {
1341dd88ab32SMasahiro Yamada			$coff = $off + length($1) - 1;
1342dd88ab32SMasahiro Yamada			$coff_set = 1;
1343dd88ab32SMasahiro Yamada			#warn "CSB: mark coff<$coff> soff<$soff> 1<$1>\n";
1344dd88ab32SMasahiro Yamada			#warn "[" . substr($blk, $soff, $coff - $soff + 1) . "]\n";
1345dd88ab32SMasahiro Yamada		}
1346dd88ab32SMasahiro Yamada
1347dd88ab32SMasahiro Yamada		if (($type eq '' || $type eq '(') && $c eq '(') {
1348dd88ab32SMasahiro Yamada			$level++;
1349dd88ab32SMasahiro Yamada			$type = '(';
1350dd88ab32SMasahiro Yamada		}
1351dd88ab32SMasahiro Yamada		if ($type eq '(' && $c eq ')') {
1352dd88ab32SMasahiro Yamada			$level--;
1353dd88ab32SMasahiro Yamada			$type = ($level != 0)? '(' : '';
1354dd88ab32SMasahiro Yamada
1355dd88ab32SMasahiro Yamada			if ($level == 0 && $coff < $soff) {
1356dd88ab32SMasahiro Yamada				$coff = $off;
1357dd88ab32SMasahiro Yamada				$coff_set = 1;
1358dd88ab32SMasahiro Yamada				#warn "CSB: mark coff<$coff>\n";
1359dd88ab32SMasahiro Yamada			}
1360dd88ab32SMasahiro Yamada		}
1361dd88ab32SMasahiro Yamada		if (($type eq '' || $type eq '{') && $c eq '{') {
1362dd88ab32SMasahiro Yamada			$level++;
1363dd88ab32SMasahiro Yamada			$type = '{';
1364dd88ab32SMasahiro Yamada		}
1365dd88ab32SMasahiro Yamada		if ($type eq '{' && $c eq '}') {
1366dd88ab32SMasahiro Yamada			$level--;
1367dd88ab32SMasahiro Yamada			$type = ($level != 0)? '{' : '';
1368dd88ab32SMasahiro Yamada
1369dd88ab32SMasahiro Yamada			if ($level == 0) {
1370dd88ab32SMasahiro Yamada				if (substr($blk, $off + 1, 1) eq ';') {
1371dd88ab32SMasahiro Yamada					$off++;
1372dd88ab32SMasahiro Yamada				}
1373dd88ab32SMasahiro Yamada				last;
1374dd88ab32SMasahiro Yamada			}
1375dd88ab32SMasahiro Yamada		}
1376dd88ab32SMasahiro Yamada		# Preprocessor commands end at the newline unless escaped.
1377dd88ab32SMasahiro Yamada		if ($type eq '#' && $c eq "\n" && $p ne "\\") {
1378dd88ab32SMasahiro Yamada			$level--;
1379dd88ab32SMasahiro Yamada			$type = '';
1380dd88ab32SMasahiro Yamada			$off++;
1381dd88ab32SMasahiro Yamada			last;
1382dd88ab32SMasahiro Yamada		}
1383dd88ab32SMasahiro Yamada		$off++;
1384dd88ab32SMasahiro Yamada	}
1385dd88ab32SMasahiro Yamada	# We are truly at the end, so shuffle to the next line.
1386dd88ab32SMasahiro Yamada	if ($off == $len) {
1387dd88ab32SMasahiro Yamada		$loff = $len + 1;
1388dd88ab32SMasahiro Yamada		$line++;
1389dd88ab32SMasahiro Yamada		$remain--;
1390dd88ab32SMasahiro Yamada	}
1391dd88ab32SMasahiro Yamada
1392dd88ab32SMasahiro Yamada	my $statement = substr($blk, $soff, $off - $soff + 1);
1393dd88ab32SMasahiro Yamada	my $condition = substr($blk, $soff, $coff - $soff + 1);
1394dd88ab32SMasahiro Yamada
1395dd88ab32SMasahiro Yamada	#warn "STATEMENT<$statement>\n";
1396dd88ab32SMasahiro Yamada	#warn "CONDITION<$condition>\n";
1397dd88ab32SMasahiro Yamada
1398dd88ab32SMasahiro Yamada	#print "coff<$coff> soff<$off> loff<$loff>\n";
1399dd88ab32SMasahiro Yamada
1400dd88ab32SMasahiro Yamada	return ($statement, $condition,
1401dd88ab32SMasahiro Yamada			$line, $remain + 1, $off - $loff + 1, $level);
1402dd88ab32SMasahiro Yamada}
1403dd88ab32SMasahiro Yamada
1404dd88ab32SMasahiro Yamadasub statement_lines {
1405dd88ab32SMasahiro Yamada	my ($stmt) = @_;
1406dd88ab32SMasahiro Yamada
1407dd88ab32SMasahiro Yamada	# Strip the diff line prefixes and rip blank lines at start and end.
1408dd88ab32SMasahiro Yamada	$stmt =~ s/(^|\n)./$1/g;
1409dd88ab32SMasahiro Yamada	$stmt =~ s/^\s*//;
1410dd88ab32SMasahiro Yamada	$stmt =~ s/\s*$//;
1411dd88ab32SMasahiro Yamada
1412dd88ab32SMasahiro Yamada	my @stmt_lines = ($stmt =~ /\n/g);
1413dd88ab32SMasahiro Yamada
1414dd88ab32SMasahiro Yamada	return $#stmt_lines + 2;
1415dd88ab32SMasahiro Yamada}
1416dd88ab32SMasahiro Yamada
1417dd88ab32SMasahiro Yamadasub statement_rawlines {
1418dd88ab32SMasahiro Yamada	my ($stmt) = @_;
1419dd88ab32SMasahiro Yamada
1420dd88ab32SMasahiro Yamada	my @stmt_lines = ($stmt =~ /\n/g);
1421dd88ab32SMasahiro Yamada
1422dd88ab32SMasahiro Yamada	return $#stmt_lines + 2;
1423dd88ab32SMasahiro Yamada}
1424dd88ab32SMasahiro Yamada
1425dd88ab32SMasahiro Yamadasub statement_block_size {
1426dd88ab32SMasahiro Yamada	my ($stmt) = @_;
1427dd88ab32SMasahiro Yamada
1428dd88ab32SMasahiro Yamada	$stmt =~ s/(^|\n)./$1/g;
1429dd88ab32SMasahiro Yamada	$stmt =~ s/^\s*{//;
1430dd88ab32SMasahiro Yamada	$stmt =~ s/}\s*$//;
1431dd88ab32SMasahiro Yamada	$stmt =~ s/^\s*//;
1432dd88ab32SMasahiro Yamada	$stmt =~ s/\s*$//;
1433dd88ab32SMasahiro Yamada
1434dd88ab32SMasahiro Yamada	my @stmt_lines = ($stmt =~ /\n/g);
1435dd88ab32SMasahiro Yamada	my @stmt_statements = ($stmt =~ /;/g);
1436dd88ab32SMasahiro Yamada
1437dd88ab32SMasahiro Yamada	my $stmt_lines = $#stmt_lines + 2;
1438dd88ab32SMasahiro Yamada	my $stmt_statements = $#stmt_statements + 1;
1439dd88ab32SMasahiro Yamada
1440dd88ab32SMasahiro Yamada	if ($stmt_lines > $stmt_statements) {
1441dd88ab32SMasahiro Yamada		return $stmt_lines;
1442dd88ab32SMasahiro Yamada	} else {
1443dd88ab32SMasahiro Yamada		return $stmt_statements;
1444dd88ab32SMasahiro Yamada	}
1445dd88ab32SMasahiro Yamada}
1446dd88ab32SMasahiro Yamada
1447dd88ab32SMasahiro Yamadasub ctx_statement_full {
1448dd88ab32SMasahiro Yamada	my ($linenr, $remain, $off) = @_;
1449dd88ab32SMasahiro Yamada	my ($statement, $condition, $level);
1450dd88ab32SMasahiro Yamada
1451dd88ab32SMasahiro Yamada	my (@chunks);
1452dd88ab32SMasahiro Yamada
1453dd88ab32SMasahiro Yamada	# Grab the first conditional/block pair.
1454dd88ab32SMasahiro Yamada	($statement, $condition, $linenr, $remain, $off, $level) =
1455dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $remain, $off);
1456dd88ab32SMasahiro Yamada	#print "F: c<$condition> s<$statement> remain<$remain>\n";
1457dd88ab32SMasahiro Yamada	push(@chunks, [ $condition, $statement ]);
1458dd88ab32SMasahiro Yamada	if (!($remain > 0 && $condition =~ /^\s*(?:\n[+-])?\s*(?:if|else|do)\b/s)) {
1459dd88ab32SMasahiro Yamada		return ($level, $linenr, @chunks);
1460dd88ab32SMasahiro Yamada	}
1461dd88ab32SMasahiro Yamada
1462dd88ab32SMasahiro Yamada	# Pull in the following conditional/block pairs and see if they
1463dd88ab32SMasahiro Yamada	# could continue the statement.
1464dd88ab32SMasahiro Yamada	for (;;) {
1465dd88ab32SMasahiro Yamada		($statement, $condition, $linenr, $remain, $off, $level) =
1466dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $remain, $off);
1467dd88ab32SMasahiro Yamada		#print "C: c<$condition> s<$statement> remain<$remain>\n";
1468dd88ab32SMasahiro Yamada		last if (!($remain > 0 && $condition =~ /^(?:\s*\n[+-])*\s*(?:else|do)\b/s));
1469dd88ab32SMasahiro Yamada		#print "C: push\n";
1470dd88ab32SMasahiro Yamada		push(@chunks, [ $condition, $statement ]);
1471dd88ab32SMasahiro Yamada	}
1472dd88ab32SMasahiro Yamada
1473dd88ab32SMasahiro Yamada	return ($level, $linenr, @chunks);
1474dd88ab32SMasahiro Yamada}
1475dd88ab32SMasahiro Yamada
1476dd88ab32SMasahiro Yamadasub ctx_block_get {
1477dd88ab32SMasahiro Yamada	my ($linenr, $remain, $outer, $open, $close, $off) = @_;
1478dd88ab32SMasahiro Yamada	my $line;
1479dd88ab32SMasahiro Yamada	my $start = $linenr - 1;
1480dd88ab32SMasahiro Yamada	my $blk = '';
1481dd88ab32SMasahiro Yamada	my @o;
1482dd88ab32SMasahiro Yamada	my @c;
1483dd88ab32SMasahiro Yamada	my @res = ();
1484dd88ab32SMasahiro Yamada
1485dd88ab32SMasahiro Yamada	my $level = 0;
1486dd88ab32SMasahiro Yamada	my @stack = ($level);
1487dd88ab32SMasahiro Yamada	for ($line = $start; $remain > 0; $line++) {
1488dd88ab32SMasahiro Yamada		next if ($rawlines[$line] =~ /^-/);
1489dd88ab32SMasahiro Yamada		$remain--;
1490dd88ab32SMasahiro Yamada
1491dd88ab32SMasahiro Yamada		$blk .= $rawlines[$line];
1492dd88ab32SMasahiro Yamada
1493dd88ab32SMasahiro Yamada		# Handle nested #if/#else.
1494dd88ab32SMasahiro Yamada		if ($lines[$line] =~ /^.\s*#\s*(?:ifndef|ifdef|if)\s/) {
1495dd88ab32SMasahiro Yamada			push(@stack, $level);
1496dd88ab32SMasahiro Yamada		} elsif ($lines[$line] =~ /^.\s*#\s*(?:else|elif)\b/) {
1497dd88ab32SMasahiro Yamada			$level = $stack[$#stack - 1];
1498dd88ab32SMasahiro Yamada		} elsif ($lines[$line] =~ /^.\s*#\s*endif\b/) {
1499dd88ab32SMasahiro Yamada			$level = pop(@stack);
1500dd88ab32SMasahiro Yamada		}
1501dd88ab32SMasahiro Yamada
1502dd88ab32SMasahiro Yamada		foreach my $c (split(//, $lines[$line])) {
1503dd88ab32SMasahiro Yamada			##print "C<$c>L<$level><$open$close>O<$off>\n";
1504dd88ab32SMasahiro Yamada			if ($off > 0) {
1505dd88ab32SMasahiro Yamada				$off--;
1506dd88ab32SMasahiro Yamada				next;
1507dd88ab32SMasahiro Yamada			}
1508dd88ab32SMasahiro Yamada
1509dd88ab32SMasahiro Yamada			if ($c eq $close && $level > 0) {
1510dd88ab32SMasahiro Yamada				$level--;
1511dd88ab32SMasahiro Yamada				last if ($level == 0);
1512dd88ab32SMasahiro Yamada			} elsif ($c eq $open) {
1513dd88ab32SMasahiro Yamada				$level++;
1514dd88ab32SMasahiro Yamada			}
1515dd88ab32SMasahiro Yamada		}
1516dd88ab32SMasahiro Yamada
1517dd88ab32SMasahiro Yamada		if (!$outer || $level <= 1) {
1518dd88ab32SMasahiro Yamada			push(@res, $rawlines[$line]);
1519dd88ab32SMasahiro Yamada		}
1520dd88ab32SMasahiro Yamada
1521dd88ab32SMasahiro Yamada		last if ($level == 0);
1522dd88ab32SMasahiro Yamada	}
1523dd88ab32SMasahiro Yamada
1524dd88ab32SMasahiro Yamada	return ($level, @res);
1525dd88ab32SMasahiro Yamada}
1526dd88ab32SMasahiro Yamadasub ctx_block_outer {
1527dd88ab32SMasahiro Yamada	my ($linenr, $remain) = @_;
1528dd88ab32SMasahiro Yamada
1529dd88ab32SMasahiro Yamada	my ($level, @r) = ctx_block_get($linenr, $remain, 1, '{', '}', 0);
1530dd88ab32SMasahiro Yamada	return @r;
1531dd88ab32SMasahiro Yamada}
1532dd88ab32SMasahiro Yamadasub ctx_block {
1533dd88ab32SMasahiro Yamada	my ($linenr, $remain) = @_;
1534dd88ab32SMasahiro Yamada
1535dd88ab32SMasahiro Yamada	my ($level, @r) = ctx_block_get($linenr, $remain, 0, '{', '}', 0);
1536dd88ab32SMasahiro Yamada	return @r;
1537dd88ab32SMasahiro Yamada}
1538dd88ab32SMasahiro Yamadasub ctx_statement {
1539dd88ab32SMasahiro Yamada	my ($linenr, $remain, $off) = @_;
1540dd88ab32SMasahiro Yamada
1541dd88ab32SMasahiro Yamada	my ($level, @r) = ctx_block_get($linenr, $remain, 0, '(', ')', $off);
1542dd88ab32SMasahiro Yamada	return @r;
1543dd88ab32SMasahiro Yamada}
1544dd88ab32SMasahiro Yamadasub ctx_block_level {
1545dd88ab32SMasahiro Yamada	my ($linenr, $remain) = @_;
1546dd88ab32SMasahiro Yamada
1547dd88ab32SMasahiro Yamada	return ctx_block_get($linenr, $remain, 0, '{', '}', 0);
1548dd88ab32SMasahiro Yamada}
1549dd88ab32SMasahiro Yamadasub ctx_statement_level {
1550dd88ab32SMasahiro Yamada	my ($linenr, $remain, $off) = @_;
1551dd88ab32SMasahiro Yamada
1552dd88ab32SMasahiro Yamada	return ctx_block_get($linenr, $remain, 0, '(', ')', $off);
1553dd88ab32SMasahiro Yamada}
1554dd88ab32SMasahiro Yamada
1555dd88ab32SMasahiro Yamadasub ctx_locate_comment {
1556dd88ab32SMasahiro Yamada	my ($first_line, $end_line) = @_;
1557dd88ab32SMasahiro Yamada
1558dd88ab32SMasahiro Yamada	# Catch a comment on the end of the line itself.
1559dd88ab32SMasahiro Yamada	my ($current_comment) = ($rawlines[$end_line - 1] =~ m@.*(/\*.*\*/)\s*(?:\\\s*)?$@);
1560dd88ab32SMasahiro Yamada	return $current_comment if (defined $current_comment);
1561dd88ab32SMasahiro Yamada
1562dd88ab32SMasahiro Yamada	# Look through the context and try and figure out if there is a
1563dd88ab32SMasahiro Yamada	# comment.
1564dd88ab32SMasahiro Yamada	my $in_comment = 0;
1565dd88ab32SMasahiro Yamada	$current_comment = '';
1566dd88ab32SMasahiro Yamada	for (my $linenr = $first_line; $linenr < $end_line; $linenr++) {
1567dd88ab32SMasahiro Yamada		my $line = $rawlines[$linenr - 1];
1568dd88ab32SMasahiro Yamada		#warn "           $line\n";
1569dd88ab32SMasahiro Yamada		if ($linenr == $first_line and $line =~ m@^.\s*\*@) {
1570dd88ab32SMasahiro Yamada			$in_comment = 1;
1571dd88ab32SMasahiro Yamada		}
1572dd88ab32SMasahiro Yamada		if ($line =~ m@/\*@) {
1573dd88ab32SMasahiro Yamada			$in_comment = 1;
1574dd88ab32SMasahiro Yamada		}
1575dd88ab32SMasahiro Yamada		if (!$in_comment && $current_comment ne '') {
1576dd88ab32SMasahiro Yamada			$current_comment = '';
1577dd88ab32SMasahiro Yamada		}
1578dd88ab32SMasahiro Yamada		$current_comment .= $line . "\n" if ($in_comment);
1579dd88ab32SMasahiro Yamada		if ($line =~ m@\*/@) {
1580dd88ab32SMasahiro Yamada			$in_comment = 0;
1581dd88ab32SMasahiro Yamada		}
1582dd88ab32SMasahiro Yamada	}
1583dd88ab32SMasahiro Yamada
1584dd88ab32SMasahiro Yamada	chomp($current_comment);
1585dd88ab32SMasahiro Yamada	return($current_comment);
1586dd88ab32SMasahiro Yamada}
1587dd88ab32SMasahiro Yamadasub ctx_has_comment {
1588dd88ab32SMasahiro Yamada	my ($first_line, $end_line) = @_;
1589dd88ab32SMasahiro Yamada	my $cmt = ctx_locate_comment($first_line, $end_line);
1590dd88ab32SMasahiro Yamada
1591dd88ab32SMasahiro Yamada	##print "LINE: $rawlines[$end_line - 1 ]\n";
1592dd88ab32SMasahiro Yamada	##print "CMMT: $cmt\n";
1593dd88ab32SMasahiro Yamada
1594dd88ab32SMasahiro Yamada	return ($cmt ne '');
1595dd88ab32SMasahiro Yamada}
1596dd88ab32SMasahiro Yamada
1597dd88ab32SMasahiro Yamadasub raw_line {
1598dd88ab32SMasahiro Yamada	my ($linenr, $cnt) = @_;
1599dd88ab32SMasahiro Yamada
1600dd88ab32SMasahiro Yamada	my $offset = $linenr - 1;
1601dd88ab32SMasahiro Yamada	$cnt++;
1602dd88ab32SMasahiro Yamada
1603dd88ab32SMasahiro Yamada	my $line;
1604dd88ab32SMasahiro Yamada	while ($cnt) {
1605dd88ab32SMasahiro Yamada		$line = $rawlines[$offset++];
1606dd88ab32SMasahiro Yamada		next if (defined($line) && $line =~ /^-/);
1607dd88ab32SMasahiro Yamada		$cnt--;
1608dd88ab32SMasahiro Yamada	}
1609dd88ab32SMasahiro Yamada
1610dd88ab32SMasahiro Yamada	return $line;
1611dd88ab32SMasahiro Yamada}
1612dd88ab32SMasahiro Yamada
1613dd88ab32SMasahiro Yamadasub cat_vet {
1614dd88ab32SMasahiro Yamada	my ($vet) = @_;
1615dd88ab32SMasahiro Yamada	my ($res, $coded);
1616dd88ab32SMasahiro Yamada
1617dd88ab32SMasahiro Yamada	$res = '';
1618dd88ab32SMasahiro Yamada	while ($vet =~ /([^[:cntrl:]]*)([[:cntrl:]]|$)/g) {
1619dd88ab32SMasahiro Yamada		$res .= $1;
1620dd88ab32SMasahiro Yamada		if ($2 ne '') {
1621dd88ab32SMasahiro Yamada			$coded = sprintf("^%c", unpack('C', $2) + 64);
1622dd88ab32SMasahiro Yamada			$res .= $coded;
1623dd88ab32SMasahiro Yamada		}
1624dd88ab32SMasahiro Yamada	}
1625dd88ab32SMasahiro Yamada	$res =~ s/$/\$/;
1626dd88ab32SMasahiro Yamada
1627dd88ab32SMasahiro Yamada	return $res;
1628dd88ab32SMasahiro Yamada}
1629dd88ab32SMasahiro Yamada
1630dd88ab32SMasahiro Yamadamy $av_preprocessor = 0;
1631dd88ab32SMasahiro Yamadamy $av_pending;
1632dd88ab32SMasahiro Yamadamy @av_paren_type;
1633dd88ab32SMasahiro Yamadamy $av_pend_colon;
1634dd88ab32SMasahiro Yamada
1635dd88ab32SMasahiro Yamadasub annotate_reset {
1636dd88ab32SMasahiro Yamada	$av_preprocessor = 0;
1637dd88ab32SMasahiro Yamada	$av_pending = '_';
1638dd88ab32SMasahiro Yamada	@av_paren_type = ('E');
1639dd88ab32SMasahiro Yamada	$av_pend_colon = 'O';
1640dd88ab32SMasahiro Yamada}
1641dd88ab32SMasahiro Yamada
1642dd88ab32SMasahiro Yamadasub annotate_values {
1643dd88ab32SMasahiro Yamada	my ($stream, $type) = @_;
1644dd88ab32SMasahiro Yamada
1645dd88ab32SMasahiro Yamada	my $res;
1646dd88ab32SMasahiro Yamada	my $var = '_' x length($stream);
1647dd88ab32SMasahiro Yamada	my $cur = $stream;
1648dd88ab32SMasahiro Yamada
1649dd88ab32SMasahiro Yamada	print "$stream\n" if ($dbg_values > 1);
1650dd88ab32SMasahiro Yamada
1651dd88ab32SMasahiro Yamada	while (length($cur)) {
1652dd88ab32SMasahiro Yamada		@av_paren_type = ('E') if ($#av_paren_type < 0);
1653dd88ab32SMasahiro Yamada		print " <" . join('', @av_paren_type) .
1654dd88ab32SMasahiro Yamada				"> <$type> <$av_pending>" if ($dbg_values > 1);
1655dd88ab32SMasahiro Yamada		if ($cur =~ /^(\s+)/o) {
1656dd88ab32SMasahiro Yamada			print "WS($1)\n" if ($dbg_values > 1);
1657dd88ab32SMasahiro Yamada			if ($1 =~ /\n/ && $av_preprocessor) {
1658dd88ab32SMasahiro Yamada				$type = pop(@av_paren_type);
1659dd88ab32SMasahiro Yamada				$av_preprocessor = 0;
1660dd88ab32SMasahiro Yamada			}
1661dd88ab32SMasahiro Yamada
1662dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\(\s*$Type\s*)\)/ && $av_pending eq '_') {
1663dd88ab32SMasahiro Yamada			print "CAST($1)\n" if ($dbg_values > 1);
1664dd88ab32SMasahiro Yamada			push(@av_paren_type, $type);
1665dd88ab32SMasahiro Yamada			$type = 'c';
1666dd88ab32SMasahiro Yamada
1667dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Type)\s*(?:$Ident|,|\)|\(|\s*$)/) {
1668dd88ab32SMasahiro Yamada			print "DECLARE($1)\n" if ($dbg_values > 1);
1669dd88ab32SMasahiro Yamada			$type = 'T';
1670dd88ab32SMasahiro Yamada
1671dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Modifier)\s*/) {
1672dd88ab32SMasahiro Yamada			print "MODIFIER($1)\n" if ($dbg_values > 1);
1673dd88ab32SMasahiro Yamada			$type = 'T';
1674dd88ab32SMasahiro Yamada
1675dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\#\s*define\s*$Ident)(\(?)/o) {
1676dd88ab32SMasahiro Yamada			print "DEFINE($1,$2)\n" if ($dbg_values > 1);
1677dd88ab32SMasahiro Yamada			$av_preprocessor = 1;
1678dd88ab32SMasahiro Yamada			push(@av_paren_type, $type);
1679dd88ab32SMasahiro Yamada			if ($2 ne '') {
1680dd88ab32SMasahiro Yamada				$av_pending = 'N';
1681dd88ab32SMasahiro Yamada			}
1682dd88ab32SMasahiro Yamada			$type = 'E';
1683dd88ab32SMasahiro Yamada
1684dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\#\s*(?:undef\s*$Ident|include\b))/o) {
1685dd88ab32SMasahiro Yamada			print "UNDEF($1)\n" if ($dbg_values > 1);
1686dd88ab32SMasahiro Yamada			$av_preprocessor = 1;
1687dd88ab32SMasahiro Yamada			push(@av_paren_type, $type);
1688dd88ab32SMasahiro Yamada
1689dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\#\s*(?:ifdef|ifndef|if))/o) {
1690dd88ab32SMasahiro Yamada			print "PRE_START($1)\n" if ($dbg_values > 1);
1691dd88ab32SMasahiro Yamada			$av_preprocessor = 1;
1692dd88ab32SMasahiro Yamada
1693dd88ab32SMasahiro Yamada			push(@av_paren_type, $type);
1694dd88ab32SMasahiro Yamada			push(@av_paren_type, $type);
1695dd88ab32SMasahiro Yamada			$type = 'E';
1696dd88ab32SMasahiro Yamada
1697dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\#\s*(?:else|elif))/o) {
1698dd88ab32SMasahiro Yamada			print "PRE_RESTART($1)\n" if ($dbg_values > 1);
1699dd88ab32SMasahiro Yamada			$av_preprocessor = 1;
1700dd88ab32SMasahiro Yamada
1701dd88ab32SMasahiro Yamada			push(@av_paren_type, $av_paren_type[$#av_paren_type]);
1702dd88ab32SMasahiro Yamada
1703dd88ab32SMasahiro Yamada			$type = 'E';
1704dd88ab32SMasahiro Yamada
1705dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\#\s*(?:endif))/o) {
1706dd88ab32SMasahiro Yamada			print "PRE_END($1)\n" if ($dbg_values > 1);
1707dd88ab32SMasahiro Yamada
1708dd88ab32SMasahiro Yamada			$av_preprocessor = 1;
1709dd88ab32SMasahiro Yamada
1710dd88ab32SMasahiro Yamada			# Assume all arms of the conditional end as this
1711dd88ab32SMasahiro Yamada			# one does, and continue as if the #endif was not here.
1712dd88ab32SMasahiro Yamada			pop(@av_paren_type);
1713dd88ab32SMasahiro Yamada			push(@av_paren_type, $type);
1714dd88ab32SMasahiro Yamada			$type = 'E';
1715dd88ab32SMasahiro Yamada
1716dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\\\n)/o) {
1717dd88ab32SMasahiro Yamada			print "PRECONT($1)\n" if ($dbg_values > 1);
1718dd88ab32SMasahiro Yamada
1719dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(__attribute__)\s*\(?/o) {
1720dd88ab32SMasahiro Yamada			print "ATTR($1)\n" if ($dbg_values > 1);
1721dd88ab32SMasahiro Yamada			$av_pending = $type;
1722dd88ab32SMasahiro Yamada			$type = 'N';
1723dd88ab32SMasahiro Yamada
1724dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(sizeof)\s*(\()?/o) {
1725dd88ab32SMasahiro Yamada			print "SIZEOF($1)\n" if ($dbg_values > 1);
1726dd88ab32SMasahiro Yamada			if (defined $2) {
1727dd88ab32SMasahiro Yamada				$av_pending = 'V';
1728dd88ab32SMasahiro Yamada			}
1729dd88ab32SMasahiro Yamada			$type = 'N';
1730dd88ab32SMasahiro Yamada
1731dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(if|while|for)\b/o) {
1732dd88ab32SMasahiro Yamada			print "COND($1)\n" if ($dbg_values > 1);
1733dd88ab32SMasahiro Yamada			$av_pending = 'E';
1734dd88ab32SMasahiro Yamada			$type = 'N';
1735dd88ab32SMasahiro Yamada
1736dd88ab32SMasahiro Yamada		} elsif ($cur =~/^(case)/o) {
1737dd88ab32SMasahiro Yamada			print "CASE($1)\n" if ($dbg_values > 1);
1738dd88ab32SMasahiro Yamada			$av_pend_colon = 'C';
1739dd88ab32SMasahiro Yamada			$type = 'N';
1740dd88ab32SMasahiro Yamada
1741dd88ab32SMasahiro Yamada		} elsif ($cur =~/^(return|else|goto|typeof|__typeof__)\b/o) {
1742dd88ab32SMasahiro Yamada			print "KEYWORD($1)\n" if ($dbg_values > 1);
1743dd88ab32SMasahiro Yamada			$type = 'N';
1744dd88ab32SMasahiro Yamada
1745dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\()/o) {
1746dd88ab32SMasahiro Yamada			print "PAREN('$1')\n" if ($dbg_values > 1);
1747dd88ab32SMasahiro Yamada			push(@av_paren_type, $av_pending);
1748dd88ab32SMasahiro Yamada			$av_pending = '_';
1749dd88ab32SMasahiro Yamada			$type = 'N';
1750dd88ab32SMasahiro Yamada
1751dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\))/o) {
1752dd88ab32SMasahiro Yamada			my $new_type = pop(@av_paren_type);
1753dd88ab32SMasahiro Yamada			if ($new_type ne '_') {
1754dd88ab32SMasahiro Yamada				$type = $new_type;
1755dd88ab32SMasahiro Yamada				print "PAREN('$1') -> $type\n"
1756dd88ab32SMasahiro Yamada							if ($dbg_values > 1);
1757dd88ab32SMasahiro Yamada			} else {
1758dd88ab32SMasahiro Yamada				print "PAREN('$1')\n" if ($dbg_values > 1);
1759dd88ab32SMasahiro Yamada			}
1760dd88ab32SMasahiro Yamada
1761dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Ident)\s*\(/o) {
1762dd88ab32SMasahiro Yamada			print "FUNC($1)\n" if ($dbg_values > 1);
1763dd88ab32SMasahiro Yamada			$type = 'V';
1764dd88ab32SMasahiro Yamada			$av_pending = 'V';
1765dd88ab32SMasahiro Yamada
1766dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Ident\s*):(?:\s*\d+\s*(,|=|;))?/) {
1767dd88ab32SMasahiro Yamada			if (defined $2 && $type eq 'C' || $type eq 'T') {
1768dd88ab32SMasahiro Yamada				$av_pend_colon = 'B';
1769dd88ab32SMasahiro Yamada			} elsif ($type eq 'E') {
1770dd88ab32SMasahiro Yamada				$av_pend_colon = 'L';
1771dd88ab32SMasahiro Yamada			}
1772dd88ab32SMasahiro Yamada			print "IDENT_COLON($1,$type>$av_pend_colon)\n" if ($dbg_values > 1);
1773dd88ab32SMasahiro Yamada			$type = 'V';
1774dd88ab32SMasahiro Yamada
1775dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Ident|$Constant)/o) {
1776dd88ab32SMasahiro Yamada			print "IDENT($1)\n" if ($dbg_values > 1);
1777dd88ab32SMasahiro Yamada			$type = 'V';
1778dd88ab32SMasahiro Yamada
1779dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Assignment)/o) {
1780dd88ab32SMasahiro Yamada			print "ASSIGN($1)\n" if ($dbg_values > 1);
1781dd88ab32SMasahiro Yamada			$type = 'N';
1782dd88ab32SMasahiro Yamada
1783dd88ab32SMasahiro Yamada		} elsif ($cur =~/^(;|{|})/) {
1784dd88ab32SMasahiro Yamada			print "END($1)\n" if ($dbg_values > 1);
1785dd88ab32SMasahiro Yamada			$type = 'E';
1786dd88ab32SMasahiro Yamada			$av_pend_colon = 'O';
1787dd88ab32SMasahiro Yamada
1788dd88ab32SMasahiro Yamada		} elsif ($cur =~/^(,)/) {
1789dd88ab32SMasahiro Yamada			print "COMMA($1)\n" if ($dbg_values > 1);
1790dd88ab32SMasahiro Yamada			$type = 'C';
1791dd88ab32SMasahiro Yamada
1792dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\?)/o) {
1793dd88ab32SMasahiro Yamada			print "QUESTION($1)\n" if ($dbg_values > 1);
1794dd88ab32SMasahiro Yamada			$type = 'N';
1795dd88ab32SMasahiro Yamada
1796dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(:)/o) {
1797dd88ab32SMasahiro Yamada			print "COLON($1,$av_pend_colon)\n" if ($dbg_values > 1);
1798dd88ab32SMasahiro Yamada
1799dd88ab32SMasahiro Yamada			substr($var, length($res), 1, $av_pend_colon);
1800dd88ab32SMasahiro Yamada			if ($av_pend_colon eq 'C' || $av_pend_colon eq 'L') {
1801dd88ab32SMasahiro Yamada				$type = 'E';
1802dd88ab32SMasahiro Yamada			} else {
1803dd88ab32SMasahiro Yamada				$type = 'N';
1804dd88ab32SMasahiro Yamada			}
1805dd88ab32SMasahiro Yamada			$av_pend_colon = 'O';
1806dd88ab32SMasahiro Yamada
1807dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(\[)/o) {
1808dd88ab32SMasahiro Yamada			print "CLOSE($1)\n" if ($dbg_values > 1);
1809dd88ab32SMasahiro Yamada			$type = 'N';
1810dd88ab32SMasahiro Yamada
1811dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^(-(?![->])|\+(?!\+)|\*|\&\&|\&)/o) {
1812dd88ab32SMasahiro Yamada			my $variant;
1813dd88ab32SMasahiro Yamada
1814dd88ab32SMasahiro Yamada			print "OPV($1)\n" if ($dbg_values > 1);
1815dd88ab32SMasahiro Yamada			if ($type eq 'V') {
1816dd88ab32SMasahiro Yamada				$variant = 'B';
1817dd88ab32SMasahiro Yamada			} else {
1818dd88ab32SMasahiro Yamada				$variant = 'U';
1819dd88ab32SMasahiro Yamada			}
1820dd88ab32SMasahiro Yamada
1821dd88ab32SMasahiro Yamada			substr($var, length($res), 1, $variant);
1822dd88ab32SMasahiro Yamada			$type = 'N';
1823dd88ab32SMasahiro Yamada
1824dd88ab32SMasahiro Yamada		} elsif ($cur =~ /^($Operators)/o) {
1825dd88ab32SMasahiro Yamada			print "OP($1)\n" if ($dbg_values > 1);
1826dd88ab32SMasahiro Yamada			if ($1 ne '++' && $1 ne '--') {
1827dd88ab32SMasahiro Yamada				$type = 'N';
1828dd88ab32SMasahiro Yamada			}
1829dd88ab32SMasahiro Yamada
1830dd88ab32SMasahiro Yamada		} elsif ($cur =~ /(^.)/o) {
1831dd88ab32SMasahiro Yamada			print "C($1)\n" if ($dbg_values > 1);
1832dd88ab32SMasahiro Yamada		}
1833dd88ab32SMasahiro Yamada		if (defined $1) {
1834dd88ab32SMasahiro Yamada			$cur = substr($cur, length($1));
1835dd88ab32SMasahiro Yamada			$res .= $type x length($1);
1836dd88ab32SMasahiro Yamada		}
1837dd88ab32SMasahiro Yamada	}
1838dd88ab32SMasahiro Yamada
1839dd88ab32SMasahiro Yamada	return ($res, $var);
1840dd88ab32SMasahiro Yamada}
1841dd88ab32SMasahiro Yamada
1842dd88ab32SMasahiro Yamadasub possible {
1843dd88ab32SMasahiro Yamada	my ($possible, $line) = @_;
1844dd88ab32SMasahiro Yamada	my $notPermitted = qr{(?:
1845dd88ab32SMasahiro Yamada		^(?:
1846dd88ab32SMasahiro Yamada			$Modifier|
1847dd88ab32SMasahiro Yamada			$Storage|
1848dd88ab32SMasahiro Yamada			$Type|
1849dd88ab32SMasahiro Yamada			DEFINE_\S+
1850dd88ab32SMasahiro Yamada		)$|
1851dd88ab32SMasahiro Yamada		^(?:
1852dd88ab32SMasahiro Yamada			goto|
1853dd88ab32SMasahiro Yamada			return|
1854dd88ab32SMasahiro Yamada			case|
1855dd88ab32SMasahiro Yamada			else|
1856dd88ab32SMasahiro Yamada			asm|__asm__|
1857dd88ab32SMasahiro Yamada			do|
1858dd88ab32SMasahiro Yamada			\#|
1859dd88ab32SMasahiro Yamada			\#\#|
1860dd88ab32SMasahiro Yamada		)(?:\s|$)|
1861dd88ab32SMasahiro Yamada		^(?:typedef|struct|enum)\b
1862dd88ab32SMasahiro Yamada	    )}x;
1863dd88ab32SMasahiro Yamada	warn "CHECK<$possible> ($line)\n" if ($dbg_possible > 2);
1864dd88ab32SMasahiro Yamada	if ($possible !~ $notPermitted) {
1865dd88ab32SMasahiro Yamada		# Check for modifiers.
1866dd88ab32SMasahiro Yamada		$possible =~ s/\s*$Storage\s*//g;
1867dd88ab32SMasahiro Yamada		$possible =~ s/\s*$Sparse\s*//g;
1868dd88ab32SMasahiro Yamada		if ($possible =~ /^\s*$/) {
1869dd88ab32SMasahiro Yamada
1870dd88ab32SMasahiro Yamada		} elsif ($possible =~ /\s/) {
1871dd88ab32SMasahiro Yamada			$possible =~ s/\s*$Type\s*//g;
1872dd88ab32SMasahiro Yamada			for my $modifier (split(' ', $possible)) {
1873dd88ab32SMasahiro Yamada				if ($modifier !~ $notPermitted) {
1874dd88ab32SMasahiro Yamada					warn "MODIFIER: $modifier ($possible) ($line)\n" if ($dbg_possible);
18757551eb4fSHeinrich Schuchardt					push(@modifierListFile, $modifier);
1876dd88ab32SMasahiro Yamada				}
1877dd88ab32SMasahiro Yamada			}
1878dd88ab32SMasahiro Yamada
1879dd88ab32SMasahiro Yamada		} else {
1880dd88ab32SMasahiro Yamada			warn "POSSIBLE: $possible ($line)\n" if ($dbg_possible);
18817551eb4fSHeinrich Schuchardt			push(@typeListFile, $possible);
1882dd88ab32SMasahiro Yamada		}
1883dd88ab32SMasahiro Yamada		build_types();
1884dd88ab32SMasahiro Yamada	} else {
1885dd88ab32SMasahiro Yamada		warn "NOTPOSS: $possible ($line)\n" if ($dbg_possible > 1);
1886dd88ab32SMasahiro Yamada	}
1887dd88ab32SMasahiro Yamada}
1888dd88ab32SMasahiro Yamada
1889dd88ab32SMasahiro Yamadamy $prefix = '';
1890dd88ab32SMasahiro Yamada
1891dd88ab32SMasahiro Yamadasub show_type {
18927551eb4fSHeinrich Schuchardt	my ($type) = @_;
18936b9709d9STom Rini
18947551eb4fSHeinrich Schuchardt	$type =~ tr/[a-z]/[A-Z]/;
18957551eb4fSHeinrich Schuchardt
18967551eb4fSHeinrich Schuchardt	return defined $use_type{$type} if (scalar keys %use_type > 0);
18977551eb4fSHeinrich Schuchardt
18987551eb4fSHeinrich Schuchardt	return !defined $ignore_type{$type};
1899dd88ab32SMasahiro Yamada}
1900dd88ab32SMasahiro Yamada
1901dd88ab32SMasahiro Yamadasub report {
19027551eb4fSHeinrich Schuchardt	my ($level, $type, $msg) = @_;
19037551eb4fSHeinrich Schuchardt
19047551eb4fSHeinrich Schuchardt	if (!show_type($type) ||
19057551eb4fSHeinrich Schuchardt	    (defined $tst_only && $msg !~ /\Q$tst_only\E/)) {
1906dd88ab32SMasahiro Yamada		return 0;
1907dd88ab32SMasahiro Yamada	}
19087551eb4fSHeinrich Schuchardt	my $output = '';
19097551eb4fSHeinrich Schuchardt	if ($color) {
19107551eb4fSHeinrich Schuchardt		if ($level eq 'ERROR') {
19117551eb4fSHeinrich Schuchardt			$output .= RED;
19127551eb4fSHeinrich Schuchardt		} elsif ($level eq 'WARNING') {
19137551eb4fSHeinrich Schuchardt			$output .= YELLOW;
1914dd88ab32SMasahiro Yamada		} else {
19157551eb4fSHeinrich Schuchardt			$output .= GREEN;
1916dd88ab32SMasahiro Yamada		}
19177551eb4fSHeinrich Schuchardt	}
19187551eb4fSHeinrich Schuchardt	$output .= $prefix . $level . ':';
19197551eb4fSHeinrich Schuchardt	if ($show_types) {
19207551eb4fSHeinrich Schuchardt		$output .= BLUE if ($color);
19217551eb4fSHeinrich Schuchardt		$output .= "$type:";
19227551eb4fSHeinrich Schuchardt	}
19237551eb4fSHeinrich Schuchardt	$output .= RESET if ($color);
19247551eb4fSHeinrich Schuchardt	$output .= ' ' . $msg . "\n";
1925dd88ab32SMasahiro Yamada
19267551eb4fSHeinrich Schuchardt	if ($showfile) {
19277551eb4fSHeinrich Schuchardt		my @lines = split("\n", $output, -1);
19287551eb4fSHeinrich Schuchardt		splice(@lines, 1, 1);
19297551eb4fSHeinrich Schuchardt		$output = join("\n", @lines);
19307551eb4fSHeinrich Schuchardt	}
19317551eb4fSHeinrich Schuchardt	$output = (split('\n', $output))[0] . "\n" if ($terse);
19327551eb4fSHeinrich Schuchardt
19337551eb4fSHeinrich Schuchardt	push(our @report, $output);
1934dd88ab32SMasahiro Yamada
1935dd88ab32SMasahiro Yamada	return 1;
1936dd88ab32SMasahiro Yamada}
19377551eb4fSHeinrich Schuchardt
1938dd88ab32SMasahiro Yamadasub report_dump {
1939dd88ab32SMasahiro Yamada	our @report;
1940dd88ab32SMasahiro Yamada}
1941dd88ab32SMasahiro Yamada
19427551eb4fSHeinrich Schuchardtsub fixup_current_range {
19437551eb4fSHeinrich Schuchardt	my ($lineRef, $offset, $length) = @_;
19447551eb4fSHeinrich Schuchardt
19457551eb4fSHeinrich Schuchardt	if ($$lineRef =~ /^\@\@ -\d+,\d+ \+(\d+),(\d+) \@\@/) {
19467551eb4fSHeinrich Schuchardt		my $o = $1;
19477551eb4fSHeinrich Schuchardt		my $l = $2;
19487551eb4fSHeinrich Schuchardt		my $no = $o + $offset;
19497551eb4fSHeinrich Schuchardt		my $nl = $l + $length;
19507551eb4fSHeinrich Schuchardt		$$lineRef =~ s/\+$o,$l \@\@/\+$no,$nl \@\@/;
19517551eb4fSHeinrich Schuchardt	}
19527551eb4fSHeinrich Schuchardt}
19537551eb4fSHeinrich Schuchardt
19547551eb4fSHeinrich Schuchardtsub fix_inserted_deleted_lines {
19557551eb4fSHeinrich Schuchardt	my ($linesRef, $insertedRef, $deletedRef) = @_;
19567551eb4fSHeinrich Schuchardt
19577551eb4fSHeinrich Schuchardt	my $range_last_linenr = 0;
19587551eb4fSHeinrich Schuchardt	my $delta_offset = 0;
19597551eb4fSHeinrich Schuchardt
19607551eb4fSHeinrich Schuchardt	my $old_linenr = 0;
19617551eb4fSHeinrich Schuchardt	my $new_linenr = 0;
19627551eb4fSHeinrich Schuchardt
19637551eb4fSHeinrich Schuchardt	my $next_insert = 0;
19647551eb4fSHeinrich Schuchardt	my $next_delete = 0;
19657551eb4fSHeinrich Schuchardt
19667551eb4fSHeinrich Schuchardt	my @lines = ();
19677551eb4fSHeinrich Schuchardt
19687551eb4fSHeinrich Schuchardt	my $inserted = @{$insertedRef}[$next_insert++];
19697551eb4fSHeinrich Schuchardt	my $deleted = @{$deletedRef}[$next_delete++];
19707551eb4fSHeinrich Schuchardt
19717551eb4fSHeinrich Schuchardt	foreach my $old_line (@{$linesRef}) {
19727551eb4fSHeinrich Schuchardt		my $save_line = 1;
19737551eb4fSHeinrich Schuchardt		my $line = $old_line;	#don't modify the array
19747551eb4fSHeinrich Schuchardt		if ($line =~ /^(?:\+\+\+|\-\-\-)\s+\S+/) {	#new filename
19757551eb4fSHeinrich Schuchardt			$delta_offset = 0;
19767551eb4fSHeinrich Schuchardt		} elsif ($line =~ /^\@\@ -\d+,\d+ \+\d+,\d+ \@\@/) {	#new hunk
19777551eb4fSHeinrich Schuchardt			$range_last_linenr = $new_linenr;
19787551eb4fSHeinrich Schuchardt			fixup_current_range(\$line, $delta_offset, 0);
19797551eb4fSHeinrich Schuchardt		}
19807551eb4fSHeinrich Schuchardt
19817551eb4fSHeinrich Schuchardt		while (defined($deleted) && ${$deleted}{'LINENR'} == $old_linenr) {
19827551eb4fSHeinrich Schuchardt			$deleted = @{$deletedRef}[$next_delete++];
19837551eb4fSHeinrich Schuchardt			$save_line = 0;
19847551eb4fSHeinrich Schuchardt			fixup_current_range(\$lines[$range_last_linenr], $delta_offset--, -1);
19857551eb4fSHeinrich Schuchardt		}
19867551eb4fSHeinrich Schuchardt
19877551eb4fSHeinrich Schuchardt		while (defined($inserted) && ${$inserted}{'LINENR'} == $old_linenr) {
19887551eb4fSHeinrich Schuchardt			push(@lines, ${$inserted}{'LINE'});
19897551eb4fSHeinrich Schuchardt			$inserted = @{$insertedRef}[$next_insert++];
19907551eb4fSHeinrich Schuchardt			$new_linenr++;
19917551eb4fSHeinrich Schuchardt			fixup_current_range(\$lines[$range_last_linenr], $delta_offset++, 1);
19927551eb4fSHeinrich Schuchardt		}
19937551eb4fSHeinrich Schuchardt
19947551eb4fSHeinrich Schuchardt		if ($save_line) {
19957551eb4fSHeinrich Schuchardt			push(@lines, $line);
19967551eb4fSHeinrich Schuchardt			$new_linenr++;
19977551eb4fSHeinrich Schuchardt		}
19987551eb4fSHeinrich Schuchardt
19997551eb4fSHeinrich Schuchardt		$old_linenr++;
20007551eb4fSHeinrich Schuchardt	}
20017551eb4fSHeinrich Schuchardt
20027551eb4fSHeinrich Schuchardt	return @lines;
20037551eb4fSHeinrich Schuchardt}
20047551eb4fSHeinrich Schuchardt
20057551eb4fSHeinrich Schuchardtsub fix_insert_line {
20067551eb4fSHeinrich Schuchardt	my ($linenr, $line) = @_;
20077551eb4fSHeinrich Schuchardt
20087551eb4fSHeinrich Schuchardt	my $inserted = {
20097551eb4fSHeinrich Schuchardt		LINENR => $linenr,
20107551eb4fSHeinrich Schuchardt		LINE => $line,
20117551eb4fSHeinrich Schuchardt	};
20127551eb4fSHeinrich Schuchardt	push(@fixed_inserted, $inserted);
20137551eb4fSHeinrich Schuchardt}
20147551eb4fSHeinrich Schuchardt
20157551eb4fSHeinrich Schuchardtsub fix_delete_line {
20167551eb4fSHeinrich Schuchardt	my ($linenr, $line) = @_;
20177551eb4fSHeinrich Schuchardt
20187551eb4fSHeinrich Schuchardt	my $deleted = {
20197551eb4fSHeinrich Schuchardt		LINENR => $linenr,
20207551eb4fSHeinrich Schuchardt		LINE => $line,
20217551eb4fSHeinrich Schuchardt	};
20227551eb4fSHeinrich Schuchardt
20237551eb4fSHeinrich Schuchardt	push(@fixed_deleted, $deleted);
20247551eb4fSHeinrich Schuchardt}
20257551eb4fSHeinrich Schuchardt
2026dd88ab32SMasahiro Yamadasub ERROR {
20277551eb4fSHeinrich Schuchardt	my ($type, $msg) = @_;
20287551eb4fSHeinrich Schuchardt
20297551eb4fSHeinrich Schuchardt	if (report("ERROR", $type, $msg)) {
2030dd88ab32SMasahiro Yamada		our $clean = 0;
2031dd88ab32SMasahiro Yamada		our $cnt_error++;
20326b9709d9STom Rini		return 1;
2033dd88ab32SMasahiro Yamada	}
20346b9709d9STom Rini	return 0;
2035dd88ab32SMasahiro Yamada}
2036dd88ab32SMasahiro Yamadasub WARN {
20377551eb4fSHeinrich Schuchardt	my ($type, $msg) = @_;
20387551eb4fSHeinrich Schuchardt
20397551eb4fSHeinrich Schuchardt	if (report("WARNING", $type, $msg)) {
2040dd88ab32SMasahiro Yamada		our $clean = 0;
2041dd88ab32SMasahiro Yamada		our $cnt_warn++;
20426b9709d9STom Rini		return 1;
2043dd88ab32SMasahiro Yamada	}
20446b9709d9STom Rini	return 0;
2045dd88ab32SMasahiro Yamada}
2046dd88ab32SMasahiro Yamadasub CHK {
20477551eb4fSHeinrich Schuchardt	my ($type, $msg) = @_;
20487551eb4fSHeinrich Schuchardt
20497551eb4fSHeinrich Schuchardt	if ($check && report("CHECK", $type, $msg)) {
2050dd88ab32SMasahiro Yamada		our $clean = 0;
2051dd88ab32SMasahiro Yamada		our $cnt_chk++;
20526b9709d9STom Rini		return 1;
2053dd88ab32SMasahiro Yamada	}
20546b9709d9STom Rini	return 0;
2055dd88ab32SMasahiro Yamada}
2056dd88ab32SMasahiro Yamada
2057dd88ab32SMasahiro Yamadasub check_absolute_file {
2058dd88ab32SMasahiro Yamada	my ($absolute, $herecurr) = @_;
2059dd88ab32SMasahiro Yamada	my $file = $absolute;
2060dd88ab32SMasahiro Yamada
2061dd88ab32SMasahiro Yamada	##print "absolute<$absolute>\n";
2062dd88ab32SMasahiro Yamada
2063dd88ab32SMasahiro Yamada	# See if any suffix of this path is a path within the tree.
2064dd88ab32SMasahiro Yamada	while ($file =~ s@^[^/]*/@@) {
2065dd88ab32SMasahiro Yamada		if (-f "$root/$file") {
2066dd88ab32SMasahiro Yamada			##print "file<$file>\n";
2067dd88ab32SMasahiro Yamada			last;
2068dd88ab32SMasahiro Yamada		}
2069dd88ab32SMasahiro Yamada	}
2070dd88ab32SMasahiro Yamada	if (! -f _)  {
2071dd88ab32SMasahiro Yamada		return 0;
2072dd88ab32SMasahiro Yamada	}
2073dd88ab32SMasahiro Yamada
2074dd88ab32SMasahiro Yamada	# It is, so see if the prefix is acceptable.
2075dd88ab32SMasahiro Yamada	my $prefix = $absolute;
2076dd88ab32SMasahiro Yamada	substr($prefix, -length($file)) = '';
2077dd88ab32SMasahiro Yamada
2078dd88ab32SMasahiro Yamada	##print "prefix<$prefix>\n";
2079dd88ab32SMasahiro Yamada	if ($prefix ne ".../") {
2080dd88ab32SMasahiro Yamada		WARN("USE_RELATIVE_PATH",
2081dd88ab32SMasahiro Yamada		     "use relative pathname instead of absolute in changelog text\n" . $herecurr);
2082dd88ab32SMasahiro Yamada	}
2083dd88ab32SMasahiro Yamada}
2084dd88ab32SMasahiro Yamada
20856b9709d9STom Rinisub trim {
20866b9709d9STom Rini	my ($string) = @_;
20876b9709d9STom Rini
20886b9709d9STom Rini	$string =~ s/^\s+|\s+$//g;
20896b9709d9STom Rini
20906b9709d9STom Rini	return $string;
20916b9709d9STom Rini}
20926b9709d9STom Rini
20936b9709d9STom Rinisub ltrim {
20946b9709d9STom Rini	my ($string) = @_;
20956b9709d9STom Rini
20966b9709d9STom Rini	$string =~ s/^\s+//;
20976b9709d9STom Rini
20986b9709d9STom Rini	return $string;
20996b9709d9STom Rini}
21006b9709d9STom Rini
21016b9709d9STom Rinisub rtrim {
21026b9709d9STom Rini	my ($string) = @_;
21036b9709d9STom Rini
21046b9709d9STom Rini	$string =~ s/\s+$//;
21056b9709d9STom Rini
21066b9709d9STom Rini	return $string;
21076b9709d9STom Rini}
21086b9709d9STom Rini
21096b9709d9STom Rinisub string_find_replace {
21106b9709d9STom Rini	my ($string, $find, $replace) = @_;
21116b9709d9STom Rini
21126b9709d9STom Rini	$string =~ s/$find/$replace/g;
21136b9709d9STom Rini
21146b9709d9STom Rini	return $string;
21156b9709d9STom Rini}
21166b9709d9STom Rini
21176b9709d9STom Rinisub tabify {
21186b9709d9STom Rini	my ($leading) = @_;
21196b9709d9STom Rini
21206b9709d9STom Rini	my $source_indent = 8;
21216b9709d9STom Rini	my $max_spaces_before_tab = $source_indent - 1;
21226b9709d9STom Rini	my $spaces_to_tab = " " x $source_indent;
21236b9709d9STom Rini
21246b9709d9STom Rini	#convert leading spaces to tabs
21256b9709d9STom Rini	1 while $leading =~ s@^([\t]*)$spaces_to_tab@$1\t@g;
21266b9709d9STom Rini	#Remove spaces before a tab
21276b9709d9STom Rini	1 while $leading =~ s@^([\t]*)( {1,$max_spaces_before_tab})\t@$1\t@g;
21286b9709d9STom Rini
21296b9709d9STom Rini	return "$leading";
21306b9709d9STom Rini}
21316b9709d9STom Rini
2132dd88ab32SMasahiro Yamadasub pos_last_openparen {
2133dd88ab32SMasahiro Yamada	my ($line) = @_;
2134dd88ab32SMasahiro Yamada
2135dd88ab32SMasahiro Yamada	my $pos = 0;
2136dd88ab32SMasahiro Yamada
2137dd88ab32SMasahiro Yamada	my $opens = $line =~ tr/\(/\(/;
2138dd88ab32SMasahiro Yamada	my $closes = $line =~ tr/\)/\)/;
2139dd88ab32SMasahiro Yamada
2140dd88ab32SMasahiro Yamada	my $last_openparen = 0;
2141dd88ab32SMasahiro Yamada
2142dd88ab32SMasahiro Yamada	if (($opens == 0) || ($closes >= $opens)) {
2143dd88ab32SMasahiro Yamada		return -1;
2144dd88ab32SMasahiro Yamada	}
2145dd88ab32SMasahiro Yamada
2146dd88ab32SMasahiro Yamada	my $len = length($line);
2147dd88ab32SMasahiro Yamada
2148dd88ab32SMasahiro Yamada	for ($pos = 0; $pos < $len; $pos++) {
2149dd88ab32SMasahiro Yamada		my $string = substr($line, $pos);
2150dd88ab32SMasahiro Yamada		if ($string =~ /^($FuncArg|$balanced_parens)/) {
2151dd88ab32SMasahiro Yamada			$pos += length($1) - 1;
2152dd88ab32SMasahiro Yamada		} elsif (substr($line, $pos, 1) eq '(') {
2153dd88ab32SMasahiro Yamada			$last_openparen = $pos;
2154dd88ab32SMasahiro Yamada		} elsif (index($string, '(') == -1) {
2155dd88ab32SMasahiro Yamada			last;
2156dd88ab32SMasahiro Yamada		}
2157dd88ab32SMasahiro Yamada	}
2158dd88ab32SMasahiro Yamada
21597551eb4fSHeinrich Schuchardt	return length(expand_tabs(substr($line, 0, $last_openparen))) + 1;
2160dd88ab32SMasahiro Yamada}
2161dd88ab32SMasahiro Yamada
2162dd88ab32SMasahiro Yamadasub process {
2163dd88ab32SMasahiro Yamada	my $filename = shift;
2164dd88ab32SMasahiro Yamada
2165dd88ab32SMasahiro Yamada	my $linenr=0;
2166dd88ab32SMasahiro Yamada	my $prevline="";
2167dd88ab32SMasahiro Yamada	my $prevrawline="";
2168dd88ab32SMasahiro Yamada	my $stashline="";
2169dd88ab32SMasahiro Yamada	my $stashrawline="";
2170dd88ab32SMasahiro Yamada
2171dd88ab32SMasahiro Yamada	my $length;
2172dd88ab32SMasahiro Yamada	my $indent;
2173dd88ab32SMasahiro Yamada	my $previndent=0;
2174dd88ab32SMasahiro Yamada	my $stashindent=0;
2175dd88ab32SMasahiro Yamada
2176dd88ab32SMasahiro Yamada	our $clean = 1;
2177dd88ab32SMasahiro Yamada	my $signoff = 0;
2178dd88ab32SMasahiro Yamada	my $is_patch = 0;
21797551eb4fSHeinrich Schuchardt	my $in_header_lines = $file ? 0 : 1;
2180dd88ab32SMasahiro Yamada	my $in_commit_log = 0;		#Scanning lines before patch
21817551eb4fSHeinrich Schuchardt	my $has_commit_log = 0;		#Encountered lines before patch
21827551eb4fSHeinrich Schuchardt	my $commit_log_possible_stack_dump = 0;
21837551eb4fSHeinrich Schuchardt	my $commit_log_long_line = 0;
21847551eb4fSHeinrich Schuchardt	my $commit_log_has_diff = 0;
21857551eb4fSHeinrich Schuchardt	my $reported_maintainer_file = 0;
2186dd88ab32SMasahiro Yamada	my $non_utf8_charset = 0;
2187dd88ab32SMasahiro Yamada
21887551eb4fSHeinrich Schuchardt	my $last_blank_line = 0;
21897551eb4fSHeinrich Schuchardt	my $last_coalesced_string_linenr = -1;
21907551eb4fSHeinrich Schuchardt
2191dd88ab32SMasahiro Yamada	our @report = ();
2192dd88ab32SMasahiro Yamada	our $cnt_lines = 0;
2193dd88ab32SMasahiro Yamada	our $cnt_error = 0;
2194dd88ab32SMasahiro Yamada	our $cnt_warn = 0;
2195dd88ab32SMasahiro Yamada	our $cnt_chk = 0;
2196dd88ab32SMasahiro Yamada
2197dd88ab32SMasahiro Yamada	# Trace the real file/line as we go.
2198dd88ab32SMasahiro Yamada	my $realfile = '';
2199dd88ab32SMasahiro Yamada	my $realline = 0;
2200dd88ab32SMasahiro Yamada	my $realcnt = 0;
2201dd88ab32SMasahiro Yamada	my $here = '';
22027551eb4fSHeinrich Schuchardt	my $context_function;		#undef'd unless there's a known function
2203dd88ab32SMasahiro Yamada	my $in_comment = 0;
2204dd88ab32SMasahiro Yamada	my $comment_edge = 0;
2205dd88ab32SMasahiro Yamada	my $first_line = 0;
2206dd88ab32SMasahiro Yamada	my $p1_prefix = '';
2207dd88ab32SMasahiro Yamada
2208dd88ab32SMasahiro Yamada	my $prev_values = 'E';
2209dd88ab32SMasahiro Yamada
2210dd88ab32SMasahiro Yamada	# suppression flags
2211dd88ab32SMasahiro Yamada	my %suppress_ifbraces;
2212dd88ab32SMasahiro Yamada	my %suppress_whiletrailers;
2213dd88ab32SMasahiro Yamada	my %suppress_export;
2214dd88ab32SMasahiro Yamada	my $suppress_statement = 0;
2215dd88ab32SMasahiro Yamada
22166b9709d9STom Rini	my %signatures = ();
2217dd88ab32SMasahiro Yamada
2218dd88ab32SMasahiro Yamada	# Pre-scan the patch sanitizing the lines.
2219dd88ab32SMasahiro Yamada	# Pre-scan the patch looking for any __setup documentation.
2220dd88ab32SMasahiro Yamada	#
2221dd88ab32SMasahiro Yamada	my @setup_docs = ();
2222dd88ab32SMasahiro Yamada	my $setup_docs = 0;
2223dd88ab32SMasahiro Yamada
22246b9709d9STom Rini	my $camelcase_file_seeded = 0;
22256b9709d9STom Rini
2226dd88ab32SMasahiro Yamada	sanitise_line_reset();
2227dd88ab32SMasahiro Yamada	my $line;
2228dd88ab32SMasahiro Yamada	foreach my $rawline (@rawlines) {
2229dd88ab32SMasahiro Yamada		$linenr++;
2230dd88ab32SMasahiro Yamada		$line = $rawline;
2231dd88ab32SMasahiro Yamada
22326b9709d9STom Rini		push(@fixed, $rawline) if ($fix);
22336b9709d9STom Rini
2234dd88ab32SMasahiro Yamada		if ($rawline=~/^\+\+\+\s+(\S+)/) {
2235dd88ab32SMasahiro Yamada			$setup_docs = 0;
22367551eb4fSHeinrich Schuchardt			if ($1 =~ m@Documentation/admin-guide/kernel-parameters.rst$@) {
2237dd88ab32SMasahiro Yamada				$setup_docs = 1;
2238dd88ab32SMasahiro Yamada			}
2239dd88ab32SMasahiro Yamada			#next;
2240dd88ab32SMasahiro Yamada		}
2241dd88ab32SMasahiro Yamada		if ($rawline =~ /^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@/) {
2242dd88ab32SMasahiro Yamada			$realline=$1-1;
2243dd88ab32SMasahiro Yamada			if (defined $2) {
2244dd88ab32SMasahiro Yamada				$realcnt=$3+1;
2245dd88ab32SMasahiro Yamada			} else {
2246dd88ab32SMasahiro Yamada				$realcnt=1+1;
2247dd88ab32SMasahiro Yamada			}
2248dd88ab32SMasahiro Yamada			$in_comment = 0;
2249dd88ab32SMasahiro Yamada
2250dd88ab32SMasahiro Yamada			# Guestimate if this is a continuing comment.  Run
2251dd88ab32SMasahiro Yamada			# the context looking for a comment "edge".  If this
2252dd88ab32SMasahiro Yamada			# edge is a close comment then we must be in a comment
2253dd88ab32SMasahiro Yamada			# at context start.
2254dd88ab32SMasahiro Yamada			my $edge;
2255dd88ab32SMasahiro Yamada			my $cnt = $realcnt;
2256dd88ab32SMasahiro Yamada			for (my $ln = $linenr + 1; $cnt > 0; $ln++) {
2257dd88ab32SMasahiro Yamada				next if (defined $rawlines[$ln - 1] &&
2258dd88ab32SMasahiro Yamada					 $rawlines[$ln - 1] =~ /^-/);
2259dd88ab32SMasahiro Yamada				$cnt--;
2260dd88ab32SMasahiro Yamada				#print "RAW<$rawlines[$ln - 1]>\n";
2261dd88ab32SMasahiro Yamada				last if (!defined $rawlines[$ln - 1]);
2262dd88ab32SMasahiro Yamada				if ($rawlines[$ln - 1] =~ m@(/\*|\*/)@ &&
2263dd88ab32SMasahiro Yamada				    $rawlines[$ln - 1] !~ m@"[^"]*(?:/\*|\*/)[^"]*"@) {
2264dd88ab32SMasahiro Yamada					($edge) = $1;
2265dd88ab32SMasahiro Yamada					last;
2266dd88ab32SMasahiro Yamada				}
2267dd88ab32SMasahiro Yamada			}
2268dd88ab32SMasahiro Yamada			if (defined $edge && $edge eq '*/') {
2269dd88ab32SMasahiro Yamada				$in_comment = 1;
2270dd88ab32SMasahiro Yamada			}
2271dd88ab32SMasahiro Yamada
2272dd88ab32SMasahiro Yamada			# Guestimate if this is a continuing comment.  If this
2273dd88ab32SMasahiro Yamada			# is the start of a diff block and this line starts
2274dd88ab32SMasahiro Yamada			# ' *' then it is very likely a comment.
2275dd88ab32SMasahiro Yamada			if (!defined $edge &&
2276dd88ab32SMasahiro Yamada			    $rawlines[$linenr] =~ m@^.\s*(?:\*\*+| \*)(?:\s|$)@)
2277dd88ab32SMasahiro Yamada			{
2278dd88ab32SMasahiro Yamada				$in_comment = 1;
2279dd88ab32SMasahiro Yamada			}
2280dd88ab32SMasahiro Yamada
2281dd88ab32SMasahiro Yamada			##print "COMMENT:$in_comment edge<$edge> $rawline\n";
2282dd88ab32SMasahiro Yamada			sanitise_line_reset($in_comment);
2283dd88ab32SMasahiro Yamada
2284dd88ab32SMasahiro Yamada		} elsif ($realcnt && $rawline =~ /^(?:\+| |$)/) {
2285dd88ab32SMasahiro Yamada			# Standardise the strings and chars within the input to
2286dd88ab32SMasahiro Yamada			# simplify matching -- only bother with positive lines.
2287dd88ab32SMasahiro Yamada			$line = sanitise_line($rawline);
2288dd88ab32SMasahiro Yamada		}
2289dd88ab32SMasahiro Yamada		push(@lines, $line);
2290dd88ab32SMasahiro Yamada
2291dd88ab32SMasahiro Yamada		if ($realcnt > 1) {
2292dd88ab32SMasahiro Yamada			$realcnt-- if ($line =~ /^(?:\+| |$)/);
2293dd88ab32SMasahiro Yamada		} else {
2294dd88ab32SMasahiro Yamada			$realcnt = 0;
2295dd88ab32SMasahiro Yamada		}
2296dd88ab32SMasahiro Yamada
2297dd88ab32SMasahiro Yamada		#print "==>$rawline\n";
2298dd88ab32SMasahiro Yamada		#print "-->$line\n";
2299dd88ab32SMasahiro Yamada
2300dd88ab32SMasahiro Yamada		if ($setup_docs && $line =~ /^\+/) {
2301dd88ab32SMasahiro Yamada			push(@setup_docs, $line);
2302dd88ab32SMasahiro Yamada		}
2303dd88ab32SMasahiro Yamada	}
2304dd88ab32SMasahiro Yamada
2305dd88ab32SMasahiro Yamada	$prefix = '';
2306dd88ab32SMasahiro Yamada
2307dd88ab32SMasahiro Yamada	$realcnt = 0;
2308dd88ab32SMasahiro Yamada	$linenr = 0;
23097551eb4fSHeinrich Schuchardt	$fixlinenr = -1;
2310dd88ab32SMasahiro Yamada	foreach my $line (@lines) {
2311dd88ab32SMasahiro Yamada		$linenr++;
23127551eb4fSHeinrich Schuchardt		$fixlinenr++;
23136b9709d9STom Rini		my $sline = $line;	#copy of $line
23146b9709d9STom Rini		$sline =~ s/$;/ /g;	#with comments as spaces
2315dd88ab32SMasahiro Yamada
2316dd88ab32SMasahiro Yamada		my $rawline = $rawlines[$linenr - 1];
2317dd88ab32SMasahiro Yamada
2318dd88ab32SMasahiro Yamada#extract the line range in the file after the patch is applied
23197551eb4fSHeinrich Schuchardt		if (!$in_commit_log &&
23207551eb4fSHeinrich Schuchardt		    $line =~ /^\@\@ -\d+(?:,\d+)? \+(\d+)(,(\d+))? \@\@(.*)/) {
23217551eb4fSHeinrich Schuchardt			my $context = $4;
2322dd88ab32SMasahiro Yamada			$is_patch = 1;
2323dd88ab32SMasahiro Yamada			$first_line = $linenr + 1;
2324dd88ab32SMasahiro Yamada			$realline=$1-1;
2325dd88ab32SMasahiro Yamada			if (defined $2) {
2326dd88ab32SMasahiro Yamada				$realcnt=$3+1;
2327dd88ab32SMasahiro Yamada			} else {
2328dd88ab32SMasahiro Yamada				$realcnt=1+1;
2329dd88ab32SMasahiro Yamada			}
2330dd88ab32SMasahiro Yamada			annotate_reset();
2331dd88ab32SMasahiro Yamada			$prev_values = 'E';
2332dd88ab32SMasahiro Yamada
2333dd88ab32SMasahiro Yamada			%suppress_ifbraces = ();
2334dd88ab32SMasahiro Yamada			%suppress_whiletrailers = ();
2335dd88ab32SMasahiro Yamada			%suppress_export = ();
2336dd88ab32SMasahiro Yamada			$suppress_statement = 0;
23377551eb4fSHeinrich Schuchardt			if ($context =~ /\b(\w+)\s*\(/) {
23387551eb4fSHeinrich Schuchardt				$context_function = $1;
23397551eb4fSHeinrich Schuchardt			} else {
23407551eb4fSHeinrich Schuchardt				undef $context_function;
23417551eb4fSHeinrich Schuchardt			}
2342dd88ab32SMasahiro Yamada			next;
2343dd88ab32SMasahiro Yamada
2344dd88ab32SMasahiro Yamada# track the line number as we move through the hunk, note that
2345dd88ab32SMasahiro Yamada# new versions of GNU diff omit the leading space on completely
2346dd88ab32SMasahiro Yamada# blank context lines so we need to count that too.
2347dd88ab32SMasahiro Yamada		} elsif ($line =~ /^( |\+|$)/) {
2348dd88ab32SMasahiro Yamada			$realline++;
2349dd88ab32SMasahiro Yamada			$realcnt-- if ($realcnt != 0);
2350dd88ab32SMasahiro Yamada
2351dd88ab32SMasahiro Yamada			# Measure the line length and indent.
2352dd88ab32SMasahiro Yamada			($length, $indent) = line_stats($rawline);
2353dd88ab32SMasahiro Yamada
2354dd88ab32SMasahiro Yamada			# Track the previous line.
2355dd88ab32SMasahiro Yamada			($prevline, $stashline) = ($stashline, $line);
2356dd88ab32SMasahiro Yamada			($previndent, $stashindent) = ($stashindent, $indent);
2357dd88ab32SMasahiro Yamada			($prevrawline, $stashrawline) = ($stashrawline, $rawline);
2358dd88ab32SMasahiro Yamada
2359dd88ab32SMasahiro Yamada			#warn "line<$line>\n";
2360dd88ab32SMasahiro Yamada
2361dd88ab32SMasahiro Yamada		} elsif ($realcnt == 1) {
2362dd88ab32SMasahiro Yamada			$realcnt--;
2363dd88ab32SMasahiro Yamada		}
2364dd88ab32SMasahiro Yamada
2365dd88ab32SMasahiro Yamada		my $hunk_line = ($realcnt != 0);
2366dd88ab32SMasahiro Yamada
2367dd88ab32SMasahiro Yamada		$here = "#$linenr: " if (!$file);
2368dd88ab32SMasahiro Yamada		$here = "#$realline: " if ($file);
2369dd88ab32SMasahiro Yamada
23707551eb4fSHeinrich Schuchardt		my $found_file = 0;
2371dd88ab32SMasahiro Yamada		# extract the filename as it passes
2372dd88ab32SMasahiro Yamada		if ($line =~ /^diff --git.*?(\S+)$/) {
2373dd88ab32SMasahiro Yamada			$realfile = $1;
23746b9709d9STom Rini			$realfile =~ s@^([^/]*)/@@ if (!$file);
2375dd88ab32SMasahiro Yamada			$in_commit_log = 0;
23767551eb4fSHeinrich Schuchardt			$found_file = 1;
2377dd88ab32SMasahiro Yamada		} elsif ($line =~ /^\+\+\+\s+(\S+)/) {
2378dd88ab32SMasahiro Yamada			$realfile = $1;
23796b9709d9STom Rini			$realfile =~ s@^([^/]*)/@@ if (!$file);
2380dd88ab32SMasahiro Yamada			$in_commit_log = 0;
2381dd88ab32SMasahiro Yamada
2382dd88ab32SMasahiro Yamada			$p1_prefix = $1;
2383dd88ab32SMasahiro Yamada			if (!$file && $tree && $p1_prefix ne '' &&
2384dd88ab32SMasahiro Yamada			    -e "$root/$p1_prefix") {
2385dd88ab32SMasahiro Yamada				WARN("PATCH_PREFIX",
2386dd88ab32SMasahiro Yamada				     "patch prefix '$p1_prefix' exists, appears to be a -p0 patch\n");
2387dd88ab32SMasahiro Yamada			}
2388dd88ab32SMasahiro Yamada
2389dd88ab32SMasahiro Yamada			if ($realfile =~ m@^include/asm/@) {
2390dd88ab32SMasahiro Yamada				ERROR("MODIFIED_INCLUDE_ASM",
2391dd88ab32SMasahiro Yamada				      "do not modify files in include/asm, change architecture specific files in include/asm-<architecture>\n" . "$here$rawline\n");
2392dd88ab32SMasahiro Yamada			}
23937551eb4fSHeinrich Schuchardt			$found_file = 1;
23947551eb4fSHeinrich Schuchardt		}
23957551eb4fSHeinrich Schuchardt
23967551eb4fSHeinrich Schuchardt#make up the handle for any error we report on this line
23977551eb4fSHeinrich Schuchardt		if ($showfile) {
23987551eb4fSHeinrich Schuchardt			$prefix = "$realfile:$realline: "
23997551eb4fSHeinrich Schuchardt		} elsif ($emacs) {
24007551eb4fSHeinrich Schuchardt			if ($file) {
24017551eb4fSHeinrich Schuchardt				$prefix = "$filename:$realline: ";
24027551eb4fSHeinrich Schuchardt			} else {
24037551eb4fSHeinrich Schuchardt				$prefix = "$filename:$linenr: ";
24047551eb4fSHeinrich Schuchardt			}
24057551eb4fSHeinrich Schuchardt		}
24067551eb4fSHeinrich Schuchardt
24077551eb4fSHeinrich Schuchardt		if ($found_file) {
24087551eb4fSHeinrich Schuchardt			if (is_maintained_obsolete($realfile)) {
24097551eb4fSHeinrich Schuchardt				WARN("OBSOLETE",
24107551eb4fSHeinrich Schuchardt				     "$realfile is marked as 'obsolete' in the MAINTAINERS hierarchy.  No unnecessary modifications please.\n");
24117551eb4fSHeinrich Schuchardt			}
24127551eb4fSHeinrich Schuchardt			if ($realfile =~ m@^(?:drivers/net/|net/|drivers/staging/)@) {
24137551eb4fSHeinrich Schuchardt				$check = 1;
24147551eb4fSHeinrich Schuchardt			} else {
24157551eb4fSHeinrich Schuchardt				$check = $check_orig;
24167551eb4fSHeinrich Schuchardt			}
2417dd88ab32SMasahiro Yamada			next;
2418dd88ab32SMasahiro Yamada		}
2419dd88ab32SMasahiro Yamada
2420dd88ab32SMasahiro Yamada		$here .= "FILE: $realfile:$realline:" if ($realcnt != 0);
2421dd88ab32SMasahiro Yamada
2422dd88ab32SMasahiro Yamada		my $hereline = "$here\n$rawline\n";
2423dd88ab32SMasahiro Yamada		my $herecurr = "$here\n$rawline\n";
2424dd88ab32SMasahiro Yamada		my $hereprev = "$here\n$prevrawline\n$rawline\n";
2425dd88ab32SMasahiro Yamada
2426dd88ab32SMasahiro Yamada		$cnt_lines++ if ($realcnt != 0);
2427dd88ab32SMasahiro Yamada
24287551eb4fSHeinrich Schuchardt# Check if the commit log has what seems like a diff which can confuse patch
24297551eb4fSHeinrich Schuchardt		if ($in_commit_log && !$commit_log_has_diff &&
24307551eb4fSHeinrich Schuchardt		    (($line =~ m@^\s+diff\b.*a/[\w/]+@ &&
24317551eb4fSHeinrich Schuchardt		      $line =~ m@^\s+diff\b.*a/([\w/]+)\s+b/$1\b@) ||
24327551eb4fSHeinrich Schuchardt		     $line =~ m@^\s*(?:\-\-\-\s+a/|\+\+\+\s+b/)@ ||
24337551eb4fSHeinrich Schuchardt		     $line =~ m/^\s*\@\@ \-\d+,\d+ \+\d+,\d+ \@\@/)) {
24347551eb4fSHeinrich Schuchardt			ERROR("DIFF_IN_COMMIT_MSG",
24357551eb4fSHeinrich Schuchardt			      "Avoid using diff content in the commit message - patch(1) might not work\n" . $herecurr);
24367551eb4fSHeinrich Schuchardt			$commit_log_has_diff = 1;
24377551eb4fSHeinrich Schuchardt		}
24387551eb4fSHeinrich Schuchardt
2439dd88ab32SMasahiro Yamada# Check for incorrect file permissions
2440dd88ab32SMasahiro Yamada		if ($line =~ /^new (file )?mode.*[7531]\d{0,2}$/) {
2441dd88ab32SMasahiro Yamada			my $permhere = $here . "FILE: $realfile\n";
24426b9709d9STom Rini			if ($realfile !~ m@scripts/@ &&
24436b9709d9STom Rini			    $realfile !~ /\.(py|pl|awk|sh)$/) {
2444dd88ab32SMasahiro Yamada				ERROR("EXECUTE_PERMISSIONS",
2445dd88ab32SMasahiro Yamada				      "do not set execute permissions for source files\n" . $permhere);
2446dd88ab32SMasahiro Yamada			}
2447dd88ab32SMasahiro Yamada		}
2448dd88ab32SMasahiro Yamada
2449dd88ab32SMasahiro Yamada# Check the patch for a signoff:
2450dd88ab32SMasahiro Yamada		if ($line =~ /^\s*signed-off-by:/i) {
2451dd88ab32SMasahiro Yamada			$signoff++;
2452dd88ab32SMasahiro Yamada			$in_commit_log = 0;
2453dd88ab32SMasahiro Yamada		}
2454dd88ab32SMasahiro Yamada
24557551eb4fSHeinrich Schuchardt# Check if MAINTAINERS is being updated.  If so, there's probably no need to
24567551eb4fSHeinrich Schuchardt# emit the "does MAINTAINERS need updating?" message on file add/move/delete
24577551eb4fSHeinrich Schuchardt		if ($line =~ /^\s*MAINTAINERS\s*\|/) {
24587551eb4fSHeinrich Schuchardt			$reported_maintainer_file = 1;
24597551eb4fSHeinrich Schuchardt		}
24607551eb4fSHeinrich Schuchardt
2461dd88ab32SMasahiro Yamada# Check signature styles
2462dd88ab32SMasahiro Yamada		if (!$in_header_lines &&
2463dd88ab32SMasahiro Yamada		    $line =~ /^(\s*)([a-z0-9_-]+by:|$signature_tags)(\s*)(.*)/i) {
2464dd88ab32SMasahiro Yamada			my $space_before = $1;
2465dd88ab32SMasahiro Yamada			my $sign_off = $2;
2466dd88ab32SMasahiro Yamada			my $space_after = $3;
2467dd88ab32SMasahiro Yamada			my $email = $4;
2468dd88ab32SMasahiro Yamada			my $ucfirst_sign_off = ucfirst(lc($sign_off));
2469dd88ab32SMasahiro Yamada
2470dd88ab32SMasahiro Yamada			if ($sign_off !~ /$signature_tags/) {
2471dd88ab32SMasahiro Yamada				WARN("BAD_SIGN_OFF",
2472dd88ab32SMasahiro Yamada				     "Non-standard signature: $sign_off\n" . $herecurr);
2473dd88ab32SMasahiro Yamada			}
2474dd88ab32SMasahiro Yamada			if (defined $space_before && $space_before ne "") {
24756b9709d9STom Rini				if (WARN("BAD_SIGN_OFF",
24766b9709d9STom Rini					 "Do not use whitespace before $ucfirst_sign_off\n" . $herecurr) &&
24776b9709d9STom Rini				    $fix) {
24787551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =
24796b9709d9STom Rini					    "$ucfirst_sign_off $email";
24806b9709d9STom Rini				}
2481dd88ab32SMasahiro Yamada			}
2482dd88ab32SMasahiro Yamada			if ($sign_off =~ /-by:$/i && $sign_off ne $ucfirst_sign_off) {
24836b9709d9STom Rini				if (WARN("BAD_SIGN_OFF",
24846b9709d9STom Rini					 "'$ucfirst_sign_off' is the preferred signature form\n" . $herecurr) &&
24856b9709d9STom Rini				    $fix) {
24867551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =
24876b9709d9STom Rini					    "$ucfirst_sign_off $email";
24886b9709d9STom Rini				}
24896b9709d9STom Rini
2490dd88ab32SMasahiro Yamada			}
2491dd88ab32SMasahiro Yamada			if (!defined $space_after || $space_after ne " ") {
24926b9709d9STom Rini				if (WARN("BAD_SIGN_OFF",
24936b9709d9STom Rini					 "Use a single space after $ucfirst_sign_off\n" . $herecurr) &&
24946b9709d9STom Rini				    $fix) {
24957551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =
24966b9709d9STom Rini					    "$ucfirst_sign_off $email";
24976b9709d9STom Rini				}
2498dd88ab32SMasahiro Yamada			}
2499dd88ab32SMasahiro Yamada
2500dd88ab32SMasahiro Yamada			my ($email_name, $email_address, $comment) = parse_email($email);
2501dd88ab32SMasahiro Yamada			my $suggested_email = format_email(($email_name, $email_address));
2502dd88ab32SMasahiro Yamada			if ($suggested_email eq "") {
2503dd88ab32SMasahiro Yamada				ERROR("BAD_SIGN_OFF",
2504dd88ab32SMasahiro Yamada				      "Unrecognized email address: '$email'\n" . $herecurr);
2505dd88ab32SMasahiro Yamada			} else {
2506dd88ab32SMasahiro Yamada				my $dequoted = $suggested_email;
2507dd88ab32SMasahiro Yamada				$dequoted =~ s/^"//;
2508dd88ab32SMasahiro Yamada				$dequoted =~ s/" </ </;
2509dd88ab32SMasahiro Yamada				# Don't force email to have quotes
2510dd88ab32SMasahiro Yamada				# Allow just an angle bracketed address
2511dd88ab32SMasahiro Yamada				if ("$dequoted$comment" ne $email &&
2512dd88ab32SMasahiro Yamada				    "<$email_address>$comment" ne $email &&
2513dd88ab32SMasahiro Yamada				    "$suggested_email$comment" ne $email) {
2514dd88ab32SMasahiro Yamada					WARN("BAD_SIGN_OFF",
2515dd88ab32SMasahiro Yamada					     "email address '$email' might be better as '$suggested_email$comment'\n" . $herecurr);
2516dd88ab32SMasahiro Yamada				}
2517dd88ab32SMasahiro Yamada			}
25186b9709d9STom Rini
25196b9709d9STom Rini# Check for duplicate signatures
25206b9709d9STom Rini			my $sig_nospace = $line;
25216b9709d9STom Rini			$sig_nospace =~ s/\s//g;
25226b9709d9STom Rini			$sig_nospace = lc($sig_nospace);
25236b9709d9STom Rini			if (defined $signatures{$sig_nospace}) {
25246b9709d9STom Rini				WARN("BAD_SIGN_OFF",
25256b9709d9STom Rini				     "Duplicate signature\n" . $herecurr);
25266b9709d9STom Rini			} else {
25276b9709d9STom Rini				$signatures{$sig_nospace} = 1;
25286b9709d9STom Rini			}
2529dd88ab32SMasahiro Yamada		}
2530dd88ab32SMasahiro Yamada
25317551eb4fSHeinrich Schuchardt# Check email subject for common tools that don't need to be mentioned
25327551eb4fSHeinrich Schuchardt		if ($in_header_lines &&
25337551eb4fSHeinrich Schuchardt		    $line =~ /^Subject:.*\b(?:checkpatch|sparse|smatch)\b[^:]/i) {
25347551eb4fSHeinrich Schuchardt			WARN("EMAIL_SUBJECT",
25357551eb4fSHeinrich Schuchardt			     "A patch subject line should describe the change not the tool that found it\n" . $herecurr);
25367551eb4fSHeinrich Schuchardt		}
25377551eb4fSHeinrich Schuchardt
25387551eb4fSHeinrich Schuchardt# Check for old stable address
25397551eb4fSHeinrich Schuchardt		if ($line =~ /^\s*cc:\s*.*<?\bstable\@kernel\.org\b>?.*$/i) {
25407551eb4fSHeinrich Schuchardt			ERROR("STABLE_ADDRESS",
25417551eb4fSHeinrich Schuchardt			      "The 'stable' address should be 'stable\@vger.kernel.org'\n" . $herecurr);
25427551eb4fSHeinrich Schuchardt		}
25437551eb4fSHeinrich Schuchardt
25447551eb4fSHeinrich Schuchardt# Check for unwanted Gerrit info
25457551eb4fSHeinrich Schuchardt		if ($in_commit_log && $line =~ /^\s*change-id:/i) {
25467551eb4fSHeinrich Schuchardt			ERROR("GERRIT_CHANGE_ID",
25477551eb4fSHeinrich Schuchardt			      "Remove Gerrit Change-Id's before submitting upstream.\n" . $herecurr);
25487551eb4fSHeinrich Schuchardt		}
25497551eb4fSHeinrich Schuchardt
25507551eb4fSHeinrich Schuchardt# Check if the commit log is in a possible stack dump
25517551eb4fSHeinrich Schuchardt		if ($in_commit_log && !$commit_log_possible_stack_dump &&
25527551eb4fSHeinrich Schuchardt		    ($line =~ /^\s*(?:WARNING:|BUG:)/ ||
25537551eb4fSHeinrich Schuchardt		     $line =~ /^\s*\[\s*\d+\.\d{6,6}\s*\]/ ||
25547551eb4fSHeinrich Schuchardt					# timestamp
25557551eb4fSHeinrich Schuchardt		     $line =~ /^\s*\[\<[0-9a-fA-F]{8,}\>\]/)) {
25567551eb4fSHeinrich Schuchardt					# stack dump address
25577551eb4fSHeinrich Schuchardt			$commit_log_possible_stack_dump = 1;
25587551eb4fSHeinrich Schuchardt		}
25597551eb4fSHeinrich Schuchardt
25607551eb4fSHeinrich Schuchardt# Check for line lengths > 75 in commit log, warn once
25617551eb4fSHeinrich Schuchardt		if ($in_commit_log && !$commit_log_long_line &&
25627551eb4fSHeinrich Schuchardt		    length($line) > 75 &&
25637551eb4fSHeinrich Schuchardt		    !($line =~ /^\s*[a-zA-Z0-9_\/\.]+\s+\|\s+\d+/ ||
25647551eb4fSHeinrich Schuchardt					# file delta changes
25657551eb4fSHeinrich Schuchardt		      $line =~ /^\s*(?:[\w\.\-]+\/)++[\w\.\-]+:/ ||
25667551eb4fSHeinrich Schuchardt					# filename then :
25677551eb4fSHeinrich Schuchardt		      $line =~ /^\s*(?:Fixes:|Link:)/i ||
25687551eb4fSHeinrich Schuchardt					# A Fixes: or Link: line
25697551eb4fSHeinrich Schuchardt		      $commit_log_possible_stack_dump)) {
25707551eb4fSHeinrich Schuchardt			WARN("COMMIT_LOG_LONG_LINE",
25717551eb4fSHeinrich Schuchardt			     "Possible unwrapped commit description (prefer a maximum 75 chars per line)\n" . $herecurr);
25727551eb4fSHeinrich Schuchardt			$commit_log_long_line = 1;
25737551eb4fSHeinrich Schuchardt		}
25747551eb4fSHeinrich Schuchardt
25757551eb4fSHeinrich Schuchardt# Reset possible stack dump if a blank line is found
25767551eb4fSHeinrich Schuchardt		if ($in_commit_log && $commit_log_possible_stack_dump &&
25777551eb4fSHeinrich Schuchardt		    $line =~ /^\s*$/) {
25787551eb4fSHeinrich Schuchardt			$commit_log_possible_stack_dump = 0;
25797551eb4fSHeinrich Schuchardt		}
25807551eb4fSHeinrich Schuchardt
25817551eb4fSHeinrich Schuchardt# Check for git id commit length and improperly formed commit descriptions
25827551eb4fSHeinrich Schuchardt		if ($in_commit_log && !$commit_log_possible_stack_dump &&
25837551eb4fSHeinrich Schuchardt		    $line !~ /^\s*(?:Link|Patchwork|http|https|BugLink):/i &&
25847551eb4fSHeinrich Schuchardt		    $line !~ /^This reverts commit [0-9a-f]{7,40}/ &&
25857551eb4fSHeinrich Schuchardt		    ($line =~ /\bcommit\s+[0-9a-f]{5,}\b/i ||
25867551eb4fSHeinrich Schuchardt		     ($line =~ /(?:\s|^)[0-9a-f]{12,40}(?:[\s"'\(\[]|$)/i &&
25877551eb4fSHeinrich Schuchardt		      $line !~ /[\<\[][0-9a-f]{12,40}[\>\]]/i &&
25887551eb4fSHeinrich Schuchardt		      $line !~ /\bfixes:\s*[0-9a-f]{12,40}/i))) {
25897551eb4fSHeinrich Schuchardt			my $init_char = "c";
25907551eb4fSHeinrich Schuchardt			my $orig_commit = "";
25917551eb4fSHeinrich Schuchardt			my $short = 1;
25927551eb4fSHeinrich Schuchardt			my $long = 0;
25937551eb4fSHeinrich Schuchardt			my $case = 1;
25947551eb4fSHeinrich Schuchardt			my $space = 1;
25957551eb4fSHeinrich Schuchardt			my $hasdesc = 0;
25967551eb4fSHeinrich Schuchardt			my $hasparens = 0;
25977551eb4fSHeinrich Schuchardt			my $id = '0123456789ab';
25987551eb4fSHeinrich Schuchardt			my $orig_desc = "commit description";
25997551eb4fSHeinrich Schuchardt			my $description = "";
26007551eb4fSHeinrich Schuchardt
26017551eb4fSHeinrich Schuchardt			if ($line =~ /\b(c)ommit\s+([0-9a-f]{5,})\b/i) {
26027551eb4fSHeinrich Schuchardt				$init_char = $1;
26037551eb4fSHeinrich Schuchardt				$orig_commit = lc($2);
26047551eb4fSHeinrich Schuchardt			} elsif ($line =~ /\b([0-9a-f]{12,40})\b/i) {
26057551eb4fSHeinrich Schuchardt				$orig_commit = lc($1);
26067551eb4fSHeinrich Schuchardt			}
26077551eb4fSHeinrich Schuchardt
26087551eb4fSHeinrich Schuchardt			$short = 0 if ($line =~ /\bcommit\s+[0-9a-f]{12,40}/i);
26097551eb4fSHeinrich Schuchardt			$long = 1 if ($line =~ /\bcommit\s+[0-9a-f]{41,}/i);
26107551eb4fSHeinrich Schuchardt			$space = 0 if ($line =~ /\bcommit [0-9a-f]/i);
26117551eb4fSHeinrich Schuchardt			$case = 0 if ($line =~ /\b[Cc]ommit\s+[0-9a-f]{5,40}[^A-F]/);
26127551eb4fSHeinrich Schuchardt			if ($line =~ /\bcommit\s+[0-9a-f]{5,}\s+\("([^"]+)"\)/i) {
26137551eb4fSHeinrich Schuchardt				$orig_desc = $1;
26147551eb4fSHeinrich Schuchardt				$hasparens = 1;
26157551eb4fSHeinrich Schuchardt			} elsif ($line =~ /\bcommit\s+[0-9a-f]{5,}\s*$/i &&
26167551eb4fSHeinrich Schuchardt				 defined $rawlines[$linenr] &&
26177551eb4fSHeinrich Schuchardt				 $rawlines[$linenr] =~ /^\s*\("([^"]+)"\)/) {
26187551eb4fSHeinrich Schuchardt				$orig_desc = $1;
26197551eb4fSHeinrich Schuchardt				$hasparens = 1;
26207551eb4fSHeinrich Schuchardt			} elsif ($line =~ /\bcommit\s+[0-9a-f]{5,}\s+\("[^"]+$/i &&
26217551eb4fSHeinrich Schuchardt				 defined $rawlines[$linenr] &&
26227551eb4fSHeinrich Schuchardt				 $rawlines[$linenr] =~ /^\s*[^"]+"\)/) {
26237551eb4fSHeinrich Schuchardt				$line =~ /\bcommit\s+[0-9a-f]{5,}\s+\("([^"]+)$/i;
26247551eb4fSHeinrich Schuchardt				$orig_desc = $1;
26257551eb4fSHeinrich Schuchardt				$rawlines[$linenr] =~ /^\s*([^"]+)"\)/;
26267551eb4fSHeinrich Schuchardt				$orig_desc .= " " . $1;
26277551eb4fSHeinrich Schuchardt				$hasparens = 1;
26287551eb4fSHeinrich Schuchardt			}
26297551eb4fSHeinrich Schuchardt
26307551eb4fSHeinrich Schuchardt			($id, $description) = git_commit_info($orig_commit,
26317551eb4fSHeinrich Schuchardt							      $id, $orig_desc);
26327551eb4fSHeinrich Schuchardt
26337551eb4fSHeinrich Schuchardt			if (defined($id) &&
26347551eb4fSHeinrich Schuchardt			   ($short || $long || $space || $case || ($orig_desc ne $description) || !$hasparens)) {
26357551eb4fSHeinrich Schuchardt				ERROR("GIT_COMMIT_ID",
26367551eb4fSHeinrich Schuchardt				      "Please use git commit description style 'commit <12+ chars of sha1> (\"<title line>\")' - ie: '${init_char}ommit $id (\"$description\")'\n" . $herecurr);
26377551eb4fSHeinrich Schuchardt			}
26387551eb4fSHeinrich Schuchardt		}
26397551eb4fSHeinrich Schuchardt
26407551eb4fSHeinrich Schuchardt# Check for added, moved or deleted files
26417551eb4fSHeinrich Schuchardt		if (!$reported_maintainer_file && !$in_commit_log &&
26427551eb4fSHeinrich Schuchardt		    ($line =~ /^(?:new|deleted) file mode\s*\d+\s*$/ ||
26437551eb4fSHeinrich Schuchardt		     $line =~ /^rename (?:from|to) [\w\/\.\-]+\s*$/ ||
26447551eb4fSHeinrich Schuchardt		     ($line =~ /\{\s*([\w\/\.\-]*)\s*\=\>\s*([\w\/\.\-]*)\s*\}/ &&
26457551eb4fSHeinrich Schuchardt		      (defined($1) || defined($2))))) {
26467551eb4fSHeinrich Schuchardt			$is_patch = 1;
26477551eb4fSHeinrich Schuchardt			$reported_maintainer_file = 1;
26487551eb4fSHeinrich Schuchardt			WARN("FILE_PATH_CHANGES",
26497551eb4fSHeinrich Schuchardt			     "added, moved or deleted file(s), does MAINTAINERS need updating?\n" . $herecurr);
26507551eb4fSHeinrich Schuchardt		}
26517551eb4fSHeinrich Schuchardt
2652dd88ab32SMasahiro Yamada# Check for wrappage within a valid hunk of the file
2653dd88ab32SMasahiro Yamada		if ($realcnt != 0 && $line !~ m{^(?:\+|-| |\\ No newline|$)}) {
2654dd88ab32SMasahiro Yamada			ERROR("CORRUPTED_PATCH",
2655dd88ab32SMasahiro Yamada			      "patch seems to be corrupt (line wrapped?)\n" .
2656dd88ab32SMasahiro Yamada				$herecurr) if (!$emitted_corrupt++);
2657dd88ab32SMasahiro Yamada		}
2658dd88ab32SMasahiro Yamada
2659dd88ab32SMasahiro Yamada# UTF-8 regex found at http://www.w3.org/International/questions/qa-forms-utf-8.en.php
2660dd88ab32SMasahiro Yamada		if (($realfile =~ /^$/ || $line =~ /^\+/) &&
2661dd88ab32SMasahiro Yamada		    $rawline !~ m/^$UTF8*$/) {
2662dd88ab32SMasahiro Yamada			my ($utf8_prefix) = ($rawline =~ /^($UTF8*)/);
2663dd88ab32SMasahiro Yamada
2664dd88ab32SMasahiro Yamada			my $blank = copy_spacing($rawline);
2665dd88ab32SMasahiro Yamada			my $ptr = substr($blank, 0, length($utf8_prefix)) . "^";
2666dd88ab32SMasahiro Yamada			my $hereptr = "$hereline$ptr\n";
2667dd88ab32SMasahiro Yamada
2668dd88ab32SMasahiro Yamada			CHK("INVALID_UTF8",
2669dd88ab32SMasahiro Yamada			    "Invalid UTF-8, patch and commit message should be encoded in UTF-8\n" . $hereptr);
2670dd88ab32SMasahiro Yamada		}
2671dd88ab32SMasahiro Yamada
2672dd88ab32SMasahiro Yamada# Check if it's the start of a commit log
2673dd88ab32SMasahiro Yamada# (not a header line and we haven't seen the patch filename)
2674dd88ab32SMasahiro Yamada		if ($in_header_lines && $realfile =~ /^$/ &&
26757551eb4fSHeinrich Schuchardt		    !($rawline =~ /^\s+(?:\S|$)/ ||
26767551eb4fSHeinrich Schuchardt		      $rawline =~ /^(?:commit\b|from\b|[\w-]+:)/i)) {
2677dd88ab32SMasahiro Yamada			$in_header_lines = 0;
2678dd88ab32SMasahiro Yamada			$in_commit_log = 1;
26797551eb4fSHeinrich Schuchardt			$has_commit_log = 1;
2680dd88ab32SMasahiro Yamada		}
2681dd88ab32SMasahiro Yamada
2682dd88ab32SMasahiro Yamada# Check if there is UTF-8 in a commit log when a mail header has explicitly
2683dd88ab32SMasahiro Yamada# declined it, i.e defined some charset where it is missing.
2684dd88ab32SMasahiro Yamada		if ($in_header_lines &&
2685dd88ab32SMasahiro Yamada		    $rawline =~ /^Content-Type:.+charset="(.+)".*$/ &&
2686dd88ab32SMasahiro Yamada		    $1 !~ /utf-8/i) {
2687dd88ab32SMasahiro Yamada			$non_utf8_charset = 1;
2688dd88ab32SMasahiro Yamada		}
2689dd88ab32SMasahiro Yamada
2690dd88ab32SMasahiro Yamada		if ($in_commit_log && $non_utf8_charset && $realfile =~ /^$/ &&
2691dd88ab32SMasahiro Yamada		    $rawline =~ /$NON_ASCII_UTF8/) {
2692dd88ab32SMasahiro Yamada			WARN("UTF8_BEFORE_PATCH",
2693dd88ab32SMasahiro Yamada			    "8-bit UTF-8 used in possible commit log\n" . $herecurr);
2694dd88ab32SMasahiro Yamada		}
2695dd88ab32SMasahiro Yamada
26967551eb4fSHeinrich Schuchardt# Check for absolute kernel paths in commit message
26977551eb4fSHeinrich Schuchardt		if ($tree && $in_commit_log) {
26987551eb4fSHeinrich Schuchardt			while ($line =~ m{(?:^|\s)(/\S*)}g) {
26997551eb4fSHeinrich Schuchardt				my $file = $1;
27007551eb4fSHeinrich Schuchardt
27017551eb4fSHeinrich Schuchardt				if ($file =~ m{^(.*?)(?::\d+)+:?$} &&
27027551eb4fSHeinrich Schuchardt				    check_absolute_file($1, $herecurr)) {
27037551eb4fSHeinrich Schuchardt					#
27047551eb4fSHeinrich Schuchardt				} else {
27057551eb4fSHeinrich Schuchardt					check_absolute_file($file, $herecurr);
27067551eb4fSHeinrich Schuchardt				}
27077551eb4fSHeinrich Schuchardt			}
27087551eb4fSHeinrich Schuchardt		}
27097551eb4fSHeinrich Schuchardt
2710c10e0f5bSDan Murphy# Check for various typo / spelling mistakes
2711c10e0f5bSDan Murphy		if (defined($misspellings) &&
2712c10e0f5bSDan Murphy		    ($in_commit_log || $line =~ /^(?:\+|Subject:)/i)) {
2713c10e0f5bSDan Murphy			while ($rawline =~ /(?:^|[^a-z@])($misspellings)(?:\b|$|[^a-z@])/gi) {
2714c10e0f5bSDan Murphy				my $typo = $1;
2715c10e0f5bSDan Murphy				my $typo_fix = $spelling_fix{lc($typo)};
2716c10e0f5bSDan Murphy				$typo_fix = ucfirst($typo_fix) if ($typo =~ /^[A-Z]/);
2717c10e0f5bSDan Murphy				$typo_fix = uc($typo_fix) if ($typo =~ /^[A-Z]+$/);
2718c10e0f5bSDan Murphy				my $msg_type = \&WARN;
2719c10e0f5bSDan Murphy				$msg_type = \&CHK if ($file);
2720c10e0f5bSDan Murphy				if (&{$msg_type}("TYPO_SPELLING",
2721c10e0f5bSDan Murphy						 "'$typo' may be misspelled - perhaps '$typo_fix'?\n" . $herecurr) &&
2722c10e0f5bSDan Murphy				    $fix) {
2723c10e0f5bSDan Murphy					$fixed[$fixlinenr] =~ s/(^|[^A-Za-z@])($typo)($|[^A-Za-z@])/$1$typo_fix$3/;
2724c10e0f5bSDan Murphy				}
2725c10e0f5bSDan Murphy			}
2726c10e0f5bSDan Murphy		}
2727c10e0f5bSDan Murphy
2728dd88ab32SMasahiro Yamada# ignore non-hunk lines and lines being removed
2729dd88ab32SMasahiro Yamada		next if (!$hunk_line || $line =~ /^-/);
2730dd88ab32SMasahiro Yamada
2731dd88ab32SMasahiro Yamada#trailing whitespace
2732dd88ab32SMasahiro Yamada		if ($line =~ /^\+.*\015/) {
2733dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($rawline) . "\n";
27346b9709d9STom Rini			if (ERROR("DOS_LINE_ENDINGS",
27356b9709d9STom Rini				  "DOS line endings\n" . $herevet) &&
27366b9709d9STom Rini			    $fix) {
27377551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/[\s\015]+$//;
27386b9709d9STom Rini			}
2739dd88ab32SMasahiro Yamada		} elsif ($rawline =~ /^\+.*\S\s+$/ || $rawline =~ /^\+\s+$/) {
2740dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($rawline) . "\n";
27416b9709d9STom Rini			if (ERROR("TRAILING_WHITESPACE",
27426b9709d9STom Rini				  "trailing whitespace\n" . $herevet) &&
27436b9709d9STom Rini			    $fix) {
27447551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\s+$//;
27456b9709d9STom Rini			}
27466b9709d9STom Rini
2747dd88ab32SMasahiro Yamada			$rpt_cleaners = 1;
2748dd88ab32SMasahiro Yamada		}
2749dd88ab32SMasahiro Yamada
27506b9709d9STom Rini# Check for FSF mailing addresses.
27516b9709d9STom Rini		if ($rawline =~ /\bwrite to the Free/i ||
27527551eb4fSHeinrich Schuchardt		    $rawline =~ /\b675\s+Mass\s+Ave/i ||
27536b9709d9STom Rini		    $rawline =~ /\b59\s+Temple\s+Pl/i ||
27546b9709d9STom Rini		    $rawline =~ /\b51\s+Franklin\s+St/i) {
27556b9709d9STom Rini			my $herevet = "$here\n" . cat_vet($rawline) . "\n";
27566b9709d9STom Rini			my $msg_type = \&ERROR;
27576b9709d9STom Rini			$msg_type = \&CHK if ($file);
27586b9709d9STom Rini			&{$msg_type}("FSF_MAILING_ADDRESS",
27596b9709d9STom Rini				     "Do not include the paragraph about writing to the Free Software Foundation's mailing address from the sample GPL notice. The FSF has changed addresses in the past, and may do so again. Linux already includes a copy of the GPL.\n" . $herevet)
27606b9709d9STom Rini		}
27616b9709d9STom Rini
2762dd88ab32SMasahiro Yamada# check for Kconfig help text having a real description
2763dd88ab32SMasahiro Yamada# Only applies when adding the entry originally, after that we do not have
2764dd88ab32SMasahiro Yamada# sufficient context to determine whether it is indeed long enough.
2765dd88ab32SMasahiro Yamada		if ($realfile =~ /Kconfig/ &&
27667551eb4fSHeinrich Schuchardt		    $line =~ /^\+\s*config\s+/) {
2767dd88ab32SMasahiro Yamada			my $length = 0;
2768dd88ab32SMasahiro Yamada			my $cnt = $realcnt;
2769dd88ab32SMasahiro Yamada			my $ln = $linenr + 1;
2770dd88ab32SMasahiro Yamada			my $f;
2771dd88ab32SMasahiro Yamada			my $is_start = 0;
2772dd88ab32SMasahiro Yamada			my $is_end = 0;
2773dd88ab32SMasahiro Yamada			for (; $cnt > 0 && defined $lines[$ln - 1]; $ln++) {
2774dd88ab32SMasahiro Yamada				$f = $lines[$ln - 1];
2775dd88ab32SMasahiro Yamada				$cnt-- if ($lines[$ln - 1] !~ /^-/);
2776dd88ab32SMasahiro Yamada				$is_end = $lines[$ln - 1] =~ /^\+/;
2777dd88ab32SMasahiro Yamada
2778dd88ab32SMasahiro Yamada				next if ($f =~ /^-/);
27797551eb4fSHeinrich Schuchardt				last if (!$file && $f =~ /^\@\@/);
2780dd88ab32SMasahiro Yamada
27817551eb4fSHeinrich Schuchardt				if ($lines[$ln - 1] =~ /^\+\s*(?:bool|tristate)\s*\"/) {
2782dd88ab32SMasahiro Yamada					$is_start = 1;
27837551eb4fSHeinrich Schuchardt				} elsif ($lines[$ln - 1] =~ /^\+\s*(?:---)?help(?:---)?$/) {
2784dd88ab32SMasahiro Yamada					$length = -1;
2785dd88ab32SMasahiro Yamada				}
2786dd88ab32SMasahiro Yamada
2787dd88ab32SMasahiro Yamada				$f =~ s/^.//;
2788dd88ab32SMasahiro Yamada				$f =~ s/#.*//;
2789dd88ab32SMasahiro Yamada				$f =~ s/^\s+//;
2790dd88ab32SMasahiro Yamada				next if ($f =~ /^$/);
2791dd88ab32SMasahiro Yamada				if ($f =~ /^\s*config\s/) {
2792dd88ab32SMasahiro Yamada					$is_end = 1;
2793dd88ab32SMasahiro Yamada					last;
2794dd88ab32SMasahiro Yamada				}
2795dd88ab32SMasahiro Yamada				$length++;
2796dd88ab32SMasahiro Yamada			}
27977551eb4fSHeinrich Schuchardt			if ($is_start && $is_end && $length < $min_conf_desc_length) {
2798dd88ab32SMasahiro Yamada				WARN("CONFIG_DESCRIPTION",
27997551eb4fSHeinrich Schuchardt				     "please write a paragraph that describes the config symbol fully\n" . $herecurr);
28007551eb4fSHeinrich Schuchardt			}
2801dd88ab32SMasahiro Yamada			#print "is_start<$is_start> is_end<$is_end> length<$length>\n";
2802dd88ab32SMasahiro Yamada		}
2803dd88ab32SMasahiro Yamada
28047551eb4fSHeinrich Schuchardt# check for MAINTAINERS entries that don't have the right form
28057551eb4fSHeinrich Schuchardt		if ($realfile =~ /^MAINTAINERS$/ &&
28067551eb4fSHeinrich Schuchardt		    $rawline =~ /^\+[A-Z]:/ &&
28077551eb4fSHeinrich Schuchardt		    $rawline !~ /^\+[A-Z]:\t\S/) {
28087551eb4fSHeinrich Schuchardt			if (WARN("MAINTAINERS_STYLE",
28097551eb4fSHeinrich Schuchardt				 "MAINTAINERS entries use one tab after TYPE:\n" . $herecurr) &&
28107551eb4fSHeinrich Schuchardt			    $fix) {
28117551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/^(\+[A-Z]):\s*/$1:\t/;
28127551eb4fSHeinrich Schuchardt			}
28137551eb4fSHeinrich Schuchardt		}
28147551eb4fSHeinrich Schuchardt
28157551eb4fSHeinrich Schuchardt# discourage the use of boolean for type definition attributes of Kconfig options
2816dd88ab32SMasahiro Yamada		if ($realfile =~ /Kconfig/ &&
28177551eb4fSHeinrich Schuchardt		    $line =~ /^\+\s*\bboolean\b/) {
28187551eb4fSHeinrich Schuchardt			WARN("CONFIG_TYPE_BOOLEAN",
28197551eb4fSHeinrich Schuchardt			     "Use of boolean is deprecated, please use bool instead.\n" . $herecurr);
2820dd88ab32SMasahiro Yamada		}
2821dd88ab32SMasahiro Yamada
2822dd88ab32SMasahiro Yamada		if (($realfile =~ /Makefile.*/ || $realfile =~ /Kbuild.*/) &&
2823dd88ab32SMasahiro Yamada		    ($line =~ /\+(EXTRA_[A-Z]+FLAGS).*/)) {
2824dd88ab32SMasahiro Yamada			my $flag = $1;
2825dd88ab32SMasahiro Yamada			my $replacement = {
2826dd88ab32SMasahiro Yamada				'EXTRA_AFLAGS' =>   'asflags-y',
2827dd88ab32SMasahiro Yamada				'EXTRA_CFLAGS' =>   'ccflags-y',
2828dd88ab32SMasahiro Yamada				'EXTRA_CPPFLAGS' => 'cppflags-y',
2829dd88ab32SMasahiro Yamada				'EXTRA_LDFLAGS' =>  'ldflags-y',
2830dd88ab32SMasahiro Yamada			};
2831dd88ab32SMasahiro Yamada
2832dd88ab32SMasahiro Yamada			WARN("DEPRECATED_VARIABLE",
2833dd88ab32SMasahiro Yamada			     "Use of $flag is deprecated, please use \`$replacement->{$flag} instead.\n" . $herecurr) if ($replacement->{$flag});
2834dd88ab32SMasahiro Yamada		}
2835dd88ab32SMasahiro Yamada
28366b9709d9STom Rini# check for DT compatible documentation
28377551eb4fSHeinrich Schuchardt		if (defined $root &&
28387551eb4fSHeinrich Schuchardt			(($realfile =~ /\.dtsi?$/ && $line =~ /^\+\s*compatible\s*=\s*\"/) ||
28397551eb4fSHeinrich Schuchardt			 ($realfile =~ /\.[ch]$/ && $line =~ /^\+.*\.compatible\s*=\s*\"/))) {
28407551eb4fSHeinrich Schuchardt
28416b9709d9STom Rini			my @compats = $rawline =~ /\"([a-zA-Z0-9\-\,\.\+_]+)\"/g;
28426b9709d9STom Rini
28437551eb4fSHeinrich Schuchardt			my $dt_path = $root . "/Documentation/devicetree/bindings/";
28447551eb4fSHeinrich Schuchardt			my $vp_file = $dt_path . "vendor-prefixes.txt";
28457551eb4fSHeinrich Schuchardt
28466b9709d9STom Rini			foreach my $compat (@compats) {
28476b9709d9STom Rini				my $compat2 = $compat;
28487551eb4fSHeinrich Schuchardt				$compat2 =~ s/\,[a-zA-Z0-9]*\-/\,<\.\*>\-/;
28497551eb4fSHeinrich Schuchardt				my $compat3 = $compat;
28507551eb4fSHeinrich Schuchardt				$compat3 =~ s/\,([a-z]*)[0-9]*\-/\,$1<\.\*>\-/;
28517551eb4fSHeinrich Schuchardt				`grep -Erq "$compat|$compat2|$compat3" $dt_path`;
28526b9709d9STom Rini				if ( $? >> 8 ) {
28536b9709d9STom Rini					WARN("UNDOCUMENTED_DT_STRING",
28546b9709d9STom Rini					     "DT compatible string \"$compat\" appears un-documented -- check $dt_path\n" . $herecurr);
28556b9709d9STom Rini				}
28566b9709d9STom Rini
28577551eb4fSHeinrich Schuchardt				next if $compat !~ /^([a-zA-Z0-9\-]+)\,/;
28587551eb4fSHeinrich Schuchardt				my $vendor = $1;
28597551eb4fSHeinrich Schuchardt				`grep -Eq "^$vendor\\b" $vp_file`;
28606b9709d9STom Rini				if ( $? >> 8 ) {
28616b9709d9STom Rini					WARN("UNDOCUMENTED_DT_STRING",
28627551eb4fSHeinrich Schuchardt					     "DT compatible string vendor \"$vendor\" appears un-documented -- check $vp_file\n" . $herecurr);
28636b9709d9STom Rini				}
28646b9709d9STom Rini			}
28656b9709d9STom Rini		}
28666b9709d9STom Rini
2867dd88ab32SMasahiro Yamada# check we are in a valid source file if not then ignore this hunk
28687551eb4fSHeinrich Schuchardt		next if ($realfile !~ /\.(h|c|s|S|sh|dtsi|dts)$/);
2869dd88ab32SMasahiro Yamada
28707551eb4fSHeinrich Schuchardt# line length limit (with some exclusions)
28717551eb4fSHeinrich Schuchardt#
28727551eb4fSHeinrich Schuchardt# There are a few types of lines that may extend beyond $max_line_length:
28737551eb4fSHeinrich Schuchardt#	logging functions like pr_info that end in a string
28747551eb4fSHeinrich Schuchardt#	lines with a single string
28757551eb4fSHeinrich Schuchardt#	#defines that are a single string
28767551eb4fSHeinrich Schuchardt#
28777551eb4fSHeinrich Schuchardt# There are 3 different line length message types:
28787551eb4fSHeinrich Schuchardt# LONG_LINE_COMMENT	a comment starts before but extends beyond $max_linelength
28797551eb4fSHeinrich Schuchardt# LONG_LINE_STRING	a string starts before but extends beyond $max_line_length
28807551eb4fSHeinrich Schuchardt# LONG_LINE		all other lines longer than $max_line_length
28817551eb4fSHeinrich Schuchardt#
28827551eb4fSHeinrich Schuchardt# if LONG_LINE is ignored, the other 2 types are also ignored
28837551eb4fSHeinrich Schuchardt#
28847551eb4fSHeinrich Schuchardt
28857551eb4fSHeinrich Schuchardt		if ($line =~ /^\+/ && $length > $max_line_length) {
28867551eb4fSHeinrich Schuchardt			my $msg_type = "LONG_LINE";
28877551eb4fSHeinrich Schuchardt
28887551eb4fSHeinrich Schuchardt			# Check the allowed long line types first
28897551eb4fSHeinrich Schuchardt
28907551eb4fSHeinrich Schuchardt			# logging functions that end in a string that starts
28917551eb4fSHeinrich Schuchardt			# before $max_line_length
28927551eb4fSHeinrich Schuchardt			if ($line =~ /^\+\s*$logFunctions\s*\(\s*(?:(?:KERN_\S+\s*|[^"]*))?($String\s*(?:|,|\)\s*;)\s*)$/ &&
28937551eb4fSHeinrich Schuchardt			    length(expand_tabs(substr($line, 1, length($line) - length($1) - 1))) <= $max_line_length) {
28947551eb4fSHeinrich Schuchardt				$msg_type = "";
28957551eb4fSHeinrich Schuchardt
28967551eb4fSHeinrich Schuchardt			# lines with only strings (w/ possible termination)
28977551eb4fSHeinrich Schuchardt			# #defines with only strings
28987551eb4fSHeinrich Schuchardt			} elsif ($line =~ /^\+\s*$String\s*(?:\s*|,|\)\s*;)\s*$/ ||
28997551eb4fSHeinrich Schuchardt				 $line =~ /^\+\s*#\s*define\s+\w+\s+$String$/) {
29007551eb4fSHeinrich Schuchardt				$msg_type = "";
29017551eb4fSHeinrich Schuchardt
29027551eb4fSHeinrich Schuchardt			# EFI_GUID is another special case
29037551eb4fSHeinrich Schuchardt			} elsif ($line =~ /^\+.*\bEFI_GUID\s*\(/) {
29047551eb4fSHeinrich Schuchardt				$msg_type = "";
29057551eb4fSHeinrich Schuchardt
29067551eb4fSHeinrich Schuchardt			# Otherwise set the alternate message types
29077551eb4fSHeinrich Schuchardt
29087551eb4fSHeinrich Schuchardt			# a comment starts before $max_line_length
29097551eb4fSHeinrich Schuchardt			} elsif ($line =~ /($;[\s$;]*)$/ &&
29107551eb4fSHeinrich Schuchardt				 length(expand_tabs(substr($line, 1, length($line) - length($1) - 1))) <= $max_line_length) {
29117551eb4fSHeinrich Schuchardt				$msg_type = "LONG_LINE_COMMENT"
29127551eb4fSHeinrich Schuchardt
29137551eb4fSHeinrich Schuchardt			# a quoted string starts before $max_line_length
29147551eb4fSHeinrich Schuchardt			} elsif ($sline =~ /\s*($String(?:\s*(?:\\|,\s*|\)\s*;\s*))?)$/ &&
29157551eb4fSHeinrich Schuchardt				 length(expand_tabs(substr($line, 1, length($line) - length($1) - 1))) <= $max_line_length) {
29167551eb4fSHeinrich Schuchardt				$msg_type = "LONG_LINE_STRING"
29177551eb4fSHeinrich Schuchardt			}
29187551eb4fSHeinrich Schuchardt
29197551eb4fSHeinrich Schuchardt			if ($msg_type ne "" &&
29207551eb4fSHeinrich Schuchardt			    (show_type("LONG_LINE") || show_type($msg_type))) {
29217551eb4fSHeinrich Schuchardt				WARN($msg_type,
2922dd88ab32SMasahiro Yamada				     "line over $max_line_length characters\n" . $herecurr);
2923dd88ab32SMasahiro Yamada			}
2924dd88ab32SMasahiro Yamada		}
2925dd88ab32SMasahiro Yamada
2926dd88ab32SMasahiro Yamada# check for adding lines without a newline.
2927dd88ab32SMasahiro Yamada		if ($line =~ /^\+/ && defined $lines[$linenr] && $lines[$linenr] =~ /^\\ No newline at end of file/) {
2928dd88ab32SMasahiro Yamada			WARN("MISSING_EOF_NEWLINE",
2929dd88ab32SMasahiro Yamada			     "adding a line without newline at end of file\n" . $herecurr);
2930dd88ab32SMasahiro Yamada		}
2931dd88ab32SMasahiro Yamada
2932dd88ab32SMasahiro Yamada# Blackfin: use hi/lo macros
2933dd88ab32SMasahiro Yamada		if ($realfile =~ m@arch/blackfin/.*\.S$@) {
2934dd88ab32SMasahiro Yamada			if ($line =~ /\.[lL][[:space:]]*=.*&[[:space:]]*0x[fF][fF][fF][fF]/) {
2935dd88ab32SMasahiro Yamada				my $herevet = "$here\n" . cat_vet($line) . "\n";
2936dd88ab32SMasahiro Yamada				ERROR("LO_MACRO",
2937dd88ab32SMasahiro Yamada				      "use the LO() macro, not (... & 0xFFFF)\n" . $herevet);
2938dd88ab32SMasahiro Yamada			}
2939dd88ab32SMasahiro Yamada			if ($line =~ /\.[hH][[:space:]]*=.*>>[[:space:]]*16/) {
2940dd88ab32SMasahiro Yamada				my $herevet = "$here\n" . cat_vet($line) . "\n";
2941dd88ab32SMasahiro Yamada				ERROR("HI_MACRO",
2942dd88ab32SMasahiro Yamada				      "use the HI() macro, not (... >> 16)\n" . $herevet);
2943dd88ab32SMasahiro Yamada			}
2944dd88ab32SMasahiro Yamada		}
2945dd88ab32SMasahiro Yamada
2946dd88ab32SMasahiro Yamada# check we are in a valid source file C or perl if not then ignore this hunk
29477551eb4fSHeinrich Schuchardt		next if ($realfile !~ /\.(h|c|pl|dtsi|dts)$/);
2948dd88ab32SMasahiro Yamada
2949dd88ab32SMasahiro Yamada# at the beginning of a line any tabs must come first and anything
2950dd88ab32SMasahiro Yamada# more than 8 must use tabs.
2951dd88ab32SMasahiro Yamada		if ($rawline =~ /^\+\s* \t\s*\S/ ||
2952dd88ab32SMasahiro Yamada		    $rawline =~ /^\+\s*        \s*/) {
2953dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($rawline) . "\n";
2954dd88ab32SMasahiro Yamada			$rpt_cleaners = 1;
29556b9709d9STom Rini			if (ERROR("CODE_INDENT",
29566b9709d9STom Rini				  "code indent should use tabs where possible\n" . $herevet) &&
29576b9709d9STom Rini			    $fix) {
29587551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/^\+([ \t]+)/"\+" . tabify($1)/e;
29596b9709d9STom Rini			}
2960dd88ab32SMasahiro Yamada		}
2961dd88ab32SMasahiro Yamada
2962dd88ab32SMasahiro Yamada# check for space before tabs.
2963dd88ab32SMasahiro Yamada		if ($rawline =~ /^\+/ && $rawline =~ / \t/) {
2964dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($rawline) . "\n";
29656b9709d9STom Rini			if (WARN("SPACE_BEFORE_TAB",
29666b9709d9STom Rini				"please, no space before tabs\n" . $herevet) &&
29676b9709d9STom Rini			    $fix) {
29687551eb4fSHeinrich Schuchardt				while ($fixed[$fixlinenr] =~
2969e3a4facdSJoe Perches					   s/(^\+.*) {8,8}\t/$1\t\t/) {}
29707551eb4fSHeinrich Schuchardt				while ($fixed[$fixlinenr] =~
29716b9709d9STom Rini					   s/(^\+.*) +\t/$1\t/) {}
29726b9709d9STom Rini			}
2973dd88ab32SMasahiro Yamada		}
2974dd88ab32SMasahiro Yamada
2975dd88ab32SMasahiro Yamada# check for && or || at the start of a line
2976dd88ab32SMasahiro Yamada		if ($rawline =~ /^\+\s*(&&|\|\|)/) {
2977dd88ab32SMasahiro Yamada			CHK("LOGICAL_CONTINUATIONS",
2978dd88ab32SMasahiro Yamada			    "Logical continuations should be on the previous line\n" . $hereprev);
2979dd88ab32SMasahiro Yamada		}
2980dd88ab32SMasahiro Yamada
29817551eb4fSHeinrich Schuchardt# check indentation starts on a tab stop
29827551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
29837551eb4fSHeinrich Schuchardt		    $sline =~ /^\+\t+( +)(?:$c90_Keywords\b|\{\s*$|\}\s*(?:else\b|while\b|\s*$))/) {
29847551eb4fSHeinrich Schuchardt			my $indent = length($1);
29857551eb4fSHeinrich Schuchardt			if ($indent % 8) {
29867551eb4fSHeinrich Schuchardt				if (WARN("TABSTOP",
29877551eb4fSHeinrich Schuchardt					 "Statements should start on a tabstop\n" . $herecurr) &&
29887551eb4fSHeinrich Schuchardt				    $fix) {
29897551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s@(^\+\t+) +@$1 . "\t" x ($indent/8)@e;
29907551eb4fSHeinrich Schuchardt				}
29917551eb4fSHeinrich Schuchardt			}
29927551eb4fSHeinrich Schuchardt		}
29937551eb4fSHeinrich Schuchardt
2994dd88ab32SMasahiro Yamada# check multi-line statement indentation matches previous line
2995dd88ab32SMasahiro Yamada		if ($^V && $^V ge 5.10.0 &&
29967551eb4fSHeinrich Schuchardt		    $prevline =~ /^\+([ \t]*)((?:$c90_Keywords(?:\s+if)\s*)|(?:$Declare\s*)?(?:$Ident|\(\s*\*\s*$Ident\s*\))\s*|(?:\*\s*)*$Lval\s*=\s*$Ident\s*)\(.*(\&\&|\|\||,)\s*$/) {
2997dd88ab32SMasahiro Yamada			$prevline =~ /^\+(\t*)(.*)$/;
2998dd88ab32SMasahiro Yamada			my $oldindent = $1;
2999dd88ab32SMasahiro Yamada			my $rest = $2;
3000dd88ab32SMasahiro Yamada
3001dd88ab32SMasahiro Yamada			my $pos = pos_last_openparen($rest);
3002dd88ab32SMasahiro Yamada			if ($pos >= 0) {
3003dd88ab32SMasahiro Yamada				$line =~ /^(\+| )([ \t]*)/;
3004dd88ab32SMasahiro Yamada				my $newindent = $2;
3005dd88ab32SMasahiro Yamada
3006dd88ab32SMasahiro Yamada				my $goodtabindent = $oldindent .
3007dd88ab32SMasahiro Yamada					"\t" x ($pos / 8) .
3008dd88ab32SMasahiro Yamada					" "  x ($pos % 8);
3009dd88ab32SMasahiro Yamada				my $goodspaceindent = $oldindent . " "  x $pos;
3010dd88ab32SMasahiro Yamada
3011dd88ab32SMasahiro Yamada				if ($newindent ne $goodtabindent &&
3012dd88ab32SMasahiro Yamada				    $newindent ne $goodspaceindent) {
30136b9709d9STom Rini
30146b9709d9STom Rini					if (CHK("PARENTHESIS_ALIGNMENT",
30156b9709d9STom Rini						"Alignment should match open parenthesis\n" . $hereprev) &&
30166b9709d9STom Rini					    $fix && $line =~ /^\+/) {
30177551eb4fSHeinrich Schuchardt						$fixed[$fixlinenr] =~
30186b9709d9STom Rini						    s/^\+[ \t]*/\+$goodtabindent/;
30196b9709d9STom Rini					}
3020dd88ab32SMasahiro Yamada				}
3021dd88ab32SMasahiro Yamada			}
3022dd88ab32SMasahiro Yamada		}
3023dd88ab32SMasahiro Yamada
30247551eb4fSHeinrich Schuchardt# check for space after cast like "(int) foo" or "(struct foo) bar"
30257551eb4fSHeinrich Schuchardt# avoid checking a few false positives:
30267551eb4fSHeinrich Schuchardt#   "sizeof(<type>)" or "__alignof__(<type>)"
30277551eb4fSHeinrich Schuchardt#   function pointer declarations like "(*foo)(int) = bar;"
30287551eb4fSHeinrich Schuchardt#   structure definitions like "(struct foo) { 0 };"
30297551eb4fSHeinrich Schuchardt#   multiline macros that define functions
30307551eb4fSHeinrich Schuchardt#   known attributes or the __attribute__ keyword
30317551eb4fSHeinrich Schuchardt		if ($line =~ /^\+(.*)\(\s*$Type\s*\)([ \t]++)((?![={]|\\$|$Attribute|__attribute__))/ &&
30327551eb4fSHeinrich Schuchardt		    (!defined($1) || $1 !~ /\b(?:sizeof|__alignof__)\s*$/)) {
30336b9709d9STom Rini			if (CHK("SPACING",
30347551eb4fSHeinrich Schuchardt				"No space is necessary after a cast\n" . $herecurr) &&
30356b9709d9STom Rini			    $fix) {
30367551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
30377551eb4fSHeinrich Schuchardt				    s/(\(\s*$Type\s*\))[ \t]+/$1/;
30386b9709d9STom Rini			}
3039dd88ab32SMasahiro Yamada		}
3040dd88ab32SMasahiro Yamada
30417551eb4fSHeinrich Schuchardt# Block comment styles
30427551eb4fSHeinrich Schuchardt# Networking with an initial /*
3043dd88ab32SMasahiro Yamada		if ($realfile =~ m@^(drivers/net/|net/)@ &&
30446b9709d9STom Rini		    $prevrawline =~ /^\+[ \t]*\/\*[ \t]*$/ &&
30457551eb4fSHeinrich Schuchardt		    $rawline =~ /^\+[ \t]*\*/ &&
30467551eb4fSHeinrich Schuchardt		    $realline > 2) {
3047dd88ab32SMasahiro Yamada			WARN("NETWORKING_BLOCK_COMMENT_STYLE",
3048dd88ab32SMasahiro Yamada			     "networking block comments don't use an empty /* line, use /* Comment...\n" . $hereprev);
3049dd88ab32SMasahiro Yamada		}
3050dd88ab32SMasahiro Yamada
30517551eb4fSHeinrich Schuchardt# Block comments use * on subsequent lines
30527551eb4fSHeinrich Schuchardt		if ($prevline =~ /$;[ \t]*$/ &&			#ends in comment
30537551eb4fSHeinrich Schuchardt		    $prevrawline =~ /^\+.*?\/\*/ &&		#starting /*
30546b9709d9STom Rini		    $prevrawline !~ /\*\/[ \t]*$/ &&		#no trailing */
30556b9709d9STom Rini		    $rawline =~ /^\+/ &&			#line is new
30566b9709d9STom Rini		    $rawline !~ /^\+[ \t]*\*/) {		#no leading *
30577551eb4fSHeinrich Schuchardt			WARN("BLOCK_COMMENT_STYLE",
30587551eb4fSHeinrich Schuchardt			     "Block comments use * on subsequent lines\n" . $hereprev);
30596b9709d9STom Rini		}
30606b9709d9STom Rini
30617551eb4fSHeinrich Schuchardt# Block comments use */ on trailing lines
30627551eb4fSHeinrich Schuchardt		if ($rawline !~ m@^\+[ \t]*\*/[ \t]*$@ &&	#trailing */
3063dd88ab32SMasahiro Yamada		    $rawline !~ m@^\+.*/\*.*\*/[ \t]*$@ &&	#inline /*...*/
3064dd88ab32SMasahiro Yamada		    $rawline !~ m@^\+.*\*{2,}/[ \t]*$@ &&	#trailing **/
3065dd88ab32SMasahiro Yamada		    $rawline =~ m@^\+[ \t]*.+\*\/[ \t]*$@) {	#non blank */
30667551eb4fSHeinrich Schuchardt			WARN("BLOCK_COMMENT_STYLE",
30677551eb4fSHeinrich Schuchardt			     "Block comments use a trailing */ on a separate line\n" . $herecurr);
30687551eb4fSHeinrich Schuchardt		}
30697551eb4fSHeinrich Schuchardt
30707551eb4fSHeinrich Schuchardt# Block comment * alignment
30717551eb4fSHeinrich Schuchardt		if ($prevline =~ /$;[ \t]*$/ &&			#ends in comment
30727551eb4fSHeinrich Schuchardt		    $line =~ /^\+[ \t]*$;/ &&			#leading comment
30737551eb4fSHeinrich Schuchardt		    $rawline =~ /^\+[ \t]*\*/ &&		#leading *
30747551eb4fSHeinrich Schuchardt		    (($prevrawline =~ /^\+.*?\/\*/ &&		#leading /*
30757551eb4fSHeinrich Schuchardt		      $prevrawline !~ /\*\/[ \t]*$/) ||		#no trailing */
30767551eb4fSHeinrich Schuchardt		     $prevrawline =~ /^\+[ \t]*\*/)) {		#leading *
30777551eb4fSHeinrich Schuchardt			my $oldindent;
30787551eb4fSHeinrich Schuchardt			$prevrawline =~ m@^\+([ \t]*/?)\*@;
30797551eb4fSHeinrich Schuchardt			if (defined($1)) {
30807551eb4fSHeinrich Schuchardt				$oldindent = expand_tabs($1);
30817551eb4fSHeinrich Schuchardt			} else {
30827551eb4fSHeinrich Schuchardt				$prevrawline =~ m@^\+(.*/?)\*@;
30837551eb4fSHeinrich Schuchardt				$oldindent = expand_tabs($1);
30847551eb4fSHeinrich Schuchardt			}
30857551eb4fSHeinrich Schuchardt			$rawline =~ m@^\+([ \t]*)\*@;
30867551eb4fSHeinrich Schuchardt			my $newindent = $1;
30877551eb4fSHeinrich Schuchardt			$newindent = expand_tabs($newindent);
30887551eb4fSHeinrich Schuchardt			if (length($oldindent) ne length($newindent)) {
30897551eb4fSHeinrich Schuchardt				WARN("BLOCK_COMMENT_STYLE",
30907551eb4fSHeinrich Schuchardt				     "Block comments should align the * on each line\n" . $hereprev);
30917551eb4fSHeinrich Schuchardt			}
30927551eb4fSHeinrich Schuchardt		}
30937551eb4fSHeinrich Schuchardt
30947551eb4fSHeinrich Schuchardt# check for missing blank lines after struct/union declarations
30957551eb4fSHeinrich Schuchardt# with exceptions for various attributes and macros
30967551eb4fSHeinrich Schuchardt		if ($prevline =~ /^[\+ ]};?\s*$/ &&
30977551eb4fSHeinrich Schuchardt		    $line =~ /^\+/ &&
30987551eb4fSHeinrich Schuchardt		    !($line =~ /^\+\s*$/ ||
30997551eb4fSHeinrich Schuchardt		      $line =~ /^\+\s*EXPORT_SYMBOL/ ||
31007551eb4fSHeinrich Schuchardt		      $line =~ /^\+\s*MODULE_/i ||
31017551eb4fSHeinrich Schuchardt		      $line =~ /^\+\s*\#\s*(?:end|elif|else)/ ||
31027551eb4fSHeinrich Schuchardt		      $line =~ /^\+[a-z_]*init/ ||
31037551eb4fSHeinrich Schuchardt		      $line =~ /^\+\s*(?:static\s+)?[A-Z_]*ATTR/ ||
31047551eb4fSHeinrich Schuchardt		      $line =~ /^\+\s*DECLARE/ ||
31057551eb4fSHeinrich Schuchardt		      $line =~ /^\+\s*__setup/)) {
31067551eb4fSHeinrich Schuchardt			if (CHK("LINE_SPACING",
31077551eb4fSHeinrich Schuchardt				"Please use a blank line after function/struct/union/enum declarations\n" . $hereprev) &&
31087551eb4fSHeinrich Schuchardt			    $fix) {
31097551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, "\+");
31107551eb4fSHeinrich Schuchardt			}
31117551eb4fSHeinrich Schuchardt		}
31127551eb4fSHeinrich Schuchardt
31137551eb4fSHeinrich Schuchardt# check for multiple consecutive blank lines
31147551eb4fSHeinrich Schuchardt		if ($prevline =~ /^[\+ ]\s*$/ &&
31157551eb4fSHeinrich Schuchardt		    $line =~ /^\+\s*$/ &&
31167551eb4fSHeinrich Schuchardt		    $last_blank_line != ($linenr - 1)) {
31177551eb4fSHeinrich Schuchardt			if (CHK("LINE_SPACING",
31187551eb4fSHeinrich Schuchardt				"Please don't use multiple blank lines\n" . $hereprev) &&
31197551eb4fSHeinrich Schuchardt			    $fix) {
31207551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
31217551eb4fSHeinrich Schuchardt			}
31227551eb4fSHeinrich Schuchardt
31237551eb4fSHeinrich Schuchardt			$last_blank_line = $linenr;
31247551eb4fSHeinrich Schuchardt		}
31257551eb4fSHeinrich Schuchardt
31267551eb4fSHeinrich Schuchardt# check for missing blank lines after declarations
31277551eb4fSHeinrich Schuchardt		if ($sline =~ /^\+\s+\S/ &&			#Not at char 1
31287551eb4fSHeinrich Schuchardt			# actual declarations
31297551eb4fSHeinrich Schuchardt		    ($prevline =~ /^\+\s+$Declare\s*$Ident\s*[=,;:\[]/ ||
31307551eb4fSHeinrich Schuchardt			# function pointer declarations
31317551eb4fSHeinrich Schuchardt		     $prevline =~ /^\+\s+$Declare\s*\(\s*\*\s*$Ident\s*\)\s*[=,;:\[\(]/ ||
31327551eb4fSHeinrich Schuchardt			# foo bar; where foo is some local typedef or #define
31337551eb4fSHeinrich Schuchardt		     $prevline =~ /^\+\s+$Ident(?:\s+|\s*\*\s*)$Ident\s*[=,;\[]/ ||
31347551eb4fSHeinrich Schuchardt			# known declaration macros
31357551eb4fSHeinrich Schuchardt		     $prevline =~ /^\+\s+$declaration_macros/) &&
31367551eb4fSHeinrich Schuchardt			# for "else if" which can look like "$Ident $Ident"
31377551eb4fSHeinrich Schuchardt		    !($prevline =~ /^\+\s+$c90_Keywords\b/ ||
31387551eb4fSHeinrich Schuchardt			# other possible extensions of declaration lines
31397551eb4fSHeinrich Schuchardt		      $prevline =~ /(?:$Compare|$Assignment|$Operators)\s*$/ ||
31407551eb4fSHeinrich Schuchardt			# not starting a section or a macro "\" extended line
31417551eb4fSHeinrich Schuchardt		      $prevline =~ /(?:\{\s*|\\)$/) &&
31427551eb4fSHeinrich Schuchardt			# looks like a declaration
31437551eb4fSHeinrich Schuchardt		    !($sline =~ /^\+\s+$Declare\s*$Ident\s*[=,;:\[]/ ||
31447551eb4fSHeinrich Schuchardt			# function pointer declarations
31457551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+$Declare\s*\(\s*\*\s*$Ident\s*\)\s*[=,;:\[\(]/ ||
31467551eb4fSHeinrich Schuchardt			# foo bar; where foo is some local typedef or #define
31477551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+$Ident(?:\s+|\s*\*\s*)$Ident\s*[=,;\[]/ ||
31487551eb4fSHeinrich Schuchardt			# known declaration macros
31497551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+$declaration_macros/ ||
31507551eb4fSHeinrich Schuchardt			# start of struct or union or enum
31517551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+(?:union|struct|enum|typedef)\b/ ||
31527551eb4fSHeinrich Schuchardt			# start or end of block or continuation of declaration
31537551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+(?:$|[\{\}\.\#\"\?\:\(\[])/ ||
31547551eb4fSHeinrich Schuchardt			# bitfield continuation
31557551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+$Ident\s*:\s*\d+\s*[,;]/ ||
31567551eb4fSHeinrich Schuchardt			# other possible extensions of declaration lines
31577551eb4fSHeinrich Schuchardt		      $sline =~ /^\+\s+\(?\s*(?:$Compare|$Assignment|$Operators)/) &&
31587551eb4fSHeinrich Schuchardt			# indentation of previous and current line are the same
31597551eb4fSHeinrich Schuchardt		    (($prevline =~ /\+(\s+)\S/) && $sline =~ /^\+$1\S/)) {
31607551eb4fSHeinrich Schuchardt			if (WARN("LINE_SPACING",
31617551eb4fSHeinrich Schuchardt				 "Missing a blank line after declarations\n" . $hereprev) &&
31627551eb4fSHeinrich Schuchardt			    $fix) {
31637551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, "\+");
31647551eb4fSHeinrich Schuchardt			}
3165dd88ab32SMasahiro Yamada		}
3166dd88ab32SMasahiro Yamada
3167dd88ab32SMasahiro Yamada# check for spaces at the beginning of a line.
3168dd88ab32SMasahiro Yamada# Exceptions:
3169dd88ab32SMasahiro Yamada#  1) within comments
3170dd88ab32SMasahiro Yamada#  2) indented preprocessor commands
3171dd88ab32SMasahiro Yamada#  3) hanging labels
31726b9709d9STom Rini		if ($rawline =~ /^\+ / && $line !~ /^\+ *(?:$;|#|$Ident:)/)  {
3173dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($rawline) . "\n";
31746b9709d9STom Rini			if (WARN("LEADING_SPACE",
31756b9709d9STom Rini				 "please, no spaces at the start of a line\n" . $herevet) &&
31766b9709d9STom Rini			    $fix) {
31777551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/^\+([ \t]+)/"\+" . tabify($1)/e;
31786b9709d9STom Rini			}
3179dd88ab32SMasahiro Yamada		}
3180dd88ab32SMasahiro Yamada
3181dd88ab32SMasahiro Yamada# check we are in a valid C source file if not then ignore this hunk
3182dd88ab32SMasahiro Yamada		next if ($realfile !~ /\.(h|c)$/);
3183dd88ab32SMasahiro Yamada
31847551eb4fSHeinrich Schuchardt# check if this appears to be the start function declaration, save the name
31857551eb4fSHeinrich Schuchardt		if ($sline =~ /^\+\{\s*$/ &&
31867551eb4fSHeinrich Schuchardt		    $prevline =~ /^\+(?:(?:(?:$Storage|$Inline)\s*)*\s*$Type\s*)?($Ident)\(/) {
31877551eb4fSHeinrich Schuchardt			$context_function = $1;
31887551eb4fSHeinrich Schuchardt		}
31897551eb4fSHeinrich Schuchardt
31907551eb4fSHeinrich Schuchardt# check if this appears to be the end of function declaration
31917551eb4fSHeinrich Schuchardt		if ($sline =~ /^\+\}\s*$/) {
31927551eb4fSHeinrich Schuchardt			undef $context_function;
31937551eb4fSHeinrich Schuchardt		}
31947551eb4fSHeinrich Schuchardt
31957551eb4fSHeinrich Schuchardt# check indentation of any line with a bare else
31967551eb4fSHeinrich Schuchardt# (but not if it is a multiple line "if (foo) return bar; else return baz;")
31977551eb4fSHeinrich Schuchardt# if the previous line is a break or return and is indented 1 tab more...
31987551eb4fSHeinrich Schuchardt		if ($sline =~ /^\+([\t]+)(?:}[ \t]*)?else(?:[ \t]*{)?\s*$/) {
31997551eb4fSHeinrich Schuchardt			my $tabs = length($1) + 1;
32007551eb4fSHeinrich Schuchardt			if ($prevline =~ /^\+\t{$tabs,$tabs}break\b/ ||
32017551eb4fSHeinrich Schuchardt			    ($prevline =~ /^\+\t{$tabs,$tabs}return\b/ &&
32027551eb4fSHeinrich Schuchardt			     defined $lines[$linenr] &&
32037551eb4fSHeinrich Schuchardt			     $lines[$linenr] !~ /^[ \+]\t{$tabs,$tabs}return/)) {
32047551eb4fSHeinrich Schuchardt				WARN("UNNECESSARY_ELSE",
32057551eb4fSHeinrich Schuchardt				     "else is not generally useful after a break or return\n" . $hereprev);
32067551eb4fSHeinrich Schuchardt			}
32077551eb4fSHeinrich Schuchardt		}
32087551eb4fSHeinrich Schuchardt
32097551eb4fSHeinrich Schuchardt# check indentation of a line with a break;
32107551eb4fSHeinrich Schuchardt# if the previous line is a goto or return and is indented the same # of tabs
32117551eb4fSHeinrich Schuchardt		if ($sline =~ /^\+([\t]+)break\s*;\s*$/) {
32127551eb4fSHeinrich Schuchardt			my $tabs = $1;
32137551eb4fSHeinrich Schuchardt			if ($prevline =~ /^\+$tabs(?:goto|return)\b/) {
32147551eb4fSHeinrich Schuchardt				WARN("UNNECESSARY_BREAK",
32157551eb4fSHeinrich Schuchardt				     "break is not useful after a goto or return\n" . $hereprev);
32167551eb4fSHeinrich Schuchardt			}
3217dd88ab32SMasahiro Yamada		}
3218dd88ab32SMasahiro Yamada
3219dd88ab32SMasahiro Yamada# check for RCS/CVS revision markers
3220dd88ab32SMasahiro Yamada		if ($rawline =~ /^\+.*\$(Revision|Log|Id)(?:\$|)/) {
3221dd88ab32SMasahiro Yamada			WARN("CVS_KEYWORD",
3222dd88ab32SMasahiro Yamada			     "CVS style keyword markers, these will _not_ be updated\n". $herecurr);
3223dd88ab32SMasahiro Yamada		}
3224dd88ab32SMasahiro Yamada
3225dd88ab32SMasahiro Yamada# Blackfin: don't use __builtin_bfin_[cs]sync
3226dd88ab32SMasahiro Yamada		if ($line =~ /__builtin_bfin_csync/) {
3227dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($line) . "\n";
3228dd88ab32SMasahiro Yamada			ERROR("CSYNC",
3229dd88ab32SMasahiro Yamada			      "use the CSYNC() macro in asm/blackfin.h\n" . $herevet);
3230dd88ab32SMasahiro Yamada		}
3231dd88ab32SMasahiro Yamada		if ($line =~ /__builtin_bfin_ssync/) {
3232dd88ab32SMasahiro Yamada			my $herevet = "$here\n" . cat_vet($line) . "\n";
3233dd88ab32SMasahiro Yamada			ERROR("SSYNC",
3234dd88ab32SMasahiro Yamada			      "use the SSYNC() macro in asm/blackfin.h\n" . $herevet);
3235dd88ab32SMasahiro Yamada		}
3236dd88ab32SMasahiro Yamada
3237dd88ab32SMasahiro Yamada# check for old HOTPLUG __dev<foo> section markings
3238dd88ab32SMasahiro Yamada		if ($line =~ /\b(__dev(init|exit)(data|const|))\b/) {
3239dd88ab32SMasahiro Yamada			WARN("HOTPLUG_SECTION",
3240dd88ab32SMasahiro Yamada			     "Using $1 is unnecessary\n" . $herecurr);
3241dd88ab32SMasahiro Yamada		}
3242dd88ab32SMasahiro Yamada
3243dd88ab32SMasahiro Yamada# Check for potential 'bare' types
3244dd88ab32SMasahiro Yamada		my ($stat, $cond, $line_nr_next, $remain_next, $off_next,
3245dd88ab32SMasahiro Yamada		    $realline_next);
3246dd88ab32SMasahiro Yamada#print "LINE<$line>\n";
32477551eb4fSHeinrich Schuchardt		if ($linenr > $suppress_statement &&
32486b9709d9STom Rini		    $realcnt && $sline =~ /.\s*\S/) {
3249dd88ab32SMasahiro Yamada			($stat, $cond, $line_nr_next, $remain_next, $off_next) =
3250dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $realcnt, 0);
3251dd88ab32SMasahiro Yamada			$stat =~ s/\n./\n /g;
3252dd88ab32SMasahiro Yamada			$cond =~ s/\n./\n /g;
3253dd88ab32SMasahiro Yamada
3254dd88ab32SMasahiro Yamada#print "linenr<$linenr> <$stat>\n";
3255dd88ab32SMasahiro Yamada			# If this statement has no statement boundaries within
3256dd88ab32SMasahiro Yamada			# it there is no point in retrying a statement scan
3257dd88ab32SMasahiro Yamada			# until we hit end of it.
3258dd88ab32SMasahiro Yamada			my $frag = $stat; $frag =~ s/;+\s*$//;
3259dd88ab32SMasahiro Yamada			if ($frag !~ /(?:{|;)/) {
3260dd88ab32SMasahiro Yamada#print "skip<$line_nr_next>\n";
3261dd88ab32SMasahiro Yamada				$suppress_statement = $line_nr_next;
3262dd88ab32SMasahiro Yamada			}
3263dd88ab32SMasahiro Yamada
3264dd88ab32SMasahiro Yamada			# Find the real next line.
3265dd88ab32SMasahiro Yamada			$realline_next = $line_nr_next;
3266dd88ab32SMasahiro Yamada			if (defined $realline_next &&
3267dd88ab32SMasahiro Yamada			    (!defined $lines[$realline_next - 1] ||
3268dd88ab32SMasahiro Yamada			     substr($lines[$realline_next - 1], $off_next) =~ /^\s*$/)) {
3269dd88ab32SMasahiro Yamada				$realline_next++;
3270dd88ab32SMasahiro Yamada			}
3271dd88ab32SMasahiro Yamada
3272dd88ab32SMasahiro Yamada			my $s = $stat;
3273dd88ab32SMasahiro Yamada			$s =~ s/{.*$//s;
3274dd88ab32SMasahiro Yamada
3275dd88ab32SMasahiro Yamada			# Ignore goto labels.
3276dd88ab32SMasahiro Yamada			if ($s =~ /$Ident:\*$/s) {
3277dd88ab32SMasahiro Yamada
3278dd88ab32SMasahiro Yamada			# Ignore functions being called
3279dd88ab32SMasahiro Yamada			} elsif ($s =~ /^.\s*$Ident\s*\(/s) {
3280dd88ab32SMasahiro Yamada
3281dd88ab32SMasahiro Yamada			} elsif ($s =~ /^.\s*else\b/s) {
3282dd88ab32SMasahiro Yamada
3283dd88ab32SMasahiro Yamada			# declarations always start with types
3284dd88ab32SMasahiro Yamada			} 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) {
3285dd88ab32SMasahiro Yamada				my $type = $1;
3286dd88ab32SMasahiro Yamada				$type =~ s/\s+/ /g;
3287dd88ab32SMasahiro Yamada				possible($type, "A:" . $s);
3288dd88ab32SMasahiro Yamada
3289dd88ab32SMasahiro Yamada			# definitions in global scope can only start with types
3290dd88ab32SMasahiro Yamada			} elsif ($s =~ /^.(?:$Storage\s+)?(?:$Inline\s+)?(?:const\s+)?($Ident)\b\s*(?!:)/s) {
3291dd88ab32SMasahiro Yamada				possible($1, "B:" . $s);
3292dd88ab32SMasahiro Yamada			}
3293dd88ab32SMasahiro Yamada
3294dd88ab32SMasahiro Yamada			# any (foo ... *) is a pointer cast, and foo is a type
3295dd88ab32SMasahiro Yamada			while ($s =~ /\(($Ident)(?:\s+$Sparse)*[\s\*]+\s*\)/sg) {
3296dd88ab32SMasahiro Yamada				possible($1, "C:" . $s);
3297dd88ab32SMasahiro Yamada			}
3298dd88ab32SMasahiro Yamada
3299dd88ab32SMasahiro Yamada			# Check for any sort of function declaration.
3300dd88ab32SMasahiro Yamada			# int foo(something bar, other baz);
3301dd88ab32SMasahiro Yamada			# void (*store_gdt)(x86_descr_ptr *);
3302dd88ab32SMasahiro Yamada			if ($prev_values eq 'E' && $s =~ /^(.(?:typedef\s*)?(?:(?:$Storage|$Inline)\s*)*\s*$Type\s*(?:\b$Ident|\(\*\s*$Ident\))\s*)\(/s) {
3303dd88ab32SMasahiro Yamada				my ($name_len) = length($1);
3304dd88ab32SMasahiro Yamada
3305dd88ab32SMasahiro Yamada				my $ctx = $s;
3306dd88ab32SMasahiro Yamada				substr($ctx, 0, $name_len + 1, '');
3307dd88ab32SMasahiro Yamada				$ctx =~ s/\)[^\)]*$//;
3308dd88ab32SMasahiro Yamada
3309dd88ab32SMasahiro Yamada				for my $arg (split(/\s*,\s*/, $ctx)) {
3310dd88ab32SMasahiro Yamada					if ($arg =~ /^(?:const\s+)?($Ident)(?:\s+$Sparse)*\s*\**\s*(:?\b$Ident)?$/s || $arg =~ /^($Ident)$/s) {
3311dd88ab32SMasahiro Yamada
3312dd88ab32SMasahiro Yamada						possible($1, "D:" . $s);
3313dd88ab32SMasahiro Yamada					}
3314dd88ab32SMasahiro Yamada				}
3315dd88ab32SMasahiro Yamada			}
3316dd88ab32SMasahiro Yamada
3317dd88ab32SMasahiro Yamada		}
3318dd88ab32SMasahiro Yamada
3319dd88ab32SMasahiro Yamada#
3320dd88ab32SMasahiro Yamada# Checks which may be anchored in the context.
3321dd88ab32SMasahiro Yamada#
3322dd88ab32SMasahiro Yamada
3323dd88ab32SMasahiro Yamada# Check for switch () and associated case and default
3324dd88ab32SMasahiro Yamada# statements should be at the same indent.
3325dd88ab32SMasahiro Yamada		if ($line=~/\bswitch\s*\(.*\)/) {
3326dd88ab32SMasahiro Yamada			my $err = '';
3327dd88ab32SMasahiro Yamada			my $sep = '';
3328dd88ab32SMasahiro Yamada			my @ctx = ctx_block_outer($linenr, $realcnt);
3329dd88ab32SMasahiro Yamada			shift(@ctx);
3330dd88ab32SMasahiro Yamada			for my $ctx (@ctx) {
3331dd88ab32SMasahiro Yamada				my ($clen, $cindent) = line_stats($ctx);
3332dd88ab32SMasahiro Yamada				if ($ctx =~ /^\+\s*(case\s+|default:)/ &&
3333dd88ab32SMasahiro Yamada							$indent != $cindent) {
3334dd88ab32SMasahiro Yamada					$err .= "$sep$ctx\n";
3335dd88ab32SMasahiro Yamada					$sep = '';
3336dd88ab32SMasahiro Yamada				} else {
3337dd88ab32SMasahiro Yamada					$sep = "[...]\n";
3338dd88ab32SMasahiro Yamada				}
3339dd88ab32SMasahiro Yamada			}
3340dd88ab32SMasahiro Yamada			if ($err ne '') {
3341dd88ab32SMasahiro Yamada				ERROR("SWITCH_CASE_INDENT_LEVEL",
3342dd88ab32SMasahiro Yamada				      "switch and case should be at the same indent\n$hereline$err");
3343dd88ab32SMasahiro Yamada			}
3344dd88ab32SMasahiro Yamada		}
3345dd88ab32SMasahiro Yamada
3346dd88ab32SMasahiro Yamada# if/while/etc brace do not go on next line, unless defining a do while loop,
3347dd88ab32SMasahiro Yamada# or if that brace on the next line is for something else
33487551eb4fSHeinrich Schuchardt		if ($line =~ /(.*)\b((?:if|while|for|switch|(?:[a-z_]+|)for_each[a-z_]+)\s*\(|do\b|else\b)/ && $line !~ /^.\s*\#/) {
3349dd88ab32SMasahiro Yamada			my $pre_ctx = "$1$2";
3350dd88ab32SMasahiro Yamada
3351dd88ab32SMasahiro Yamada			my ($level, @ctx) = ctx_statement_level($linenr, $realcnt, 0);
3352dd88ab32SMasahiro Yamada
3353dd88ab32SMasahiro Yamada			if ($line =~ /^\+\t{6,}/) {
3354dd88ab32SMasahiro Yamada				WARN("DEEP_INDENTATION",
3355dd88ab32SMasahiro Yamada				     "Too many leading tabs - consider code refactoring\n" . $herecurr);
3356dd88ab32SMasahiro Yamada			}
3357dd88ab32SMasahiro Yamada
3358dd88ab32SMasahiro Yamada			my $ctx_cnt = $realcnt - $#ctx - 1;
3359dd88ab32SMasahiro Yamada			my $ctx = join("\n", @ctx);
3360dd88ab32SMasahiro Yamada
3361dd88ab32SMasahiro Yamada			my $ctx_ln = $linenr;
3362dd88ab32SMasahiro Yamada			my $ctx_skip = $realcnt;
3363dd88ab32SMasahiro Yamada
3364dd88ab32SMasahiro Yamada			while ($ctx_skip > $ctx_cnt || ($ctx_skip == $ctx_cnt &&
3365dd88ab32SMasahiro Yamada					defined $lines[$ctx_ln - 1] &&
3366dd88ab32SMasahiro Yamada					$lines[$ctx_ln - 1] =~ /^-/)) {
3367dd88ab32SMasahiro Yamada				##print "SKIP<$ctx_skip> CNT<$ctx_cnt>\n";
3368dd88ab32SMasahiro Yamada				$ctx_skip-- if (!defined $lines[$ctx_ln - 1] || $lines[$ctx_ln - 1] !~ /^-/);
3369dd88ab32SMasahiro Yamada				$ctx_ln++;
3370dd88ab32SMasahiro Yamada			}
3371dd88ab32SMasahiro Yamada
3372dd88ab32SMasahiro Yamada			#print "realcnt<$realcnt> ctx_cnt<$ctx_cnt>\n";
3373dd88ab32SMasahiro Yamada			#print "pre<$pre_ctx>\nline<$line>\nctx<$ctx>\nnext<$lines[$ctx_ln - 1]>\n";
3374dd88ab32SMasahiro Yamada
3375dd88ab32SMasahiro Yamada			if ($ctx !~ /{\s*/ && defined($lines[$ctx_ln - 1]) && $lines[$ctx_ln - 1] =~ /^\+\s*{/) {
3376dd88ab32SMasahiro Yamada				ERROR("OPEN_BRACE",
3377dd88ab32SMasahiro Yamada				      "that open brace { should be on the previous line\n" .
3378dd88ab32SMasahiro Yamada					"$here\n$ctx\n$rawlines[$ctx_ln - 1]\n");
3379dd88ab32SMasahiro Yamada			}
3380dd88ab32SMasahiro Yamada			if ($level == 0 && $pre_ctx !~ /}\s*while\s*\($/ &&
3381dd88ab32SMasahiro Yamada			    $ctx =~ /\)\s*\;\s*$/ &&
3382dd88ab32SMasahiro Yamada			    defined $lines[$ctx_ln - 1])
3383dd88ab32SMasahiro Yamada			{
3384dd88ab32SMasahiro Yamada				my ($nlength, $nindent) = line_stats($lines[$ctx_ln - 1]);
3385dd88ab32SMasahiro Yamada				if ($nindent > $indent) {
3386dd88ab32SMasahiro Yamada					WARN("TRAILING_SEMICOLON",
3387dd88ab32SMasahiro Yamada					     "trailing semicolon indicates no statements, indent implies otherwise\n" .
3388dd88ab32SMasahiro Yamada						"$here\n$ctx\n$rawlines[$ctx_ln - 1]\n");
3389dd88ab32SMasahiro Yamada				}
3390dd88ab32SMasahiro Yamada			}
3391dd88ab32SMasahiro Yamada		}
3392dd88ab32SMasahiro Yamada
3393dd88ab32SMasahiro Yamada# Check relative indent for conditionals and blocks.
33947551eb4fSHeinrich Schuchardt		if ($line =~ /\b(?:(?:if|while|for|(?:[a-z_]+|)for_each[a-z_]+)\s*\(|(?:do|else)\b)/ && $line !~ /^.\s*#/ && $line !~ /\}\s*while\s*/) {
3395dd88ab32SMasahiro Yamada			($stat, $cond, $line_nr_next, $remain_next, $off_next) =
3396dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $realcnt, 0)
3397dd88ab32SMasahiro Yamada					if (!defined $stat);
3398dd88ab32SMasahiro Yamada			my ($s, $c) = ($stat, $cond);
3399dd88ab32SMasahiro Yamada
3400dd88ab32SMasahiro Yamada			substr($s, 0, length($c), '');
3401dd88ab32SMasahiro Yamada
34027551eb4fSHeinrich Schuchardt			# remove inline comments
34037551eb4fSHeinrich Schuchardt			$s =~ s/$;/ /g;
34047551eb4fSHeinrich Schuchardt			$c =~ s/$;/ /g;
3405dd88ab32SMasahiro Yamada
3406dd88ab32SMasahiro Yamada			# Find out how long the conditional actually is.
3407dd88ab32SMasahiro Yamada			my @newlines = ($c =~ /\n/gs);
3408dd88ab32SMasahiro Yamada			my $cond_lines = 1 + $#newlines;
3409dd88ab32SMasahiro Yamada
34107551eb4fSHeinrich Schuchardt			# Make sure we remove the line prefixes as we have
34117551eb4fSHeinrich Schuchardt			# none on the first line, and are going to readd them
34127551eb4fSHeinrich Schuchardt			# where necessary.
34137551eb4fSHeinrich Schuchardt			$s =~ s/\n./\n/gs;
34147551eb4fSHeinrich Schuchardt			while ($s =~ /\n\s+\\\n/) {
34157551eb4fSHeinrich Schuchardt				$cond_lines += $s =~ s/\n\s+\\\n/\n/g;
34167551eb4fSHeinrich Schuchardt			}
34177551eb4fSHeinrich Schuchardt
3418dd88ab32SMasahiro Yamada			# We want to check the first line inside the block
3419dd88ab32SMasahiro Yamada			# starting at the end of the conditional, so remove:
3420dd88ab32SMasahiro Yamada			#  1) any blank line termination
3421dd88ab32SMasahiro Yamada			#  2) any opening brace { on end of the line
3422dd88ab32SMasahiro Yamada			#  3) any do (...) {
3423dd88ab32SMasahiro Yamada			my $continuation = 0;
3424dd88ab32SMasahiro Yamada			my $check = 0;
3425dd88ab32SMasahiro Yamada			$s =~ s/^.*\bdo\b//;
3426dd88ab32SMasahiro Yamada			$s =~ s/^\s*{//;
3427dd88ab32SMasahiro Yamada			if ($s =~ s/^\s*\\//) {
3428dd88ab32SMasahiro Yamada				$continuation = 1;
3429dd88ab32SMasahiro Yamada			}
3430dd88ab32SMasahiro Yamada			if ($s =~ s/^\s*?\n//) {
3431dd88ab32SMasahiro Yamada				$check = 1;
3432dd88ab32SMasahiro Yamada				$cond_lines++;
3433dd88ab32SMasahiro Yamada			}
3434dd88ab32SMasahiro Yamada
3435dd88ab32SMasahiro Yamada			# Also ignore a loop construct at the end of a
3436dd88ab32SMasahiro Yamada			# preprocessor statement.
3437dd88ab32SMasahiro Yamada			if (($prevline =~ /^.\s*#\s*define\s/ ||
3438dd88ab32SMasahiro Yamada			    $prevline =~ /\\\s*$/) && $continuation == 0) {
3439dd88ab32SMasahiro Yamada				$check = 0;
3440dd88ab32SMasahiro Yamada			}
3441dd88ab32SMasahiro Yamada
3442dd88ab32SMasahiro Yamada			my $cond_ptr = -1;
3443dd88ab32SMasahiro Yamada			$continuation = 0;
3444dd88ab32SMasahiro Yamada			while ($cond_ptr != $cond_lines) {
3445dd88ab32SMasahiro Yamada				$cond_ptr = $cond_lines;
3446dd88ab32SMasahiro Yamada
3447dd88ab32SMasahiro Yamada				# If we see an #else/#elif then the code
3448dd88ab32SMasahiro Yamada				# is not linear.
3449dd88ab32SMasahiro Yamada				if ($s =~ /^\s*\#\s*(?:else|elif)/) {
3450dd88ab32SMasahiro Yamada					$check = 0;
3451dd88ab32SMasahiro Yamada				}
3452dd88ab32SMasahiro Yamada
3453dd88ab32SMasahiro Yamada				# Ignore:
3454dd88ab32SMasahiro Yamada				#  1) blank lines, they should be at 0,
3455dd88ab32SMasahiro Yamada				#  2) preprocessor lines, and
3456dd88ab32SMasahiro Yamada				#  3) labels.
3457dd88ab32SMasahiro Yamada				if ($continuation ||
3458dd88ab32SMasahiro Yamada				    $s =~ /^\s*?\n/ ||
3459dd88ab32SMasahiro Yamada				    $s =~ /^\s*#\s*?/ ||
3460dd88ab32SMasahiro Yamada				    $s =~ /^\s*$Ident\s*:/) {
3461dd88ab32SMasahiro Yamada					$continuation = ($s =~ /^.*?\\\n/) ? 1 : 0;
3462dd88ab32SMasahiro Yamada					if ($s =~ s/^.*?\n//) {
3463dd88ab32SMasahiro Yamada						$cond_lines++;
3464dd88ab32SMasahiro Yamada					}
3465dd88ab32SMasahiro Yamada				}
3466dd88ab32SMasahiro Yamada			}
3467dd88ab32SMasahiro Yamada
3468dd88ab32SMasahiro Yamada			my (undef, $sindent) = line_stats("+" . $s);
3469dd88ab32SMasahiro Yamada			my $stat_real = raw_line($linenr, $cond_lines);
3470dd88ab32SMasahiro Yamada
3471dd88ab32SMasahiro Yamada			# Check if either of these lines are modified, else
3472dd88ab32SMasahiro Yamada			# this is not this patch's fault.
3473dd88ab32SMasahiro Yamada			if (!defined($stat_real) ||
3474dd88ab32SMasahiro Yamada			    $stat !~ /^\+/ && $stat_real !~ /^\+/) {
3475dd88ab32SMasahiro Yamada				$check = 0;
3476dd88ab32SMasahiro Yamada			}
3477dd88ab32SMasahiro Yamada			if (defined($stat_real) && $cond_lines > 1) {
3478dd88ab32SMasahiro Yamada				$stat_real = "[...]\n$stat_real";
3479dd88ab32SMasahiro Yamada			}
3480dd88ab32SMasahiro Yamada
3481dd88ab32SMasahiro Yamada			#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";
3482dd88ab32SMasahiro Yamada
34837551eb4fSHeinrich Schuchardt			if ($check && $s ne '' &&
34847551eb4fSHeinrich Schuchardt			    (($sindent % 8) != 0 ||
34857551eb4fSHeinrich Schuchardt			     ($sindent < $indent) ||
34867551eb4fSHeinrich Schuchardt			     ($sindent == $indent &&
34877551eb4fSHeinrich Schuchardt			      ($s !~ /^\s*(?:\}|\{|else\b)/)) ||
34887551eb4fSHeinrich Schuchardt			     ($sindent > $indent + 8))) {
3489dd88ab32SMasahiro Yamada				WARN("SUSPECT_CODE_INDENT",
3490dd88ab32SMasahiro Yamada				     "suspect code indent for conditional statements ($indent, $sindent)\n" . $herecurr . "$stat_real\n");
3491dd88ab32SMasahiro Yamada			}
3492dd88ab32SMasahiro Yamada		}
3493dd88ab32SMasahiro Yamada
3494dd88ab32SMasahiro Yamada		# Track the 'values' across context and added lines.
3495dd88ab32SMasahiro Yamada		my $opline = $line; $opline =~ s/^./ /;
3496dd88ab32SMasahiro Yamada		my ($curr_values, $curr_vars) =
3497dd88ab32SMasahiro Yamada				annotate_values($opline . "\n", $prev_values);
3498dd88ab32SMasahiro Yamada		$curr_values = $prev_values . $curr_values;
3499dd88ab32SMasahiro Yamada		if ($dbg_values) {
3500dd88ab32SMasahiro Yamada			my $outline = $opline; $outline =~ s/\t/ /g;
3501dd88ab32SMasahiro Yamada			print "$linenr > .$outline\n";
3502dd88ab32SMasahiro Yamada			print "$linenr > $curr_values\n";
3503dd88ab32SMasahiro Yamada			print "$linenr >  $curr_vars\n";
3504dd88ab32SMasahiro Yamada		}
3505dd88ab32SMasahiro Yamada		$prev_values = substr($curr_values, -1);
3506dd88ab32SMasahiro Yamada
3507dd88ab32SMasahiro Yamada#ignore lines not being added
35086b9709d9STom Rini		next if ($line =~ /^[^\+]/);
3509dd88ab32SMasahiro Yamada
35107551eb4fSHeinrich Schuchardt# check for dereferences that span multiple lines
35117551eb4fSHeinrich Schuchardt		if ($prevline =~ /^\+.*$Lval\s*(?:\.|->)\s*$/ &&
35127551eb4fSHeinrich Schuchardt		    $line =~ /^\+\s*(?!\#\s*(?!define\s+|if))\s*$Lval/) {
35137551eb4fSHeinrich Schuchardt			$prevline =~ /($Lval\s*(?:\.|->))\s*$/;
35147551eb4fSHeinrich Schuchardt			my $ref = $1;
35157551eb4fSHeinrich Schuchardt			$line =~ /^.\s*($Lval)/;
35167551eb4fSHeinrich Schuchardt			$ref .= $1;
35177551eb4fSHeinrich Schuchardt			$ref =~ s/\s//g;
35187551eb4fSHeinrich Schuchardt			WARN("MULTILINE_DEREFERENCE",
35197551eb4fSHeinrich Schuchardt			     "Avoid multiple line dereference - prefer '$ref'\n" . $hereprev);
35207551eb4fSHeinrich Schuchardt		}
35217551eb4fSHeinrich Schuchardt
35227551eb4fSHeinrich Schuchardt# check for declarations of signed or unsigned without int
35237551eb4fSHeinrich Schuchardt		while ($line =~ m{\b($Declare)\s*(?!char\b|short\b|int\b|long\b)\s*($Ident)?\s*[=,;\[\)\(]}g) {
35247551eb4fSHeinrich Schuchardt			my $type = $1;
35257551eb4fSHeinrich Schuchardt			my $var = $2;
35267551eb4fSHeinrich Schuchardt			$var = "" if (!defined $var);
35277551eb4fSHeinrich Schuchardt			if ($type =~ /^(?:(?:$Storage|$Inline|$Attribute)\s+)*((?:un)?signed)((?:\s*\*)*)\s*$/) {
35287551eb4fSHeinrich Schuchardt				my $sign = $1;
35297551eb4fSHeinrich Schuchardt				my $pointer = $2;
35307551eb4fSHeinrich Schuchardt
35317551eb4fSHeinrich Schuchardt				$pointer = "" if (!defined $pointer);
35327551eb4fSHeinrich Schuchardt
35337551eb4fSHeinrich Schuchardt				if (WARN("UNSPECIFIED_INT",
35347551eb4fSHeinrich Schuchardt					 "Prefer '" . trim($sign) . " int" . rtrim($pointer) . "' to bare use of '$sign" . rtrim($pointer) . "'\n" . $herecurr) &&
35357551eb4fSHeinrich Schuchardt				    $fix) {
35367551eb4fSHeinrich Schuchardt					my $decl = trim($sign) . " int ";
35377551eb4fSHeinrich Schuchardt					my $comp_pointer = $pointer;
35387551eb4fSHeinrich Schuchardt					$comp_pointer =~ s/\s//g;
35397551eb4fSHeinrich Schuchardt					$decl .= $comp_pointer;
35407551eb4fSHeinrich Schuchardt					$decl = rtrim($decl) if ($var eq "");
35417551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s@\b$sign\s*\Q$pointer\E\s*$var\b@$decl$var@;
35427551eb4fSHeinrich Schuchardt				}
35437551eb4fSHeinrich Schuchardt			}
35447551eb4fSHeinrich Schuchardt		}
35457551eb4fSHeinrich Schuchardt
3546dd88ab32SMasahiro Yamada# TEST: allow direct testing of the type matcher.
3547dd88ab32SMasahiro Yamada		if ($dbg_type) {
3548dd88ab32SMasahiro Yamada			if ($line =~ /^.\s*$Declare\s*$/) {
3549dd88ab32SMasahiro Yamada				ERROR("TEST_TYPE",
3550dd88ab32SMasahiro Yamada				      "TEST: is type\n" . $herecurr);
3551dd88ab32SMasahiro Yamada			} elsif ($dbg_type > 1 && $line =~ /^.+($Declare)/) {
3552dd88ab32SMasahiro Yamada				ERROR("TEST_NOT_TYPE",
3553dd88ab32SMasahiro Yamada				      "TEST: is not type ($1 is)\n". $herecurr);
3554dd88ab32SMasahiro Yamada			}
3555dd88ab32SMasahiro Yamada			next;
3556dd88ab32SMasahiro Yamada		}
3557dd88ab32SMasahiro Yamada# TEST: allow direct testing of the attribute matcher.
3558dd88ab32SMasahiro Yamada		if ($dbg_attr) {
3559dd88ab32SMasahiro Yamada			if ($line =~ /^.\s*$Modifier\s*$/) {
3560dd88ab32SMasahiro Yamada				ERROR("TEST_ATTR",
3561dd88ab32SMasahiro Yamada				      "TEST: is attr\n" . $herecurr);
3562dd88ab32SMasahiro Yamada			} elsif ($dbg_attr > 1 && $line =~ /^.+($Modifier)/) {
3563dd88ab32SMasahiro Yamada				ERROR("TEST_NOT_ATTR",
3564dd88ab32SMasahiro Yamada				      "TEST: is not attr ($1 is)\n". $herecurr);
3565dd88ab32SMasahiro Yamada			}
3566dd88ab32SMasahiro Yamada			next;
3567dd88ab32SMasahiro Yamada		}
3568dd88ab32SMasahiro Yamada
3569dd88ab32SMasahiro Yamada# check for initialisation to aggregates open brace on the next line
3570dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*{/ &&
3571dd88ab32SMasahiro Yamada		    $prevline =~ /(?:^|[^=])=\s*$/) {
35727551eb4fSHeinrich Schuchardt			if (ERROR("OPEN_BRACE",
35737551eb4fSHeinrich Schuchardt				  "that open brace { should be on the previous line\n" . $hereprev) &&
35747551eb4fSHeinrich Schuchardt			    $fix && $prevline =~ /^\+/ && $line =~ /^\+/) {
35757551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr - 1, $prevrawline);
35767551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
35777551eb4fSHeinrich Schuchardt				my $fixedline = $prevrawline;
35787551eb4fSHeinrich Schuchardt				$fixedline =~ s/\s*=\s*$/ = {/;
35797551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, $fixedline);
35807551eb4fSHeinrich Schuchardt				$fixedline = $line;
35817551eb4fSHeinrich Schuchardt				$fixedline =~ s/^(.\s*)\{\s*/$1/;
35827551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, $fixedline);
35837551eb4fSHeinrich Schuchardt			}
3584dd88ab32SMasahiro Yamada		}
3585dd88ab32SMasahiro Yamada
3586dd88ab32SMasahiro Yamada#
3587dd88ab32SMasahiro Yamada# Checks which are anchored on the added line.
3588dd88ab32SMasahiro Yamada#
3589dd88ab32SMasahiro Yamada
3590dd88ab32SMasahiro Yamada# check for malformed paths in #include statements (uses RAW line)
3591dd88ab32SMasahiro Yamada		if ($rawline =~ m{^.\s*\#\s*include\s+[<"](.*)[">]}) {
3592dd88ab32SMasahiro Yamada			my $path = $1;
3593dd88ab32SMasahiro Yamada			if ($path =~ m{//}) {
3594dd88ab32SMasahiro Yamada				ERROR("MALFORMED_INCLUDE",
3595dd88ab32SMasahiro Yamada				      "malformed #include filename\n" . $herecurr);
3596dd88ab32SMasahiro Yamada			}
3597dd88ab32SMasahiro Yamada			if ($path =~ "^uapi/" && $realfile =~ m@\binclude/uapi/@) {
3598dd88ab32SMasahiro Yamada				ERROR("UAPI_INCLUDE",
3599dd88ab32SMasahiro Yamada				      "No #include in ...include/uapi/... should use a uapi/ path prefix\n" . $herecurr);
3600dd88ab32SMasahiro Yamada			}
3601dd88ab32SMasahiro Yamada		}
3602dd88ab32SMasahiro Yamada
3603dd88ab32SMasahiro Yamada# no C99 // comments
3604dd88ab32SMasahiro Yamada		if ($line =~ m{//}) {
36056b9709d9STom Rini			if (ERROR("C99_COMMENTS",
36066b9709d9STom Rini				  "do not use C99 // comments\n" . $herecurr) &&
36076b9709d9STom Rini			    $fix) {
36087551eb4fSHeinrich Schuchardt				my $line = $fixed[$fixlinenr];
36096b9709d9STom Rini				if ($line =~ /\/\/(.*)$/) {
36106b9709d9STom Rini					my $comment = trim($1);
36117551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s@\/\/(.*)$@/\* $comment \*/@;
36126b9709d9STom Rini				}
36136b9709d9STom Rini			}
3614dd88ab32SMasahiro Yamada		}
3615dd88ab32SMasahiro Yamada		# Remove C99 comments.
3616dd88ab32SMasahiro Yamada		$line =~ s@//.*@@;
3617dd88ab32SMasahiro Yamada		$opline =~ s@//.*@@;
3618dd88ab32SMasahiro Yamada
3619dd88ab32SMasahiro Yamada# EXPORT_SYMBOL should immediately follow the thing it is exporting, consider
3620dd88ab32SMasahiro Yamada# the whole statement.
3621dd88ab32SMasahiro Yamada#print "APW <$lines[$realline_next - 1]>\n";
3622dd88ab32SMasahiro Yamada		if (defined $realline_next &&
3623dd88ab32SMasahiro Yamada		    exists $lines[$realline_next - 1] &&
3624dd88ab32SMasahiro Yamada		    !defined $suppress_export{$realline_next} &&
3625dd88ab32SMasahiro Yamada		    ($lines[$realline_next - 1] =~ /EXPORT_SYMBOL.*\((.*)\)/ ||
3626dd88ab32SMasahiro Yamada		     $lines[$realline_next - 1] =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) {
3627dd88ab32SMasahiro Yamada			# Handle definitions which produce identifiers with
3628dd88ab32SMasahiro Yamada			# a prefix:
3629dd88ab32SMasahiro Yamada			#   XXX(foo);
3630dd88ab32SMasahiro Yamada			#   EXPORT_SYMBOL(something_foo);
3631dd88ab32SMasahiro Yamada			my $name = $1;
3632dd88ab32SMasahiro Yamada			if ($stat =~ /^(?:.\s*}\s*\n)?.([A-Z_]+)\s*\(\s*($Ident)/ &&
3633dd88ab32SMasahiro Yamada			    $name =~ /^${Ident}_$2/) {
3634dd88ab32SMasahiro Yamada#print "FOO C name<$name>\n";
3635dd88ab32SMasahiro Yamada				$suppress_export{$realline_next} = 1;
3636dd88ab32SMasahiro Yamada
3637dd88ab32SMasahiro Yamada			} elsif ($stat !~ /(?:
3638dd88ab32SMasahiro Yamada				\n.}\s*$|
3639dd88ab32SMasahiro Yamada				^.DEFINE_$Ident\(\Q$name\E\)|
3640dd88ab32SMasahiro Yamada				^.DECLARE_$Ident\(\Q$name\E\)|
3641dd88ab32SMasahiro Yamada				^.LIST_HEAD\(\Q$name\E\)|
3642dd88ab32SMasahiro Yamada				^.(?:$Storage\s+)?$Type\s*\(\s*\*\s*\Q$name\E\s*\)\s*\(|
3643dd88ab32SMasahiro Yamada				\b\Q$name\E(?:\s+$Attribute)*\s*(?:;|=|\[|\()
3644dd88ab32SMasahiro Yamada			    )/x) {
3645dd88ab32SMasahiro Yamada#print "FOO A<$lines[$realline_next - 1]> stat<$stat> name<$name>\n";
3646dd88ab32SMasahiro Yamada				$suppress_export{$realline_next} = 2;
3647dd88ab32SMasahiro Yamada			} else {
3648dd88ab32SMasahiro Yamada				$suppress_export{$realline_next} = 1;
3649dd88ab32SMasahiro Yamada			}
3650dd88ab32SMasahiro Yamada		}
3651dd88ab32SMasahiro Yamada		if (!defined $suppress_export{$linenr} &&
3652dd88ab32SMasahiro Yamada		    $prevline =~ /^.\s*$/ &&
3653dd88ab32SMasahiro Yamada		    ($line =~ /EXPORT_SYMBOL.*\((.*)\)/ ||
3654dd88ab32SMasahiro Yamada		     $line =~ /EXPORT_UNUSED_SYMBOL.*\((.*)\)/)) {
3655dd88ab32SMasahiro Yamada#print "FOO B <$lines[$linenr - 1]>\n";
3656dd88ab32SMasahiro Yamada			$suppress_export{$linenr} = 2;
3657dd88ab32SMasahiro Yamada		}
3658dd88ab32SMasahiro Yamada		if (defined $suppress_export{$linenr} &&
3659dd88ab32SMasahiro Yamada		    $suppress_export{$linenr} == 2) {
3660dd88ab32SMasahiro Yamada			WARN("EXPORT_SYMBOL",
3661dd88ab32SMasahiro Yamada			     "EXPORT_SYMBOL(foo); should immediately follow its function/variable\n" . $herecurr);
3662dd88ab32SMasahiro Yamada		}
3663dd88ab32SMasahiro Yamada
3664dd88ab32SMasahiro Yamada# check for global initialisers.
36657551eb4fSHeinrich Schuchardt		if ($line =~ /^\+$Type\s*$Ident(?:\s+$Modifier)*\s*=\s*($zero_initializer)\s*;/) {
36666b9709d9STom Rini			if (ERROR("GLOBAL_INITIALISERS",
36677551eb4fSHeinrich Schuchardt				  "do not initialise globals to $1\n" . $herecurr) &&
36686b9709d9STom Rini			    $fix) {
36697551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/(^.$Type\s*$Ident(?:\s+$Modifier)*)\s*=\s*$zero_initializer\s*;/$1;/;
36706b9709d9STom Rini			}
3671dd88ab32SMasahiro Yamada		}
3672dd88ab32SMasahiro Yamada# check for static initialisers.
36737551eb4fSHeinrich Schuchardt		if ($line =~ /^\+.*\bstatic\s.*=\s*($zero_initializer)\s*;/) {
36746b9709d9STom Rini			if (ERROR("INITIALISED_STATIC",
36757551eb4fSHeinrich Schuchardt				  "do not initialise statics to $1\n" .
36766b9709d9STom Rini				      $herecurr) &&
36776b9709d9STom Rini			    $fix) {
36787551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/(\bstatic\s.*?)\s*=\s*$zero_initializer\s*;/$1;/;
36796b9709d9STom Rini			}
3680dd88ab32SMasahiro Yamada		}
3681dd88ab32SMasahiro Yamada
36827551eb4fSHeinrich Schuchardt# check for misordered declarations of char/short/int/long with signed/unsigned
36837551eb4fSHeinrich Schuchardt		while ($sline =~ m{(\b$TypeMisordered\b)}g) {
36847551eb4fSHeinrich Schuchardt			my $tmp = trim($1);
36857551eb4fSHeinrich Schuchardt			WARN("MISORDERED_TYPE",
36867551eb4fSHeinrich Schuchardt			     "type '$tmp' should be specified in [[un]signed] [short|int|long|long long] order\n" . $herecurr);
36877551eb4fSHeinrich Schuchardt		}
36887551eb4fSHeinrich Schuchardt
3689dd88ab32SMasahiro Yamada# check for static const char * arrays.
3690dd88ab32SMasahiro Yamada		if ($line =~ /\bstatic\s+const\s+char\s*\*\s*(\w+)\s*\[\s*\]\s*=\s*/) {
3691dd88ab32SMasahiro Yamada			WARN("STATIC_CONST_CHAR_ARRAY",
3692dd88ab32SMasahiro Yamada			     "static const char * array should probably be static const char * const\n" .
3693dd88ab32SMasahiro Yamada				$herecurr);
3694dd88ab32SMasahiro Yamada               }
3695dd88ab32SMasahiro Yamada
3696dd88ab32SMasahiro Yamada# check for static char foo[] = "bar" declarations.
3697dd88ab32SMasahiro Yamada		if ($line =~ /\bstatic\s+char\s+(\w+)\s*\[\s*\]\s*=\s*"/) {
3698dd88ab32SMasahiro Yamada			WARN("STATIC_CONST_CHAR_ARRAY",
3699dd88ab32SMasahiro Yamada			     "static char array declaration should probably be static const char\n" .
3700dd88ab32SMasahiro Yamada				$herecurr);
3701dd88ab32SMasahiro Yamada               }
3702dd88ab32SMasahiro Yamada
37037551eb4fSHeinrich Schuchardt# check for const <foo> const where <foo> is not a pointer or array type
37047551eb4fSHeinrich Schuchardt		if ($sline =~ /\bconst\s+($BasicType)\s+const\b/) {
37057551eb4fSHeinrich Schuchardt			my $found = $1;
37067551eb4fSHeinrich Schuchardt			if ($sline =~ /\bconst\s+\Q$found\E\s+const\b\s*\*/) {
37077551eb4fSHeinrich Schuchardt				WARN("CONST_CONST",
37087551eb4fSHeinrich Schuchardt				     "'const $found const *' should probably be 'const $found * const'\n" . $herecurr);
37097551eb4fSHeinrich Schuchardt			} elsif ($sline !~ /\bconst\s+\Q$found\E\s+const\s+\w+\s*\[/) {
37107551eb4fSHeinrich Schuchardt				WARN("CONST_CONST",
37117551eb4fSHeinrich Schuchardt				     "'const $found const' should probably be 'const $found'\n" . $herecurr);
37127551eb4fSHeinrich Schuchardt			}
37137551eb4fSHeinrich Schuchardt		}
37147551eb4fSHeinrich Schuchardt
37157551eb4fSHeinrich Schuchardt# check for non-global char *foo[] = {"bar", ...} declarations.
37167551eb4fSHeinrich Schuchardt		if ($line =~ /^.\s+(?:static\s+|const\s+)?char\s+\*\s*\w+\s*\[\s*\]\s*=\s*\{/) {
37177551eb4fSHeinrich Schuchardt			WARN("STATIC_CONST_CHAR_ARRAY",
37187551eb4fSHeinrich Schuchardt			     "char * array declaration might be better as static const\n" .
37197551eb4fSHeinrich Schuchardt				$herecurr);
37207551eb4fSHeinrich Schuchardt               }
37217551eb4fSHeinrich Schuchardt
37227551eb4fSHeinrich Schuchardt# check for sizeof(foo)/sizeof(foo[0]) that could be ARRAY_SIZE(foo)
37237551eb4fSHeinrich Schuchardt		if ($line =~ m@\bsizeof\s*\(\s*($Lval)\s*\)@) {
37247551eb4fSHeinrich Schuchardt			my $array = $1;
37257551eb4fSHeinrich Schuchardt			if ($line =~ m@\b(sizeof\s*\(\s*\Q$array\E\s*\)\s*/\s*sizeof\s*\(\s*\Q$array\E\s*\[\s*0\s*\]\s*\))@) {
37267551eb4fSHeinrich Schuchardt				my $array_div = $1;
37277551eb4fSHeinrich Schuchardt				if (WARN("ARRAY_SIZE",
37287551eb4fSHeinrich Schuchardt					 "Prefer ARRAY_SIZE($array)\n" . $herecurr) &&
37297551eb4fSHeinrich Schuchardt				    $fix) {
37307551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\Q$array_div\E/ARRAY_SIZE($array)/;
37317551eb4fSHeinrich Schuchardt				}
37327551eb4fSHeinrich Schuchardt			}
37337551eb4fSHeinrich Schuchardt		}
37347551eb4fSHeinrich Schuchardt
37356b9709d9STom Rini# check for function declarations without arguments like "int foo()"
37366b9709d9STom Rini		if ($line =~ /(\b$Type\s+$Ident)\s*\(\s*\)/) {
37376b9709d9STom Rini			if (ERROR("FUNCTION_WITHOUT_ARGS",
37386b9709d9STom Rini				  "Bad function definition - $1() should probably be $1(void)\n" . $herecurr) &&
37396b9709d9STom Rini			    $fix) {
37407551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/(\b($Type)\s+($Ident))\s*\(\s*\)/$2 $3(void)/;
37416b9709d9STom Rini			}
3742dd88ab32SMasahiro Yamada		}
3743dd88ab32SMasahiro Yamada
3744dd88ab32SMasahiro Yamada# check for new typedefs, only function parameters and sparse annotations
3745dd88ab32SMasahiro Yamada# make sense.
3746dd88ab32SMasahiro Yamada		if ($line =~ /\btypedef\s/ &&
3747dd88ab32SMasahiro Yamada		    $line !~ /\btypedef\s+$Type\s*\(\s*\*?$Ident\s*\)\s*\(/ &&
3748dd88ab32SMasahiro Yamada		    $line !~ /\btypedef\s+$Type\s+$Ident\s*\(/ &&
3749dd88ab32SMasahiro Yamada		    $line !~ /\b$typeTypedefs\b/ &&
37507551eb4fSHeinrich Schuchardt		    $line !~ /\b__bitwise\b/) {
3751dd88ab32SMasahiro Yamada			WARN("NEW_TYPEDEFS",
3752dd88ab32SMasahiro Yamada			     "do not add new typedefs\n" . $herecurr);
3753dd88ab32SMasahiro Yamada		}
3754dd88ab32SMasahiro Yamada
3755dd88ab32SMasahiro Yamada# * goes on variable not on type
3756dd88ab32SMasahiro Yamada		# (char*[ const])
3757dd88ab32SMasahiro Yamada		while ($line =~ m{(\($NonptrType(\s*(?:$Modifier\b\s*|\*\s*)+)\))}g) {
3758dd88ab32SMasahiro Yamada			#print "AA<$1>\n";
37596b9709d9STom Rini			my ($ident, $from, $to) = ($1, $2, $2);
3760dd88ab32SMasahiro Yamada
3761dd88ab32SMasahiro Yamada			# Should start with a space.
3762dd88ab32SMasahiro Yamada			$to =~ s/^(\S)/ $1/;
3763dd88ab32SMasahiro Yamada			# Should not end with a space.
3764dd88ab32SMasahiro Yamada			$to =~ s/\s+$//;
3765dd88ab32SMasahiro Yamada			# '*'s should not have spaces between.
3766dd88ab32SMasahiro Yamada			while ($to =~ s/\*\s+\*/\*\*/) {
3767dd88ab32SMasahiro Yamada			}
3768dd88ab32SMasahiro Yamada
37696b9709d9STom Rini##			print "1: from<$from> to<$to> ident<$ident>\n";
3770dd88ab32SMasahiro Yamada			if ($from ne $to) {
37716b9709d9STom Rini				if (ERROR("POINTER_LOCATION",
37726b9709d9STom Rini					  "\"(foo$from)\" should be \"(foo$to)\"\n" .  $herecurr) &&
37736b9709d9STom Rini				    $fix) {
37746b9709d9STom Rini					my $sub_from = $ident;
37756b9709d9STom Rini					my $sub_to = $ident;
37766b9709d9STom Rini					$sub_to =~ s/\Q$from\E/$to/;
37777551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~
37786b9709d9STom Rini					    s@\Q$sub_from\E@$sub_to@;
37796b9709d9STom Rini				}
3780dd88ab32SMasahiro Yamada			}
3781dd88ab32SMasahiro Yamada		}
3782dd88ab32SMasahiro Yamada		while ($line =~ m{(\b$NonptrType(\s*(?:$Modifier\b\s*|\*\s*)+)($Ident))}g) {
3783dd88ab32SMasahiro Yamada			#print "BB<$1>\n";
37846b9709d9STom Rini			my ($match, $from, $to, $ident) = ($1, $2, $2, $3);
3785dd88ab32SMasahiro Yamada
3786dd88ab32SMasahiro Yamada			# Should start with a space.
3787dd88ab32SMasahiro Yamada			$to =~ s/^(\S)/ $1/;
3788dd88ab32SMasahiro Yamada			# Should not end with a space.
3789dd88ab32SMasahiro Yamada			$to =~ s/\s+$//;
3790dd88ab32SMasahiro Yamada			# '*'s should not have spaces between.
3791dd88ab32SMasahiro Yamada			while ($to =~ s/\*\s+\*/\*\*/) {
3792dd88ab32SMasahiro Yamada			}
3793dd88ab32SMasahiro Yamada			# Modifiers should have spaces.
3794dd88ab32SMasahiro Yamada			$to =~ s/(\b$Modifier$)/$1 /;
3795dd88ab32SMasahiro Yamada
37966b9709d9STom Rini##			print "2: from<$from> to<$to> ident<$ident>\n";
3797dd88ab32SMasahiro Yamada			if ($from ne $to && $ident !~ /^$Modifier$/) {
37986b9709d9STom Rini				if (ERROR("POINTER_LOCATION",
37996b9709d9STom Rini					  "\"foo${from}bar\" should be \"foo${to}bar\"\n" .  $herecurr) &&
38006b9709d9STom Rini				    $fix) {
38016b9709d9STom Rini
38026b9709d9STom Rini					my $sub_from = $match;
38036b9709d9STom Rini					my $sub_to = $match;
38046b9709d9STom Rini					$sub_to =~ s/\Q$from\E/$to/;
38057551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~
38066b9709d9STom Rini					    s@\Q$sub_from\E@$sub_to@;
38076b9709d9STom Rini				}
3808dd88ab32SMasahiro Yamada			}
3809dd88ab32SMasahiro Yamada		}
3810dd88ab32SMasahiro Yamada
38117551eb4fSHeinrich Schuchardt# avoid BUG() or BUG_ON()
38127551eb4fSHeinrich Schuchardt		if ($line =~ /\b(?:BUG|BUG_ON)\b/) {
38137551eb4fSHeinrich Schuchardt			my $msg_type = \&WARN;
38147551eb4fSHeinrich Schuchardt			$msg_type = \&CHK if ($file);
38157551eb4fSHeinrich Schuchardt			&{$msg_type}("AVOID_BUG",
38167551eb4fSHeinrich Schuchardt				     "Avoid crashing the kernel - try using WARN_ON & recovery code rather than BUG() or BUG_ON()\n" . $herecurr);
38177551eb4fSHeinrich Schuchardt		}
3818dd88ab32SMasahiro Yamada
38197551eb4fSHeinrich Schuchardt# avoid LINUX_VERSION_CODE
3820dd88ab32SMasahiro Yamada		if ($line =~ /\bLINUX_VERSION_CODE\b/) {
3821dd88ab32SMasahiro Yamada			WARN("LINUX_VERSION_CODE",
3822dd88ab32SMasahiro Yamada			     "LINUX_VERSION_CODE should be avoided, code should be for the version to which it is merged\n" . $herecurr);
3823dd88ab32SMasahiro Yamada		}
3824dd88ab32SMasahiro Yamada
3825dd88ab32SMasahiro Yamada# check for uses of printk_ratelimit
3826dd88ab32SMasahiro Yamada		if ($line =~ /\bprintk_ratelimit\s*\(/) {
3827dd88ab32SMasahiro Yamada			WARN("PRINTK_RATELIMITED",
3828dd88ab32SMasahiro Yamada			     "Prefer printk_ratelimited or pr_<level>_ratelimited to printk_ratelimit\n" . $herecurr);
3829dd88ab32SMasahiro Yamada		}
3830dd88ab32SMasahiro Yamada
3831dd88ab32SMasahiro Yamada# printk should use KERN_* levels.  Note that follow on printk's on the
3832dd88ab32SMasahiro Yamada# same line do not need a level, so we use the current block context
3833dd88ab32SMasahiro Yamada# to try and find and validate the current printk.  In summary the current
3834dd88ab32SMasahiro Yamada# printk includes all preceding printk's which have no newline on the end.
3835dd88ab32SMasahiro Yamada# we assume the first bad printk is the one to report.
3836dd88ab32SMasahiro Yamada		if ($line =~ /\bprintk\((?!KERN_)\s*"/) {
3837dd88ab32SMasahiro Yamada			my $ok = 0;
3838dd88ab32SMasahiro Yamada			for (my $ln = $linenr - 1; $ln >= $first_line; $ln--) {
3839dd88ab32SMasahiro Yamada				#print "CHECK<$lines[$ln - 1]\n";
3840dd88ab32SMasahiro Yamada				# we have a preceding printk if it ends
3841dd88ab32SMasahiro Yamada				# with "\n" ignore it, else it is to blame
3842dd88ab32SMasahiro Yamada				if ($lines[$ln - 1] =~ m{\bprintk\(}) {
3843dd88ab32SMasahiro Yamada					if ($rawlines[$ln - 1] !~ m{\\n"}) {
3844dd88ab32SMasahiro Yamada						$ok = 1;
3845dd88ab32SMasahiro Yamada					}
3846dd88ab32SMasahiro Yamada					last;
3847dd88ab32SMasahiro Yamada				}
3848dd88ab32SMasahiro Yamada			}
3849dd88ab32SMasahiro Yamada			if ($ok == 0) {
3850dd88ab32SMasahiro Yamada				WARN("PRINTK_WITHOUT_KERN_LEVEL",
3851dd88ab32SMasahiro Yamada				     "printk() should include KERN_ facility level\n" . $herecurr);
3852dd88ab32SMasahiro Yamada			}
3853dd88ab32SMasahiro Yamada		}
3854dd88ab32SMasahiro Yamada
3855dd88ab32SMasahiro Yamada		if ($line =~ /\bprintk\s*\(\s*KERN_([A-Z]+)/) {
3856dd88ab32SMasahiro Yamada			my $orig = $1;
3857dd88ab32SMasahiro Yamada			my $level = lc($orig);
3858dd88ab32SMasahiro Yamada			$level = "warn" if ($level eq "warning");
3859dd88ab32SMasahiro Yamada			my $level2 = $level;
3860dd88ab32SMasahiro Yamada			$level2 = "dbg" if ($level eq "debug");
3861dd88ab32SMasahiro Yamada			WARN("PREFER_PR_LEVEL",
38627551eb4fSHeinrich Schuchardt			     "Prefer [subsystem eg: netdev]_$level2([subsystem]dev, ... then dev_$level2(dev, ... then pr_$level(...  to printk(KERN_$orig ...\n" . $herecurr);
3863dd88ab32SMasahiro Yamada		}
3864dd88ab32SMasahiro Yamada
3865dd88ab32SMasahiro Yamada		if ($line =~ /\bpr_warning\s*\(/) {
38666b9709d9STom Rini			if (WARN("PREFER_PR_LEVEL",
38676b9709d9STom Rini				 "Prefer pr_warn(... to pr_warning(...\n" . $herecurr) &&
38686b9709d9STom Rini			    $fix) {
38697551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
38706b9709d9STom Rini				    s/\bpr_warning\b/pr_warn/;
38716b9709d9STom Rini			}
3872dd88ab32SMasahiro Yamada		}
3873dd88ab32SMasahiro Yamada
3874dd88ab32SMasahiro Yamada		if ($line =~ /\bdev_printk\s*\(\s*KERN_([A-Z]+)/) {
3875dd88ab32SMasahiro Yamada			my $orig = $1;
3876dd88ab32SMasahiro Yamada			my $level = lc($orig);
3877dd88ab32SMasahiro Yamada			$level = "warn" if ($level eq "warning");
3878dd88ab32SMasahiro Yamada			$level = "dbg" if ($level eq "debug");
3879dd88ab32SMasahiro Yamada			WARN("PREFER_DEV_LEVEL",
3880dd88ab32SMasahiro Yamada			     "Prefer dev_$level(... to dev_printk(KERN_$orig, ...\n" . $herecurr);
3881dd88ab32SMasahiro Yamada		}
3882dd88ab32SMasahiro Yamada
38837551eb4fSHeinrich Schuchardt# ENOSYS means "bad syscall nr" and nothing else.  This will have a small
38847551eb4fSHeinrich Schuchardt# number of false positives, but assembly files are not checked, so at
38857551eb4fSHeinrich Schuchardt# least the arch entry code will not trigger this warning.
38867551eb4fSHeinrich Schuchardt		if ($line =~ /\bENOSYS\b/) {
38877551eb4fSHeinrich Schuchardt			WARN("ENOSYS",
38887551eb4fSHeinrich Schuchardt			     "ENOSYS means 'invalid syscall nr' and nothing else\n" . $herecurr);
38897551eb4fSHeinrich Schuchardt		}
38907551eb4fSHeinrich Schuchardt
3891dd88ab32SMasahiro Yamada# function brace can't be on same line, except for #defines of do while,
3892dd88ab32SMasahiro Yamada# or if closed on same line
38937551eb4fSHeinrich Schuchardt		if (($line=~/$Type\s*$Ident\(.*\).*\s*{/) and
3894d8a1a304SHeiko Schocher		    !($line=~/\#\s*define.*do\s\{/) and !($line=~/}/)) {
38957551eb4fSHeinrich Schuchardt			if (ERROR("OPEN_BRACE",
38967551eb4fSHeinrich Schuchardt				  "open brace '{' following function declarations go on the next line\n" . $herecurr) &&
38977551eb4fSHeinrich Schuchardt			    $fix) {
38987551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
38997551eb4fSHeinrich Schuchardt				my $fixed_line = $rawline;
39007551eb4fSHeinrich Schuchardt				$fixed_line =~ /(^..*$Type\s*$Ident\(.*\)\s*){(.*)$/;
39017551eb4fSHeinrich Schuchardt				my $line1 = $1;
39027551eb4fSHeinrich Schuchardt				my $line2 = $2;
39037551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, ltrim($line1));
39047551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, "\+{");
39057551eb4fSHeinrich Schuchardt				if ($line2 !~ /^\s*$/) {
39067551eb4fSHeinrich Schuchardt					fix_insert_line($fixlinenr, "\+\t" . trim($line2));
39077551eb4fSHeinrich Schuchardt				}
39087551eb4fSHeinrich Schuchardt			}
3909dd88ab32SMasahiro Yamada		}
3910dd88ab32SMasahiro Yamada
3911dd88ab32SMasahiro Yamada# open braces for enum, union and struct go on the same line.
3912dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*{/ &&
3913dd88ab32SMasahiro Yamada		    $prevline =~ /^.\s*(?:typedef\s+)?(enum|union|struct)(?:\s+$Ident)?\s*$/) {
39147551eb4fSHeinrich Schuchardt			if (ERROR("OPEN_BRACE",
39157551eb4fSHeinrich Schuchardt				  "open brace '{' following $1 go on the same line\n" . $hereprev) &&
39167551eb4fSHeinrich Schuchardt			    $fix && $prevline =~ /^\+/ && $line =~ /^\+/) {
39177551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr - 1, $prevrawline);
39187551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
39197551eb4fSHeinrich Schuchardt				my $fixedline = rtrim($prevrawline) . " {";
39207551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, $fixedline);
39217551eb4fSHeinrich Schuchardt				$fixedline = $rawline;
39227551eb4fSHeinrich Schuchardt				$fixedline =~ s/^(.\s*)\{\s*/$1\t/;
39237551eb4fSHeinrich Schuchardt				if ($fixedline !~ /^\+\s*$/) {
39247551eb4fSHeinrich Schuchardt					fix_insert_line($fixlinenr, $fixedline);
39257551eb4fSHeinrich Schuchardt				}
39267551eb4fSHeinrich Schuchardt			}
3927dd88ab32SMasahiro Yamada		}
3928dd88ab32SMasahiro Yamada
3929dd88ab32SMasahiro Yamada# missing space after union, struct or enum definition
39306b9709d9STom Rini		if ($line =~ /^.\s*(?:typedef\s+)?(enum|union|struct)(?:\s+$Ident){1,2}[=\{]/) {
39316b9709d9STom Rini			if (WARN("SPACING",
39326b9709d9STom Rini				 "missing space after $1 definition\n" . $herecurr) &&
39336b9709d9STom Rini			    $fix) {
39347551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
39356b9709d9STom Rini				    s/^(.\s*(?:typedef\s+)?(?:enum|union|struct)(?:\s+$Ident){1,2})([=\{])/$1 $2/;
39366b9709d9STom Rini			}
39376b9709d9STom Rini		}
39386b9709d9STom Rini
39396b9709d9STom Rini# Function pointer declarations
39406b9709d9STom Rini# check spacing between type, funcptr, and args
39416b9709d9STom Rini# canonical declaration is "type (*funcptr)(args...)"
39427551eb4fSHeinrich Schuchardt		if ($line =~ /^.\s*($Declare)\((\s*)\*(\s*)($Ident)(\s*)\)(\s*)\(/) {
39436b9709d9STom Rini			my $declare = $1;
39446b9709d9STom Rini			my $pre_pointer_space = $2;
39456b9709d9STom Rini			my $post_pointer_space = $3;
39466b9709d9STom Rini			my $funcname = $4;
39476b9709d9STom Rini			my $post_funcname_space = $5;
39486b9709d9STom Rini			my $pre_args_space = $6;
39496b9709d9STom Rini
39507551eb4fSHeinrich Schuchardt# the $Declare variable will capture all spaces after the type
39517551eb4fSHeinrich Schuchardt# so check it for a missing trailing missing space but pointer return types
39527551eb4fSHeinrich Schuchardt# don't need a space so don't warn for those.
39537551eb4fSHeinrich Schuchardt			my $post_declare_space = "";
39547551eb4fSHeinrich Schuchardt			if ($declare =~ /(\s+)$/) {
39557551eb4fSHeinrich Schuchardt				$post_declare_space = $1;
39567551eb4fSHeinrich Schuchardt				$declare = rtrim($declare);
39577551eb4fSHeinrich Schuchardt			}
39587551eb4fSHeinrich Schuchardt			if ($declare !~ /\*$/ && $post_declare_space =~ /^$/) {
3959dd88ab32SMasahiro Yamada				WARN("SPACING",
39606b9709d9STom Rini				     "missing space after return type\n" . $herecurr);
39617551eb4fSHeinrich Schuchardt				$post_declare_space = " ";
39626b9709d9STom Rini			}
39636b9709d9STom Rini
39646b9709d9STom Rini# unnecessary space "type  (*funcptr)(args...)"
39657551eb4fSHeinrich Schuchardt# This test is not currently implemented because these declarations are
39667551eb4fSHeinrich Schuchardt# equivalent to
39677551eb4fSHeinrich Schuchardt#	int  foo(int bar, ...)
39687551eb4fSHeinrich Schuchardt# and this is form shouldn't/doesn't generate a checkpatch warning.
39697551eb4fSHeinrich Schuchardt#
39707551eb4fSHeinrich Schuchardt#			elsif ($declare =~ /\s{2,}$/) {
39717551eb4fSHeinrich Schuchardt#				WARN("SPACING",
39727551eb4fSHeinrich Schuchardt#				     "Multiple spaces after return type\n" . $herecurr);
39737551eb4fSHeinrich Schuchardt#			}
39746b9709d9STom Rini
39756b9709d9STom Rini# unnecessary space "type ( *funcptr)(args...)"
39766b9709d9STom Rini			if (defined $pre_pointer_space &&
39776b9709d9STom Rini			    $pre_pointer_space =~ /^\s/) {
39786b9709d9STom Rini				WARN("SPACING",
39796b9709d9STom Rini				     "Unnecessary space after function pointer open parenthesis\n" . $herecurr);
39806b9709d9STom Rini			}
39816b9709d9STom Rini
39826b9709d9STom Rini# unnecessary space "type (* funcptr)(args...)"
39836b9709d9STom Rini			if (defined $post_pointer_space &&
39846b9709d9STom Rini			    $post_pointer_space =~ /^\s/) {
39856b9709d9STom Rini				WARN("SPACING",
39866b9709d9STom Rini				     "Unnecessary space before function pointer name\n" . $herecurr);
39876b9709d9STom Rini			}
39886b9709d9STom Rini
39896b9709d9STom Rini# unnecessary space "type (*funcptr )(args...)"
39906b9709d9STom Rini			if (defined $post_funcname_space &&
39916b9709d9STom Rini			    $post_funcname_space =~ /^\s/) {
39926b9709d9STom Rini				WARN("SPACING",
39936b9709d9STom Rini				     "Unnecessary space after function pointer name\n" . $herecurr);
39946b9709d9STom Rini			}
39956b9709d9STom Rini
39966b9709d9STom Rini# unnecessary space "type (*funcptr) (args...)"
39976b9709d9STom Rini			if (defined $pre_args_space &&
39986b9709d9STom Rini			    $pre_args_space =~ /^\s/) {
39996b9709d9STom Rini				WARN("SPACING",
40006b9709d9STom Rini				     "Unnecessary space before function pointer arguments\n" . $herecurr);
40016b9709d9STom Rini			}
40026b9709d9STom Rini
40036b9709d9STom Rini			if (show_type("SPACING") && $fix) {
40047551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
40057551eb4fSHeinrich Schuchardt				    s/^(.\s*)$Declare\s*\(\s*\*\s*$Ident\s*\)\s*\(/$1 . $declare . $post_declare_space . '(*' . $funcname . ')('/ex;
40066b9709d9STom Rini			}
4007dd88ab32SMasahiro Yamada		}
4008dd88ab32SMasahiro Yamada
4009dd88ab32SMasahiro Yamada# check for spacing round square brackets; allowed:
4010dd88ab32SMasahiro Yamada#  1. with a type on the left -- int [] a;
4011dd88ab32SMasahiro Yamada#  2. at the beginning of a line for slice initialisers -- [0...10] = 5,
4012dd88ab32SMasahiro Yamada#  3. inside a curly brace -- = { [0...10] = 5 }
4013dd88ab32SMasahiro Yamada		while ($line =~ /(.*?\s)\[/g) {
4014dd88ab32SMasahiro Yamada			my ($where, $prefix) = ($-[1], $1);
4015dd88ab32SMasahiro Yamada			if ($prefix !~ /$Type\s+$/ &&
4016dd88ab32SMasahiro Yamada			    ($where != 0 || $prefix !~ /^.\s+$/) &&
4017dd88ab32SMasahiro Yamada			    $prefix !~ /[{,]\s+$/) {
40186b9709d9STom Rini				if (ERROR("BRACKET_SPACE",
40196b9709d9STom Rini					  "space prohibited before open square bracket '['\n" . $herecurr) &&
40206b9709d9STom Rini				    $fix) {
40217551eb4fSHeinrich Schuchardt				    $fixed[$fixlinenr] =~
40226b9709d9STom Rini					s/^(\+.*?)\s+\[/$1\[/;
40236b9709d9STom Rini				}
4024dd88ab32SMasahiro Yamada			}
4025dd88ab32SMasahiro Yamada		}
4026dd88ab32SMasahiro Yamada
4027dd88ab32SMasahiro Yamada# check for spaces between functions and their parentheses.
4028dd88ab32SMasahiro Yamada		while ($line =~ /($Ident)\s+\(/g) {
4029dd88ab32SMasahiro Yamada			my $name = $1;
4030dd88ab32SMasahiro Yamada			my $ctx_before = substr($line, 0, $-[1]);
4031dd88ab32SMasahiro Yamada			my $ctx = "$ctx_before$name";
4032dd88ab32SMasahiro Yamada
4033dd88ab32SMasahiro Yamada			# Ignore those directives where spaces _are_ permitted.
4034dd88ab32SMasahiro Yamada			if ($name =~ /^(?:
4035dd88ab32SMasahiro Yamada				if|for|while|switch|return|case|
4036dd88ab32SMasahiro Yamada				volatile|__volatile__|
4037dd88ab32SMasahiro Yamada				__attribute__|format|__extension__|
4038dd88ab32SMasahiro Yamada				asm|__asm__)$/x)
4039dd88ab32SMasahiro Yamada			{
4040dd88ab32SMasahiro Yamada			# cpp #define statements have non-optional spaces, ie
4041dd88ab32SMasahiro Yamada			# if there is a space between the name and the open
4042dd88ab32SMasahiro Yamada			# parenthesis it is simply not a parameter group.
4043dd88ab32SMasahiro Yamada			} elsif ($ctx_before =~ /^.\s*\#\s*define\s*$/) {
4044dd88ab32SMasahiro Yamada
4045dd88ab32SMasahiro Yamada			# cpp #elif statement condition may start with a (
4046dd88ab32SMasahiro Yamada			} elsif ($ctx =~ /^.\s*\#\s*elif\s*$/) {
4047dd88ab32SMasahiro Yamada
4048dd88ab32SMasahiro Yamada			# If this whole things ends with a type its most
4049dd88ab32SMasahiro Yamada			# likely a typedef for a function.
4050dd88ab32SMasahiro Yamada			} elsif ($ctx =~ /$Type$/) {
4051dd88ab32SMasahiro Yamada
4052dd88ab32SMasahiro Yamada			} else {
40536b9709d9STom Rini				if (WARN("SPACING",
40546b9709d9STom Rini					 "space prohibited between function name and open parenthesis '('\n" . $herecurr) &&
40556b9709d9STom Rini					     $fix) {
40567551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~
40576b9709d9STom Rini					    s/\b$name\s+\(/$name\(/;
4058dd88ab32SMasahiro Yamada				}
4059dd88ab32SMasahiro Yamada			}
4060dd88ab32SMasahiro Yamada		}
4061dd88ab32SMasahiro Yamada
4062dd88ab32SMasahiro Yamada# Check operator spacing.
4063dd88ab32SMasahiro Yamada		if (!($line=~/\#\s*include/)) {
40646b9709d9STom Rini			my $fixed_line = "";
40656b9709d9STom Rini			my $line_fixed = 0;
40666b9709d9STom Rini
4067dd88ab32SMasahiro Yamada			my $ops = qr{
4068dd88ab32SMasahiro Yamada				<<=|>>=|<=|>=|==|!=|
4069dd88ab32SMasahiro Yamada				\+=|-=|\*=|\/=|%=|\^=|\|=|&=|
4070dd88ab32SMasahiro Yamada				=>|->|<<|>>|<|>|=|!|~|
4071dd88ab32SMasahiro Yamada				&&|\|\||,|\^|\+\+|--|&|\||\+|-|\*|\/|%|
40726b9709d9STom Rini				\?:|\?|:
4073dd88ab32SMasahiro Yamada			}x;
4074dd88ab32SMasahiro Yamada			my @elements = split(/($ops|;)/, $opline);
40756b9709d9STom Rini
40766b9709d9STom Rini##			print("element count: <" . $#elements . ">\n");
40776b9709d9STom Rini##			foreach my $el (@elements) {
40786b9709d9STom Rini##				print("el: <$el>\n");
40796b9709d9STom Rini##			}
40806b9709d9STom Rini
40816b9709d9STom Rini			my @fix_elements = ();
4082dd88ab32SMasahiro Yamada			my $off = 0;
4083dd88ab32SMasahiro Yamada
40846b9709d9STom Rini			foreach my $el (@elements) {
40856b9709d9STom Rini				push(@fix_elements, substr($rawline, $off, length($el)));
40866b9709d9STom Rini				$off += length($el);
40876b9709d9STom Rini			}
40886b9709d9STom Rini
40896b9709d9STom Rini			$off = 0;
40906b9709d9STom Rini
4091dd88ab32SMasahiro Yamada			my $blank = copy_spacing($opline);
40926b9709d9STom Rini			my $last_after = -1;
4093dd88ab32SMasahiro Yamada
4094dd88ab32SMasahiro Yamada			for (my $n = 0; $n < $#elements; $n += 2) {
40956b9709d9STom Rini
40966b9709d9STom Rini				my $good = $fix_elements[$n] . $fix_elements[$n + 1];
40976b9709d9STom Rini
40986b9709d9STom Rini##				print("n: <$n> good: <$good>\n");
40996b9709d9STom Rini
4100dd88ab32SMasahiro Yamada				$off += length($elements[$n]);
4101dd88ab32SMasahiro Yamada
4102dd88ab32SMasahiro Yamada				# Pick up the preceding and succeeding characters.
4103dd88ab32SMasahiro Yamada				my $ca = substr($opline, 0, $off);
4104dd88ab32SMasahiro Yamada				my $cc = '';
4105dd88ab32SMasahiro Yamada				if (length($opline) >= ($off + length($elements[$n + 1]))) {
4106dd88ab32SMasahiro Yamada					$cc = substr($opline, $off + length($elements[$n + 1]));
4107dd88ab32SMasahiro Yamada				}
4108dd88ab32SMasahiro Yamada				my $cb = "$ca$;$cc";
4109dd88ab32SMasahiro Yamada
4110dd88ab32SMasahiro Yamada				my $a = '';
4111dd88ab32SMasahiro Yamada				$a = 'V' if ($elements[$n] ne '');
4112dd88ab32SMasahiro Yamada				$a = 'W' if ($elements[$n] =~ /\s$/);
4113dd88ab32SMasahiro Yamada				$a = 'C' if ($elements[$n] =~ /$;$/);
4114dd88ab32SMasahiro Yamada				$a = 'B' if ($elements[$n] =~ /(\[|\()$/);
4115dd88ab32SMasahiro Yamada				$a = 'O' if ($elements[$n] eq '');
4116dd88ab32SMasahiro Yamada				$a = 'E' if ($ca =~ /^\s*$/);
4117dd88ab32SMasahiro Yamada
4118dd88ab32SMasahiro Yamada				my $op = $elements[$n + 1];
4119dd88ab32SMasahiro Yamada
4120dd88ab32SMasahiro Yamada				my $c = '';
4121dd88ab32SMasahiro Yamada				if (defined $elements[$n + 2]) {
4122dd88ab32SMasahiro Yamada					$c = 'V' if ($elements[$n + 2] ne '');
4123dd88ab32SMasahiro Yamada					$c = 'W' if ($elements[$n + 2] =~ /^\s/);
4124dd88ab32SMasahiro Yamada					$c = 'C' if ($elements[$n + 2] =~ /^$;/);
4125dd88ab32SMasahiro Yamada					$c = 'B' if ($elements[$n + 2] =~ /^(\)|\]|;)/);
4126dd88ab32SMasahiro Yamada					$c = 'O' if ($elements[$n + 2] eq '');
4127dd88ab32SMasahiro Yamada					$c = 'E' if ($elements[$n + 2] =~ /^\s*\\$/);
4128dd88ab32SMasahiro Yamada				} else {
4129dd88ab32SMasahiro Yamada					$c = 'E';
4130dd88ab32SMasahiro Yamada				}
4131dd88ab32SMasahiro Yamada
4132dd88ab32SMasahiro Yamada				my $ctx = "${a}x${c}";
4133dd88ab32SMasahiro Yamada
4134dd88ab32SMasahiro Yamada				my $at = "(ctx:$ctx)";
4135dd88ab32SMasahiro Yamada
4136dd88ab32SMasahiro Yamada				my $ptr = substr($blank, 0, $off) . "^";
4137dd88ab32SMasahiro Yamada				my $hereptr = "$hereline$ptr\n";
4138dd88ab32SMasahiro Yamada
4139dd88ab32SMasahiro Yamada				# Pull out the value of this operator.
4140dd88ab32SMasahiro Yamada				my $op_type = substr($curr_values, $off + 1, 1);
4141dd88ab32SMasahiro Yamada
4142dd88ab32SMasahiro Yamada				# Get the full operator variant.
4143dd88ab32SMasahiro Yamada				my $opv = $op . substr($curr_vars, $off, 1);
4144dd88ab32SMasahiro Yamada
4145dd88ab32SMasahiro Yamada				# Ignore operators passed as parameters.
4146dd88ab32SMasahiro Yamada				if ($op_type ne 'V' &&
41477551eb4fSHeinrich Schuchardt				    $ca =~ /\s$/ && $cc =~ /^\s*[,\)]/) {
4148dd88ab32SMasahiro Yamada
4149dd88ab32SMasahiro Yamada#				# Ignore comments
4150dd88ab32SMasahiro Yamada#				} elsif ($op =~ /^$;+$/) {
4151dd88ab32SMasahiro Yamada
4152dd88ab32SMasahiro Yamada				# ; should have either the end of line or a space or \ after it
4153dd88ab32SMasahiro Yamada				} elsif ($op eq ';') {
4154dd88ab32SMasahiro Yamada					if ($ctx !~ /.x[WEBC]/ &&
4155dd88ab32SMasahiro Yamada					    $cc !~ /^\\/ && $cc !~ /^;/) {
41566b9709d9STom Rini						if (ERROR("SPACING",
41576b9709d9STom Rini							  "space required after that '$op' $at\n" . $hereptr)) {
41586b9709d9STom Rini							$good = $fix_elements[$n] . trim($fix_elements[$n + 1]) . " ";
41596b9709d9STom Rini							$line_fixed = 1;
41606b9709d9STom Rini						}
4161dd88ab32SMasahiro Yamada					}
4162dd88ab32SMasahiro Yamada
4163dd88ab32SMasahiro Yamada				# // is a comment
4164dd88ab32SMasahiro Yamada				} elsif ($op eq '//') {
4165dd88ab32SMasahiro Yamada
41667551eb4fSHeinrich Schuchardt				#   :   when part of a bitfield
41677551eb4fSHeinrich Schuchardt				} elsif ($opv eq ':B') {
41687551eb4fSHeinrich Schuchardt					# skip the bitfield test for now
41697551eb4fSHeinrich Schuchardt
4170dd88ab32SMasahiro Yamada				# No spaces for:
4171dd88ab32SMasahiro Yamada				#   ->
41727551eb4fSHeinrich Schuchardt				} elsif ($op eq '->') {
4173dd88ab32SMasahiro Yamada					if ($ctx =~ /Wx.|.xW/) {
41746b9709d9STom Rini						if (ERROR("SPACING",
41756b9709d9STom Rini							  "spaces prohibited around that '$op' $at\n" . $hereptr)) {
41766b9709d9STom Rini							$good = rtrim($fix_elements[$n]) . trim($fix_elements[$n + 1]);
41776b9709d9STom Rini							if (defined $fix_elements[$n + 2]) {
41786b9709d9STom Rini								$fix_elements[$n + 2] =~ s/^\s+//;
41796b9709d9STom Rini							}
41806b9709d9STom Rini							$line_fixed = 1;
41816b9709d9STom Rini						}
4182dd88ab32SMasahiro Yamada					}
4183dd88ab32SMasahiro Yamada
41847551eb4fSHeinrich Schuchardt				# , must not have a space before and must have a space on the right.
4185dd88ab32SMasahiro Yamada				} elsif ($op eq ',') {
41867551eb4fSHeinrich Schuchardt					my $rtrim_before = 0;
41877551eb4fSHeinrich Schuchardt					my $space_after = 0;
41887551eb4fSHeinrich Schuchardt					if ($ctx =~ /Wx./) {
41897551eb4fSHeinrich Schuchardt						if (ERROR("SPACING",
41907551eb4fSHeinrich Schuchardt							  "space prohibited before that '$op' $at\n" . $hereptr)) {
41917551eb4fSHeinrich Schuchardt							$line_fixed = 1;
41927551eb4fSHeinrich Schuchardt							$rtrim_before = 1;
41937551eb4fSHeinrich Schuchardt						}
41947551eb4fSHeinrich Schuchardt					}
4195dd88ab32SMasahiro Yamada					if ($ctx !~ /.x[WEC]/ && $cc !~ /^}/) {
41966b9709d9STom Rini						if (ERROR("SPACING",
41976b9709d9STom Rini							  "space required after that '$op' $at\n" . $hereptr)) {
41986b9709d9STom Rini							$line_fixed = 1;
41996b9709d9STom Rini							$last_after = $n;
42007551eb4fSHeinrich Schuchardt							$space_after = 1;
42017551eb4fSHeinrich Schuchardt						}
42027551eb4fSHeinrich Schuchardt					}
42037551eb4fSHeinrich Schuchardt					if ($rtrim_before || $space_after) {
42047551eb4fSHeinrich Schuchardt						if ($rtrim_before) {
42057551eb4fSHeinrich Schuchardt							$good = rtrim($fix_elements[$n]) . trim($fix_elements[$n + 1]);
42067551eb4fSHeinrich Schuchardt						} else {
42077551eb4fSHeinrich Schuchardt							$good = $fix_elements[$n] . trim($fix_elements[$n + 1]);
42087551eb4fSHeinrich Schuchardt						}
42097551eb4fSHeinrich Schuchardt						if ($space_after) {
42107551eb4fSHeinrich Schuchardt							$good .= " ";
42116b9709d9STom Rini						}
4212dd88ab32SMasahiro Yamada					}
4213dd88ab32SMasahiro Yamada
4214dd88ab32SMasahiro Yamada				# '*' as part of a type definition -- reported already.
4215dd88ab32SMasahiro Yamada				} elsif ($opv eq '*_') {
4216dd88ab32SMasahiro Yamada					#warn "'*' is part of type\n";
4217dd88ab32SMasahiro Yamada
4218dd88ab32SMasahiro Yamada				# unary operators should have a space before and
4219dd88ab32SMasahiro Yamada				# none after.  May be left adjacent to another
4220dd88ab32SMasahiro Yamada				# unary operator, or a cast
4221dd88ab32SMasahiro Yamada				} elsif ($op eq '!' || $op eq '~' ||
4222dd88ab32SMasahiro Yamada					 $opv eq '*U' || $opv eq '-U' ||
4223dd88ab32SMasahiro Yamada					 $opv eq '&U' || $opv eq '&&U') {
4224dd88ab32SMasahiro Yamada					if ($ctx !~ /[WEBC]x./ && $ca !~ /(?:\)|!|~|\*|-|\&|\||\+\+|\-\-|\{)$/) {
42256b9709d9STom Rini						if (ERROR("SPACING",
42266b9709d9STom Rini							  "space required before that '$op' $at\n" . $hereptr)) {
42276b9709d9STom Rini							if ($n != $last_after + 2) {
42286b9709d9STom Rini								$good = $fix_elements[$n] . " " . ltrim($fix_elements[$n + 1]);
42296b9709d9STom Rini								$line_fixed = 1;
42306b9709d9STom Rini							}
42316b9709d9STom Rini						}
4232dd88ab32SMasahiro Yamada					}
4233dd88ab32SMasahiro Yamada					if ($op eq '*' && $cc =~/\s*$Modifier\b/) {
4234dd88ab32SMasahiro Yamada						# A unary '*' may be const
4235dd88ab32SMasahiro Yamada
4236dd88ab32SMasahiro Yamada					} elsif ($ctx =~ /.xW/) {
42376b9709d9STom Rini						if (ERROR("SPACING",
42386b9709d9STom Rini							  "space prohibited after that '$op' $at\n" . $hereptr)) {
42396b9709d9STom Rini							$good = $fix_elements[$n] . rtrim($fix_elements[$n + 1]);
42406b9709d9STom Rini							if (defined $fix_elements[$n + 2]) {
42416b9709d9STom Rini								$fix_elements[$n + 2] =~ s/^\s+//;
42426b9709d9STom Rini							}
42436b9709d9STom Rini							$line_fixed = 1;
42446b9709d9STom Rini						}
4245dd88ab32SMasahiro Yamada					}
4246dd88ab32SMasahiro Yamada
4247dd88ab32SMasahiro Yamada				# unary ++ and unary -- are allowed no space on one side.
4248dd88ab32SMasahiro Yamada				} elsif ($op eq '++' or $op eq '--') {
4249dd88ab32SMasahiro Yamada					if ($ctx !~ /[WEOBC]x[^W]/ && $ctx !~ /[^W]x[WOBEC]/) {
42506b9709d9STom Rini						if (ERROR("SPACING",
42516b9709d9STom Rini							  "space required one side of that '$op' $at\n" . $hereptr)) {
42526b9709d9STom Rini							$good = $fix_elements[$n] . trim($fix_elements[$n + 1]) . " ";
42536b9709d9STom Rini							$line_fixed = 1;
42546b9709d9STom Rini						}
4255dd88ab32SMasahiro Yamada					}
4256dd88ab32SMasahiro Yamada					if ($ctx =~ /Wx[BE]/ ||
4257dd88ab32SMasahiro Yamada					    ($ctx =~ /Wx./ && $cc =~ /^;/)) {
42586b9709d9STom Rini						if (ERROR("SPACING",
42596b9709d9STom Rini							  "space prohibited before that '$op' $at\n" . $hereptr)) {
42606b9709d9STom Rini							$good = rtrim($fix_elements[$n]) . trim($fix_elements[$n + 1]);
42616b9709d9STom Rini							$line_fixed = 1;
42626b9709d9STom Rini						}
4263dd88ab32SMasahiro Yamada					}
4264dd88ab32SMasahiro Yamada					if ($ctx =~ /ExW/) {
42656b9709d9STom Rini						if (ERROR("SPACING",
42666b9709d9STom Rini							  "space prohibited after that '$op' $at\n" . $hereptr)) {
42676b9709d9STom Rini							$good = $fix_elements[$n] . trim($fix_elements[$n + 1]);
42686b9709d9STom Rini							if (defined $fix_elements[$n + 2]) {
42696b9709d9STom Rini								$fix_elements[$n + 2] =~ s/^\s+//;
4270dd88ab32SMasahiro Yamada							}
42716b9709d9STom Rini							$line_fixed = 1;
42726b9709d9STom Rini						}
42736b9709d9STom Rini					}
4274dd88ab32SMasahiro Yamada
4275dd88ab32SMasahiro Yamada				# << and >> may either have or not have spaces both sides
4276dd88ab32SMasahiro Yamada				} elsif ($op eq '<<' or $op eq '>>' or
4277dd88ab32SMasahiro Yamada					 $op eq '&' or $op eq '^' or $op eq '|' or
4278dd88ab32SMasahiro Yamada					 $op eq '+' or $op eq '-' or
4279dd88ab32SMasahiro Yamada					 $op eq '*' or $op eq '/' or
4280dd88ab32SMasahiro Yamada					 $op eq '%')
4281dd88ab32SMasahiro Yamada				{
42827551eb4fSHeinrich Schuchardt					if ($check) {
42837551eb4fSHeinrich Schuchardt						if (defined $fix_elements[$n + 2] && $ctx !~ /[EW]x[EW]/) {
42847551eb4fSHeinrich Schuchardt							if (CHK("SPACING",
42857551eb4fSHeinrich Schuchardt								"spaces preferred around that '$op' $at\n" . $hereptr)) {
42867551eb4fSHeinrich Schuchardt								$good = rtrim($fix_elements[$n]) . " " . trim($fix_elements[$n + 1]) . " ";
42877551eb4fSHeinrich Schuchardt								$fix_elements[$n + 2] =~ s/^\s+//;
42887551eb4fSHeinrich Schuchardt								$line_fixed = 1;
42897551eb4fSHeinrich Schuchardt							}
42907551eb4fSHeinrich Schuchardt						} elsif (!defined $fix_elements[$n + 2] && $ctx !~ /Wx[OE]/) {
42917551eb4fSHeinrich Schuchardt							if (CHK("SPACING",
42927551eb4fSHeinrich Schuchardt								"space preferred before that '$op' $at\n" . $hereptr)) {
42937551eb4fSHeinrich Schuchardt								$good = rtrim($fix_elements[$n]) . " " . trim($fix_elements[$n + 1]);
42947551eb4fSHeinrich Schuchardt								$line_fixed = 1;
42957551eb4fSHeinrich Schuchardt							}
42967551eb4fSHeinrich Schuchardt						}
42977551eb4fSHeinrich Schuchardt					} elsif ($ctx =~ /Wx[^WCE]|[^WCE]xW/) {
42986b9709d9STom Rini						if (ERROR("SPACING",
42996b9709d9STom Rini							  "need consistent spacing around '$op' $at\n" . $hereptr)) {
43006b9709d9STom Rini							$good = rtrim($fix_elements[$n]) . " " . trim($fix_elements[$n + 1]) . " ";
43016b9709d9STom Rini							if (defined $fix_elements[$n + 2]) {
43026b9709d9STom Rini								$fix_elements[$n + 2] =~ s/^\s+//;
43036b9709d9STom Rini							}
43046b9709d9STom Rini							$line_fixed = 1;
43056b9709d9STom Rini						}
4306dd88ab32SMasahiro Yamada					}
4307dd88ab32SMasahiro Yamada
4308dd88ab32SMasahiro Yamada				# A colon needs no spaces before when it is
4309dd88ab32SMasahiro Yamada				# terminating a case value or a label.
4310dd88ab32SMasahiro Yamada				} elsif ($opv eq ':C' || $opv eq ':L') {
4311dd88ab32SMasahiro Yamada					if ($ctx =~ /Wx./) {
43126b9709d9STom Rini						if (ERROR("SPACING",
43136b9709d9STom Rini							  "space prohibited before that '$op' $at\n" . $hereptr)) {
43146b9709d9STom Rini							$good = rtrim($fix_elements[$n]) . trim($fix_elements[$n + 1]);
43156b9709d9STom Rini							$line_fixed = 1;
43166b9709d9STom Rini						}
4317dd88ab32SMasahiro Yamada					}
4318dd88ab32SMasahiro Yamada
4319dd88ab32SMasahiro Yamada				# All the others need spaces both sides.
4320dd88ab32SMasahiro Yamada				} elsif ($ctx !~ /[EWC]x[CWE]/) {
4321dd88ab32SMasahiro Yamada					my $ok = 0;
4322dd88ab32SMasahiro Yamada
4323dd88ab32SMasahiro Yamada					# Ignore email addresses <foo@bar>
4324dd88ab32SMasahiro Yamada					if (($op eq '<' &&
4325dd88ab32SMasahiro Yamada					     $cc =~ /^\S+\@\S+>/) ||
4326dd88ab32SMasahiro Yamada					    ($op eq '>' &&
4327dd88ab32SMasahiro Yamada					     $ca =~ /<\S+\@\S+$/))
4328dd88ab32SMasahiro Yamada					{
4329dd88ab32SMasahiro Yamada					    	$ok = 1;
4330dd88ab32SMasahiro Yamada					}
4331dd88ab32SMasahiro Yamada
43327551eb4fSHeinrich Schuchardt					# for asm volatile statements
43337551eb4fSHeinrich Schuchardt					# ignore a colon with another
43347551eb4fSHeinrich Schuchardt					# colon immediately before or after
43357551eb4fSHeinrich Schuchardt					if (($op eq ':') &&
43367551eb4fSHeinrich Schuchardt					    ($ca =~ /:$/ || $cc =~ /^:/)) {
43377551eb4fSHeinrich Schuchardt						$ok = 1;
43387551eb4fSHeinrich Schuchardt					}
43397551eb4fSHeinrich Schuchardt
43406b9709d9STom Rini					# messages are ERROR, but ?: are CHK
4341dd88ab32SMasahiro Yamada					if ($ok == 0) {
43426b9709d9STom Rini						my $msg_type = \&ERROR;
43436b9709d9STom Rini						$msg_type = \&CHK if (($op eq '?:' || $op eq '?' || $op eq ':') && $ctx =~ /VxV/);
43446b9709d9STom Rini
43456b9709d9STom Rini						if (&{$msg_type}("SPACING",
43466b9709d9STom Rini								 "spaces required around that '$op' $at\n" . $hereptr)) {
43476b9709d9STom Rini							$good = rtrim($fix_elements[$n]) . " " . trim($fix_elements[$n + 1]) . " ";
43486b9709d9STom Rini							if (defined $fix_elements[$n + 2]) {
43496b9709d9STom Rini								$fix_elements[$n + 2] =~ s/^\s+//;
43506b9709d9STom Rini							}
43516b9709d9STom Rini							$line_fixed = 1;
43526b9709d9STom Rini						}
4353dd88ab32SMasahiro Yamada					}
4354dd88ab32SMasahiro Yamada				}
4355dd88ab32SMasahiro Yamada				$off += length($elements[$n + 1]);
43566b9709d9STom Rini
43576b9709d9STom Rini##				print("n: <$n> GOOD: <$good>\n");
43586b9709d9STom Rini
43596b9709d9STom Rini				$fixed_line = $fixed_line . $good;
43606b9709d9STom Rini			}
43616b9709d9STom Rini
43626b9709d9STom Rini			if (($#elements % 2) == 0) {
43636b9709d9STom Rini				$fixed_line = $fixed_line . $fix_elements[$#elements];
43646b9709d9STom Rini			}
43656b9709d9STom Rini
43667551eb4fSHeinrich Schuchardt			if ($fix && $line_fixed && $fixed_line ne $fixed[$fixlinenr]) {
43677551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] = $fixed_line;
43686b9709d9STom Rini			}
43696b9709d9STom Rini
43706b9709d9STom Rini
43716b9709d9STom Rini		}
43726b9709d9STom Rini
43736b9709d9STom Rini# check for whitespace before a non-naked semicolon
43746b9709d9STom Rini		if ($line =~ /^\+.*\S\s+;\s*$/) {
43756b9709d9STom Rini			if (WARN("SPACING",
43766b9709d9STom Rini				 "space prohibited before semicolon\n" . $herecurr) &&
43776b9709d9STom Rini			    $fix) {
43787551eb4fSHeinrich Schuchardt				1 while $fixed[$fixlinenr] =~
43796b9709d9STom Rini				    s/^(\+.*\S)\s+;/$1;/;
4380dd88ab32SMasahiro Yamada			}
4381dd88ab32SMasahiro Yamada		}
4382dd88ab32SMasahiro Yamada
4383dd88ab32SMasahiro Yamada# check for multiple assignments
4384dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*$Lval\s*=\s*$Lval\s*=(?!=)/) {
4385dd88ab32SMasahiro Yamada			CHK("MULTIPLE_ASSIGNMENTS",
4386dd88ab32SMasahiro Yamada			    "multiple assignments should be avoided\n" . $herecurr);
4387dd88ab32SMasahiro Yamada		}
4388dd88ab32SMasahiro Yamada
4389dd88ab32SMasahiro Yamada## # check for multiple declarations, allowing for a function declaration
4390dd88ab32SMasahiro Yamada## # continuation.
4391dd88ab32SMasahiro Yamada## 		if ($line =~ /^.\s*$Type\s+$Ident(?:\s*=[^,{]*)?\s*,\s*$Ident.*/ &&
4392dd88ab32SMasahiro Yamada## 		    $line !~ /^.\s*$Type\s+$Ident(?:\s*=[^,{]*)?\s*,\s*$Type\s*$Ident.*/) {
4393dd88ab32SMasahiro Yamada##
4394dd88ab32SMasahiro Yamada## 			# Remove any bracketed sections to ensure we do not
4395dd88ab32SMasahiro Yamada## 			# falsly report the parameters of functions.
4396dd88ab32SMasahiro Yamada## 			my $ln = $line;
4397dd88ab32SMasahiro Yamada## 			while ($ln =~ s/\([^\(\)]*\)//g) {
4398dd88ab32SMasahiro Yamada## 			}
4399dd88ab32SMasahiro Yamada## 			if ($ln =~ /,/) {
4400dd88ab32SMasahiro Yamada## 				WARN("MULTIPLE_DECLARATION",
4401dd88ab32SMasahiro Yamada##				     "declaring multiple variables together should be avoided\n" . $herecurr);
4402dd88ab32SMasahiro Yamada## 			}
4403dd88ab32SMasahiro Yamada## 		}
4404dd88ab32SMasahiro Yamada
4405dd88ab32SMasahiro Yamada#need space before brace following if, while, etc
44067551eb4fSHeinrich Schuchardt		if (($line =~ /\(.*\)\{/ && $line !~ /\($Type\)\{/) ||
4407d8a1a304SHeiko Schocher		    $line =~ /do\{/) {
44086b9709d9STom Rini			if (ERROR("SPACING",
44096b9709d9STom Rini				  "space required before the open brace '{'\n" . $herecurr) &&
44106b9709d9STom Rini			    $fix) {
44117551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/^(\+.*(?:do|\)))\{/$1 {/;
4412dd88ab32SMasahiro Yamada			}
44136b9709d9STom Rini		}
44146b9709d9STom Rini
44156b9709d9STom Rini## # check for blank lines before declarations
44166b9709d9STom Rini##		if ($line =~ /^.\t+$Type\s+$Ident(?:\s*=.*)?;/ &&
44176b9709d9STom Rini##		    $prevrawline =~ /^.\s*$/) {
44186b9709d9STom Rini##			WARN("SPACING",
44196b9709d9STom Rini##			     "No blank lines before declarations\n" . $hereprev);
44206b9709d9STom Rini##		}
44216b9709d9STom Rini##
4422dd88ab32SMasahiro Yamada
4423dd88ab32SMasahiro Yamada# closing brace should have a space following it when it has anything
4424dd88ab32SMasahiro Yamada# on the line
4425dd88ab32SMasahiro Yamada		if ($line =~ /}(?!(?:,|;|\)))\S/) {
44266b9709d9STom Rini			if (ERROR("SPACING",
44276b9709d9STom Rini				  "space required after that close brace '}'\n" . $herecurr) &&
44286b9709d9STom Rini			    $fix) {
44297551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
44306b9709d9STom Rini				    s/}((?!(?:,|;|\)))\S)/} $1/;
44316b9709d9STom Rini			}
4432dd88ab32SMasahiro Yamada		}
4433dd88ab32SMasahiro Yamada
4434dd88ab32SMasahiro Yamada# check spacing on square brackets
4435dd88ab32SMasahiro Yamada		if ($line =~ /\[\s/ && $line !~ /\[\s*$/) {
44366b9709d9STom Rini			if (ERROR("SPACING",
44376b9709d9STom Rini				  "space prohibited after that open square bracket '['\n" . $herecurr) &&
44386b9709d9STom Rini			    $fix) {
44397551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
44406b9709d9STom Rini				    s/\[\s+/\[/;
44416b9709d9STom Rini			}
4442dd88ab32SMasahiro Yamada		}
4443dd88ab32SMasahiro Yamada		if ($line =~ /\s\]/) {
44446b9709d9STom Rini			if (ERROR("SPACING",
44456b9709d9STom Rini				  "space prohibited before that close square bracket ']'\n" . $herecurr) &&
44466b9709d9STom Rini			    $fix) {
44477551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
44486b9709d9STom Rini				    s/\s+\]/\]/;
44496b9709d9STom Rini			}
4450dd88ab32SMasahiro Yamada		}
4451dd88ab32SMasahiro Yamada
4452dd88ab32SMasahiro Yamada# check spacing on parentheses
4453dd88ab32SMasahiro Yamada		if ($line =~ /\(\s/ && $line !~ /\(\s*(?:\\)?$/ &&
4454dd88ab32SMasahiro Yamada		    $line !~ /for\s*\(\s+;/) {
44556b9709d9STom Rini			if (ERROR("SPACING",
44566b9709d9STom Rini				  "space prohibited after that open parenthesis '('\n" . $herecurr) &&
44576b9709d9STom Rini			    $fix) {
44587551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
44596b9709d9STom Rini				    s/\(\s+/\(/;
44606b9709d9STom Rini			}
4461dd88ab32SMasahiro Yamada		}
4462dd88ab32SMasahiro Yamada		if ($line =~ /(\s+)\)/ && $line !~ /^.\s*\)/ &&
4463dd88ab32SMasahiro Yamada		    $line !~ /for\s*\(.*;\s+\)/ &&
4464dd88ab32SMasahiro Yamada		    $line !~ /:\s+\)/) {
44656b9709d9STom Rini			if (ERROR("SPACING",
44666b9709d9STom Rini				  "space prohibited before that close parenthesis ')'\n" . $herecurr) &&
44676b9709d9STom Rini			    $fix) {
44687551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
44696b9709d9STom Rini				    s/\s+\)/\)/;
44706b9709d9STom Rini			}
4471dd88ab32SMasahiro Yamada		}
4472dd88ab32SMasahiro Yamada
44737551eb4fSHeinrich Schuchardt# check unnecessary parentheses around addressof/dereference single $Lvals
44747551eb4fSHeinrich Schuchardt# ie: &(foo->bar) should be &foo->bar and *(foo->bar) should be *foo->bar
44757551eb4fSHeinrich Schuchardt
44767551eb4fSHeinrich Schuchardt		while ($line =~ /(?:[^&]&\s*|\*)\(\s*($Ident\s*(?:$Member\s*)+)\s*\)/g) {
44777551eb4fSHeinrich Schuchardt			my $var = $1;
44787551eb4fSHeinrich Schuchardt			if (CHK("UNNECESSARY_PARENTHESES",
44797551eb4fSHeinrich Schuchardt				"Unnecessary parentheses around $var\n" . $herecurr) &&
44807551eb4fSHeinrich Schuchardt			    $fix) {
44817551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\(\s*\Q$var\E\s*\)/$var/;
44827551eb4fSHeinrich Schuchardt			}
44837551eb4fSHeinrich Schuchardt		}
44847551eb4fSHeinrich Schuchardt
44857551eb4fSHeinrich Schuchardt# check for unnecessary parentheses around function pointer uses
44867551eb4fSHeinrich Schuchardt# ie: (foo->bar)(); should be foo->bar();
44877551eb4fSHeinrich Schuchardt# but not "if (foo->bar) (" to avoid some false positives
44887551eb4fSHeinrich Schuchardt		if ($line =~ /(\bif\s*|)(\(\s*$Ident\s*(?:$Member\s*)+\))[ \t]*\(/ && $1 !~ /^if/) {
44897551eb4fSHeinrich Schuchardt			my $var = $2;
44907551eb4fSHeinrich Schuchardt			if (CHK("UNNECESSARY_PARENTHESES",
44917551eb4fSHeinrich Schuchardt				"Unnecessary parentheses around function pointer $var\n" . $herecurr) &&
44927551eb4fSHeinrich Schuchardt			    $fix) {
44937551eb4fSHeinrich Schuchardt				my $var2 = deparenthesize($var);
44947551eb4fSHeinrich Schuchardt				$var2 =~ s/\s//g;
44957551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\Q$var\E/$var2/;
44967551eb4fSHeinrich Schuchardt			}
44977551eb4fSHeinrich Schuchardt		}
44987551eb4fSHeinrich Schuchardt
4499dd88ab32SMasahiro Yamada#goto labels aren't indented, allow a single space however
4500dd88ab32SMasahiro Yamada		if ($line=~/^.\s+[A-Za-z\d_]+:(?![0-9]+)/ and
4501dd88ab32SMasahiro Yamada		   !($line=~/^. [A-Za-z\d_]+:/) and !($line=~/^.\s+default:/)) {
45026b9709d9STom Rini			if (WARN("INDENTED_LABEL",
45036b9709d9STom Rini				 "labels should not be indented\n" . $herecurr) &&
45046b9709d9STom Rini			    $fix) {
45057551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
45066b9709d9STom Rini				    s/^(.)\s+/$1/;
45076b9709d9STom Rini			}
4508dd88ab32SMasahiro Yamada		}
4509dd88ab32SMasahiro Yamada
45107551eb4fSHeinrich Schuchardt# return is not a function
45116b9709d9STom Rini		if (defined($stat) && $stat =~ /^.\s*return(\s*)\(/s) {
4512dd88ab32SMasahiro Yamada			my $spacing = $1;
45136b9709d9STom Rini			if ($^V && $^V ge 5.10.0 &&
45147551eb4fSHeinrich Schuchardt			    $stat =~ /^.\s*return\s*($balanced_parens)\s*;\s*$/) {
45157551eb4fSHeinrich Schuchardt				my $value = $1;
45167551eb4fSHeinrich Schuchardt				$value = deparenthesize($value);
45177551eb4fSHeinrich Schuchardt				if ($value =~ m/^\s*$FuncArg\s*(?:\?|$)/) {
4518dd88ab32SMasahiro Yamada					ERROR("RETURN_PARENTHESES",
4519dd88ab32SMasahiro Yamada					      "return is not a function, parentheses are not required\n" . $herecurr);
45207551eb4fSHeinrich Schuchardt				}
4521dd88ab32SMasahiro Yamada			} elsif ($spacing !~ /\s+/) {
4522dd88ab32SMasahiro Yamada				ERROR("SPACING",
4523dd88ab32SMasahiro Yamada				      "space required before the open parenthesis '('\n" . $herecurr);
4524dd88ab32SMasahiro Yamada			}
4525dd88ab32SMasahiro Yamada		}
45266b9709d9STom Rini
45277551eb4fSHeinrich Schuchardt# unnecessary return in a void function
45287551eb4fSHeinrich Schuchardt# at end-of-function, with the previous line a single leading tab, then return;
45297551eb4fSHeinrich Schuchardt# and the line before that not a goto label target like "out:"
45307551eb4fSHeinrich Schuchardt		if ($sline =~ /^[ \+]}\s*$/ &&
45317551eb4fSHeinrich Schuchardt		    $prevline =~ /^\+\treturn\s*;\s*$/ &&
45327551eb4fSHeinrich Schuchardt		    $linenr >= 3 &&
45337551eb4fSHeinrich Schuchardt		    $lines[$linenr - 3] =~ /^[ +]/ &&
45347551eb4fSHeinrich Schuchardt		    $lines[$linenr - 3] !~ /^[ +]\s*$Ident\s*:/) {
45357551eb4fSHeinrich Schuchardt			WARN("RETURN_VOID",
45367551eb4fSHeinrich Schuchardt			     "void function return statements are not generally useful\n" . $hereprev);
45377551eb4fSHeinrich Schuchardt               }
45387551eb4fSHeinrich Schuchardt
45396b9709d9STom Rini# if statements using unnecessary parentheses - ie: if ((foo == bar))
45406b9709d9STom Rini		if ($^V && $^V ge 5.10.0 &&
45416b9709d9STom Rini		    $line =~ /\bif\s*((?:\(\s*){2,})/) {
45426b9709d9STom Rini			my $openparens = $1;
45436b9709d9STom Rini			my $count = $openparens =~ tr@\(@\(@;
45446b9709d9STom Rini			my $msg = "";
45456b9709d9STom Rini			if ($line =~ /\bif\s*(?:\(\s*){$count,$count}$LvalOrFunc\s*($Compare)\s*$LvalOrFunc(?:\s*\)){$count,$count}/) {
45466b9709d9STom Rini				my $comp = $4;	#Not $1 because of $LvalOrFunc
45476b9709d9STom Rini				$msg = " - maybe == should be = ?" if ($comp eq "==");
45486b9709d9STom Rini				WARN("UNNECESSARY_PARENTHESES",
45496b9709d9STom Rini				     "Unnecessary parentheses$msg\n" . $herecurr);
45506b9709d9STom Rini			}
45516b9709d9STom Rini		}
45526b9709d9STom Rini
45537551eb4fSHeinrich Schuchardt# comparisons with a constant or upper case identifier on the left
45547551eb4fSHeinrich Schuchardt#	avoid cases like "foo + BAR < baz"
45557551eb4fSHeinrich Schuchardt#	only fix matches surrounded by parentheses to avoid incorrect
45567551eb4fSHeinrich Schuchardt#	conversions like "FOO < baz() + 5" being "misfixed" to "baz() > FOO + 5"
45577551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
45587551eb4fSHeinrich Schuchardt		    $line =~ /^\+(.*)\b($Constant|[A-Z_][A-Z0-9_]*)\s*($Compare)\s*($LvalOrFunc)/) {
45597551eb4fSHeinrich Schuchardt			my $lead = $1;
45607551eb4fSHeinrich Schuchardt			my $const = $2;
45617551eb4fSHeinrich Schuchardt			my $comp = $3;
45627551eb4fSHeinrich Schuchardt			my $to = $4;
45637551eb4fSHeinrich Schuchardt			my $newcomp = $comp;
45647551eb4fSHeinrich Schuchardt			if ($lead !~ /(?:$Operators|\.)\s*$/ &&
45657551eb4fSHeinrich Schuchardt			    $to !~ /^(?:Constant|[A-Z_][A-Z0-9_]*)$/ &&
45667551eb4fSHeinrich Schuchardt			    WARN("CONSTANT_COMPARISON",
45677551eb4fSHeinrich Schuchardt				 "Comparisons should place the constant on the right side of the test\n" . $herecurr) &&
45687551eb4fSHeinrich Schuchardt			    $fix) {
45697551eb4fSHeinrich Schuchardt				if ($comp eq "<") {
45707551eb4fSHeinrich Schuchardt					$newcomp = ">";
45717551eb4fSHeinrich Schuchardt				} elsif ($comp eq "<=") {
45727551eb4fSHeinrich Schuchardt					$newcomp = ">=";
45737551eb4fSHeinrich Schuchardt				} elsif ($comp eq ">") {
45747551eb4fSHeinrich Schuchardt					$newcomp = "<";
45757551eb4fSHeinrich Schuchardt				} elsif ($comp eq ">=") {
45767551eb4fSHeinrich Schuchardt					$newcomp = "<=";
45777551eb4fSHeinrich Schuchardt				}
45787551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\(\s*\Q$const\E\s*$Compare\s*\Q$to\E\s*\)/($to $newcomp $const)/;
45797551eb4fSHeinrich Schuchardt			}
45807551eb4fSHeinrich Schuchardt		}
45817551eb4fSHeinrich Schuchardt
45827551eb4fSHeinrich Schuchardt# Return of what appears to be an errno should normally be negative
45837551eb4fSHeinrich Schuchardt		if ($sline =~ /\breturn(?:\s*\(+\s*|\s+)(E[A-Z]+)(?:\s*\)+\s*|\s*)[;:,]/) {
4584dd88ab32SMasahiro Yamada			my $name = $1;
4585dd88ab32SMasahiro Yamada			if ($name ne 'EOF' && $name ne 'ERROR') {
4586dd88ab32SMasahiro Yamada				WARN("USE_NEGATIVE_ERRNO",
45877551eb4fSHeinrich Schuchardt				     "return of an errno should typically be negative (ie: return -$1)\n" . $herecurr);
4588dd88ab32SMasahiro Yamada			}
4589dd88ab32SMasahiro Yamada		}
4590dd88ab32SMasahiro Yamada
4591dd88ab32SMasahiro Yamada# Need a space before open parenthesis after if, while etc
4592dd88ab32SMasahiro Yamada		if ($line =~ /\b(if|while|for|switch)\(/) {
45936b9709d9STom Rini			if (ERROR("SPACING",
45946b9709d9STom Rini				  "space required before the open parenthesis '('\n" . $herecurr) &&
45956b9709d9STom Rini			    $fix) {
45967551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
45976b9709d9STom Rini				    s/\b(if|while|for|switch)\(/$1 \(/;
45986b9709d9STom Rini			}
4599dd88ab32SMasahiro Yamada		}
4600dd88ab32SMasahiro Yamada
4601dd88ab32SMasahiro Yamada# Check for illegal assignment in if conditional -- and check for trailing
4602dd88ab32SMasahiro Yamada# statements after the conditional.
4603dd88ab32SMasahiro Yamada		if ($line =~ /do\s*(?!{)/) {
4604dd88ab32SMasahiro Yamada			($stat, $cond, $line_nr_next, $remain_next, $off_next) =
4605dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $realcnt, 0)
4606dd88ab32SMasahiro Yamada					if (!defined $stat);
4607dd88ab32SMasahiro Yamada			my ($stat_next) = ctx_statement_block($line_nr_next,
4608dd88ab32SMasahiro Yamada						$remain_next, $off_next);
4609dd88ab32SMasahiro Yamada			$stat_next =~ s/\n./\n /g;
4610dd88ab32SMasahiro Yamada			##print "stat<$stat> stat_next<$stat_next>\n";
4611dd88ab32SMasahiro Yamada
4612dd88ab32SMasahiro Yamada			if ($stat_next =~ /^\s*while\b/) {
4613dd88ab32SMasahiro Yamada				# If the statement carries leading newlines,
4614dd88ab32SMasahiro Yamada				# then count those as offsets.
4615dd88ab32SMasahiro Yamada				my ($whitespace) =
4616dd88ab32SMasahiro Yamada					($stat_next =~ /^((?:\s*\n[+-])*\s*)/s);
4617dd88ab32SMasahiro Yamada				my $offset =
4618dd88ab32SMasahiro Yamada					statement_rawlines($whitespace) - 1;
4619dd88ab32SMasahiro Yamada
4620dd88ab32SMasahiro Yamada				$suppress_whiletrailers{$line_nr_next +
4621dd88ab32SMasahiro Yamada								$offset} = 1;
4622dd88ab32SMasahiro Yamada			}
4623dd88ab32SMasahiro Yamada		}
4624dd88ab32SMasahiro Yamada		if (!defined $suppress_whiletrailers{$linenr} &&
46256b9709d9STom Rini		    defined($stat) && defined($cond) &&
4626dd88ab32SMasahiro Yamada		    $line =~ /\b(?:if|while|for)\s*\(/ && $line !~ /^.\s*#/) {
4627dd88ab32SMasahiro Yamada			my ($s, $c) = ($stat, $cond);
4628dd88ab32SMasahiro Yamada
4629dd88ab32SMasahiro Yamada			if ($c =~ /\bif\s*\(.*[^<>!=]=[^=].*/s) {
4630dd88ab32SMasahiro Yamada				ERROR("ASSIGN_IN_IF",
4631dd88ab32SMasahiro Yamada				      "do not use assignment in if condition\n" . $herecurr);
4632dd88ab32SMasahiro Yamada			}
4633dd88ab32SMasahiro Yamada
4634dd88ab32SMasahiro Yamada			# Find out what is on the end of the line after the
4635dd88ab32SMasahiro Yamada			# conditional.
4636dd88ab32SMasahiro Yamada			substr($s, 0, length($c), '');
4637dd88ab32SMasahiro Yamada			$s =~ s/\n.*//g;
4638dd88ab32SMasahiro Yamada			$s =~ s/$;//g; 	# Remove any comments
4639dd88ab32SMasahiro Yamada			if (length($c) && $s !~ /^\s*{?\s*\\*\s*$/ &&
4640dd88ab32SMasahiro Yamada			    $c !~ /}\s*while\s*/)
4641dd88ab32SMasahiro Yamada			{
4642dd88ab32SMasahiro Yamada				# Find out how long the conditional actually is.
4643dd88ab32SMasahiro Yamada				my @newlines = ($c =~ /\n/gs);
4644dd88ab32SMasahiro Yamada				my $cond_lines = 1 + $#newlines;
4645dd88ab32SMasahiro Yamada				my $stat_real = '';
4646dd88ab32SMasahiro Yamada
4647dd88ab32SMasahiro Yamada				$stat_real = raw_line($linenr, $cond_lines)
4648dd88ab32SMasahiro Yamada							. "\n" if ($cond_lines);
4649dd88ab32SMasahiro Yamada				if (defined($stat_real) && $cond_lines > 1) {
4650dd88ab32SMasahiro Yamada					$stat_real = "[...]\n$stat_real";
4651dd88ab32SMasahiro Yamada				}
4652dd88ab32SMasahiro Yamada
4653dd88ab32SMasahiro Yamada				ERROR("TRAILING_STATEMENTS",
4654dd88ab32SMasahiro Yamada				      "trailing statements should be on next line\n" . $herecurr . $stat_real);
4655dd88ab32SMasahiro Yamada			}
4656dd88ab32SMasahiro Yamada		}
4657dd88ab32SMasahiro Yamada
4658dd88ab32SMasahiro Yamada# Check for bitwise tests written as boolean
4659dd88ab32SMasahiro Yamada		if ($line =~ /
4660dd88ab32SMasahiro Yamada			(?:
4661dd88ab32SMasahiro Yamada				(?:\[|\(|\&\&|\|\|)
4662dd88ab32SMasahiro Yamada				\s*0[xX][0-9]+\s*
4663dd88ab32SMasahiro Yamada				(?:\&\&|\|\|)
4664dd88ab32SMasahiro Yamada			|
4665dd88ab32SMasahiro Yamada				(?:\&\&|\|\|)
4666dd88ab32SMasahiro Yamada				\s*0[xX][0-9]+\s*
4667dd88ab32SMasahiro Yamada				(?:\&\&|\|\||\)|\])
4668dd88ab32SMasahiro Yamada			)/x)
4669dd88ab32SMasahiro Yamada		{
4670dd88ab32SMasahiro Yamada			WARN("HEXADECIMAL_BOOLEAN_TEST",
4671dd88ab32SMasahiro Yamada			     "boolean test with hexadecimal, perhaps just 1 \& or \|?\n" . $herecurr);
4672dd88ab32SMasahiro Yamada		}
4673dd88ab32SMasahiro Yamada
4674dd88ab32SMasahiro Yamada# if and else should not have general statements after it
4675dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*(?:}\s*)?else\b(.*)/) {
4676dd88ab32SMasahiro Yamada			my $s = $1;
4677dd88ab32SMasahiro Yamada			$s =~ s/$;//g; 	# Remove any comments
4678dd88ab32SMasahiro Yamada			if ($s !~ /^\s*(?:\sif|(?:{|)\s*\\?\s*$)/) {
4679dd88ab32SMasahiro Yamada				ERROR("TRAILING_STATEMENTS",
4680dd88ab32SMasahiro Yamada				      "trailing statements should be on next line\n" . $herecurr);
4681dd88ab32SMasahiro Yamada			}
4682dd88ab32SMasahiro Yamada		}
4683dd88ab32SMasahiro Yamada# if should not continue a brace
4684dd88ab32SMasahiro Yamada		if ($line =~ /}\s*if\b/) {
4685dd88ab32SMasahiro Yamada			ERROR("TRAILING_STATEMENTS",
46867551eb4fSHeinrich Schuchardt			      "trailing statements should be on next line (or did you mean 'else if'?)\n" .
4687dd88ab32SMasahiro Yamada				$herecurr);
4688dd88ab32SMasahiro Yamada		}
4689dd88ab32SMasahiro Yamada# case and default should not have general statements after them
4690dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*(?:case\s*.*|default\s*):/g &&
4691dd88ab32SMasahiro Yamada		    $line !~ /\G(?:
4692dd88ab32SMasahiro Yamada			(?:\s*$;*)(?:\s*{)?(?:\s*$;*)(?:\s*\\)?\s*$|
4693dd88ab32SMasahiro Yamada			\s*return\s+
4694dd88ab32SMasahiro Yamada		    )/xg)
4695dd88ab32SMasahiro Yamada		{
4696dd88ab32SMasahiro Yamada			ERROR("TRAILING_STATEMENTS",
4697dd88ab32SMasahiro Yamada			      "trailing statements should be on next line\n" . $herecurr);
4698dd88ab32SMasahiro Yamada		}
4699dd88ab32SMasahiro Yamada
4700dd88ab32SMasahiro Yamada		# Check for }<nl>else {, these must be at the same
4701dd88ab32SMasahiro Yamada		# indent level to be relevant to each other.
47027551eb4fSHeinrich Schuchardt		if ($prevline=~/}\s*$/ and $line=~/^.\s*else\s*/ &&
4703dd88ab32SMasahiro Yamada		    $previndent == $indent) {
47047551eb4fSHeinrich Schuchardt			if (ERROR("ELSE_AFTER_BRACE",
47057551eb4fSHeinrich Schuchardt				  "else should follow close brace '}'\n" . $hereprev) &&
47067551eb4fSHeinrich Schuchardt			    $fix && $prevline =~ /^\+/ && $line =~ /^\+/) {
47077551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr - 1, $prevrawline);
47087551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
47097551eb4fSHeinrich Schuchardt				my $fixedline = $prevrawline;
47107551eb4fSHeinrich Schuchardt				$fixedline =~ s/}\s*$//;
47117551eb4fSHeinrich Schuchardt				if ($fixedline !~ /^\+\s*$/) {
47127551eb4fSHeinrich Schuchardt					fix_insert_line($fixlinenr, $fixedline);
47137551eb4fSHeinrich Schuchardt				}
47147551eb4fSHeinrich Schuchardt				$fixedline = $rawline;
47157551eb4fSHeinrich Schuchardt				$fixedline =~ s/^(.\s*)else/$1} else/;
47167551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr, $fixedline);
47177551eb4fSHeinrich Schuchardt			}
4718dd88ab32SMasahiro Yamada		}
4719dd88ab32SMasahiro Yamada
47207551eb4fSHeinrich Schuchardt		if ($prevline=~/}\s*$/ and $line=~/^.\s*while\s*/ &&
4721dd88ab32SMasahiro Yamada		    $previndent == $indent) {
4722dd88ab32SMasahiro Yamada			my ($s, $c) = ctx_statement_block($linenr, $realcnt, 0);
4723dd88ab32SMasahiro Yamada
4724dd88ab32SMasahiro Yamada			# Find out what is on the end of the line after the
4725dd88ab32SMasahiro Yamada			# conditional.
4726dd88ab32SMasahiro Yamada			substr($s, 0, length($c), '');
4727dd88ab32SMasahiro Yamada			$s =~ s/\n.*//g;
4728dd88ab32SMasahiro Yamada
4729dd88ab32SMasahiro Yamada			if ($s =~ /^\s*;/) {
47307551eb4fSHeinrich Schuchardt				if (ERROR("WHILE_AFTER_BRACE",
47317551eb4fSHeinrich Schuchardt					  "while should follow close brace '}'\n" . $hereprev) &&
47327551eb4fSHeinrich Schuchardt				    $fix && $prevline =~ /^\+/ && $line =~ /^\+/) {
47337551eb4fSHeinrich Schuchardt					fix_delete_line($fixlinenr - 1, $prevrawline);
47347551eb4fSHeinrich Schuchardt					fix_delete_line($fixlinenr, $rawline);
47357551eb4fSHeinrich Schuchardt					my $fixedline = $prevrawline;
47367551eb4fSHeinrich Schuchardt					my $trailing = $rawline;
47377551eb4fSHeinrich Schuchardt					$trailing =~ s/^\+//;
47387551eb4fSHeinrich Schuchardt					$trailing = trim($trailing);
47397551eb4fSHeinrich Schuchardt					$fixedline =~ s/}\s*$/} $trailing/;
47407551eb4fSHeinrich Schuchardt					fix_insert_line($fixlinenr, $fixedline);
47417551eb4fSHeinrich Schuchardt				}
4742dd88ab32SMasahiro Yamada			}
4743dd88ab32SMasahiro Yamada		}
4744dd88ab32SMasahiro Yamada
47456b9709d9STom Rini#Specific variable tests
4746dd88ab32SMasahiro Yamada		while ($line =~ m{($Constant|$Lval)}g) {
4747dd88ab32SMasahiro Yamada			my $var = $1;
47486b9709d9STom Rini
47496b9709d9STom Rini#gcc binary extension
47506b9709d9STom Rini			if ($var =~ /^$Binary$/) {
47516b9709d9STom Rini				if (WARN("GCC_BINARY_CONSTANT",
47526b9709d9STom Rini					 "Avoid gcc v4.3+ binary constant extension: <$var>\n" . $herecurr) &&
47536b9709d9STom Rini				    $fix) {
47546b9709d9STom Rini					my $hexval = sprintf("0x%x", oct($var));
47557551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~
47566b9709d9STom Rini					    s/\b$var\b/$hexval/;
47576b9709d9STom Rini				}
47586b9709d9STom Rini			}
47596b9709d9STom Rini
47606b9709d9STom Rini#CamelCase
47616b9709d9STom Rini			if ($var !~ /^$Constant$/ &&
47626b9709d9STom Rini			    $var =~ /[A-Z][a-z]|[a-z][A-Z]/ &&
47636b9709d9STom Rini#Ignore Page<foo> variants
47646b9709d9STom Rini			    $var !~ /^(?:Clear|Set|TestClear|TestSet|)Page[A-Z]/ &&
47656b9709d9STom Rini#Ignore SI style variants like nS, mV and dB (ie: max_uV, regulator_min_uA_show)
47667551eb4fSHeinrich Schuchardt			    $var !~ /^(?:[a-z_]*?)_?[a-z][A-Z](?:_[a-z_]+)?$/ &&
47677551eb4fSHeinrich Schuchardt#Ignore some three character SI units explicitly, like MiB and KHz
47687551eb4fSHeinrich Schuchardt			    $var !~ /^(?:[a-z_]*?)_?(?:[KMGT]iB|[KMGT]?Hz)(?:_[a-z_]+)?$/) {
47696b9709d9STom Rini				while ($var =~ m{($Ident)}g) {
47706b9709d9STom Rini					my $word = $1;
47716b9709d9STom Rini					next if ($word !~ /[A-Z][a-z]|[a-z][A-Z]/);
47726b9709d9STom Rini					if ($check) {
47736b9709d9STom Rini						seed_camelcase_includes();
47746b9709d9STom Rini						if (!$file && !$camelcase_file_seeded) {
47756b9709d9STom Rini							seed_camelcase_file($realfile);
47766b9709d9STom Rini							$camelcase_file_seeded = 1;
47776b9709d9STom Rini						}
47786b9709d9STom Rini					}
47796b9709d9STom Rini					if (!defined $camelcase{$word}) {
47806b9709d9STom Rini						$camelcase{$word} = 1;
47816b9709d9STom Rini						CHK("CAMELCASE",
47826b9709d9STom Rini						    "Avoid CamelCase: <$word>\n" . $herecurr);
47836b9709d9STom Rini					}
47846b9709d9STom Rini				}
4785dd88ab32SMasahiro Yamada			}
4786dd88ab32SMasahiro Yamada		}
4787dd88ab32SMasahiro Yamada
4788dd88ab32SMasahiro Yamada#no spaces allowed after \ in define
47896b9709d9STom Rini		if ($line =~ /\#\s*define.*\\\s+$/) {
47906b9709d9STom Rini			if (WARN("WHITESPACE_AFTER_LINE_CONTINUATION",
47916b9709d9STom Rini				 "Whitespace after \\ makes next lines useless\n" . $herecurr) &&
47926b9709d9STom Rini			    $fix) {
47937551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\s+$//;
47946b9709d9STom Rini			}
4795dd88ab32SMasahiro Yamada		}
4796dd88ab32SMasahiro Yamada
47977551eb4fSHeinrich Schuchardt# warn if <asm/foo.h> is #included and <linux/foo.h> is available and includes
47987551eb4fSHeinrich Schuchardt# itself <asm/foo.h> (uses RAW line)
4799dd88ab32SMasahiro Yamada		if ($tree && $rawline =~ m{^.\s*\#\s*include\s*\<asm\/(.*)\.h\>}) {
4800dd88ab32SMasahiro Yamada			my $file = "$1.h";
4801dd88ab32SMasahiro Yamada			my $checkfile = "include/linux/$file";
4802dd88ab32SMasahiro Yamada			if (-f "$root/$checkfile" &&
4803dd88ab32SMasahiro Yamada			    $realfile ne $checkfile &&
4804dd88ab32SMasahiro Yamada			    $1 !~ /$allowed_asm_includes/)
4805dd88ab32SMasahiro Yamada			{
48067551eb4fSHeinrich Schuchardt				my $asminclude = `grep -Ec "#include\\s+<asm/$file>" $root/$checkfile`;
48077551eb4fSHeinrich Schuchardt				if ($asminclude > 0) {
4808dd88ab32SMasahiro Yamada					if ($realfile =~ m{^arch/}) {
4809dd88ab32SMasahiro Yamada						CHK("ARCH_INCLUDE_LINUX",
4810dd88ab32SMasahiro Yamada						    "Consider using #include <linux/$file> instead of <asm/$file>\n" . $herecurr);
4811dd88ab32SMasahiro Yamada					} else {
4812dd88ab32SMasahiro Yamada						WARN("INCLUDE_LINUX",
4813dd88ab32SMasahiro Yamada						     "Use #include <linux/$file> instead of <asm/$file>\n" . $herecurr);
4814dd88ab32SMasahiro Yamada					}
4815dd88ab32SMasahiro Yamada				}
4816dd88ab32SMasahiro Yamada			}
48177551eb4fSHeinrich Schuchardt		}
4818dd88ab32SMasahiro Yamada
4819dd88ab32SMasahiro Yamada# multi-statement macros should be enclosed in a do while loop, grab the
4820dd88ab32SMasahiro Yamada# first statement and ensure its the whole macro if its not enclosed
4821dd88ab32SMasahiro Yamada# in a known good container
4822dd88ab32SMasahiro Yamada		if ($realfile !~ m@/vmlinux.lds.h$@ &&
4823dd88ab32SMasahiro Yamada		    $line =~ /^.\s*\#\s*define\s*$Ident(\()?/) {
4824dd88ab32SMasahiro Yamada			my $ln = $linenr;
4825dd88ab32SMasahiro Yamada			my $cnt = $realcnt;
4826dd88ab32SMasahiro Yamada			my ($off, $dstat, $dcond, $rest);
4827dd88ab32SMasahiro Yamada			my $ctx = '';
48287551eb4fSHeinrich Schuchardt			my $has_flow_statement = 0;
48297551eb4fSHeinrich Schuchardt			my $has_arg_concat = 0;
4830dd88ab32SMasahiro Yamada			($dstat, $dcond, $ln, $cnt, $off) =
4831dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $realcnt, 0);
4832dd88ab32SMasahiro Yamada			$ctx = $dstat;
4833dd88ab32SMasahiro Yamada			#print "dstat<$dstat> dcond<$dcond> cnt<$cnt> off<$off>\n";
4834dd88ab32SMasahiro Yamada			#print "LINE<$lines[$ln-1]> len<" . length($lines[$ln-1]) . "\n";
4835dd88ab32SMasahiro Yamada
48367551eb4fSHeinrich Schuchardt			$has_flow_statement = 1 if ($ctx =~ /\b(goto|return)\b/);
48377551eb4fSHeinrich Schuchardt			$has_arg_concat = 1 if ($ctx =~ /\#\#/ && $ctx !~ /\#\#\s*(?:__VA_ARGS__|args)\b/);
48387551eb4fSHeinrich Schuchardt
48397551eb4fSHeinrich Schuchardt			$dstat =~ s/^.\s*\#\s*define\s+$Ident(\([^\)]*\))?\s*//;
48407551eb4fSHeinrich Schuchardt			my $define_args = $1;
48417551eb4fSHeinrich Schuchardt			my $define_stmt = $dstat;
48427551eb4fSHeinrich Schuchardt			my @def_args = ();
48437551eb4fSHeinrich Schuchardt
48447551eb4fSHeinrich Schuchardt			if (defined $define_args && $define_args ne "") {
48457551eb4fSHeinrich Schuchardt				$define_args = substr($define_args, 1, length($define_args) - 2);
48467551eb4fSHeinrich Schuchardt				$define_args =~ s/\s*//g;
48477551eb4fSHeinrich Schuchardt				@def_args = split(",", $define_args);
48487551eb4fSHeinrich Schuchardt			}
48497551eb4fSHeinrich Schuchardt
4850dd88ab32SMasahiro Yamada			$dstat =~ s/$;//g;
4851dd88ab32SMasahiro Yamada			$dstat =~ s/\\\n.//g;
4852dd88ab32SMasahiro Yamada			$dstat =~ s/^\s*//s;
4853dd88ab32SMasahiro Yamada			$dstat =~ s/\s*$//s;
4854dd88ab32SMasahiro Yamada
4855dd88ab32SMasahiro Yamada			# Flatten any parentheses and braces
4856dd88ab32SMasahiro Yamada			while ($dstat =~ s/\([^\(\)]*\)/1/ ||
4857dd88ab32SMasahiro Yamada			       $dstat =~ s/\{[^\{\}]*\}/1/ ||
48587551eb4fSHeinrich Schuchardt			       $dstat =~ s/.\[[^\[\]]*\]/1/)
4859dd88ab32SMasahiro Yamada			{
4860dd88ab32SMasahiro Yamada			}
4861dd88ab32SMasahiro Yamada
4862dd88ab32SMasahiro Yamada			# Flatten any obvious string concatentation.
48637551eb4fSHeinrich Schuchardt			while ($dstat =~ s/($String)\s*$Ident/$1/ ||
48647551eb4fSHeinrich Schuchardt			       $dstat =~ s/$Ident\s*($String)/$1/)
4865dd88ab32SMasahiro Yamada			{
4866dd88ab32SMasahiro Yamada			}
4867dd88ab32SMasahiro Yamada
48687551eb4fSHeinrich Schuchardt			# Make asm volatile uses seem like a generic function
48697551eb4fSHeinrich Schuchardt			$dstat =~ s/\b_*asm_*\s+_*volatile_*\b/asm_volatile/g;
48707551eb4fSHeinrich Schuchardt
4871dd88ab32SMasahiro Yamada			my $exceptions = qr{
4872dd88ab32SMasahiro Yamada				$Declare|
4873dd88ab32SMasahiro Yamada				module_param_named|
4874dd88ab32SMasahiro Yamada				MODULE_PARM_DESC|
4875dd88ab32SMasahiro Yamada				DECLARE_PER_CPU|
4876dd88ab32SMasahiro Yamada				DEFINE_PER_CPU|
4877dd88ab32SMasahiro Yamada				__typeof__\(|
4878dd88ab32SMasahiro Yamada				union|
4879dd88ab32SMasahiro Yamada				struct|
4880dd88ab32SMasahiro Yamada				\.$Ident\s*=\s*|
48817551eb4fSHeinrich Schuchardt				^\"|\"$|
48827551eb4fSHeinrich Schuchardt				^\[
4883dd88ab32SMasahiro Yamada			}x;
4884dd88ab32SMasahiro Yamada			#print "REST<$rest> dstat<$dstat> ctx<$ctx>\n";
48857551eb4fSHeinrich Schuchardt
48867551eb4fSHeinrich Schuchardt			$ctx =~ s/\n*$//;
48877551eb4fSHeinrich Schuchardt			my $herectx = $here . "\n";
48887551eb4fSHeinrich Schuchardt			my $stmt_cnt = statement_rawlines($ctx);
48897551eb4fSHeinrich Schuchardt
48907551eb4fSHeinrich Schuchardt			for (my $n = 0; $n < $stmt_cnt; $n++) {
48917551eb4fSHeinrich Schuchardt				$herectx .= raw_line($linenr, $n) . "\n";
48927551eb4fSHeinrich Schuchardt			}
48937551eb4fSHeinrich Schuchardt
4894dd88ab32SMasahiro Yamada			if ($dstat ne '' &&
4895dd88ab32SMasahiro Yamada			    $dstat !~ /^(?:$Ident|-?$Constant),$/ &&			# 10, // foo(),
4896dd88ab32SMasahiro Yamada			    $dstat !~ /^(?:$Ident|-?$Constant);$/ &&			# foo();
48976b9709d9STom Rini			    $dstat !~ /^[!~-]?(?:$Lval|$Constant)$/ &&		# 10 // foo() // !foo // ~foo // -foo // foo->bar // foo.bar->baz
48987551eb4fSHeinrich Schuchardt			    $dstat !~ /^'X'$/ && $dstat !~ /^'XX'$/ &&			# character constants
4899dd88ab32SMasahiro Yamada			    $dstat !~ /$exceptions/ &&
4900dd88ab32SMasahiro Yamada			    $dstat !~ /^\.$Ident\s*=/ &&				# .foo =
49016b9709d9STom Rini			    $dstat !~ /^(?:\#\s*$Ident|\#\s*$Constant)\s*$/ &&		# stringification #foo
4902dd88ab32SMasahiro Yamada			    $dstat !~ /^do\s*$Constant\s*while\s*$Constant;?$/ &&	# do {...} while (...); // do {...} while (...)
4903dd88ab32SMasahiro Yamada			    $dstat !~ /^for\s*$Constant$/ &&				# for (...)
4904dd88ab32SMasahiro Yamada			    $dstat !~ /^for\s*$Constant\s+(?:$Ident|-?$Constant)$/ &&	# for (...) bar()
4905dd88ab32SMasahiro Yamada			    $dstat !~ /^do\s*{/ &&					# do {...
4906d8a1a304SHeiko Schocher			    $dstat !~ /^\(\{/ &&						# ({...
49076b9709d9STom Rini			    $ctx !~ /^.\s*#\s*define\s+TRACE_(?:SYSTEM|INCLUDE_FILE|INCLUDE_PATH)\b/)
4908dd88ab32SMasahiro Yamada			{
49097551eb4fSHeinrich Schuchardt				if ($dstat =~ /^\s*if\b/) {
49107551eb4fSHeinrich Schuchardt					ERROR("MULTISTATEMENT_MACRO_USE_DO_WHILE",
49117551eb4fSHeinrich Schuchardt					      "Macros starting with if should be enclosed by a do - while loop to avoid possible if/else logic defects\n" . "$herectx");
49127551eb4fSHeinrich Schuchardt				} elsif ($dstat =~ /;/) {
49137551eb4fSHeinrich Schuchardt					ERROR("MULTISTATEMENT_MACRO_USE_DO_WHILE",
49147551eb4fSHeinrich Schuchardt					      "Macros with multiple statements should be enclosed in a do - while loop\n" . "$herectx");
49157551eb4fSHeinrich Schuchardt				} else {
49167551eb4fSHeinrich Schuchardt					ERROR("COMPLEX_MACRO",
49177551eb4fSHeinrich Schuchardt					      "Macros with complex values should be enclosed in parentheses\n" . "$herectx");
49187551eb4fSHeinrich Schuchardt				}
49197551eb4fSHeinrich Schuchardt
49207551eb4fSHeinrich Schuchardt			}
49217551eb4fSHeinrich Schuchardt
49227551eb4fSHeinrich Schuchardt			# Make $define_stmt single line, comment-free, etc
49237551eb4fSHeinrich Schuchardt			my @stmt_array = split('\n', $define_stmt);
49247551eb4fSHeinrich Schuchardt			my $first = 1;
49257551eb4fSHeinrich Schuchardt			$define_stmt = "";
49267551eb4fSHeinrich Schuchardt			foreach my $l (@stmt_array) {
49277551eb4fSHeinrich Schuchardt				$l =~ s/\\$//;
49287551eb4fSHeinrich Schuchardt				if ($first) {
49297551eb4fSHeinrich Schuchardt					$define_stmt = $l;
49307551eb4fSHeinrich Schuchardt					$first = 0;
49317551eb4fSHeinrich Schuchardt				} elsif ($l =~ /^[\+ ]/) {
49327551eb4fSHeinrich Schuchardt					$define_stmt .= substr($l, 1);
49337551eb4fSHeinrich Schuchardt				}
49347551eb4fSHeinrich Schuchardt			}
49357551eb4fSHeinrich Schuchardt			$define_stmt =~ s/$;//g;
49367551eb4fSHeinrich Schuchardt			$define_stmt =~ s/\s+/ /g;
49377551eb4fSHeinrich Schuchardt			$define_stmt = trim($define_stmt);
49387551eb4fSHeinrich Schuchardt
49397551eb4fSHeinrich Schuchardt# check if any macro arguments are reused (ignore '...' and 'type')
49407551eb4fSHeinrich Schuchardt			foreach my $arg (@def_args) {
49417551eb4fSHeinrich Schuchardt			        next if ($arg =~ /\.\.\./);
49427551eb4fSHeinrich Schuchardt			        next if ($arg =~ /^type$/i);
49437551eb4fSHeinrich Schuchardt				my $tmp_stmt = $define_stmt;
49447551eb4fSHeinrich Schuchardt				$tmp_stmt =~ s/\b(typeof|__typeof__|__builtin\w+|typecheck\s*\(\s*$Type\s*,|\#+)\s*\(*\s*$arg\s*\)*\b//g;
49457551eb4fSHeinrich Schuchardt				$tmp_stmt =~ s/\#+\s*$arg\b//g;
49467551eb4fSHeinrich Schuchardt				$tmp_stmt =~ s/\b$arg\s*\#\#//g;
49477551eb4fSHeinrich Schuchardt				my $use_cnt = $tmp_stmt =~ s/\b$arg\b//g;
49487551eb4fSHeinrich Schuchardt				if ($use_cnt > 1) {
49497551eb4fSHeinrich Schuchardt					CHK("MACRO_ARG_REUSE",
49507551eb4fSHeinrich Schuchardt					    "Macro argument reuse '$arg' - possible side-effects?\n" . "$herectx");
49517551eb4fSHeinrich Schuchardt				    }
49527551eb4fSHeinrich Schuchardt# check if any macro arguments may have other precedence issues
49537551eb4fSHeinrich Schuchardt				if ($tmp_stmt =~ m/($Operators)?\s*\b$arg\b\s*($Operators)?/m &&
49547551eb4fSHeinrich Schuchardt				    ((defined($1) && $1 ne ',') ||
49557551eb4fSHeinrich Schuchardt				     (defined($2) && $2 ne ','))) {
49567551eb4fSHeinrich Schuchardt					CHK("MACRO_ARG_PRECEDENCE",
49577551eb4fSHeinrich Schuchardt					    "Macro argument '$arg' may be better as '($arg)' to avoid precedence issues\n" . "$herectx");
49587551eb4fSHeinrich Schuchardt				}
49597551eb4fSHeinrich Schuchardt			}
49607551eb4fSHeinrich Schuchardt
49617551eb4fSHeinrich Schuchardt# check for macros with flow control, but without ## concatenation
49627551eb4fSHeinrich Schuchardt# ## concatenation is commonly a macro that defines a function so ignore those
49637551eb4fSHeinrich Schuchardt			if ($has_flow_statement && !$has_arg_concat) {
4964dd88ab32SMasahiro Yamada				my $herectx = $here . "\n";
4965dd88ab32SMasahiro Yamada				my $cnt = statement_rawlines($ctx);
4966dd88ab32SMasahiro Yamada
4967dd88ab32SMasahiro Yamada				for (my $n = 0; $n < $cnt; $n++) {
4968dd88ab32SMasahiro Yamada					$herectx .= raw_line($linenr, $n) . "\n";
4969dd88ab32SMasahiro Yamada				}
49707551eb4fSHeinrich Schuchardt				WARN("MACRO_WITH_FLOW_CONTROL",
49717551eb4fSHeinrich Schuchardt				     "Macros with flow control statements should be avoided\n" . "$herectx");
4972dd88ab32SMasahiro Yamada			}
4973dd88ab32SMasahiro Yamada
4974dd88ab32SMasahiro Yamada# check for line continuations outside of #defines, preprocessor #, and asm
4975dd88ab32SMasahiro Yamada
4976dd88ab32SMasahiro Yamada		} else {
4977dd88ab32SMasahiro Yamada			if ($prevline !~ /^..*\\$/ &&
4978dd88ab32SMasahiro Yamada			    $line !~ /^\+\s*\#.*\\$/ &&		# preprocessor
4979dd88ab32SMasahiro Yamada			    $line !~ /^\+.*\b(__asm__|asm)\b.*\\$/ &&	# asm
4980dd88ab32SMasahiro Yamada			    $line =~ /^\+.*\\$/) {
4981dd88ab32SMasahiro Yamada				WARN("LINE_CONTINUATIONS",
4982dd88ab32SMasahiro Yamada				     "Avoid unnecessary line continuations\n" . $herecurr);
4983dd88ab32SMasahiro Yamada			}
4984dd88ab32SMasahiro Yamada		}
4985dd88ab32SMasahiro Yamada
4986dd88ab32SMasahiro Yamada# do {} while (0) macro tests:
4987dd88ab32SMasahiro Yamada# single-statement macros do not need to be enclosed in do while (0) loop,
4988dd88ab32SMasahiro Yamada# macro should not end with a semicolon
4989dd88ab32SMasahiro Yamada		if ($^V && $^V ge 5.10.0 &&
4990dd88ab32SMasahiro Yamada		    $realfile !~ m@/vmlinux.lds.h$@ &&
4991dd88ab32SMasahiro Yamada		    $line =~ /^.\s*\#\s*define\s+$Ident(\()?/) {
4992dd88ab32SMasahiro Yamada			my $ln = $linenr;
4993dd88ab32SMasahiro Yamada			my $cnt = $realcnt;
4994dd88ab32SMasahiro Yamada			my ($off, $dstat, $dcond, $rest);
4995dd88ab32SMasahiro Yamada			my $ctx = '';
4996dd88ab32SMasahiro Yamada			($dstat, $dcond, $ln, $cnt, $off) =
4997dd88ab32SMasahiro Yamada				ctx_statement_block($linenr, $realcnt, 0);
4998dd88ab32SMasahiro Yamada			$ctx = $dstat;
4999dd88ab32SMasahiro Yamada
5000dd88ab32SMasahiro Yamada			$dstat =~ s/\\\n.//g;
50017551eb4fSHeinrich Schuchardt			$dstat =~ s/$;/ /g;
5002dd88ab32SMasahiro Yamada
5003dd88ab32SMasahiro Yamada			if ($dstat =~ /^\+\s*#\s*define\s+$Ident\s*${balanced_parens}\s*do\s*{(.*)\s*}\s*while\s*\(\s*0\s*\)\s*([;\s]*)\s*$/) {
5004dd88ab32SMasahiro Yamada				my $stmts = $2;
5005dd88ab32SMasahiro Yamada				my $semis = $3;
5006dd88ab32SMasahiro Yamada
5007dd88ab32SMasahiro Yamada				$ctx =~ s/\n*$//;
5008dd88ab32SMasahiro Yamada				my $cnt = statement_rawlines($ctx);
5009dd88ab32SMasahiro Yamada				my $herectx = $here . "\n";
5010dd88ab32SMasahiro Yamada
5011dd88ab32SMasahiro Yamada				for (my $n = 0; $n < $cnt; $n++) {
5012dd88ab32SMasahiro Yamada					$herectx .= raw_line($linenr, $n) . "\n";
5013dd88ab32SMasahiro Yamada				}
5014dd88ab32SMasahiro Yamada
5015dd88ab32SMasahiro Yamada				if (($stmts =~ tr/;/;/) == 1 &&
5016dd88ab32SMasahiro Yamada				    $stmts !~ /^\s*(if|while|for|switch)\b/) {
5017dd88ab32SMasahiro Yamada					WARN("SINGLE_STATEMENT_DO_WHILE_MACRO",
5018dd88ab32SMasahiro Yamada					     "Single statement macros should not use a do {} while (0) loop\n" . "$herectx");
5019dd88ab32SMasahiro Yamada				}
5020dd88ab32SMasahiro Yamada				if (defined $semis && $semis ne "") {
5021dd88ab32SMasahiro Yamada					WARN("DO_WHILE_MACRO_WITH_TRAILING_SEMICOLON",
5022dd88ab32SMasahiro Yamada					     "do {} while (0) macros should not be semicolon terminated\n" . "$herectx");
5023dd88ab32SMasahiro Yamada				}
50247551eb4fSHeinrich Schuchardt			} elsif ($dstat =~ /^\+\s*#\s*define\s+$Ident.*;\s*$/) {
50257551eb4fSHeinrich Schuchardt				$ctx =~ s/\n*$//;
50267551eb4fSHeinrich Schuchardt				my $cnt = statement_rawlines($ctx);
50277551eb4fSHeinrich Schuchardt				my $herectx = $here . "\n";
50287551eb4fSHeinrich Schuchardt
50297551eb4fSHeinrich Schuchardt				for (my $n = 0; $n < $cnt; $n++) {
50307551eb4fSHeinrich Schuchardt					$herectx .= raw_line($linenr, $n) . "\n";
50317551eb4fSHeinrich Schuchardt				}
50327551eb4fSHeinrich Schuchardt
50337551eb4fSHeinrich Schuchardt				WARN("TRAILING_SEMICOLON",
50347551eb4fSHeinrich Schuchardt				     "macros should not use a trailing semicolon\n" . "$herectx");
5035dd88ab32SMasahiro Yamada			}
5036dd88ab32SMasahiro Yamada		}
5037dd88ab32SMasahiro Yamada
5038dd88ab32SMasahiro Yamada# make sure symbols are always wrapped with VMLINUX_SYMBOL() ...
5039dd88ab32SMasahiro Yamada# all assignments may have only one of the following with an assignment:
5040dd88ab32SMasahiro Yamada#	.
5041dd88ab32SMasahiro Yamada#	ALIGN(...)
5042dd88ab32SMasahiro Yamada#	VMLINUX_SYMBOL(...)
5043dd88ab32SMasahiro Yamada		if ($realfile eq 'vmlinux.lds.h' && $line =~ /(?:(?:^|\s)$Ident\s*=|=\s*$Ident(?:\s|$))/) {
5044dd88ab32SMasahiro Yamada			WARN("MISSING_VMLINUX_SYMBOL",
5045dd88ab32SMasahiro Yamada			     "vmlinux.lds.h needs VMLINUX_SYMBOL() around C-visible symbols\n" . $herecurr);
5046dd88ab32SMasahiro Yamada		}
5047dd88ab32SMasahiro Yamada
5048dd88ab32SMasahiro Yamada# check for redundant bracing round if etc
5049dd88ab32SMasahiro Yamada		if ($line =~ /(^.*)\bif\b/ && $1 !~ /else\s*$/) {
5050dd88ab32SMasahiro Yamada			my ($level, $endln, @chunks) =
5051dd88ab32SMasahiro Yamada				ctx_statement_full($linenr, $realcnt, 1);
5052dd88ab32SMasahiro Yamada			#print "chunks<$#chunks> linenr<$linenr> endln<$endln> level<$level>\n";
5053dd88ab32SMasahiro Yamada			#print "APW: <<$chunks[1][0]>><<$chunks[1][1]>>\n";
5054dd88ab32SMasahiro Yamada			if ($#chunks > 0 && $level == 0) {
5055dd88ab32SMasahiro Yamada				my @allowed = ();
5056dd88ab32SMasahiro Yamada				my $allow = 0;
5057dd88ab32SMasahiro Yamada				my $seen = 0;
5058dd88ab32SMasahiro Yamada				my $herectx = $here . "\n";
5059dd88ab32SMasahiro Yamada				my $ln = $linenr - 1;
5060dd88ab32SMasahiro Yamada				for my $chunk (@chunks) {
5061dd88ab32SMasahiro Yamada					my ($cond, $block) = @{$chunk};
5062dd88ab32SMasahiro Yamada
5063dd88ab32SMasahiro Yamada					# If the condition carries leading newlines, then count those as offsets.
5064dd88ab32SMasahiro Yamada					my ($whitespace) = ($cond =~ /^((?:\s*\n[+-])*\s*)/s);
5065dd88ab32SMasahiro Yamada					my $offset = statement_rawlines($whitespace) - 1;
5066dd88ab32SMasahiro Yamada
5067dd88ab32SMasahiro Yamada					$allowed[$allow] = 0;
5068dd88ab32SMasahiro Yamada					#print "COND<$cond> whitespace<$whitespace> offset<$offset>\n";
5069dd88ab32SMasahiro Yamada
5070dd88ab32SMasahiro Yamada					# We have looked at and allowed this specific line.
5071dd88ab32SMasahiro Yamada					$suppress_ifbraces{$ln + $offset} = 1;
5072dd88ab32SMasahiro Yamada
5073dd88ab32SMasahiro Yamada					$herectx .= "$rawlines[$ln + $offset]\n[...]\n";
5074dd88ab32SMasahiro Yamada					$ln += statement_rawlines($block) - 1;
5075dd88ab32SMasahiro Yamada
5076dd88ab32SMasahiro Yamada					substr($block, 0, length($cond), '');
5077dd88ab32SMasahiro Yamada
5078dd88ab32SMasahiro Yamada					$seen++ if ($block =~ /^\s*{/);
5079dd88ab32SMasahiro Yamada
5080dd88ab32SMasahiro Yamada					#print "cond<$cond> block<$block> allowed<$allowed[$allow]>\n";
5081dd88ab32SMasahiro Yamada					if (statement_lines($cond) > 1) {
5082dd88ab32SMasahiro Yamada						#print "APW: ALLOWED: cond<$cond>\n";
5083dd88ab32SMasahiro Yamada						$allowed[$allow] = 1;
5084dd88ab32SMasahiro Yamada					}
5085dd88ab32SMasahiro Yamada					if ($block =~/\b(?:if|for|while)\b/) {
5086dd88ab32SMasahiro Yamada						#print "APW: ALLOWED: block<$block>\n";
5087dd88ab32SMasahiro Yamada						$allowed[$allow] = 1;
5088dd88ab32SMasahiro Yamada					}
5089dd88ab32SMasahiro Yamada					if (statement_block_size($block) > 1) {
5090dd88ab32SMasahiro Yamada						#print "APW: ALLOWED: lines block<$block>\n";
5091dd88ab32SMasahiro Yamada						$allowed[$allow] = 1;
5092dd88ab32SMasahiro Yamada					}
5093dd88ab32SMasahiro Yamada					$allow++;
5094dd88ab32SMasahiro Yamada				}
5095dd88ab32SMasahiro Yamada				if ($seen) {
5096dd88ab32SMasahiro Yamada					my $sum_allowed = 0;
5097dd88ab32SMasahiro Yamada					foreach (@allowed) {
5098dd88ab32SMasahiro Yamada						$sum_allowed += $_;
5099dd88ab32SMasahiro Yamada					}
5100dd88ab32SMasahiro Yamada					if ($sum_allowed == 0) {
5101dd88ab32SMasahiro Yamada						WARN("BRACES",
5102dd88ab32SMasahiro Yamada						     "braces {} are not necessary for any arm of this statement\n" . $herectx);
5103dd88ab32SMasahiro Yamada					} elsif ($sum_allowed != $allow &&
5104dd88ab32SMasahiro Yamada						 $seen != $allow) {
5105dd88ab32SMasahiro Yamada						CHK("BRACES",
5106dd88ab32SMasahiro Yamada						    "braces {} should be used on all arms of this statement\n" . $herectx);
5107dd88ab32SMasahiro Yamada					}
5108dd88ab32SMasahiro Yamada				}
5109dd88ab32SMasahiro Yamada			}
5110dd88ab32SMasahiro Yamada		}
5111dd88ab32SMasahiro Yamada		if (!defined $suppress_ifbraces{$linenr - 1} &&
5112dd88ab32SMasahiro Yamada					$line =~ /\b(if|while|for|else)\b/) {
5113dd88ab32SMasahiro Yamada			my $allowed = 0;
5114dd88ab32SMasahiro Yamada
5115dd88ab32SMasahiro Yamada			# Check the pre-context.
5116dd88ab32SMasahiro Yamada			if (substr($line, 0, $-[0]) =~ /(\}\s*)$/) {
5117dd88ab32SMasahiro Yamada				#print "APW: ALLOWED: pre<$1>\n";
5118dd88ab32SMasahiro Yamada				$allowed = 1;
5119dd88ab32SMasahiro Yamada			}
5120dd88ab32SMasahiro Yamada
5121dd88ab32SMasahiro Yamada			my ($level, $endln, @chunks) =
5122dd88ab32SMasahiro Yamada				ctx_statement_full($linenr, $realcnt, $-[0]);
5123dd88ab32SMasahiro Yamada
5124dd88ab32SMasahiro Yamada			# Check the condition.
5125dd88ab32SMasahiro Yamada			my ($cond, $block) = @{$chunks[0]};
5126dd88ab32SMasahiro Yamada			#print "CHECKING<$linenr> cond<$cond> block<$block>\n";
5127dd88ab32SMasahiro Yamada			if (defined $cond) {
5128dd88ab32SMasahiro Yamada				substr($block, 0, length($cond), '');
5129dd88ab32SMasahiro Yamada			}
5130dd88ab32SMasahiro Yamada			if (statement_lines($cond) > 1) {
5131dd88ab32SMasahiro Yamada				#print "APW: ALLOWED: cond<$cond>\n";
5132dd88ab32SMasahiro Yamada				$allowed = 1;
5133dd88ab32SMasahiro Yamada			}
5134dd88ab32SMasahiro Yamada			if ($block =~/\b(?:if|for|while)\b/) {
5135dd88ab32SMasahiro Yamada				#print "APW: ALLOWED: block<$block>\n";
5136dd88ab32SMasahiro Yamada				$allowed = 1;
5137dd88ab32SMasahiro Yamada			}
5138dd88ab32SMasahiro Yamada			if (statement_block_size($block) > 1) {
5139dd88ab32SMasahiro Yamada				#print "APW: ALLOWED: lines block<$block>\n";
5140dd88ab32SMasahiro Yamada				$allowed = 1;
5141dd88ab32SMasahiro Yamada			}
5142dd88ab32SMasahiro Yamada			# Check the post-context.
5143dd88ab32SMasahiro Yamada			if (defined $chunks[1]) {
5144dd88ab32SMasahiro Yamada				my ($cond, $block) = @{$chunks[1]};
5145dd88ab32SMasahiro Yamada				if (defined $cond) {
5146dd88ab32SMasahiro Yamada					substr($block, 0, length($cond), '');
5147dd88ab32SMasahiro Yamada				}
5148dd88ab32SMasahiro Yamada				if ($block =~ /^\s*\{/) {
5149dd88ab32SMasahiro Yamada					#print "APW: ALLOWED: chunk-1 block<$block>\n";
5150dd88ab32SMasahiro Yamada					$allowed = 1;
5151dd88ab32SMasahiro Yamada				}
5152dd88ab32SMasahiro Yamada			}
5153dd88ab32SMasahiro Yamada			if ($level == 0 && $block =~ /^\s*\{/ && !$allowed) {
5154dd88ab32SMasahiro Yamada				my $herectx = $here . "\n";
5155dd88ab32SMasahiro Yamada				my $cnt = statement_rawlines($block);
5156dd88ab32SMasahiro Yamada
5157dd88ab32SMasahiro Yamada				for (my $n = 0; $n < $cnt; $n++) {
5158dd88ab32SMasahiro Yamada					$herectx .= raw_line($linenr, $n) . "\n";
5159dd88ab32SMasahiro Yamada				}
5160dd88ab32SMasahiro Yamada
5161dd88ab32SMasahiro Yamada				WARN("BRACES",
5162dd88ab32SMasahiro Yamada				     "braces {} are not necessary for single statement blocks\n" . $herectx);
5163dd88ab32SMasahiro Yamada			}
5164dd88ab32SMasahiro Yamada		}
5165dd88ab32SMasahiro Yamada
51667551eb4fSHeinrich Schuchardt# check for single line unbalanced braces
51677551eb4fSHeinrich Schuchardt		if ($sline =~ /^.\s*\}\s*else\s*$/ ||
51687551eb4fSHeinrich Schuchardt		    $sline =~ /^.\s*else\s*\{\s*$/) {
51697551eb4fSHeinrich Schuchardt			CHK("BRACES", "Unbalanced braces around else statement\n" . $herecurr);
51707551eb4fSHeinrich Schuchardt		}
51717551eb4fSHeinrich Schuchardt
5172dd88ab32SMasahiro Yamada# check for unnecessary blank lines around braces
51736b9709d9STom Rini		if (($line =~ /^.\s*}\s*$/ && $prevrawline =~ /^.\s*$/)) {
51747551eb4fSHeinrich Schuchardt			if (CHK("BRACES",
51757551eb4fSHeinrich Schuchardt				"Blank lines aren't necessary before a close brace '}'\n" . $hereprev) &&
51767551eb4fSHeinrich Schuchardt			    $fix && $prevrawline =~ /^\+/) {
51777551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr - 1, $prevrawline);
51787551eb4fSHeinrich Schuchardt			}
5179dd88ab32SMasahiro Yamada		}
51806b9709d9STom Rini		if (($rawline =~ /^.\s*$/ && $prevline =~ /^..*{\s*$/)) {
51817551eb4fSHeinrich Schuchardt			if (CHK("BRACES",
51827551eb4fSHeinrich Schuchardt				"Blank lines aren't necessary after an open brace '{'\n" . $hereprev) &&
51837551eb4fSHeinrich Schuchardt			    $fix) {
51847551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
51857551eb4fSHeinrich Schuchardt			}
5186dd88ab32SMasahiro Yamada		}
5187dd88ab32SMasahiro Yamada
5188dd88ab32SMasahiro Yamada# no volatiles please
5189dd88ab32SMasahiro Yamada		my $asm_volatile = qr{\b(__asm__|asm)\s+(__volatile__|volatile)\b};
5190dd88ab32SMasahiro Yamada		if ($line =~ /\bvolatile\b/ && $line !~ /$asm_volatile/) {
5191dd88ab32SMasahiro Yamada			WARN("VOLATILE",
51927551eb4fSHeinrich Schuchardt			     "Use of volatile is usually wrong: see Documentation/process/volatile-considered-harmful.rst\n" . $herecurr);
51937551eb4fSHeinrich Schuchardt		}
51947551eb4fSHeinrich Schuchardt
51957551eb4fSHeinrich Schuchardt# Check for user-visible strings broken across lines, which breaks the ability
51967551eb4fSHeinrich Schuchardt# to grep for the string.  Make exceptions when the previous string ends in a
51977551eb4fSHeinrich Schuchardt# newline (multiple lines in one string constant) or '\t', '\r', ';', or '{'
51987551eb4fSHeinrich Schuchardt# (common in inline assembly) or is a octal \123 or hexadecimal \xaf value
51997551eb4fSHeinrich Schuchardt		if ($line =~ /^\+\s*$String/ &&
52007551eb4fSHeinrich Schuchardt		    $prevline =~ /"\s*$/ &&
52017551eb4fSHeinrich Schuchardt		    $prevrawline !~ /(?:\\(?:[ntr]|[0-7]{1,3}|x[0-9a-fA-F]{1,2})|;\s*|\{\s*)"\s*$/) {
52027551eb4fSHeinrich Schuchardt			if (WARN("SPLIT_STRING",
52037551eb4fSHeinrich Schuchardt				 "quoted string split across lines\n" . $hereprev) &&
52047551eb4fSHeinrich Schuchardt				     $fix &&
52057551eb4fSHeinrich Schuchardt				     $prevrawline =~ /^\+.*"\s*$/ &&
52067551eb4fSHeinrich Schuchardt				     $last_coalesced_string_linenr != $linenr - 1) {
52077551eb4fSHeinrich Schuchardt				my $extracted_string = get_quoted_string($line, $rawline);
52087551eb4fSHeinrich Schuchardt				my $comma_close = "";
52097551eb4fSHeinrich Schuchardt				if ($rawline =~ /\Q$extracted_string\E(\s*\)\s*;\s*$|\s*,\s*)/) {
52107551eb4fSHeinrich Schuchardt					$comma_close = $1;
52117551eb4fSHeinrich Schuchardt				}
52127551eb4fSHeinrich Schuchardt
52137551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr - 1, $prevrawline);
52147551eb4fSHeinrich Schuchardt				fix_delete_line($fixlinenr, $rawline);
52157551eb4fSHeinrich Schuchardt				my $fixedline = $prevrawline;
52167551eb4fSHeinrich Schuchardt				$fixedline =~ s/"\s*$//;
52177551eb4fSHeinrich Schuchardt				$fixedline .= substr($extracted_string, 1) . trim($comma_close);
52187551eb4fSHeinrich Schuchardt				fix_insert_line($fixlinenr - 1, $fixedline);
52197551eb4fSHeinrich Schuchardt				$fixedline = $rawline;
52207551eb4fSHeinrich Schuchardt				$fixedline =~ s/\Q$extracted_string\E\Q$comma_close\E//;
52217551eb4fSHeinrich Schuchardt				if ($fixedline !~ /\+\s*$/) {
52227551eb4fSHeinrich Schuchardt					fix_insert_line($fixlinenr, $fixedline);
52237551eb4fSHeinrich Schuchardt				}
52247551eb4fSHeinrich Schuchardt				$last_coalesced_string_linenr = $linenr;
52257551eb4fSHeinrich Schuchardt			}
52267551eb4fSHeinrich Schuchardt		}
52277551eb4fSHeinrich Schuchardt
52287551eb4fSHeinrich Schuchardt# check for missing a space in a string concatenation
52297551eb4fSHeinrich Schuchardt		if ($prevrawline =~ /[^\\]\w"$/ && $rawline =~ /^\+[\t ]+"\w/) {
52307551eb4fSHeinrich Schuchardt			WARN('MISSING_SPACE',
52317551eb4fSHeinrich Schuchardt			     "break quoted strings at a space character\n" . $hereprev);
52327551eb4fSHeinrich Schuchardt		}
52337551eb4fSHeinrich Schuchardt
52347551eb4fSHeinrich Schuchardt# check for an embedded function name in a string when the function is known
52357551eb4fSHeinrich Schuchardt# This does not work very well for -f --file checking as it depends on patch
52367551eb4fSHeinrich Schuchardt# context providing the function name or a single line form for in-file
52377551eb4fSHeinrich Schuchardt# function declarations
52387551eb4fSHeinrich Schuchardt		if ($line =~ /^\+.*$String/ &&
52397551eb4fSHeinrich Schuchardt		    defined($context_function) &&
52407551eb4fSHeinrich Schuchardt		    get_quoted_string($line, $rawline) =~ /\b$context_function\b/ &&
52417551eb4fSHeinrich Schuchardt		    length(get_quoted_string($line, $rawline)) != (length($context_function) + 2)) {
52427551eb4fSHeinrich Schuchardt			WARN("EMBEDDED_FUNCTION_NAME",
52437551eb4fSHeinrich Schuchardt			     "Prefer using '\"%s...\", __func__' to using '$context_function', this function's name, in a string\n" . $herecurr);
52447551eb4fSHeinrich Schuchardt		}
52457551eb4fSHeinrich Schuchardt
52467551eb4fSHeinrich Schuchardt# check for spaces before a quoted newline
52477551eb4fSHeinrich Schuchardt		if ($rawline =~ /^.*\".*\s\\n/) {
52487551eb4fSHeinrich Schuchardt			if (WARN("QUOTED_WHITESPACE_BEFORE_NEWLINE",
52497551eb4fSHeinrich Schuchardt				 "unnecessary whitespace before a quoted newline\n" . $herecurr) &&
52507551eb4fSHeinrich Schuchardt			    $fix) {
52517551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/^(\+.*\".*)\s+\\n/$1\\n/;
52527551eb4fSHeinrich Schuchardt			}
52537551eb4fSHeinrich Schuchardt
52547551eb4fSHeinrich Schuchardt		}
52557551eb4fSHeinrich Schuchardt
52567551eb4fSHeinrich Schuchardt# concatenated string without spaces between elements
5257*722c07ddSHeinrich Schuchardt		if ($line =~ /$String[A-Z_]/ ||
5258*722c07ddSHeinrich Schuchardt		    ($line =~ /([A-Za-z0-9_]+)$String/ && $1 !~ /^L$/)) {
52597551eb4fSHeinrich Schuchardt			CHK("CONCATENATED_STRING",
52607551eb4fSHeinrich Schuchardt			    "Concatenated strings should use spaces between elements\n" . $herecurr);
52617551eb4fSHeinrich Schuchardt		}
52627551eb4fSHeinrich Schuchardt
52637551eb4fSHeinrich Schuchardt# uncoalesced string fragments
5264*722c07ddSHeinrich Schuchardt		if ($line =~ /$String\s*L?"/) {
52657551eb4fSHeinrich Schuchardt			WARN("STRING_FRAGMENTS",
52667551eb4fSHeinrich Schuchardt			     "Consecutive strings are generally better as a single string\n" . $herecurr);
52677551eb4fSHeinrich Schuchardt		}
52687551eb4fSHeinrich Schuchardt
52697551eb4fSHeinrich Schuchardt# check for non-standard and hex prefixed decimal printf formats
52707551eb4fSHeinrich Schuchardt		my $show_L = 1;	#don't show the same defect twice
52717551eb4fSHeinrich Schuchardt		my $show_Z = 1;
52727551eb4fSHeinrich Schuchardt		while ($line =~ /(?:^|")([X\t]*)(?:"|$)/g) {
52737551eb4fSHeinrich Schuchardt			my $string = substr($rawline, $-[1], $+[1] - $-[1]);
52747551eb4fSHeinrich Schuchardt			$string =~ s/%%/__/g;
52757551eb4fSHeinrich Schuchardt			# check for %L
52767551eb4fSHeinrich Schuchardt			if ($show_L && $string =~ /%[\*\d\.\$]*L([diouxX])/) {
52777551eb4fSHeinrich Schuchardt				WARN("PRINTF_L",
52787551eb4fSHeinrich Schuchardt				     "\%L$1 is non-standard C, use %ll$1\n" . $herecurr);
52797551eb4fSHeinrich Schuchardt				$show_L = 0;
52807551eb4fSHeinrich Schuchardt			}
52817551eb4fSHeinrich Schuchardt			# check for %Z
52827551eb4fSHeinrich Schuchardt			if ($show_Z && $string =~ /%[\*\d\.\$]*Z([diouxX])/) {
52837551eb4fSHeinrich Schuchardt				WARN("PRINTF_Z",
52847551eb4fSHeinrich Schuchardt				     "%Z$1 is non-standard C, use %z$1\n" . $herecurr);
52857551eb4fSHeinrich Schuchardt				$show_Z = 0;
52867551eb4fSHeinrich Schuchardt			}
52877551eb4fSHeinrich Schuchardt			# check for 0x<decimal>
52887551eb4fSHeinrich Schuchardt			if ($string =~ /0x%[\*\d\.\$\Llzth]*[diou]/) {
52897551eb4fSHeinrich Schuchardt				ERROR("PRINTF_0XDECIMAL",
52907551eb4fSHeinrich Schuchardt				      "Prefixing 0x with decimal output is defective\n" . $herecurr);
52917551eb4fSHeinrich Schuchardt			}
52927551eb4fSHeinrich Schuchardt		}
52937551eb4fSHeinrich Schuchardt
52947551eb4fSHeinrich Schuchardt# check for line continuations in quoted strings with odd counts of "
52957551eb4fSHeinrich Schuchardt		if ($rawline =~ /\\$/ && $rawline =~ tr/"/"/ % 2) {
52967551eb4fSHeinrich Schuchardt			WARN("LINE_CONTINUATIONS",
52977551eb4fSHeinrich Schuchardt			     "Avoid line continuations in quoted strings\n" . $herecurr);
5298dd88ab32SMasahiro Yamada		}
5299dd88ab32SMasahiro Yamada
5300dd88ab32SMasahiro Yamada# warn about #if 0
5301dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*\#\s*if\s+0\b/) {
5302dd88ab32SMasahiro Yamada			CHK("REDUNDANT_CODE",
5303dd88ab32SMasahiro Yamada			    "if this code is redundant consider removing it\n" .
5304dd88ab32SMasahiro Yamada				$herecurr);
5305dd88ab32SMasahiro Yamada		}
5306dd88ab32SMasahiro Yamada
5307dd88ab32SMasahiro Yamada# check for needless "if (<foo>) fn(<foo>)" uses
5308dd88ab32SMasahiro Yamada		if ($prevline =~ /\bif\s*\(\s*($Lval)\s*\)/) {
53097551eb4fSHeinrich Schuchardt			my $tested = quotemeta($1);
53107551eb4fSHeinrich Schuchardt			my $expr = '\s*\(\s*' . $tested . '\s*\)\s*;';
53117551eb4fSHeinrich Schuchardt			if ($line =~ /\b(kfree|usb_free_urb|debugfs_remove(?:_recursive)?|(?:kmem_cache|mempool|dma_pool)_destroy)$expr/) {
53127551eb4fSHeinrich Schuchardt				my $func = $1;
53137551eb4fSHeinrich Schuchardt				if (WARN('NEEDLESS_IF',
53147551eb4fSHeinrich Schuchardt					 "$func(NULL) is safe and this check is probably not required\n" . $hereprev) &&
53157551eb4fSHeinrich Schuchardt				    $fix) {
53167551eb4fSHeinrich Schuchardt					my $do_fix = 1;
53177551eb4fSHeinrich Schuchardt					my $leading_tabs = "";
53187551eb4fSHeinrich Schuchardt					my $new_leading_tabs = "";
53197551eb4fSHeinrich Schuchardt					if ($lines[$linenr - 2] =~ /^\+(\t*)if\s*\(\s*$tested\s*\)\s*$/) {
53207551eb4fSHeinrich Schuchardt						$leading_tabs = $1;
53217551eb4fSHeinrich Schuchardt					} else {
53227551eb4fSHeinrich Schuchardt						$do_fix = 0;
53237551eb4fSHeinrich Schuchardt					}
53247551eb4fSHeinrich Schuchardt					if ($lines[$linenr - 1] =~ /^\+(\t+)$func\s*\(\s*$tested\s*\)\s*;\s*$/) {
53257551eb4fSHeinrich Schuchardt						$new_leading_tabs = $1;
53267551eb4fSHeinrich Schuchardt						if (length($leading_tabs) + 1 ne length($new_leading_tabs)) {
53277551eb4fSHeinrich Schuchardt							$do_fix = 0;
53287551eb4fSHeinrich Schuchardt						}
53297551eb4fSHeinrich Schuchardt					} else {
53307551eb4fSHeinrich Schuchardt						$do_fix = 0;
53317551eb4fSHeinrich Schuchardt					}
53327551eb4fSHeinrich Schuchardt					if ($do_fix) {
53337551eb4fSHeinrich Schuchardt						fix_delete_line($fixlinenr - 1, $prevrawline);
53347551eb4fSHeinrich Schuchardt						$fixed[$fixlinenr] =~ s/^\+$new_leading_tabs/\+$leading_tabs/;
53357551eb4fSHeinrich Schuchardt					}
53367551eb4fSHeinrich Schuchardt				}
53377551eb4fSHeinrich Schuchardt			}
53387551eb4fSHeinrich Schuchardt		}
53397551eb4fSHeinrich Schuchardt
53407551eb4fSHeinrich Schuchardt# check for unnecessary "Out of Memory" messages
53417551eb4fSHeinrich Schuchardt		if ($line =~ /^\+.*\b$logFunctions\s*\(/ &&
53427551eb4fSHeinrich Schuchardt		    $prevline =~ /^[ \+]\s*if\s*\(\s*(\!\s*|NULL\s*==\s*)?($Lval)(\s*==\s*NULL\s*)?\s*\)/ &&
53437551eb4fSHeinrich Schuchardt		    (defined $1 || defined $3) &&
53447551eb4fSHeinrich Schuchardt		    $linenr > 3) {
53457551eb4fSHeinrich Schuchardt			my $testval = $2;
53467551eb4fSHeinrich Schuchardt			my $testline = $lines[$linenr - 3];
53477551eb4fSHeinrich Schuchardt
53487551eb4fSHeinrich Schuchardt			my ($s, $c) = ctx_statement_block($linenr - 3, $realcnt, 0);
53497551eb4fSHeinrich Schuchardt#			print("line: <$line>\nprevline: <$prevline>\ns: <$s>\nc: <$c>\n\n\n");
53507551eb4fSHeinrich Schuchardt
53517551eb4fSHeinrich Schuchardt			if ($s =~ /(?:^|\n)[ \+]\s*(?:$Type\s*)?\Q$testval\E\s*=\s*(?:\([^\)]*\)\s*)?\s*(?:devm_)?(?:[kv][czm]alloc(?:_node|_array)?\b|kstrdup|kmemdup|(?:dev_)?alloc_skb)/) {
53527551eb4fSHeinrich Schuchardt				WARN("OOM_MESSAGE",
53537551eb4fSHeinrich Schuchardt				     "Possible unnecessary 'out of memory' message\n" . $hereprev);
53547551eb4fSHeinrich Schuchardt			}
53557551eb4fSHeinrich Schuchardt		}
53567551eb4fSHeinrich Schuchardt
53577551eb4fSHeinrich Schuchardt# check for logging functions with KERN_<LEVEL>
53587551eb4fSHeinrich Schuchardt		if ($line !~ /printk(?:_ratelimited|_once)?\s*\(/ &&
53597551eb4fSHeinrich Schuchardt		    $line =~ /\b$logFunctions\s*\(.*\b(KERN_[A-Z]+)\b/) {
53607551eb4fSHeinrich Schuchardt			my $level = $1;
53617551eb4fSHeinrich Schuchardt			if (WARN("UNNECESSARY_KERN_LEVEL",
53627551eb4fSHeinrich Schuchardt				 "Possible unnecessary $level\n" . $herecurr) &&
53637551eb4fSHeinrich Schuchardt			    $fix) {
53647551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\s*$level\s*//;
53657551eb4fSHeinrich Schuchardt			}
53667551eb4fSHeinrich Schuchardt		}
53677551eb4fSHeinrich Schuchardt
53687551eb4fSHeinrich Schuchardt# check for logging continuations
53697551eb4fSHeinrich Schuchardt		if ($line =~ /\bprintk\s*\(\s*KERN_CONT\b|\bpr_cont\s*\(/) {
53707551eb4fSHeinrich Schuchardt			WARN("LOGGING_CONTINUATION",
53717551eb4fSHeinrich Schuchardt			     "Avoid logging continuation uses where feasible\n" . $herecurr);
53727551eb4fSHeinrich Schuchardt		}
53737551eb4fSHeinrich Schuchardt
53747551eb4fSHeinrich Schuchardt# check for mask then right shift without a parentheses
53757551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
53767551eb4fSHeinrich Schuchardt		    $line =~ /$LvalOrFunc\s*\&\s*($LvalOrFunc)\s*>>/ &&
53777551eb4fSHeinrich Schuchardt		    $4 !~ /^\&/) { # $LvalOrFunc may be &foo, ignore if so
53787551eb4fSHeinrich Schuchardt			WARN("MASK_THEN_SHIFT",
53797551eb4fSHeinrich Schuchardt			     "Possible precedence defect with mask then right shift - may need parentheses\n" . $herecurr);
53807551eb4fSHeinrich Schuchardt		}
53817551eb4fSHeinrich Schuchardt
53827551eb4fSHeinrich Schuchardt# check for pointer comparisons to NULL
53837551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0) {
53847551eb4fSHeinrich Schuchardt			while ($line =~ /\b$LvalOrFunc\s*(==|\!=)\s*NULL\b/g) {
53857551eb4fSHeinrich Schuchardt				my $val = $1;
53867551eb4fSHeinrich Schuchardt				my $equal = "!";
53877551eb4fSHeinrich Schuchardt				$equal = "" if ($4 eq "!=");
53887551eb4fSHeinrich Schuchardt				if (CHK("COMPARISON_TO_NULL",
53897551eb4fSHeinrich Schuchardt					"Comparison to NULL could be written \"${equal}${val}\"\n" . $herecurr) &&
53907551eb4fSHeinrich Schuchardt					    $fix) {
53917551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\b\Q$val\E\s*(?:==|\!=)\s*NULL\b/$equal$val/;
53927551eb4fSHeinrich Schuchardt				}
5393dd88ab32SMasahiro Yamada			}
5394dd88ab32SMasahiro Yamada		}
5395dd88ab32SMasahiro Yamada
53966b9709d9STom Rini# check for bad placement of section $InitAttribute (e.g.: __initdata)
53976b9709d9STom Rini		if ($line =~ /(\b$InitAttribute\b)/) {
53986b9709d9STom Rini			my $attr = $1;
53996b9709d9STom Rini			if ($line =~ /^\+\s*static\s+(?:const\s+)?(?:$attr\s+)?($NonptrTypeWithAttr)\s+(?:$attr\s+)?($Ident(?:\[[^]]*\])?)\s*[=;]/) {
54006b9709d9STom Rini				my $ptr = $1;
54016b9709d9STom Rini				my $var = $2;
54026b9709d9STom Rini				if ((($ptr =~ /\b(union|struct)\s+$attr\b/ &&
54036b9709d9STom Rini				      ERROR("MISPLACED_INIT",
54046b9709d9STom Rini					    "$attr should be placed after $var\n" . $herecurr)) ||
54056b9709d9STom Rini				     ($ptr !~ /\b(union|struct)\s+$attr\b/ &&
54066b9709d9STom Rini				      WARN("MISPLACED_INIT",
54076b9709d9STom Rini					   "$attr should be placed after $var\n" . $herecurr))) &&
54086b9709d9STom Rini				    $fix) {
54097551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/(\bstatic\s+(?:const\s+)?)(?:$attr\s+)?($NonptrTypeWithAttr)\s+(?:$attr\s+)?($Ident(?:\[[^]]*\])?)\s*([=;])\s*/"$1" . trim(string_find_replace($2, "\\s*$attr\\s*", " ")) . " " . trim(string_find_replace($3, "\\s*$attr\\s*", "")) . " $attr" . ("$4" eq ";" ? ";" : " = ")/e;
54106b9709d9STom Rini				}
54116b9709d9STom Rini			}
54126b9709d9STom Rini		}
54136b9709d9STom Rini
54146b9709d9STom Rini# check for $InitAttributeData (ie: __initdata) with const
54156b9709d9STom Rini		if ($line =~ /\bconst\b/ && $line =~ /($InitAttributeData)/) {
54166b9709d9STom Rini			my $attr = $1;
54176b9709d9STom Rini			$attr =~ /($InitAttributePrefix)(.*)/;
54186b9709d9STom Rini			my $attr_prefix = $1;
54196b9709d9STom Rini			my $attr_type = $2;
54206b9709d9STom Rini			if (ERROR("INIT_ATTRIBUTE",
54216b9709d9STom Rini				  "Use of const init definition must use ${attr_prefix}initconst\n" . $herecurr) &&
54226b9709d9STom Rini			    $fix) {
54237551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
54246b9709d9STom Rini				    s/$InitAttributeData/${attr_prefix}initconst/;
54256b9709d9STom Rini			}
54266b9709d9STom Rini		}
54276b9709d9STom Rini
54286b9709d9STom Rini# check for $InitAttributeConst (ie: __initconst) without const
54296b9709d9STom Rini		if ($line !~ /\bconst\b/ && $line =~ /($InitAttributeConst)/) {
54306b9709d9STom Rini			my $attr = $1;
54316b9709d9STom Rini			if (ERROR("INIT_ATTRIBUTE",
54326b9709d9STom Rini				  "Use of $attr requires a separate use of const\n" . $herecurr) &&
54336b9709d9STom Rini			    $fix) {
54347551eb4fSHeinrich Schuchardt				my $lead = $fixed[$fixlinenr] =~
54356b9709d9STom Rini				    /(^\+\s*(?:static\s+))/;
54366b9709d9STom Rini				$lead = rtrim($1);
54376b9709d9STom Rini				$lead = "$lead " if ($lead !~ /^\+$/);
54386b9709d9STom Rini				$lead = "${lead}const ";
54397551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/(^\+\s*(?:static\s+))/$lead/;
54407551eb4fSHeinrich Schuchardt			}
54417551eb4fSHeinrich Schuchardt		}
54427551eb4fSHeinrich Schuchardt
54437551eb4fSHeinrich Schuchardt# check for __read_mostly with const non-pointer (should just be const)
54447551eb4fSHeinrich Schuchardt		if ($line =~ /\b__read_mostly\b/ &&
54457551eb4fSHeinrich Schuchardt		    $line =~ /($Type)\s*$Ident/ && $1 !~ /\*\s*$/ && $1 =~ /\bconst\b/) {
54467551eb4fSHeinrich Schuchardt			if (ERROR("CONST_READ_MOSTLY",
54477551eb4fSHeinrich Schuchardt				  "Invalid use of __read_mostly with const type\n" . $herecurr) &&
54487551eb4fSHeinrich Schuchardt			    $fix) {
54497551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\s+__read_mostly\b//;
54507551eb4fSHeinrich Schuchardt			}
54517551eb4fSHeinrich Schuchardt		}
54527551eb4fSHeinrich Schuchardt
54537551eb4fSHeinrich Schuchardt# don't use __constant_<foo> functions outside of include/uapi/
54547551eb4fSHeinrich Schuchardt		if ($realfile !~ m@^include/uapi/@ &&
54557551eb4fSHeinrich Schuchardt		    $line =~ /(__constant_(?:htons|ntohs|[bl]e(?:16|32|64)_to_cpu|cpu_to_[bl]e(?:16|32|64)))\s*\(/) {
54567551eb4fSHeinrich Schuchardt			my $constant_func = $1;
54577551eb4fSHeinrich Schuchardt			my $func = $constant_func;
54587551eb4fSHeinrich Schuchardt			$func =~ s/^__constant_//;
54597551eb4fSHeinrich Schuchardt			if (WARN("CONSTANT_CONVERSION",
54607551eb4fSHeinrich Schuchardt				 "$constant_func should be $func\n" . $herecurr) &&
54617551eb4fSHeinrich Schuchardt			    $fix) {
54627551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\b$constant_func\b/$func/g;
54636b9709d9STom Rini			}
54646b9709d9STom Rini		}
54656b9709d9STom Rini
5466dd88ab32SMasahiro Yamada# prefer usleep_range over udelay
5467dd88ab32SMasahiro Yamada		if ($line =~ /\budelay\s*\(\s*(\d+)\s*\)/) {
54687551eb4fSHeinrich Schuchardt			my $delay = $1;
5469dd88ab32SMasahiro Yamada			# ignore udelay's < 10, however
54707551eb4fSHeinrich Schuchardt			if (! ($delay < 10) ) {
5471dd88ab32SMasahiro Yamada				CHK("USLEEP_RANGE",
54727551eb4fSHeinrich Schuchardt				    "usleep_range is preferred over udelay; see Documentation/timers/timers-howto.txt\n" . $herecurr);
54737551eb4fSHeinrich Schuchardt			}
54747551eb4fSHeinrich Schuchardt			if ($delay > 2000) {
54757551eb4fSHeinrich Schuchardt				WARN("LONG_UDELAY",
54767551eb4fSHeinrich Schuchardt				     "long udelay - prefer mdelay; see arch/arm/include/asm/delay.h\n" . $herecurr);
5477dd88ab32SMasahiro Yamada			}
5478dd88ab32SMasahiro Yamada		}
5479dd88ab32SMasahiro Yamada
5480dd88ab32SMasahiro Yamada# warn about unexpectedly long msleep's
5481dd88ab32SMasahiro Yamada		if ($line =~ /\bmsleep\s*\((\d+)\);/) {
5482dd88ab32SMasahiro Yamada			if ($1 < 20) {
5483dd88ab32SMasahiro Yamada				WARN("MSLEEP",
54847551eb4fSHeinrich Schuchardt				     "msleep < 20ms can sleep for up to 20ms; see Documentation/timers/timers-howto.txt\n" . $herecurr);
5485dd88ab32SMasahiro Yamada			}
5486dd88ab32SMasahiro Yamada		}
5487dd88ab32SMasahiro Yamada
54886b9709d9STom Rini# check for comparisons of jiffies
54896b9709d9STom Rini		if ($line =~ /\bjiffies\s*$Compare|$Compare\s*jiffies\b/) {
54906b9709d9STom Rini			WARN("JIFFIES_COMPARISON",
54916b9709d9STom Rini			     "Comparing jiffies is almost always wrong; prefer time_after, time_before and friends\n" . $herecurr);
54926b9709d9STom Rini		}
54936b9709d9STom Rini
54946b9709d9STom Rini# check for comparisons of get_jiffies_64()
54956b9709d9STom Rini		if ($line =~ /\bget_jiffies_64\s*\(\s*\)\s*$Compare|$Compare\s*get_jiffies_64\s*\(\s*\)/) {
54966b9709d9STom Rini			WARN("JIFFIES_COMPARISON",
54976b9709d9STom Rini			     "Comparing get_jiffies_64() is almost always wrong; prefer time_after64, time_before64 and friends\n" . $herecurr);
54986b9709d9STom Rini		}
54996b9709d9STom Rini
5500dd88ab32SMasahiro Yamada# warn about #ifdefs in C files
5501dd88ab32SMasahiro Yamada#		if ($line =~ /^.\s*\#\s*if(|n)def/ && ($realfile =~ /\.c$/)) {
5502dd88ab32SMasahiro Yamada#			print "#ifdef in C files should be avoided\n";
5503dd88ab32SMasahiro Yamada#			print "$herecurr";
5504dd88ab32SMasahiro Yamada#			$clean = 0;
5505dd88ab32SMasahiro Yamada#		}
5506dd88ab32SMasahiro Yamada
5507dd88ab32SMasahiro Yamada# warn about spacing in #ifdefs
5508dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*\#\s*(ifdef|ifndef|elif)\s\s+/) {
55096b9709d9STom Rini			if (ERROR("SPACING",
55106b9709d9STom Rini				  "exactly one space required after that #$1\n" . $herecurr) &&
55116b9709d9STom Rini			    $fix) {
55127551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~
55136b9709d9STom Rini				    s/^(.\s*\#\s*(ifdef|ifndef|elif))\s{2,}/$1 /;
55146b9709d9STom Rini			}
55156b9709d9STom Rini
5516dd88ab32SMasahiro Yamada		}
5517dd88ab32SMasahiro Yamada
5518dd88ab32SMasahiro Yamada# check for spinlock_t definitions without a comment.
5519dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*(struct\s+mutex|spinlock_t)\s+\S+;/ ||
5520dd88ab32SMasahiro Yamada		    $line =~ /^.\s*(DEFINE_MUTEX)\s*\(/) {
5521dd88ab32SMasahiro Yamada			my $which = $1;
5522dd88ab32SMasahiro Yamada			if (!ctx_has_comment($first_line, $linenr)) {
5523dd88ab32SMasahiro Yamada				CHK("UNCOMMENTED_DEFINITION",
5524dd88ab32SMasahiro Yamada				    "$1 definition without comment\n" . $herecurr);
5525dd88ab32SMasahiro Yamada			}
5526dd88ab32SMasahiro Yamada		}
5527dd88ab32SMasahiro Yamada# check for memory barriers without a comment.
55287551eb4fSHeinrich Schuchardt
55297551eb4fSHeinrich Schuchardt		my $barriers = qr{
55307551eb4fSHeinrich Schuchardt			mb|
55317551eb4fSHeinrich Schuchardt			rmb|
55327551eb4fSHeinrich Schuchardt			wmb|
55337551eb4fSHeinrich Schuchardt			read_barrier_depends
55347551eb4fSHeinrich Schuchardt		}x;
55357551eb4fSHeinrich Schuchardt		my $barrier_stems = qr{
55367551eb4fSHeinrich Schuchardt			mb__before_atomic|
55377551eb4fSHeinrich Schuchardt			mb__after_atomic|
55387551eb4fSHeinrich Schuchardt			store_release|
55397551eb4fSHeinrich Schuchardt			load_acquire|
55407551eb4fSHeinrich Schuchardt			store_mb|
55417551eb4fSHeinrich Schuchardt			(?:$barriers)
55427551eb4fSHeinrich Schuchardt		}x;
55437551eb4fSHeinrich Schuchardt		my $all_barriers = qr{
55447551eb4fSHeinrich Schuchardt			(?:$barriers)|
55457551eb4fSHeinrich Schuchardt			smp_(?:$barrier_stems)|
55467551eb4fSHeinrich Schuchardt			virt_(?:$barrier_stems)
55477551eb4fSHeinrich Schuchardt		}x;
55487551eb4fSHeinrich Schuchardt
55497551eb4fSHeinrich Schuchardt		if ($line =~ /\b(?:$all_barriers)\s*\(/) {
5550dd88ab32SMasahiro Yamada			if (!ctx_has_comment($first_line, $linenr)) {
55516b9709d9STom Rini				WARN("MEMORY_BARRIER",
5552dd88ab32SMasahiro Yamada				     "memory barrier without comment\n" . $herecurr);
5553dd88ab32SMasahiro Yamada			}
5554dd88ab32SMasahiro Yamada		}
55557551eb4fSHeinrich Schuchardt
55567551eb4fSHeinrich Schuchardt		my $underscore_smp_barriers = qr{__smp_(?:$barrier_stems)}x;
55577551eb4fSHeinrich Schuchardt
55587551eb4fSHeinrich Schuchardt		if ($realfile !~ m@^include/asm-generic/@ &&
55597551eb4fSHeinrich Schuchardt		    $realfile !~ m@/barrier\.h$@ &&
55607551eb4fSHeinrich Schuchardt		    $line =~ m/\b(?:$underscore_smp_barriers)\s*\(/ &&
55617551eb4fSHeinrich Schuchardt		    $line !~ m/^.\s*\#\s*define\s+(?:$underscore_smp_barriers)\s*\(/) {
55627551eb4fSHeinrich Schuchardt			WARN("MEMORY_BARRIER",
55637551eb4fSHeinrich Schuchardt			     "__smp memory barriers shouldn't be used outside barrier.h and asm-generic\n" . $herecurr);
55647551eb4fSHeinrich Schuchardt		}
55657551eb4fSHeinrich Schuchardt
55667551eb4fSHeinrich Schuchardt# check for waitqueue_active without a comment.
55677551eb4fSHeinrich Schuchardt		if ($line =~ /\bwaitqueue_active\s*\(/) {
55687551eb4fSHeinrich Schuchardt			if (!ctx_has_comment($first_line, $linenr)) {
55697551eb4fSHeinrich Schuchardt				WARN("WAITQUEUE_ACTIVE",
55707551eb4fSHeinrich Schuchardt				     "waitqueue_active without comment\n" . $herecurr);
55717551eb4fSHeinrich Schuchardt			}
55727551eb4fSHeinrich Schuchardt		}
55737551eb4fSHeinrich Schuchardt
5574dd88ab32SMasahiro Yamada# check of hardware specific defines
5575dd88ab32SMasahiro Yamada		if ($line =~ m@^.\s*\#\s*if.*\b(__i386__|__powerpc64__|__sun__|__s390x__)\b@ && $realfile !~ m@include/asm-@) {
5576dd88ab32SMasahiro Yamada			CHK("ARCH_DEFINES",
5577dd88ab32SMasahiro Yamada			    "architecture specific defines should be avoided\n" .  $herecurr);
5578dd88ab32SMasahiro Yamada		}
5579dd88ab32SMasahiro Yamada
55807551eb4fSHeinrich Schuchardt# check that the storage class is not after a type
55817551eb4fSHeinrich Schuchardt		if ($line =~ /\b($Type)\s+($Storage)\b/) {
5582dd88ab32SMasahiro Yamada			WARN("STORAGE_CLASS",
55837551eb4fSHeinrich Schuchardt			     "storage class '$2' should be located before type '$1'\n" . $herecurr);
55847551eb4fSHeinrich Schuchardt		}
55857551eb4fSHeinrich Schuchardt# Check that the storage class is at the beginning of a declaration
55867551eb4fSHeinrich Schuchardt		if ($line =~ /\b$Storage\b/ &&
55877551eb4fSHeinrich Schuchardt		    $line !~ /^.\s*$Storage/ &&
55887551eb4fSHeinrich Schuchardt		    $line =~ /^.\s*(.+?)\$Storage\s/ &&
55897551eb4fSHeinrich Schuchardt		    $1 !~ /[\,\)]\s*$/) {
55907551eb4fSHeinrich Schuchardt			WARN("STORAGE_CLASS",
55917551eb4fSHeinrich Schuchardt			     "storage class should be at the beginning of the declaration\n" . $herecurr);
5592dd88ab32SMasahiro Yamada		}
5593dd88ab32SMasahiro Yamada
5594dd88ab32SMasahiro Yamada# check the location of the inline attribute, that it is between
5595dd88ab32SMasahiro Yamada# storage class and type.
5596dd88ab32SMasahiro Yamada		if ($line =~ /\b$Type\s+$Inline\b/ ||
5597dd88ab32SMasahiro Yamada		    $line =~ /\b$Inline\s+$Storage\b/) {
5598dd88ab32SMasahiro Yamada			ERROR("INLINE_LOCATION",
5599dd88ab32SMasahiro Yamada			      "inline keyword should sit between storage class and type\n" . $herecurr);
5600dd88ab32SMasahiro Yamada		}
5601dd88ab32SMasahiro Yamada
5602dd88ab32SMasahiro Yamada# Check for __inline__ and __inline, prefer inline
56036b9709d9STom Rini		if ($realfile !~ m@\binclude/uapi/@ &&
56046b9709d9STom Rini		    $line =~ /\b(__inline__|__inline)\b/) {
56056b9709d9STom Rini			if (WARN("INLINE",
56066b9709d9STom Rini				 "plain inline is preferred over $1\n" . $herecurr) &&
56076b9709d9STom Rini			    $fix) {
56087551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\b(__inline__|__inline)\b/inline/;
56096b9709d9STom Rini
56106b9709d9STom Rini			}
5611dd88ab32SMasahiro Yamada		}
5612dd88ab32SMasahiro Yamada
5613dd88ab32SMasahiro Yamada# Check for __attribute__ packed, prefer __packed
56146b9709d9STom Rini		if ($realfile !~ m@\binclude/uapi/@ &&
56156b9709d9STom Rini		    $line =~ /\b__attribute__\s*\(\s*\(.*\bpacked\b/) {
5616dd88ab32SMasahiro Yamada			WARN("PREFER_PACKED",
5617dd88ab32SMasahiro Yamada			     "__packed is preferred over __attribute__((packed))\n" . $herecurr);
5618dd88ab32SMasahiro Yamada		}
5619dd88ab32SMasahiro Yamada
5620dd10e6c7SHeinrich Schuchardt# Check for new packed members, warn to use care
5621dd10e6c7SHeinrich Schuchardt		if ($realfile !~ m@\binclude/uapi/@ &&
5622dd10e6c7SHeinrich Schuchardt		    $line =~ /\b(__attribute__\s*\(\s*\(.*\bpacked|__packed)\b/) {
5623dd10e6c7SHeinrich Schuchardt			WARN("NEW_PACKED",
5624dd10e6c7SHeinrich Schuchardt			     "Adding new packed members is to be done with care\n" . $herecurr);
5625dd10e6c7SHeinrich Schuchardt		}
5626dd10e6c7SHeinrich Schuchardt
5627dd88ab32SMasahiro Yamada# Check for __attribute__ aligned, prefer __aligned
56286b9709d9STom Rini		if ($realfile !~ m@\binclude/uapi/@ &&
56296b9709d9STom Rini		    $line =~ /\b__attribute__\s*\(\s*\(.*aligned/) {
5630dd88ab32SMasahiro Yamada			WARN("PREFER_ALIGNED",
5631dd88ab32SMasahiro Yamada			     "__aligned(size) is preferred over __attribute__((aligned(size)))\n" . $herecurr);
5632dd88ab32SMasahiro Yamada		}
5633dd88ab32SMasahiro Yamada
5634dd88ab32SMasahiro Yamada# Check for __attribute__ format(printf, prefer __printf
56356b9709d9STom Rini		if ($realfile !~ m@\binclude/uapi/@ &&
56366b9709d9STom Rini		    $line =~ /\b__attribute__\s*\(\s*\(\s*format\s*\(\s*printf/) {
56376b9709d9STom Rini			if (WARN("PREFER_PRINTF",
56386b9709d9STom Rini				 "__printf(string-index, first-to-check) is preferred over __attribute__((format(printf, string-index, first-to-check)))\n" . $herecurr) &&
56396b9709d9STom Rini			    $fix) {
56407551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\b__attribute__\s*\(\s*\(\s*format\s*\(\s*printf\s*,\s*(.*)\)\s*\)\s*\)/"__printf(" . trim($1) . ")"/ex;
56416b9709d9STom Rini
56426b9709d9STom Rini			}
5643dd88ab32SMasahiro Yamada		}
5644dd88ab32SMasahiro Yamada
5645dd88ab32SMasahiro Yamada# Check for __attribute__ format(scanf, prefer __scanf
56466b9709d9STom Rini		if ($realfile !~ m@\binclude/uapi/@ &&
56476b9709d9STom Rini		    $line =~ /\b__attribute__\s*\(\s*\(\s*format\s*\(\s*scanf\b/) {
56486b9709d9STom Rini			if (WARN("PREFER_SCANF",
56496b9709d9STom Rini				 "__scanf(string-index, first-to-check) is preferred over __attribute__((format(scanf, string-index, first-to-check)))\n" . $herecurr) &&
56506b9709d9STom Rini			    $fix) {
56517551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\b__attribute__\s*\(\s*\(\s*format\s*\(\s*scanf\s*,\s*(.*)\)\s*\)\s*\)/"__scanf(" . trim($1) . ")"/ex;
56527551eb4fSHeinrich Schuchardt			}
56537551eb4fSHeinrich Schuchardt		}
56547551eb4fSHeinrich Schuchardt
56557551eb4fSHeinrich Schuchardt# Check for __attribute__ weak, or __weak declarations (may have link issues)
56567551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
56577551eb4fSHeinrich Schuchardt		    $line =~ /(?:$Declare|$DeclareMisordered)\s*$Ident\s*$balanced_parens\s*(?:$Attribute)?\s*;/ &&
56587551eb4fSHeinrich Schuchardt		    ($line =~ /\b__attribute__\s*\(\s*\(.*\bweak\b/ ||
56597551eb4fSHeinrich Schuchardt		     $line =~ /\b__weak\b/)) {
56607551eb4fSHeinrich Schuchardt			ERROR("WEAK_DECLARATION",
56617551eb4fSHeinrich Schuchardt			      "Using weak declarations can have unintended link defects\n" . $herecurr);
56627551eb4fSHeinrich Schuchardt		}
56637551eb4fSHeinrich Schuchardt
56647551eb4fSHeinrich Schuchardt# check for c99 types like uint8_t used outside of uapi/ and tools/
56657551eb4fSHeinrich Schuchardt		if ($realfile !~ m@\binclude/uapi/@ &&
56667551eb4fSHeinrich Schuchardt		    $realfile !~ m@\btools/@ &&
56677551eb4fSHeinrich Schuchardt		    $line =~ /\b($Declare)\s*$Ident\s*[=;,\[]/) {
56687551eb4fSHeinrich Schuchardt			my $type = $1;
56697551eb4fSHeinrich Schuchardt			if ($type =~ /\b($typeC99Typedefs)\b/) {
56707551eb4fSHeinrich Schuchardt				$type = $1;
56717551eb4fSHeinrich Schuchardt				my $kernel_type = 'u';
56727551eb4fSHeinrich Schuchardt				$kernel_type = 's' if ($type =~ /^_*[si]/);
56737551eb4fSHeinrich Schuchardt				$type =~ /(\d+)/;
56747551eb4fSHeinrich Schuchardt				$kernel_type .= $1;
56757551eb4fSHeinrich Schuchardt				if (CHK("PREFER_KERNEL_TYPES",
56767551eb4fSHeinrich Schuchardt					"Prefer kernel type '$kernel_type' over '$type'\n" . $herecurr) &&
56777551eb4fSHeinrich Schuchardt				    $fix) {
56787551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\b$type\b/$kernel_type/;
56797551eb4fSHeinrich Schuchardt				}
56807551eb4fSHeinrich Schuchardt			}
56817551eb4fSHeinrich Schuchardt		}
56827551eb4fSHeinrich Schuchardt
56837551eb4fSHeinrich Schuchardt# check for cast of C90 native int or longer types constants
56847551eb4fSHeinrich Schuchardt		if ($line =~ /(\(\s*$C90_int_types\s*\)\s*)($Constant)\b/) {
56857551eb4fSHeinrich Schuchardt			my $cast = $1;
56867551eb4fSHeinrich Schuchardt			my $const = $2;
56877551eb4fSHeinrich Schuchardt			if (WARN("TYPECAST_INT_CONSTANT",
56887551eb4fSHeinrich Schuchardt				 "Unnecessary typecast of c90 int constant\n" . $herecurr) &&
56897551eb4fSHeinrich Schuchardt			    $fix) {
56907551eb4fSHeinrich Schuchardt				my $suffix = "";
56917551eb4fSHeinrich Schuchardt				my $newconst = $const;
56927551eb4fSHeinrich Schuchardt				$newconst =~ s/${Int_type}$//;
56937551eb4fSHeinrich Schuchardt				$suffix .= 'U' if ($cast =~ /\bunsigned\b/);
56947551eb4fSHeinrich Schuchardt				if ($cast =~ /\blong\s+long\b/) {
56957551eb4fSHeinrich Schuchardt					$suffix .= 'LL';
56967551eb4fSHeinrich Schuchardt				} elsif ($cast =~ /\blong\b/) {
56977551eb4fSHeinrich Schuchardt					$suffix .= 'L';
56987551eb4fSHeinrich Schuchardt				}
56997551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\Q$cast\E$const\b/$newconst$suffix/;
57006b9709d9STom Rini			}
5701dd88ab32SMasahiro Yamada		}
5702dd88ab32SMasahiro Yamada
5703dd88ab32SMasahiro Yamada# check for sizeof(&)
5704dd88ab32SMasahiro Yamada		if ($line =~ /\bsizeof\s*\(\s*\&/) {
5705dd88ab32SMasahiro Yamada			WARN("SIZEOF_ADDRESS",
5706dd88ab32SMasahiro Yamada			     "sizeof(& should be avoided\n" . $herecurr);
5707dd88ab32SMasahiro Yamada		}
5708dd88ab32SMasahiro Yamada
5709dd88ab32SMasahiro Yamada# check for sizeof without parenthesis
5710dd88ab32SMasahiro Yamada		if ($line =~ /\bsizeof\s+((?:\*\s*|)$Lval|$Type(?:\s+$Lval|))/) {
57116b9709d9STom Rini			if (WARN("SIZEOF_PARENTHESIS",
57126b9709d9STom Rini				 "sizeof $1 should be sizeof($1)\n" . $herecurr) &&
57136b9709d9STom Rini			    $fix) {
57147551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\bsizeof\s+((?:\*\s*|)$Lval|$Type(?:\s+$Lval|))/"sizeof(" . trim($1) . ")"/ex;
57156b9709d9STom Rini			}
5716dd88ab32SMasahiro Yamada		}
5717dd88ab32SMasahiro Yamada
5718dd88ab32SMasahiro Yamada# check for struct spinlock declarations
5719dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*\bstruct\s+spinlock\s+\w+\s*;/) {
5720dd88ab32SMasahiro Yamada			WARN("USE_SPINLOCK_T",
5721dd88ab32SMasahiro Yamada			     "struct spinlock should be spinlock_t\n" . $herecurr);
5722dd88ab32SMasahiro Yamada		}
5723dd88ab32SMasahiro Yamada
57246b9709d9STom Rini# check for seq_printf uses that could be seq_puts
57256b9709d9STom Rini		if ($sline =~ /\bseq_printf\s*\(.*"\s*\)\s*;\s*$/) {
57266b9709d9STom Rini			my $fmt = get_quoted_string($line, $rawline);
57277551eb4fSHeinrich Schuchardt			$fmt =~ s/%%//g;
57287551eb4fSHeinrich Schuchardt			if ($fmt !~ /%/) {
57296b9709d9STom Rini				if (WARN("PREFER_SEQ_PUTS",
57306b9709d9STom Rini					 "Prefer seq_puts to seq_printf\n" . $herecurr) &&
57316b9709d9STom Rini				    $fix) {
57327551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\bseq_printf\b/seq_puts/;
57336b9709d9STom Rini				}
57346b9709d9STom Rini			}
57356b9709d9STom Rini		}
57366b9709d9STom Rini
57377551eb4fSHeinrich Schuchardt		# check for vsprintf extension %p<foo> misuses
57387551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
57397551eb4fSHeinrich Schuchardt		    defined $stat &&
57407551eb4fSHeinrich Schuchardt		    $stat =~ /^\+(?![^\{]*\{\s*).*\b(\w+)\s*\(.*$String\s*,/s &&
57417551eb4fSHeinrich Schuchardt		    $1 !~ /^_*volatile_*$/) {
57427551eb4fSHeinrich Schuchardt			my $bad_extension = "";
57437551eb4fSHeinrich Schuchardt			my $lc = $stat =~ tr@\n@@;
57447551eb4fSHeinrich Schuchardt			$lc = $lc + $linenr;
57457551eb4fSHeinrich Schuchardt		        for (my $count = $linenr; $count <= $lc; $count++) {
57467551eb4fSHeinrich Schuchardt				my $fmt = get_quoted_string($lines[$count - 1], raw_line($count, 0));
57477551eb4fSHeinrich Schuchardt				$fmt =~ s/%%//g;
57487551eb4fSHeinrich Schuchardt				if ($fmt =~ /(\%[\*\d\.]*p(?![\WFfSsBKRraEhMmIiUDdgVCbGNO]).)/) {
57497551eb4fSHeinrich Schuchardt					$bad_extension = $1;
57507551eb4fSHeinrich Schuchardt					last;
57517551eb4fSHeinrich Schuchardt				}
57527551eb4fSHeinrich Schuchardt			}
57537551eb4fSHeinrich Schuchardt			if ($bad_extension ne "") {
57547551eb4fSHeinrich Schuchardt				my $stat_real = raw_line($linenr, 0);
57557551eb4fSHeinrich Schuchardt				for (my $count = $linenr + 1; $count <= $lc; $count++) {
57567551eb4fSHeinrich Schuchardt					$stat_real = $stat_real . "\n" . raw_line($count, 0);
57577551eb4fSHeinrich Schuchardt				}
57587551eb4fSHeinrich Schuchardt				WARN("VSPRINTF_POINTER_EXTENSION",
57597551eb4fSHeinrich Schuchardt				     "Invalid vsprintf pointer extension '$bad_extension'\n" . "$here\n$stat_real\n");
57607551eb4fSHeinrich Schuchardt			}
57617551eb4fSHeinrich Schuchardt		}
57627551eb4fSHeinrich Schuchardt
5763dd88ab32SMasahiro Yamada# Check for misused memsets
5764dd88ab32SMasahiro Yamada		if ($^V && $^V ge 5.10.0 &&
5765dd88ab32SMasahiro Yamada		    defined $stat &&
57667551eb4fSHeinrich Schuchardt		    $stat =~ /^\+(?:.*?)\bmemset\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*\,\s*$FuncArg\s*\)/) {
5767dd88ab32SMasahiro Yamada
5768dd88ab32SMasahiro Yamada			my $ms_addr = $2;
5769dd88ab32SMasahiro Yamada			my $ms_val = $7;
5770dd88ab32SMasahiro Yamada			my $ms_size = $12;
5771dd88ab32SMasahiro Yamada
5772dd88ab32SMasahiro Yamada			if ($ms_size =~ /^(0x|)0$/i) {
5773dd88ab32SMasahiro Yamada				ERROR("MEMSET",
5774dd88ab32SMasahiro Yamada				      "memset to 0's uses 0 as the 2nd argument, not the 3rd\n" . "$here\n$stat\n");
5775dd88ab32SMasahiro Yamada			} elsif ($ms_size =~ /^(0x|)1$/i) {
5776dd88ab32SMasahiro Yamada				WARN("MEMSET",
5777dd88ab32SMasahiro Yamada				     "single byte memset is suspicious. Swapped 2nd/3rd argument?\n" . "$here\n$stat\n");
5778dd88ab32SMasahiro Yamada			}
5779dd88ab32SMasahiro Yamada		}
5780dd88ab32SMasahiro Yamada
57816b9709d9STom Rini# Check for memcpy(foo, bar, ETH_ALEN) that could be ether_addr_copy(foo, bar)
57827551eb4fSHeinrich Schuchardt#		if ($^V && $^V ge 5.10.0 &&
57837551eb4fSHeinrich Schuchardt#		    defined $stat &&
57847551eb4fSHeinrich Schuchardt#		    $stat =~ /^\+(?:.*?)\bmemcpy\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*\,\s*ETH_ALEN\s*\)/) {
57857551eb4fSHeinrich Schuchardt#			if (WARN("PREFER_ETHER_ADDR_COPY",
57867551eb4fSHeinrich Schuchardt#				 "Prefer ether_addr_copy() over memcpy() if the Ethernet addresses are __aligned(2)\n" . "$here\n$stat\n") &&
57877551eb4fSHeinrich Schuchardt#			    $fix) {
57887551eb4fSHeinrich Schuchardt#				$fixed[$fixlinenr] =~ s/\bmemcpy\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*\,\s*ETH_ALEN\s*\)/ether_addr_copy($2, $7)/;
57897551eb4fSHeinrich Schuchardt#			}
57907551eb4fSHeinrich Schuchardt#		}
57917551eb4fSHeinrich Schuchardt
57927551eb4fSHeinrich Schuchardt# Check for memcmp(foo, bar, ETH_ALEN) that could be ether_addr_equal*(foo, bar)
57937551eb4fSHeinrich Schuchardt#		if ($^V && $^V ge 5.10.0 &&
57947551eb4fSHeinrich Schuchardt#		    defined $stat &&
57957551eb4fSHeinrich Schuchardt#		    $stat =~ /^\+(?:.*?)\bmemcmp\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*\,\s*ETH_ALEN\s*\)/) {
57967551eb4fSHeinrich Schuchardt#			WARN("PREFER_ETHER_ADDR_EQUAL",
57977551eb4fSHeinrich Schuchardt#			     "Prefer ether_addr_equal() or ether_addr_equal_unaligned() over memcmp()\n" . "$here\n$stat\n")
57987551eb4fSHeinrich Schuchardt#		}
57997551eb4fSHeinrich Schuchardt
58007551eb4fSHeinrich Schuchardt# check for memset(foo, 0x0, ETH_ALEN) that could be eth_zero_addr
58017551eb4fSHeinrich Schuchardt# check for memset(foo, 0xFF, ETH_ALEN) that could be eth_broadcast_addr
58027551eb4fSHeinrich Schuchardt#		if ($^V && $^V ge 5.10.0 &&
58037551eb4fSHeinrich Schuchardt#		    defined $stat &&
58047551eb4fSHeinrich Schuchardt#		    $stat =~ /^\+(?:.*?)\bmemset\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*\,\s*ETH_ALEN\s*\)/) {
58057551eb4fSHeinrich Schuchardt#
58067551eb4fSHeinrich Schuchardt#			my $ms_val = $7;
58077551eb4fSHeinrich Schuchardt#
58087551eb4fSHeinrich Schuchardt#			if ($ms_val =~ /^(?:0x|)0+$/i) {
58097551eb4fSHeinrich Schuchardt#				if (WARN("PREFER_ETH_ZERO_ADDR",
58107551eb4fSHeinrich Schuchardt#					 "Prefer eth_zero_addr over memset()\n" . "$here\n$stat\n") &&
58117551eb4fSHeinrich Schuchardt#				    $fix) {
58127551eb4fSHeinrich Schuchardt#					$fixed[$fixlinenr] =~ s/\bmemset\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*,\s*ETH_ALEN\s*\)/eth_zero_addr($2)/;
58137551eb4fSHeinrich Schuchardt#				}
58147551eb4fSHeinrich Schuchardt#			} elsif ($ms_val =~ /^(?:0xff|255)$/i) {
58157551eb4fSHeinrich Schuchardt#				if (WARN("PREFER_ETH_BROADCAST_ADDR",
58167551eb4fSHeinrich Schuchardt#					 "Prefer eth_broadcast_addr() over memset()\n" . "$here\n$stat\n") &&
58177551eb4fSHeinrich Schuchardt#				    $fix) {
58187551eb4fSHeinrich Schuchardt#					$fixed[$fixlinenr] =~ s/\bmemset\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*,\s*ETH_ALEN\s*\)/eth_broadcast_addr($2)/;
58197551eb4fSHeinrich Schuchardt#				}
58207551eb4fSHeinrich Schuchardt#			}
58217551eb4fSHeinrich Schuchardt#		}
58226b9709d9STom Rini
5823dd88ab32SMasahiro Yamada# typecasts on min/max could be min_t/max_t
5824dd88ab32SMasahiro Yamada		if ($^V && $^V ge 5.10.0 &&
5825dd88ab32SMasahiro Yamada		    defined $stat &&
5826dd88ab32SMasahiro Yamada		    $stat =~ /^\+(?:.*?)\b(min|max)\s*\(\s*$FuncArg\s*,\s*$FuncArg\s*\)/) {
5827dd88ab32SMasahiro Yamada			if (defined $2 || defined $7) {
5828dd88ab32SMasahiro Yamada				my $call = $1;
5829dd88ab32SMasahiro Yamada				my $cast1 = deparenthesize($2);
5830dd88ab32SMasahiro Yamada				my $arg1 = $3;
5831dd88ab32SMasahiro Yamada				my $cast2 = deparenthesize($7);
5832dd88ab32SMasahiro Yamada				my $arg2 = $8;
5833dd88ab32SMasahiro Yamada				my $cast;
5834dd88ab32SMasahiro Yamada
5835dd88ab32SMasahiro Yamada				if ($cast1 ne "" && $cast2 ne "" && $cast1 ne $cast2) {
5836dd88ab32SMasahiro Yamada					$cast = "$cast1 or $cast2";
5837dd88ab32SMasahiro Yamada				} elsif ($cast1 ne "") {
5838dd88ab32SMasahiro Yamada					$cast = $cast1;
5839dd88ab32SMasahiro Yamada				} else {
5840dd88ab32SMasahiro Yamada					$cast = $cast2;
5841dd88ab32SMasahiro Yamada				}
5842dd88ab32SMasahiro Yamada				WARN("MINMAX",
5843dd88ab32SMasahiro Yamada				     "$call() should probably be ${call}_t($cast, $arg1, $arg2)\n" . "$here\n$stat\n");
5844dd88ab32SMasahiro Yamada			}
5845dd88ab32SMasahiro Yamada		}
5846dd88ab32SMasahiro Yamada
5847dd88ab32SMasahiro Yamada# check usleep_range arguments
5848dd88ab32SMasahiro Yamada		if ($^V && $^V ge 5.10.0 &&
5849dd88ab32SMasahiro Yamada		    defined $stat &&
5850dd88ab32SMasahiro Yamada		    $stat =~ /^\+(?:.*?)\busleep_range\s*\(\s*($FuncArg)\s*,\s*($FuncArg)\s*\)/) {
5851dd88ab32SMasahiro Yamada			my $min = $1;
5852dd88ab32SMasahiro Yamada			my $max = $7;
5853dd88ab32SMasahiro Yamada			if ($min eq $max) {
5854dd88ab32SMasahiro Yamada				WARN("USLEEP_RANGE",
5855dd88ab32SMasahiro Yamada				     "usleep_range should not use min == max args; see Documentation/timers/timers-howto.txt\n" . "$here\n$stat\n");
5856dd88ab32SMasahiro Yamada			} elsif ($min =~ /^\d+$/ && $max =~ /^\d+$/ &&
5857dd88ab32SMasahiro Yamada				 $min > $max) {
5858dd88ab32SMasahiro Yamada				WARN("USLEEP_RANGE",
5859dd88ab32SMasahiro Yamada				     "usleep_range args reversed, use min then max; see Documentation/timers/timers-howto.txt\n" . "$here\n$stat\n");
5860dd88ab32SMasahiro Yamada			}
5861dd88ab32SMasahiro Yamada		}
5862dd88ab32SMasahiro Yamada
58636b9709d9STom Rini# check for naked sscanf
58646b9709d9STom Rini		if ($^V && $^V ge 5.10.0 &&
58656b9709d9STom Rini		    defined $stat &&
58667551eb4fSHeinrich Schuchardt		    $line =~ /\bsscanf\b/ &&
58676b9709d9STom Rini		    ($stat !~ /$Ident\s*=\s*sscanf\s*$balanced_parens/ &&
58686b9709d9STom Rini		     $stat !~ /\bsscanf\s*$balanced_parens\s*(?:$Compare)/ &&
58696b9709d9STom Rini		     $stat !~ /(?:$Compare)\s*\bsscanf\s*$balanced_parens/)) {
58706b9709d9STom Rini			my $lc = $stat =~ tr@\n@@;
58716b9709d9STom Rini			$lc = $lc + $linenr;
58726b9709d9STom Rini			my $stat_real = raw_line($linenr, 0);
58736b9709d9STom Rini		        for (my $count = $linenr + 1; $count <= $lc; $count++) {
58746b9709d9STom Rini				$stat_real = $stat_real . "\n" . raw_line($count, 0);
58756b9709d9STom Rini			}
58766b9709d9STom Rini			WARN("NAKED_SSCANF",
58776b9709d9STom Rini			     "unchecked sscanf return value\n" . "$here\n$stat_real\n");
58786b9709d9STom Rini		}
58796b9709d9STom Rini
58807551eb4fSHeinrich Schuchardt# check for simple sscanf that should be kstrto<foo>
58817551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
58827551eb4fSHeinrich Schuchardt		    defined $stat &&
58837551eb4fSHeinrich Schuchardt		    $line =~ /\bsscanf\b/) {
58847551eb4fSHeinrich Schuchardt			my $lc = $stat =~ tr@\n@@;
58857551eb4fSHeinrich Schuchardt			$lc = $lc + $linenr;
58867551eb4fSHeinrich Schuchardt			my $stat_real = raw_line($linenr, 0);
58877551eb4fSHeinrich Schuchardt		        for (my $count = $linenr + 1; $count <= $lc; $count++) {
58887551eb4fSHeinrich Schuchardt				$stat_real = $stat_real . "\n" . raw_line($count, 0);
58897551eb4fSHeinrich Schuchardt			}
58907551eb4fSHeinrich Schuchardt			if ($stat_real =~ /\bsscanf\b\s*\(\s*$FuncArg\s*,\s*("[^"]+")/) {
58917551eb4fSHeinrich Schuchardt				my $format = $6;
58927551eb4fSHeinrich Schuchardt				my $count = $format =~ tr@%@%@;
58937551eb4fSHeinrich Schuchardt				if ($count == 1 &&
58947551eb4fSHeinrich Schuchardt				    $format =~ /^"\%(?i:ll[udxi]|[udxi]ll|ll|[hl]h?[udxi]|[udxi][hl]h?|[hl]h?|[udxi])"$/) {
58957551eb4fSHeinrich Schuchardt					WARN("SSCANF_TO_KSTRTO",
58967551eb4fSHeinrich Schuchardt					     "Prefer kstrto<type> to single variable sscanf\n" . "$here\n$stat_real\n");
58977551eb4fSHeinrich Schuchardt				}
58987551eb4fSHeinrich Schuchardt			}
58997551eb4fSHeinrich Schuchardt		}
59007551eb4fSHeinrich Schuchardt
59016b9709d9STom Rini# check for new externs in .h files.
59026b9709d9STom Rini		if ($realfile =~ /\.h$/ &&
59036b9709d9STom Rini		    $line =~ /^\+\s*(extern\s+)$Type\s*$Ident\s*\(/s) {
59046b9709d9STom Rini			if (CHK("AVOID_EXTERNS",
59056b9709d9STom Rini				"extern prototypes should be avoided in .h files\n" . $herecurr) &&
59066b9709d9STom Rini			    $fix) {
59077551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/(.*)\bextern\b\s*(.*)/$1$2/;
59086b9709d9STom Rini			}
59096b9709d9STom Rini		}
59106b9709d9STom Rini
5911dd88ab32SMasahiro Yamada# check for new externs in .c files.
5912dd88ab32SMasahiro Yamada		if ($realfile =~ /\.c$/ && defined $stat &&
5913dd88ab32SMasahiro Yamada		    $stat =~ /^.\s*(?:extern\s+)?$Type\s+($Ident)(\s*)\(/s)
5914dd88ab32SMasahiro Yamada		{
5915dd88ab32SMasahiro Yamada			my $function_name = $1;
5916dd88ab32SMasahiro Yamada			my $paren_space = $2;
5917dd88ab32SMasahiro Yamada
5918dd88ab32SMasahiro Yamada			my $s = $stat;
5919dd88ab32SMasahiro Yamada			if (defined $cond) {
5920dd88ab32SMasahiro Yamada				substr($s, 0, length($cond), '');
5921dd88ab32SMasahiro Yamada			}
5922dd88ab32SMasahiro Yamada			if ($s =~ /^\s*;/ &&
5923dd88ab32SMasahiro Yamada			    $function_name ne 'uninitialized_var')
5924dd88ab32SMasahiro Yamada			{
5925dd88ab32SMasahiro Yamada				WARN("AVOID_EXTERNS",
5926dd88ab32SMasahiro Yamada				     "externs should be avoided in .c files\n" .  $herecurr);
5927dd88ab32SMasahiro Yamada			}
5928dd88ab32SMasahiro Yamada
5929dd88ab32SMasahiro Yamada			if ($paren_space =~ /\n/) {
5930dd88ab32SMasahiro Yamada				WARN("FUNCTION_ARGUMENTS",
5931dd88ab32SMasahiro Yamada				     "arguments for function declarations should follow identifier\n" . $herecurr);
5932dd88ab32SMasahiro Yamada			}
5933dd88ab32SMasahiro Yamada
5934dd88ab32SMasahiro Yamada		} elsif ($realfile =~ /\.c$/ && defined $stat &&
5935dd88ab32SMasahiro Yamada		    $stat =~ /^.\s*extern\s+/)
5936dd88ab32SMasahiro Yamada		{
5937dd88ab32SMasahiro Yamada			WARN("AVOID_EXTERNS",
5938dd88ab32SMasahiro Yamada			     "externs should be avoided in .c files\n" .  $herecurr);
5939dd88ab32SMasahiro Yamada		}
5940dd88ab32SMasahiro Yamada
59417551eb4fSHeinrich Schuchardt# check for function declarations that have arguments without identifier names
59427551eb4fSHeinrich Schuchardt		if (defined $stat &&
59437551eb4fSHeinrich Schuchardt		    $stat =~ /^.\s*(?:extern\s+)?$Type\s*$Ident\s*\(\s*([^{]+)\s*\)\s*;/s &&
59447551eb4fSHeinrich Schuchardt		    $1 ne "void") {
59457551eb4fSHeinrich Schuchardt			my $args = trim($1);
59467551eb4fSHeinrich Schuchardt			while ($args =~ m/\s*($Type\s*(?:$Ident|\(\s*\*\s*$Ident?\s*\)\s*$balanced_parens)?)/g) {
59477551eb4fSHeinrich Schuchardt				my $arg = trim($1);
59487551eb4fSHeinrich Schuchardt				if ($arg =~ /^$Type$/ && $arg !~ /enum\s+$Ident$/) {
59497551eb4fSHeinrich Schuchardt					WARN("FUNCTION_ARGUMENTS",
59507551eb4fSHeinrich Schuchardt					     "function definition argument '$arg' should also have an identifier name\n" . $herecurr);
59517551eb4fSHeinrich Schuchardt				}
59527551eb4fSHeinrich Schuchardt			}
59537551eb4fSHeinrich Schuchardt		}
59547551eb4fSHeinrich Schuchardt
59557551eb4fSHeinrich Schuchardt# check for function definitions
59567551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
59577551eb4fSHeinrich Schuchardt		    defined $stat &&
59587551eb4fSHeinrich Schuchardt		    $stat =~ /^.\s*(?:$Storage\s+)?$Type\s*($Ident)\s*$balanced_parens\s*{/s) {
59597551eb4fSHeinrich Schuchardt			$context_function = $1;
59607551eb4fSHeinrich Schuchardt
59617551eb4fSHeinrich Schuchardt# check for multiline function definition with misplaced open brace
59627551eb4fSHeinrich Schuchardt			my $ok = 0;
59637551eb4fSHeinrich Schuchardt			my $cnt = statement_rawlines($stat);
59647551eb4fSHeinrich Schuchardt			my $herectx = $here . "\n";
59657551eb4fSHeinrich Schuchardt			for (my $n = 0; $n < $cnt; $n++) {
59667551eb4fSHeinrich Schuchardt				my $rl = raw_line($linenr, $n);
59677551eb4fSHeinrich Schuchardt				$herectx .=  $rl . "\n";
59687551eb4fSHeinrich Schuchardt				$ok = 1 if ($rl =~ /^[ \+]\{/);
59697551eb4fSHeinrich Schuchardt				$ok = 1 if ($rl =~ /\{/ && $n == 0);
59707551eb4fSHeinrich Schuchardt				last if $rl =~ /^[ \+].*\{/;
59717551eb4fSHeinrich Schuchardt			}
59727551eb4fSHeinrich Schuchardt			if (!$ok) {
59737551eb4fSHeinrich Schuchardt				ERROR("OPEN_BRACE",
59747551eb4fSHeinrich Schuchardt				      "open brace '{' following function definitions go on the next line\n" . $herectx);
59757551eb4fSHeinrich Schuchardt			}
59767551eb4fSHeinrich Schuchardt		}
59777551eb4fSHeinrich Schuchardt
5978dd88ab32SMasahiro Yamada# checks for new __setup's
5979dd88ab32SMasahiro Yamada		if ($rawline =~ /\b__setup\("([^"]*)"/) {
5980dd88ab32SMasahiro Yamada			my $name = $1;
5981dd88ab32SMasahiro Yamada
5982dd88ab32SMasahiro Yamada			if (!grep(/$name/, @setup_docs)) {
5983dd88ab32SMasahiro Yamada				CHK("UNDOCUMENTED_SETUP",
59847551eb4fSHeinrich Schuchardt				    "__setup appears un-documented -- check Documentation/admin-guide/kernel-parameters.rst\n" . $herecurr);
5985dd88ab32SMasahiro Yamada			}
5986dd88ab32SMasahiro Yamada		}
5987dd88ab32SMasahiro Yamada
5988dd88ab32SMasahiro Yamada# check for pointless casting of kmalloc return
5989dd88ab32SMasahiro Yamada		if ($line =~ /\*\s*\)\s*[kv][czm]alloc(_node){0,1}\b/) {
5990dd88ab32SMasahiro Yamada			WARN("UNNECESSARY_CASTS",
5991dd88ab32SMasahiro Yamada			     "unnecessary cast may hide bugs, see http://c-faq.com/malloc/mallocnocast.html\n" . $herecurr);
5992dd88ab32SMasahiro Yamada		}
5993dd88ab32SMasahiro Yamada
59946b9709d9STom Rini# alloc style
59956b9709d9STom Rini# p = alloc(sizeof(struct foo), ...) should be p = alloc(sizeof(*p), ...)
59966b9709d9STom Rini		if ($^V && $^V ge 5.10.0 &&
59976b9709d9STom Rini		    $line =~ /\b($Lval)\s*\=\s*(?:$balanced_parens)?\s*([kv][mz]alloc(?:_node)?)\s*\(\s*(sizeof\s*\(\s*struct\s+$Lval\s*\))/) {
59986b9709d9STom Rini			CHK("ALLOC_SIZEOF_STRUCT",
59996b9709d9STom Rini			    "Prefer $3(sizeof(*$1)...) over $3($4...)\n" . $herecurr);
60006b9709d9STom Rini		}
60016b9709d9STom Rini
60027551eb4fSHeinrich Schuchardt# check for k[mz]alloc with multiplies that could be kmalloc_array/kcalloc
60037551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
60047551eb4fSHeinrich Schuchardt		    defined $stat &&
60057551eb4fSHeinrich Schuchardt		    $stat =~ /^\+\s*($Lval)\s*\=\s*(?:$balanced_parens)?\s*(k[mz]alloc)\s*\(\s*($FuncArg)\s*\*\s*($FuncArg)\s*,/) {
60067551eb4fSHeinrich Schuchardt			my $oldfunc = $3;
60077551eb4fSHeinrich Schuchardt			my $a1 = $4;
60087551eb4fSHeinrich Schuchardt			my $a2 = $10;
60097551eb4fSHeinrich Schuchardt			my $newfunc = "kmalloc_array";
60107551eb4fSHeinrich Schuchardt			$newfunc = "kcalloc" if ($oldfunc eq "kzalloc");
60117551eb4fSHeinrich Schuchardt			my $r1 = $a1;
60127551eb4fSHeinrich Schuchardt			my $r2 = $a2;
60137551eb4fSHeinrich Schuchardt			if ($a1 =~ /^sizeof\s*\S/) {
60147551eb4fSHeinrich Schuchardt				$r1 = $a2;
60157551eb4fSHeinrich Schuchardt				$r2 = $a1;
60167551eb4fSHeinrich Schuchardt			}
60177551eb4fSHeinrich Schuchardt			if ($r1 !~ /^sizeof\b/ && $r2 =~ /^sizeof\s*\S/ &&
60187551eb4fSHeinrich Schuchardt			    !($r1 =~ /^$Constant$/ || $r1 =~ /^[A-Z_][A-Z0-9_]*$/)) {
60197551eb4fSHeinrich Schuchardt				my $ctx = '';
60207551eb4fSHeinrich Schuchardt				my $herectx = $here . "\n";
60217551eb4fSHeinrich Schuchardt				my $cnt = statement_rawlines($stat);
60227551eb4fSHeinrich Schuchardt				for (my $n = 0; $n < $cnt; $n++) {
60237551eb4fSHeinrich Schuchardt					$herectx .= raw_line($linenr, $n) . "\n";
60247551eb4fSHeinrich Schuchardt				}
60257551eb4fSHeinrich Schuchardt				if (WARN("ALLOC_WITH_MULTIPLY",
60267551eb4fSHeinrich Schuchardt					 "Prefer $newfunc over $oldfunc with multiply\n" . $herectx) &&
60277551eb4fSHeinrich Schuchardt				    $cnt == 1 &&
60287551eb4fSHeinrich Schuchardt				    $fix) {
60297551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\b($Lval)\s*\=\s*(?:$balanced_parens)?\s*(k[mz]alloc)\s*\(\s*($FuncArg)\s*\*\s*($FuncArg)/$1 . ' = ' . "$newfunc(" . trim($r1) . ', ' . trim($r2)/e;
60307551eb4fSHeinrich Schuchardt				}
60317551eb4fSHeinrich Schuchardt			}
60327551eb4fSHeinrich Schuchardt		}
60337551eb4fSHeinrich Schuchardt
60346b9709d9STom Rini# check for krealloc arg reuse
60356b9709d9STom Rini		if ($^V && $^V ge 5.10.0 &&
60366b9709d9STom Rini		    $line =~ /\b($Lval)\s*\=\s*(?:$balanced_parens)?\s*krealloc\s*\(\s*\1\s*,/) {
60376b9709d9STom Rini			WARN("KREALLOC_ARG_REUSE",
60386b9709d9STom Rini			     "Reusing the krealloc arg is almost always a bug\n" . $herecurr);
60396b9709d9STom Rini		}
60406b9709d9STom Rini
6041dd88ab32SMasahiro Yamada# check for alloc argument mismatch
6042dd88ab32SMasahiro Yamada		if ($line =~ /\b(kcalloc|kmalloc_array)\s*\(\s*sizeof\b/) {
6043dd88ab32SMasahiro Yamada			WARN("ALLOC_ARRAY_ARGS",
6044dd88ab32SMasahiro Yamada			     "$1 uses number as first arg, sizeof is generally wrong\n" . $herecurr);
6045dd88ab32SMasahiro Yamada		}
6046dd88ab32SMasahiro Yamada
6047dd88ab32SMasahiro Yamada# check for multiple semicolons
6048dd88ab32SMasahiro Yamada		if ($line =~ /;\s*;\s*$/) {
60496b9709d9STom Rini			if (WARN("ONE_SEMICOLON",
60506b9709d9STom Rini				 "Statements terminations use 1 semicolon\n" . $herecurr) &&
60516b9709d9STom Rini			    $fix) {
60527551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/(\s*;\s*){2,}$/;/g;
60537551eb4fSHeinrich Schuchardt			}
60547551eb4fSHeinrich Schuchardt		}
60557551eb4fSHeinrich Schuchardt
60567551eb4fSHeinrich Schuchardt# check for #defines like: 1 << <digit> that could be BIT(digit), it is not exported to uapi
60577551eb4fSHeinrich Schuchardt		if ($realfile !~ m@^include/uapi/@ &&
60587551eb4fSHeinrich Schuchardt		    $line =~ /#\s*define\s+\w+\s+\(?\s*1\s*([ulUL]*)\s*\<\<\s*(?:\d+|$Ident)\s*\)?/) {
60597551eb4fSHeinrich Schuchardt			my $ull = "";
60607551eb4fSHeinrich Schuchardt			$ull = "_ULL" if (defined($1) && $1 =~ /ll/i);
60617551eb4fSHeinrich Schuchardt			if (CHK("BIT_MACRO",
60627551eb4fSHeinrich Schuchardt				"Prefer using the BIT$ull macro\n" . $herecurr) &&
60637551eb4fSHeinrich Schuchardt			    $fix) {
60647551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\(?\s*1\s*[ulUL]*\s*<<\s*(\d+|$Ident)\s*\)?/BIT${ull}($1)/;
60657551eb4fSHeinrich Schuchardt			}
60667551eb4fSHeinrich Schuchardt		}
60677551eb4fSHeinrich Schuchardt
60687551eb4fSHeinrich Schuchardt# check for #if defined CONFIG_<FOO> || defined CONFIG_<FOO>_MODULE
60697551eb4fSHeinrich Schuchardt		if ($line =~ /^\+\s*#\s*if\s+defined(?:\s*\(?\s*|\s+)(CONFIG_[A-Z_]+)\s*\)?\s*\|\|\s*defined(?:\s*\(?\s*|\s+)\1_MODULE\s*\)?\s*$/) {
60707551eb4fSHeinrich Schuchardt			my $config = $1;
60717551eb4fSHeinrich Schuchardt			if (WARN("PREFER_IS_ENABLED",
60727551eb4fSHeinrich Schuchardt				 "Prefer IS_ENABLED(<FOO>) to CONFIG_<FOO> || CONFIG_<FOO>_MODULE\n" . $herecurr) &&
60737551eb4fSHeinrich Schuchardt			    $fix) {
60747551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] = "\+#if IS_ENABLED($config)";
60756b9709d9STom Rini			}
60766b9709d9STom Rini		}
60776b9709d9STom Rini
6078fc0b5948SRobert P. J. Day# check for case / default statements not preceded by break/fallthrough/switch
60796b9709d9STom Rini		if ($line =~ /^.\s*(?:case\s+(?:$Ident|$Constant)\s*|default):/) {
60806b9709d9STom Rini			my $has_break = 0;
60816b9709d9STom Rini			my $has_statement = 0;
60826b9709d9STom Rini			my $count = 0;
60836b9709d9STom Rini			my $prevline = $linenr;
60847551eb4fSHeinrich Schuchardt			while ($prevline > 1 && ($file || $count < 3) && !$has_break) {
60856b9709d9STom Rini				$prevline--;
60866b9709d9STom Rini				my $rline = $rawlines[$prevline - 1];
60876b9709d9STom Rini				my $fline = $lines[$prevline - 1];
60886b9709d9STom Rini				last if ($fline =~ /^\@\@/);
60896b9709d9STom Rini				next if ($fline =~ /^\-/);
60906b9709d9STom Rini				next if ($fline =~ /^.(?:\s*(?:case\s+(?:$Ident|$Constant)[\s$;]*|default):[\s$;]*)*$/);
60916b9709d9STom Rini				$has_break = 1 if ($rline =~ /fall[\s_-]*(through|thru)/i);
60926b9709d9STom Rini				next if ($fline =~ /^.[\s$;]*$/);
60936b9709d9STom Rini				$has_statement = 1;
60946b9709d9STom Rini				$count++;
60956b9709d9STom Rini				$has_break = 1 if ($fline =~ /\bswitch\b|\b(?:break\s*;[\s$;]*$|return\b|goto\b|continue\b)/);
60966b9709d9STom Rini			}
60976b9709d9STom Rini			if (!$has_break && $has_statement) {
60986b9709d9STom Rini				WARN("MISSING_BREAK",
6099fc0b5948SRobert P. J. Day				     "Possible switch case/default not preceded by break or fallthrough comment\n" . $herecurr);
61006b9709d9STom Rini			}
6101dd88ab32SMasahiro Yamada		}
6102dd88ab32SMasahiro Yamada
6103dd88ab32SMasahiro Yamada# check for switch/default statements without a break;
6104dd88ab32SMasahiro Yamada		if ($^V && $^V ge 5.10.0 &&
6105dd88ab32SMasahiro Yamada		    defined $stat &&
6106dd88ab32SMasahiro Yamada		    $stat =~ /^\+[$;\s]*(?:case[$;\s]+\w+[$;\s]*:[$;\s]*|)*[$;\s]*\bdefault[$;\s]*:[$;\s]*;/g) {
6107dd88ab32SMasahiro Yamada			my $ctx = '';
6108dd88ab32SMasahiro Yamada			my $herectx = $here . "\n";
6109dd88ab32SMasahiro Yamada			my $cnt = statement_rawlines($stat);
6110dd88ab32SMasahiro Yamada			for (my $n = 0; $n < $cnt; $n++) {
6111dd88ab32SMasahiro Yamada				$herectx .= raw_line($linenr, $n) . "\n";
6112dd88ab32SMasahiro Yamada			}
6113dd88ab32SMasahiro Yamada			WARN("DEFAULT_NO_BREAK",
6114dd88ab32SMasahiro Yamada			     "switch default: should use break\n" . $herectx);
6115dd88ab32SMasahiro Yamada		}
6116dd88ab32SMasahiro Yamada
6117dd88ab32SMasahiro Yamada# check for gcc specific __FUNCTION__
61186b9709d9STom Rini		if ($line =~ /\b__FUNCTION__\b/) {
61196b9709d9STom Rini			if (WARN("USE_FUNC",
61206b9709d9STom Rini				 "__func__ should be used instead of gcc specific __FUNCTION__\n"  . $herecurr) &&
61216b9709d9STom Rini			    $fix) {
61227551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/\b__FUNCTION__\b/__func__/g;
61236b9709d9STom Rini			}
6124dd88ab32SMasahiro Yamada		}
6125dd88ab32SMasahiro Yamada
61267551eb4fSHeinrich Schuchardt# check for uses of __DATE__, __TIME__, __TIMESTAMP__
61277551eb4fSHeinrich Schuchardt		while ($line =~ /\b(__(?:DATE|TIME|TIMESTAMP)__)\b/g) {
61287551eb4fSHeinrich Schuchardt			ERROR("DATE_TIME",
61297551eb4fSHeinrich Schuchardt			      "Use of the '$1' macro makes the build non-deterministic\n" . $herecurr);
61307551eb4fSHeinrich Schuchardt		}
61317551eb4fSHeinrich Schuchardt
6132dd88ab32SMasahiro Yamada# check for use of yield()
6133dd88ab32SMasahiro Yamada		if ($line =~ /\byield\s*\(\s*\)/) {
6134dd88ab32SMasahiro Yamada			WARN("YIELD",
6135dd88ab32SMasahiro Yamada			     "Using yield() is generally wrong. See yield() kernel-doc (sched/core.c)\n"  . $herecurr);
6136dd88ab32SMasahiro Yamada		}
6137dd88ab32SMasahiro Yamada
61386b9709d9STom Rini# check for comparisons against true and false
61396b9709d9STom Rini		if ($line =~ /\+\s*(.*?)\b(true|false|$Lval)\s*(==|\!=)\s*(true|false|$Lval)\b(.*)$/i) {
61406b9709d9STom Rini			my $lead = $1;
61416b9709d9STom Rini			my $arg = $2;
61426b9709d9STom Rini			my $test = $3;
61436b9709d9STom Rini			my $otype = $4;
61446b9709d9STom Rini			my $trail = $5;
61456b9709d9STom Rini			my $op = "!";
61466b9709d9STom Rini
61476b9709d9STom Rini			($arg, $otype) = ($otype, $arg) if ($arg =~ /^(?:true|false)$/i);
61486b9709d9STom Rini
61496b9709d9STom Rini			my $type = lc($otype);
61506b9709d9STom Rini			if ($type =~ /^(?:true|false)$/) {
61516b9709d9STom Rini				if (("$test" eq "==" && "$type" eq "true") ||
61526b9709d9STom Rini				    ("$test" eq "!=" && "$type" eq "false")) {
61536b9709d9STom Rini					$op = "";
61546b9709d9STom Rini				}
61556b9709d9STom Rini
61566b9709d9STom Rini				CHK("BOOL_COMPARISON",
61576b9709d9STom Rini				    "Using comparison to $otype is error prone\n" . $herecurr);
61586b9709d9STom Rini
61596b9709d9STom Rini## maybe suggesting a correct construct would better
61606b9709d9STom Rini##				    "Using comparison to $otype is error prone.  Perhaps use '${lead}${op}${arg}${trail}'\n" . $herecurr);
61616b9709d9STom Rini
61626b9709d9STom Rini			}
61636b9709d9STom Rini		}
61646b9709d9STom Rini
6165dd88ab32SMasahiro Yamada# check for semaphores initialized locked
6166dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*sema_init.+,\W?0\W?\)/) {
6167dd88ab32SMasahiro Yamada			WARN("CONSIDER_COMPLETION",
6168dd88ab32SMasahiro Yamada			     "consider using a completion\n" . $herecurr);
6169dd88ab32SMasahiro Yamada		}
6170dd88ab32SMasahiro Yamada
6171dd88ab32SMasahiro Yamada# recommend kstrto* over simple_strto* and strict_strto*
6172dd88ab32SMasahiro Yamada		if ($line =~ /\b((simple|strict)_(strto(l|ll|ul|ull)))\s*\(/) {
6173dd88ab32SMasahiro Yamada			WARN("CONSIDER_KSTRTO",
6174dd88ab32SMasahiro Yamada			     "$1 is obsolete, use k$3 instead\n" . $herecurr);
6175dd88ab32SMasahiro Yamada		}
6176dd88ab32SMasahiro Yamada
61777551eb4fSHeinrich Schuchardt# check for __initcall(), use device_initcall() explicitly or more appropriate function please
6178dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*__initcall\s*\(/) {
6179dd88ab32SMasahiro Yamada			WARN("USE_DEVICE_INITCALL",
61807551eb4fSHeinrich Schuchardt			     "please use device_initcall() or more appropriate function instead of __initcall() (see include/linux/init.h)\n" . $herecurr);
6181dd88ab32SMasahiro Yamada		}
6182dd88ab32SMasahiro Yamada
61837551eb4fSHeinrich Schuchardt# check for various structs that are normally const (ops, kgdb, device_tree)
61847551eb4fSHeinrich Schuchardt# and avoid what seem like struct definitions 'struct foo {'
6185dd88ab32SMasahiro Yamada		if ($line !~ /\bconst\b/ &&
61867551eb4fSHeinrich Schuchardt		    $line =~ /\bstruct\s+($const_structs)\b(?!\s*\{)/) {
6187dd88ab32SMasahiro Yamada			WARN("CONST_STRUCT",
61887551eb4fSHeinrich Schuchardt			     "struct $1 should normally be const\n" . $herecurr);
6189dd88ab32SMasahiro Yamada		}
6190dd88ab32SMasahiro Yamada
6191dd88ab32SMasahiro Yamada# use of NR_CPUS is usually wrong
6192dd88ab32SMasahiro Yamada# ignore definitions of NR_CPUS and usage to define arrays as likely right
6193dd88ab32SMasahiro Yamada		if ($line =~ /\bNR_CPUS\b/ &&
6194dd88ab32SMasahiro Yamada		    $line !~ /^.\s*\s*#\s*if\b.*\bNR_CPUS\b/ &&
6195dd88ab32SMasahiro Yamada		    $line !~ /^.\s*\s*#\s*define\b.*\bNR_CPUS\b/ &&
6196dd88ab32SMasahiro Yamada		    $line !~ /^.\s*$Declare\s.*\[[^\]]*NR_CPUS[^\]]*\]/ &&
6197dd88ab32SMasahiro Yamada		    $line !~ /\[[^\]]*\.\.\.[^\]]*NR_CPUS[^\]]*\]/ &&
6198dd88ab32SMasahiro Yamada		    $line !~ /\[[^\]]*NR_CPUS[^\]]*\.\.\.[^\]]*\]/)
6199dd88ab32SMasahiro Yamada		{
6200dd88ab32SMasahiro Yamada			WARN("NR_CPUS",
6201dd88ab32SMasahiro Yamada			     "usage of NR_CPUS is often wrong - consider using cpu_possible(), num_possible_cpus(), for_each_possible_cpu(), etc\n" . $herecurr);
6202dd88ab32SMasahiro Yamada		}
6203dd88ab32SMasahiro Yamada
62046b9709d9STom Rini# Use of __ARCH_HAS_<FOO> or ARCH_HAVE_<BAR> is wrong.
62056b9709d9STom Rini		if ($line =~ /\+\s*#\s*define\s+((?:__)?ARCH_(?:HAS|HAVE)\w*)\b/) {
62066b9709d9STom Rini			ERROR("DEFINE_ARCH_HAS",
62076b9709d9STom Rini			      "#define of '$1' is wrong - use Kconfig variables or standard guards instead\n" . $herecurr);
62086b9709d9STom Rini		}
62096b9709d9STom Rini
62107551eb4fSHeinrich Schuchardt# likely/unlikely comparisons similar to "(likely(foo) > 0)"
62117551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
62127551eb4fSHeinrich Schuchardt		    $line =~ /\b((?:un)?likely)\s*\(\s*$FuncArg\s*\)\s*$Compare/) {
62137551eb4fSHeinrich Schuchardt			WARN("LIKELY_MISUSE",
62147551eb4fSHeinrich Schuchardt			     "Using $1 should generally have parentheses around the comparison\n" . $herecurr);
6215dd88ab32SMasahiro Yamada		}
6216dd88ab32SMasahiro Yamada
6217dd88ab32SMasahiro Yamada# whine mightly about in_atomic
6218dd88ab32SMasahiro Yamada		if ($line =~ /\bin_atomic\s*\(/) {
6219dd88ab32SMasahiro Yamada			if ($realfile =~ m@^drivers/@) {
6220dd88ab32SMasahiro Yamada				ERROR("IN_ATOMIC",
6221dd88ab32SMasahiro Yamada				      "do not use in_atomic in drivers\n" . $herecurr);
6222dd88ab32SMasahiro Yamada			} elsif ($realfile !~ m@^kernel/@) {
6223dd88ab32SMasahiro Yamada				WARN("IN_ATOMIC",
6224dd88ab32SMasahiro Yamada				     "use of in_atomic() is incorrect outside core kernel code\n" . $herecurr);
6225dd88ab32SMasahiro Yamada			}
6226dd88ab32SMasahiro Yamada		}
6227dd88ab32SMasahiro Yamada
62287551eb4fSHeinrich Schuchardt# whine about ACCESS_ONCE
62297551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
62307551eb4fSHeinrich Schuchardt		    $line =~ /\bACCESS_ONCE\s*$balanced_parens\s*(=(?!=))?\s*($FuncArg)?/) {
62317551eb4fSHeinrich Schuchardt			my $par = $1;
62327551eb4fSHeinrich Schuchardt			my $eq = $2;
62337551eb4fSHeinrich Schuchardt			my $fun = $3;
62347551eb4fSHeinrich Schuchardt			$par =~ s/^\(\s*(.*)\s*\)$/$1/;
62357551eb4fSHeinrich Schuchardt			if (defined($eq)) {
62367551eb4fSHeinrich Schuchardt				if (WARN("PREFER_WRITE_ONCE",
62377551eb4fSHeinrich Schuchardt					 "Prefer WRITE_ONCE(<FOO>, <BAR>) over ACCESS_ONCE(<FOO>) = <BAR>\n" . $herecurr) &&
62387551eb4fSHeinrich Schuchardt				    $fix) {
62397551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\bACCESS_ONCE\s*\(\s*\Q$par\E\s*\)\s*$eq\s*\Q$fun\E/WRITE_ONCE($par, $fun)/;
62407551eb4fSHeinrich Schuchardt				}
62417551eb4fSHeinrich Schuchardt			} else {
62427551eb4fSHeinrich Schuchardt				if (WARN("PREFER_READ_ONCE",
62437551eb4fSHeinrich Schuchardt					 "Prefer READ_ONCE(<FOO>) over ACCESS_ONCE(<FOO>)\n" . $herecurr) &&
62447551eb4fSHeinrich Schuchardt				    $fix) {
62457551eb4fSHeinrich Schuchardt					$fixed[$fixlinenr] =~ s/\bACCESS_ONCE\s*\(\s*\Q$par\E\s*\)/READ_ONCE($par)/;
62467551eb4fSHeinrich Schuchardt				}
62477551eb4fSHeinrich Schuchardt			}
62487551eb4fSHeinrich Schuchardt		}
62497551eb4fSHeinrich Schuchardt
62507551eb4fSHeinrich Schuchardt# check for mutex_trylock_recursive usage
62517551eb4fSHeinrich Schuchardt		if ($line =~ /mutex_trylock_recursive/) {
62527551eb4fSHeinrich Schuchardt			ERROR("LOCKING",
62537551eb4fSHeinrich Schuchardt			      "recursive locking is bad, do not use this ever.\n" . $herecurr);
62547551eb4fSHeinrich Schuchardt		}
62557551eb4fSHeinrich Schuchardt
6256dd88ab32SMasahiro Yamada# check for lockdep_set_novalidate_class
6257dd88ab32SMasahiro Yamada		if ($line =~ /^.\s*lockdep_set_novalidate_class\s*\(/ ||
6258dd88ab32SMasahiro Yamada		    $line =~ /__lockdep_no_validate__\s*\)/ ) {
6259dd88ab32SMasahiro Yamada			if ($realfile !~ m@^kernel/lockdep@ &&
6260dd88ab32SMasahiro Yamada			    $realfile !~ m@^include/linux/lockdep@ &&
6261dd88ab32SMasahiro Yamada			    $realfile !~ m@^drivers/base/core@) {
6262dd88ab32SMasahiro Yamada				ERROR("LOCKDEP",
6263dd88ab32SMasahiro Yamada				      "lockdep_no_validate class is reserved for device->mutex.\n" . $herecurr);
6264dd88ab32SMasahiro Yamada			}
6265dd88ab32SMasahiro Yamada		}
6266dd88ab32SMasahiro Yamada
62677551eb4fSHeinrich Schuchardt		if ($line =~ /debugfs_create_\w+.*\b$mode_perms_world_writable\b/ ||
62687551eb4fSHeinrich Schuchardt		    $line =~ /DEVICE_ATTR.*\b$mode_perms_world_writable\b/) {
6269dd88ab32SMasahiro Yamada			WARN("EXPORTED_WORLD_WRITABLE",
6270dd88ab32SMasahiro Yamada			     "Exporting world writable files is usually an error. Consider more restrictive permissions.\n" . $herecurr);
6271dd88ab32SMasahiro Yamada		}
62727551eb4fSHeinrich Schuchardt
62737551eb4fSHeinrich Schuchardt# Mode permission misuses where it seems decimal should be octal
62747551eb4fSHeinrich Schuchardt# This uses a shortcut match to avoid unnecessary uses of a slow foreach loop
62757551eb4fSHeinrich Schuchardt		if ($^V && $^V ge 5.10.0 &&
62767551eb4fSHeinrich Schuchardt		    defined $stat &&
62777551eb4fSHeinrich Schuchardt		    $line =~ /$mode_perms_search/) {
62787551eb4fSHeinrich Schuchardt			foreach my $entry (@mode_permission_funcs) {
62797551eb4fSHeinrich Schuchardt				my $func = $entry->[0];
62807551eb4fSHeinrich Schuchardt				my $arg_pos = $entry->[1];
62817551eb4fSHeinrich Schuchardt
62827551eb4fSHeinrich Schuchardt				my $lc = $stat =~ tr@\n@@;
62837551eb4fSHeinrich Schuchardt				$lc = $lc + $linenr;
62847551eb4fSHeinrich Schuchardt				my $stat_real = raw_line($linenr, 0);
62857551eb4fSHeinrich Schuchardt				for (my $count = $linenr + 1; $count <= $lc; $count++) {
62867551eb4fSHeinrich Schuchardt					$stat_real = $stat_real . "\n" . raw_line($count, 0);
62877551eb4fSHeinrich Schuchardt				}
62887551eb4fSHeinrich Schuchardt
62897551eb4fSHeinrich Schuchardt				my $skip_args = "";
62907551eb4fSHeinrich Schuchardt				if ($arg_pos > 1) {
62917551eb4fSHeinrich Schuchardt					$arg_pos--;
62927551eb4fSHeinrich Schuchardt					$skip_args = "(?:\\s*$FuncArg\\s*,\\s*){$arg_pos,$arg_pos}";
62937551eb4fSHeinrich Schuchardt				}
62947551eb4fSHeinrich Schuchardt				my $test = "\\b$func\\s*\\(${skip_args}($FuncArg(?:\\|\\s*$FuncArg)*)\\s*[,\\)]";
62957551eb4fSHeinrich Schuchardt				if ($stat =~ /$test/) {
62967551eb4fSHeinrich Schuchardt					my $val = $1;
62977551eb4fSHeinrich Schuchardt					$val = $6 if ($skip_args ne "");
62987551eb4fSHeinrich Schuchardt					if (($val =~ /^$Int$/ && $val !~ /^$Octal$/) ||
62997551eb4fSHeinrich Schuchardt					    ($val =~ /^$Octal$/ && length($val) ne 4)) {
63007551eb4fSHeinrich Schuchardt						ERROR("NON_OCTAL_PERMISSIONS",
63017551eb4fSHeinrich Schuchardt						      "Use 4 digit octal (0777) not decimal permissions\n" . "$here\n" . $stat_real);
63027551eb4fSHeinrich Schuchardt					}
63037551eb4fSHeinrich Schuchardt					if ($val =~ /^$Octal$/ && (oct($val) & 02)) {
63047551eb4fSHeinrich Schuchardt						ERROR("EXPORTED_WORLD_WRITABLE",
63057551eb4fSHeinrich Schuchardt						      "Exporting writable files is usually an error. Consider more restrictive permissions.\n" . "$here\n" . $stat_real);
63067551eb4fSHeinrich Schuchardt					}
63077551eb4fSHeinrich Schuchardt				}
63087551eb4fSHeinrich Schuchardt			}
63097551eb4fSHeinrich Schuchardt		}
63107551eb4fSHeinrich Schuchardt
63117551eb4fSHeinrich Schuchardt# check for uses of S_<PERMS> that could be octal for readability
63127551eb4fSHeinrich Schuchardt		if ($line =~ /\b$mode_perms_string_search\b/) {
63137551eb4fSHeinrich Schuchardt			my $val = "";
63147551eb4fSHeinrich Schuchardt			my $oval = "";
63157551eb4fSHeinrich Schuchardt			my $to = 0;
63167551eb4fSHeinrich Schuchardt			my $curpos = 0;
63177551eb4fSHeinrich Schuchardt			my $lastpos = 0;
63187551eb4fSHeinrich Schuchardt			while ($line =~ /\b(($mode_perms_string_search)\b(?:\s*\|\s*)?\s*)/g) {
63197551eb4fSHeinrich Schuchardt				$curpos = pos($line);
63207551eb4fSHeinrich Schuchardt				my $match = $2;
63217551eb4fSHeinrich Schuchardt				my $omatch = $1;
63227551eb4fSHeinrich Schuchardt				last if ($lastpos > 0 && ($curpos - length($omatch) != $lastpos));
63237551eb4fSHeinrich Schuchardt				$lastpos = $curpos;
63247551eb4fSHeinrich Schuchardt				$to |= $mode_permission_string_types{$match};
63257551eb4fSHeinrich Schuchardt				$val .= '\s*\|\s*' if ($val ne "");
63267551eb4fSHeinrich Schuchardt				$val .= $match;
63277551eb4fSHeinrich Schuchardt				$oval .= $omatch;
63287551eb4fSHeinrich Schuchardt			}
63297551eb4fSHeinrich Schuchardt			$oval =~ s/^\s*\|\s*//;
63307551eb4fSHeinrich Schuchardt			$oval =~ s/\s*\|\s*$//;
63317551eb4fSHeinrich Schuchardt			my $octal = sprintf("%04o", $to);
63327551eb4fSHeinrich Schuchardt			if (WARN("SYMBOLIC_PERMS",
63337551eb4fSHeinrich Schuchardt				 "Symbolic permissions '$oval' are not preferred. Consider using octal permissions '$octal'.\n" . $herecurr) &&
63347551eb4fSHeinrich Schuchardt			    $fix) {
63357551eb4fSHeinrich Schuchardt				$fixed[$fixlinenr] =~ s/$val/$octal/;
63367551eb4fSHeinrich Schuchardt			}
63377551eb4fSHeinrich Schuchardt		}
63387551eb4fSHeinrich Schuchardt
63397551eb4fSHeinrich Schuchardt# validate content of MODULE_LICENSE against list from include/linux/module.h
63407551eb4fSHeinrich Schuchardt		if ($line =~ /\bMODULE_LICENSE\s*\(\s*($String)\s*\)/) {
63417551eb4fSHeinrich Schuchardt			my $extracted_string = get_quoted_string($line, $rawline);
63427551eb4fSHeinrich Schuchardt			my $valid_licenses = qr{
63437551eb4fSHeinrich Schuchardt						GPL|
63447551eb4fSHeinrich Schuchardt						GPL\ v2|
63457551eb4fSHeinrich Schuchardt						GPL\ and\ additional\ rights|
63467551eb4fSHeinrich Schuchardt						Dual\ BSD/GPL|
63477551eb4fSHeinrich Schuchardt						Dual\ MIT/GPL|
63487551eb4fSHeinrich Schuchardt						Dual\ MPL/GPL|
63497551eb4fSHeinrich Schuchardt						Proprietary
63507551eb4fSHeinrich Schuchardt					}x;
63517551eb4fSHeinrich Schuchardt			if ($extracted_string !~ /^"(?:$valid_licenses)"$/x) {
63527551eb4fSHeinrich Schuchardt				WARN("MODULE_LICENSE",
63537551eb4fSHeinrich Schuchardt				     "unknown module license " . $extracted_string . "\n" . $herecurr);
63547551eb4fSHeinrich Schuchardt			}
63557551eb4fSHeinrich Schuchardt		}
6356dd88ab32SMasahiro Yamada	}
6357dd88ab32SMasahiro Yamada
6358dd88ab32SMasahiro Yamada	# If we have no input at all, then there is nothing to report on
6359dd88ab32SMasahiro Yamada	# so just keep quiet.
6360dd88ab32SMasahiro Yamada	if ($#rawlines == -1) {
6361dd88ab32SMasahiro Yamada		exit(0);
6362dd88ab32SMasahiro Yamada	}
6363dd88ab32SMasahiro Yamada
6364dd88ab32SMasahiro Yamada	# In mailback mode only produce a report in the negative, for
6365dd88ab32SMasahiro Yamada	# things that appear to be patches.
6366dd88ab32SMasahiro Yamada	if ($mailback && ($clean == 1 || !$is_patch)) {
6367dd88ab32SMasahiro Yamada		exit(0);
6368dd88ab32SMasahiro Yamada	}
6369dd88ab32SMasahiro Yamada
6370dd88ab32SMasahiro Yamada	# This is not a patch, and we are are in 'no-patch' mode so
6371dd88ab32SMasahiro Yamada	# just keep quiet.
6372dd88ab32SMasahiro Yamada	if (!$chk_patch && !$is_patch) {
6373dd88ab32SMasahiro Yamada		exit(0);
6374dd88ab32SMasahiro Yamada	}
6375dd88ab32SMasahiro Yamada
63767551eb4fSHeinrich Schuchardt	if (!$is_patch && $file !~ /cover-letter\.patch$/) {
6377dd88ab32SMasahiro Yamada		ERROR("NOT_UNIFIED_DIFF",
6378dd88ab32SMasahiro Yamada		      "Does not appear to be a unified-diff format patch\n");
6379dd88ab32SMasahiro Yamada	}
63807551eb4fSHeinrich Schuchardt	if ($is_patch && $has_commit_log && $chk_signoff && $signoff == 0) {
6381dd88ab32SMasahiro Yamada		ERROR("MISSING_SIGN_OFF",
6382dd88ab32SMasahiro Yamada		      "Missing Signed-off-by: line(s)\n");
6383dd88ab32SMasahiro Yamada	}
6384dd88ab32SMasahiro Yamada
6385dd88ab32SMasahiro Yamada	print report_dump();
6386dd88ab32SMasahiro Yamada	if ($summary && !($clean == 1 && $quiet == 1)) {
6387dd88ab32SMasahiro Yamada		print "$filename " if ($summary_file);
6388dd88ab32SMasahiro Yamada		print "total: $cnt_error errors, $cnt_warn warnings, " .
6389dd88ab32SMasahiro Yamada			(($check)? "$cnt_chk checks, " : "") .
6390dd88ab32SMasahiro Yamada			"$cnt_lines lines checked\n";
6391dd88ab32SMasahiro Yamada	}
6392dd88ab32SMasahiro Yamada
6393dd88ab32SMasahiro Yamada	if ($quiet == 0) {
63947551eb4fSHeinrich Schuchardt		# If there were any defects found and not already fixing them
63957551eb4fSHeinrich Schuchardt		if (!$clean and !$fix) {
63967551eb4fSHeinrich Schuchardt			print << "EOM"
6397dd88ab32SMasahiro Yamada
63987551eb4fSHeinrich SchuchardtNOTE: For some of the reported defects, checkpatch may be able to
63997551eb4fSHeinrich Schuchardt      mechanically convert to the typical style using --fix or --fix-inplace.
64007551eb4fSHeinrich SchuchardtEOM
6401dd88ab32SMasahiro Yamada		}
6402dd88ab32SMasahiro Yamada		# If there were whitespace errors which cleanpatch can fix
6403dd88ab32SMasahiro Yamada		# then suggest that.
6404dd88ab32SMasahiro Yamada		if ($rpt_cleaners) {
6405dd88ab32SMasahiro Yamada			$rpt_cleaners = 0;
64067551eb4fSHeinrich Schuchardt			print << "EOM"
64077551eb4fSHeinrich Schuchardt
64087551eb4fSHeinrich SchuchardtNOTE: Whitespace errors detected.
64097551eb4fSHeinrich Schuchardt      You may wish to use scripts/cleanpatch or scripts/cleanfile
64107551eb4fSHeinrich SchuchardtEOM
6411dd88ab32SMasahiro Yamada		}
6412dd88ab32SMasahiro Yamada	}
6413dd88ab32SMasahiro Yamada
64147551eb4fSHeinrich Schuchardt	if ($clean == 0 && $fix &&
64157551eb4fSHeinrich Schuchardt	    ("@rawlines" ne "@fixed" ||
64167551eb4fSHeinrich Schuchardt	     $#fixed_inserted >= 0 || $#fixed_deleted >= 0)) {
64176b9709d9STom Rini		my $newfile = $filename;
64186b9709d9STom Rini		$newfile .= ".EXPERIMENTAL-checkpatch-fixes" if (!$fix_inplace);
64196b9709d9STom Rini		my $linecount = 0;
64206b9709d9STom Rini		my $f;
64216b9709d9STom Rini
64227551eb4fSHeinrich Schuchardt		@fixed = fix_inserted_deleted_lines(\@fixed, \@fixed_inserted, \@fixed_deleted);
64237551eb4fSHeinrich Schuchardt
64246b9709d9STom Rini		open($f, '>', $newfile)
64256b9709d9STom Rini		    or die "$P: Can't open $newfile for write\n";
64266b9709d9STom Rini		foreach my $fixed_line (@fixed) {
64276b9709d9STom Rini			$linecount++;
64286b9709d9STom Rini			if ($file) {
64296b9709d9STom Rini				if ($linecount > 3) {
64306b9709d9STom Rini					$fixed_line =~ s/^\+//;
64316b9709d9STom Rini					print $f $fixed_line . "\n";
6432dd88ab32SMasahiro Yamada				}
64336b9709d9STom Rini			} else {
64346b9709d9STom Rini				print $f $fixed_line . "\n";
64356b9709d9STom Rini			}
64366b9709d9STom Rini		}
64376b9709d9STom Rini		close($f);
64386b9709d9STom Rini
64396b9709d9STom Rini		if (!$quiet) {
64406b9709d9STom Rini			print << "EOM";
64417551eb4fSHeinrich Schuchardt
64426b9709d9STom RiniWrote EXPERIMENTAL --fix correction(s) to '$newfile'
64436b9709d9STom Rini
64446b9709d9STom RiniDo _NOT_ trust the results written to this file.
64456b9709d9STom RiniDo _NOT_ submit these changes without inspecting them for correctness.
64466b9709d9STom Rini
64476b9709d9STom RiniThis EXPERIMENTAL file is simply a convenience to help rewrite patches.
64486b9709d9STom RiniNo warranties, expressed or implied...
64496b9709d9STom RiniEOM
64506b9709d9STom Rini		}
6451dd88ab32SMasahiro Yamada	}
6452dd88ab32SMasahiro Yamada
64537551eb4fSHeinrich Schuchardt	if ($quiet == 0) {
64547551eb4fSHeinrich Schuchardt		print "\n";
64557551eb4fSHeinrich Schuchardt		if ($clean == 1) {
64567551eb4fSHeinrich Schuchardt			print "$vname has no obvious style problems and is ready for submission.\n";
64577551eb4fSHeinrich Schuchardt		} else {
64587551eb4fSHeinrich Schuchardt			print "$vname has style problems, please review.\n";
6459dd88ab32SMasahiro Yamada		}
6460dd88ab32SMasahiro Yamada	}
6461dd88ab32SMasahiro Yamada	return $clean;
6462dd88ab32SMasahiro Yamada}
6463