I've been playing with three scripts for identifying variables in the ports
tree and locating their doc.

I've attached all 3.

Basically: I go
make show=.VARIABLES | lister >fullwords
to extract every relevant public variable name from the tree.

The second script, locatewords, will try to find all variables in manpages.

Coincidentally, it's great at finding badly annotated variables !

The third script, mgrep, looks in MAKEFILE_LIST for a given construct,
helping the user figure out where a variable is defined/used
#! /usr/bin/perl

use v5.36;
my %hash;
my ($pkgpath, $fullpkgpath);

while (<>) {
        chomp;
        if (m/^\=\=\=\>\s+(.*)/) {
                $fullpkgpath = $1;
                $pkgpath = $fullpkgpath;
                $pkgpath =~ s/,.*//;
                say STDERR $pkgpath;
                next;
        }
        for my $word (split /\s+/, $_) {
                next if $word =~ m/^\_/;
                next if $word eq "BULK_$pkgpath";
                next if $word eq "BULK_DO_$pkgpath";
                next if $word eq "BULK_TARGETS_$pkgpath";
                next if $word eq "CLEANDEPENDS_$pkgpath";
                next if $word eq "WRKOBJDIR_$pkgpath";
                next if $word eq "FAKEOBJDIR_$pkgpath";
                next if $word =~ m/^LIB.*_VERSION$/;

                for my $w (qw(COMMENT PKG_ARCH PERMIT_PACKAGE PKGFILE
                    PKGNAME PKGSTEM FULLPKGNAME REVISION EPOCH FULLPKGPATH
                    RUN_DEPENDS WANTLIB LIB_DEPENDS IGNORE ONLY_FOR_ARCHS
                    NOT_FOR_ARCHS PKG_ARGS PREFIX CATEGORIES MESSAGE
                    UNMESSAGE DESCR PLIST STATIC_PLIST PKGSPEC SUBST_CMD)) {
                        $word =~ s/^(\Q$w\E)\-.*/$1/;
                }
                for my $w (qw(SITES DISTFILES SUPDISTFILES PATCHFILES
                    TEMPLATE_DISTFILES TEMPLATE_HOMEPAGE)) {
                        $word =~ s/^(\Q$w\E)\..*/$1/;
                }
                $hash{$word} //= $pkgpath;
        }
}

for my $w (sort keys %hash) {
        say "$w => $hash{$w}";
}
#! /usr/bin/perl

use v5.36;

my %keys;

sub find_manpage($man, $section)
{
        my $f;
        for my $d ("/usr/share/man/", "/usr/X11R6/man", "/usr/local/man") {
                for my $try (split(/,\s+/, $man)) {
                        if (open($f, '<', "$d/man$section/$try.$section")) {
                                return $f;
                        }
                }
        }
        return undef;
}

sub cache_file($man, $section)
{
        my $f = find_manpage($man, $section);
        if (!defined $f) {
                say STDERR "Can't locate $man($section)";
                return;
        }
        my $h = {};
        while (<$f>) {
                chomp;
                if (m/^\.Ev\s+(.*)/) {
                        for my $word (split(/\s+/, $1)) {
                                $h->{$word} = 1;
                        }
                } elsif (m/^\.It\s+Ev\s+(.*)/) {
                        for my $word (split(/\s+/, $1)) {
                                $h->{$word} = 1;
                        }
                }
        }
        $keys{$man.$section} = $h;
        close($f);
}

sub contains($man, $section, $ev)
{
        if (!defined $keys{$man.$section}) {
                cache_file($man, $section);
        }
        if ($keys{$man.$section}{$ev}) {
                return 1;
        } else {
                return 0;
        }
}



open(my $g, '<', "fullwords") or die;
while (<$g>) {
        chomp;
        if (m/^(.*)(\s\=\>.*)/) {
                my ($var, $rest) = ($1, $2);
                my @mans;
                open(my $pipe, "man -k Ev=$var 2>/dev/null|");
                while (<$pipe>) {
                        chomp;
                        if (m/^(.*)\((\dp?)\)\s+\-\s+/) {
                                my ($man, $section) = ($1, $2);
                                if (contains($man, $section, $var)) {
                                        push(@mans, "$man($section)");
                                }
                        }
                }
                close($pipe);
                if (@mans) {
                        say $var.' ('.join(', ', @mans).')'.$rest;
                } else {
                        say $var.$rest;
                }
        }
}

#! /bin/sh
for i in `make show=MAKEFILE_LIST`
do
        grep -l "$1" $i
done

Reply via email to