http://qs1969.pair.com?node_id=762248
Category: code
Author/Contact Info none
Description: none

sub make_command 
{
    my @arr          = @_;
    for (@arr) 
    {
        $_ = qq["$_"] if /\s/;
    } 
    my $_command_to_execute = join(' ',@arr);
    return ($_command_to_execute);
}
Replies are listed 'Best First'.
Re: Construct command portable way
by ikegami (Patriarch) on May 06, 2009 at 15:30 UTC

      Of course, the multiple argument form of system isn't all that portable, either. On Windows, system(@ARGS) is system("@ARGS"), so you need to take proper care of quoting. On more unixish operating systems, you cannot quote the commands if you're going to use system(LIST), so some more care than in the OP is needed.

      Of course it would be nice if Win32 system() knew when to add double quotes around strings...

        On Windows, system(@ARGS) is system("@ARGS"), so you need to take proper care of quoting.

        No it's not, so no you don't.

        >perl -e"@cmd = ('perl', '-le print for @ARGV', 'foo', 'bar'); system +@cmd;" foo bar >perl -e"@cmd = ('perl', '-le print for @ARGV', 'foo bar'); system @cm +d;" foo bar

        The Windows command line cannot handle some characters. You need to verify for their presence, but you won't be able to quote them.

        Of course it would be nice if Win32 system() knew when to add double quotes around strings...

        ActivePerl does since 5.6.1. Can't verify Perl in general.

        Just adding double quotes is not enough, not even on Windows. How to you pass a double quote as argument to the invoked program (system('/usr/local/bin/foo','-bar','"','-baz','""'))? You need some kind of escaping, and that becomes more and more ugly while the distance to a classic unix /bin/sh grows. I've heard that cmd.exe uses the ^ for some escaping, while command.com just does not have any escaping at all.

        Adding double quotes also is not safe on Unix-like systems, as it does not disable shell interpolation, so you probably want to use single quotes there, or better: Use system(@ARGS).

        I agree that system(@ARGS) on Windows should emulate system(@ARGS) on Unix-like systems, preferably by not messing with cmd.exe/command.com at all. Unfortunately, the Windows API does not offer a way to pass more than a single string to an invoked program, and splitting that string into C's argv is left to the application (or its runtime library). Avoiding command.com/cmd.exe is only the first step.

        Alexander

        --
        Today I will gladly share my knowledge and experience, for there are no sweeter words than "I told you so". ;-)