IRIX bash shell expands expression in single quote

2019-08-31 02:43发布

问题:

At the shell, I enter a single-quote and then carriage return and then a series of lines and then another single-quote:

root@aim:/root > '
> @stat = lstat($ARGV[0]);
> if (!@stat) {
if (@stat = lstat($ARGV[0]);) {
> print "nil\n";
> exit 0;
>  }
> '

However, if you notice the interpreted output from the shell:

bash: 
@stat = lstat($ARGV[0]);
if (@stat = lstat($ARGV[0]);) {
print "nil\n";
exit 0;
 }
: command not found
root@aim:/root > uname -a
IRIX64 aim 6.5 04091957 IP27
root@aim:/root > echo $0
-bash
root@aim:/root > 

You notice that !@stat gets converted to @stat = lstat($ARGV[0]);

How should the following shell program be written so that the perl program within it gets interpreted literally?

tramp_perl_file_attributes () {
\perl -e '
@stat = lstat($ARGV[0]);
if (!@stat) {
   print "nil\n";
   exit 0;
}
if (($stat[2] & 0170000) == 0120000)
{
   $type = readlink($ARGV[0]);
   $type = "\"$type\"";
}
elsif (($stat[2] & 0170000) == 040000)
{
   $type = "t";
}
else
{
   $type = "nil"
};
$uid = ($ARGV[1] eq "integer") ? $stat[4] : "\"" . getpwuid($stat[4]) . "\"";
$gid = ($ARGV[1] eq "integer") ? $stat[5] : "\"" . getgrgid($stat[5]) . "\"";
printf(
   "(%s %u %s %s (%u %u) (%u %u) (%u %u) %u.0 %u t (%u . %u) -1)\n",
   $type,
   $stat[3],
   $uid,
   $gid,
   $stat[8] >> 16 & 0xffff,
   $stat[8] & 0xffff,
   $stat[9] >> 16 & 0xffff,
   $stat[9] & 0xffff,
   $stat[10] >> 16 & 0xffff,
   $stat[10] & 0xffff,
   $stat[7],
   $stat[2],
   $stat[1] >> 16 & 0xffff,
   $stat[1] & 0xffff
);' "$1" "$2"
}

回答1:

Escape the ! or disable history expansion (with set +H) while you type the command.

For some reason, ! is expanded from the history (!! gets expanded to the last command you typed on the command line) which shouldn't happen between single quotes.



回答2:

Works perfectly here with bash 4.1.5 under Debian Linux. What version of bash do you have on IRIX? Maybe it's old and buggy? As a workaround, you can use here-docs:

tramp_perl_file_attributes () {
perl - "$1" "$2" <<'EOF'
@stat = lstat($ARGV[0]);
if (!@stat) {
   print "nil\n";
   exit 0;
}
if (($stat[2] & 0170000) == 0120000)
{
   $type = readlink($ARGV[0]);
   $type = "\"$type\"";
}
elsif (($stat[2] & 0170000) == 040000)
{
   $type = "t";
}
else
{
   $type = "nil"
};
$uid = ($ARGV[1] eq "integer") ? $stat[4] : "\"" . getpwuid($stat[4]) . "\"";
$gid = ($ARGV[1] eq "integer") ? $stat[5] : "\"" . getgrgid($stat[5]) . "\"";
printf(
   "(%s %u %s %s (%u %u) (%u %u) (%u %u) %u.0 %u t (%u . %u) -1)\n",
   $type,
   $stat[3],
   $uid,
   $gid,
   $stat[8] >> 16 & 0xffff,
   $stat[8] & 0xffff,
   $stat[9] >> 16 & 0xffff,
   $stat[9] & 0xffff,
   $stat[10] >> 16 & 0xffff,
   $stat[10] & 0xffff,
   $stat[7],
   $stat[2],
   $stat[1] >> 16 & 0xffff,
   $stat[1] & 0xffff
);
EOF
}


标签: bash shell irix