diff options
Diffstat (limited to 'scripts')
-rw-r--r-- | scripts/Makefile.modsign | 32 | ||||
-rwxr-xr-x | scripts/checkpatch.pl | 150 | ||||
-rw-r--r-- | scripts/coccinelle/api/d_find_alias.cocci | 80 | ||||
-rw-r--r-- | scripts/coccinelle/misc/warn.cocci | 109 | ||||
-rwxr-xr-x | scripts/config | 1 | ||||
-rw-r--r-- | scripts/pnmtologo.c | 7 | ||||
-rwxr-xr-x | scripts/tags.sh | 57 |
7 files changed, 365 insertions, 71 deletions
diff --git a/scripts/Makefile.modsign b/scripts/Makefile.modsign new file mode 100644 index 00000000000..abfda626dba --- /dev/null +++ b/scripts/Makefile.modsign @@ -0,0 +1,32 @@ +# ========================================================================== +# Signing modules +# ========================================================================== + +PHONY := __modsign +__modsign: + +include scripts/Kbuild.include + +__modules := $(sort $(shell grep -h '\.ko' /dev/null $(wildcard $(MODVERDIR)/*.mod))) +modules := $(patsubst %.o,%.ko,$(wildcard $(__modules:.ko=.o))) + +PHONY += $(modules) +__modsign: $(modules) + @: + +quiet_cmd_sign_ko = SIGN [M] $(2)/$(notdir $@) + cmd_sign_ko = $(mod_sign_cmd) $(2)/$(notdir $@) + +# Modules built outside the kernel source tree go into extra by default +INSTALL_MOD_DIR ?= extra +ext-mod-dir = $(INSTALL_MOD_DIR)$(subst $(patsubst %/,%,$(KBUILD_EXTMOD)),,$(@D)) + +modinst_dir = $(if $(KBUILD_EXTMOD),$(ext-mod-dir),kernel/$(@D)) + +$(modules): + $(call cmd,sign_ko,$(MODLIB)/$(modinst_dir)) + +# Declare the contents of the .PHONY variable as phony. We keep that +# information in a variable se we can use it in if_changed and friends. + +.PHONY: $(PHONY) diff --git a/scripts/checkpatch.pl b/scripts/checkpatch.pl index f18750e3bd6..4d2c7dfdaab 100755 --- a/scripts/checkpatch.pl +++ b/scripts/checkpatch.pl @@ -33,6 +33,7 @@ my %ignore_type = (); my @ignore = (); my $help = 0; my $configuration_file = ".checkpatch.conf"; +my $max_line_length = 80; sub help { my ($exitcode) = @_; @@ -51,6 +52,7 @@ Options: -f, --file treat FILE as regular source file --subjective, --strict enable more subjective tests --ignore TYPE(,TYPE2...) ignore various comma separated message types + --max-line-length=n set the maximum line length, if exceeded, warn --show-types show the message "types" in the output --root=PATH PATH to the kernel tree root --no-summary suppress the per-file summary @@ -107,6 +109,7 @@ GetOptions( 'strict!' => \$check, 'ignore=s' => \@ignore, 'show-types!' => \$show_types, + 'max-line-length=i' => \$max_line_length, 'root=s' => \$root, 'summary!' => \$summary, 'mailback!' => \$mailback, @@ -227,7 +230,11 @@ our $Inline = qr{inline|__always_inline|noinline}; our $Member = qr{->$Ident|\.$Ident|\[[^]]*\]}; our $Lval = qr{$Ident(?:$Member)*}; -our $Constant = qr{(?i:(?:[0-9]+|0x[0-9a-f]+)[ul]*)}; +our $Float_hex = qr{(?i:0x[0-9a-f]+p-?[0-9]+[fl]?)}; +our $Float_dec = qr{(?i:((?:[0-9]+\.[0-9]*|[0-9]*\.[0-9]+)(?:e-?[0-9]+)?[fl]?))}; +our $Float_int = qr{(?i:[0-9]+e-?[0-9]+[fl]?)}; +our $Float = qr{$Float_hex|$Float_dec|$Float_int}; +our $Constant = qr{(?:$Float|(?i:(?:0x[0-9a-f]+|[0-9]+)[ul]*))}; our $Assignment = qr{(?:\*\=|/=|%=|\+=|-=|<<=|>>=|&=|\^=|\|=|=)}; our $Compare = qr{<=|>=|==|!=|<|>}; our $Operators = qr{ @@ -352,27 +359,6 @@ sub deparenthesize { $chk_signoff = 0 if ($file); -my @dep_includes = (); -my @dep_functions = (); -my $removal = "Documentation/feature-removal-schedule.txt"; -if ($tree && -f "$root/$removal") { - open(my $REMOVE, '<', "$root/$removal") || - die "$P: $removal: open failed - $!\n"; - while (<$REMOVE>) { - if (/^Check:\s+(.*\S)/) { - for my $entry (split(/[, ]+/, $1)) { - if ($entry =~ m@include/(.*)@) { - push(@dep_includes, $1); - - } elsif ($entry !~ m@/@) { - push(@dep_functions, $entry); - } - } - } - } - close($REMOVE); -} - my @rawlines = (); my @lines = (); my $vname; @@ -1412,6 +1398,8 @@ sub process { my %suppress_export; my $suppress_statement = 0; + my %camelcase = (); + # Pre-scan the patch sanitizing the lines. # Pre-scan the patch looking for any __setup documentation. # @@ -1757,6 +1745,13 @@ sub process { #print "is_start<$is_start> is_end<$is_end> length<$length>\n"; } +# discourage the addition of CONFIG_EXPERIMENTAL in Kconfig. + if ($realfile =~ /Kconfig/ && + $line =~ /.\s*depends on\s+.*\bEXPERIMENTAL\b/) { + WARN("CONFIG_EXPERIMENTAL", + "Use of CONFIG_EXPERIMENTAL is deprecated. For alternatives, see https://lkml.org/lkml/2012/10/23/580\n"); + } + if (($realfile =~ /Makefile.*/ || $realfile =~ /Kbuild.*/) && ($line =~ /\+(EXTRA_[A-Z]+FLAGS).*/)) { my $flag = $1; @@ -1774,15 +1769,15 @@ sub process { # check we are in a valid source file if not then ignore this hunk next if ($realfile !~ /\.(h|c|s|S|pl|sh)$/); -#80 column limit +#line length limit if ($line =~ /^\+/ && $prevrawline !~ /\/\*\*/ && $rawline !~ /^.\s*\*\s*\@$Ident\s/ && !($line =~ /^\+\s*$logFunctions\s*\(\s*(?:(KERN_\S+\s*|[^"]*))?"[X\t]*"\s*(?:|,|\)\s*;)\s*$/ || $line =~ /^\+\s*"[^"]*"\s*(?:\s*|,|\)\s*;)\s*$/) && - $length > 80) + $length > $max_line_length) { WARN("LONG_LINE", - "line over 80 characters\n" . $herecurr); + "line over $max_line_length characters\n" . $herecurr); } # Check for user-visible strings broken across lines, which breaks the ability @@ -1912,6 +1907,12 @@ sub process { # check we are in a valid C source file if not then ignore this hunk next if ($realfile !~ /\.(h|c)$/); +# discourage the addition of CONFIG_EXPERIMENTAL in #if(def). + if ($line =~ /^\+\s*\#\s*if.*\bCONFIG_EXPERIMENTAL\b/) { + WARN("CONFIG_EXPERIMENTAL", + "Use of CONFIG_EXPERIMENTAL is deprecated. For alternatives, see https://lkml.org/lkml/2012/10/23/580\n"); + } + # check for RCS/CVS revision markers if ($rawline =~ /^\+.*\$(Revision|Log|Id)(?:\$|)/) { WARN("CVS_KEYWORD", @@ -2225,8 +2226,11 @@ sub process { my $path = $1; if ($path =~ m{//}) { ERROR("MALFORMED_INCLUDE", - "malformed #include filename\n" . - $herecurr); + "malformed #include filename\n" . $herecurr); + } + if ($path =~ "^uapi/" && $realfile =~ m@\binclude/uapi/@) { + ERROR("UAPI_INCLUDE", + "No #include in ...include/uapi/... should use a uapi/ path prefix\n" . $herecurr); } } @@ -2906,12 +2910,17 @@ sub process { } } -#studly caps, commented out until figure out how to distinguish between use of existing and adding new -# if (($line=~/[\w_][a-z\d]+[A-Z]/) and !($line=~/print/)) { -# print "No studly caps, use _\n"; -# print "$herecurr"; -# $clean = 0; -# } +#CamelCase + while ($line =~ m{($Constant|$Lval)}g) { + my $var = $1; + if ($var !~ /$Constant/ && + $var =~ /[A-Z]\w*[a-z]|[a-z]\w*[A-Z]/ && + !defined $camelcase{$var}) { + $camelcase{$var} = 1; + WARN("CAMELCASE", + "Avoid CamelCase: <$var>\n" . $herecurr); + } + } #no spaces allowed after \ in define if ($line=~/\#\s*define.*\\\s$/) { @@ -3013,6 +3022,17 @@ sub process { "Macros with complex values should be enclosed in parenthesis\n" . "$herectx"); } } + +# check for line continuations outside of #defines, preprocessor #, and asm + + } else { + if ($prevline !~ /^..*\\$/ && + $line !~ /^\+\s*\#.*\\$/ && # preprocessor + $line !~ /^\+.*\b(__asm__|asm)\b.*\\$/ && # asm + $line =~ /^\+.*\\$/) { + WARN("LINE_CONTINUATIONS", + "Avoid unnecessary line continuations\n" . $herecurr); + } } # do {} while (0) macro tests: @@ -3183,20 +3203,14 @@ sub process { } } -# don't include deprecated include files (uses RAW line) - for my $inc (@dep_includes) { - if ($rawline =~ m@^.\s*\#\s*include\s*\<$inc>@) { - ERROR("DEPRECATED_INCLUDE", - "Don't use <$inc>: see Documentation/feature-removal-schedule.txt\n" . $herecurr); - } +# check for unnecessary blank lines around braces + if (($line =~ /^..*}\s*$/ && $prevline =~ /^.\s*$/)) { + CHK("BRACES", + "Blank lines aren't necessary before a close brace '}'\n" . $hereprev); } - -# don't use deprecated functions - for my $func (@dep_functions) { - if ($line =~ /\b$func\b/) { - ERROR("DEPRECATED_FUNCTION", - "Don't use $func(): see Documentation/feature-removal-schedule.txt\n" . $herecurr); - } + if (($line =~ /^.\s*$/ && $prevline =~ /^..*{\s*$/)) { + CHK("BRACES", + "Blank lines aren't necessary after an open brace '{'\n" . $hereprev); } # no volatiles please @@ -3213,20 +3227,12 @@ sub process { $herecurr); } -# check for needless kfree() checks - if ($prevline =~ /\bif\s*\(([^\)]*)\)/) { - my $expr = $1; - if ($line =~ /\bkfree\(\Q$expr\E\);/) { - WARN("NEEDLESS_KFREE", - "kfree(NULL) is safe this check is probably not required\n" . $hereprev); - } - } -# check for needless usb_free_urb() checks - if ($prevline =~ /\bif\s*\(([^\)]*)\)/) { - my $expr = $1; - if ($line =~ /\busb_free_urb\(\Q$expr\E\);/) { - WARN("NEEDLESS_USB_FREE_URB", - "usb_free_urb(NULL) is safe this check is probably not required\n" . $hereprev); +# check for needless "if (<foo>) fn(<foo>)" uses + if ($prevline =~ /\bif\s*\(\s*($Lval)\s*\)/) { + my $expr = '\s*\(\s*' . quotemeta($1) . '\s*\)\s*;'; + if ($line =~ /\b(kfree|usb_free_urb|debugfs_remove(?:_recursive)?)$expr/) { + WARN('NEEDLESS_IF', + "$1(NULL) is safe this check is probably not required\n" . $hereprev); } } @@ -3344,6 +3350,12 @@ sub process { "Avoid line continuations in quoted strings\n" . $herecurr); } +# check for struct spinlock declarations + if ($line =~ /^.\s*\bstruct\s+spinlock\s+\w+\s*;/) { + WARN("USE_SPINLOCK_T", + "struct spinlock should be spinlock_t\n" . $herecurr); + } + # Check for misused memsets if ($^V && $^V ge 5.10.0 && defined $stat && @@ -3450,8 +3462,22 @@ sub process { # check for multiple semicolons if ($line =~ /;\s*;\s*$/) { - WARN("ONE_SEMICOLON", - "Statements terminations use 1 semicolon\n" . $herecurr); + WARN("ONE_SEMICOLON", + "Statements terminations use 1 semicolon\n" . $herecurr); + } + +# check for switch/default statements without a break; + if ($^V && $^V ge 5.10.0 && + defined $stat && + $stat =~ /^\+[$;\s]*(?:case[$;\s]+\w+[$;\s]*:[$;\s]*|)*[$;\s]*\bdefault[$;\s]*:[$;\s]*;/g) { + my $ctx = ''; + my $herectx = $here . "\n"; + my $cnt = statement_rawlines($stat); + for (my $n = 0; $n < $cnt; $n++) { + $herectx .= raw_line($linenr, $n) . "\n"; + } + WARN("DEFAULT_NO_BREAK", + "switch default: should use break\n" . $herectx); } # check for gcc specific __FUNCTION__ diff --git a/scripts/coccinelle/api/d_find_alias.cocci b/scripts/coccinelle/api/d_find_alias.cocci new file mode 100644 index 00000000000..a9694a8d3e5 --- /dev/null +++ b/scripts/coccinelle/api/d_find_alias.cocci @@ -0,0 +1,80 @@ +/// Make sure calls to d_find_alias() have a corresponding call to dput(). +// +// Keywords: d_find_alias, dput +// +// Confidence: Moderate +// URL: http://coccinelle.lip6.fr/ +// Options: -include_headers + +virtual context +virtual org +virtual patch +virtual report + +@r exists@ +local idexpression struct dentry *dent; +expression E, E1; +statement S1, S2; +position p1, p2; +@@ +( + if (!(dent@p1 = d_find_alias(...))) S1 +| + dent@p1 = d_find_alias(...) +) + +<...when != dput(dent) + when != if (...) { <+... dput(dent) ...+> } + when != true !dent || ... + when != dent = E + when != E = dent +if (!dent || ...) S2 +...> +( + return <+...dent...+>; +| + return @p2 ...; +| + dent@p2 = E1; +| + E1 = dent; +) + +@depends on context@ +local idexpression struct dentry *r.dent; +position r.p1,r.p2; +@@ +* dent@p1 = ... + ... +( +* return@p2 ...; +| +* dent@p2 +) + + +@script:python depends on org@ +p1 << r.p1; +p2 << r.p2; +@@ +cocci.print_main("Missing call to dput()",p1) +cocci.print_secs("",p2) + +@depends on patch@ +local idexpression struct dentry *r.dent; +position r.p2; +@@ +( ++ dput(dent); + return @p2 ...; +| ++ dput(dent); + dent@p2 = ...; +) + +@script:python depends on report@ +p1 << r.p1; +p2 << r.p2; +@@ +msg = "Missing call to dput() at line %s." +coccilib.report.print_report(p1[0], msg % (p2[0].line)) diff --git a/scripts/coccinelle/misc/warn.cocci b/scripts/coccinelle/misc/warn.cocci new file mode 100644 index 00000000000..fda8c3558e4 --- /dev/null +++ b/scripts/coccinelle/misc/warn.cocci @@ -0,0 +1,109 @@ +/// Use WARN(1,...) rather than printk followed by WARN_ON(1) +/// +// Confidence: High +// Copyright: (C) 2012 Julia Lawall, INRIA/LIP6. GPLv2. +// Copyright: (C) 2012 Gilles Muller, INRIA/LiP6. GPLv2. +// URL: http://coccinelle.lip6.fr/ +// Comments: +// Options: -no_includes -include_headers + +virtual patch +virtual context +virtual org +virtual report + +@bad1@ +position p; +@@ + +printk(...); +printk@p(...); +WARN_ON(1); + +@r1 depends on context || report || org@ +position p != bad1.p; +@@ + + printk@p(...); +*WARN_ON(1); + +@script:python depends on org@ +p << r1.p; +@@ + +cocci.print_main("printk + WARN_ON can be just WARN",p) + +@script:python depends on report@ +p << r1.p; +@@ + +msg = "SUGGESTION: printk + WARN_ON can be just WARN" +coccilib.report.print_report(p[0],msg) + +@ok1 depends on patch@ +expression list es; +position p != bad1.p; +@@ + +-printk@p( ++WARN(1, + es); +-WARN_ON(1); + +@depends on patch@ +expression list ok1.es; +@@ + +if (...) +- { + WARN(1,es); +- } + +// -------------------------------------------------------------------- + +@bad2@ +position p; +@@ + +printk(...); +printk@p(...); +WARN_ON_ONCE(1); + +@r2 depends on context || report || org@ +position p != bad1.p; +@@ + + printk@p(...); +*WARN_ON_ONCE(1); + +@script:python depends on org@ +p << r2.p; +@@ + +cocci.print_main("printk + WARN_ON_ONCE can be just WARN_ONCE",p) + +@script:python depends on report@ +p << r2.p; +@@ + +msg = "SUGGESTION: printk + WARN_ON_ONCE can be just WARN_ONCE" +coccilib.report.print_report(p[0],msg) + +@ok2 depends on patch@ +expression list es; +position p != bad2.p; +@@ + +-printk@p( ++WARN_ONCE(1, + es); +-WARN_ON_ONCE(1); + +@depends on patch@ +expression list ok2.es; +@@ + +if (...) +- { + WARN_ONCE(1,es); +- } diff --git a/scripts/config b/scripts/config index ee355394f4e..bb4d3deb6d1 100755 --- a/scripts/config +++ b/scripts/config @@ -101,7 +101,6 @@ while [ "$1" != "" ] ; do case "$CMD" in --keep-case|-k) MUNGE_CASE=no - shift continue ;; --refresh) diff --git a/scripts/pnmtologo.c b/scripts/pnmtologo.c index 5c113123ed9..68bb4efc5af 100644 --- a/scripts/pnmtologo.c +++ b/scripts/pnmtologo.c @@ -74,6 +74,7 @@ static unsigned int logo_height; static struct color **logo_data; static struct color logo_clut[MAX_LINUX_LOGO_COLORS]; static unsigned int logo_clutsize; +static int is_plain_pbm = 0; static void die(const char *fmt, ...) __attribute__ ((noreturn)) __attribute ((format (printf, 1, 2))); @@ -103,6 +104,11 @@ static unsigned int get_number(FILE *fp) val = 0; while (isdigit(c)) { val = 10*val+c-'0'; + /* some PBM are 'broken'; GiMP for example exports a PBM without space + * between the digits. This is Ok cause we know a PBM can only have a '1' + * or a '0' for the digit. */ + if (is_plain_pbm) + break; c = fgetc(fp); if (c == EOF) die("%s: end of file\n", filename); @@ -167,6 +173,7 @@ static void read_image(void) switch (magic) { case '1': /* Plain PBM */ + is_plain_pbm = 1; for (i = 0; i < logo_height; i++) for (j = 0; j < logo_width; j++) logo_data[i][j].red = logo_data[i][j].green = diff --git a/scripts/tags.sh b/scripts/tags.sh index 79fdafb0d26..08f06c00745 100755 --- a/scripts/tags.sh +++ b/scripts/tags.sh @@ -48,13 +48,14 @@ find_arch_sources() for i in $archincludedir; do prune="$prune -wholename $i -prune -o" done - find ${tree}arch/$1 $ignore $prune -name "$2" -print; + find ${tree}arch/$1 $ignore $subarchprune $prune -name "$2" -print; } # find sources in arch/$1/include find_arch_include_sources() { - include=$(find ${tree}arch/$1/ -name include -type d); + include=$(find ${tree}arch/$1/ $subarchprune \ + -name include -type d -print); if [ -n "$include" ]; then archincludedir="$archincludedir $include" find $include $ignore -name "$2" -print; @@ -95,6 +96,32 @@ all_sources() find_other_sources '*.[chS]' } +all_compiled_sources() +{ + for i in $(all_sources); do + case "$i" in + *.[cS]) + j=${i/\.[cS]/\.o} + if [ -e $j ]; then + echo $i + fi + ;; + *) + echo $i + ;; + esac + done +} + +all_target_sources() +{ + if [ -n "$COMPILED_SOURCE" ]; then + all_compiled_sources + else + all_sources + fi +} + all_kconfigs() { for arch in $ALLSOURCE_ARCHS; do @@ -110,18 +137,18 @@ all_defconfigs() docscope() { - (echo \-k; echo \-q; all_sources) > cscope.files + (echo \-k; echo \-q; all_target_sources) > cscope.files cscope -b -f cscope.out } dogtags() { - all_sources | gtags -i -f - + all_target_sources | gtags -i -f - } exuberant() { - all_sources | xargs $1 -a \ + all_target_sources | xargs $1 -a \ -I __initdata,__exitdata,__acquires,__releases \ -I __read_mostly,____cacheline_aligned \ -I ____cacheline_aligned_in_smp \ @@ -173,7 +200,7 @@ exuberant() emacs() { - all_sources | xargs $1 -a \ + all_target_sources | xargs $1 -a \ --regex='/^(ENTRY|_GLOBAL)(\([^)]*\)).*/\2/' \ --regex='/^SYSCALL_DEFINE[0-9]?(\([^,)]*\).*/sys_\1/' \ --regex='/^TRACE_EVENT(\([^,)]*\).*/trace_\1/' \ @@ -220,11 +247,10 @@ xtags() elif $1 --version 2>&1 | grep -iq emacs; then emacs $1 else - all_sources | xargs $1 -a + all_target_sources | xargs $1 -a fi } - # Support um (which uses SUBARCH) if [ "${ARCH}" = "um" ]; then if [ "$SUBARCH" = "i386" ]; then @@ -234,6 +260,21 @@ if [ "${ARCH}" = "um" ]; then else archinclude=${SUBARCH} fi +elif [ "${SRCARCH}" = "arm" -a "${SUBARCH}" != "" ]; then + subarchdir=$(find ${tree}arch/$SRCARCH/ -name "mach-*" -type d -o \ + -name "plat-*" -type d); + for i in $subarchdir; do + case "$i" in + *"mach-"${SUBARCH}) + ;; + *"plat-"${SUBARCH}) + ;; + *) + subarchprune="$subarchprune \ + -wholename $i -prune -o" + ;; + esac + done fi remove_structs= |