thr_syscalls.c revision 115260
1112918Sjeff/*
2112918Sjeff * Copyright (c) 2000 Jason Evans <jasone@freebsd.org>.
3112918Sjeff * Copyright (c) 2002 Daniel M. Eischen <deischen@freebsd.org>
4112918Sjeff * Copyright (c) 2003 Jeff Roberson <jeff@freebsd.org>
5112918Sjeff * All rights reserved.
6112918Sjeff *
7112918Sjeff * Redistribution and use in source and binary forms, with or without
8112918Sjeff * modification, are permitted provided that the following conditions
9112918Sjeff * are met:
10112918Sjeff * 1. Redistributions of source code must retain the above copyright
11112918Sjeff *    notice(s), this list of conditions and the following disclaimer as
12112918Sjeff *    the first lines of this file unmodified other than the possible
13112918Sjeff *    addition of one or more copyright notices.
14112918Sjeff * 2. Redistributions in binary form must reproduce the above copyright
15112918Sjeff *    notice(s), this list of conditions and the following disclaimer in
16112918Sjeff *    the documentation and/or other materials provided with the
17112918Sjeff *    distribution.
18112918Sjeff *
19112918Sjeff * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDER(S) ``AS IS'' AND ANY
20112918Sjeff * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21112918Sjeff * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22112918Sjeff * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) BE
23112918Sjeff * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24112918Sjeff * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25112918Sjeff * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
26112918Sjeff * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
27112918Sjeff * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
28112918Sjeff * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
29112918Sjeff * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30112918Sjeff *
31112918Sjeff * $FreeBSD: head/lib/libthr/thread/thr_syscalls.c 115260 2003-05-23 09:48:20Z mtm $
32112918Sjeff */
33112918Sjeff
34112918Sjeff/*
35112918Sjeff * Copyright (c) 1995-1998 John Birrell <jb@cimlogic.com.au>
36112918Sjeff * All rights reserved.
37112918Sjeff *
38112918Sjeff * Redistribution and use in source and binary forms, with or without
39112918Sjeff * modification, are permitted provided that the following conditions
40112918Sjeff * are met:
41112918Sjeff * 1. Redistributions of source code must retain the above copyright
42112918Sjeff *    notice, this list of conditions and the following disclaimer.
43112918Sjeff * 2. Redistributions in binary form must reproduce the above copyright
44112918Sjeff *    notice, this list of conditions and the following disclaimer in the
45112918Sjeff *    documentation and/or other materials provided with the distribution.
46112918Sjeff * 3. All advertising materials mentioning features or use of this software
47112918Sjeff *    must display the following acknowledgement:
48112918Sjeff *	This product includes software developed by John Birrell.
49112918Sjeff * 4. Neither the name of the author nor the names of any co-contributors
50112918Sjeff *    may be used to endorse or promote products derived from this software
51112918Sjeff *    without specific prior written permission.
52112918Sjeff *
53112918Sjeff * THIS SOFTWARE IS PROVIDED BY JOHN BIRRELL AND CONTRIBUTORS ``AS IS'' AND
54112918Sjeff * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
55112918Sjeff * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
56112918Sjeff * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
57112918Sjeff * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
58112918Sjeff * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
59112918Sjeff * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
60112918Sjeff * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
61112918Sjeff * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
62112918Sjeff * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
63112918Sjeff * SUCH DAMAGE.
64112918Sjeff *
65112918Sjeff */
66112918Sjeff
67112918Sjeff#include <sys/cdefs.h>
68112918Sjeff#include <sys/fcntl.h>
69112918Sjeff#include <sys/mman.h>
70112918Sjeff#include <sys/param.h>
71112918Sjeff#include <sys/select.h>
72112918Sjeff#include <sys/time.h>
73112918Sjeff#include <sys/types.h>
74112918Sjeff#include <sys/uio.h>
75112918Sjeff#include <sys/wait.h>
76112918Sjeff
77112918Sjeff#include <aio.h>
78112918Sjeff#include <dirent.h>
79112918Sjeff#include <errno.h>
80112918Sjeff#include <fcntl.h>
81112918Sjeff#include <poll.h>
82112918Sjeff#include <pthread.h>
83112918Sjeff#include <signal.h>
84112918Sjeff#include <stdarg.h>
85112918Sjeff#include <stdio.h>
86112918Sjeff#include <stdlib.h>
87112918Sjeff#include <string.h>
88112918Sjeff#include <termios.h>
89112918Sjeff#include <unistd.h>
90112918Sjeff
91112918Sjeff#include "thr_private.h"
92112918Sjeff
93115260Smtmextern int __creat(const char *, mode_t);
94115260Smtmextern int __sleep(unsigned int);
95115260Smtmextern int __sys_nanosleep(const struct timespec *, struct timespec *);
96115260Smtmextern int __sys_select(int, fd_set *, fd_set *, fd_set *, struct timeval *);
97115260Smtmextern int __system(const char *);
98115260Smtmextern int __tcdrain(int);
99115260Smtmextern pid_t __wait(int *);
100115260Smtmextern pid_t _wait4(pid_t, int *, int, struct rusage *);
101115260Smtmextern pid_t __waitpid(pid_t, int *, int);
102115260Smtm
103112918Sjeff__weak_reference(_aio_suspend, aio_suspend);
104112918Sjeff
105112918Sjeffint
106112918Sjeff_aio_suspend(const struct aiocb * const iocbs[], int niocb, const struct
107112918Sjeff    timespec *timeout)
108112918Sjeff{
109112918Sjeff	int	ret;
110112918Sjeff
111112918Sjeff	_thread_enter_cancellation_point();
112112918Sjeff	ret = __sys_aio_suspend(iocbs, niocb, timeout);
113112918Sjeff	_thread_leave_cancellation_point();
114112918Sjeff
115112918Sjeff	return ret;
116112918Sjeff}
117112918Sjeff
118112918Sjeff__weak_reference(__close, close);
119112918Sjeff
120112918Sjeffint
121112918Sjeff__close(int fd)
122112918Sjeff{
123112918Sjeff	int	ret;
124112918Sjeff
125112918Sjeff	_thread_enter_cancellation_point();
126112918Sjeff	ret = __sys_close(fd);
127112918Sjeff	_thread_leave_cancellation_point();
128112918Sjeff
129112918Sjeff	return ret;
130112918Sjeff}
131112918Sjeff__weak_reference(___creat, creat);
132112918Sjeff
133112918Sjeffint
134112918Sjeff___creat(const char *path, mode_t mode)
135112918Sjeff{
136112918Sjeff	int	ret;
137112918Sjeff
138112918Sjeff	_thread_enter_cancellation_point();
139112918Sjeff	ret = __creat(path, mode);
140112918Sjeff	_thread_leave_cancellation_point();
141112918Sjeff
142112918Sjeff	return ret;
143112918Sjeff}
144112918Sjeff
145112918Sjeff__weak_reference(__fcntl, fcntl);
146112918Sjeff
147112918Sjeffint
148112918Sjeff__fcntl(int fd, int cmd,...)
149112918Sjeff{
150112918Sjeff	int	ret;
151112918Sjeff	va_list	ap;
152112918Sjeff
153112918Sjeff	_thread_enter_cancellation_point();
154112918Sjeff
155112918Sjeff	va_start(ap, cmd);
156112918Sjeff	switch (cmd) {
157112918Sjeff		case F_DUPFD:
158112918Sjeff		case F_SETFD:
159112918Sjeff		case F_SETFL:
160112918Sjeff			ret = __sys_fcntl(fd, cmd, va_arg(ap, int));
161112918Sjeff			break;
162112918Sjeff		case F_GETFD:
163112918Sjeff		case F_GETFL:
164112918Sjeff			ret = __sys_fcntl(fd, cmd);
165112918Sjeff			break;
166112918Sjeff		default:
167112918Sjeff			ret = __sys_fcntl(fd, cmd, va_arg(ap, void *));
168112918Sjeff	}
169112918Sjeff	va_end(ap);
170112918Sjeff
171112918Sjeff	_thread_leave_cancellation_point();
172112918Sjeff
173112918Sjeff	return ret;
174112918Sjeff}
175112918Sjeff
176112918Sjeff__weak_reference(__fsync, fsync);
177112918Sjeff
178112918Sjeffint
179112918Sjeff__fsync(int fd)
180112918Sjeff{
181112918Sjeff	int	ret;
182112918Sjeff
183112918Sjeff	_thread_enter_cancellation_point();
184112918Sjeff	ret = __sys_fsync(fd);
185112918Sjeff	_thread_leave_cancellation_point();
186112918Sjeff
187112918Sjeff	return ret;
188112918Sjeff}
189112918Sjeff
190112918Sjeff__weak_reference(__msync, msync);
191112918Sjeff
192112918Sjeffint
193112918Sjeff__msync(void *addr, size_t len, int flags)
194112918Sjeff{
195112918Sjeff	int	ret;
196112918Sjeff
197112918Sjeff	_thread_enter_cancellation_point();
198112918Sjeff	ret = __sys_msync(addr, len, flags);
199112918Sjeff	_thread_leave_cancellation_point();
200112918Sjeff
201112918Sjeff	return ret;
202112918Sjeff}
203112918Sjeff
204112918Sjeff__weak_reference(_nanosleep, nanosleep);
205112918Sjeff
206112918Sjeffint
207112918Sjeff_nanosleep(const struct timespec * time_to_sleep, struct timespec *
208112918Sjeff    time_remaining)
209112918Sjeff{
210112918Sjeff	int	ret;
211112918Sjeff
212112918Sjeff	_thread_enter_cancellation_point();
213112918Sjeff	ret = __sys_nanosleep(time_to_sleep, time_remaining);
214112918Sjeff	_thread_leave_cancellation_point();
215112918Sjeff
216112918Sjeff	return ret;
217112918Sjeff}
218112918Sjeff
219112918Sjeff__weak_reference(__open, open);
220112918Sjeff
221112918Sjeffint
222112918Sjeff__open(const char *path, int flags,...)
223112918Sjeff{
224112918Sjeff	int	ret;
225112918Sjeff	int	mode = 0;
226112918Sjeff	va_list	ap;
227112918Sjeff
228112918Sjeff	_thread_enter_cancellation_point();
229112918Sjeff
230112918Sjeff	/* Check if the file is being created: */
231112918Sjeff	if (flags & O_CREAT) {
232112918Sjeff		/* Get the creation mode: */
233112918Sjeff		va_start(ap, flags);
234112918Sjeff		mode = va_arg(ap, int);
235112918Sjeff		va_end(ap);
236112918Sjeff	}
237112918Sjeff
238112918Sjeff	ret = __sys_open(path, flags, mode);
239112918Sjeff	_thread_leave_cancellation_point();
240112918Sjeff
241112918Sjeff	return ret;
242112918Sjeff}
243112918Sjeff
244112918Sjeff__weak_reference(__poll, poll);
245112918Sjeff
246112918Sjeffint
247112918Sjeff__poll(struct pollfd *fds, unsigned int nfds, int timeout)
248112918Sjeff{
249112918Sjeff	int ret;
250112918Sjeff
251112918Sjeff	_thread_enter_cancellation_point();
252112918Sjeff	ret = __sys_poll(fds, nfds, timeout);
253112918Sjeff	_thread_leave_cancellation_point();
254112918Sjeff
255112918Sjeff	return ret;
256112918Sjeff}
257112918Sjeff
258112918Sjeffextern int __pselect(int count, fd_set *rfds, fd_set *wfds, fd_set *efds,
259112918Sjeff		const struct timespec *timo, const sigset_t *mask);
260112918Sjeff
261112918Sjeffint
262112918Sjeffpselect(int count, fd_set *rfds, fd_set *wfds, fd_set *efds,
263112918Sjeff	const struct timespec *timo, const sigset_t *mask)
264112918Sjeff{
265112918Sjeff	int ret;
266112918Sjeff
267112918Sjeff	_thread_enter_cancellation_point();
268112918Sjeff	ret = __pselect(count, rfds, wfds, efds, timo, mask);
269112918Sjeff	_thread_leave_cancellation_point();
270112918Sjeff
271112918Sjeff	return (ret);
272112918Sjeff}
273112918Sjeff
274112918Sjeff__weak_reference(__read, read);
275112918Sjeff
276112918Sjeffssize_t
277112918Sjeff__read(int fd, void *buf, size_t nbytes)
278112918Sjeff{
279112918Sjeff	ssize_t	ret;
280112918Sjeff
281112918Sjeff	_thread_enter_cancellation_point();
282112918Sjeff	ret = __sys_read(fd, buf, nbytes);
283112918Sjeff	_thread_leave_cancellation_point();
284112918Sjeff
285112918Sjeff	return ret;
286112918Sjeff}
287112918Sjeff
288112918Sjeff__weak_reference(__readv, readv);
289112918Sjeff
290112918Sjeffssize_t
291112918Sjeff__readv(int fd, const struct iovec *iov, int iovcnt)
292112918Sjeff{
293112918Sjeff	ssize_t ret;
294112918Sjeff
295112918Sjeff	_thread_enter_cancellation_point();
296112918Sjeff	ret = __sys_readv(fd, iov, iovcnt);
297112918Sjeff	_thread_leave_cancellation_point();
298112918Sjeff
299112918Sjeff	return ret;
300112918Sjeff}
301112918Sjeff
302112918Sjeff__weak_reference(__select, select);
303112918Sjeff
304112918Sjeffint
305112918Sjeff__select(int numfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds,
306112918Sjeff	struct timeval *timeout)
307112918Sjeff{
308112918Sjeff	int ret;
309112918Sjeff
310112918Sjeff	_thread_enter_cancellation_point();
311112918Sjeff	ret = __sys_select(numfds, readfds, writefds, exceptfds, timeout);
312112918Sjeff	_thread_leave_cancellation_point();
313112918Sjeff
314112918Sjeff	return ret;
315112918Sjeff}
316112918Sjeff
317112918Sjeff__weak_reference(_sleep, sleep);
318112918Sjeff
319112918Sjeffunsigned int
320112918Sjeff_sleep(unsigned int seconds)
321112918Sjeff{
322112918Sjeff	unsigned int	ret;
323112918Sjeff
324112918Sjeff	_thread_enter_cancellation_point();
325112918Sjeff	ret = __sleep(seconds);
326112918Sjeff	_thread_leave_cancellation_point();
327112918Sjeff
328112918Sjeff	return ret;
329112918Sjeff}
330112918Sjeff
331112918Sjeff__weak_reference(_system, system);
332112918Sjeff
333112918Sjeffint
334112918Sjeff_system(const char *string)
335112918Sjeff{
336112918Sjeff	int	ret;
337112918Sjeff
338112918Sjeff	_thread_enter_cancellation_point();
339112918Sjeff	ret = __system(string);
340112918Sjeff	_thread_leave_cancellation_point();
341112918Sjeff
342112918Sjeff	return ret;
343112918Sjeff}
344112918Sjeff
345112918Sjeff
346112918Sjeff__weak_reference(_tcdrain, tcdrain);
347112918Sjeff
348112918Sjeffint
349112918Sjeff_tcdrain(int fd)
350112918Sjeff{
351112918Sjeff	int	ret;
352112918Sjeff
353112918Sjeff	_thread_enter_cancellation_point();
354112918Sjeff	ret = __tcdrain(fd);
355112918Sjeff	_thread_leave_cancellation_point();
356112918Sjeff
357112918Sjeff	return ret;
358112918Sjeff}
359112918Sjeff
360112918Sjeff__weak_reference(_wait, wait);
361112918Sjeff
362112918Sjeffpid_t
363112918Sjeff_wait(int *istat)
364112918Sjeff{
365112918Sjeff	pid_t	ret;
366112918Sjeff
367112918Sjeff	_thread_enter_cancellation_point();
368112918Sjeff	ret = __wait(istat);
369112918Sjeff	_thread_leave_cancellation_point();
370112918Sjeff
371112918Sjeff	return ret;
372112918Sjeff}
373112918Sjeff
374112918Sjeff__weak_reference(__wait4, wait4);
375112918Sjeff
376112918Sjeffpid_t
377112918Sjeff__wait4(pid_t pid, int *istat, int options, struct rusage *rusage)
378112918Sjeff{
379112918Sjeff	pid_t ret;
380112918Sjeff
381112918Sjeff	_thread_enter_cancellation_point();
382112918Sjeff	ret = _wait4(pid, istat, options, rusage);
383112918Sjeff	_thread_leave_cancellation_point();
384112918Sjeff
385112918Sjeff	return ret;
386112918Sjeff}
387112918Sjeff
388112918Sjeff__weak_reference(_waitpid, waitpid);
389112918Sjeff
390112918Sjeffpid_t
391112918Sjeff_waitpid(pid_t wpid, int *status, int options)
392112918Sjeff{
393112918Sjeff	pid_t	ret;
394112918Sjeff
395112918Sjeff	_thread_enter_cancellation_point();
396112918Sjeff	ret = __waitpid(wpid, status, options);
397112918Sjeff	_thread_leave_cancellation_point();
398112918Sjeff
399112918Sjeff	return ret;
400112918Sjeff}
401112918Sjeff
402112918Sjeff__weak_reference(__write, write);
403112918Sjeff
404112918Sjeffssize_t
405112918Sjeff__write(int fd, const void *buf, size_t nbytes)
406112918Sjeff{
407112918Sjeff	ssize_t	ret;
408112918Sjeff
409112918Sjeff	_thread_enter_cancellation_point();
410112918Sjeff	ret = __sys_write(fd, buf, nbytes);
411112918Sjeff	_thread_leave_cancellation_point();
412112918Sjeff
413112918Sjeff	return ret;
414112918Sjeff}
415112918Sjeff
416112918Sjeff__weak_reference(__writev, writev);
417112918Sjeff
418112918Sjeffssize_t
419112918Sjeff__writev(int fd, const struct iovec *iov, int iovcnt)
420112918Sjeff{
421112918Sjeff	ssize_t ret;
422112918Sjeff
423112918Sjeff	_thread_enter_cancellation_point();
424112918Sjeff	ret = __sys_writev(fd, iov, iovcnt);
425112918Sjeff	_thread_leave_cancellation_point();
426112918Sjeff
427112918Sjeff	return ret;
428112918Sjeff}
429