2010-08-16 22 views
2

Je cette exigence dans laquelle je dois augmenter la valeur d'un sémaphore POSIX plus de 1.incrémenter la valeur de sémaphores POSIX de plus de 1

Apparemment, il n'y a aucun moyen de spécifications POSIX pour ce faire. Il n'y a pas de sem_setvalue() similaire à sem_getvalue(). Je ne veux pas revenir aux sémaphores de System V juste à cause de cette contrainte.

Existe-t-il un autre moyen d'y parvenir? Ou devrais-je suivre la voie du système V?

Je programme en C sur GNU/Linux.

Un grand merci d'avance.

Répondre

3

Je cette exigence dans laquelle je dois augmenter la valeur d'un sémaphore POSIX plus de 1. Y at-il autre façon d'y arriver? Ou devrais-je suivre la voie du système V?

Alors, quelle est vraiment votre question? Comment implémenter quelque chose qui n'est pas supporté par l'interface? Ou comment créer une structure se comportant comme semaphore en utilisant POSIX? Si cela est plus tard, avant de recourir à des pistolets lourds comme SysV, vous pouvez toujours utiliser la paire pthread_mutex_t/pthread_cond_t pour implémenter à peu près n'importe quelle primitive de synchronisation multi-thread, y compris le sémaphore.

Par ex, non testé:

typedef cool_sem { 
    pthread_mutex_t guard; 
    pthread_cond_t cond; 
    int count; 
} cool_sem_t; 

void init(cool_sem_t *s) 
{ 
    pthread_mutex_init(&s->guard, 0); 
    pthread_cond_init(&s->cond, 0); 
    s->S = 0; 
} 

void incr(cool_sem_t *s, unsigned delta) 
{ 
    assert(s); 
    pthread_mutex_lock(&s->guard); 
    s->S += delta; 
    pthread_cond_broadcast(&s->cond); 
    pthread_mutex_unlock(&s->guard); 
} 

void decr(cool_sem_t *s, unsigned delta) 
{ 
    assert(s); 
    pthread_mutex_lock(&s->guard); 
    do { 
     if (s->S >= delta) { 
      s->S -= delta; 
      break; 
     } 
     pthread_cond_wait(&s->cond, &s->guard); 
    } while (1); 
    pthread_mutex_unlock(&s->guard); 
} 
+1

Il existe plusieurs problèmes avec cette implémentation. La variable 'count' ne reflète pas le nombre de processus en attente sur le sémaphore. Et les processus faisant 'decr()' avec une valeur 'delta' plus basse auront la plupart du temps la priorité sur les processus avec une valeur' delta' plus élevée, ce qui pourrait causer la famine. –

0

Si c'est la spécification complète, je pense que votre professeur veut que vous proposiez un mécanisme qui vous permettra d'incrémenter un sémaphore de plusieurs manières atomiquement. Donc, je suppose que l'une de vos tâches est de synchroniser l'incrémentation.

+0

qui est en partie vrai. Une des options est de rendre l'incrémentation atomique. Mais j'aimerais savoir s'il existe ou non une alternative "élégante" à celle de POSIX (comme c'est le cas dans SysV) – puffadder

1

semctl et semop sont ce que vous need.Use GETVAL REGVAL dans smectl pour getter et setter.Set sem_op dans sembuf struct à ce que vous voulez faire avec le sémaphores lors de l'utilisation semop. Voir l'homme pour plus.

+0

Cela fonctionne sur les sémaphores System V, que l'OP a explicitement exclus. –

1

Non, il n'y a pas une telle alternative lorsque vous travaillez avec sem_t. Si vous ne l'avez pas encore fait, lisez la page de manuel sem_overview sur Linux. Les appels listés ici sont tout ce que vous pouvez obtenir: initialisation à une valeur spécifique, incrémentation et décrémentation de un.