51e6ba0f00
I really don't want any pieces of code to include ioctl_compat.h, so let the ibcs2 and svr4 compat leave sgtty alone. If they want to support sgtty, they should emulate it on top of termios, not sgtty. The code has been marked with BURN_BRIDGES for a long time. ibcs2 and svr4 are not really popular pieces of code anyway.
687 lines
17 KiB
C
687 lines
17 KiB
C
/* $NetBSD: ibcs2_ioctl.c,v 1.6 1995/03/14 15:12:28 scottb Exp $ */
|
|
|
|
/*-
|
|
* Copyright (c) 1994, 1995 Scott Bartram
|
|
* All rights reserved.
|
|
*
|
|
* based on compat/sunos/sun_ioctl.c
|
|
*
|
|
* Redistribution and use in source and binary forms, with or without
|
|
* modification, are permitted provided that the following conditions
|
|
* are met:
|
|
* 1. Redistributions of source code must retain the above copyright
|
|
* notice, this list of conditions and the following disclaimer.
|
|
* 2. The name of the author may not be used to endorse or promote products
|
|
* derived from this software without specific prior written permission
|
|
*
|
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
|
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
|
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
|
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
|
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
|
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
*/
|
|
|
|
#include <sys/cdefs.h>
|
|
__FBSDID("$FreeBSD$");
|
|
|
|
#include <sys/param.h>
|
|
#include <sys/systm.h>
|
|
#include <sys/consio.h>
|
|
#include <sys/fcntl.h>
|
|
#include <sys/file.h>
|
|
#include <sys/filedesc.h>
|
|
#include <sys/filio.h>
|
|
#include <sys/kbio.h>
|
|
#include <sys/lock.h>
|
|
#include <sys/mutex.h>
|
|
#include <sys/sysproto.h>
|
|
#include <sys/tty.h>
|
|
|
|
#include <i386/ibcs2/ibcs2_signal.h>
|
|
#include <i386/ibcs2/ibcs2_socksys.h>
|
|
#include <i386/ibcs2/ibcs2_stropts.h>
|
|
#include <i386/ibcs2/ibcs2_proto.h>
|
|
#include <i386/ibcs2/ibcs2_termios.h>
|
|
#include <i386/ibcs2/ibcs2_util.h>
|
|
#include <i386/ibcs2/ibcs2_ioctl.h>
|
|
|
|
static void stios2btios(struct ibcs2_termios *, struct termios *);
|
|
static void btios2stios(struct termios *, struct ibcs2_termios *);
|
|
static void stios2stio(struct ibcs2_termios *, struct ibcs2_termio *);
|
|
static void stio2stios(struct ibcs2_termio *, struct ibcs2_termios *);
|
|
|
|
/*
|
|
* iBCS2 ioctl calls.
|
|
*/
|
|
|
|
struct speedtab {
|
|
int sp_speed; /* Speed. */
|
|
int sp_code; /* Code. */
|
|
};
|
|
|
|
static struct speedtab sptab[] = {
|
|
{ 0, 0 },
|
|
{ 50, 1 },
|
|
{ 75, 2 },
|
|
{ 110, 3 },
|
|
{ 134, 4 },
|
|
{ 135, 4 },
|
|
{ 150, 5 },
|
|
{ 200, 6 },
|
|
{ 300, 7 },
|
|
{ 600, 8 },
|
|
{ 1200, 9 },
|
|
{ 1800, 10 },
|
|
{ 2400, 11 },
|
|
{ 4800, 12 },
|
|
{ 9600, 13 },
|
|
{ 19200, 14 },
|
|
{ 38400, 15 },
|
|
{ -1, -1 }
|
|
};
|
|
|
|
static u_long s2btab[] = {
|
|
0,
|
|
50,
|
|
75,
|
|
110,
|
|
134,
|
|
150,
|
|
200,
|
|
300,
|
|
600,
|
|
1200,
|
|
1800,
|
|
2400,
|
|
4800,
|
|
9600,
|
|
19200,
|
|
38400,
|
|
};
|
|
|
|
static int
|
|
ttspeedtab(int speed, struct speedtab *table)
|
|
{
|
|
|
|
for ( ; table->sp_speed != -1; table++)
|
|
if (table->sp_speed == speed)
|
|
return (table->sp_code);
|
|
return (-1);
|
|
}
|
|
|
|
static void
|
|
stios2btios(st, bt)
|
|
struct ibcs2_termios *st;
|
|
struct termios *bt;
|
|
{
|
|
register u_long l, r;
|
|
|
|
l = st->c_iflag; r = 0;
|
|
if (l & IBCS2_IGNBRK) r |= IGNBRK;
|
|
if (l & IBCS2_BRKINT) r |= BRKINT;
|
|
if (l & IBCS2_IGNPAR) r |= IGNPAR;
|
|
if (l & IBCS2_PARMRK) r |= PARMRK;
|
|
if (l & IBCS2_INPCK) r |= INPCK;
|
|
if (l & IBCS2_ISTRIP) r |= ISTRIP;
|
|
if (l & IBCS2_INLCR) r |= INLCR;
|
|
if (l & IBCS2_IGNCR) r |= IGNCR;
|
|
if (l & IBCS2_ICRNL) r |= ICRNL;
|
|
if (l & IBCS2_IXON) r |= IXON;
|
|
if (l & IBCS2_IXANY) r |= IXANY;
|
|
if (l & IBCS2_IXOFF) r |= IXOFF;
|
|
if (l & IBCS2_IMAXBEL) r |= IMAXBEL;
|
|
bt->c_iflag = r;
|
|
|
|
l = st->c_oflag; r = 0;
|
|
if (l & IBCS2_OPOST) r |= OPOST;
|
|
if (l & IBCS2_ONLCR) r |= ONLCR;
|
|
if (l & IBCS2_TAB3) r |= TAB3;
|
|
bt->c_oflag = r;
|
|
|
|
l = st->c_cflag; r = 0;
|
|
switch (l & IBCS2_CSIZE) {
|
|
case IBCS2_CS5: r |= CS5; break;
|
|
case IBCS2_CS6: r |= CS6; break;
|
|
case IBCS2_CS7: r |= CS7; break;
|
|
case IBCS2_CS8: r |= CS8; break;
|
|
}
|
|
if (l & IBCS2_CSTOPB) r |= CSTOPB;
|
|
if (l & IBCS2_CREAD) r |= CREAD;
|
|
if (l & IBCS2_PARENB) r |= PARENB;
|
|
if (l & IBCS2_PARODD) r |= PARODD;
|
|
if (l & IBCS2_HUPCL) r |= HUPCL;
|
|
if (l & IBCS2_CLOCAL) r |= CLOCAL;
|
|
bt->c_cflag = r;
|
|
|
|
bt->c_ispeed = bt->c_ospeed = s2btab[l & 0x0000000f];
|
|
|
|
l = st->c_lflag; r = 0;
|
|
if (l & IBCS2_ISIG) r |= ISIG;
|
|
if (l & IBCS2_ICANON) r |= ICANON;
|
|
if (l & IBCS2_ECHO) r |= ECHO;
|
|
if (l & IBCS2_ECHOE) r |= ECHOE;
|
|
if (l & IBCS2_ECHOK) r |= ECHOK;
|
|
if (l & IBCS2_ECHONL) r |= ECHONL;
|
|
if (l & IBCS2_NOFLSH) r |= NOFLSH;
|
|
if (l & IBCS2_TOSTOP) r |= TOSTOP;
|
|
bt->c_lflag = r;
|
|
|
|
bt->c_cc[VINTR] =
|
|
st->c_cc[IBCS2_VINTR] ? st->c_cc[IBCS2_VINTR] : _POSIX_VDISABLE;
|
|
bt->c_cc[VQUIT] =
|
|
st->c_cc[IBCS2_VQUIT] ? st->c_cc[IBCS2_VQUIT] : _POSIX_VDISABLE;
|
|
bt->c_cc[VERASE] =
|
|
st->c_cc[IBCS2_VERASE] ? st->c_cc[IBCS2_VERASE] : _POSIX_VDISABLE;
|
|
bt->c_cc[VKILL] =
|
|
st->c_cc[IBCS2_VKILL] ? st->c_cc[IBCS2_VKILL] : _POSIX_VDISABLE;
|
|
if (bt->c_lflag & ICANON) {
|
|
bt->c_cc[VEOF] =
|
|
st->c_cc[IBCS2_VEOF] ? st->c_cc[IBCS2_VEOF] : _POSIX_VDISABLE;
|
|
bt->c_cc[VEOL] =
|
|
st->c_cc[IBCS2_VEOL] ? st->c_cc[IBCS2_VEOL] : _POSIX_VDISABLE;
|
|
} else {
|
|
bt->c_cc[VMIN] = st->c_cc[IBCS2_VMIN];
|
|
bt->c_cc[VTIME] = st->c_cc[IBCS2_VTIME];
|
|
}
|
|
bt->c_cc[VEOL2] =
|
|
st->c_cc[IBCS2_VEOL2] ? st->c_cc[IBCS2_VEOL2] : _POSIX_VDISABLE;
|
|
#if 0
|
|
bt->c_cc[VSWTCH] =
|
|
st->c_cc[IBCS2_VSWTCH] ? st->c_cc[IBCS2_VSWTCH] : _POSIX_VDISABLE;
|
|
#endif
|
|
bt->c_cc[VSTART] =
|
|
st->c_cc[IBCS2_VSTART] ? st->c_cc[IBCS2_VSTART] : _POSIX_VDISABLE;
|
|
bt->c_cc[VSTOP] =
|
|
st->c_cc[IBCS2_VSTOP] ? st->c_cc[IBCS2_VSTOP] : _POSIX_VDISABLE;
|
|
bt->c_cc[VSUSP] =
|
|
st->c_cc[IBCS2_VSUSP] ? st->c_cc[IBCS2_VSUSP] : _POSIX_VDISABLE;
|
|
bt->c_cc[VDSUSP] = _POSIX_VDISABLE;
|
|
bt->c_cc[VREPRINT] = _POSIX_VDISABLE;
|
|
bt->c_cc[VDISCARD] = _POSIX_VDISABLE;
|
|
bt->c_cc[VWERASE] = _POSIX_VDISABLE;
|
|
bt->c_cc[VLNEXT] = _POSIX_VDISABLE;
|
|
bt->c_cc[VSTATUS] = _POSIX_VDISABLE;
|
|
}
|
|
|
|
static void
|
|
btios2stios(bt, st)
|
|
struct termios *bt;
|
|
struct ibcs2_termios *st;
|
|
{
|
|
register u_long l, r;
|
|
|
|
l = bt->c_iflag; r = 0;
|
|
if (l & IGNBRK) r |= IBCS2_IGNBRK;
|
|
if (l & BRKINT) r |= IBCS2_BRKINT;
|
|
if (l & IGNPAR) r |= IBCS2_IGNPAR;
|
|
if (l & PARMRK) r |= IBCS2_PARMRK;
|
|
if (l & INPCK) r |= IBCS2_INPCK;
|
|
if (l & ISTRIP) r |= IBCS2_ISTRIP;
|
|
if (l & INLCR) r |= IBCS2_INLCR;
|
|
if (l & IGNCR) r |= IBCS2_IGNCR;
|
|
if (l & ICRNL) r |= IBCS2_ICRNL;
|
|
if (l & IXON) r |= IBCS2_IXON;
|
|
if (l & IXANY) r |= IBCS2_IXANY;
|
|
if (l & IXOFF) r |= IBCS2_IXOFF;
|
|
if (l & IMAXBEL) r |= IBCS2_IMAXBEL;
|
|
st->c_iflag = r;
|
|
|
|
l = bt->c_oflag; r = 0;
|
|
if (l & OPOST) r |= IBCS2_OPOST;
|
|
if (l & ONLCR) r |= IBCS2_ONLCR;
|
|
if (l & TAB3) r |= IBCS2_TAB3;
|
|
st->c_oflag = r;
|
|
|
|
l = bt->c_cflag; r = 0;
|
|
switch (l & CSIZE) {
|
|
case CS5: r |= IBCS2_CS5; break;
|
|
case CS6: r |= IBCS2_CS6; break;
|
|
case CS7: r |= IBCS2_CS7; break;
|
|
case CS8: r |= IBCS2_CS8; break;
|
|
}
|
|
if (l & CSTOPB) r |= IBCS2_CSTOPB;
|
|
if (l & CREAD) r |= IBCS2_CREAD;
|
|
if (l & PARENB) r |= IBCS2_PARENB;
|
|
if (l & PARODD) r |= IBCS2_PARODD;
|
|
if (l & HUPCL) r |= IBCS2_HUPCL;
|
|
if (l & CLOCAL) r |= IBCS2_CLOCAL;
|
|
st->c_cflag = r;
|
|
|
|
l = bt->c_lflag; r = 0;
|
|
if (l & ISIG) r |= IBCS2_ISIG;
|
|
if (l & ICANON) r |= IBCS2_ICANON;
|
|
if (l & ECHO) r |= IBCS2_ECHO;
|
|
if (l & ECHOE) r |= IBCS2_ECHOE;
|
|
if (l & ECHOK) r |= IBCS2_ECHOK;
|
|
if (l & ECHONL) r |= IBCS2_ECHONL;
|
|
if (l & NOFLSH) r |= IBCS2_NOFLSH;
|
|
if (l & TOSTOP) r |= IBCS2_TOSTOP;
|
|
st->c_lflag = r;
|
|
|
|
l = ttspeedtab(bt->c_ospeed, sptab);
|
|
if ((int)l >= 0)
|
|
st->c_cflag |= l;
|
|
|
|
st->c_cc[IBCS2_VINTR] =
|
|
bt->c_cc[VINTR] != _POSIX_VDISABLE ? bt->c_cc[VINTR] : 0;
|
|
st->c_cc[IBCS2_VQUIT] =
|
|
bt->c_cc[VQUIT] != _POSIX_VDISABLE ? bt->c_cc[VQUIT] : 0;
|
|
st->c_cc[IBCS2_VERASE] =
|
|
bt->c_cc[VERASE] != _POSIX_VDISABLE ? bt->c_cc[VERASE] : 0;
|
|
st->c_cc[IBCS2_VKILL] =
|
|
bt->c_cc[VKILL] != _POSIX_VDISABLE ? bt->c_cc[VKILL] : 0;
|
|
if (bt->c_lflag & ICANON) {
|
|
st->c_cc[IBCS2_VEOF] =
|
|
bt->c_cc[VEOF] != _POSIX_VDISABLE ? bt->c_cc[VEOF] : 0;
|
|
st->c_cc[IBCS2_VEOL] =
|
|
bt->c_cc[VEOL] != _POSIX_VDISABLE ? bt->c_cc[VEOL] : 0;
|
|
} else {
|
|
st->c_cc[IBCS2_VMIN] = bt->c_cc[VMIN];
|
|
st->c_cc[IBCS2_VTIME] = bt->c_cc[VTIME];
|
|
}
|
|
st->c_cc[IBCS2_VEOL2] =
|
|
bt->c_cc[VEOL2] != _POSIX_VDISABLE ? bt->c_cc[VEOL2] : 0;
|
|
st->c_cc[IBCS2_VSWTCH] =
|
|
0;
|
|
st->c_cc[IBCS2_VSUSP] =
|
|
bt->c_cc[VSUSP] != _POSIX_VDISABLE ? bt->c_cc[VSUSP] : 0;
|
|
st->c_cc[IBCS2_VSTART] =
|
|
bt->c_cc[VSTART] != _POSIX_VDISABLE ? bt->c_cc[VSTART] : 0;
|
|
st->c_cc[IBCS2_VSTOP] =
|
|
bt->c_cc[VSTOP] != _POSIX_VDISABLE ? bt->c_cc[VSTOP] : 0;
|
|
|
|
st->c_line = 0;
|
|
}
|
|
|
|
static void
|
|
stios2stio(ts, t)
|
|
struct ibcs2_termios *ts;
|
|
struct ibcs2_termio *t;
|
|
{
|
|
t->c_iflag = ts->c_iflag;
|
|
t->c_oflag = ts->c_oflag;
|
|
t->c_cflag = ts->c_cflag;
|
|
t->c_lflag = ts->c_lflag;
|
|
t->c_line = ts->c_line;
|
|
bcopy(ts->c_cc, t->c_cc, IBCS2_NCC);
|
|
}
|
|
|
|
static void
|
|
stio2stios(t, ts)
|
|
struct ibcs2_termio *t;
|
|
struct ibcs2_termios *ts;
|
|
{
|
|
ts->c_iflag = t->c_iflag;
|
|
ts->c_oflag = t->c_oflag;
|
|
ts->c_cflag = t->c_cflag;
|
|
ts->c_lflag = t->c_lflag;
|
|
ts->c_line = t->c_line;
|
|
bcopy(t->c_cc, ts->c_cc, IBCS2_NCC);
|
|
}
|
|
|
|
int
|
|
ibcs2_ioctl(td, uap)
|
|
struct thread *td;
|
|
struct ibcs2_ioctl_args *uap;
|
|
{
|
|
struct proc *p = td->td_proc;
|
|
struct file *fp;
|
|
int error;
|
|
|
|
if ((error = fget(td, uap->fd, &fp)) != 0) {
|
|
DPRINTF(("ibcs2_ioctl(%d): bad fd %d ", p->p_pid,
|
|
uap->fd));
|
|
return EBADF;
|
|
}
|
|
|
|
if ((fp->f_flag & (FREAD|FWRITE)) == 0) {
|
|
fdrop(fp, td);
|
|
DPRINTF(("ibcs2_ioctl(%d): bad fp flag ", p->p_pid));
|
|
return EBADF;
|
|
}
|
|
|
|
switch (uap->cmd) {
|
|
case IBCS2_TCGETA:
|
|
case IBCS2_XCGETA:
|
|
case IBCS2_OXCGETA:
|
|
{
|
|
struct termios bts;
|
|
struct ibcs2_termios sts;
|
|
struct ibcs2_termio st;
|
|
|
|
if ((error = fo_ioctl(fp, TIOCGETA, (caddr_t)&bts,
|
|
td->td_ucred, td)) != 0)
|
|
break;
|
|
|
|
btios2stios (&bts, &sts);
|
|
if (uap->cmd == IBCS2_TCGETA) {
|
|
stios2stio (&sts, &st);
|
|
error = copyout((caddr_t)&st, uap->data,
|
|
sizeof (st));
|
|
#ifdef DEBUG_IBCS2
|
|
if (error)
|
|
DPRINTF(("ibcs2_ioctl(%d): copyout failed ",
|
|
p->p_pid));
|
|
#endif
|
|
break;
|
|
} else {
|
|
error = copyout((caddr_t)&sts, uap->data,
|
|
sizeof (sts));
|
|
break;
|
|
}
|
|
/*NOTREACHED*/
|
|
}
|
|
|
|
case IBCS2_TCSETA:
|
|
case IBCS2_TCSETAW:
|
|
case IBCS2_TCSETAF:
|
|
{
|
|
struct termios bts;
|
|
struct ibcs2_termios sts;
|
|
struct ibcs2_termio st;
|
|
|
|
if ((error = copyin(uap->data, (caddr_t)&st,
|
|
sizeof(st))) != 0) {
|
|
DPRINTF(("ibcs2_ioctl(%d): TCSET copyin failed ",
|
|
p->p_pid));
|
|
break;
|
|
}
|
|
|
|
/* get full BSD termios so we don't lose information */
|
|
if ((error = fo_ioctl(fp, TIOCGETA, (caddr_t)&bts,
|
|
td->td_ucred, td)) != 0) {
|
|
DPRINTF(("ibcs2_ioctl(%d): TCSET ctl failed fd %d ",
|
|
p->p_pid, uap->fd));
|
|
break;
|
|
}
|
|
|
|
/*
|
|
* convert to iBCS2 termios, copy in information from
|
|
* termio, and convert back, then set new values.
|
|
*/
|
|
btios2stios(&bts, &sts);
|
|
stio2stios(&st, &sts);
|
|
stios2btios(&sts, &bts);
|
|
|
|
error = fo_ioctl(fp, uap->cmd - IBCS2_TCSETA + TIOCSETA,
|
|
(caddr_t)&bts, td->td_ucred, td);
|
|
break;
|
|
}
|
|
|
|
case IBCS2_XCSETA:
|
|
case IBCS2_XCSETAW:
|
|
case IBCS2_XCSETAF:
|
|
{
|
|
struct termios bts;
|
|
struct ibcs2_termios sts;
|
|
|
|
if ((error = copyin(uap->data, (caddr_t)&sts,
|
|
sizeof (sts))) != 0)
|
|
break;
|
|
stios2btios (&sts, &bts);
|
|
error = fo_ioctl(fp, uap->cmd - IBCS2_XCSETA + TIOCSETA,
|
|
(caddr_t)&bts, td->td_ucred, td);
|
|
break;
|
|
}
|
|
|
|
case IBCS2_OXCSETA:
|
|
case IBCS2_OXCSETAW:
|
|
case IBCS2_OXCSETAF:
|
|
{
|
|
struct termios bts;
|
|
struct ibcs2_termios sts;
|
|
|
|
if ((error = copyin(uap->data, (caddr_t)&sts,
|
|
sizeof (sts))) != 0)
|
|
break;
|
|
stios2btios (&sts, &bts);
|
|
error = fo_ioctl(fp, uap->cmd - IBCS2_OXCSETA + TIOCSETA,
|
|
(caddr_t)&bts, td->td_ucred, td);
|
|
break;
|
|
}
|
|
|
|
case IBCS2_TCSBRK:
|
|
DPRINTF(("ibcs2_ioctl(%d): TCSBRK ", p->p_pid));
|
|
error = ENOSYS;
|
|
break;
|
|
|
|
case IBCS2_TCXONC:
|
|
{
|
|
switch ((int)uap->data) {
|
|
case 0:
|
|
case 1:
|
|
DPRINTF(("ibcs2_ioctl(%d): TCXONC ", p->p_pid));
|
|
error = ENOSYS;
|
|
break;
|
|
case 2:
|
|
error = fo_ioctl(fp, TIOCSTOP, (caddr_t)0,
|
|
td->td_ucred, td);
|
|
break;
|
|
case 3:
|
|
error = fo_ioctl(fp, TIOCSTART, (caddr_t)1,
|
|
td->td_ucred, td);
|
|
break;
|
|
default:
|
|
error = EINVAL;
|
|
break;
|
|
}
|
|
break;
|
|
}
|
|
|
|
case IBCS2_TCFLSH:
|
|
{
|
|
int arg;
|
|
|
|
switch ((int)uap->data) {
|
|
case 0:
|
|
arg = FREAD;
|
|
break;
|
|
case 1:
|
|
arg = FWRITE;
|
|
break;
|
|
case 2:
|
|
arg = FREAD | FWRITE;
|
|
break;
|
|
default:
|
|
fdrop(fp, td);
|
|
return EINVAL;
|
|
}
|
|
error = fo_ioctl(fp, TIOCFLUSH, (caddr_t)&arg, td->td_ucred,
|
|
td);
|
|
break;
|
|
}
|
|
|
|
case IBCS2_TIOCGWINSZ:
|
|
uap->cmd = TIOCGWINSZ;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_TIOCSWINSZ:
|
|
uap->cmd = TIOCSWINSZ;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_TIOCGPGRP:
|
|
{
|
|
pid_t pg_id;
|
|
|
|
PROC_LOCK(p);
|
|
pg_id = p->p_pgrp->pg_id;
|
|
PROC_UNLOCK(p);
|
|
error = copyout((caddr_t)&pg_id, uap->data,
|
|
sizeof(pg_id));
|
|
break;
|
|
}
|
|
|
|
case IBCS2_TIOCSPGRP: /* XXX - is uap->data a pointer to pgid? */
|
|
{
|
|
struct setpgid_args sa;
|
|
|
|
sa.pid = 0;
|
|
sa.pgid = (int)uap->data;
|
|
error = setpgid(td, &sa);
|
|
break;
|
|
}
|
|
|
|
case IBCS2_TCGETSC: /* SCO console - get scancode flags */
|
|
error = EINTR; /* ENOSYS; */
|
|
break;
|
|
|
|
case IBCS2_TCSETSC: /* SCO console - set scancode flags */
|
|
error = 0; /* ENOSYS; */
|
|
break;
|
|
|
|
case IBCS2_JWINSIZE: /* Unix to Jerq I/O control */
|
|
{
|
|
struct ibcs2_jwinsize {
|
|
char bytex, bytey;
|
|
short bitx, bity;
|
|
} ibcs2_jwinsize;
|
|
|
|
PROC_LOCK(p);
|
|
SESS_LOCK(p->p_session);
|
|
ibcs2_jwinsize.bytex = 80;
|
|
/* p->p_session->s_ttyp->t_winsize.ws_col; XXX */
|
|
ibcs2_jwinsize.bytey = 25;
|
|
/* p->p_session->s_ttyp->t_winsize.ws_row; XXX */
|
|
ibcs2_jwinsize.bitx =
|
|
p->p_session->s_ttyp->t_winsize.ws_xpixel;
|
|
ibcs2_jwinsize.bity =
|
|
p->p_session->s_ttyp->t_winsize.ws_ypixel;
|
|
SESS_UNLOCK(p->p_session);
|
|
PROC_UNLOCK(p);
|
|
error = copyout((caddr_t)&ibcs2_jwinsize, uap->data,
|
|
sizeof(ibcs2_jwinsize));
|
|
break;
|
|
}
|
|
|
|
/* keyboard and display ioctl's -- type 'K' */
|
|
case IBCS2_KDGKBMODE: /* get keyboard translation mode */
|
|
uap->cmd = KDGKBMODE;
|
|
/* printf("ioctl KDGKBMODE = %x\n", uap->cmd);*/
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDSKBMODE: /* set keyboard translation mode */
|
|
uap->cmd = KDSKBMODE;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDMKTONE: /* sound tone */
|
|
uap->cmd = KDMKTONE;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDGETMODE: /* get text/graphics mode */
|
|
uap->cmd = KDGETMODE;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDSETMODE: /* set text/graphics mode */
|
|
uap->cmd = KDSETMODE;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDSBORDER: /* set ega color border */
|
|
uap->cmd = KDSBORDER;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDGKBSTATE:
|
|
uap->cmd = KDGKBSTATE;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDSETRAD:
|
|
uap->cmd = KDSETRAD;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDENABIO: /* enable direct I/O to ports */
|
|
uap->cmd = KDENABIO;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDDISABIO: /* disable direct I/O to ports */
|
|
uap->cmd = KDDISABIO;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KIOCSOUND: /* start sound generation */
|
|
uap->cmd = KIOCSOUND;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDGKBTYPE: /* get keyboard type */
|
|
uap->cmd = KDGKBTYPE;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDGETLED: /* get keyboard LED status */
|
|
uap->cmd = KDGETLED;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_KDSETLED: /* set keyboard LED status */
|
|
uap->cmd = KDSETLED;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
/* Xenix keyboard and display ioctl's from sys/kd.h -- type 'k' */
|
|
case IBCS2_GETFKEY: /* Get function key */
|
|
uap->cmd = GETFKEY;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_SETFKEY: /* Set function key */
|
|
uap->cmd = SETFKEY;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_GIO_SCRNMAP: /* Get screen output map table */
|
|
uap->cmd = GIO_SCRNMAP;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_PIO_SCRNMAP: /* Set screen output map table */
|
|
uap->cmd = PIO_SCRNMAP;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_GIO_KEYMAP: /* Get keyboard map table */
|
|
uap->cmd = GIO_KEYMAP;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_PIO_KEYMAP: /* Set keyboard map table */
|
|
uap->cmd = PIO_KEYMAP;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
/* socksys */
|
|
case IBCS2_SIOCSOCKSYS:
|
|
error = ibcs2_socksys(td, (struct ibcs2_socksys_args *)uap);
|
|
break;
|
|
|
|
case IBCS2_FIONREAD:
|
|
case IBCS2_I_NREAD: /* STREAMS */
|
|
uap->cmd = FIONREAD;
|
|
error = ioctl(td, (struct ioctl_args *)uap);
|
|
break;
|
|
|
|
default:
|
|
DPRINTF(("ibcs2_ioctl(%d): unknown cmd 0x%lx ",
|
|
td->proc->p_pid, uap->cmd));
|
|
error = ENOSYS;
|
|
break;
|
|
}
|
|
|
|
fdrop(fp, td);
|
|
return error;
|
|
}
|