Home | History | Annotate | Line # | Download | only in kern
kern_syscall.c revision 1.10
      1  1.10  christos /*	$NetBSD: kern_syscall.c,v 1.10 2015/03/07 16:38:07 christos Exp $	*/
      2   1.1     pooka 
      3   1.1     pooka /*-
      4   1.1     pooka  * Copyright (c) 2008 The NetBSD Foundation, Inc.
      5   1.1     pooka  * All rights reserved.
      6   1.1     pooka  *
      7   1.1     pooka  * This code is derived from software developed for The NetBSD Foundation
      8   1.1     pooka  * by Andrew Doran.
      9   1.1     pooka  *
     10   1.1     pooka  * Redistribution and use in source and binary forms, with or without
     11   1.1     pooka  * modification, are permitted provided that the following conditions
     12   1.1     pooka  * are met:
     13   1.1     pooka  * 1. Redistributions of source code must retain the above copyright
     14   1.1     pooka  *    notice, this list of conditions and the following disclaimer.
     15   1.1     pooka  * 2. Redistributions in binary form must reproduce the above copyright
     16   1.1     pooka  *    notice, this list of conditions and the following disclaimer in the
     17   1.1     pooka  *    documentation and/or other materials provided with the distribution.
     18   1.1     pooka  *
     19   1.1     pooka  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
     20   1.1     pooka  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
     21   1.1     pooka  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     22   1.1     pooka  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
     23   1.1     pooka  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     24   1.1     pooka  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     25   1.1     pooka  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     26   1.1     pooka  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     27   1.1     pooka  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     28   1.1     pooka  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     29   1.1     pooka  * POSSIBILITY OF SUCH DAMAGE.
     30   1.1     pooka  */
     31   1.1     pooka 
     32   1.1     pooka #include <sys/cdefs.h>
     33  1.10  christos __KERNEL_RCSID(0, "$NetBSD: kern_syscall.c,v 1.10 2015/03/07 16:38:07 christos Exp $");
     34   1.2     pooka 
     35   1.8     pooka #ifdef _KERNEL_OPT
     36   1.2     pooka #include "opt_modular.h"
     37   1.8     pooka #include "opt_syscall_debug.h"
     38   1.8     pooka #include "opt_ktrace.h"
     39   1.8     pooka #include "opt_ptrace.h"
     40  1.10  christos #include "opt_dtrace.h"
     41   1.8     pooka #endif
     42   1.1     pooka 
     43   1.3     pooka /* XXX To get syscall prototypes. */
     44   1.3     pooka #define SYSVSHM
     45   1.3     pooka #define SYSVSEM
     46   1.3     pooka #define SYSVMSG
     47   1.3     pooka 
     48   1.1     pooka #include <sys/param.h>
     49   1.1     pooka #include <sys/module.h>
     50   1.4     pooka #include <sys/sched.h>
     51   1.1     pooka #include <sys/syscall.h>
     52   1.1     pooka #include <sys/syscallargs.h>
     53   1.1     pooka #include <sys/syscallvar.h>
     54   1.5  pgoyette #include <sys/systm.h>
     55   1.1     pooka #include <sys/xcall.h>
     56   1.8     pooka #include <sys/ktrace.h>
     57   1.8     pooka #include <sys/ptrace.h>
     58   1.1     pooka 
     59   1.1     pooka int
     60   1.1     pooka sys_nomodule(struct lwp *l, const void *v, register_t *retval)
     61   1.1     pooka {
     62   1.1     pooka #ifdef MODULAR
     63   1.1     pooka 	static struct {
     64   1.1     pooka 		u_int		al_code;
     65   1.1     pooka 		const char	*al_module;
     66   1.1     pooka 	} const autoload[] = {
     67   1.1     pooka 	    { SYS_aio_cancel, "aio" },
     68   1.1     pooka 	    { SYS_aio_error, "aio" },
     69   1.1     pooka 	    { SYS_aio_fsync, "aio" },
     70   1.1     pooka 	    { SYS_aio_read, "aio" },
     71   1.1     pooka 	    { SYS_aio_return, "aio" },
     72   1.1     pooka 	    { SYS___aio_suspend50, "aio" },
     73   1.1     pooka 	    { SYS_aio_write, "aio" },
     74   1.1     pooka 	    { SYS_lio_listio, "aio" },
     75   1.1     pooka 	    { SYS_mq_open, "mqueue" },
     76   1.1     pooka 	    { SYS_mq_close, "mqueue" },
     77   1.1     pooka 	    { SYS_mq_unlink, "mqueue" },
     78   1.1     pooka 	    { SYS_mq_getattr, "mqueue" },
     79   1.1     pooka 	    { SYS_mq_setattr, "mqueue" },
     80   1.1     pooka 	    { SYS_mq_notify, "mqueue" },
     81   1.1     pooka 	    { SYS_mq_send, "mqueue" },
     82   1.1     pooka 	    { SYS_mq_receive, "mqueue" },
     83   1.1     pooka 	    { SYS___mq_timedsend50, "mqueue" },
     84   1.1     pooka 	    { SYS___mq_timedreceive50, "mqueue" },
     85   1.1     pooka 	    { SYS_compat_43_fstat43, "compat" },
     86   1.1     pooka 	    { SYS_compat_43_lstat43, "compat" },
     87   1.1     pooka 	    { SYS_compat_43_oaccept, "compat" },
     88   1.1     pooka 	    { SYS_compat_43_ocreat, "compat" },
     89   1.1     pooka 	    { SYS_compat_43_oftruncate, "compat" },
     90   1.1     pooka 	    { SYS_compat_43_ogetdirentries, "compat" },
     91   1.1     pooka 	    { SYS_compat_43_ogetdtablesize, "compat" },
     92   1.1     pooka 	    { SYS_compat_43_ogethostid, "compat" },
     93   1.1     pooka 	    { SYS_compat_43_ogethostname, "compat" },
     94   1.1     pooka 	    { SYS_compat_43_ogetkerninfo, "compat" },
     95   1.1     pooka 	    { SYS_compat_43_ogetpagesize, "compat" },
     96   1.1     pooka 	    { SYS_compat_43_ogetpeername, "compat" },
     97   1.1     pooka 	    { SYS_compat_43_ogetrlimit, "compat" },
     98   1.1     pooka 	    { SYS_compat_43_ogetsockname, "compat" },
     99   1.1     pooka 	    { SYS_compat_43_okillpg, "compat" },
    100   1.1     pooka 	    { SYS_compat_43_olseek, "compat" },
    101   1.1     pooka 	    { SYS_compat_43_ommap, "compat" },
    102   1.1     pooka 	    { SYS_compat_43_oquota, "compat" },
    103   1.1     pooka 	    { SYS_compat_43_orecv, "compat" },
    104   1.1     pooka 	    { SYS_compat_43_orecvfrom, "compat" },
    105   1.1     pooka 	    { SYS_compat_43_orecvmsg, "compat" },
    106   1.1     pooka 	    { SYS_compat_43_osend, "compat" },
    107   1.1     pooka 	    { SYS_compat_43_osendmsg, "compat" },
    108   1.1     pooka 	    { SYS_compat_43_osethostid, "compat" },
    109   1.1     pooka 	    { SYS_compat_43_osethostname, "compat" },
    110   1.1     pooka 	    { SYS_compat_43_osetrlimit, "compat" },
    111   1.1     pooka 	    { SYS_compat_43_osigblock, "compat" },
    112   1.1     pooka 	    { SYS_compat_43_osigsetmask, "compat" },
    113   1.1     pooka 	    { SYS_compat_43_osigstack, "compat" },
    114   1.1     pooka 	    { SYS_compat_43_osigvec, "compat" },
    115   1.1     pooka 	    { SYS_compat_43_otruncate, "compat" },
    116   1.1     pooka 	    { SYS_compat_43_owait, "compat" },
    117   1.1     pooka 	    { SYS_compat_43_stat43, "compat" },
    118   1.1     pooka 	    { SYS_compat_09_ogetdomainname, "compat" },
    119   1.1     pooka 	    { SYS_compat_09_osetdomainname, "compat" },
    120   1.1     pooka 	    { SYS_compat_09_ouname, "compat" },
    121   1.1     pooka #ifndef _LP64
    122   1.1     pooka 	    { SYS_compat_10_omsgsys, "compat" },
    123   1.1     pooka 	    { SYS_compat_10_osemsys, "compat" },
    124   1.1     pooka 	    { SYS_compat_10_oshmsys, "compat" },
    125   1.1     pooka #endif
    126   1.1     pooka 	    { SYS_compat_12_fstat12, "compat" },
    127   1.1     pooka 	    { SYS_compat_12_getdirentries, "compat" },
    128   1.1     pooka 	    { SYS_compat_12_lstat12, "compat" },
    129   1.1     pooka 	    { SYS_compat_12_msync, "compat" },
    130   1.1     pooka 	    { SYS_compat_12_oreboot, "compat" },
    131   1.1     pooka 	    { SYS_compat_12_oswapon, "compat" },
    132   1.1     pooka 	    { SYS_compat_12_stat12, "compat" },
    133   1.1     pooka 	    { SYS_compat_13_sigaction13, "compat" },
    134   1.1     pooka 	    { SYS_compat_13_sigaltstack13, "compat" },
    135   1.1     pooka 	    { SYS_compat_13_sigpending13, "compat" },
    136   1.1     pooka 	    { SYS_compat_13_sigprocmask13, "compat" },
    137   1.1     pooka 	    { SYS_compat_13_sigreturn13, "compat" },
    138   1.1     pooka 	    { SYS_compat_13_sigsuspend13, "compat" },
    139   1.1     pooka 	    { SYS_compat_14___semctl, "compat" },
    140   1.1     pooka 	    { SYS_compat_14_msgctl, "compat" },
    141   1.1     pooka 	    { SYS_compat_14_shmctl, "compat" },
    142   1.1     pooka 	    { SYS_compat_16___sigaction14, "compat" },
    143   1.1     pooka 	    { SYS_compat_16___sigreturn14, "compat" },
    144   1.1     pooka 	    { SYS_compat_20_fhstatfs, "compat" },
    145   1.1     pooka 	    { SYS_compat_20_fstatfs, "compat" },
    146   1.1     pooka 	    { SYS_compat_20_getfsstat, "compat" },
    147   1.1     pooka 	    { SYS_compat_20_statfs, "compat" },
    148   1.1     pooka 	    { SYS_compat_30___fhstat30, "compat" },
    149   1.1     pooka 	    { SYS_compat_30___fstat13, "compat" },
    150   1.1     pooka 	    { SYS_compat_30___lstat13, "compat" },
    151   1.1     pooka 	    { SYS_compat_30___stat13, "compat" },
    152   1.1     pooka 	    { SYS_compat_30_fhopen, "compat" },
    153   1.1     pooka 	    { SYS_compat_30_fhstat, "compat" },
    154   1.1     pooka 	    { SYS_compat_30_fhstatvfs1, "compat" },
    155   1.1     pooka 	    { SYS_compat_30_getdents, "compat" },
    156   1.1     pooka 	    { SYS_compat_30_getfh, "compat" },
    157   1.1     pooka 	    { SYS_compat_30_socket, "compat" },
    158   1.1     pooka 	    { SYS_compat_40_mount, "compat" },
    159   1.1     pooka 	    { SYS_compat_50_wait4, "compat" },
    160   1.1     pooka 	    { SYS_compat_50_mknod, "compat" },
    161   1.1     pooka 	    { SYS_compat_50_setitimer, "compat" },
    162   1.1     pooka 	    { SYS_compat_50_getitimer, "compat" },
    163   1.1     pooka 	    { SYS_compat_50_select, "compat" },
    164   1.1     pooka 	    { SYS_compat_50_gettimeofday, "compat" },
    165   1.1     pooka 	    { SYS_compat_50_getrusage, "compat" },
    166   1.1     pooka 	    { SYS_compat_50_settimeofday, "compat" },
    167   1.1     pooka 	    { SYS_compat_50_utimes, "compat" },
    168   1.1     pooka 	    { SYS_compat_50_adjtime, "compat" },
    169   1.1     pooka 	    { SYS_compat_50_lfs_segwait, "compat" },
    170   1.1     pooka 	    { SYS_compat_50_futimes, "compat" },
    171   1.1     pooka 	    { SYS_compat_50_clock_gettime, "compat" },
    172   1.1     pooka 	    { SYS_compat_50_clock_settime, "compat" },
    173   1.1     pooka 	    { SYS_compat_50_clock_getres, "compat" },
    174   1.1     pooka 	    { SYS_compat_50_timer_settime, "compat" },
    175   1.1     pooka 	    { SYS_compat_50_timer_gettime, "compat" },
    176   1.1     pooka 	    { SYS_compat_50_nanosleep, "compat" },
    177   1.1     pooka 	    { SYS_compat_50___sigtimedwait, "compat" },
    178   1.1     pooka 	    { SYS_compat_50_mq_timedsend, "compat" },
    179   1.1     pooka 	    { SYS_compat_50_mq_timedreceive, "compat" },
    180   1.1     pooka 	    { SYS_compat_50_lutimes, "compat" },
    181   1.1     pooka 	    { SYS_compat_50_____semctl13, "compat" },
    182   1.1     pooka 	    { SYS_compat_50___msgctl13, "compat" },
    183   1.1     pooka 	    { SYS_compat_50___shmctl13, "compat" },
    184   1.1     pooka 	    { SYS_compat_50__lwp_park, "compat" },
    185   1.1     pooka 	    { SYS_compat_50_kevent, "compat" },
    186   1.1     pooka 	    { SYS_compat_50_pselect, "compat" },
    187   1.1     pooka 	    { SYS_compat_50_pollts, "compat" },
    188   1.1     pooka 	    { SYS_compat_50___stat30, "compat" },
    189   1.1     pooka 	    { SYS_compat_50___fstat30, "compat" },
    190   1.1     pooka 	    { SYS_compat_50___lstat30, "compat" },
    191   1.1     pooka 	    { SYS_compat_50___ntp_gettime30, "compat" },
    192   1.1     pooka 	    { SYS_compat_50___fhstat40, "compat" },
    193   1.1     pooka 	    { SYS_compat_50_aio_suspend, "compat" },
    194   1.9  pgoyette 	    { SYS_compat_60__lwp_park, "compat" },
    195   1.1     pooka 	    { SYS__ksem_init, "ksem" },
    196   1.1     pooka 	    { SYS__ksem_open, "ksem" },
    197   1.1     pooka 	    { SYS__ksem_unlink, "ksem" },
    198   1.1     pooka 	    { SYS__ksem_close, "ksem" },
    199   1.1     pooka 	    { SYS__ksem_post, "ksem" },
    200   1.1     pooka 	    { SYS__ksem_wait, "ksem" },
    201   1.1     pooka 	    { SYS__ksem_trywait, "ksem" },
    202   1.1     pooka 	    { SYS__ksem_getvalue, "ksem" },
    203   1.1     pooka 	    { SYS__ksem_destroy, "ksem" },
    204   1.6     joerg 	    { SYS__ksem_timedwait, "ksem" },
    205   1.1     pooka 	    { SYS_nfssvc, "nfsserver" },
    206   1.7  christos 	    { SYS_afssys, "openafs" },
    207   1.1     pooka 	};
    208   1.1     pooka 	const struct sysent *sy;
    209   1.1     pooka 	const struct emul *em;
    210   1.1     pooka 	int code, i;
    211   1.1     pooka 
    212   1.1     pooka 	/*
    213   1.1     pooka 	 * Restart the syscall if we interrupted a module unload that
    214   1.5  pgoyette 	 * failed.  Acquiring kernconfig_lock delays us until any unload
    215   1.1     pooka 	 * has been completed or rolled back.
    216   1.1     pooka 	 */
    217   1.5  pgoyette 	kernconfig_lock();
    218   1.1     pooka 	sy = l->l_sysent;
    219   1.1     pooka 	if (sy->sy_call != sys_nomodule) {
    220   1.5  pgoyette 		kernconfig_unlock();
    221   1.1     pooka 		return ERESTART;
    222   1.1     pooka 	}
    223   1.1     pooka 	/*
    224   1.1     pooka 	 * Try to autoload a module to satisfy the request.  If it
    225   1.1     pooka 	 * works, retry the request.
    226   1.1     pooka 	 */
    227   1.1     pooka 	em = l->l_proc->p_emul;
    228   1.1     pooka 	if (em == &emul_netbsd) {
    229   1.1     pooka 		code = sy - em->e_sysent;
    230   1.1     pooka 		for (i = 0; i < __arraycount(autoload); i++) {
    231   1.1     pooka 			if (autoload[i].al_code != code) {
    232   1.1     pooka 				continue;
    233   1.1     pooka 			}
    234   1.1     pooka 			if (module_autoload(autoload[i].al_module,
    235   1.1     pooka 			    MODULE_CLASS_ANY) != 0 ||
    236   1.1     pooka 			    sy->sy_call == sys_nomodule) {
    237   1.1     pooka 			    	break;
    238   1.1     pooka 			}
    239   1.5  pgoyette 			kernconfig_unlock();
    240   1.1     pooka 			return ERESTART;
    241   1.1     pooka 		}
    242   1.1     pooka 	}
    243   1.5  pgoyette 	kernconfig_unlock();
    244   1.1     pooka #endif	/* MODULAR */
    245   1.1     pooka 
    246   1.1     pooka 	return sys_nosys(l, v, retval);
    247   1.1     pooka }
    248   1.1     pooka 
    249   1.1     pooka int
    250   1.1     pooka syscall_establish(const struct emul *em, const struct syscall_package *sp)
    251   1.1     pooka {
    252   1.1     pooka 	struct sysent *sy;
    253   1.1     pooka 	int i;
    254   1.1     pooka 
    255   1.5  pgoyette 	KASSERT(kernconfig_is_held());
    256   1.1     pooka 
    257   1.1     pooka 	if (em == NULL) {
    258   1.1     pooka 		em = &emul_netbsd;
    259   1.1     pooka 	}
    260   1.1     pooka 	sy = em->e_sysent;
    261   1.1     pooka 
    262   1.1     pooka 	/*
    263   1.1     pooka 	 * Ensure that all preconditions are valid, since this is
    264   1.1     pooka 	 * an all or nothing deal.  Once a system call is entered,
    265   1.1     pooka 	 * it can become busy and we could be unable to remove it
    266   1.1     pooka 	 * on error.
    267   1.1     pooka 	 */
    268   1.1     pooka 	for (i = 0; sp[i].sp_call != NULL; i++) {
    269   1.1     pooka 		if (sy[sp[i].sp_code].sy_call != sys_nomodule) {
    270   1.1     pooka #ifdef DIAGNOSTIC
    271   1.1     pooka 			printf("syscall %d is busy\n", sp[i].sp_code);
    272   1.1     pooka #endif
    273   1.1     pooka 			return EBUSY;
    274   1.1     pooka 		}
    275   1.1     pooka 	}
    276   1.1     pooka 	/* Everything looks good, patch them in. */
    277   1.1     pooka 	for (i = 0; sp[i].sp_call != NULL; i++) {
    278   1.1     pooka 		sy[sp[i].sp_code].sy_call = sp[i].sp_call;
    279   1.1     pooka 	}
    280   1.1     pooka 
    281   1.1     pooka 	return 0;
    282   1.1     pooka }
    283   1.1     pooka 
    284   1.1     pooka int
    285   1.1     pooka syscall_disestablish(const struct emul *em, const struct syscall_package *sp)
    286   1.1     pooka {
    287   1.1     pooka 	struct sysent *sy;
    288   1.1     pooka 	uint64_t where;
    289   1.1     pooka 	lwp_t *l;
    290   1.1     pooka 	int i;
    291   1.1     pooka 
    292   1.5  pgoyette 	KASSERT(kernconfig_is_held());
    293   1.1     pooka 
    294   1.1     pooka 	if (em == NULL) {
    295   1.1     pooka 		em = &emul_netbsd;
    296   1.1     pooka 	}
    297   1.1     pooka 	sy = em->e_sysent;
    298   1.1     pooka 
    299   1.1     pooka 	/*
    300   1.1     pooka 	 * First, patch the system calls to sys_nomodule to gate further
    301   1.1     pooka 	 * activity.
    302   1.1     pooka 	 */
    303   1.1     pooka 	for (i = 0; sp[i].sp_call != NULL; i++) {
    304   1.1     pooka 		KASSERT(sy[sp[i].sp_code].sy_call == sp[i].sp_call);
    305   1.1     pooka 		sy[sp[i].sp_code].sy_call = sys_nomodule;
    306   1.1     pooka 	}
    307   1.1     pooka 
    308   1.1     pooka 	/*
    309   1.1     pooka 	 * Run a cross call to cycle through all CPUs.  This does two
    310   1.1     pooka 	 * things: lock activity provides a barrier and makes our update
    311   1.1     pooka 	 * of sy_call visible to all CPUs, and upon return we can be sure
    312   1.1     pooka 	 * that we see pertinent values of l_sysent posted by remote CPUs.
    313   1.1     pooka 	 */
    314   1.1     pooka 	where = xc_broadcast(0, (xcfunc_t)nullop, NULL, NULL);
    315   1.1     pooka 	xc_wait(where);
    316   1.1     pooka 
    317   1.1     pooka 	/*
    318   1.1     pooka 	 * Now it's safe to check l_sysent.  Run through all LWPs and see
    319   1.1     pooka 	 * if anyone is still using the system call.
    320   1.1     pooka 	 */
    321   1.1     pooka 	for (i = 0; sp[i].sp_call != NULL; i++) {
    322   1.1     pooka 		mutex_enter(proc_lock);
    323   1.1     pooka 		LIST_FOREACH(l, &alllwp, l_list) {
    324   1.1     pooka 			if (l->l_sysent == &sy[sp[i].sp_code]) {
    325   1.1     pooka 				break;
    326   1.1     pooka 			}
    327   1.1     pooka 		}
    328   1.1     pooka 		mutex_exit(proc_lock);
    329   1.1     pooka 		if (l == NULL) {
    330   1.1     pooka 			continue;
    331   1.1     pooka 		}
    332   1.1     pooka 		/*
    333   1.1     pooka 		 * We lose: one or more calls are still in use.  Put back
    334   1.1     pooka 		 * the old entrypoints and act like nothing happened.
    335   1.5  pgoyette 		 * When we drop kernconfig_lock, any system calls held in
    336   1.1     pooka 		 * sys_nomodule() will be restarted.
    337   1.1     pooka 		 */
    338   1.1     pooka 		for (i = 0; sp[i].sp_call != NULL; i++) {
    339   1.1     pooka 			sy[sp[i].sp_code].sy_call = sp[i].sp_call;
    340   1.1     pooka 		}
    341   1.1     pooka 		return EBUSY;
    342   1.1     pooka 	}
    343   1.1     pooka 
    344   1.1     pooka 	return 0;
    345   1.1     pooka }
    346   1.8     pooka 
    347   1.8     pooka /*
    348   1.8     pooka  * Return true if system call tracing is enabled for the specified process.
    349   1.8     pooka  */
    350   1.8     pooka bool
    351   1.8     pooka trace_is_enabled(struct proc *p)
    352   1.8     pooka {
    353   1.8     pooka #ifdef SYSCALL_DEBUG
    354   1.8     pooka 	return (true);
    355   1.8     pooka #endif
    356   1.8     pooka #ifdef KTRACE
    357   1.8     pooka 	if (ISSET(p->p_traceflag, (KTRFAC_SYSCALL | KTRFAC_SYSRET)))
    358   1.8     pooka 		return (true);
    359   1.8     pooka #endif
    360   1.8     pooka #ifdef PTRACE
    361   1.8     pooka 	if (ISSET(p->p_slflag, PSL_SYSCALL))
    362   1.8     pooka 		return (true);
    363   1.8     pooka #endif
    364   1.8     pooka 
    365   1.8     pooka 	return (false);
    366   1.8     pooka }
    367   1.8     pooka 
    368   1.8     pooka /*
    369   1.8     pooka  * Start trace of particular system call. If process is being traced,
    370   1.8     pooka  * this routine is called by MD syscall dispatch code just before
    371   1.8     pooka  * a system call is actually executed.
    372   1.8     pooka  */
    373   1.8     pooka int
    374  1.10  christos trace_enter(register_t code, const struct sysent *sy, const void *args)
    375   1.8     pooka {
    376   1.8     pooka 	int error = 0;
    377   1.8     pooka 
    378  1.10  christos #ifdef KDTRACE_HOOKS
    379  1.10  christos 	if (sy->sy_entry) {
    380  1.10  christos 		struct emul *e = curlwp->l_proc->p_emul;
    381  1.10  christos 		(*e->e_dtrace_syscall)(sy->sy_entry, code, sy, args, NULL, 0);
    382  1.10  christos 	}
    383  1.10  christos #endif
    384  1.10  christos 
    385   1.8     pooka #ifdef SYSCALL_DEBUG
    386   1.8     pooka 	scdebug_call(code, args);
    387   1.8     pooka #endif /* SYSCALL_DEBUG */
    388   1.8     pooka 
    389  1.10  christos 	ktrsyscall(code, args, sy->sy_narg);
    390   1.8     pooka 
    391   1.8     pooka #ifdef PTRACE
    392   1.8     pooka 	if ((curlwp->l_proc->p_slflag & (PSL_SYSCALL|PSL_TRACED)) ==
    393   1.8     pooka 	    (PSL_SYSCALL|PSL_TRACED)) {
    394   1.8     pooka 		process_stoptrace();
    395   1.8     pooka 		if (curlwp->l_proc->p_slflag & PSL_SYSCALLEMU) {
    396   1.8     pooka 			/* tracer will emulate syscall for us */
    397   1.8     pooka 			error = EJUSTRETURN;
    398   1.8     pooka 		}
    399   1.8     pooka 	}
    400   1.8     pooka #endif
    401   1.8     pooka 	return error;
    402   1.8     pooka }
    403   1.8     pooka 
    404   1.8     pooka /*
    405   1.8     pooka  * End trace of particular system call. If process is being traced,
    406   1.8     pooka  * this routine is called by MD syscall dispatch code just after
    407   1.8     pooka  * a system call finishes.
    408   1.8     pooka  * MD caller guarantees the passed 'code' is within the supported
    409   1.8     pooka  * system call number range for emulation the process runs under.
    410   1.8     pooka  */
    411   1.8     pooka void
    412  1.10  christos trace_exit(register_t code, const struct sysent *sy, const void *args,
    413  1.10  christos     register_t rval[], int error)
    414   1.8     pooka {
    415  1.10  christos #if defined(PTRACE) || defined(KDTRACE_HOOKS)
    416   1.8     pooka 	struct proc *p = curlwp->l_proc;
    417   1.8     pooka #endif
    418   1.8     pooka 
    419  1.10  christos #ifdef KDTRACE_HOOKS
    420  1.10  christos 	if (sy->sy_return) {
    421  1.10  christos 		(*p->p_emul->e_dtrace_syscall)(sy->sy_return, code, sy, args,
    422  1.10  christos 		    rval, error);
    423  1.10  christos 	}
    424  1.10  christos #endif
    425  1.10  christos 
    426   1.8     pooka #ifdef SYSCALL_DEBUG
    427   1.8     pooka 	scdebug_ret(code, error, rval);
    428   1.8     pooka #endif /* SYSCALL_DEBUG */
    429   1.8     pooka 
    430   1.8     pooka 	ktrsysret(code, error, rval);
    431   1.8     pooka 
    432   1.8     pooka #ifdef PTRACE
    433   1.8     pooka 	if ((p->p_slflag & (PSL_SYSCALL|PSL_TRACED|PSL_SYSCALLEMU)) ==
    434   1.8     pooka 	    (PSL_SYSCALL|PSL_TRACED))
    435   1.8     pooka 		process_stoptrace();
    436   1.8     pooka 	CLR(p->p_slflag, PSL_SYSCALLEMU);
    437   1.8     pooka #endif
    438   1.8     pooka }
    439