Ejemplo Semaforo

#include "stdio.h" 
#include "sys/types.h" 
#include "sys/ipc.h" 
#include "sys/sem.h" 
#include "sys/time.h" 
#include "unistd.h" 
#include "errno.h" 
#define ESPERA 1000 // Son los microsegundos de espera usados para asegurar 
                    // la finalizaci�n del quantum. 

/********************************************************************** 
 * 
 * PROBAR EL SISTEMA CON Y SIN LAS OPERACIONES P Y V  
 * 
**********************************************************************/ 

main() 
{ 
int pid;  /* identifica el proceso hijo */ 
int mutex;  /* semaforo binario */ 

mutex=inicia(1); 

if (0==(pid=fork())) 
  proceso_hijo(mutex); 
else 
 proceso_padre(mutex); 

borra_s(mutex); 
} 

/********************************************************************** 
 * 
 * Tanto el proceso hijo como el padre escriben 30 secuencias de 80 caracteres 
 * 
**********************************************************************/ 

proceso_hijo(critica) 
int critica; 
{ 
/* escribe 30 ristras de 80 caracteres '+' */ 
int i,j; 

for (i=0;i< 30; i++) { 
P(critica); 
  for (j=0; j<80; j++) { 
    printf("+"); 
    fflush(stdout); 
    // Provocamos la finalizaci�n del quantum de tiempo 
    retardo (); 
  } 
  
  printf("\n"); 
V(critica); 
 } 

exit(); 
} 
  

proceso_padre(critica) 
int critica; 
{ 
/* escribe 30 ristras de 80 caracteres '-' */ 
int i,j; 

for (i=0;i< 30; i++) { 
P(critica);  
  for (j=0; j<80; j++) { 
    printf("-"); 
    fflush (stdout); 
    // Provocamos la finalizaci�n del quantum de tiempo 
    retardo (); 
  } 
printf("\n"); 
V(critica); 
} 
 wait(0); /* espera a que finalice el hijo */ 
} 

/********************************************************************** 
 * 
 * Provocamos la espera durante ESPERA microsegundos 
 * 
**********************************************************************/ 
retardo() 
{ 

struct timeval tiempo; 
struct timezone tz; 
unsigned long inicio, ahora; 

gettimeofday(&tiempo, &tz); 
ahora = inicio = tiempo.tv_sec * 1000000 + tiempo.tv_usec; 

//  ESPERA microsegs 
while (ahora < inicio + ESPERA) { 
  gettimeofday(&tiempo, &tz); 
  ahora = tiempo.tv_sec * 1000000 + tiempo.tv_usec; 
} 

} 

/*********************************************************************** 
  * 
  * Rutinas de manejo de sem�foros 
  * 
***********************************************************************/ 

inicia(valor) 
int valor; 
{ 
int semval; 
int id; 
union semun { 
  int val; 
  struct semid_ds *buf; 
  ushort *array; 
} arg; 

  if ((id=semget(IPC_PRIVATE, 1, (IPC_CREAT|0666))) == -1) { 
    perror("Error al crear el sem�foro."); 
    return(-1); 
  } 

  arg.val = valor; 
  if (semctl(id, 0, SETVAL, arg) == -1) { 
    perror("Error al inicializar el sem�foro."); 
    return (-1); /*error en inicializacion*/ 
  } 
  return(id); 
} 

/*Rutina P */ 

P(semaforo) 
int semaforo; 
{ 
  if ( semcall(semaforo, -1) == -1 )  
    perror("Error en operaci�n P."); 
} 

/*Rutina V */ 

V(semaforo) 
int semaforo; 
{ 
  if ( semcall(semaforo, 1) == -1 )  
    perror("Error en operaci�n V."); 
} 

semcall(semaforo, operacion) 
int semaforo, operacion; 
{ 
  struct sembuf sb; 
  sb.sem_num = 0; 
  sb.sem_op = operacion; 
  sb.sem_flg = 0; 

  return ( semop(semaforo, &sb, 1) ); /*devuelve -1 si error */ 
} 

borra_s(semaforo) 
int semaforo; 
{ 

  if ( semctl(semaforo, 0, IPC_RMID, 0) == -1) { 
    perror("Error al eliminar el sem�foro."); 
    return(-1); 
  } 

} 
 

  

En esta parte se puede descargar el programa


Hosted by www.Geocities.ws

1