X-Git-Url: http://erislabs.net/gitweb/?a=blobdiff_plain;f=debian%2Fclscan%2Fclscan;h=0e427e203f462d63f0d26b897b0b5304fe61613d;hb=35170063f45ccb74210505c198c8c0ab5c532be0;hp=594452dd42af430d18c8145773532147bf0886d3;hpb=625c08b836bfcb23e37ba1300371d065838392c3;p=gnulib.git diff --git a/debian/clscan/clscan b/debian/clscan/clscan index 594452dd4..0e427e203 100755 --- a/debian/clscan/clscan +++ b/debian/clscan/clscan @@ -17,26 +17,117 @@ our $FILESCACHE="$CLSCANDIR/files.yaml"; our $NEWFILES="$CLSCANDIR/new.txt"; our $COPYRIGHTSTUB="$CLSCANDIR/copyright.in"; +my $gpl_boilerplate=<<"EOL"; + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + . + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + . + You should have received a copy of the GNU General Public License + along with this program. If not, see . +EOL + +my $lgpl2_boilerplate=<<"EOL"; + This program is free software; you can redistribute it and/or modify it + under the terms of the GNU Library General Public License as published + by the Free Software Foundation; either version 2, or (at your option) + any later version. + . + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + . + You should have received a copy of the GNU Library General Public + License along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, + USA. +EOL + +my $lgpl3_boilerplate=<<"EOL"; + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + . + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + . + You should have received a copy of the GNU General Public License + along with this program. If not, see . +EOL + +# license overrides as specified in modules/* +our $module_licenses = { + "public domain" => { + license => "PD", + license_text => "", + }, + "unlimited" => { + license => "other", + license_text => "This file is free software; the Free Software Foundation\n" . + "gives unlimited permission to copy and/or distribute it,\n" . + "with or without modifications, as long as this notice is preserved.\n", + }, + "LGPL" => { + license => "LGPL", + license_text => $lgpl3_boilerplate, + }, + "LGPLv2+" => { + license => "LGPL-2+", + license_text => $lgpl2_boilerplate, + }, + "LGPLv3+" => { + license => "LGPL-3+", + license_text => $lgpl3_boilerplate, + }, + "unmodifiable license text" => { + license => "other", + license_text => "Everyone is permitted to copy and distribute verbatim copies\n" . + "of this license document, but changing it is not allowed.\n", + }, + "GPLed build tool" => { + license => "GPL", + license_text => $gpl_boilerplate, + }, + "GPL" => { + license => "GPL", + license_text => $gpl_boilerplate, + }, +}; + our @filenames=(); -our @modules=(); +our %overrides=(); our $files={}; our $new={}; +our @deleted_files=(); +# actions my $scan=0; my $merge=0; +my $help=0; my $writecopyright=0; usage() unless(@ARGV); -usage() unless GetOptions("scan|s" => \$scan, +usage() unless GetOptions("scan|s" => \$scan, "merge|m" => \$merge, "write|w" => \$writecopyright, - "help|h" => sub { usage(); }); + "help|h" => \$help); +usage() if $help; load_cache(); scan() if($scan); merge() if($merge); write_copyright() if ($merge || $writecopyright); + sub scan { get_filenames(); @@ -44,13 +135,14 @@ sub scan { scan_file($file); } - write_new(); find_deleted(); + write_new(); } sub merge { merge_new(); + load_overrides(); save_cache(); } @@ -73,13 +165,15 @@ sub write_copyright my $licenses={}; for my $file (sort keys(%$files)) { - my $license=$files->{$file}->{license}; + my $license=$files->{$file}->{license_override} || $files->{$file}->{license}; my $copyright=$files->{$file}->{copyright}; - my $license_text=$files->{$file}->{license_text}; + my $license_text=$files->{$file}->{license_text_override} || + $files->{$file}->{license_text}; push(@{$licenses->{$license}->{$license_text}->{$copyright}}, $file); } my %refs=(); my $refnum="00"; + print COPYRIGHT license_trailer(sort keys(%$licenses)); for my $license (sort keys(%$licenses)) { for my $license_text (sort keys(%{$licenses->{$license}})) @@ -96,28 +190,45 @@ sub write_copyright $licensestr .= " [REF$refnum]"; $refs{$licensestr}=$license_text; } + else + { + if(!length($license)) { + $licensestr="unknown"; + } + } for my $copyright (sort keys(%{$licenses->{$license}->{$license_text}})) { next if(!length($license) && !length($copyright) && !length($license_text)); my @filelist=sort @{$licenses->{$license}->{$license_text}->{$copyright}}; - print COPYRIGHT "Files: ", join(', ', @filelist), "\n"; - print COPYRIGHT "Copyright: $copyright\n" if length($copyright); + print COPYRIGHT "Files: ", join(' ', @filelist), "\n"; + print COPYRIGHT "Copyright: ". (length($copyright) ? $copyright : "unknown" ) . "\n"; print COPYRIGHT "License: $licensestr\n" if length($licensestr); print COPYRIGHT "\n"; } } } - for my $ref (sort keys(%refs)) + for my $ref (sort byref keys(%refs)) { print COPYRIGHT "License: $ref\n"; my @text=split(/\n/, $refs{$ref}); + @text=map { ($_ eq "") ? "." : $_; } @text; print COPYRIGHT map { " " . $_ . "\n" } @text; print COPYRIGHT "\n"; } - print COPYRIGHT license_trailer(sort keys(%$licenses)); close(COPYRIGHT); } +sub byref +{ + my $aref=($a=~/\[REF(\d+)\]/)[0]; + my $bref=($b=~/\[REF(\d+)\]/)[0]; + if($aref && $bref) + { + return($aref <=> $bref); + } + return($a cmp $b); +} + sub license_trailer { my @licenses_used=@_; @@ -137,37 +248,36 @@ sub license_trailer }; my %types_found=(); -TYPE: for my $type (reverse sort keys(%$license_data)) + for my $type (reverse sort keys(%$license_data)) { for my $license (@licenses_used) { - if($license =~ /$type(\+|\b)/i) + if($license =~ /$type(\+|\s|$)/i) { $types_found{$type}=1; - # avoid matching eg GPL-2 *and* GPL - next TYPE; } } } - my $text="\n"; + my $text=" .\n"; # if just one, use standard style if(keys(%types_found) == 1) { my ($file, $name)=each(%types_found); - $text .= "The complete text of the $name can be\n"; - $text .= "found in /usr/share/common-licenses/$file\n"; + $text .= " The complete text of the $name can be\n"; + $text .= " found in /usr/share/common-licenses/$file\n"; } else { # more than one, use table. - $text .= "The complete text of standard licenses referenced above\n"; - $text .= "can be found in /usr/share/common-licenses/ as follows:\n\n"; - $text .= sprintf("%-70s %s\n", "LICENSE", "FILE"); + $text .= " The complete text of standard licenses referenced above\n"; + $text .= " can be found in /usr/share/common-licenses/ as follows:\n .\n "; + $text .= sprintf("%-60s %s\n", "LICENSE", "FILE"); for my $type (sort keys(%types_found)) { - $text .= sprintf("%-70s %s\n", $license_data->{$type}, $type); + $text .= sprintf(" %-60s %s\n", $license_data->{$type}, $type); } } + $text .= "\n\n"; return $text; } @@ -243,15 +353,17 @@ sub filechanged { if(exists($files->{$filename}->{copyright})) { - $new->{$filename}->{copyright_old}=$files->{$filename}->{copyright}; + $new->{$filename}->{copyright}=$files->{$filename}->{copyright}; + $new->{$filename}->{copyright_guess}=$copyright_guess; } if(exists($files->{$filename}->{license})) { - $new->{$filename}->{license_old}=$files->{$filename}->{license}; + $new->{$filename}->{license}=$files->{$filename}->{license}; + $new->{$filename}->{license_guess}=$license_guess; } if(exists($files->{$filename}->{license_text})) { - $new->{$filename}->{license_text_old}=$files->{$filename}->{license_text}; + $new->{$filename}->{license_text}=$files->{$filename}->{license_text}; } } } @@ -263,7 +375,7 @@ sub get_filenames sub wanted_files { - if(/^\.git/ || /^\.cvs/ || /^debian/ || /^modules$/) + if(/^\.git/ || /^\.cvs/ || /^debian/ || /^modules$/ || /^\.pc/) { $File::Find::prune=1; } @@ -275,29 +387,21 @@ sub wanted_files sub wanted_modules { - if(/^\./ || /^README$/ || /^COPYING$/) + if(/^\.[^\/]/ || /^README$/ || /^COPYING$/) { $File::Find::prune=1; + return; } elsif(-f) { - push(@modules, $File::Find::name); - } -} - -sub load_overrides -{ - find(\&wanted_modules, "modules/"); - my %modules=(); - for my $module (@modules) - { - unless(open(MOD, $module)) + unless(open(MOD, $File::Find::name)) { - warn("$me: cannot open $module: $!\n"); - next; + warn("$me: cannot open $File::Find::name: $!\n"); + return; } my $infiles=0; my $inlicense=0; + my @files=(); while() { chomp; @@ -307,12 +411,12 @@ sub load_overrides } if($inlicense) { - $modules{$module}->{license}=$_; + push(@{$overrides{$_}},@files); $inlicense=0; } elsif($infiles) { - push(@{$modules{$module}->{files}}, $_); + push(@files, $_); } elsif(/^License:/) { @@ -327,6 +431,31 @@ sub load_overrides } } +sub load_overrides +{ + find({ wanted => \&wanted_modules, no_chdir => 1}, "modules/"); + for my $license (keys(%overrides)) + { + if(!exists($module_licenses->{$license})) + { + die("$me: license override \"$license\" not found in \$module_licenses\n"); + } + my @overridden_files=map { "./" . $_; } @{$overrides{$license}}; + for my $file (@overridden_files) + { + my $override=$module_licenses->{$license}; + if(length($override->{license})) + { + $files->{$file}->{license_override}=$override->{license}; + } + if(length($override->{license_text})) + { + $files->{$file}->{license_text_override}=$override->{license_text}; + } + } + } +} + sub load_cache { @@ -362,7 +491,6 @@ sub write_new unless(keys(%$new)) { warn("$me: no new/changed files found\n"); - return; } unless(open(NEW,">$NEWFILES")) { @@ -373,19 +501,19 @@ sub write_new print NEW "File: $file\n"; print NEW "Hash: ", $new->{$file}->{hash}, "\n"; print NEW "Copyright: ", $new->{$file}->{copyright}, "\n"; - print NEW "License: ", $new->{$file}->{license}, "\n"; - print NEW "License_Text: \n"; - if($new->{$file}->{license_old}) + if($new->{$file}->{copyright_guess}) { - print NEW "#License_old: ", $new->{$file}->{license_old}, "\n"; + print NEW "#Copyright_guess: ", $new->{$file}->{copyright_guess}, "\n"; } - if($new->{$file}->{copyright_old}) + print NEW "License: ", $new->{$file}->{license}, "\n"; + if($new->{$file}->{license_guess}) { - print NEW "#Copyright_old: ", $new->{$file}->{copyright_old}, "\n"; + print NEW "#License_guess: ", $new->{$file}->{license_guess}, "\n"; } - if($new->{$file}->{licence_text_old}) + if($new->{$file}->{license_text}) { - print NEW "#License_text_old: ", $new->{$file}->{licence_text_old}, "\n"; + my @text=split(/\n/, $new->{$file}->{license_text}); + print NEW "\t" . join("\n\t", @text), "\n"; } print NEW "#Header: \n"; my @headerlines=split(/\n/, $new->{$file}->{header}); @@ -393,6 +521,10 @@ sub write_new print NEW join("\n", @headerlines); print NEW "\n\n"; } + if(@deleted_files) + { + print NEW map { "Deleted: $_\n"; } @deleted_files; + } close NEW; } @@ -454,6 +586,13 @@ sub merge_new $in_license_text=1; $license_text=''; } + elsif(/^Deleted:\s*(.*)/) + { + if(exists($files->{$1})) + { + delete($files->{$1}); + } + } else { warn("$me: $NEWFILES: line $line not recognized\n"); @@ -472,19 +611,18 @@ sub merge_new sub find_deleted { - my @deleted=(); my %newnames = map { $_ => 1 } @filenames; for my $file (sort keys(%$files)) { unless(exists($newnames{$file})) { - push(@deleted, $file); + push(@deleted_files, $file); } } - if(@deleted) + if(@deleted_files) { print "Removed files:\n"; - print join("\n", @deleted),"\n"; + print join("\n", @deleted_files),"\n"; } }