jim99 has asked for the wisdom of the Perl Monks concerning the following question:

Maybe this is a FAQ, but I can't find it in perlfaq8, or here on perlmonks. On Linux, I call a matlab script from Perl:
1. $matlab_cmd_str = "$path_to_matlab -nodesktop -r my_script"; 2. open(RUN_MATLAB, "$matlab_cmd_str |") or die("Can't run $matlab_cmd_str: $!\n"); 3. while(<RUN_MATLAB>) { 4. print FH "$_"; 5. } 6. my $return_status = close(RUN_MATLAB); 7. unless($return_status) { print STDERR "There was a problem: $?\n" +}

Output sent to the matlab command window is captured to a file. Execution does not get to line 7 until the exit at the end of the matlab script is reached.

However, when I run this on WinXP, the code immediately executes to line 7, instead of waiting until the matlab script completes execution.

I get similar behavior when I replace the piped open with a

$sts = system($matlab_cmd_str);
or with a
my $stdout = qx/$matlab_cmd_str/;
Is there a way of getting the Linux-like behavior on WinXP, so execution of the Perl script pauses until the matlab script completes?

Replies are listed 'Best First'.
Re: Problem invoking Matlab from Perl: works on Linux, fails on Windows
by technojosh (Priest) on Oct 02, 2007 at 21:39 UTC
    Your first "replacement":
    $sts = system($matlab_cmd_str);
    should work like you want it to on a win32 system. The system command has to be told specifically to return before the command completes, and you do not do that here.
Re: Problem invoking Matlab from Perl: works on Linux, fails on Windows
by Anonymous Monk on Oct 02, 2007 at 21:14 UTC
    Yes.

    I vaguely remember something like system(1, $command). You should also check some of the information here.

Re: Problem invoking Matlab from Perl: works on Linux, fails on Windows
by arcnon (Monk) on Oct 03, 2007 at 16:52 UTC
    I read you question but I think this is what you are looking for:
    my $matlab_cmd_str = system("$path_to_matlab -nodesktop -r my_script +"); my $file = "matt_log.txt"; open(F, ">$file") or die "can't open file"; print F $matlab_cmd_str; close(F) or die ""can't close;
      This turned out not to be a Perl issue at all: matlab, when invoked from a Windows command line, returns immediately after launching a separate Matlab process/Windows. When launched from a command line in Unix, Matlab opens in a separate process/window, but the command line process does not exit until a File/Exit in the Matlab window. The Mathworks, makers of matlab, came through with a solution: use an undocumented command line argument in Windows: "-wait". With this arg, the matlab command line process does not exit until Matlab exits. Before this solution appeared, I had come up with another, which seems to work but is far from bulletproof:
      my @matlab_pids_before = find_win32_pids("matlab"); system($matlab_cmd_str) == 0 or die("Unable to invoke $matlab_cmd_str\ +n"); my @matlab_pids_after = find_win32_pids("matlab"); my @pid = find_new_pid(\@matlab_pids_before, \@matlab_pids_after); if ($#pid != 0) { die(sprintf("Expecting one new matlab PID, found %d new matlab pids" +,1+$#pid)); } waitpid($pid[0], 0); # Wait here until Matlab completes.
      This method is not atomic, but will probably be ok in the environment the code will run in. find_win32_pids() uses pslist, a free Microsoft download, that's a ps lookalike. I was unable to get WMIC to work from Perl, although it worked ok from the command line. Thanks to everyone for their help.