sysv semaphore broken
Maxim Konovalov
maxim at macomnet.ru
Thu Jun 29 11:06:41 UTC 2006
On Thu, 29 Jun 2006, 12:48+0400, Maxim Konovalov wrote:
> On Thu, 29 Jun 2006, 15:39+0800, David Xu wrote:
>
> > Is sysv semaphore broken ? all super-smack processes are
> > stucked at "semwai" state now.
>
> There was a report that recent commit broke sysv sems. Looking at it
> ATM.
>
> [root at fujic /usr/src/tools/regression/sysvsem]# make regress
> semtest: semctl IPC_STAT: Invalid argument
> semtest: semctl IPC_RMID: Invalid argument
> FAIL
Something like that should fix the issue:
Index: sysv_sem.c
===================================================================
RCS file: /home/ncvs/src/sys/kern/sysv_sem.c,v
retrieving revision 1.80
diff -u -p -r1.80 sysv_sem.c
--- sysv_sem.c 27 Jun 2006 18:28:50 -0000 1.80
+++ sysv_sem.c 29 Jun 2006 11:00:43 -0000
@@ -586,7 +586,7 @@ kern_semctl(struct thread *td, int semid
{
u_short *array;
struct ucred *cred = td->td_ucred;
- int i, rval, error;
+ int i, rval, error, savedid;
struct semid_ds sbuf;
struct semid_kernel *semakptr;
struct mtx *sema_mtxp;
@@ -632,6 +632,7 @@ kern_semctl(struct thread *td, int semid
return (error);
}
+ savedid = semid;
semid = IPCID_TO_IX(semid);
if (semid < 0 || semid >= seminfo.semmni)
return (EINVAL);
@@ -655,7 +656,7 @@ kern_semctl(struct thread *td, int semid
switch (cmd) {
case IPC_RMID:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_M)))
goto done2;
@@ -687,7 +688,7 @@ kern_semctl(struct thread *td, int semid
} else
bcopy(arg->buf, &sbuf, sizeof(sbuf));
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_M)))
goto done2;
@@ -700,7 +701,7 @@ kern_semctl(struct thread *td, int semid
case IPC_STAT:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_R)))
goto done2;
@@ -715,7 +716,7 @@ kern_semctl(struct thread *td, int semid
case GETNCNT:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_R)))
goto done2;
@@ -728,7 +729,7 @@ kern_semctl(struct thread *td, int semid
case GETPID:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_R)))
goto done2;
@@ -741,7 +742,7 @@ kern_semctl(struct thread *td, int semid
case GETVAL:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_R)))
goto done2;
@@ -764,7 +765,7 @@ kern_semctl(struct thread *td, int semid
array = malloc(sizeof(*array) * semakptr->u.sem_nsems, M_TEMP,
M_WAITOK);
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_R)))
goto done2;
@@ -777,7 +778,7 @@ kern_semctl(struct thread *td, int semid
case GETZCNT:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_R)))
goto done2;
@@ -790,7 +791,7 @@ kern_semctl(struct thread *td, int semid
case SETVAL:
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
if ((error = ipcperm(td, &semakptr->u.sem_perm, IPC_W)))
goto done2;
@@ -819,7 +820,7 @@ kern_semctl(struct thread *td, int semid
return (EINVAL);
mtx_lock(sema_mtxp);
raced:
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
count = semakptr->u.sem_nsems;
mtx_unlock(sema_mtxp);
@@ -828,7 +829,7 @@ raced:
if (error)
break;
mtx_lock(sema_mtxp);
- if ((error = semvalid(semid, semakptr)) != 0)
+ if ((error = semvalid(savedid, semakptr)) != 0)
goto done2;
/* we could have raced? */
if (count != semakptr->u.sem_nsems) {
%%%
--
Maxim Konovalov
More information about the freebsd-current
mailing list