OVH Cloud OVH Cloud

Attente de donnees...

5 réponses
Avatar
Christophe CLEMENT
Bonsoir,

J'essaye de faire un script qui doit au final recevoir des données de
deux sources différentes : d'une part il écoute le port $port de la
machine, et d'autre part il est connecté à un autre serveur qui peut
lui envoyer de temps à autre un message.

Ce que je veux faire, c'est que dès que je reçoit des données de la
source A, j'appelle la fonction &procedureA, et dès que j'ai des
données de la source B, j'appelle &procedureB.

Mais je n'y arrive pas. Voilà mon bout de code :

for(;;) {
if ($str1 = <$source1>) {
&procedureA($str1);
}
if ($str2 = <$source2>) {
&procedureB($str2);
}
}

Le problème c'est que tant que ça n'a rien lu sur A, il attend, et une
fois qu'il a lu quelque chose, il attend que B envoie quelque chose, et
ne fait rien si A renvoie quelque chose entre temps.
Bref, ça ne marche pas du tout comme je le voudrais.

Mais je suis sûr que quelqu'un ici a la solution ?


Christophe
--
Pour me répondre, cliquez ici -> http://www.75018.org/email.cgi

5 réponses

Avatar
root
On Tue, 10 Feb 2004 20:27:11 +0000, Christophe CLEMENT wrote:

Bonsoir,

J'essaye de faire un script qui doit au final recevoir des données de
deux sources différentes : d'une part il écoute le port $port de la
machine, et d'autre part il est connecté à un autre serveur qui peut lui
envoyer de temps à autre un message.

Ce que je veux faire, c'est que dès que je reçoit des données de la
source A, j'appelle la fonction &procedureA, et dès que j'ai des données
de la source B, j'appelle &procedureB.

Mais je n'y arrive pas. Voilà mon bout de code :

for(;;) {
if ($str1 = <$source1>) {
&procedureA($str1);
}
if ($str2 = <$source2>) {
&procedureB($str2);
}
}
}
Le problème c'est que tant que ça n'a rien lu sur A, il attend, et une
fois qu'il a lu quelque chose, il attend que B envoie quelque chose, et ne
fait rien si A renvoie quelque chose entre temps. Bref, ça ne marche pas
du tout comme je le voudrais.



Voir la fonction select(), IO::Select
(http://search.cpan.org/~nwclark/perl-5.8.3/ext/IO/lib/IO/Select.pm) ou
bien Event (http://search.cpan.org/~jprit/Event-0.87/lib/Event.pod)

Avatar
tyoup
Christophe CLEMENT wrote:
Bonsoir,

J'essaye de faire un script qui doit au final recevoir des données de
deux sources différentes : d'une part il écoute le port $port de la
machine, et d'autre part il est connecté à un autre serveur qui peut
lui envoyer de temps à autre un message.

Ce que je veux faire, c'est que dès que je reçoit des données de la
source A, j'appelle la fonction &procedureA, et dès que j'ai des
données de la source B, j'appelle &procedureB.

Mais je n'y arrive pas. Voilà mon bout de code :

for(;;) {
if ($str1 = <$source1>) {
&procedureA($str1);
}
if ($str2 = <$source2>) {
&procedureB($str2);
}
}

Le problème c'est que tant que ça n'a rien lu sur A, il attend, et une
fois qu'il a lu quelque chose, il attend que B envoie quelque chose, et
ne fait rien si A renvoie quelque chose entre temps.
Bref, ça ne marche pas du tout comme je le voudrais.

Mais je suis sûr que quelqu'un ici a la solution ?


Christophe


il faut utiliser la fonction select pour savoir quels fichiers sont
disponibles en lecture. il y a également l'interface IO::select.

--
tyoup

Avatar
Christophe CLEMENT

Voir la fonction select(), IO::Select
(http://search.cpan.org/~nwclark/perl-5.8.3/ext/IO/lib/IO/Select.pm) ou
bien Event (http://search.cpan.org/~jprit/Event-0.87/lib/Event.pod)


Merci à toi et à Tyoup. Hier soir, j'ai essayé de refaire mon code avec
ça, mais je me heurte à un autre problème. En fait mon script se
connecte à un serveur distant et est lui-même un serveur qui est censé
accepter un client (ou éventuellement plusieurs clients).

Pour lancer le serveur, je procède ainsi :

use IO::Socket;
use IO::Select;

$sel = new IO::Select();

my $server = IO::Socket::INET->new(
LocalPort => 1234,
Type => SOCK_STREAM,
Listen => 1,
ReuseAddr => 1) or die "Impossible de lancer le serveur : $@n";

# puis je rajoute $server dans $sel, comme vous me l'avez dit hier :

$sel->add($server);

while(@ready = $sel->can_read) {
foreach $fh (@ready) {
if ($fh == $server) {
# et c'est là que je bloque...
($client) = $server->accept;
print <$client>."n";
}
}
}

Le problème c'est que ça ne marche qu'avec la première ligne que le
client envoie, après, le client peut continuer à renvoyer des lignes,
le serveur semble les ignorer...
Ça vient sûrement de moi qui n'ai pas trop compris le module
IO::Socket::INET. Si quelqu'un pouvait m'aider à corriger cette petite
partie du code, ça serait simpa.


Christophe
--
Pour me répondre, cliquez ici -> http://www.75018.org/email.cgi

Avatar
Paul GABORIT
À (at) 11 Feb 2004 20:30:38 GMT,
"Christophe CLEMENT" écrivait (wrote):
[...]
# puis je rajoute $server dans $sel, comme vous me l'avez dit hier :

$sel->add($server);

while(@ready = $sel->can_read) {
foreach $fh (@ready) {
if ($fh == $server) {
# et c'est là que je bloque...
($client) = $server->accept;
print <$client>."n";
}
}
}

Le problème c'est que ça ne marche qu'avec la première ligne que le
client envoie, après, le client peut continuer à renvoyer des lignes,
le serveur semble les ignorer...


Une fois établie la connexion avec le client, il faut surveiller ce qui
arrive. Donc, ajoutez $client dans $sel pour que 'select' puisse vous prévenir
de l'arrivée de nouvelles données depuis le client. Si 'select' déclenche sur
une entrée alors qu'il n'y a rien à lire, c'est que la connexion se ferme.

En fait vous avez toujours n+1 entrées à surveiller : une pour les nouvelles
connexions (pour vous, $server) plus une pour chacun des clients connectés
(les différents $client que vous créez).

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

Avatar
Christophe CLEMENT
Le 12/02/2004 vers 11h57, Paul GABORIT a

Une fois établie la connexion avec le client, il faut surveiller ce qui
arrive. Donc, ajoutez $client dans $sel pour que 'select' puisse vous prévenir
de l'arrivée de nouvelles données depuis le client. Si 'select' déclenche sur
une entrée alors qu'il n'y a rien à lire, c'est que la connexion se ferme.


Effectivement, maintenant ça marche !

En fait vous avez toujours n+1 entrées à surveiller : une pour les nouvelles
connexions (pour vous, $server) plus une pour chacun des clients connectés
(les différents $client que vous créez).


Merci beaucoup !


Christophe
--
Pour me répondre, cliquez ici -> http://www.75018.org/email.cgi