OpenPKG CVS Repository http://cvs.openpkg.org/ ____________________________________________________________________________
Server: cvs.openpkg.org Name: Ralf S. Engelschall Root: /e/openpkg/cvs Email: [EMAIL PROTECTED] Module: openpkg-re Date: 21-Jul-2003 16:46:24 Branch: HEAD Handle: 2003072115462400 Modified files: openpkg-re speclint.pl Log: and hammer it down forever: add a bunch a checks for the source definition and referencing Summary: Revision Changes Path 1.41 +218 -0 openpkg-re/speclint.pl ____________________________________________________________________________ patch -p0 <<'@@ .' Index: openpkg-re/speclint.pl ============================================================================ $ cvs diff -u -r1.40 -r1.41 speclint.pl --- openpkg-re/speclint.pl 21 Jul 2003 12:18:10 -0000 1.40 +++ openpkg-re/speclint.pl 21 Jul 2003 14:46:24 -0000 1.41 @@ -105,6 +105,7 @@ preproc script global + sources )); my @checks = (); if ($check eq 'all') { @@ -887,6 +888,223 @@ $done .= $`; $this = $&; $todo = $'; &lint_warning($file, $done, $this, "found constant \"root\" in %attr (expected variable %{l_susr})"); $done .= $this; + } +} + +## _________________________________________________________________ +## +## CHECK "sources": source file consistency +## _________________________________________________________________ +## + +sub check_sources { + my ($file, $spec) = @_; + + ## + ## PREPARATION + ## + + my $D = {}; + my $S = {}; + my $i = 99; + + # determine defines values + my $done = ''; my $this = ''; my $todo = $spec; + while ($todo =~ m/^\%(define|option)\s+(\S+)\s+(.+)\s*$/m) { + $done .= $`; $this = $&; $todo = $'; + my ($var, $val) = ($2, $3); + $val =~ s|(\%\{([a-zA-Z_][a-zA-Z0-9_]*)\})|defined($D->{$2}) ? $D->{$2} : $1|sge; + $D->{$var} = $val; + $done .= $this; + } + $done = ''; $this = ''; $todo = $spec; + while ($todo =~ m/^([a-zA-Z][a-zA-Z0-9_]+):\s+(.*)$/m) { + $done .= $`; $this = $&; $todo = $'; + my ($var, $val) = (lc($1), $2); + $val =~ s|(\%\{([a-zA-Z_][a-zA-Z0-9_]*)\})|defined($D->{$2}) ? $D->{$2} : $1|sge; + $D->{$var} = $val; + $done .= $this; + } + + # expand define values (allow one level of nesting) + $spec =~ s|(\%\{([a-zA-Z_][a-zA-Z0-9_]*)\})|defined($D->{$2}) ? $D->{$2} : $1|sge; + $spec =~ s|(\%\{([a-zA-Z_][a-zA-Z0-9_]*)\})|defined($D->{$2}) ? $D->{$2} : $1|sge; + + # parse Source# and Patch# headers + $done = ''; $this = ''; $todo = $spec; + while ($todo =~ m/^(Source|Patch)(\d+):[ \t]*(.*?)$/m) { + $done .= $`; $this = $&; $todo = $'; + my ($type, $num, $file) = (lc($1), $2, $3); + my $url = ""; + if ($file =~ m|^(.+/)([^/]+)$|s) { + ($url, $file) = ($1, $2); + } + if (not defined($S->{"$type$num"})) { + $S->{"$type$num"} = { + -type => $type, + -num => $num, + -url => $url, + -file => $file, + -refhdr => 1, + -refcmd => 0, + -refmac => 0, + -refvar => 0, + }; + } + else { + $S->{"$type$num"}->{-refhdr}++; + } + $done .= $this; + } + + # parse %setup and %patch commands + $done = ''; $this = ''; $todo = $spec; + while ($todo =~ m/^\s*\%(setup|patch)(\d+)?(\s+.*)?$/m) { + $done .= $`; $this = $&; $todo = $'; + my ($type, $num, $opts) = ($1, $2, $3); + $type = 'source' if ($type eq 'setup'); + my $num_force = ''; + if ($opts =~ m/\s-(?:a|b)\s*(\d+)/s) { + $num_force = $1; + } + if ($num ne '' and $num_force ne '' and $num ne $num_force) { + &lint_warning($file, $done, $this, "macro and enforced $type number conflict: $num <-> $num_force" . + " (expected either just enforced number or make them match)"); + } + $num = $num_force if ($num_force ne ''); + $num = 0 if ($num eq ''); + next if ($opts =~ m|\s-T|s and $num == 0); + if (not defined($S->{"$type$num"})) { + $S->{"$type$num"} = { + -type => $type, + -num => $num, + -url => "", + -file => "", + -refhdr => 0, + -refcmd => 1, + -refmac => 0, + -refvar => 0, + }; + } + else { + $S->{"$type$num"}->{-refcmd}++; + } + $done .= $this; + } + + # parse %{SOURCE#} and %{PATCH#} macros + $done = ''; $this = ''; $todo = $spec; + while ($todo =~ m/\%\{(SOURCE|PATCH)(\d+)\}/m) { + $done .= $`; $this = $&; $todo = $'; + my ($type, $num) = (lc($1), $2); + if (not defined($S->{"$type$num"})) { + $S->{"$type$num"} = { + -type => $type, + -num => $num, + -url => "", + -file => "", + -refhdr => 0, + -refcmd => 0, + -refmac => 1, + -refvar => 0, + }; + } + else { + $S->{"$type$num"}->{-refmac}++; + } + $done .= $this; + } + + # parse %{SOURCE ...} and %{PATCH ...} macros + $done = ''; $this = ''; $todo = $spec; + while ($todo =~ m/\%\{(SOURCE|PATCH)\s+([^\s}]+)\}/m) { + $done .= $`; $this = $&; $todo = $'; + my ($type, $file) = (lc($1), $2); + my $key = ""; + foreach my $src (keys(%{$S})) { + if ($S->{$src}->{-type} eq $type and $S->{$src}->{-file} eq $file) { + $key = $src; + } + } + if ($key eq '') { + $S->{"$type$i"} = { + -type => $type, + -num => $i, + -url => "", + -file => $file, + -refhdr => 0, + -refcmd => 0, + -refmac => 1, + -refvar => 0, + }; + $i++; + } + else { + $S->{$key}->{-refmac}++; + } + $done .= $this; + } + + # parse $RPM_SOURCE_DIR based references + $done = ''; $this = ''; $todo = $spec; + while ($todo =~ m/\$RPM_SOURCE_DIR\/([^\s;"']+)/m) { + $done .= $`; $this = $&; $todo = $'; + my ($file) = ($1); + my $key = ""; + foreach my $src (keys(%{$S})) { + if ($S->{$src}->{-file} eq $file) { + $key = $src; + } + } + if ($key eq '') { + $S->{"source$i"} = { + -type => "source", + -num => $i, + -url => "", + -file => $file, + -refhdr => 0, + -refcmd => 0, + -refmac => 0, + -refvar => 1, + }; + $i++; + } + else { + $S->{$key}->{-refmac}++; + } + $done .= $this; + } + + ## + ## CHECKING + ## + + # check refernce counts + foreach my $src (%{$S}) { + my $s = $S->{$src}; + my $str_hdr = ($s->{-type} eq 'source' ? 'Source' : 'Patch' ) . $s->{-num}; + my $str_cmd = ($s->{-type} eq 'source' ? '%setup' : '%patch') . $s->{-num}; + my $str_mac = ($s->{-type} eq 'source' ? '%{SOURCE ...}' : '%{PATCH ...}'); + my $str_var = "\$RPM_SOURCE_DIR"; + if ($file !~ m/\b(openpkg-.*|openpkg|vim|ncurses|openssh)\.spec$/) { + if ($s->{-refhdr} > 0) { + if ($s->{-refcmd} == 0 and $s->{-refmac} == 0 and $s->{-refmac} == 0) { + &lint_error($file, undef, undef, "source \"$str_hdr\" defined (file $s->{-file}), but never used" . + " (expected at least one reference via \"$str_cmd\", \"$str_mac\" or \"$str_var\")"); + } + elsif ($s->{-refcmd} > 1) { + &lint_error($file, undef, undef, "source \"$str_hdr\" defined (file $s->{-file}), but used multiple times" . + " (expected just one reference via \"$str_cmd\")"); + } + } + else { + if ($s->{-refcmd}+$s->{-refmac}+$s->{-refmac} > 0) { + &lint_error($file, undef, undef, "source \"$str_hdr\" not defined, but used ". + ($s->{-file} ? "(file ".$s->{-file}.")" : ""). + " (expected at least one definition via \"$str_hdr\")"); + } + } + } } } @@ . ______________________________________________________________________ The OpenPKG Project www.openpkg.org CVS Repository Commit List [EMAIL PROTECTED]