Deleted Added
full compact
sysv_sem.c (59828) sysv_sem.c (59839)
1/* $FreeBSD: head/sys/kern/sysv_sem.c 59828 2000-05-01 11:13:41Z peter $ */
1/* $FreeBSD: head/sys/kern/sysv_sem.c 59839 2000-05-01 13:33:56Z peter $ */
2
3/*
4 * Implementation of SVID semaphores
5 *
6 * Author: Daniel Boulet
7 *
8 * This software is provided ``AS IS'' without any warranties of any kind.
9 */
10
2
3/*
4 * Implementation of SVID semaphores
5 *
6 * Author: Daniel Boulet
7 *
8 * This software is provided ``AS IS'' without any warranties of any kind.
9 */
10
11#include "opt_sysvipc.h"
12
11#include <sys/param.h>
12#include <sys/systm.h>
13#include <sys/sysproto.h>
14#include <sys/kernel.h>
15#include <sys/proc.h>
16#include <sys/sem.h>
17#include <sys/sysent.h>
13#include <sys/param.h>
14#include <sys/systm.h>
15#include <sys/sysproto.h>
16#include <sys/kernel.h>
17#include <sys/proc.h>
18#include <sys/sem.h>
19#include <sys/sysent.h>
20#include <sys/sysctl.h>
21#include <sys/malloc.h>
18
22
23static MALLOC_DEFINE(M_SEM, "sem", "SVID compatible semaphores");
24
19static void seminit __P((void *));
25static void seminit __P((void *));
20SYSINIT(sysv_sem, SI_SUB_SYSV_SEM, SI_ORDER_FIRST, seminit, NULL)
21
22#ifndef _SYS_SYSPROTO_H_
23struct __semctl_args;
24int __semctl __P((struct proc *p, struct __semctl_args *uap));
25struct semget_args;
26int semget __P((struct proc *p, struct semget_args *uap));
27struct semop_args;
28int semop __P((struct proc *p, struct semop_args *uap));

--- 6 unchanged lines hidden (view full) ---

35
36/* XXX casting to (sy_call_t *) is bogus, as usual. */
37static sy_call_t *semcalls[] = {
38 (sy_call_t *)__semctl, (sy_call_t *)semget,
39 (sy_call_t *)semop
40};
41
42static int semtot = 0;
26
27#ifndef _SYS_SYSPROTO_H_
28struct __semctl_args;
29int __semctl __P((struct proc *p, struct __semctl_args *uap));
30struct semget_args;
31int semget __P((struct proc *p, struct semget_args *uap));
32struct semop_args;
33int semop __P((struct proc *p, struct semop_args *uap));

--- 6 unchanged lines hidden (view full) ---

40
41/* XXX casting to (sy_call_t *) is bogus, as usual. */
42static sy_call_t *semcalls[] = {
43 (sy_call_t *)__semctl, (sy_call_t *)semget,
44 (sy_call_t *)semop
45};
46
47static int semtot = 0;
43struct semid_ds *sema; /* semaphore id pool */
44struct sem *sem; /* semaphore pool */
45static struct sem_undo *semu_list; /* list of active undo structures */
46int *semu; /* undo structure pool */
48static struct semid_ds *sema; /* semaphore id pool */
49static struct sem *sem; /* semaphore pool */
50static struct sem_undo *semu_list; /* list of active undo structures */
51static int *semu; /* undo structure pool */
47
52
48void
53struct sem {
54 u_short semval; /* semaphore value */
55 pid_t sempid; /* pid of last operation */
56 u_short semncnt; /* # awaiting semval > cval */
57 u_short semzcnt; /* # awaiting semval = 0 */
58};
59
60/*
61 * Undo structure (one per process)
62 */
63struct sem_undo {
64 struct sem_undo *un_next; /* ptr to next active undo structure */
65 struct proc *un_proc; /* owner of this structure */
66 short un_cnt; /* # of active entries */
67 struct undo {
68 short un_adjval; /* adjust on exit values */
69 short un_num; /* semaphore # */
70 int un_id; /* semid */
71 } un_ent[1]; /* undo entries */
72};
73
74/*
75 * Configuration parameters
76 */
77#ifndef SEMMNI
78#define SEMMNI 10 /* # of semaphore identifiers */
79#endif
80#ifndef SEMMNS
81#define SEMMNS 60 /* # of semaphores in system */
82#endif
83#ifndef SEMUME
84#define SEMUME 10 /* max # of undo entries per process */
85#endif
86#ifndef SEMMNU
87#define SEMMNU 30 /* # of undo structures in system */
88#endif
89
90/* shouldn't need tuning */
91#ifndef SEMMAP
92#define SEMMAP 30 /* # of entries in semaphore map */
93#endif
94#ifndef SEMMSL
95#define SEMMSL SEMMNS /* max # of semaphores per id */
96#endif
97#ifndef SEMOPM
98#define SEMOPM 100 /* max # of operations per semop call */
99#endif
100
101#define SEMVMX 32767 /* semaphore maximum value */
102#define SEMAEM 16384 /* adjust on exit max value */
103
104/*
105 * Due to the way semaphore memory is allocated, we have to ensure that
106 * SEMUSZ is properly aligned.
107 */
108
109#ifndef offsetof
110#define offsetof(type, member) ((size_t)(&((type *)0)->member))
111#endif
112
113#define SEM_ALIGN(bytes) (((bytes) + (sizeof(long) - 1)) & ~(sizeof(long) - 1))
114
115/* actual size of an undo structure */
116#define SEMUSZ SEM_ALIGN(offsetof(struct sem_undo, un_ent[SEMUME]))
117
118/*
119 * Macro to find a particular sem_undo vector
120 */
121#define SEMU(ix) ((struct sem_undo *)(((intptr_t)semu)+ix * seminfo.semusz))
122
123/*
124 * semaphore info struct
125 */
126struct seminfo seminfo = {
127 SEMMAP, /* # of entries in semaphore map */
128 SEMMNI, /* # of semaphore identifiers */
129 SEMMNS, /* # of semaphores in system */
130 SEMMNU, /* # of undo structures in system */
131 SEMMSL, /* max # of semaphores per id */
132 SEMOPM, /* max # of operations per semop call */
133 SEMUME, /* max # of undo entries per process */
134 SEMUSZ, /* size in bytes of undo structure */
135 SEMVMX, /* semaphore maximum value */
136 SEMAEM /* adjust on exit max value */
137};
138
139SYSCTL_DECL(_kern_ipc);
140SYSCTL_INT(_kern_ipc, OID_AUTO, semmap, CTLFLAG_RW, &seminfo.semmap, 0, "");
141SYSCTL_INT(_kern_ipc, OID_AUTO, semmni, CTLFLAG_RD, &seminfo.semmni, 0, "");
142SYSCTL_INT(_kern_ipc, OID_AUTO, semmns, CTLFLAG_RD, &seminfo.semmns, 0, "");
143SYSCTL_INT(_kern_ipc, OID_AUTO, semmnu, CTLFLAG_RD, &seminfo.semmnu, 0, "");
144SYSCTL_INT(_kern_ipc, OID_AUTO, semmsl, CTLFLAG_RW, &seminfo.semmsl, 0, "");
145SYSCTL_INT(_kern_ipc, OID_AUTO, semopm, CTLFLAG_RD, &seminfo.semopm, 0, "");
146SYSCTL_INT(_kern_ipc, OID_AUTO, semume, CTLFLAG_RD, &seminfo.semume, 0, "");
147SYSCTL_INT(_kern_ipc, OID_AUTO, semusz, CTLFLAG_RD, &seminfo.semusz, 0, "");
148SYSCTL_INT(_kern_ipc, OID_AUTO, semvmx, CTLFLAG_RW, &seminfo.semvmx, 0, "");
149SYSCTL_INT(_kern_ipc, OID_AUTO, semaem, CTLFLAG_RW, &seminfo.semaem, 0, "");
150
151#if 0
152RO seminfo.semmap /* SEMMAP unused */
153RO seminfo.semmni
154RO seminfo.semmns
155RO seminfo.semmnu /* undo entries per system */
156RW seminfo.semmsl
157RO seminfo.semopm /* SEMOPM unused */
158RO seminfo.semume
159RO seminfo.semusz /* param - derived from SEMUME for per-proc sizeof */
160RO seminfo.semvmx /* SEMVMX unused - user param */
161RO seminfo.semaem /* SEMAEM unused - user param */
162#endif
163
164static void
49seminit(dummy)
50 void *dummy;
51{
52 register int i;
53
165seminit(dummy)
166 void *dummy;
167{
168 register int i;
169
170 sem = malloc(sizeof(struct sem) * seminfo.semmns, M_SEM, M_WAITOK);
171 if (sem == NULL)
172 panic("sem is NULL");
173 sema = malloc(sizeof(struct semid_ds) * seminfo.semmni, M_SEM, M_WAITOK);
54 if (sema == NULL)
55 panic("sema is NULL");
174 if (sema == NULL)
175 panic("sema is NULL");
176 semu = malloc(seminfo.semmnu * seminfo.semusz, M_SEM, M_WAITOK);
56 if (semu == NULL)
57 panic("semu is NULL");
58
59 for (i = 0; i < seminfo.semmni; i++) {
60 sema[i].sem_base = 0;
61 sema[i].sem_perm.mode = 0;
62 }
63 for (i = 0; i < seminfo.semmnu; i++) {
64 register struct sem_undo *suptr = SEMU(i);
65 suptr->un_proc = NULL;
66 }
67 semu_list = NULL;
68}
177 if (semu == NULL)
178 panic("semu is NULL");
179
180 for (i = 0; i < seminfo.semmni; i++) {
181 sema[i].sem_base = 0;
182 sema[i].sem_perm.mode = 0;
183 }
184 for (i = 0; i < seminfo.semmnu; i++) {
185 register struct sem_undo *suptr = SEMU(i);
186 suptr->un_proc = NULL;
187 }
188 semu_list = NULL;
189}
190SYSINIT(sysv_sem, SI_SUB_SYSV_SEM, SI_ORDER_FIRST, seminit, NULL)
69
70/*
71 * Entry point for all SEM calls
72 */
73int
74semsys(p, uap)
75 struct proc *p;
76 /* XXX actually varargs. */

--- 626 unchanged lines hidden (view full) ---

703#ifdef SEM_DEBUG
704 printf("semop: good morning!\n");
705#endif
706
707 /*
708 * Make sure that the semaphore still exists
709 */
710 if ((semaptr->sem_perm.mode & SEM_ALLOC) == 0 ||
191
192/*
193 * Entry point for all SEM calls
194 */
195int
196semsys(p, uap)
197 struct proc *p;
198 /* XXX actually varargs. */

--- 626 unchanged lines hidden (view full) ---

825#ifdef SEM_DEBUG
826 printf("semop: good morning!\n");
827#endif
828
829 /*
830 * Make sure that the semaphore still exists
831 */
832 if ((semaptr->sem_perm.mode & SEM_ALLOC) == 0 ||
711 semaptr->sem_perm.seq != IPCID_TO_SEQ(uap->semid)) {
712 /* The man page says to return EIDRM. */
713 /* Unfortunately, BSD doesn't define that code! */
714#ifdef EIDRM
833 semaptr->sem_perm.seq != IPCID_TO_SEQ(uap->semid))
715 return(EIDRM);
834 return(EIDRM);
716#else
717 return(EINVAL);
718#endif
719 }
720
721 /*
722 * The semaphore is still alive. Readjust the count of
723 * waiting processes.
724 */
725 if (sopptr->sem_op == 0)
726 semptr->semzcnt--;
727 else

--- 164 unchanged lines hidden ---
835
836 /*
837 * The semaphore is still alive. Readjust the count of
838 * waiting processes.
839 */
840 if (sopptr->sem_op == 0)
841 semptr->semzcnt--;
842 else

--- 164 unchanged lines hidden ---