From fd6bb20116127f6ac903d4b03abac72a49baa1ae Mon Sep 17 00:00:00 2001 From: fishsoupisgood Date: Sat, 27 Apr 2019 22:20:21 +0100 Subject: fish --- vt.c | 196 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 196 insertions(+) create mode 100644 vt.c (limited to 'vt.c') diff --git a/vt.c b/vt.c new file mode 100644 index 0000000..084a072 --- /dev/null +++ b/vt.c @@ -0,0 +1,196 @@ +/* + * Copyright 1996-2002 - Karl R. Hakimian and David Fries + * + * This file is part of datalink. + * + * Datalink is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * Datalink is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with datalink (see COPYING); if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +/* + * Linux version of Timex/Microsoft SDK for Timex datalink watches. + * SVGA needs a terminal when going to graphics mode. This will take + * care of that. + */ + +#include +#include +#include +#include +#include + +#define VTFMT "/dev/tty%d" + +int open_vt() +{ + struct vt_stat vts; + int fd; + int newvt; + char buf[1024]; + +/* Need to become root again to deal with vt's */ + seteuid(0); + + if ((fd = open("/dev/tty", O_RDWR)) == -1) + { + perror("open"); + return (-1); + } + +/* See if we are on a VT. */ + if (ioctl(fd, VT_GETSTATE, &vts) == 0) + { + close(fd); + return (0); + } + +/* We are not on a VT, switch to one. */ + close(fd); + + if ((fd = open("/dev/tty0", O_RDWR)) == -1) + { + perror("open"); + return (-1); + } + +/* Get info on current vt. */ + if (ioctl(fd, VT_GETSTATE, &vts) == -1) + { + perror("VT_GETSTATE"); + return (-1); + } + +/* Open a new vt. */ + if (ioctl(fd, VT_OPENQRY, &newvt) == -1) + { + perror("VT_OPENQRY"); + return (-1); + } + + if (newvt == -1) + { + fprintf(stderr, "No free vts to open\n"); + return (-1); + } + +/* Make the new vt, the active vt. */ + if (ioctl(fd, VT_ACTIVATE, newvt) == -1) + { + perror("VT_ACTIVATE"); + return (-1); + } + + if (ioctl(fd, VT_WAITACTIVE, newvt) == -1) + { + perror("VT_WAITACTIVE"); + return (-1); + } + + close(fd); + close(2); + close(1); + close(0); +/* + Detach from controlling terminal here so that we can get a new + controlling terminal. +*/ + setsid(); + sprintf(buf, VTFMT, newvt); + (void) open(buf, O_RDWR); + (void) open(buf, O_RDWR); + (void) open(buf, O_RDWR); + +/* No longer need root privs - drop them*/ + seteuid(getuid()); + + return (vts.v_active); +} + +void close_vt(int oldvt) +{ + int fd; + struct vt_stat vts; + struct vt_mode VT; + int vt; + + if (!oldvt) + return; + +/* Need to become root again to deal with vt's */ + seteuid(0); + +/* SVGA lib sets the tty change mode to require a call back. + * We aren't in graphics mode, so set it back to auto. + */ + if( ioctl(0, VT_GETMODE, &VT) == -1) + { + perror("VT_GETMODE"); + return; + } + + VT.mode = VT_AUTO; + if( ioctl(0, VT_SETMODE, &VT)== -1) + { + perror("VT_SETMODE"); + return; + } + +/* Get info on current vt. */ + if (ioctl(0, VT_GETSTATE, &vts) == -1) + { + perror("VT_GETSTATE"); + return; + } + + vt = vts.v_active; + +/* Switch back to previous vt. */ + + if (ioctl(0, VT_ACTIVATE, oldvt) == -1) + { + perror("VT_ACTIVATE"); + return; + } + + if (ioctl(0, VT_WAITACTIVE, oldvt) == -1) + { + perror("VT_WAITACTIVE"); + return; + } + + close(0); + close(1); + close(2); + setsid(); + +/* Open current vt. */ + if ((fd = open("/dev/tty0", O_RDWR)) == -1) + { + perror("open"); + return; + } + +/* Free up our old vt. */ + if (ioctl(fd, VT_DISALLOCATE, vt) == -1) + { + perror("VT_DISALLOCATE"); + return; + } + + close(fd); + +/* No longer need root privs - drop them*/ + seteuid(getuid()); +} -- cgit v1.2.3