slattach.c
来自「Linux下网络相关工具源代码。」· C语言 代码 · 共 724 行 · 第 1/2 页
C
724 行
tty_set_state(struct termios *tty){ if (ioctl(tty_fd, TCSETS, tty) < 0) { if (opt_q == 0) fprintf(stderr, "slattach: tty_set_state: %s\n", strerror(errno)); return(-errno); } return(0);}/* Get the line discipline of a terminal line. */static inttty_get_disc(int *disc){ if (ioctl(tty_fd, TIOCGETD, disc) < 0) { if (opt_q == 0) fprintf(stderr, "slattach: tty_get_disc: %s\n", strerror(errno)); return(-errno); } return(0);}/* Set the line discipline of a terminal line. */static inttty_set_disc(int disc){ if (disc == -1) disc = tty_sdisc; if (ioctl(tty_fd, TIOCSETD, &disc) < 0) { if (opt_q == 0) fprintf(stderr, "slattach: tty_set_disc(%d, %d): %s\n", tty_fd, disc, strerror(errno)); return(-errno); } return(0);}/* Fetch the name of the network interface attached to this terminal. */static inttty_get_name(char *name){ if (ioctl(tty_fd, SIOCGIFNAME, name) < 0) { if (opt_q == 0) fprintf(stderr, "slattach: tty_get_name: %s\n", strerror(errno)); return(-errno); } return(0);}/* Hangup the line. */static inttty_hangup(void){ struct termios tty; tty = tty_current; (void) tty_set_speed(&tty, "0"); if (tty_set_state(&tty) < 0) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_hangup(DROP): %s\n"), strerror(errno)); return(-errno); } (void) sleep(1); if (tty_set_state(&tty_current) < 0) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_hangup(RAISE): %s\n"), strerror(errno)); return(-errno); } return(0);}/* Close down a terminal line. */static inttty_close(void){ (void) tty_set_disc(tty_sdisc); (void) tty_hangup(); (void) tty_lock(NULL, 0); return(0);}/* Open and initialize a terminal line. */static inttty_open(char *name, char *speed){ char path[PATH_MAX]; register char *sp; int fd; /* Try opening the TTY device. */ if (name != NULL) { if ((sp = strrchr(name, '/')) != (char *)NULL) *sp++ = '\0'; else sp = name; sprintf(path, "/dev/%s", sp); if (tty_lock(sp, 1)) return(-1); /* can we lock the device? */ if ((fd = open(path, O_RDWR)) < 0) { if (opt_q == 0) fprintf(stderr, "slattach: tty_open(%s, RW): %s\n", path, strerror(errno)); return(-errno); } tty_fd = fd; if (opt_d) printf("slattach: tty_open: %s (%d) ", path, fd); } else { tty_fd = 0; sp = (char *)NULL; } /* Fetch the current state of the terminal. */ if (tty_get_state(&tty_saved) < 0) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_open: cannot get current state!\n")); return(-errno); } tty_current = tty_saved; /* Fetch the current line discipline of this terminal. */ if (tty_get_disc(&tty_sdisc) < 0) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_open: cannot get current line disc!\n")); return(-errno); } tty_ldisc = tty_sdisc; /* Put this terminal line in a 8-bit transparent mode. */ if (opt_m == 0) { if (tty_set_raw(&tty_current) < 0) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_open: cannot set RAW mode!\n")); return(-errno); } /* Set the default speed if we need to. */ if (speed != NULL) { if (tty_set_speed(&tty_current, speed) != 0) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_open: cannot set %s bps!\n"), speed); return(-errno); } } /* Set up a completely 8-bit clean line. */ if (tty_set_databits(&tty_current, "8") || tty_set_stopbits(&tty_current, "1") || tty_set_parity(&tty_current, "N")) { if (opt_q == 0) fprintf(stderr, _("slattach: tty_open: cannot set 8N1 mode!\n")); return(-errno); } /* Set the new line mode. */ if ((fd = tty_set_state(&tty_current)) < 0) return(fd); } /* OK, line is open. Do we need to "silence" it? */ (void) tty_nomesg(tty_fd); return(0);}/* Catch any signals. */static voidsig_catch(int sig){/* (void) signal(sig, sig_catch); */ tty_close(); exit(0);}static voidusage(void){ char *usage_msg = "Usage: slattach [-ehlLmnqv] "#ifdef SIOCSKEEPALIVE "[-k keepalive] "#endif#ifdef SIOCSOUTFILL "[-o outfill] "#endif "[-c cmd] [-s speed] [-p protocol] tty | -\n" " slattach -V | --version\n"; fprintf(stderr, usage_msg); exit(1);}static void version(void){ printf("%s\n%s\n%s\n", Release, Version, Signature); exit(E_VERSION);}intmain(int argc, char *argv[]){ char path[128]; char buff[128]; char *speed = NULL; char *proto = DEF_PROTO; char *extcmd = (char *)0; struct hwtype *ht; char *sp; int s; static struct option longopts[] = { { "version", 0, NULL, 'V' }, { NULL, 0, NULL, 0 } }; strcpy(path, ""); /* Scan command line for any arguments. */ opterr = 0; while ((s = getopt_long(argc, argv, "c:ehlLmnp:qs:vdVk:o:", longopts, NULL)) != EOF) switch(s) { case 'c': extcmd = optarg; break; case 'e': opt_e = 1 - opt_e; break; case 'h': opt_h = 1 - opt_h; break;#ifdef SIOCSKEEPALIVE case 'k': opt_k = atoi(optarg); break;#endif case 'L': opt_L = 1 - opt_L; break; case 'l': opt_l = 1 - opt_l; break; case 'm': opt_m = 1 - opt_m; break; case 'n': opt_n = 1 - opt_n; break;#ifdef SIOCSOUTFILL case 'o': opt_o = atoi(optarg); break;#endif case 'p': proto = optarg; break; case 'q': opt_q = 1 - opt_q; break; case 's': speed = optarg; break; case 'd': opt_d = 1 - opt_d; break; case 'v': opt_v = 1 - opt_v; break; case 'V': version(); /*NOTREACHED*/ default: usage(); /*NOTREACHED*/ } activate_init(); /* Check the protocol. */ if ((ht = get_hwtype(proto)) == NULL && strcmp(proto, "tty")) { if (opt_q == 0) fprintf(stderr, _("slattach: unsupported protocol %s\n"), proto); return(2); } if (ht == NULL) opt_m++; /* Is a terminal given? */ if (optind != (argc - 1)) usage(); strncpy(path, argv[optind], 128); if (!strcmp(path, "-")) { opt_e = 1; sp = NULL; if (tty_open(NULL, speed) < 0) { return(3); } } else { if ((sp = strrchr(path, '/')) != NULL) *sp++ = '\0'; else sp = path; if (tty_open(sp, speed) < 0) { return(3); } } /* Start the correct protocol. */ if (ht == NULL) { tty_sdisc = N_TTY; tty_close(); return(0); } (*ht->activate)(tty_fd); if (opt_v == 1) { tty_get_name(buff); printf(_("%s started"), proto); if (sp != NULL) printf(_(" on %s"), sp); printf(_(" interface %s\n"), buff); } /* Configure keepalive and outfill. */#ifdef SIOCSKEEPALIVE if (opt_k && (ioctl(tty_fd, SIOCSKEEPALIVE, &opt_k) < 0)) fprintf(stderr, "slattach: ioctl(SIOCSKEEPALIVE): %s\n", strerror(errno));#endif#ifdef SIOCSOUTFILL if (opt_o && (ioctl(tty_fd, SIOCSOUTFILL, &opt_o) < 0)) fprintf(stderr, "slattach: ioctl(SIOCSOUTFILL): %s\n", strerror(errno));#endif (void) signal(SIGHUP, sig_catch); (void) signal(SIGINT, sig_catch); (void) signal(SIGQUIT, sig_catch); (void) signal(SIGTERM, sig_catch); /* Wait until we get killed if hanging on a terminal. */ if (opt_e == 0) { while(1) { if(opt_h == 1) { /* hangup on carrier loss */ int n = 0; ioctl(tty_fd, TIOCMGET, &n); if(!(n & TIOCM_CAR)) break; sleep(15); } else sleep(60); }; tty_close(); if(extcmd!=(char *)0) /* external command on exit */ system(extcmd); } exit(0);}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?