xref: /onnv-gate/usr/src/lib/libc/port/sys/semsys.c (revision 6812:febeba71273d)
10Sstevel@tonic-gate /*
20Sstevel@tonic-gate  * CDDL HEADER START
30Sstevel@tonic-gate  *
40Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*6812Sraf  * Common Development and Distribution License (the "License").
6*6812Sraf  * You may not use this file except in compliance with the License.
70Sstevel@tonic-gate  *
80Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
90Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
100Sstevel@tonic-gate  * See the License for the specific language governing permissions
110Sstevel@tonic-gate  * and limitations under the License.
120Sstevel@tonic-gate  *
130Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
140Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
150Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
160Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
170Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
180Sstevel@tonic-gate  *
190Sstevel@tonic-gate  * CDDL HEADER END
200Sstevel@tonic-gate  */
21*6812Sraf 
220Sstevel@tonic-gate /*
23*6812Sraf  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
240Sstevel@tonic-gate  * Use is subject to license terms.
250Sstevel@tonic-gate  */
260Sstevel@tonic-gate 
270Sstevel@tonic-gate /*	Copyright (c) 1988 AT&T	*/
280Sstevel@tonic-gate /*	  All Rights Reserved  	*/
290Sstevel@tonic-gate 
30*6812Sraf #pragma ident	"%Z%%M%	%I%	%E% SMI"
310Sstevel@tonic-gate 
32*6812Sraf #pragma weak _semctl = semctl
33*6812Sraf #pragma weak _semctl64 = semctl64
34*6812Sraf #pragma weak _semget = semget
35*6812Sraf #pragma weak _semop = semop
36*6812Sraf #pragma weak _semids = semids
37*6812Sraf #pragma weak _semtimedop = semtimedop
380Sstevel@tonic-gate 
39*6812Sraf #include "lint.h"
400Sstevel@tonic-gate #include <sys/types.h>
410Sstevel@tonic-gate #include <sys/ipc.h>
420Sstevel@tonic-gate #include <sys/ipc_impl.h>
430Sstevel@tonic-gate #include <sys/sem.h>
440Sstevel@tonic-gate #include <sys/sem_impl.h>
450Sstevel@tonic-gate #include <sys/syscall.h>
460Sstevel@tonic-gate #include <stdarg.h>
470Sstevel@tonic-gate #include <errno.h>
480Sstevel@tonic-gate 
490Sstevel@tonic-gate union semun {
500Sstevel@tonic-gate 	int val;
510Sstevel@tonic-gate 	struct semid_ds *buf;
520Sstevel@tonic-gate 	struct semid_ds64 *buf64;
530Sstevel@tonic-gate 	ushort_t *array;
540Sstevel@tonic-gate };
550Sstevel@tonic-gate 
560Sstevel@tonic-gate /*
570Sstevel@tonic-gate  * The kernel implementation of semsys expects an argument containing the
580Sstevel@tonic-gate  * value of the semun argument, but the Sparc compiler passes a pointer
590Sstevel@tonic-gate  * to it, since it is a union.  So, we convert here and pass the value,
600Sstevel@tonic-gate  * but to keep the naive user from being penalized for the counterintuitive
610Sstevel@tonic-gate  * behaviour of the Sparc compiler, we ignore the union if it will not be
620Sstevel@tonic-gate  * used by the system call (to protect the caller from SIGSEGVs, e.g.
630Sstevel@tonic-gate  * semctl(semid, semnum, cmd, NULL);  which would otherwise always result
640Sstevel@tonic-gate  * in a segmentation violation).  We do this partly for consistency, since
650Sstevel@tonic-gate  * the ICL port did it.  This all works just fine for the Intel compiler,
660Sstevel@tonic-gate  * which actually does pass the union by value.
670Sstevel@tonic-gate  */
680Sstevel@tonic-gate int
semctl(int semid,int semnum,int cmd,...)690Sstevel@tonic-gate semctl(int semid, int semnum, int cmd, ...)
700Sstevel@tonic-gate {
710Sstevel@tonic-gate 	uintptr_t arg;
720Sstevel@tonic-gate 	va_list ap;
730Sstevel@tonic-gate 
740Sstevel@tonic-gate 	switch (cmd) {
750Sstevel@tonic-gate 	case SETVAL:
760Sstevel@tonic-gate 		va_start(ap, cmd);
770Sstevel@tonic-gate 		arg = (uintptr_t)va_arg(ap, union semun).val;
780Sstevel@tonic-gate 		va_end(ap);
790Sstevel@tonic-gate 		break;
800Sstevel@tonic-gate 	case GETALL:
810Sstevel@tonic-gate 	case SETALL:
820Sstevel@tonic-gate 		va_start(ap, cmd);
830Sstevel@tonic-gate 		arg = (uintptr_t)va_arg(ap, union semun).array;
840Sstevel@tonic-gate 		va_end(ap);
850Sstevel@tonic-gate 		break;
860Sstevel@tonic-gate 	case IPC_STAT:
870Sstevel@tonic-gate 	case IPC_SET:
880Sstevel@tonic-gate 		va_start(ap, cmd);
890Sstevel@tonic-gate 		arg = (uintptr_t)va_arg(ap, union semun).buf;
900Sstevel@tonic-gate 		va_end(ap);
910Sstevel@tonic-gate 		break;
920Sstevel@tonic-gate 	case IPC_SET64:
930Sstevel@tonic-gate 	case IPC_STAT64:
940Sstevel@tonic-gate 		(void) __set_errno(EINVAL);
950Sstevel@tonic-gate 		return (-1);
960Sstevel@tonic-gate 	default:
970Sstevel@tonic-gate 		arg = 0;
980Sstevel@tonic-gate 		break;
990Sstevel@tonic-gate 	}
1000Sstevel@tonic-gate 
1010Sstevel@tonic-gate 	return (syscall(SYS_semsys, SEMCTL, semid, semnum, cmd, arg));
1020Sstevel@tonic-gate }
1030Sstevel@tonic-gate 
1040Sstevel@tonic-gate int
semctl64(int semid,int semnum,int cmd,...)1050Sstevel@tonic-gate semctl64(int semid, int semnum, int cmd, ...)
1060Sstevel@tonic-gate {
1070Sstevel@tonic-gate 	struct semid_ds64 *buf;
1080Sstevel@tonic-gate 	va_list ap;
1090Sstevel@tonic-gate 
1100Sstevel@tonic-gate 	if (cmd != IPC_SET64 && cmd != IPC_STAT64) {
1110Sstevel@tonic-gate 		(void) __set_errno(EINVAL);
1120Sstevel@tonic-gate 		return (-1);
1130Sstevel@tonic-gate 	}
1140Sstevel@tonic-gate 
1150Sstevel@tonic-gate 	va_start(ap, cmd);
1160Sstevel@tonic-gate 	buf = va_arg(ap, union semun).buf64;
1170Sstevel@tonic-gate 	va_end(ap);
1180Sstevel@tonic-gate 
1190Sstevel@tonic-gate 	return (syscall(SYS_semsys, SEMCTL, semid, semnum, cmd, buf));
1200Sstevel@tonic-gate }
1210Sstevel@tonic-gate 
1220Sstevel@tonic-gate int
semget(key_t key,int nsems,int semflg)1230Sstevel@tonic-gate semget(key_t key, int nsems, int semflg)
1240Sstevel@tonic-gate {
1250Sstevel@tonic-gate 	return (syscall(SYS_semsys, SEMGET, key, nsems, semflg));
1260Sstevel@tonic-gate }
1270Sstevel@tonic-gate 
1280Sstevel@tonic-gate int
semop(int semid,struct sembuf * sops,size_t nsops)1290Sstevel@tonic-gate semop(int semid, struct sembuf *sops, size_t nsops)
1300Sstevel@tonic-gate {
1310Sstevel@tonic-gate 	return (syscall(SYS_semsys, SEMOP, semid, sops, nsops));
1320Sstevel@tonic-gate }
1330Sstevel@tonic-gate 
1340Sstevel@tonic-gate int
semids(int * buf,uint_t nids,uint_t * pnids)1350Sstevel@tonic-gate semids(int *buf, uint_t nids, uint_t *pnids)
1360Sstevel@tonic-gate {
1370Sstevel@tonic-gate 	return (syscall(SYS_semsys, SEMIDS, buf, nids, pnids));
1380Sstevel@tonic-gate }
1390Sstevel@tonic-gate 
1400Sstevel@tonic-gate int
semtimedop(int semid,struct sembuf * sops,size_t nsops,const timespec_t * timeout)1410Sstevel@tonic-gate semtimedop(int semid, struct sembuf *sops, size_t nsops,
1420Sstevel@tonic-gate     const timespec_t *timeout)
1430Sstevel@tonic-gate {
1440Sstevel@tonic-gate 	return (syscall(SYS_semsys, SEMTIMEDOP, semid, sops, nsops,
1450Sstevel@tonic-gate 	    timeout));
1460Sstevel@tonic-gate }
147