6972 lines · 205.6 KB · Perl
RawDownload
					}					if ($block =~/\b(?:if|for|while)\b/) {						#print "APW: ALLOWED: block<$block>\n";						$allowed[$allow] = 1;					}					if (statement_block_size($block) > 1) {						#print "APW: ALLOWED: lines block<$block>\n";						$allowed[$allow] = 1;					}					$allow++;				}				if ($seen) {					my $sum_allowed = 0;					foreach (@allowed) {						$sum_allowed += $_;					}					if ($sum_allowed == 0) {						WARN("BRACES",						     "braces {} are not necessary for any arm of this statement\n" . $herectx);					} elsif ($sum_allowed != $allow &&						 $seen != $allow) {						CHK("BRACES",						    "braces {} should be used on all arms of this statement\n" . $herectx);					}				}			}		}		if (!defined $suppress_ifbraces{$linenr - 1} &&					$line =~ /\b(if|while|for|else)\b/) {			my $allowed = 0; 			# Check the pre-context.			if (substr($line, 0, $-[0]) =~ /(\}\s*)$/) {				#print "APW: ALLOWED: pre<$1>\n";				$allowed = 1;			} 			my ($level, $endln, @chunks) =				ctx_statement_full($linenr, $realcnt, $-[0]); 			# Check the condition.			my ($cond, $block) = @{$chunks[0]};			#print "CHECKING<$linenr> cond<$cond> block<$block>\n";			if (defined $cond) {				substr($block, 0, length($cond), '');			}			if (statement_lines($cond) > 1) {				#print "APW: ALLOWED: cond<$cond>\n";				$allowed = 1;			}			if ($block =~/\b(?:if|for|while)\b/) {				#print "APW: ALLOWED: block<$block>\n";				$allowed = 1;			}			if (statement_block_size($block) > 1) {				#print "APW: ALLOWED: lines block<$block>\n";				$allowed = 1;			}			# Check the post-context.			if (defined $chunks[1]) {				my ($cond, $block) = @{$chunks[1]};				if (defined $cond) {					substr($block, 0, length($cond), '');				}				if ($block =~ /^\s*\{/) {					#print "APW: ALLOWED: chunk-1 block<$block>\n";					$allowed = 1;				}			}			if ($level == 0 && $block =~ /^\s*\{/ && !$allowed) {				my $cnt = statement_rawlines($block);				my $herectx = get_stat_here($linenr, $cnt, $here); 				WARN("BRACES",				     "braces {} are not necessary for single statement blocks\n" . $herectx);			}		} # check for single line unbalanced braces		if ($sline =~ /^.\s*\}\s*else\s*$/ ||		    $sline =~ /^.\s*else\s*\{\s*$/) {			CHK("BRACES", "Unbalanced braces around else statement\n" . $herecurr);		} # check for unnecessary blank lines around braces		if (($line =~ /^.\s*}\s*$/ && $prevrawline =~ /^.\s*$/)) {			if (CHK("BRACES",				"Blank lines aren't necessary before a close brace '}'\n" . $hereprev) &&			    $fix && $prevrawline =~ /^\+/) {				fix_delete_line($fixlinenr - 1, $prevrawline);			}		}		if (($rawline =~ /^.\s*$/ && $prevline =~ /^..*{\s*$/)) {			if (CHK("BRACES",				"Blank lines aren't necessary after an open brace '{'\n" . $hereprev) &&			    $fix) {				fix_delete_line($fixlinenr, $rawline);			}		} # no volatiles please		my $asm_volatile = qr{\b(__asm__|asm)\s+(__volatile__|volatile)\b};		if ($line =~ /\bvolatile\b/ && $line !~ /$asm_volatile/) {			WARN("VOLATILE",			     "Use of volatile is usually wrong: see Documentation/process/volatile-considered-harmful.rst\n" . $herecurr);		} # Check for user-visible strings broken across lines, which breaks the ability# to grep for the string.  Make exceptions when the previous string ends in a# newline (multiple lines in one string constant) or '\t', '\r', ';', or '{'# (common in inline assembly) or is a octal \123 or hexadecimal \xaf value		if ($line =~ /^\+\s*$String/ &&		    $prevline =~ /"\s*$/ &&		    $prevrawline !~ /(?:\\(?:[ntr]|[0-7]{1,3}|x[0-9a-fA-F]{1,2})|;\s*|\{\s*)"\s*$/) {			if (WARN("SPLIT_STRING",				 "quoted string split across lines\n" . $hereprev) &&				     $fix &&				     $prevrawline =~ /^\+.*"\s*$/ &&				     $last_coalesced_string_linenr != $linenr - 1) {				my $extracted_string = get_quoted_string($line, $rawline);				my $comma_close = "";				if ($rawline =~ /\Q$extracted_string\E(\s*\)\s*;\s*$|\s*,\s*)/) {					$comma_close = $1;				} 				fix_delete_line($fixlinenr - 1, $prevrawline);				fix_delete_line($fixlinenr, $rawline);				my $fixedline = $prevrawline;				$fixedline =~ s/"\s*$//;				$fixedline .= substr($extracted_string, 1) . trim($comma_close);				fix_insert_line($fixlinenr - 1, $fixedline);				$fixedline = $rawline;				$fixedline =~ s/\Q$extracted_string\E\Q$comma_close\E//;				if ($fixedline !~ /\+\s*$/) {					fix_insert_line($fixlinenr, $fixedline);				}				$last_coalesced_string_linenr = $linenr;			}		} # check for missing a space in a string concatenation		if ($prevrawline =~ /[^\\]\w"$/ && $rawline =~ /^\+[\t ]+"\w/) {			WARN('MISSING_SPACE',			     "break quoted strings at a space character\n" . $hereprev);		} # check for an embedded function name in a string when the function is known# This does not work very well for -f --file checking as it depends on patch# context providing the function name or a single line form for in-file# function declarations		if ($line =~ /^\+.*$String/ &&		    defined($context_function) &&		    get_quoted_string($line, $rawline) =~ /\b$context_function\b/ &&		    length(get_quoted_string($line, $rawline)) != (length($context_function) + 2)) {			WARN("EMBEDDED_FUNCTION_NAME",			     "Prefer using '\"%s...\", __func__' to using '$context_function', this function's name, in a string\n" . $herecurr);		} # check for spaces before a quoted newline		if ($rawline =~ /^.*\".*\s\\n/) {			if (WARN("QUOTED_WHITESPACE_BEFORE_NEWLINE",				 "unnecessary whitespace before a quoted newline\n" . $herecurr) &&			    $fix) {				$fixed[$fixlinenr] =~ s/^(\+.*\".*)\s+\\n/$1\\n/;			} 		} # concatenated string without spaces between elements		if ($line =~ /$String[A-Za-z0-9_]/ || $line =~ /[A-Za-z0-9_]$String/) {			if (CHK("CONCATENATED_STRING",				"Concatenated strings should use spaces between elements\n" . $herecurr) &&			    $fix) {				while ($line =~ /($String)/g) {					my $extracted_string = substr($rawline, $-[0], $+[0] - $-[0]);					$fixed[$fixlinenr] =~ s/\Q$extracted_string\E([A-Za-z0-9_])/$extracted_string $1/;					$fixed[$fixlinenr] =~ s/([A-Za-z0-9_])\Q$extracted_string\E/$1 $extracted_string/;				}			}		} # uncoalesced string fragments		if ($line =~ /$String\s*"/) {			if (WARN("STRING_FRAGMENTS",				 "Consecutive strings are generally better as a single string\n" . $herecurr) &&			    $fix) {				while ($line =~ /($String)(?=\s*")/g) {					my $extracted_string = substr($rawline, $-[0], $+[0] - $-[0]);					$fixed[$fixlinenr] =~ s/\Q$extracted_string\E\s*"/substr($extracted_string, 0, -1)/e;				}			}		} # check for non-standard and hex prefixed decimal printf formats		my $show_L = 1;	#don't show the same defect twice		my $show_Z = 1;		while ($line =~ /(?:^|")([X\t]*)(?:"|$)/g) {			my $string = substr($rawline, $-[1], $+[1] - $-[1]);			$string =~ s/%%/__/g;			# check for %L			if ($show_L && $string =~ /%[\*\d\.\$]*L([diouxX])/) {				WARN("PRINTF_L",				     "\%L$1 is non-standard C, use %ll$1\n" . $herecurr);				$show_L = 0;			}			# check for %Z			if ($show_Z && $string =~ /%[\*\d\.\$]*Z([diouxX])/) {				WARN("PRINTF_Z",				     "%Z$1 is non-standard C, use %z$1\n" . $herecurr);				$show_Z = 0;			}			# check for 0x<decimal>			if ($string =~ /0x%[\*\d\.\$\Llzth]*[diou]/) {				ERROR("PRINTF_0XDECIMAL",				      "Prefixing 0x with decimal output is defective\n" . $herecurr);			}		} # check for line continuations in quoted strings with odd counts of "		if ($rawline =~ /\\$/ && $sline =~ tr/"/"/ % 2) {			WARN("LINE_CONTINUATIONS",			     "Avoid line continuations in quoted strings\n" . $herecurr);		} # warn about #if 0		if ($line =~ /^.\s*\#\s*if\s+0\b/) {			WARN("IF_0",			     "Consider removing the code enclosed by this #if 0 and its #endif\n" . $herecurr);		} # warn about #if 1		if ($line =~ /^.\s*\#\s*if\s+1\b/) {			WARN("IF_1",			     "Consider removing the #if 1 and its #endif\n" . $herecurr);		} # check for needless "if (<foo>) fn(<foo>)" uses		if ($prevline =~ /\bif\s*\(\s*($Lval)\s*\)/) {			my $tested = quotemeta($1);			my $expr = '\s*\(\s*' . $tested . '\s*\)\s*;';			if ($line =~ /\b(kfree|usb_free_urb|debugfs_remove(?:_recursive)?|(?:kmem_cache|mempool|dma_pool)_destroy)$expr/) {				my $func = $1;				if (WARN('NEEDLESS_IF',					 "$func(NULL) is safe and this check is probably not required\n" . $hereprev) &&				    $fix) {					my $do_fix = 1;					my $leading_tabs = "";					my $new_leading_tabs = "";					if ($lines[$linenr - 2] =~ /^\+(\t*)if\s*\(\s*$tested\s*\)\s*$/) {						$leading_tabs = $1;					} else {						$do_fix = 0;					}					if ($lines[$linenr - 1] =~ /^\+(\t+)$func\s*\(\s*$tested\s*\)\s*;\s*$/) {						$new_leading_tabs = $1;						if (length($leading_tabs) + 1 ne length($new_leading_tabs)) {							$do_fix = 0;						}					} else {						$do_fix = 0;					}					if ($do_fix) {						fix_delete_line($fixlinenr - 1, $prevrawline);						$fixed[$fixlinenr] =~ s/^\+$new_leading_tabs/\+$leading_tabs/;					}				}			}		} # check for unnecessary "Out of Memory" messages		if ($line =~ /^\+.*\b$logFunctions\s*\(/ &&		    $prevline =~ /^[ \+]\s*if\s*\(\s*(\!\s*|NULL\s*==\s*)?($Lval)(\s*==\s*NULL\s*)?\s*\)/ &&		    (defined $1 || defined $3) &&		    $linenr > 3) {			my $testval = $2;			my $testline = $lines[$linenr - 3]; 			my ($s, $c) = ctx_statement_block($linenr - 3, $realcnt, 0);#			print("line: <$line>\nprevline: <$prevline>\ns: <$s>\nc: <$c>\n\n\n"); 			if ($s =~ /(?:^|\n)[ \+]\s*(?:$Type\s*)?\Q$testval\E\s*=\s*(?:\([^\)]*\)\s*)?\s*$allocFunctions\s*\(/ &&			    $s !~ /\b__GFP_NOWARN\b/ ) {				WARN("OOM_MESSAGE",				     "Possible unnecessary 'out of memory' message\n" . $hereprev);			}		} # check for logging functions with KERN_<LEVEL>		if ($line !~ /printk(?:_ratelimited|_once)?\s*\(/ &&		    $line =~ /\b$logFunctions\s*\(.*\b(KERN_[A-Z]+)\b/) {			my $level = $1;			if (WARN("UNNECESSARY_KERN_LEVEL",				 "Possible unnecessary $level\n" . $herecurr) &&			    $fix) {				$fixed[$fixlinenr] =~ s/\s*$level\s*//;			}		} # check for logging continuations		if ($line =~ /\bprintk\s*\(\s*KERN_CONT\b|\bpr_cont\s*\(/) {			WARN("LOGGING_CONTINUATION",			     "Avoid logging continuation uses where feasible\n" . $herecurr);		} # check for mask then right shift without a parentheses		if ($perl_version_ok &&		    $line =~ /$LvalOrFunc\s*\&\s*($LvalOrFunc)\s*>>/ &&		    $4 !~ /^\&/) { # $LvalOrFunc may be &foo, ignore if so			WARN("MASK_THEN_SHIFT",			     "Possible precedence defect with mask then right shift - may need parentheses\n" . $herecurr);		} # check for pointer comparisons to NULL		if ($perl_version_ok) {			while ($line =~ /\b$LvalOrFunc\s*(==|\!=)\s*NULL\b/g) {				my $val = $1;				my $equal = "!";				$equal = "" if ($4 eq "!=");				if (CHK("COMPARISON_TO_NULL",					"Comparison to NULL could be written \"${equal}${val}\"\n" . $herecurr) &&					    $fix) {					$fixed[$fixlinenr] =~ s/\b\Q$val\E\s*(?:==|\!=)\s*NULL\b/$equal$val/;				}			}		} # check for bad placement of section $InitAttribute (e.g.: __initdata)		if ($line =~ /(\b$InitAttribute\b)/) {			my $attr = $1;			if ($line =~ /^\+\s*static\s+(?:const\s+)?(?:$attr\s+)?($NonptrTypeWithAttr)\s+(?:$attr\s+)?($Ident(?:\[[^]]*\])?)\s*[=;]/) {				my $ptr = $1;				my $var = $2;				if ((($ptr =~ /\b(union|struct)\s+$attr\b/ &&				      ERROR("MISPLACED_INIT",					    "$attr should be placed after $var\n" . $herecurr)) ||				     ($ptr !~ /\b(union|struct)\s+$attr\b/ &&				      WARN("MISPLACED_INIT",					   "$attr should be placed after $var\n" . $herecurr))) &&				    $fix) {					$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;				}			}		} # check for $InitAttributeData (ie: __initdata) with const		if ($line =~ /\bconst\b/ && $line =~ /($InitAttributeData)/) {			my $attr = $1;			$attr =~ /($InitAttributePrefix)(.*)/;			my $attr_prefix = $1;			my $attr_type = $2;			if (ERROR("INIT_ATTRIBUTE",				  "Use of const init definition must use ${attr_prefix}initconst\n" . $herecurr) &&			    $fix) {				$fixed[$fixlinenr] =~				    s/$InitAttributeData/${attr_prefix}initconst/;			}		} # check for $InitAttributeConst (ie: __initconst) without const		if ($line !~ /\bconst\b/ && $line =~ /($InitAttributeConst)/) {			my $attr = $1;			if (ERROR("INIT_ATTRIBUTE",				  "Use of $attr requires a separate use of const\n" . $herecurr) &&			    $fix) {				my $lead = $fixed[$fixlinenr] =~				    /(^\+\s*(?:static\s+))/;				$lead = rtrim($1);				$lead = "$lead " if ($lead !~ /^\+$/);				$lead = "${lead}const ";				$fixed[$fixlinenr] =~ s/(^\+\s*(?:static\s+))/$lead/;			}		} # check for __read_mostly with const non-pointer (should just be const)		if ($line =~ /\b__read_mostly\b/ &&		    $line =~ /($Type)\s*$Ident/ && $1 !~ /\*\s*$/ && $1 =~ /\bconst\b/) {			if (ERROR("CONST_READ_MOSTLY",				  "Invalid use of __read_mostly with const type\n" . $herecurr) &&			    $fix) {				$fixed[$fixlinenr] =~ s/\s+__read_mostly\b//;			}		} # don't use __constant_<foo> functions outside of include/uapi/		if ($realfile !~ m@^include/uapi/@ &&		    $line =~ /(__constant_(?:htons|ntohs|[bl]e(?:16|32|64)_to_cpu|cpu_to_[bl]e(?:16|32|64)))\s*\(/) {			my $constant_func = $1;			my $func = $constant_func;			$func =~ s/^__constant_//;			if (WARN("CONSTANT_CONVERSION",				 "$constant_func should be $func\n" . $herecurr) &&			    $fix) {				$fixed[$fixlinenr] =~ s/\b$constant_func\b/$func/g;			}		} # prefer usleep_range over udelay		if ($line =~ /\budelay\s*\(\s*(\d+)\s*\)/) {			my $delay = $1;			# ignore udelay's < 10, however			if (! ($delay < 10) ) {				CHK("USLEEP_RANGE",				    "usleep_range is preferred over udelay; see Documentation/timers/timers-howto.rst\n" . $herecurr);			}			if ($delay > 2000) {				WARN("LONG_UDELAY",				     "long udelay - prefer mdelay; see arch/arm/include/asm/delay.h\n" . $herecurr);			}		} # warn about unexpectedly long msleep's		if ($line =~ /\bmsleep\s*\((\d+)\);/) {			if ($1 < 20) {				WARN("MSLEEP",				     "msleep < 20ms can sleep for up to 20ms; see Documentation/timers/timers-howto.rst\n" . $herecurr);			}		} # check for comparisons of jiffies		if ($line =~ /\bjiffies\s*$Compare|$Compare\s*jiffies\b/) {			WARN("JIFFIES_COMPARISON",			     "Comparing jiffies is almost always wrong; prefer time_after, time_before and friends\n" . $herecurr);		} # check for comparisons of get_jiffies_64()		if ($line =~ /\bget_jiffies_64\s*\(\s*\)\s*$Compare|$Compare\s*get_jiffies_64\s*\(\s*\)/) {			WARN("JIFFIES_COMPARISON",			     "Comparing get_jiffies_64() is almost always wrong; prefer time_after64, time_before64 and friends\n" . $herecurr);		} # warn about #ifdefs in C files#		if ($line =~ /^.\s*\#\s*if(|n)def/ && ($realfile =~ /\.c$/)) {#			print "#ifdef in C files should be avoided\n";#			print "$herecurr";#			$clean = 0;#		} # warn about spacing in #ifdefs		if ($line =~ /^.\s*\#\s*(ifdef|ifndef|elif)\s\s+/) {			if (ERROR("SPACING",				  "exactly one space required after that #$1\n" . $herecurr) &&			    $fix) {				$fixed[$fixlinenr] =~				    s/^(.\s*\#\s*(ifdef|ifndef|elif))\s{2,}/$1 /;			} 		} # check for spinlock_t definitions without a comment.		if ($line =~ /^.\s*(struct\s+mutex|spinlock_t)\s+\S+;/ ||		    $line =~ /^.\s*(DEFINE_MUTEX)\s*\(/) {			my $which = $1;			if (!ctx_has_comment($first_line, $linenr)) {				CHK("UNCOMMENTED_DEFINITION",				    "$1 definition without comment\n" . $herecurr);			}		}# check for memory barriers without a comment. 		my $barriers = qr{			mb|			rmb|			wmb		}x;		my $barrier_stems = qr{			mb__before_atomic|			mb__after_atomic|			store_release|			load_acquire|			store_mb|			(?:$barriers)		}x;		my $all_barriers = qr{			(?:$barriers)|			smp_(?:$barrier_stems)|			virt_(?:$barrier_stems)		}x; 		if ($line =~ /\b(?:$all_barriers)\s*\(/) {			if (!ctx_has_comment($first_line, $linenr)) {				WARN("MEMORY_BARRIER",				     "memory barrier without comment\n" . $herecurr);			}		} 		my $underscore_smp_barriers = qr{__smp_(?:$barrier_stems)}x; 		if ($realfile !~ m@^include/asm-generic/@ &&		    $realfile !~ m@/barrier\.h$@ &&		    $line =~ m/\b(?:$underscore_smp_barriers)\s*\(/ &&		    $line !~ m/^.\s*\#\s*define\s+(?:$underscore_smp_barriers)\s*\(/) {			WARN("MEMORY_BARRIER",			     "__smp memory barriers shouldn't be used outside barrier.h and asm-generic\n" . $herecurr);		} # check for waitqueue_active without a comment.		if ($line =~ /\bwaitqueue_active\s*\(/) {			if (!ctx_has_comment($first_line, $linenr)) {				WARN("WAITQUEUE_ACTIVE",				     "waitqueue_active without comment\n" . $herecurr);

Lines 5501–6000 of 6972. Previous lines