semop(2) 

#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/sem.h>

int semop(int semid, struct sembuf *sops, unsigned nsops);

semaphore set의 각각의 semaphore는 
    unsigned short  semval;   /* semaphore value */
    unsigned short  semzcnt;  /* # waiting for zero */
    unsigned short  semncnt;  /* # waiting for increase */
    pid_t           sempid;   /* ID of process that did last op */
를 가지고 있습니다.

semop(2)는 semid에 의해서 식별되는 semaphore set에서 선택된 semaphore에 operation을 수행합니다.

 

파라미터

semid
    - semget(2)에 의해서 얻어진 semaphore set ID
sops
    - semaphore set의 각각의 semaphore에 대한 operation을 수행할 값.
    - 한 번에 여러개의 semaphore에 대해서 operation을 수행할 수 있으며, 
      배열로 또는 malloc(3)으로 여러개를 처리할 수 있습니다.

struct sembuf 
{
        unsigned short sem_num;  /* semaphore 번호 : 0 ~ */
        short          sem_op;   /* semaphore operation */
        short          sem_flg;  /* operation flags */
};

struct sembuf에서
sem_num
    - operation을 수행할 semaphore 번호로 0부터 전체갯수 - 1까지 값을 가집니다.
sem_op 
    - 3가지 경우의 operation을 수행합니다.
 <양수일 때> 프로세스는 쓰기권한이 있어야 합니다.
   semaphore의 값 (semval)을 sem_op만큼 증가 시킵니다. wait없이 바로 수행됩니다.
   
 <0일 때> 프로세스는 읽기 권한을 가지고 있어야 합니다.
   semaphore의 값이 0이 될 때까지 기다립니다. 즉, semval이 0이 되면 바로 정상 return 됩니다.
   그렇지 않으면 sem_flg가 IPC_NOWAIT 이면, errno에 EAGAIN을 설정하고 오류 종료됩니다.
   그렇지 않으면 semzcnt(이 semaphore의 값이 0이 되기를 기다리는 process의 개수)값을 1증가 시키고 
   아래 사항이 될 때까지 sleep상태가 됩니다.
      o  semval이 0되면, semzcnt는 감소합니다.
      o  semaphore set이 semctl(..,IPC_RMID,..)로 삭제되었을 때, semop(2)는 오류가 발생하고 
         errno는 EIDRM로 설정됩니다.
      o  signal이 발생하면 semzcnt 값은 감소되고 semop(2)는 오류가 발생하고 errno는 EINTR가 설정됩니다.

 <음수일 때> 프로세스는 쓰기권한을 가지고 있어야 합니다.
   semval이 sem_op값의 절대값보다 같거나 크면 semval에서 절대값 만큼 빼기를 바로 수행하고 정상 return 합니다.
   그리고, sem_flg에 SEM_UNOD가 설정되면 semadj 값을 sem_op의 절대값 만큼 증가시킵니다.
   semval이 sem_op값의 절대값보다 작고 sem_flg가 IPC_NOWAIT이면 semop()는 오류가 발생하며 
       errno에 EAGAIN을 설정합니다.
   그렇지 않으면 semncnt(semaphore값이 증가되기를 기다리는 프로세스수)를 1증가 시키고 
       아래중의 한가지 사항이 될 때까지 sleep됩니다.
      o  semval이 sem_op보다 같거나 크지면, 위에 설명한 것처럼 바로 실행하고 정상종료합니다.
      o  semaphore set이 semctl(..,IPC_RMID,..)로 삭제되었을 때, 
              semop(2)는 오류가 발생하고 errno는 EIDRM로 설정됩니다.
      o  signal이 발생하면 semzcnt 값은 감소되고 semop(2)는 오류가 발생하고 
              errno는 EINTR가 설정됩니다.

sem_flag 
    - 0, IPC_NOWAIT 또는 SEM_UNDO의 bit or로 설정됩니다.
      IPC_NOWAIT이면 바로 처리할 수 없는 상황이면 EAGAIN 오류로 종료합니다.
      SEM_UNDO가 설정되면 process가 종료되면 자동으로 sem_op를 undo합니다.
nsops
    - sops의 갯수

 

RETURN

0
    - 정상적으로 처리되었습니다.

-1
    - 오류가 발생하였으며, 상세한 오류 내용은 errno에 설정됩니다.

 E2BIG : nsops이 semaphore set을 구성하는 배열의 최대값인 SEMOPM 보다 큽니다.
 EACCES : 처리할 수 있는 권한이 없습니다.
 EAGAIN : sem_flg가 IPC_NOWAIT로 설정되어 대기하지 않고 바로 오류 종료하였습니다.
 EFAULT : sops나 timeout의 메모리 주소가 access할 수 없는 주소입니다.
 EFBIG  : sem_num가 0보다 작거나 semaphore set에 있는 배열의 갯수와 같거나 큽니다.
 EIDRM  : semaphore가 삭제되었습니다.
 EINTR  : blook되어 있는 동안 signal이 발생하였습니다.
 EINVAL : semid가 0보다 작거나 nsops가 0이하의 값입니다.
 ENOMEM : sem_flg가 SEM_UNDO로 설정되어 있고 메모리가 부족하여 undo 구조체를 
          할당할 충분한 메모리를 가지고 있지 않습니다.
 ERANGE : sem_op + semval가 SEMVMX 보다 큽니다.

 

블로그 이미지

사용자 자연&사람

행복한 개발자 programmer since 1995.

Tag , ,

댓글을 달아 주세요