Re: Can't spawn "cmd.exe":
by almut (Canon) on Mar 18, 2009 at 04:35 UTC
|
If the program does run and produce normal output, the message might be due to an
incorrect interpretation of its status/return code1. Maybe
some variation of the issue discussed in What error is "No Error", where the
problem seems to have been a negative return code of the program
in question. What return code do you get when you run the same
command interactively from the command line?
___
1 this is the respective snippet from Perl's win32.c
where the warning (presumably) originates from:
if (status < 0) {
if (ckWARN(WARN_EXEC))
Perl_warner(aTHX_ packWARN(WARN_EXEC), "Can't spawn \"%s\": %s
+", argv[0], strerror(errno));
status = 255 * 256;
}
| [reply] [d/l] [select] |
|
|
| [reply] |
|
|
in windows what would be the "normal" return code, 0 or 1?
0 for success, like unix.
then did echo %ERRORLEVEL% and the value returned was -1.
That's weird. Error codes are unsigned in Win32. IF ERRORLEVEL even relies on that.
@echo off
program.exe
if errorlevel 3 goto ERROR
if errorlevel 1 goto WARNING
rem 0 <= errorlevel < 1
echo Success
goto END
:WARNING
rem 1 <= errorlevel < 3
echo Warning
goto END
:ERROR
rem 3 <= errorlevel
echo Error
:END
That's a very strange error message to return in the event of a negative return code.
No, the message is correct for a negative code being returned from the function that implements system. The problem is that the function is returning negative when the child was successfully launched.
In Win32, exit codes are unsigned 32 bit values. Perl treats it as a signed 32-bit value.
DWORD status;
...
GetExitCodeProcess(ProcessInformation.hProcess, &status);
ret = (int)status;
The second line is a bug. Sufficiently high exit codes will be converted to negative. Negatives are used to signal a problem launching the process.
| [reply] [d/l] [select] |
|
|
|
|
"Normal" return code seems to be zero. E.g., do a "dir" and then echo %ERRORLEVEL%. Now do "dir file_that_doesnt_exist" and echo %ERRORLEVEL% again. Now do "
perl -e exit(-1)".
| [reply] [d/l] |
|
|
echo %ERRORLEVEL% ... Is this the proper way to check this?
Yes, I think so, but I'm no Windows expert...
As to the negative return code, IIRC, I was able to reproduce the
issue last time with a self-compiled perl-5.8.8 on a Win XP (32-bit) vmware
image. Unfortunately, I don't have access to that image at the moment,
and any attempts to reproduce the problem on the Windows box I
currently have access to (XP x64 SP2, with ActiveState's Perl 5.8.8)
have failed so far...
Maybe I'll continue to play with this later. In case I should dig up
something of interest, I'll report back.
| [reply] |
Re: Can't spawn "cmd.exe":
by ikegami (Patriarch) on Mar 18, 2009 at 04:44 UTC
|
In this case I'm not even asking it to start cmd.exe, but yet it's telling me that it can't spawn it.
A command that requires the shell (such as one contains quotes) causes Perl to invoke the shell. This and related details is documented.
"Can't spawn "cmd": Bad file descriptor at temp2.plx line 11."
Are you checking $! to see if an error occurred? That would be incorrect.
.plx? Do you get the error without whatever packager you are using?
| [reply] [d/l] [select] |
|
|
Hi,
I'm not sure what you mean by packager. temp2.plx is just a perl script. As I mentioned above, I don't get the error when that program is run directly in the cmd CLI.
| [reply] |
Re: Can't spawn "cmd.exe":
by ikegami (Patriarch) on Mar 18, 2009 at 15:21 UTC
|
Independent of the problem you are reporting, your usage of system (as follows) is wrong.
my $test = "/C \"C:\\...\\EXCEL.EXE\" C:\\test.xls";
system ("cmd",$test);
You can either pass the whole command as one argument:
my $test = "/C \"C:\\...\\EXCEL.EXE\" C:\\test.xls";
system ("cmd $test");
or pass the arguments separately (note the lack of quotes):
my @test= ("/C", "C:\\...\\EXCEL.EXE", "C:\\test.xls");
system ("cmd", @test);
You are currently relying on a bug.
| [reply] [d/l] [select] |
|
|
| [reply] |
|
|
system documents that the value of $test in system ("cmd",$test); will be passed as a single argument. If system behaved as documented, it would execute
cmd "/C excel.exe text.xls"
cmd does not accept that.
| [reply] [d/l] [select] |
|
|
|
|
|
Re: Can't spawn "cmd.exe":
by Sandy (Curate) on Mar 18, 2009 at 14:50 UTC
|
int
Perl_do_aspawn(pTHX_ SV *really, SV **mark, SV **sp)
{
char **argv;
char *str;
int status;
int flag = P_WAIT;
int index = 0;
if (sp <= mark)
return -1;
get_shell();
Newx(argv, (sp - mark) + w32_perlshell_items + 2, char*);
if (SvNIOKp(*(mark+1)) && !SvPOKp(*(mark+1))) {
++mark;
flag = SvIVx(*mark);
}
while (++mark <= sp) {
if (*mark && (str = SvPV_nolen(*mark)))
argv[index++] = str;
else
argv[index++] = "";
}
argv[index++] = 0;
status = win32_spawnvp(flag,
(const char*)(really ? SvPV_nolen(really) : argv[0]),
(const char* const*)argv);
if (status < 0 && (errno == ENOEXEC || errno == ENOENT)) {
/* possible shell-builtin, invoke with shell */
int sh_items;
sh_items = w32_perlshell_items;
while (--index >= 0)
argv[index+sh_items] = argv[index];
while (--sh_items >= 0)
argv[sh_items] = w32_perlshell_vec[sh_items];
status = win32_spawnvp(flag,
(const char*)(really ? SvPV_nolen(really) : argv[0]
+),
(const char* const*)argv);
}
if (flag == P_NOWAIT) {
PL_statusvalue = -1; /* >16bits hint for pp_system() */
}
else {
if (status < 0) {
if (ckWARN(WARN_EXEC))
Perl_warner(aTHX_ packWARN(WARN_EXEC), "Can't spawn \"%s\": %s
+", argv[0], strerror(errno));
status = 255 * 256;
}
else
status *= 256;
PL_statusvalue = status;
}
Safefree(argv);
return (status);
}
Notice that if the executable returns a negative error code, the assumption is that the spawn didn't work.
| [reply] [d/l] |
Re: Can't spawn "cmd.exe":
by BrowserUk (Patriarch) on Mar 18, 2009 at 11:57 UTC
|
#! /usr/bin/perl -slw
use strict;
print "About to try fail 1";
my $testfile = "test.exe";
my $test = "/C ${testfile} localhost root pwd";
system ("cmd", $test);
print "About to try fail 2";
$test = "${testfile} localhost root pwd";
system ($test);
In the following test.exe just displays its args:
c:\test\test\test>test.pl
About to try fail 1
0 : test.exe
1 : localhost
2 : root
3 : pwd
About to try fail 2
0 : test.exe
1 : localhost
2 : root
3 : pwd
In the first case Perl starts cmd.exe, which runs test.exe. In the second, perl runs test.exe directly. No error messages are produced by either.
What version/build of Perl are you using?
Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
"Science is about questioning the status quo. Questioning authority".
In the absence of evidence, opinion is indistinguishable from prejudice.
| [reply] [d/l] [select] |
|
|
Browser,
It's 5.8.8. I think almut is on to something in his reply concerning negative return codes. Can you verify this by returning -1 from your test executable?
| [reply] |
|
|
C:\test\test\test>test.pl
About to try fail 1
0 : test.exe
1 : localhost
2 : root
3 : pwd
Can't spawn "cmd": No error at C:\test\test\test\test.pl line 7.
About to try fail 2
0 : test.exe
1 : localhost
2 : root
3 : pwd
Can't spawn "test.exe localhost root pwd": No error at C:\test\test\te
+st\test.pl line 11.
Same result whether the return value is -1 or -100_000.
The problem is with Perl's handling of Windows return codes. Trying to force fit a 32-bit signed int into an unsigned char doesn't go :)
As for what constitutes a "valid windows return code"--a signed integer covers it. Long ago, there was a convention that positive return codes were 'informational', negative 'failures', with zero being unadorned success.
Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
"Science is about questioning the status quo. Questioning authority".
In the absence of evidence, opinion is indistinguishable from prejudice.
| [reply] [d/l] |
|
|
|
|
|
Re: Can't spawn "cmd.exe":
by ikegami (Patriarch) on Mar 18, 2009 at 04:45 UTC
|
In this case I'm not even asking it to start cmd.exe, but yet it's telling me that it can't spawn it.
A command that requires the shell (such as one contains quotes) causes Perl to invoke the shell. This and related details is documented.
"Can't spawn "cmd": Bad file descriptor at temp2.plx line 11."
Are you checking $! to see if an error occurred? That would be incorrect.
.plx? Do you get the error without whatever packager you are using?
| [reply] [d/l] [select] |
Re: Can't spawn "cmd.exe":
by Anonymous Monk on Mar 18, 2009 at 04:00 UTC
|
You don't show any error checking, where are you seeing these errors? | [reply] |
Re: Can't spawn "cmd.exe":
by Anonymous Monk on Jul 17, 2012 at 04:10 UTC
|
For me returning -1 from the called script causes the problem.
Returning other values i.e -2 solves the problem. | [reply] |
|
|
I have a script where -1 is being returned from a lot of places which can not be changed. I have used "system" to call that script. Can anyone suggest how to get it working as I am getting the same can't spawn warning which is breaking my other logic.
Thanks in advance
| [reply] |
|
|
no, not without details (code)
| [reply] |