slattach.c

来自「Linux下网络相关工具源代码。」· C语言 代码 · 共 724 行 · 第 1/2 页

C
724
字号
/* * slattach	A program for handling dialup IP connecions. *		This program forces a TTY line to go into a special *		terminal line discipline, so that it can be used for *		network traffic instead of the regular terminal I/O. * * Usage:	slattach [-ehlmnqv] [ -k keepalive ] [ -o outfill ] * 			[-c cmd] [-s speed] [-p protocol] tty | - * * Version:	@(#)slattach.c	1.1.30  03/01/95 * * Author:      Fred N. van Kempen, <waltje@uWalt.NL.Mugnet.ORG> *		Copyright 1988-1993 MicroWalt Corporation * * Modified: *		Alan Cox, <A.Cox@swansea.ac.uk> , July 16 1994 *		Miquel van Smoorenburg, <miquels@drinkel.ow.org>, October 1994 *		George Shearer, <gshearer@one.net>, January 3, 1995 *		Yossi Gottlieb, <yogo@math.tau.ac.il>, February 11, 1995 *		Peter Tobias, <tobias@et-inf.fho-emden.de>, July 30 1995 * *		This program 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. */#include <sys/types.h>#include <sys/socket.h>#include <sys/ioctl.h>#include <sys/stat.h>#include <stdio.h>#include <ctype.h>#include <errno.h>#include <fcntl.h>#include <limits.h>#include <pwd.h>#include <signal.h>#include <stdlib.h>          #include <string.h>#include <unistd.h>#include <getopt.h>#include <linux/if_slip.h>#if defined(__GLIBC__)#if __GLIBC__ == 2 && __GLIBC_MINOR__ == 0# include <termbits.h>#else# include <termios.h>#endif#endif#include "pathnames.h"#include "net-support.h"#include "version.h"#include "config.h"#include "intl.h"#ifndef _PATH_LOCKD#define _PATH_LOCKD		"/var/lock"		/* lock files   */#endif#ifndef _UID_UUCP#define _UID_UUCP		"uucp"			/* owns locks   */#endif#define DEF_PROTO	"cslip"char *Release = RELEASE,     *Version = "@(#) slattach 1.1.91 (12-Feb-95)",     *Signature = "Fred N. van Kempen et al.";struct {  char	*speed;  int	code;} tty_speeds[] = {			/* table of usable baud rates	*/  { "50",	B50	}, { "75",	B75  	},	  { "110",	B110	}, { "300",	B300	},  { "600",	B600	}, { "1200",	B1200	},  { "2400",	B2400	}, { "4800",	B4800	},  { "9600",	B9600	},#ifdef B14400  { "14400",	B14400	},#endif#ifdef B19200  { "19200",	B19200	},#endif#ifdef B38400  { "38400",	B38400	},#endif#ifdef B57600  { "57600",	B57600	},#endif#ifdef B115200  { "115200",	B115200	},#endif  { NULL,	0	}};struct termios	tty_saved,		/* saved TTY device state	*/		tty_current;		/* current TTY device state	*/int		tty_sdisc,		/* saved TTY line discipline	*/		tty_ldisc,		/* current TTY line discipline	*/		tty_fd = -1;		/* TTY file descriptor		*/int		opt_c = 0;		/* "command" to run at exit	*/int		opt_e = 0;		/* "activate only" flag		*/int		opt_h = 0;		/* "hangup" on carrier loss	*/#ifdef SIOCSKEEPALIVEint		opt_k = 0;		/* "keepalive" value		*/#endifint		opt_l = 0;		/* "lock it" flag		*/int		opt_L = 0;		/* clocal flag			*/int		opt_m = 0;		/* "set RAW mode" flag		*/int		opt_n = 0;		/* "set No Mesg" flag		*/#ifdef SIOCSOUTFILLint		opt_o = 0;		/* "outfill" value		*/#endifint		opt_q = 0;		/* "quiet" flag			*/int		opt_d = 0;		/* debug flag			*/int		opt_v = 0;		/* Verbose flag			*//* Disable any messages to the input channel of this process. */static inttty_nomesg(int fd){  if (opt_n == 0) return(0);  return(fchmod(fd, 0600));}/* Check for an existing lock file on our device */static inttty_already_locked(char *nam){  int  i = 0, pid = 0;  FILE *fd = (FILE *)0;  /* Does the lock file on our device exist? */  if ((fd = fopen(nam, "r")) == (FILE *)0)    return(0); /* No, return perm to continue */  /* Yes, the lock is there.  Now let's make sure */  /* at least there's no active process that owns */  /* that lock.                                   */  i = fscanf(fd, "%d", &pid);  (void) fclose(fd);   if (i != 1) /* Lock file format's wrong! Kill't */    return(0);  /* We got the pid, check if the process's alive */  if (kill(pid, 0) == 0)      /* it found process */      return(1);          /* Yup, it's running... */  /* Dead, we can proceed locking this device...  */  return(0);}/* Lock or unlock a terminal line. */static inttty_lock(char *path, int mode){  static char saved_path[PATH_MAX];  static int saved_lock = 0;  struct passwd *pw;  int fd;  char apid[16];  /* We do not lock standard input. */  if ((opt_l == 0) || ((path == NULL) && (saved_lock == 0))) return(0);  if (mode == 1) {	/* lock */	sprintf(saved_path, "%s/LCK..%s", _PATH_LOCKD, path);	if (tty_already_locked(saved_path)) {		fprintf(stderr, _("slattach: /dev/%s already locked!\n"), path);		return(-1);	}	if ((fd = creat(saved_path, 0644)) < 0) {		if (errno != EEXIST)			if (opt_q == 0) fprintf(stderr,				_("slattach: tty_lock: (%s): %s\n"),					saved_path, strerror(errno));		return(-1);	}	sprintf(apid, "%10d\n", getpid());	if (write(fd, apid, strlen(apid)) != strlen(apid)) {		fprintf(stderr, _("slattach: cannot write PID file\n"));		close(fd);		unlink(saved_path);		return(-1);	}	(void) close(fd);	/* Make sure UUCP owns the lockfile.  Required by some packages. */	if ((pw = getpwnam(_UID_UUCP)) == NULL) {		if (opt_q == 0) fprintf(stderr, _("slattach: tty_lock: UUCP user %s unknown!\n"),					_UID_UUCP);		return(0);	/* keep the lock anyway */	}	(void) chown(saved_path, pw->pw_uid, pw->pw_gid);	saved_lock = 1;  } else {	/* unlock */	if (saved_lock != 1) return(0);	if (unlink(saved_path) < 0) {		if (opt_q == 0) fprintf(stderr,			"slattach: tty_unlock: (%s): %s\n", saved_path,							strerror(errno));		return(-1);	}	saved_lock = 0;  }  return(0);}/* Find a serial speed code in the table. */static inttty_find_speed(char *speed){  int i;  i = 0;  while (tty_speeds[i].speed != NULL) {	if (!strcmp(tty_speeds[i].speed, speed)) return(tty_speeds[i].code);	i++;  }  return(-EINVAL);}/* Set the number of stop bits. */static inttty_set_stopbits(struct termios *tty, char *stopbits){  if (opt_d) printf("slattach: tty_set_stopbits: %c\n", *stopbits);  switch(*stopbits) {	case '1':		tty->c_cflag &= ~CSTOPB;		break;	case '2':		tty->c_cflag |= CSTOPB;		break;	default:		return(-EINVAL);  }  return(0);}/* Set the number of data bits. */static inttty_set_databits(struct termios *tty, char *databits){  if (opt_d) printf("slattach: tty_set_databits: %c\n", *databits);  tty->c_cflag &= ~CSIZE;  switch(*databits) {	case '5':		tty->c_cflag |= CS5;		break;	case '6':		tty->c_cflag |= CS6;		break;	case '7':		tty->c_cflag |= CS7;		break;	case '8':		tty->c_cflag |= CS8;		break;	default:		return(-EINVAL);  }  return(0);}/* Set the type of parity encoding. */static inttty_set_parity(struct termios *tty, char *parity){  if (opt_d) printf("slattach: tty_set_parity: %c\n", *parity);  switch(toupper(*parity)) {	case 'N':		tty->c_cflag &= ~(PARENB | PARODD);		break;  	case 'O':		tty->c_cflag &= ~(PARENB | PARODD);		tty->c_cflag |= (PARENB | PARODD);		break;	case 'E':		tty->c_cflag &= ~(PARENB | PARODD);		tty->c_cflag |= (PARENB);		break;	default:		return(-EINVAL);  }  return(0);}/* Set the line speed of a terminal line. */static inttty_set_speed(struct termios *tty, char *speed){  int code;  if (opt_d) printf("slattach: tty_set_speed: %s\n", speed);  if ((code = tty_find_speed(speed)) < 0) return(code);  tty->c_cflag &= ~CBAUD;  tty->c_cflag |= code;  return(0);}/* Put a terminal line in a transparent state. */static inttty_set_raw(struct termios *tty){  int i;  int speed;  for(i = 0; i < NCCS; i++)		tty->c_cc[i] = '\0';		/* no spec chr		*/  tty->c_cc[VMIN] = 1;  tty->c_cc[VTIME] = 0;  tty->c_iflag = (IGNBRK | IGNPAR);		/* input flags		*/  tty->c_oflag = (0);				/* output flags		*/  tty->c_lflag = (0);				/* local flags		*/  speed = (tty->c_cflag & CBAUD);		/* save current speed	*/  tty->c_cflag = (CRTSCTS | HUPCL | CREAD);	/* UART flags		*/  if (opt_L) 	tty->c_cflag |= CLOCAL;  tty->c_cflag |= speed;			/* restore speed	*/  return(0);}/* Fetch the state of a terminal. */static inttty_get_state(struct termios *tty){  if (ioctl(tty_fd, TCGETS, tty) < 0) {	if (opt_q == 0) fprintf(stderr,		"slattach: tty_get_state: %s\n", strerror(errno));	return(-errno);  }  return(0);}/* Set the state of a terminal. */static int

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?