Explorar el Código

- enabled locking in shm_malloc/free/...
- added locking test program

Andrei Pelinescu-Onciul hace 24 años
padre
commit
e2a443dfb3
Se han modificado 3 ficheros con 264 adiciones y 2 borrados
  1. 2 2
      shm_mem.h
  2. 30 0
      test/locking/Makefile
  3. 232 0
      test/locking/locking_test.c

+ 2 - 2
shm_mem.h

@@ -38,7 +38,7 @@ inline static void shm_lock()
 	sop.sem_op=-1; /*down*/
 	sop.sem_flg=0 /*SEM_UNDO*/;
 again:
-//	semop(shm_semid, &sop, 1);
+	semop(shm_semid, &sop, 1);
 #if 0
 	switch(ret){
 		case 0: /*ok*/
@@ -63,7 +63,7 @@ inline static void shm_unlock()
 	sop.sem_op=1; /*up*/
 	sop.sem_flg=0 /*SEM_UNDO*/;
 again:
-//	semop(shm_semid, &sop, 1);
+	semop(shm_semid, &sop, 1);
 #if 0
 	/*should ret immediately*/
 	switch(ret){

+ 30 - 0
test/locking/Makefile

@@ -0,0 +1,30 @@
+
+
+
+NAME=locking_test
+
+CC=gcc
+CFLAGS= -O2
+DEFS=
+LIBS=
+
+$(NAME): $(NAME).c
+	gcc $(CFLAGS) $(DEFS) -DNO_LOCK -o $@ $< $(LIBS)
+
+
+$(NAME)_sysv: $(NAME).c
+	gcc $(CFLAGS) $(DEFS) -DSYSV_SEM -o $@ $< $(LIBS)
+
+
+$(NAME)_flock: $(NAME).c
+	gcc $(CFLAGS) $(DEFS) -DFLOCK -o $@ $< $(LIBS)
+
+$(NAME)_lin: $(NAME).c
+	gcc $(CFLAGS) $(DEFS) -DLIN_SEM -o $@ $< $(LIBS) -lpthread
+
+
+all: $(NAME) $(NAME)_sysv $(NAME)_flock $(NAME)_lin
+
+
+clean:
+	rm $(NAME) $(NAME)_sysv $(NAME)_flock $(NAME)_lin

+ 232 - 0
test/locking/locking_test.c

@@ -0,0 +1,232 @@
+/* $Id$ */
+
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+#include <ctype.h>
+#include <netdb.h>
+#include <unistd.h>
+#include <sys/types.h>
+#include <fcntl.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+#ifdef FLOCK
+#include <sys/file.h>
+
+static int lock_fd;
+#endif
+
+#ifdef LIN_SEM
+#include <semaphore.h>
+
+static sem_t sem;
+#endif
+
+#ifdef SYSV_SEM
+#include <sys/ipc.h>
+#include <sys/sem.h>
+
+
+#if defined(__GNU_LIBRARY__) && !defined(_SEM_SEMUN_UNDEFINED)
+	/* union semun is defined by including <sys/sem.h> */
+#else
+	/* according to X/OPEN we have to define it ourselves */
+	union semun {
+		int val;                    /* value for SETVAL */
+		struct semid_ds *buf;       /* buffer for IPC_STAT, IPC_SET */
+		unsigned short int *array;  /* array for GETALL, SETALL */
+		struct seminfo *__buf;      /* buffer for IPC_INFO */
+	};
+#endif
+
+static int semid=-1;
+
+#endif
+
+
+#ifdef NO_LOCK
+	#define LOCK()
+	#define UNLOCK()
+#elif defined SYSV_SEM
+	#define LOCK() \
+	{\
+		struct sembuf sop; \
+		sop.sem_num=0; \
+		sop.sem_op=-1; /*down*/ \
+		sop.sem_flg=0 /*SEM_UNDO*/; \
+		semop(semid, &sop, 1); \
+	}
+
+	#define UNLOCK()	\
+	{\
+		struct sembuf sop;\
+		sop.sem_num=0;\
+		sop.sem_op=1; /*up*/\
+		sop.sem_flg=0 /*SEM_UNDO*/;\
+		semop(semid, &sop, 1);\
+	}
+#elif defined FLOCK
+
+	#define LOCK() \
+		flock(lock_fd, LOCK_EX)
+	#define  UNLOCK() \
+		flock(lock_fd, LOCK_UN)
+#elif defined LIN_SEM
+	#define LOCK() \
+		sem_wait(&sem)
+	#define UNLOCK() \
+		sem_post(&sem);
+#endif
+
+
+
+
+static char *id="$Id$";
+static char *version="locking_test 0.1-"
+#ifdef NO_LOCK
+ "nolock"
+#elif defined SYSV_SEM
+ "sysv_sem"
+#elif defined FLOCK
+ "flock"
+#elif defined LIN_SEM
+ "lin_sem";
+#endif
+;
+static char* help_msg="\
+Usage: locking_test -n address [-c count] [-v]\n\
+Options:\n\
+    -c count      how many times to try lock/unlock \n\
+    -v            increase verbosity level\n\
+    -V            version number\n\
+    -h            this help message\n\
+";
+
+
+
+int main (int argc, char** argv)
+{
+	char c;
+	struct hostent* he;
+	int r;
+	char *tmp;
+	
+	int count;
+	int verbose;
+	char *address;
+#ifdef SYSV_SEM
+	union semun su;
+#endif
+	
+	/* init */
+	count=0;
+	verbose=0;
+	address=0;
+
+
+	opterr=0;
+	while ((c=getopt(argc,argv, "c:vhV"))!=-1){
+		switch(c){
+			case 'v':
+				verbose++;
+				break;
+			case 'c':
+				count=strtol(optarg, &tmp, 10);
+				if ((tmp==0)||(*tmp)){
+					fprintf(stderr, "bad count: -c %s\n", optarg);
+					goto error;
+				}
+				break;
+			case 'V':
+				printf("version: %s\n", version);
+				printf("%s\n",id);
+				exit(0);
+				break;
+			case 'h':
+				printf("version: %s\n", version);
+				printf("%s", help_msg);
+				exit(0);
+				break;
+			case '?':
+				if (isprint(optopt))
+					fprintf(stderr, "Unknown option `-%c´\n", optopt);
+				else
+					fprintf(stderr, "Unknown character `\\x%x´\n", optopt);
+				goto error;
+			case ':':
+				fprintf(stderr, "Option `-%c´ requires an argument.\n",
+						optopt);
+				goto error;
+				break;
+			default:
+					abort();
+		}
+	}
+	
+	/* check if all the required params are present */
+	if(count==0){
+		fprintf(stderr, "Missing count (-c number)\n");
+		exit(-1);
+	}else if(count<0){
+		fprintf(stderr, "Invalid count (-c %d)\n", count);
+		exit(-1);
+	}
+
+#ifdef SYSV_SEM
+	/*init*/
+	puts("Initializing SYS V semaphores\n");
+	semid=semget(IPC_PRIVATE,1,0700);
+	if(semid==-1){
+		fprintf(stderr, "ERROR: could not init sempahore: %s\n",
+				strerror(errno));
+		goto error;
+	}
+	/*set init value to 1 (mutex)*/
+	su.val=1;
+	if (semctl(semid, 0, SETVAL, su)==-1){
+		fprintf(stderr, "ERROR: could not set initial sempahore value: %s\n",
+				strerror(errno));
+		shmctl(semid, IPC_RMID, (union semun)0);
+		goto error;
+	}
+#elif defined FLOCK
+	puts("Initializing flock\n");
+	lock_fd=open("/dev/zero", O_RDONLY);
+	if (lock_fd==-1){
+		fprintf(stderr, "ERROR: could not open file: %s\n", strerror(errno));
+		goto error;
+	}
+#elif defined LIN_SEM
+	puts("Initializing sempahores\n");
+	if (sem_init(&sem, 0, 1)<0){
+		fprintf(stderr, "ERROR: could not initialize sempahore: %s\n",
+				strerror(errno));
+		goto error;
+	}
+#endif
+
+
+	/*  loop */
+	for (r=0; r<count; r++){
+		LOCK();
+		if ((verbose>1)&&(r%1000))  putchar('.');
+		UNLOCK();
+	}
+
+	printf("%d loops\n", count);
+
+#ifdef SYSV_SEM
+	shmctl(semid, IPC_RMID, (union semun)0);
+#elif defined LIN_SEM
+	sem_destroy(&sem);
+#endif
+
+	exit(0);
+
+error:
+	exit(-1);
+}