X-Git-Url: https://www.chiark.greenend.org.uk/ucgi/~ian/git?p=subdirmk.git;a=blobdiff_plain;f=generate;h=61bbd507c683adc89d5fe648260737a7c0492e73;hp=c9ade62c3299518c72847b8f8528ffb4764df199;hb=08e825fede28f22ce3fbaf494c3e06360ed74d7a;hpb=32261735a134418b3bc26fc49d816e487b8338e5 diff --git a/generate b/generate index c9ade62..61bbd50 100755 --- a/generate +++ b/generate @@ -173,14 +173,32 @@ sub set_dir_vars ($) { our $err_file; +our @warn_ena_dfl = map { $_ => 1 } qw( + local+global + single-char-var + unknown-warning +); +our %warn_ena = @warn_ena_dfl; + +our $warned; +our %warn_unk; + sub err ($) { my ($m) = @_; die "subdirmk: ${err_file}:$.: $m\n"; } -sub wrn ($) { - my ($m) = @_; - print STDERR "subdirmk: warning: ${err_file}:$.: $m\n"; +sub wrncore ($$) { + my ($wk,$m) = @_; + return 0 unless $warn_ena{$wk} // warn "internal error $wk ?"; + $warned++; + print STDERR "subdirmk: warning ($wk): $m\n"; + return 1; +} + +sub wrn ($$) { + my ($wk,$m) = @_; + wrncore($wk, "${err_file}:$.: $m"); } sub ddbl_only ($) { @@ -257,9 +275,29 @@ sub process_input_mk ($$$$) { $pop_nest->('macro'); od "endef\n"; next; + } elsif (s#^\s*$esc\:warn\s+(\S.*)$##) { + foreach my $wk (split /\s+/, $1) { + my $yes = $wk !~ s{^!}{}; + if (defined $warn_ena{$wk}) { + $warn_ena{$wk} = $yes; + next; + } elsif ($yes) { + wrn 'unknown-warning', + "unknown warning $wk requested"; + } else { + $warn_unk{$wk} //= "$f:$."; + } + } + next; + } elsif (s#^\s*$esc\:local\+global\s+(\S.*)$##) { + foreach my $vn (split /\s+/, $1) { + $vn =~ s{^$esc}{}; + $varref{$vn}{NoWarn} = 1; + } + next; } elsif (s#^\s*$esc\:(?=(-?)include|macro)##) { $buffering_output=''; - } elsif (m#^\s*$esc\:([a-z][-0-9a-z_]*)#) { + } elsif (m#^\s*$esc\:([a-z][-+0-9a-z_]*)#) { err "unknown directive &:$1 or bad argumnt syntax"; } elsif (s{^\s*${esc}TARGETS(?:_([0-9a-zA-Z_]+))?(?=\W)}{}) { my $t = $1 // 'all'; @@ -289,7 +327,7 @@ sub process_input_mk ($$$$) { od $2; if (s{^\$}{}) { od $&; } elsif (m{^[a-zA-Z]\w}) { - wrn + wrn 'single-char-var', 'possibly confusing unbracketed single-char $-expansion'; } elsif (m{^\(($esc)?([^()\$]+)\)} || @@ -402,6 +440,7 @@ sub process_subtree ($$) { my @childpath = (@$path, $child->[0]); my $child_subdir = join '/', @childpath; mkdir $child_subdir or $!==EEXIST or die "mkdir $child_subdir: $!\n"; + local %warn_ena = @warn_ena_dfl; push @{ $targets{$_} }, $child_subdir foreach process_subtree($child, \@childpath); } @@ -474,20 +513,34 @@ sub process_tree() { oraw "include \$(SUBDIRMK_MAKEFILES)\n"; } +sub flmap ($) { local ($_) = @_; s{:(\d+)$}{ sprintf ":%10d", $1 }e; $_; } + sub print_varref_warnings () { foreach my $vn (sort keys %varref) { my $vv = $varref{$vn}; next unless $vv->{''} && $vv->{1}; - print STDERR "subdirmk: warning: saw both $vn and &$vn\n"; + next if $vv->{NoWarn}; + wrncore 'local+global', "saw both $vn and &$vn" or return; foreach my $amp ('', 1) { printf STDERR " saw %s%s at %s\n", ($amp ? '&' : ''), $vn, $_ - foreach sort keys %{ $vv->{$amp} }; + foreach + sort { flmap($a) cmp flmap($b) } + keys %{ $vv->{$amp} }; } } } +sub print_warning_warnings () { + return unless $warned; + foreach my $wk (sort keys %warn_unk) { + wrncore 'unknown-warning', + "$warn_unk{$wk}: attempt to suppress unknown warning(s) \`$wk'"; + } +} + build_tree(); process_tree(); print_varref_warnings(); +print_warning_warnings(); install_output_files();