Come puoi implementare una variabile di condizione usando semafori?
-
27-10-2019 - |
Domanda
Qualche tempo fa stavo pensando a come implementare varie primitive di sincronizzazione in termini reciproci. Ad esempio, nelle pThread si ottiene mutex e variabili di condizione e da questi possono costruire semafori.
Nell'API di Windows (o almeno, versioni precedenti dell'API di Windows) ci sono mutex e semafori, ma nessuna variabile di condizione. Penso che dovrebbe essere possibile costruire variabili di condizione da mutex e semafori, ma per la mia vita non riesco proprio a pensare a un modo per farlo.
Qualcuno sa di una buona costruzione per farlo?
Soluzione
Ecco un Documento di Microsoft Research PDF] che si occupa esattamente di questo.
Altri suggerimenti
Un modo per implementare X semafori è quello di aggiungere un processo del server al sistema, utilizzare i semafori per comunicare con esso e far sì che il processo faccia tutto il duro lavoro di implementazione di X. Come esercizio accademico, questo potrebbe essere un imbroglio, ma lo fa Portare il lavoro e può essere più robusto per il comportamento scorretto dai processi del cliente o alla loro morte improvvisa.
Potrei perdere qualcosa qui, ma sembra che ci sia un modo più semplice per implementare una condizione da un semaforo e un blocco rispetto al modo descritto nel documento.
class Condition {
sem_t m_sem;
int m_waiters;
int m_signals;
pthread_mutex_t *m_mutex;
public:
Condition(pthread_mutex_t *_mutex){
sem_init(&this->m_sem,0,0);
this->m_waiters = 0;
this->m_signals = 0;
this->m_mutex = _mutex;
}
~Condition(){}
void wait();
void signal();
void broadcast();
};
void Condition::wait() {
this->m_waiters++;
pthread_mutex_unlock(this->m_mutex);
sem_wait(&this->m_sem);
pthread_mutex_lock(this->m_mutex);
this->m_waiters--;
this->m_signals--;
}
void Condition::signal() {
pthread_mutex_lock(this->m_mutex);
if (this->m_waiters && (this->m_waiters > this->m_signals)) {
sem_post(&this->m_sem);
this->m_signals++;
}
pthread_mutex_unlock(this->m_mutex);
}