-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy path_C
executable file
·114 lines (93 loc) · 2.66 KB
/
_C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
#!/usr/bin/perl -w
# Tue May 4 07:00:03 EDT 2010
my $copyright= <<'COPYRIGHT';
# Copyright 2010-2023 by Christian Jaeger <ch@christianjaeger.ch>
# Published under the same terms as perl itself
COPYRIGHT
my ($email_full)= $copyright=~ / by ([^\n]*)/s;
use strict;
use Chj::xtmpfile;
use Chj::singlequote qw(possibly_singlequote_sh);
use Chj::xperlfunc 'xchmod';
$0=~ /(.*?)([^\/]+)\z/s or die "?";
my ($mydir, $myname)=($1,$2);
my $is_CC = $myname eq "CC";
my $is_C_ = $myname eq "C_";
sub usage {
print STDERR map{"$_\n"} @_ if @_;
print "$myname cmd [args] _ [other args [ _ [further args]]]
Returns the path to a script that when called replaces the '_' with
the script arguments in the same order. I.e. the same as: \$(lambda
'cmd args \"\$1\" other args \"\$2\" further args').
When called as 'C', the generated script will not accept further
arguments. When called as 'CC', the script passes further arguments
as additional arguments to cmd. When called as 'C_', the script
ignores further arguments.
($email_full)
";
exit (@_ ? 1 : 0);
}
usage unless @ARGV;
usage if (@ARGV==1 and ($ARGV[0] eq "-h" or $ARGV[0] eq "--help"));
my $t= xtmpfile;
# need the number of _ already; so choose to walk @ARGV twice
my $n = do {
my $n=0;
for (@ARGV) {
if ($_ eq "_") {
$n++
}
}
$n
};
# also produce the call code twice: here for display, later with '_'
# replaced by positional argument references
my $origcode= join(" ", map{possibly_singlequote_sh $_} @ARGV);
if ($is_CC or $is_C_) {
$t->xprint('#!/bin/bash
set -eu
if [ $# -lt '.$n.' ]; then
echo "$0 ("'.possibly_singlequote_sh($origcode).'"): '.
'got $# arguments, expecting at least '.$n.'"
exit 1
fi
');
} else {
$t->xprint('#!/bin/bash
set -eu
if [ $# -ne '.$n.' ]; then
echo "$0 ("'.possibly_singlequote_sh($origcode).'"): '.
'got $# arguments, expecting '.$n.'"
exit 1
fi
');
}
# now with '_' replaced with positional argument references:
my $i=1;
for (@ARGV) {
$t->xprint(
do {
if ($_ eq "_") {
'"$'.($i++).'"'
} else {
possibly_singlequote_sh $_
}
},
" ");
}
if ($is_CC) {
# Get the slice of $@ after the elements used to replace '_'s:
# (mis-setting slice len to just $# but hey, so what, is it not OK
# to let the C code cap that?). Also, @ is 1-based (?! the special
# cases? `arr=("$@")` would allow arr to be accessed by $n.).
$t->xprint('"${@:'.($n + 1).':$#}"');
}
$t->xprintln;
$t->xclose;
$t->autoclean(0);
my $path= $t->path;
xchmod 0700, $path;
print $path, "\n"
or die $!;
#use Chj::ruse;
#use Chj::Backtrace; use Chj::repl; repl;