使用此程序可以粗略的测试linux系统下pv操作的性能。(System V 信号灯)
如下:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ipc.h>
#include <sys/sem.h>
#include <asm/errno.h>
#include <errno.h>
#define key_t double
union semun{
int val;
struct semid_ds *buf;
ushort *array;
}para;
int SemP(int id, int off,int flag);
int SemV(int id, int off);
int main(int argc,char **argv)
{
int semid,oflags,nsems;
int op_flag,id;
char path[256]="";
key_t keyvalue;
int i,ret;
int semsem,looptime;
if(argc != 6){
printf("useage: ./semop pathname nsems op_flag semsem looptime\n");
exit(0);
}
strcpy(path,argv[1]);
nsems = atoi(argv[2]);
op_flag = atoi(argv[3]);
semsem = atoi(argv[4]);
looptime = atoi(argv[5]);
printf("You Input Args is:\n");
printf("path:%s\t nsems:%d\t op_flag:%d\t semsem:%d\t looptime:%d\n",path,nsems,op_flag,semsem,looptime);
oflags = 0666 | IPC_CREAT | IPC_EXCL;
keyvalue = ftok(path, 'S');
if(op_flag == 0){
/* Create Sem */
if((semid = semget(keyvalue,nsems,oflags))<0){
fprintf(stderr,"semget create failed!errno is %d\n",errno);
exit(0);
}
/* Init Sem Values */
for(i=0;i<nsems;i++){
para.val = 1;
if((ret = semctl(semid,i,SETVAL,para))<0)
printf("sem %d set value failed!\n",i);
}
printf("semop create ok!\nsemid is %d\n",semid);
}
/* PV opration */
if(op_flag == 1){
if((semid = semget(keyvalue,0,0666)) < 0){
printf("semget read failed!errno is %d\n",errno);
exit(-1);
}
for(i=0;i<looptime;i++){
if(SemP(semid,semsem,1) < 0){
printf("SemP failed!i=%d\n",i);
exit(-1);
}
if(SemV(semid,semsem) < 0){
printf("SemV failed!i=%d\n",i);
exit(-1);
}
}
}
/* Del Sem */
if(op_flag == 2){
if((semid = semget(keyvalue,0,0666)) < 0){
printf("semget read failed!errno is %d\n",errno);
exit(-1);
}
if((semctl(semid,0,IPC_RMID,0))<0){
printf("semop delete failed!semid is %d\n",semid);
}
else
printf("semop delete ok!\nsemid is %d\n",semid);
}
return 0;
}
int SemP(int id, int off, int flag)
{
int rtn,errno;
struct sembuf p_buf;
p_buf.sem_num = off;
p_buf.sem_op = -1;
if (flag)
p_buf.sem_flg = SEM_UNDO;
while(1)
{
rtn=semop(id, &p_buf, 1);
if( rtn < 0 )
{
if( errno == EINTR ) continue;
else return -1;
}
break;
}
return 0;
}
int SemV(int id, int off)
{
int rtn,errno;
struct sembuf p_buf;
p_buf.sem_num = off;
p_buf.sem_op = 1;
p_buf.sem_flg = SEM_UNDO;
while(1)
{
rtn=semop(id, &p_buf, 1);
if( rtn < 0 )
{
if( errno == EINTR ) continue;
else return -1;
}
break;
}
return 0;
}
参数说明:
op_flag:0代表创建信号灯,1代表进行PV操作,2代表删除信号灯。
执行过程:
首先创建信号灯,其次进行PV操作测试,注意可以在命令执行的前面加上 time 指令,方便时间统计。使用完毕之后删除信号灯即可。
执行脚本:
#bin/sh
time ./semop /tmp 1 1 0 2000000 &
time ./semop /tmp 1 1 1 2000000 &
time ./semop /tmp 1 1 2 2000000 &
time ./semop /tmp 1 1 3 2000000 &
exit