2013-06-20 4 views
1

Когда я запускаю следующий сценарий, он делает именно то, что я хочу, чтобы это сделать, и выходы:Perl - выполнение команд внутри сценария висит

setDisplay.sh:

#!/bin/bash 

Xvfb -fp /usr/share/fonts/X11/misc/ :22 -screen 0 1024x768x16 2>&1 & 
export DISPLAY=:22 

Когда я бегу ./setDisplay.sh , все работает нормально.

ОК, вот где начинается самое интересное ...

У меня есть сценарий Perl, который вызывает setDisplay ...

Вот eamorr.pl сценарий:

#!/usr/bin/perl 

use strict; 
use warnings; 

my $homeDir="/home/eamorr/Dropbox/site/"; 

my $cmd; 
my $result; 

print "-----Setting display...\n"; 
$cmd="sh $homeDir/setDisplay.sh"; 
print $cmd."\n"; 
$result=`$cmd`; 
print $result; 

Это просто зависает, когда я бегу ./eamorr.pl

Я полностью застрял ...

+0

Использование 'sh', когда shebanh является' bash', как правило, плохая идея. –

+0

Не знаю, но если это все, что вы делаете perl-скрипт, вы можете просто выполнить 'exec $ cmd;'. – kjprice

ответ

9

Когда вы сделаете это:

$result=`$cmd`; 

труба создаются соединяющим процесс PERL с внешней командой, и Perl читает из этого канала до конца файла.

Ваша внешняя команда создает фоновый процесс, который по-прежнему имеет трубу на его stdout (а также его stderr, так как вы сделали 2>&1). На этой трубке не будет EOF до тех пор, пока фоновый процесс не выйдет или не закроет его stdout и stderr или не перенаправит их в другом месте.

Если вы собираетесь собирать stdout и stderr Xvfb в переменную perl $result, вам, естественно, придется подождать, пока она закончится. Если вы этого не сделали, я не могу догадаться, что вы пытались сделать с 2>&1.

Также считается, что сценарий, заканчивающийся командой export, является подозрительным. Он может изменить только свою среду, а затем сразу же выходит, поэтому заметного эффекта нет. Обычно это знак того, что кто-то пытается изменить среду родительского процесса, что невозможно.