#include <stdio.h>
#include <sys/types.h>
#include <sys/sem.h>
#include <sys/ipc.h>
//#include <linux/sem.h>
#include <unistd.h>
#include <errno.h>
#include "mysem.h"
#define SEM_KEY 7589
#define SEMSIZE 5
static int mysem_id = -1;
union semun{
int val;
struct semid_ds *buf;
unsigned short *array;
};
void init_mysem(int ini_flag)
{
key_t key;
int i;
struct sembuf op;
union semun arg;
// op.sem_num = s_id;
op.sem_op = 1;
op.sem_flg = 0;
// key=ftok(PATHNAME,'O');
if((mysem_id=semget(SEM_KEY,SEMSIZE,IPC_CREAT|0666))==-1){
perror("semget err!\n");
exit(-1);
}
if(ini_flag == 1){
arg.array = (unsigned short *) calloc(SEMSIZE,sizeof(unsigned short));
if(arg.array == NULL){
printf("No enough memory to calloc!\n");
exit(-1);
}
for(i=0;i<SEMSIZE;i++){
arg.array[i] = 1;
}
if(semctl(mysem_id,0,SETALL,arg) == -1){
perror("semctl err:");
exit(-1);
}
}
}
void init_mysemvalue(int s_id,int ini_value)
{
key_t key;
int i;
struct sembuf op;
union semun arg;
// op.sem_num = s_id;
op.sem_op = 1;
op.sem_flg = 0;
// key=ftok(PATHNAME,'O');
if(mysem_id == -1){
if((mysem_id=semget(SEM_KEY,SEMSIZE,IPC_CREAT|0666))==-1){
perror("semget err!\n");
exit(-1);
}
}
/*arg.array = (unsigned short *) calloc(SEMSIZE,sizeof(unsigned short));
if(arg.array == NULL){
printf("No enough memory to calloc!\n");
exit(-1);
}
arg.array[s_id] = ini_value;*/
arg.val = ini_value;
if(semctl(mysem_id,s_id,SETVAL,arg) == -1){
perror("semctl err:");
exit(-1);
}
}
int getmysemvalue(int s_id)
{
int i_value;
if(mysem_id == -1){
if((mysem_id=semget(SEM_KEY,SEMSIZE,IPC_CREAT|0666))==-1){
perror("semget err!\n");
exit(-1);
}
}
i_value = semctl(mysem_id,s_id,GETVAL);
if(i_value == -1){
perror("semctl err:");
exit(-1);
}
return i_value;
}
void mywait(int s_id)
{
struct sembuf op;
int i_result;
op.sem_num = s_id;
op.sem_op = -1;
op.sem_flg = SEM_UNDO;
if(mysem_id == -1)
init_mysem(0);
while((i_result = semop(mysem_id,&op,1)) == -1 && errno == EINTR) usleep(5000);
if(i_result==-1){
printf("mywait sid = %d errno = %d %s\n",s_id,errno,strerror(errno));
if(errno == ERANGE){
printf("semval = %d\n",getmysemvalue(s_id));
}
perror("semop err!\n");
exit(-1);
}
}
void mysignal(int s_id)
{
struct sembuf op;
int i_result;
op.sem_num = s_id;
op.sem_op = 1;
op.sem_flg = SEM_UNDO;
if(mysem_id == -1)
init_mysem(0);
while((i_result = semop(mysem_id,&op,1)) == -1 && errno == EINTR) usleep(5000);
if(i_result==-1){
printf("mysignal s_id = %d errno = %d %s\n",s_id,errno,strerror(errno));
if(errno == ERANGE){
printf("semval = %d\n",getmysemvalue(s_id));
}
perror("semop err!\n");
exit(-1);
}
}
void myuwait(int s_id)
{
struct sembuf op;
int i_result;
op.sem_num = s_id;
op.sem_op = -1;
op.sem_flg = 0;
if(mysem_id == -1)
init_mysem(0);
while((i_result = semop(mysem_id,&op,1)) == -1 && errno == EINTR) usleep(5000);
if(i_result==-1){
printf("myuwait s_id = %d errno = %d %s\n",s_id,errno,strerror(errno));
if(errno == ERANGE){
printf("semval = %d\n",getmysemvalue(s_id));
}
perror("semop err!\n");
exit(-1);
}
}
void myusignal(int s_id)
{
struct sembuf op;
int i_result;
op.sem_num = s_id;
op.sem_op = 1;
op.sem_flg = 0;
if(mysem_id == -1)
init_mysem(0);
while((i_result = semop(mysem_id,&op,1)) == -1 && errno == EINTR) usleep(5000);
if(i_result==-1){
printf("myusignal s_id = %d errno = %d %s\n",s_id,errno,strerror(errno));
if(errno == ERANGE){
printf("semval = %d\n",getmysemvalue(s_id));
}
perror("semop err!\n");
exit(-1);
}
}