OVH Cloud OVH Cloud

Fork en boucle

6 réponses
Avatar
Georges Kosto
Bonjour,
Je vais essayer d'être le plus claire possible quant à la question qui
motive mon post.
Je cherche à faire un script qui lancera par lot de 3 en parallèle (avec un
fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wai ou
waitpid ).
Une idéé ?
Merci

Georges

Voici le script :
# Les commandes à passer
my @dormir = ("dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh",
"dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh");
# Variable qui incréménte le nombre de fils
my $i=0;
# Total du tableau
my $tot_rrr = @dormir;

# Tant que le tableau contient des commandes
while ( $tot_rrr != "0" ) {
# Si le nombre de fils n'est pas 3 on fork un nouveau fils
if ( $i != "3") {
my $pid = fork();
print "Erreur fork du Child de $$\n" unless defined $pid;
if($pid == 0) {
$proc = shift (@dormir);
exec ("./$proc");
exit(0);

} else {
print "Child $pid en cours\n";
}
$i++;
sleep 2;
}
}

6 réponses

Avatar
tfe
Bonjour,

si c'est le fait de savoir si un fils est toujours en vie qui
t'interesse, tu peux utiliser la commande kill avec l'option "0", qui
effectue un test sur le processus sans le modifier.

Je ne sais pas si cela va t'aider pour autant...

--
tfe
http://tfeserver.be

Georges Kosto ha escrito:

Bonjour,
Je vais essayer d'être le plus claire possible quant à la question qui
motive mon post.
Je cherche à faire un script qui lancera par lot de 3 en parallèle (a vec un
fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wai ou
waitpid ).
Une idéé ?
Merci

Georges

Voici le script :
# Les commandes à passer
my @dormir = ("dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh",
"dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh");
# Variable qui incréménte le nombre de fils
my $i=0;
# Total du tableau
my $tot_rrr = @dormir;

# Tant que le tableau contient des commandes
while ( $tot_rrr != "0" ) {
# Si le nombre de fils n'est pas 3 on fork un nouveau fils
if ( $i != "3") {
my $pid = fork();
print "Erreur fork du Child de $$n" unless defined $pid;
if($pid == 0) {
$proc = shift (@dormir);
exec ("./$proc");
exit(0);

} else {
print "Child $pid en coursn";
}
$i++;
sleep 2;
}
}


Avatar
Georges Kosto
Re,
Oui c'est bien ça en effet, savoir à quel moment le fils n'est plus en vie.
D'ailleurs, merci pour le kill, cela apporte les résultats escomptés avec un
signale user defined :
j'ai déclaré : $SIG{USR1} = "fini"; (fini étant un sub qui décremente ma
variable $i de 1 ), le N° de proc du père my $papa = "$$";
ensuite dans le fork :
system ("./$proc");
kill "USR1",$papa;

Il reste simplement à fairte communiquer fils et père afin de décrément la
variable du while ( pour des raisons de porté de variable ) et ca fonctionne
comme je le souhaite.

Merci
Georges

"tfe" a écrit dans le message de news:

Bonjour,

si c'est le fait de savoir si un fils est toujours en vie qui
t'interesse, tu peux utiliser la commande kill avec l'option "0", qui
effectue un test sur le processus sans le modifier.

Je ne sais pas si cela va t'aider pour autant...

--
tfe
http://tfeserver.be

Georges Kosto ha escrito:

Bonjour,
Je vais essayer d'être le plus claire possible quant à la question qui
motive mon post.
Je cherche à faire un script qui lancera par lot de 3 en parallèle (avec
un

fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wai ou
waitpid ).
Une idéé ?
Merci

Georges

Voici le script :
# Les commandes à passer
my @dormir = ("dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh",
"dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh");
# Variable qui incréménte le nombre de fils
my $i=0;
# Total du tableau
my $tot_rrr = @dormir;

# Tant que le tableau contient des commandes
while ( $tot_rrr != "0" ) {
# Si le nombre de fils n'est pas 3 on fork un nouveau fils
if ( $i != "3") {
my $pid = fork();
print "Erreur fork du Child de $$n" unless defined $pid;
if($pid == 0) {
$proc = shift (@dormir);
exec ("./$proc");
exit(0);

} else {
print "Child $pid en coursn";
}
$i++;
sleep 2;
}
}


Avatar
tfe
Es-tu sur de bon changement de ta variable $i:
si elle est changee dans un fils, le père n'est pas modifié: les fils
contiennent des copies de variables.

perl -e '$i=1; if(fork) { sleep 1; print $i++; } else { print $i; }
print "n"; '
1
1

--
tfe
http://tfeserver.be

Georges Kosto ha escrito:

Re,
Oui c'est bien ça en effet, savoir à quel moment le fils n'est plus e n vie.
D'ailleurs, merci pour le kill, cela apporte les résultats escomptés avec un
signale user defined :
j'ai déclaré : $SIG{USR1} = "fini"; (fini étant un sub qui décr emente ma
variable $i de 1 ), le N° de proc du père my $papa = "$$";
ensuite dans le fork :
system ("./$proc");
kill "USR1",$papa;

Il reste simplement à fairte communiquer fils et père afin de décr ément la
variable du while ( pour des raisons de porté de variable ) et ca fonct ionne
comme je le souhaite.

Merci
Georges

"tfe" a écrit dans le message de news:

Bonjour,

si c'est le fait de savoir si un fils est toujours en vie qui
t'interesse, tu peux utiliser la commande kill avec l'option "0", qui
effectue un test sur le processus sans le modifier.

Je ne sais pas si cela va t'aider pour autant...

--
tfe
http://tfeserver.be

Georges Kosto ha escrito:

Bonjour,
Je vais essayer d'être le plus claire possible quant à la question qui
motive mon post.
Je cherche à faire un script qui lancera par lot de 3 en parallèle (avec
un

fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wa i ou
waitpid ).
Une idéé ?
Merci

Georges

Voici le script :
# Les commandes à passer
my @dormir = ("dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh",
"dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh");
# Variable qui incréménte le nombre de fils
my $i=0;
# Total du tableau
my $tot_rrr = @dormir;

# Tant que le tableau contient des commandes
while ( $tot_rrr != "0" ) {
# Si le nombre de fils n'est pas 3 on fork un nouveau fils
if ( $i != "3") {
my $pid = fork();
print "Erreur fork du Child de $$n" unless defined $pi d;
if($pid == 0) {
$proc = shift (@dormir);
exec ("./$proc");
exit(0);

} else {
print "Child $pid en coursn";
}
$i++;
sleep 2;
}
}




Avatar
Georges Kosto
Oui, en effet, y'a bidouille, le script ci dessous fonctionne mais on ne
teste pas le resultat du fils :

#!/usr/bin/perl -w

my @dormir = (8,10,12,14,16,18,20,22,24,26);
$SIG{USR1} = "fini";
my $i=0;
$| = 1;
my $tot_rrr = @dormir;
my $papa = "$$";
while ( $tot_rrr != "0" ) {
if ( $i != "3") {
$proc = shift (@dormir);
my $pid = fork();
print "Erreur fork du Child de $$n" unless defined $pid;

if($pid == 0) {
sleep $proc;
kill "USR1",$papa;
exit(0);}
else {
print "Child $pid en cours d'execution - Valeur Tableau Dormir :
$tot_rrrn";
$tot_rrr--;
}
$i++;
sleep 2;
}
}

sub fini {
$i--;
}
exit (0);

Georges

Es-tu sur de bon changement de ta variable $i:
si elle est changee dans un fils, le père n'est pas modifié: les fils
contiennent des copies de variables.

perl -e '$i=1; if(fork) { sleep 1; print $i++; } else { print $i; }
print "n"; '
1
1

--
tfe
http://tfeserver.be

Georges Kosto ha escrito:

Re,
Oui c'est bien ça en effet, savoir à quel moment le fils n'est plus en vie.
D'ailleurs, merci pour le kill, cela apporte les résultats escomptés avec un
signale user defined :
j'ai déclaré : $SIG{USR1} = "fini"; (fini étant un sub qui décremente ma
variable $i de 1 ), le N° de proc du père my $papa = "$$";
ensuite dans le fork :
system ("./$proc");
kill "USR1",$papa;

Il reste simplement à fairte communiquer fils et père afin de décrément la
variable du while ( pour des raisons de porté de variable ) et ca fonctionne
comme je le souhaite.

Merci
Georges

"tfe" a écrit dans le message de news:

Bonjour,

si c'est le fait de savoir si un fils est toujours en vie qui
t'interesse, tu peux utiliser la commande kill avec l'option "0", qui
effectue un test sur le processus sans le modifier.

Je ne sais pas si cela va t'aider pour autant...

--
tfe
http://tfeserver.be

Georges Kosto ha escrito:

Bonjour,
Je vais essayer d'être le plus claire possible quant à la question qui
motive mon post.
Je cherche à faire un script qui lancera par lot de 3 en parallèle (avec
un

fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wai ou
waitpid ).
Une idéé ?
Merci

Georges

Voici le script :
# Les commandes à passer
my @dormir = ("dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh",
"dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh", "dodo.sh");
# Variable qui incréménte le nombre de fils
my $i=0;
# Total du tableau
my $tot_rrr = @dormir;

# Tant que le tableau contient des commandes
while ( $tot_rrr != "0" ) {
# Si le nombre de fils n'est pas 3 on fork un nouveau fils
if ( $i != "3") {
my $pid = fork();
print "Erreur fork du Child de $$n" unless defined $pid;
if($pid == 0) {
$proc = shift (@dormir);
exec ("./$proc");
exit(0);

} else {
print "Child $pid en coursn";
}
$i++;
sleep 2;
}
}







Avatar
Nicolas George
"Georges Kosto" wrote in message
<4593ca27$0$25056$:
Je cherche à faire un script qui lancera par lot de 3 en parallèle (avec un
fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wai ou
waitpid ).
Une idéé ?


Tu as besoin que ce soit du perl ? Sinon, tu peux essayer de regarder make,
avec son option -j.

Avatar
Paul Gaborit
À (at) Thu, 28 Dec 2006 14:47:58 +0100,
"Georges Kosto" écrivait (wrote):
Je cherche à faire un script qui lancera par lot de 3 en parallèle (avec un
fork ) un nombre déterminer de commandes ( dans mon cas une centaine ).
Par contre, je n'arrive pas à determiner quand le fils a terminer et par
consequent ma je ne peux pas décrementer ma boucle ( sans utiliser wai ou
waitpid ).


À un moment ou un autre vous voudrez, en plus, récupérer la sortie de
chacune des commandes, gérer les erreurs d'exécution, connaître le
statut final de la commande, etc... Personnellement, pour ce genre de
programmes, j'utilise toujours le module Parallel::Jobs.

--
Paul Gaborit - <http://perso.enstimac.fr/~gaborit/>
Perl en français - <http://perl.enstimac.fr/>