a similar topic already came up which was about how to quote shell parameters so they are safe to pass to the shell.
I have another problem, I get as input a string containing the shell command to execute with it's parameters. Now I want to re-quote that so it's not going to execute something unwanted.
e.g. this
is transformed intols -al "file 1" "file'2" ; cat /etc/passwd
and ls will complain about non found files ";" and "cat".ls '-al' 'file 1' 'file'\''2' ';' 'cat' '/etc/passwd'
#!/usr/bin/perl # used http://www.cs.hmc.edu/courses/2003/spring/cs60/fsm.pdf # to transform state machine into regexp $cmd=<>; $arg=""; chomp $cmd; $cmd.=" "; # regexp # ( |([^'"\\ ]+)|(\\.)|("(([^"\\])|(\\.))*")|('[^']*')) # only global matching # ( |(?:[^'"\\ ]+)|(?:\\.)|(?:"(?:(?:[^"\\])|(?:\\.))*")|(?:'[^']*')) # we need to do second subst to remove " and ' pairs and unescape \ so + need some flags # ( |(?:[^'"\\ ]+)|(\\.)|("(?:(?:[^"\\])|(\\.))*")|('[^']*')) while($cmd=~s/^( |(?:[^'"\\ ]+)|(\\.)|("(?:(?:[^"\\])|(\\.))*")|('[^'] +*'))(.*)$/$6/) { $c=$1; # the flags... $esc=$2; $dquote=$3; $dquoteEsc=$4; $squote=$5; print "c=$c arg=$arg cmd=$cmd esc=$esc dquote=$dquote dquoteEsc=$dqu +oteEsc squote=$squote\n"; if($c eq " ") { $arg=~s/'/'\\''/g; # shell escape the ' $res .= "'$arg' "; $arg=""; next; } if(($esc ne "")|($dquoteEsc ne "")) { $c=~s/\\//g } if($dquote ne "") { $c =~ s/^"(.*)"$/$1/} if($squote ne "") { $c =~ s/^'(.*)'$/$1/} $arg .= $c; } print "$res\n";
In reply to safe quoting for shell parameters by Gunstick
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |