Zsh Mailing List Archive
Messages sorted by:
Reverse Date,
Date,
Thread,
Author
Re: completions for make targets?
- X-seq: zsh-users 2402
- From: "Stefan Monnier" <monnier+lists/zsh/users/news/@tequila.cs.yale.edu>
- To: zsh-users@xxxxxxxxxxxxxx
- Subject: Re: completions for make targets?
- Date: 21 Jun 1999 08:05:24 -0400
- Mailing-list: contact zsh-users-help@xxxxxxxxxxxxxx; run by ezmlm
- References: <Pine.SV4.3.93.990621101124.5328A-100000@tagore>
- Sender: monnier@xxxxxxxxxxxxxxxxxxx
>>>>> "Raju" == Raju K V <rajukv@xxxxxxxxxxxxxxxx> writes:
> How can I use compctl to complate make targets?
Admittedly, my solution doesn't exploit compctl too much (maybe
because I had it for tcsh before and just adapted it), but it's
probably a bit fancier (in some respects) than many others:
comp_make () {
local cmd args i where
read -Ac cmd; read -cn where
i=1
while [[ "$i" -lt "$#cmd" ]]; do
if [[ "$cmd[$i]" = "-f" ]]; then
reply=("${(@f)$(~/libexec/complete/make.perl "$cmd[$[$i + 1]]" 2>/dev/null)}")
comp_fixreply
return 0;
else
((i += 1))
fi
done
reply=("${(@f)$(~/libexec/complete/make.perl 2>/dev/null)}")
comp_fixreply
}
compctl -x 'c[-1,-f]' -f -- + -Q -S '' -K comp_make + gmake make
now, you'll notice that this depends on a perl file that does the actual
target extraction. The perl file is appended.
Stefan
#!/usr/bin/env perl
# read all the var definitions into the "vars" hash-table
# and the target lines into the "targetlines" array
sub ReadFile {
local($file) = @_;
local($prevs) = ("");
open(MAKEFILE, "<$file") || return;
for (<MAKEFILE>) {
chomp();
$_ = $prevs . $_; $prevs = "";
if (s/\\$//o ) {
$prevs = $_;
} elsif (/^[- \t]*include[ \t]+([^ \t]+)/) {
push(@includes, $1);
} elsif (/^[ \t]*([-a-zA-Z0-9_.]+)[ \t]*=(.*)$/o) {
$vars{$1} = $2;
} elsif (/^((([-a-zA-Z0-9_ ][-a-zA-Z0-9_. ]*)|(\$\((([^()]+)|(\$\([^()]+\)))\)))+)[\t ]*:/o) {
push(@targetlines, $1);
}
}
close(MAKEFILE);
if ($file = pop(@includes)) {
ReadFile($file);
}
}
# debugging: dump out the vars, their values and the targetlines
#print "**bindings**\n";
#@vars = keys(%vars);
#for (@vars) {
# print "<$_> is <$vars{$_}>\n";
#}
#print "**targets**\n";
#for (@targetlines) {
# print "$_\n";
#}
sub ExpandTargets {
local(@targets);
# look for potential targets (lines with a ":")
for $targets (@targetlines) {
# for each set of targets, look for variables to substitue
while (($var) = $targets =~ /\$\( *([^()\$]*)\)/o ) {
# print "var =$var: <$targets> => <";
# first case: a simple macro
if ($tmpvar = $vars{$var}) {
$var =~ s/([^a-zA-Z0-9 ])/\\$1/og; # quote var
$targets =~ s/\$\( *$var\)/$tmpvar/g ;
#second case: a macro with simple substitution
} elsif (($var0, $s1, $s2) = $var =~ / *(.*):(.*)=(.*)/o) {
if ($tmpvar = $vars{$var0}) {
$s1 =~ s/([^a-zA-Z0-9 ])/\\$1/og; # quote s1
$tmpvar =~ s/$s1/$s2/g ;
$s2 =~ s/([^a-zA-Z0-9 ])/\\$1/og; # quote s2
$var0 =~ s/([^a-zA-Z0-9 ])/\\$1/og; # quote var0
$targets =~ s/\$\( *$var0:$s1=$s2\)/$tmpvar/g ;
} else {
$var0 =~ s/([^a-zA-Z0-9 ])/\\$1/og; # quote var0
$targets =~ s/\$\( *$var0:$s1=$s2\)//g ;
}
} else {
$var =~ s/([^a-zA-Z0-9 ])/\\$1/og; # quote var
$targets =~ s/\$\( *$var\)//g ;
}
# print "$targets>\n";
}
$targets =~ s/:.*$//; # removes anything after a :
# split the "targets line" into an array of targets
@targets = ($targets =~ /([^ ]+)/og );
#put each target into a hash-table (to remove duplicates)
for $target (@targets) {
$targets{$target} = true;
}
}
}
if ($#ARGV < 0) {
if (-r "GNUmakefile") { $file = "GNUmakefile"; }
elsif (-r "Makefile") { $file = "Makefile"; }
elsif (-r "makefile") { $file = "makefile"; }
else { $file = "/dev/null"; }
} else {
$file = $ARGV[0];
}
ReadFile($file);
ExpandTargets();
# dump out the table of targets
for $target (keys(%targets)) { print "$target \n"; }
for $var (keys(%vars)) { print "$var=\n"; }
Messages sorted by:
Reverse Date,
Date,
Thread,
Author