Subject: iBCS2 work-in-progress patches
To: None <port-i386@netbsd.org>
From: Arne H Juul <arnej@dsl.unit.no>
List: port-i386
Date: 09/25/1994 12:07:09
Here's a set of patches from netbsd-current to my
work-in-progress version of the iBCS2 emulator.
Highlights:
* the signal() routine now done in the 'correct' SYSV style, with
an extra flag to sigaction (SA_IBCS2) to support it.
* poll() implemented on top of select()
* /dev/socksys implemented by intercepting the ioctl's for it. I have
added some fake numbers for the socket syscalls to facilitate
ktrace of programs using sockets. Currently this means you have to
define the KTRACE option to compile this stuff. If you are unhappy
about this feel free to tell me.
Still not done:
* lots of ioctl's (I hope to have some of the socket ioctl's done
soon).
* the semid_ds and shmid_ds data structures are different on
my SCO box compared to the NetBSD implementation. This is a bit
strange, since the comments in the NetBSD implementation indicates
that they were indeed meant to be SYSV binary compatible. I'll add
some conversion routines for these. Please tell me if conversion
should be ifdef SCO_EMUL or something.
* ...and probably lots more...
Yours,
- Arne H. Juul
diff -ruP /sys/compat/ibcs2/ibcs2_ioctl.c ./compat/ibcs2/ibcs2_ioctl.c
--- /sys/compat/ibcs2/ibcs2_ioctl.c Wed Aug 24 21:13:54 1994
+++ ./compat/ibcs2/ibcs2_ioctl.c Fri Sep 9 20:26:16 1994
@@ -30,14 +30,18 @@
#include <sys/file.h>
#include <sys/filedesc.h>
#include <sys/ioctl.h>
+#include <sys/kernel.h>
#include <sys/termios.h>
#include <sys/tty.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <net/if.h>
+#include <sys/ktrace.h>
#include <compat/ibcs2/ibcs2_types.h>
#include <compat/ibcs2/ibcs2_termios.h>
+#include <compat/ibcs2/ibcs2_socksys.h>
+#include <compat/ibcs2/ibcs2_syscall.h>
#ifdef DEBUG_IBCS2
#define DPRINTF(s) printf s
@@ -410,9 +414,8 @@
DPRINTF(("ibcs2_ioctl(%d): TCFLSH ", p->p_pid));
return ENOSYS;
case IBCS2_TIOCGWINSZ:
- DPRINTF(("ibcs2_ioctl(%d): TIOCGWINSZ ", p->p_pid));
- return ENOSYS;
-
+ uap->cmd = TIOCGWINSZ;
+ return(ioctl(p, uap, retval));
case IBCS2_TIOCSWINSZ:
DPRINTF(("ibcs2_ioctl(%d): TIOCSWINSZ ", p->p_pid));
return ENOSYS;
@@ -434,6 +437,8 @@
return error;
return 0;
}
+ case IBCS2_SIOCSOCKSYS:
+ return ibcs2_socksys(p, uap, retval);
default:
DPRINTF(("ibcs2_ioctl(%d): unknown cmd 0x%x ",
@@ -443,3 +448,125 @@
return ENOSYS;
}
+struct ibcs2_getipdomainname_args {
+ caddr_t name;
+ int namelen;
+};
+
+int
+ibcs2_getipdomainname(p, uap, retval)
+ register struct proc *p;
+ register struct ibcs2_getipdomainname_args *uap;
+ int *retval;
+{
+ char *cp;
+ cp = hostname;
+ while (*cp && (*cp != '.'))
+ cp++;
+ if (*cp == '.') cp++;
+ return copyout(cp, uap->name,
+ min(MAXHOSTNAMELEN-(cp-hostname), uap->namelen));
+}
+
+struct ibcs2_socksys_args {
+ int fd;
+ int magic;
+ caddr_t argsp;
+};
+
+int
+ibcs2_socksys(p, uap, retval)
+ register struct proc *p;
+ register struct ibcs2_socksys_args *uap;
+ int *retval;
+{
+ register struct filedesc *fdp = p->p_fd;
+ register struct file *fp;
+ int error;
+ int realargs[7]; /* 1 for command, 6 for recvfrom */
+
+ /*
+ * SOCKET should only be legal on /dev/socksys.
+ * GETIPDOMAINNAME should only be legal on /dev/socksys ?
+ * The others are (and should be) only legal on sockets ?
+ */
+
+ if (error = copyin(uap->argsp, (caddr_t)realargs, sizeof(realargs)))
+ return error;
+ switch (realargs[0]) {
+ /* XXX - this is wrong. */
+ case SOCKSYS_GETIPDOMAINNAME:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep,
+ IBCS2_SYS_ibcs2_getipdomainname,
+ 3, realargs+1);
+ return ibcs2_getipdomainname(p, realargs+1, retval);
+ case SOCKSYS_ACCEPT:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_accept,
+ 3, realargs+1);
+ return accept(p, realargs+1, retval);
+ case SOCKSYS_BIND:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_bind,
+ 3, realargs+1);
+ return bind(p, realargs+1, retval);
+ case SOCKSYS_CONNECT:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_connect,
+ 3, realargs+1);
+ return connect(p, realargs+1, retval);
+ case SOCKSYS_GETPEERNAME:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_getpeername,
+ 3, realargs+1);
+ return getpeername(p, realargs+1, retval);
+ case SOCKSYS_GETSOCKNAME:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_getsockname,
+ 3, realargs+1);
+ return getsockname(p, realargs+1, retval);
+ case SOCKSYS_GETSOCKOPT:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_getsockopt,
+ 5, realargs+1);
+ return getsockopt(p, realargs+1, retval);
+ case SOCKSYS_LISTEN:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_listen,
+ 2, realargs+1);
+ return listen(p, realargs+1, retval);
+ case SOCKSYS_RECVFROM:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_recvfrom,
+ 6, realargs+1);
+ return recvfrom(p, realargs+1, retval);
+ case SOCKSYS_SENDTO:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_sendto,
+ 6, realargs+1);
+ return sendto(p, realargs+1, retval);
+ case SOCKSYS_SETSOCKOPT:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_setsockopt,
+ 5, realargs+1);
+ return setsockopt(p, realargs+1, retval);
+ case SOCKSYS_SHUTDOWN:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_shutdown,
+ 2, realargs+1);
+ return shutdown(p, realargs+1, retval);
+ case SOCKSYS_SOCKET:
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_socket,
+ 3, realargs+1);
+ return socket(p, realargs+1, retval);
+
+ default:
+ printf("socksys unknown %08x %08x %08x %08x %08x %08x %08x\n",
+ realargs[0], realargs[1], realargs[2], realargs[3],
+ realargs[4], realargs[5], realargs[6]);
+ return EINVAL;
+ }
+ /* NOTREACHED */
+}
diff -ruP /sys/compat/ibcs2/ibcs2_misc.c ./compat/ibcs2/ibcs2_misc.c
--- /sys/compat/ibcs2/ibcs2_misc.c Wed Aug 24 21:13:56 1994
+++ ./compat/ibcs2/ibcs2_misc.c Fri Sep 9 20:26:19 1994
@@ -80,6 +80,9 @@
#include <sys/wait.h>
#include <sys/utsname.h>
#include <sys/unistd.h>
+#include <sys/ipc.h>
+#include <sys/sem.h>
+#include <sys/ktrace.h>
#include <netinet/in.h>
@@ -100,6 +103,8 @@
#include <compat/ibcs2/ibcs2_unistd.h>
#include <compat/ibcs2/ibcs2_ustat.h>
#include <compat/ibcs2/ibcs2_utsname.h>
+#include <compat/ibcs2/ibcs2_poll.h>
+#include <compat/ibcs2/ibcs2_syscall.h>
#ifdef DEBUG_IBCS2
#define DPRINTF(s) printf s
@@ -108,7 +113,7 @@
#endif
#define szsigcode (esigcode - sigcode)
-#define STACK_ALLOC() ALIGN(PS_STRINGS - szsigcode - STACKGAPLEN)
+#define STACK_ALLOC() ALIGN(((caddr_t)PS_STRINGS) - szsigcode - STACKGAPLEN)
#define NOSIG (-1)
extern char sigcode[], esigcode[];
@@ -142,8 +147,8 @@
SIGCONT, /* 25 */
SIGTTIN, /* 26 */
SIGTTOU, /* 27 */
- NOSIG, /* 28 */
- NOSIG, /* 29 */
+ SIGVTALRM, /* 28 */
+ SIGPROF, /* 29 */
NOSIG, /* 30 */
NOSIG, /* 31 */
};
@@ -175,8 +180,8 @@
NOSIG, /* 23 */
NOSIG, /* 24 */
NOSIG, /* 25 */
- NOSIG, /* 26 */
- NOSIG, /* 27 */
+ IBCS2_SIGVTALRM, /* 26 */
+ IBCS2_SIGPROF, /* 27 */
IBCS2_SIGWINCH, /* 28 */
NOSIG, /* 29 */
IBCS2_SIGUSR1, /* 30 */
@@ -201,8 +206,8 @@
int i, newmask;
for (i = 0, newmask = 0; i < NSIG; i++)
- if ((sigtbl[i] != NOSIG) && (mask & (1 << i)))
- newmask |= (1 << (sigtbl[i] - 1));
+ if ((sigtbl[i] != NOSIG) && (mask & sigmask(i)))
+ newmask |= sigmask(sigtbl[i]);
return newmask;
}
@@ -218,89 +223,83 @@
int *retval;
{
int error;
+ struct sigprocmask_args {
+ int how;
+ sigset_t mask;
+ } spma;
+ struct sigaction *sap, *osap;
+ struct sigaction_args {
+ int sig;
+ struct sigaction *sa;
+ struct sigaction *osa;
+ } sa_args;
int nsig = ibcs2bsd_sig(IBCS2_SIGNO(uap->sig));
+/*
+ printf("sigsys sig %x nsig %x mask %x\n",
+ uap->sig, nsig, sigmask(nsig));
+*/
+
if (nsig == NOSIG) {
if (IBCS2_SIGCALL(uap->sig) == IBCS2_SIGNAL_MASK
|| IBCS2_SIGCALL(uap->sig) == IBCS2_SIGSET_MASK)
*retval = (int)IBCS2_SIG_ERR;
return EINVAL;
}
+
switch (IBCS2_SIGCALL(uap->sig)) {
/*
* sigset is identical to signal() except that SIG_HOLD is allowed as
- * an action and we don't set the bit in the ibcs_sigflags field.
+ * an action, pending signals are released not still blocked, and
+ * the SA_IBCS2 option is not used to set the ibcs_sigflags bit.
*/
case IBCS2_SIGSET_MASK:
if (uap->fp == IBCS2_SIG_HOLD) {
- struct sigprocmask_args {
- int how;
- sigset_t mask;
- } sa;
-
- sa.how = SIG_BLOCK;
- sa.mask = sigmask(nsig);
- return sigprocmask(p, &sa, retval);
+ spma.how = SIG_BLOCK;
+ spma.mask = sigmask(nsig);
+ return sigprocmask(p, &spma, retval);
+ } else {
+ /* sigset() releases pending signals */
+ spma.how = SIG_UNBLOCK;
+ spma.mask = sigmask(nsig);
+ if (error=sigprocmask(p, &spma, retval))
+ return(error);
}
- /* else fall through */
-
+ /* FALLTHROUGH */
case IBCS2_SIGNAL_MASK:
- {
- struct sigaction *sap, *osap;
- struct sigaction_args {
- int sig;
- struct sigaction *sa;
- struct sigaction *osa;
- } sa_args;
-
- sap = (struct sigaction *)STACK_ALLOC();
- osap = &sap[1];
- sa_args.sig = nsig;
- sa_args.sa = sap;
- sa_args.osa = osap;
- sa_args.sa->sa_handler = uap->fp;
- sa_args.sa->sa_mask = (sigset_t)0;
- sa_args.sa->sa_flags = 0;
-#if 0
- if (sa_args.sig != SIGALRM)
- sa_args.sa->sa_flags = SA_RESTART;
-#endif
- error = sigaction(p, &sa_args, retval);
- if (error) {
- DPRINTF(("signal: sigaction failed: %d\n",
- error));
- *retval = (int)IBCS2_SIG_ERR;
- return error;
- }
- *retval = (int)sa_args.osa->sa_handler;
- if (IBCS2_SIGCALL(uap->sig) == IBCS2_SIGNAL_MASK)
- p->p_md.ibcs_sigflags |= sigmask(nsig);
- return 0;
+ sap = (struct sigaction *)STACK_ALLOC();
+ osap = &sap[1];
+ sa_args.sig = nsig;
+ sa_args.sa = sap;
+ sa_args.osa = osap;
+ sa_args.sa->sa_handler = uap->fp;
+ sa_args.sa->sa_mask = (sigset_t)0;
+ sa_args.sa->sa_flags = 0;
+ if (IBCS2_SIGCALL(uap->sig) == IBCS2_SIGNAL_MASK) {
+ if (uap->fp == IBCS2_SIG_HOLD)
+ return EINVAL;
+ /* signal() cancels pending signals XXX */
+ p->p_siglist &= ~sigmask(nsig);
+ sa_args.sa->sa_flags = SA_IBCS2;
}
-
+ if (error = sigaction(p, &sa_args, retval))
+ return error;
+ *retval = (int)sa_args.osa->sa_handler;
+ return 0;
+
case IBCS2_SIGHOLD_MASK:
{
- struct sigprocmask_args {
- int how;
- sigset_t mask;
- } sa;
-
- sa.how = SIG_BLOCK;
- sa.mask = sigmask(nsig);
- return sigprocmask(p, &sa, retval);
+ spma.how = SIG_BLOCK;
+ spma.mask = sigmask(nsig);
+ return sigprocmask(p, &spma, retval);
}
case IBCS2_SIGRELSE_MASK:
{
- struct sigprocmask_args {
- int how;
- sigset_t mask;
- } sa;
-
- sa.how = SIG_UNBLOCK;
- sa.mask = sigmask(nsig);
- return sigprocmask(p, &sa, retval);
+ spma.how = SIG_UNBLOCK;
+ spma.mask = sigmask(nsig);
+ return sigprocmask(p, &spma, retval);
}
case IBCS2_SIGIGNORE_MASK:
@@ -332,7 +331,7 @@
struct sigsuspend_args {
sigset_t mask;
} sa;
- sa.mask = p->p_sigmask &~ sigmask(nsig);
+ sa.mask = p->p_sigmask & ~sigmask(nsig);
return sigsuspend(p, &sa, retval);
}
@@ -532,6 +531,7 @@
#define IBCS2_GETFSIZE 1
#define IBCS2_SETFSIZE 2
#define IBCS2_GETPSIZE 3
+#define IBCS2_GETDTABLESIZE 4
int
ibcs2_ulimit(p, uap, retval)
@@ -568,6 +568,9 @@
case IBCS2_GETPSIZE:
*retval = p->p_rlimit[RLIMIT_RSS].rlim_cur; /* XXX */
return 0;
+ case IBCS2_GETDTABLESIZE:
+ uap->cmd = IBCS2_SC_OPEN_MAX ;
+ return ibcs2_sysconf(p, uap, retval);
default:
return ENOSYS;
}
@@ -910,16 +913,22 @@
case 0: /* uname(2) */
{
struct ibcs2_utsname sut;
+ char *cp;
extern char ostype[], machine[], osrelease[];
bzero(&sut, ibcs2_utsname_len);
bcopy(ostype, sut.sysname, sizeof(sut.sysname) - 1);
- bcopy(hostname, sut.nodename, sizeof(sut.nodename));
+ sut.sysname[sizeof(sut.sysname)-1] = '\0';
+ bcopy(hostname, sut.nodename, sizeof(sut.nodename) - 1);
sut.nodename[sizeof(sut.nodename)-1] = '\0';
+ for (cp = sut.nodename; *cp; cp++)
+ if (*cp == '.') *cp = '\0';
bcopy(osrelease, sut.release, sizeof(sut.release) - 1);
+ sut.release[sizeof(sut.release)-1] = '\0';
bcopy("1", sut.version, sizeof(sut.version) - 1);
bcopy(machine, sut.machine, sizeof(sut.machine) - 1);
+ sut.machine[sizeof(sut.machine)-1] = '\0';
return copyout((caddr_t)&sut, (caddr_t)uap->u.uname_args.buf,
ibcs2_utsname_len);
@@ -1087,32 +1096,15 @@
return EINVAL;
}
-struct ibcs2_select_args {
- int nfds;
- fd_set *readfds, *writefds, *exceptfds;
- struct ibcs2_timeval *timeout;
-};
-
-/* int select(nfds, readfds, writefds, exceptfds, timeout) */
-
-int
-ibcs2_select(p, uap, retval)
- struct proc *p;
- struct ibcs2_select_args *uap;
- int *retval;
-{
- return EINVAL;
-}
-
static void
cvt_sa2isa(sap, isap)
struct sigaction *sap;
struct ibcs2_sigaction *isap;
{
- sap->sa_handler = isap->sa_handler;
- sap->sa_mask = cvt_sigmask(isap->sa_mask, ibcs2bsd_sigtbl);
- sap->sa_flags = (isap->sa_flags & IBCS2_SA_NOCLDSTOP)
- ? SA_NOCLDSTOP : 0;
+ isap->sa_handler = sap->sa_handler;
+ isap->sa_mask = cvt_sigmask(sap->sa_mask, bsd2ibcs_sigtbl);
+ isap->sa_flags = (sap->sa_flags & SA_NOCLDSTOP)
+ ? IBCS2_SA_NOCLDSTOP : 0;
}
static void
@@ -1120,15 +1112,15 @@
struct ibcs2_sigaction *isap;
struct sigaction *sap;
{
- isap->sa_handler = sap->sa_handler;
- isap->sa_mask = cvt_sigmask(sap->sa_mask, bsd2ibcs_sigtbl);
- isap->sa_flags = (sap->sa_flags & SA_NOCLDSTOP)
- ? IBCS2_SA_NOCLDSTOP : 0;
+ sap->sa_handler = isap->sa_handler;
+ sap->sa_mask = cvt_sigmask(isap->sa_mask, ibcs2bsd_sigtbl);
+ sap->sa_flags = (isap->sa_flags & IBCS2_SA_NOCLDSTOP)
+ ? SA_NOCLDSTOP : 0;
}
struct ibcs2_sigaction_args {
int sig;
- struct ibcs2_sigaction *act, *oact;
+ struct ibcs2_sigaction *nsa, *osa;
};
int
@@ -1137,25 +1129,42 @@
struct ibcs2_sigaction_args *uap;
int *retval;
{
- int error;
- struct sigaction_args {
- int sig;
- struct sigaction *act, *oact;
- } sa;
- struct ibcs2_sigaction *isa, *oisa;
-
- isa = (struct ibcs2_sigaction *)STACK_ALLOC();
- oisa = &isa[1];
- sa.sig = ibcs2bsd_sig(uap->sig);
- sa.act = (struct sigaction *)&isa[2];
- sa.oact = (struct sigaction *)&isa[3];
- if (error = copyin((caddr_t)uap->act, (caddr_t)isa, sizeof(*isa)))
- return error;
- cvt_isa2sa(isa, sa.act);
- if (error = sigaction(p, &sa, retval))
- return error;
- cvt_sa2isa(sa.oact, oisa);
- return copyout((caddr_t)oisa, (caddr_t)uap->oact, sizeof(*oisa));
+ struct ibcs2_sigaction isa;
+ struct sigaction vec;
+ register struct sigaction *sa;
+ register struct sigacts *ps = p->p_sigacts;
+ register int signum;
+ int bit, error;
+
+ signum = ibcs2bsd_sig(uap->sig);
+ if (signum <= 0 || signum >= NSIG ||
+ signum == SIGKILL || signum == SIGSTOP)
+ return (EINVAL);
+ sa = &vec;
+ if (uap->osa) {
+ sa->sa_handler = ps->ps_sigact[signum];
+ sa->sa_mask = ps->ps_catchmask[signum];
+ bit = sigmask(signum);
+ sa->sa_flags = 0;
+ if ((ps->ps_sigonstack & bit) != 0)
+ sa->sa_flags |= SA_ONSTACK;
+ if ((ps->ps_sigintr & bit) == 0)
+ sa->sa_flags |= SA_RESTART;
+ if (p->p_flag & P_NOCLDSTOP)
+ sa->sa_flags |= SA_NOCLDSTOP;
+ cvt_sa2isa(sa, &isa);
+ if (error = copyout((caddr_t)&isa, (caddr_t)uap->osa,
+ sizeof (vec)))
+ return (error);
+ }
+ if (uap->nsa) {
+ if (error = copyin((caddr_t)uap->nsa, (caddr_t)&isa,
+ sizeof (vec)))
+ return (error);
+ cvt_isa2sa(&isa, sa);
+ setsigvec(p, signum, sa);
+ }
+ return (0);
}
struct ibcs2_sigprocmask_args {
@@ -1176,25 +1185,36 @@
sigset_t mask;
} sa;
- switch (uap->how) {
- case IBCS2_SIG_BLOCK:
+ if (uap->set) {
+ switch (uap->how) {
+ case IBCS2_SIG_BLOCK:
+ sa.how = SIG_BLOCK;
+ break;
+ case IBCS2_SIG_UNBLOCK:
+ sa.how = SIG_UNBLOCK;
+ break;
+ case IBCS2_SIG_SETMASK:
+ sa.how = SIG_SETMASK;
+ break;
+ default:
+ return EINVAL;
+ }
+ if (error = copyin((caddr_t)uap->set, (caddr_t)&iset,
+ sizeof(iset)))
+ return error;
+ sa.mask = cvt_sigmask(iset, ibcs2bsd_sigtbl);
+ } else {
sa.how = SIG_BLOCK;
- break;
- case IBCS2_SIG_UNBLOCK:
- sa.how = SIG_UNBLOCK;
- break;
- case IBCS2_SIG_SETMASK:
- sa.how = SIG_SETMASK;
- break;
- default:
- return EINVAL;
+ sa.mask = 0;
}
- if (error = copyin((caddr_t)uap->set, (caddr_t)&iset, sizeof(iset)))
- return error;
- sa.mask = cvt_sigmask(iset, ibcs2bsd_sigtbl);
if (error = sigprocmask(p, &sa, retval))
return error;
+ if (uap->oset == NULL) {
+ *retval = 0;
+ return 0;
+ }
iset = cvt_sigmask(*retval, bsd2ibcs_sigtbl);
+ *retval = 0;
return copyout((caddr_t)&iset, (caddr_t)uap->oset, sizeof(iset));
}
@@ -1722,17 +1742,33 @@
return copyout(&tms, uap->tp, sizeof(tms));
}
+struct ibcs2_utime_args {
+ char *path;
+ struct ibcs2_utimbuf *times;
+};
int
-ibcs2_stime(p, uap, retval)
+ibcs2_utime(p, uap, retval)
struct proc *p;
- void *uap;
+ struct ibcs2_utime_args *uap;
int *retval;
{
- return EINVAL; /* XXX - TODO */
+ int error;
+ if (uap->times) {
+ struct ibcs2_utimbuf tmpt;
+ struct timeval *tv = (struct timeval *)STACK_ALLOC();
+ if (error = copyin(uap->times, &tmpt, sizeof tmpt))
+ return (error);
+ tv[0].tv_sec = tmpt.actime;
+ tv[1].tv_sec = tmpt.modtime;
+ tv[0].tv_usec = tv[1].tv_usec = 0;
+ uap->times = (struct ibcs2_utimbuf *)tv;
+ }
+ return utimes(p, uap, retval);
}
+
int
-ibcs2_ptrace(p, uap, retval)
+ibcs2_stime(p, uap, retval)
struct proc *p;
void *uap;
int *retval;
@@ -1741,7 +1777,7 @@
}
int
-ibcs2_utime(p, uap, retval)
+ibcs2_ptrace(p, uap, retval)
struct proc *p;
void *uap;
int *retval;
@@ -1749,6 +1785,7 @@
return EINVAL; /* XXX - TODO */
}
+
int
ibcs2_nice(p, uap, retval)
struct proc *p;
@@ -1841,11 +1878,134 @@
return EINVAL; /* XXX - TODO */
}
+struct ibcs2_poll_args {
+ struct pollfd *fds;
+ unsigned long nfds;
+ int timeout;
+};
+
int
ibcs2_poll(p, uap, retval)
struct proc *p;
- void *uap;
+ struct ibcs2_poll_args *uap;
int *retval;
{
- return EINVAL; /* XXX - TODO */
+ int i, error;
+ struct pollfd conv;
+ fd_set *readfds, *writefds, *exceptfds;
+ struct timeval *tmout;
+ struct select_args {
+ u_int nd;
+ fd_set *in, *ou, *ex;
+ struct timeval *tv;
+ } s_a;
+
+ DPRINTF(("poll nfds %d tmo %x\n", uap->nfds, uap->timeout));
+ readfds = (fd_set *)STACK_ALLOC();
+ writefds = readfds+1;
+ exceptfds = readfds+2;
+ tmout = (struct timeval *)(readfds+3);
+
+ if (uap->nfds < 0 || uap->nfds > FD_SETSIZE) {
+ return EINVAL;
+ }
+ if (uap->timeout == -1) {
+ tmout = NULL;
+ } else {
+ tmout->tv_usec = (uap->timeout % 1000)*1000;
+ tmout->tv_sec = uap->timeout / 1000;
+ }
+ FD_ZERO(readfds);
+ FD_ZERO(writefds);
+ FD_ZERO(exceptfds);
+ s_a.nd = 0;
+ s_a.tv = tmout;
+ s_a.in = readfds;
+ s_a.ou = writefds;
+ s_a.ex = exceptfds;
+
+ for (i=0; i<uap->nfds; i++) {
+ if (error = copyin(uap->fds+i, &conv, sizeof(conv)))
+ return error;
+ conv.revents = 0;
+ if (conv.fd < 0 || conv.fd > FD_SETSIZE) {
+ continue;
+ }
+ if (conv.fd >= s_a.nd) {
+ s_a.nd = conv.fd+1;
+ }
+ /* should check if fd is open here - XXX */
+ if (conv.events | POLLIN) {
+ DPRINTF(("polling for read on %d\n", conv.fd));
+ FD_SET(conv.fd, readfds);
+ }
+ if (conv.events | POLLPRI) {
+ DPRINTF(("wanted polling for pri on %d\n", conv.fd));
+ /* you may ask for it, but will not get it */
+ }
+ if (conv.events | POLLOUT) {
+ DPRINTF(("polling for write on %d\n", conv.fd));
+ FD_SET(conv.fd, writefds);
+ }
+ DPRINTF(("always polling for exceptions on %d\n", conv.fd));
+ FD_SET(conv.fd, exceptfds);
+ }
+ if (KTRPOINT(p, KTR_SYSCALL))
+ ktrsyscall(p->p_tracep, IBCS2_SYS_select, 5, &s_a);
+ if (error = select(p, &s_a, retval)) {
+ if (KTRPOINT(p, KTR_SYSRET))
+ ktrsysret(p->p_tracep, IBCS2_SYS_select, error,
+ retval[0]);
+ return error;
+ }
+ if (*retval == 0)
+ return 0; /* Nothing selected */
+ *retval = 0;
+ for (i=0; i<uap->nfds; i++) {
+ copyin(uap->fds+i, &conv, sizeof(conv)); /* ok */
+ conv.revents = 0;
+ if (!(conv.fd < 0 || conv.fd > FD_SETSIZE)) {
+ if (FD_ISSET(conv.fd, readfds))
+ conv.revents |= POLLIN;
+ if (FD_ISSET(conv.fd, writefds))
+ conv.revents |= POLLOUT;
+ if (FD_ISSET(conv.fd, exceptfds))
+ conv.revents |= POLLERR; /* XXX */
+ if (conv.revents)
+ ++*retval;
+ }
+ if (error = copyout(&conv, uap->fds+i, sizeof(conv)))
+ return error;
+ }
+ return 0;
+}
+
+/*
+ * Fake shim.
+ */
+
+struct ibcs2_semsys_semctl_args {
+ u_int which;
+ int semid;
+ int semnum;
+ int cmd;
+ union {
+ union semun arg;
+ union semun *farg;
+ } u;
+};
+
+int
+ibcs2_semsys(p, uap, retval)
+ struct proc *p;
+ struct ibcs2_semsys_semctl_args *uap;
+ int *retval;
+{
+ if (uap->which == 0) {
+ union semun *fake_arg;
+ fake_arg = (union semun *)STACK_ALLOC();
+ *fake_arg = uap->u.arg;
+ uap->u.farg = fake_arg;
+ }
+ return semsys(p, uap, retval);
}
diff -ruP /sys/compat/ibcs2/ibcs2_poll.h ./compat/ibcs2/ibcs2_poll.h
--- /sys/compat/ibcs2/ibcs2_poll.h Thu Jan 1 01:00:00 1970
+++ ./compat/ibcs2/ibcs2_poll.h Fri Sep 9 20:26:13 1994
@@ -0,0 +1,13 @@
+/* guessed these right on the first try */
+#define POLLIN 1
+#define POLLPRI 2
+#define POLLOUT 4
+#define POLLERR 8
+#define POLLHUP 16
+#define POLLNVAL 32
+
+struct pollfd {
+ int fd;
+ short events;
+ short revents;
+};
diff -ruP /sys/compat/ibcs2/ibcs2_signal.h ./compat/ibcs2/ibcs2_signal.h
--- /sys/compat/ibcs2/ibcs2_signal.h Wed Aug 24 21:14:02 1994
+++ ./compat/ibcs2/ibcs2_signal.h Fri Sep 9 20:25:52 1994
@@ -65,6 +65,9 @@
#define IBCS2_SIGCONT 25
#define IBCS2_SIGTTIN 26
#define IBCS2_SIGTTOU 27
+#define IBCS2_SIGVTALRM 28
+#define IBCS2_SIGPROF 29
+
#define IBCS2_SIG_DFL (void(*)())0
#define IBCS2_SIG_ERR (void(*)())-1
diff -ruP /sys/compat/ibcs2/ibcs2_socksys.h ./compat/ibcs2/ibcs2_socksys.h
--- /sys/compat/ibcs2/ibcs2_socksys.h Thu Jan 1 01:00:00 1970
+++ ./compat/ibcs2/ibcs2_socksys.h Fri Sep 9 20:21:29 1994
@@ -0,0 +1,17 @@
+#define IBCS2_SIOCSOCKSYS 0x801c4942
+
+#define SOCKSYS_ACCEPT 1
+#define SOCKSYS_BIND 2
+#define SOCKSYS_CONNECT 3
+#define SOCKSYS_GETPEERNAME 4
+#define SOCKSYS_GETSOCKNAME 5
+#define SOCKSYS_GETSOCKOPT 6
+#define SOCKSYS_LISTEN 7
+#define SOCKSYS_RECV 8
+#define SOCKSYS_RECVFROM 9
+#define SOCKSYS_SEND 10
+#define SOCKSYS_SENDTO 11
+#define SOCKSYS_SETSOCKOPT 12
+#define SOCKSYS_SHUTDOWN 13
+#define SOCKSYS_SOCKET 14
+#define SOCKSYS_GETIPDOMAINNAME 16
diff -ruP /sys/compat/ibcs2/ibcs2_syscall.h ./compat/ibcs2/ibcs2_syscall.h
--- /sys/compat/ibcs2/ibcs2_syscall.h Wed Aug 24 21:14:08 1994
+++ ./compat/ibcs2/ibcs2_syscall.h Fri Sep 9 20:26:08 1994
@@ -2,7 +2,7 @@
* System call numbers.
*
* DO NOT EDIT-- this file is automatically generated.
- * created from: NetBSD syscalls.master,v 1.1 1994/05/22 10:04:45
+ * created from: NetBSD syscalls.master,v 1.1 1994/08/24 19:14:29
*/
#define IBCS2_SYS_nosys 0
@@ -55,7 +55,7 @@
#define IBCS2_SYS_msgsys 49
#define IBCS2_SYS_acct 51
#define IBCS2_SYS_shmsys 52
-#define IBCS2_SYS_semsys 53
+#define IBCS2_SYS_ibcs2_semsys 53
#define IBCS2_SYS_ibcs2_ioctl 54
#define IBCS2_SYS_ibcs2_uadmin 55
#define IBCS2_SYS_ibcs2_utssys 57
@@ -84,8 +84,21 @@
#define IBCS2_SYS_ibcs2_lstat 91
#define IBCS2_SYS_readlink 92
#define IBCS2_SYS_sigreturn 103
+#define IBCS2_SYS_ibcs2_getipdomainname 109
+#define IBCS2_SYS_accept 110
+#define IBCS2_SYS_bind 111
+#define IBCS2_SYS_connect 112
+#define IBCS2_SYS_getpeername 113
+#define IBCS2_SYS_getsockname 114
+#define IBCS2_SYS_getsockopt 115
+#define IBCS2_SYS_listen 116
+#define IBCS2_SYS_recvfrom 117
+#define IBCS2_SYS_sendto 118
+#define IBCS2_SYS_setsockopt 119
+#define IBCS2_SYS_shutdown 120
+#define IBCS2_SYS_socket 121
#define IBCS2_SYS_ibcs2_ftime 139
-#define IBCS2_SYS_ibcs2_select 164
+#define IBCS2_SYS_select 164
#define IBCS2_SYS_ibcs2_sigaction 167
#define IBCS2_SYS_ibcs2_sigprocmask 168
#define IBCS2_SYS_ibcs2_sigpending 169
diff -ruP /sys/compat/ibcs2/ibcs2_syscalls.c ./compat/ibcs2/ibcs2_syscalls.c
--- /sys/compat/ibcs2/ibcs2_syscalls.c Wed Aug 24 21:14:10 1994
+++ ./compat/ibcs2/ibcs2_syscalls.c Fri Sep 9 20:26:06 1994
@@ -2,7 +2,7 @@
* System call names.
*
* DO NOT EDIT-- this file is automatically generated.
- * created from: NetBSD syscalls.master,v 1.1 1994/05/22 10:04:45
+ * created from: NetBSD syscalls.master,v 1.1 1994/08/24 19:14:29
*/
char *ibcs2_syscallnames[] = {
@@ -68,7 +68,7 @@
"#52", /* 52 = nosys */
#endif
#ifdef SYSVSEM
- "semsys", /* 53 = semsys */
+ "ibcs2_semsys", /* 53 = ibcs2_semsys */
#else
"#53", /* 53 = nosys */
#endif
@@ -127,19 +127,19 @@
"#106", /* 106 = nosys */
"#107", /* 107 = nosys */
"#108", /* 108 = nosys */
- "#109", /* 109 = nosys */
- "#110", /* 110 = nosys */
- "#111", /* 111 = nosys */
- "#112", /* 112 = nosys */
- "#113", /* 113 = nosys */
- "#114", /* 114 = nosys */
- "#115", /* 115 = nosys */
- "#116", /* 116 = nosys */
- "#117", /* 117 = nosys */
- "#118", /* 118 = nosys */
- "#119", /* 119 = nosys */
- "#120", /* 120 = nosys */
- "#121", /* 121 = nosys */
+ "ibcs2_getipdomainname", /* 109 = ibcs2_getipdomainname */
+ "accept", /* 110 = accept */
+ "bind", /* 111 = bind */
+ "connect", /* 112 = connect */
+ "getpeername", /* 113 = getpeername */
+ "getsockname", /* 114 = getsockname */
+ "getsockopt", /* 115 = getsockopt */
+ "listen", /* 116 = listen */
+ "recvfrom", /* 117 = recvfrom */
+ "sendto", /* 118 = sendto */
+ "setsockopt", /* 119 = setsockopt */
+ "shutdown", /* 120 = shutdown */
+ "socket", /* 121 = socket */
"#122", /* 122 = nosys */
"#123", /* 123 = nosys */
"#124", /* 124 = nosys */
@@ -182,7 +182,7 @@
"#161", /* 161 = XENIX execseg 0x2128 */
"#162", /* 162 = XENIX unexecseg 0x2228 */
"#163", /* 163 = XENIX nosys 0x2328 */
- "ibcs2_select", /* 164 = ibcs2_select */
+ "select", /* 164 = select */
"#165", /* 165 = XENIX eaccess 0x2528 */
"#166", /* 166 = XENIX paccess 0x2628 */
"ibcs2_sigaction", /* 167 = ibcs2_sigaction */
diff -ruP /sys/compat/ibcs2/ibcs2_sysent.c ./compat/ibcs2/ibcs2_sysent.c
--- /sys/compat/ibcs2/ibcs2_sysent.c Wed Aug 24 21:14:11 1994
+++ ./compat/ibcs2/ibcs2_sysent.c Fri Sep 9 20:26:02 1994
@@ -2,7 +2,7 @@
* System call switch table.
*
* DO NOT EDIT-- this file is automatically generated.
- * created from: NetBSD syscalls.master,v 1.1 1994/05/22 10:04:45
+ * created from: NetBSD syscalls.master,v 1.1 1994/08/24 19:14:29
*/
#include <sys/param.h>
@@ -67,7 +67,7 @@
#else
#endif
#ifdef SYSVSEM
-int semsys();
+int ibcs2_semsys();
#else
#endif
int ibcs2_ioctl();
@@ -89,8 +89,21 @@
int ibcs2_lstat();
int readlink();
int sigreturn();
+int ibcs2_getipdomainname();
+int accept();
+int bind();
+int connect();
+int getpeername();
+int getsockname();
+int getsockopt();
+int listen();
+int recvfrom();
+int sendto();
+int setsockopt();
+int shutdown();
+int socket();
int ibcs2_ftime();
-int ibcs2_select();
+int select();
int ibcs2_sigaction();
int ibcs2_sigprocmask();
int ibcs2_sigpending();
@@ -182,7 +195,7 @@
{ 0, nosys }, /* 52 = nosys */
#endif
#ifdef SYSVSEM
- { 5, semsys }, /* 53 = semsys */
+ { 5, ibcs2_semsys }, /* 53 = ibcs2_semsys */
#else
{ 0, nosys }, /* 53 = nosys */
#endif
@@ -241,19 +254,19 @@
{ 0, nosys }, /* 106 = nosys */
{ 0, nosys }, /* 107 = nosys */
{ 0, nosys }, /* 108 = nosys */
- { 0, nosys }, /* 109 = nosys */
- { 0, nosys }, /* 110 = nosys */
- { 0, nosys }, /* 111 = nosys */
- { 0, nosys }, /* 112 = nosys */
- { 0, nosys }, /* 113 = nosys */
- { 0, nosys }, /* 114 = nosys */
- { 0, nosys }, /* 115 = nosys */
- { 0, nosys }, /* 116 = nosys */
- { 0, nosys }, /* 117 = nosys */
- { 0, nosys }, /* 118 = nosys */
- { 0, nosys }, /* 119 = nosys */
- { 0, nosys }, /* 120 = nosys */
- { 0, nosys }, /* 121 = nosys */
+ { 2, ibcs2_getipdomainname }, /* 109 = ibcs2_getipdomainname */
+ { 3, accept }, /* 110 = accept */
+ { 3, bind }, /* 111 = bind */
+ { 3, connect }, /* 112 = connect */
+ { 3, getpeername }, /* 113 = getpeername */
+ { 3, getsockname }, /* 114 = getsockname */
+ { 5, getsockopt }, /* 115 = getsockopt */
+ { 2, listen }, /* 116 = listen */
+ { 6, recvfrom }, /* 117 = recvfrom */
+ { 6, sendto }, /* 118 = sendto */
+ { 5, setsockopt }, /* 119 = setsockopt */
+ { 2, shutdown }, /* 120 = shutdown */
+ { 3, socket }, /* 121 = socket */
{ 0, nosys }, /* 122 = nosys */
{ 0, nosys }, /* 123 = nosys */
{ 0, nosys }, /* 124 = nosys */
@@ -296,7 +309,7 @@
{ 0, nosys }, /* 161 = XENIX execseg 0x2128 */
{ 0, nosys }, /* 162 = XENIX unexecseg 0x2228 */
{ 0, nosys }, /* 163 = XENIX nosys 0x2328 */
- { 5, ibcs2_select }, /* 164 = ibcs2_select */
+ { 5, select }, /* 164 = select */
{ 0, nosys }, /* 165 = XENIX eaccess 0x2528 */
{ 0, nosys }, /* 166 = XENIX paccess 0x2628 */
{ 3, ibcs2_sigaction }, /* 167 = ibcs2_sigaction */
diff -ruP /sys/compat/ibcs2/ibcs2_time.h ./compat/ibcs2/ibcs2_time.h
--- /sys/compat/ibcs2/ibcs2_time.h Wed Aug 24 21:14:16 1994
+++ ./compat/ibcs2/ibcs2_time.h Fri Sep 9 20:25:47 1994
@@ -47,4 +47,9 @@
int tm_isdst;
};
+struct ibcs2_utimbuf {
+ time_t actime;
+ time_t modtime;
+};
+
#endif /* _IBCS2_TIME_H */
diff -ruP /sys/compat/ibcs2/syscalls.master ./compat/ibcs2/syscalls.master
--- /sys/compat/ibcs2/syscalls.master Wed Aug 24 21:14:29 1994
+++ ./compat/ibcs2/syscalls.master Fri Sep 9 20:25:57 1994
@@ -82,7 +82,7 @@
52 UNIMPL 0 nosys
#endif
#ifdef SYSVSEM
-53 STD 5 semsys
+53 STD 5 ibcs2_semsys
#else
53 UNIMPL 0 nosys
#endif
@@ -141,19 +141,19 @@
106 UNIMPL 0 nosys
107 UNIMPL 0 nosys
108 UNIMPL 0 nosys
-109 UNIMPL 0 nosys
-110 UNIMPL 0 nosys
-111 UNIMPL 0 nosys
-112 UNIMPL 0 nosys
-113 UNIMPL 0 nosys
-114 UNIMPL 0 nosys
-115 UNIMPL 0 nosys
-116 UNIMPL 0 nosys
-117 UNIMPL 0 nosys
-118 UNIMPL 0 nosys
-119 UNIMPL 0 nosys
-120 UNIMPL 0 nosys
-121 UNIMPL 0 nosys
+109 STD 2 ibcs2_getipdomainname
+110 STD 3 accept
+111 STD 3 bind
+112 STD 3 connect
+113 STD 3 getpeername
+114 STD 3 getsockname
+115 STD 5 getsockopt
+116 STD 2 listen
+117 STD 6 recvfrom
+118 STD 6 sendto
+119 STD 5 setsockopt
+120 STD 2 shutdown
+121 STD 3 socket
122 UNIMPL 0 nosys
123 UNIMPL 0 nosys
124 UNIMPL 0 nosys
@@ -196,7 +196,7 @@
161 UNIMPL 0 XENIX execseg 0x2128
162 UNIMPL 0 XENIX unexecseg 0x2228
163 UNIMPL 0 XENIX nosys 0x2328
-164 STD 5 ibcs2_select
+164 STD 5 select
165 UNIMPL 0 XENIX eaccess 0x2528
166 UNIMPL 0 XENIX paccess 0x2628
167 STD 3 ibcs2_sigaction
diff -ruP /sys/kern/kern_sig.c ./kern/kern_sig.c
--- /sys/kern/kern_sig.c Wed Jun 29 12:29:01 1994
+++ ./kern/kern_sig.c Fri Sep 9 20:27:14 1994
@@ -111,6 +111,10 @@
sa->sa_flags |= SA_RESTART;
if (p->p_flag & P_NOCLDSTOP)
sa->sa_flags |= SA_NOCLDSTOP;
+#ifdef COMPAT_IBCS2
+ if (p->p_md.ibcs_sigflags & bit)
+ sa->sa_flags |= SA_IBCS2;
+#endif
if (error = copyout((caddr_t)sa, (caddr_t)uap->osa,
sizeof (vec)))
return (error);
@@ -153,6 +157,13 @@
else
ps->ps_usertramp &= ~bit;
#endif
+#ifdef COMPAT_IBCS2
+ /* XXX - should check p_emul too ? */
+ if (sa->sa_flags & SA_IBCS2)
+ p->p_md.ibcs_sigflags |= bit;
+ else
+ p->p_md.ibcs_sigflags &= ~bit;
+#endif
if (signum == SIGCHLD) {
if (sa->sa_flags & SA_NOCLDSTOP)
p->p_flag |= P_NOCLDSTOP;
@@ -654,7 +665,16 @@
p->p_sigmask, code);
#endif
sendsig(ps->ps_sigact[signum], signum, p->p_sigmask, code);
+#ifdef COMPAT_IBCS2
+ /* XXX for ibcs */
+ if (p->p_md.ibcs_sigflags & mask) {
+ p->p_sigmask |= ps->ps_catchmask[signum];
+ ps->ps_sigact[signum] = SIG_DFL;
+ } else
+ p->p_sigmask |= ps->ps_catchmask[signum] | mask;
+#else
p->p_sigmask |= ps->ps_catchmask[signum] | mask;
+#endif
} else {
ps->ps_code = code; /* XXX for core dump/debugger */
psignal(p, signum);
@@ -1100,7 +1120,16 @@
ps->ps_flags &= ~SAS_OLDMASK;
} else
returnmask = p->p_sigmask;
+#ifdef COMPAT_IBCS2
+ if (p->p_md.ibcs_sigflags & mask) {
+ p->p_sigmask |= ps->ps_catchmask[signum];
+ ps->ps_sigact[signum] = SIG_DFL;
+ } else
+ p->p_sigmask |= ps->ps_catchmask[signum] | mask;
+#else
p->p_sigmask |= ps->ps_catchmask[signum] | mask;
+#endif
+ /* XXX for ibcs */
(void) spl0();
p->p_stats->p_ru.ru_nsignals++;
if (ps->ps_sig != signum) {
diff -ruP /sys/sys/exec.h ./sys/exec.h
--- /sys/sys/exec.h Fri Aug 19 14:37:39 1994
+++ ./sys/exec.h Fri Sep 9 20:28:21 1994
@@ -67,7 +67,7 @@
* Below the PS_STRINGS and sigtramp, we may require a gap on the stack
* (used to copyin/copyout various emulation data structures). The base
* address of this gap may need alignment, so use this to reference it:
- * (caddr_t)ALIGN(PS_STRINGS - szsigcode - STACKGAPLEN);
+ * ALIGN(((caddr_t)PS_STRINGS) - szsigcode - STACKGAPLEN);
*/
#if defined(COMPAT_SUNOS) || defined(COMPAT_ULTRIX) || defined(COMPAT_IBCS2)
#define STACKGAPLEN 400 /* plenty enough for now */
diff -ruP /sys/sys/signal.h ./sys/signal.h
--- /sys/sys/signal.h Wed Jun 29 12:33:09 1994
+++ ./sys/signal.h Fri Sep 9 20:27:59 1994
@@ -126,6 +126,9 @@
#ifdef COMPAT_SUNOS
#define SA_USERTRAMP 0x0100 /* do not bounce off kernel's sigtramp */
#endif
+#ifdef COMPAT_IBCS2
+#define SA_IBCS2 0x0200
+#endif
#endif
#define SA_NOCLDSTOP 0x0008 /* do not generate SIGCHLD on child stop */