Non ! C'est le même mutex qui doit servir pour les deux.
Non ! C'est le même mutex qui doit servir pour les deux.
Non ! C'est le même mutex qui doit servir pour les deux.
dans l'article
, kanze à
a écrit le 21/03/06 17:43 :}
void RXEngine::wait() {
mutex.lock();
mutex_priority.lock();
priority = false;
mutex_priority.unlock();
mutex.unlock();
}
Et ici, je ne vois pas du tout où tu attends la condition.
Je demande au moteur de s'arreter au prochain passage sur la
condition.
Non. Tu t'obstines à vouloir séparer deux opérations qui ne
peuvent pas être séparées. La gestion de la condition et les
accès à la variable associée sont indissociable. La
variable, la condition et le mutex forment un tout. En
pseudo-code :
Note bien que la variable fait aussi partie du triplet. On
ne l'utilise que pour ça, et on ne s'amuse pas à la modifier
autrement.
je viens de le comprendre je crois.
En plus, je ne comprends pas la rôle du timer. Si le but est
de mettre un time-out, il existe un appel
pthread_cond_timedwait qui fait l'affaire.
Je programme un jeu de réflexion (Othello). Mon prog joue, sur
un serveur de jeu, des parties simultanées (2 parties
identiques en même temps avec les couleurs inversées) et
synchronisées (les coups sont joués en même temps)
Mon but : après avoir terminé la recherche d'un coup, si
l'adversaire n'a pas encore donné le sien (le prog anticipe le
coup suivant et réfléchi sur le temps adverse). Mon ordinateur
étant mono core je ne peux mené qu'une recherche a la fois. Le
prog possede deux moteurs, un par jeu. Les moteurs
fonctionnent donc alternativement. D'ou mes interruptions
(wait) de recherche (moteur A/B) pour lancer (un nouvelle
recherche si l'anticipation est mauvaise) ou poursuivre (si
l'anticipation est bonne) une recherche sur l'autre jeu
(moteur B/A).
L'ordonnanceur donne la priorité a un moteur en fonction de la
demande du serveur.
Le timer gère le temps (comme sur une partie d'échec)
Aussi : si les classes de wrapper dont tu te sers n'offre
pas la possibilité de faire un scoped_lock, ou quelque chose
du genre, jette-les. Sinon, le moindre truc qui foire, et tu
risques de bloquer toute l'application.
Je travaille avec les thread posix depuis une ou deux semaine
seulement.
dans l'article
1142959397.148181.247350@i40g2000cwc.googlegroups.com, kanze à
kanze@gabi-soft.fr a écrit le 21/03/06 17:43 :
}
void RXEngine::wait() {
mutex.lock();
mutex_priority.lock();
priority = false;
mutex_priority.unlock();
mutex.unlock();
}
Et ici, je ne vois pas du tout où tu attends la condition.
Je demande au moteur de s'arreter au prochain passage sur la
condition.
Non. Tu t'obstines à vouloir séparer deux opérations qui ne
peuvent pas être séparées. La gestion de la condition et les
accès à la variable associée sont indissociable. La
variable, la condition et le mutex forment un tout. En
pseudo-code :
Note bien que la variable fait aussi partie du triplet. On
ne l'utilise que pour ça, et on ne s'amuse pas à la modifier
autrement.
je viens de le comprendre je crois.
En plus, je ne comprends pas la rôle du timer. Si le but est
de mettre un time-out, il existe un appel
pthread_cond_timedwait qui fait l'affaire.
Je programme un jeu de réflexion (Othello). Mon prog joue, sur
un serveur de jeu, des parties simultanées (2 parties
identiques en même temps avec les couleurs inversées) et
synchronisées (les coups sont joués en même temps)
Mon but : après avoir terminé la recherche d'un coup, si
l'adversaire n'a pas encore donné le sien (le prog anticipe le
coup suivant et réfléchi sur le temps adverse). Mon ordinateur
étant mono core je ne peux mené qu'une recherche a la fois. Le
prog possede deux moteurs, un par jeu. Les moteurs
fonctionnent donc alternativement. D'ou mes interruptions
(wait) de recherche (moteur A/B) pour lancer (un nouvelle
recherche si l'anticipation est mauvaise) ou poursuivre (si
l'anticipation est bonne) une recherche sur l'autre jeu
(moteur B/A).
L'ordonnanceur donne la priorité a un moteur en fonction de la
demande du serveur.
Le timer gère le temps (comme sur une partie d'échec)
Aussi : si les classes de wrapper dont tu te sers n'offre
pas la possibilité de faire un scoped_lock, ou quelque chose
du genre, jette-les. Sinon, le moindre truc qui foire, et tu
risques de bloquer toute l'application.
Je travaille avec les thread posix depuis une ou deux semaine
seulement.
dans l'article
, kanze à
a écrit le 21/03/06 17:43 :}
void RXEngine::wait() {
mutex.lock();
mutex_priority.lock();
priority = false;
mutex_priority.unlock();
mutex.unlock();
}
Et ici, je ne vois pas du tout où tu attends la condition.
Je demande au moteur de s'arreter au prochain passage sur la
condition.
Non. Tu t'obstines à vouloir séparer deux opérations qui ne
peuvent pas être séparées. La gestion de la condition et les
accès à la variable associée sont indissociable. La
variable, la condition et le mutex forment un tout. En
pseudo-code :
Note bien que la variable fait aussi partie du triplet. On
ne l'utilise que pour ça, et on ne s'amuse pas à la modifier
autrement.
je viens de le comprendre je crois.
En plus, je ne comprends pas la rôle du timer. Si le but est
de mettre un time-out, il existe un appel
pthread_cond_timedwait qui fait l'affaire.
Je programme un jeu de réflexion (Othello). Mon prog joue, sur
un serveur de jeu, des parties simultanées (2 parties
identiques en même temps avec les couleurs inversées) et
synchronisées (les coups sont joués en même temps)
Mon but : après avoir terminé la recherche d'un coup, si
l'adversaire n'a pas encore donné le sien (le prog anticipe le
coup suivant et réfléchi sur le temps adverse). Mon ordinateur
étant mono core je ne peux mené qu'une recherche a la fois. Le
prog possede deux moteurs, un par jeu. Les moteurs
fonctionnent donc alternativement. D'ou mes interruptions
(wait) de recherche (moteur A/B) pour lancer (un nouvelle
recherche si l'anticipation est mauvaise) ou poursuivre (si
l'anticipation est bonne) une recherche sur l'autre jeu
(moteur B/A).
L'ordonnanceur donne la priorité a un moteur en fonction de la
demande du serveur.
Le timer gère le temps (comme sur une partie d'échec)
Aussi : si les classes de wrapper dont tu te sers n'offre
pas la possibilité de faire un scoped_lock, ou quelque chose
du genre, jette-les. Sinon, le moindre truc qui foire, et tu
risques de bloquer toute l'application.
Je travaille avec les thread posix depuis une ou deux semaine
seulement.
kanze wrote:Non ! C'est le même mutex qui doit servir pour les deux.
je pense que c'est le paquetage qui est bizare.
http://www.partow.net/programming/posixsynchwrapper/index.html
#ifndef INCLUDE_POSIXCONDITION_H
#define INCLUDE_POSIXCONDITION_H
#include <pthread.h>
#include <sys/time.h>
#include "Utils.h"
#include "POSIXMutex.h"
#include "POSIXSynchronousException.h"
#include "POSIXSynchronousEvent.h"
class POSIXCondition
{
public:
POSIXCondition();
POSIXCondition(const POSIXCondition& obj);
~POSIXCondition();
void wait();
bool wait(unsigned int ms);
void signal();
void broadcast();
void lock_mutex();
void unlock_mutex();
private:
pthread_cond_t condition;
POSIXMutex mutex;
bool sent_signal;
unsigned int active_waiters;
};
#endif
void POSIXCondition::wait()
{
mutex.lock(); <=====
active_waiters++;
while (!sent_signal)
{
pthread_cond_wait(&condition, &(mutex.getMutex()));
}
active_waiters--;
if (active_waiters == 0)
sent_signal = false;
mutex.unlock(); <=====
};
j'ai suprimé ces 2 lignes partout dans le code de
POSIXCondition: et appliquer tes conseils et c'est ok.
kanze <kanze@gabi-soft.fr> wrote:
Non ! C'est le même mutex qui doit servir pour les deux.
je pense que c'est le paquetage qui est bizare.
http://www.partow.net/programming/posixsynchwrapper/index.html
#ifndef INCLUDE_POSIXCONDITION_H
#define INCLUDE_POSIXCONDITION_H
#include <pthread.h>
#include <sys/time.h>
#include "Utils.h"
#include "POSIXMutex.h"
#include "POSIXSynchronousException.h"
#include "POSIXSynchronousEvent.h"
class POSIXCondition
{
public:
POSIXCondition();
POSIXCondition(const POSIXCondition& obj);
~POSIXCondition();
void wait();
bool wait(unsigned int ms);
void signal();
void broadcast();
void lock_mutex();
void unlock_mutex();
private:
pthread_cond_t condition;
POSIXMutex mutex;
bool sent_signal;
unsigned int active_waiters;
};
#endif
void POSIXCondition::wait()
{
mutex.lock(); <=====
active_waiters++;
while (!sent_signal)
{
pthread_cond_wait(&condition, &(mutex.getMutex()));
}
active_waiters--;
if (active_waiters == 0)
sent_signal = false;
mutex.unlock(); <=====
};
j'ai suprimé ces 2 lignes partout dans le code de
POSIXCondition: et appliquer tes conseils et c'est ok.
kanze wrote:Non ! C'est le même mutex qui doit servir pour les deux.
je pense que c'est le paquetage qui est bizare.
http://www.partow.net/programming/posixsynchwrapper/index.html
#ifndef INCLUDE_POSIXCONDITION_H
#define INCLUDE_POSIXCONDITION_H
#include <pthread.h>
#include <sys/time.h>
#include "Utils.h"
#include "POSIXMutex.h"
#include "POSIXSynchronousException.h"
#include "POSIXSynchronousEvent.h"
class POSIXCondition
{
public:
POSIXCondition();
POSIXCondition(const POSIXCondition& obj);
~POSIXCondition();
void wait();
bool wait(unsigned int ms);
void signal();
void broadcast();
void lock_mutex();
void unlock_mutex();
private:
pthread_cond_t condition;
POSIXMutex mutex;
bool sent_signal;
unsigned int active_waiters;
};
#endif
void POSIXCondition::wait()
{
mutex.lock(); <=====
active_waiters++;
while (!sent_signal)
{
pthread_cond_wait(&condition, &(mutex.getMutex()));
}
active_waiters--;
if (active_waiters == 0)
sent_signal = false;
mutex.unlock(); <=====
};
j'ai suprimé ces 2 lignes partout dans le code de
POSIXCondition: et appliquer tes conseils et c'est ok.
kanze wrote:
...Plutôt que Boost ou Ace qui m'effraies encore.
Ace m'effraie aussi. D'autant plus qu'il n'a pas marché pour
ce qu'il m'a fallu (un socket UDP), et que j'ai trouvé des
erreurs dans la gestion de thread par ailleurs.
Dans notre projet, nous avons migré notre bus CORBA vers
ACE/TAO et pour uniformiser le code la gestion des threads de
tout nos modules est également passée à ACE.
Pour l'instant nous n'avons pas rencontré de problème
"apparent" (attendons la prochaine demo devant le client ;) )
mais j'aimerai connaitre quelles sont les erreurs de gestions
auquel vous faites référence.
kanze wrote:
...
Plutôt que Boost ou Ace qui m'effraies encore.
Ace m'effraie aussi. D'autant plus qu'il n'a pas marché pour
ce qu'il m'a fallu (un socket UDP), et que j'ai trouvé des
erreurs dans la gestion de thread par ailleurs.
Dans notre projet, nous avons migré notre bus CORBA vers
ACE/TAO et pour uniformiser le code la gestion des threads de
tout nos modules est également passée à ACE.
Pour l'instant nous n'avons pas rencontré de problème
"apparent" (attendons la prochaine demo devant le client ;) )
mais j'aimerai connaitre quelles sont les erreurs de gestions
auquel vous faites référence.
kanze wrote:
...Plutôt que Boost ou Ace qui m'effraies encore.
Ace m'effraie aussi. D'autant plus qu'il n'a pas marché pour
ce qu'il m'a fallu (un socket UDP), et que j'ai trouvé des
erreurs dans la gestion de thread par ailleurs.
Dans notre projet, nous avons migré notre bus CORBA vers
ACE/TAO et pour uniformiser le code la gestion des threads de
tout nos modules est également passée à ACE.
Pour l'instant nous n'avons pas rencontré de problème
"apparent" (attendons la prochaine demo devant le client ;) )
mais j'aimerai connaitre quelles sont les erreurs de gestions
auquel vous faites référence.
Je l'aurais appelé requestWait(),
j'utiliserais deux processus, plutôt que deux threads.
Et pour
s'assurer que l'alternance se fait correctement, plutôt que de
compter sur le fait que l'autre prend la main avant que je ne
reviens le demander, j'utiliserait un sémaphore par thread.
Alors, je ne suis pas sûr d'avoir bien compris. C-à-d qu'on
débloque l'un ou l'autre thread, selon à qui le tour ?
Et que
chaque thread a son propre timer, qui ne tourne que quand le
thread est actif ?
Je l'aurais appelé requestWait(),
j'utiliserais deux processus, plutôt que deux threads.
Et pour
s'assurer que l'alternance se fait correctement, plutôt que de
compter sur le fait que l'autre prend la main avant que je ne
reviens le demander, j'utiliserait un sémaphore par thread.
Alors, je ne suis pas sûr d'avoir bien compris. C-à-d qu'on
débloque l'un ou l'autre thread, selon à qui le tour ?
Et que
chaque thread a son propre timer, qui ne tourne que quand le
thread est actif ?
Je l'aurais appelé requestWait(),
j'utiliserais deux processus, plutôt que deux threads.
Et pour
s'assurer que l'alternance se fait correctement, plutôt que de
compter sur le fait que l'autre prend la main avant que je ne
reviens le demander, j'utiliserait un sémaphore par thread.
Alors, je ne suis pas sûr d'avoir bien compris. C-à-d qu'on
débloque l'un ou l'autre thread, selon à qui le tour ?
Et que
chaque thread a son propre timer, qui ne tourne que quand le
thread est actif ?
Les deux threads partagent un objet important une table de transposition
(implémentée sous la forme d'une table de hashache, tant que les deux jeux
sont identiques c'est un avantage, le moteur A bénéficie des recherches du
moteur B et inversement) après cette grande table (500 Mo) est
"virtuellement" divisée en deux, ce qui evite de la synchronisée
(qui est
aussi un avantage : les deux moteur ne se "polluent" pas)
Les deux threads partagent un objet important une table de transposition
(implémentée sous la forme d'une table de hashache, tant que les deux jeux
sont identiques c'est un avantage, le moteur A bénéficie des recherches du
moteur B et inversement) après cette grande table (500 Mo) est
"virtuellement" divisée en deux, ce qui evite de la synchronisée
(qui est
aussi un avantage : les deux moteur ne se "polluent" pas)
Les deux threads partagent un objet important une table de transposition
(implémentée sous la forme d'une table de hashache, tant que les deux jeux
sont identiques c'est un avantage, le moteur A bénéficie des recherches du
moteur B et inversement) après cette grande table (500 Mo) est
"virtuellement" divisée en deux, ce qui evite de la synchronisée
(qui est
aussi un avantage : les deux moteur ne se "polluent" pas)