📄 script.c
字号:
int f, val, c; char *action = NULL; if (inexpect) { fprintf(stderr, _("script \"%s\" line %d: nested expect%s\n"), curenv->scriptname, thisline->lineno, "\r"); exit(1); } etimeout = 120; inexpect = 1; s = getword(&text); if (!strcmp(s, "{")) { if (*text) syntaxerr(_("(garbage after {)")); thisline = thisline->next; seq = buildexpect(); } else { oneline.line = s; oneline.next = NULL; dflseq[0] = &oneline; dflseq[1] = NULL; seq = dflseq; } /* Seek a timeout command */ for (f = 0; seq[f]; f++) { if (!strncmp(seq[f]->line, "timeout", 7)) { c = seq[f]->line[7]; if (c == 0 || (c != ' ' && c != '\t')) continue; s = seq[f]->line + 7; /* seq[f] = NULL; */ skipspace(&s); w = getword(&s); if (w == NULL) syntaxerr(_("(argument expected)")); val = getnum(w); if (val == 0) syntaxerr(_("(invalid argument)")); etimeout = val; skipspace(&s); if (*s != 0) toact = s; break; } } if (sigsetjmp(ejmp, 1) != 0) { f = s_exec(toact); inexpect = 0; return f; } /* Allright. Now do the expect. */ c = OK; while (!found) { action = NULL; readchar(); for (f = 0; seq[f]; f++) { s = seq[f]->line; w = getword(&s); if (expfound(w)) { action = s; found = 1; break; } } if (action != NULL && *action) { found = 0; /* Maybe BREAK or RETURN */ if ((c = s_exec(action)) != OK) found = 1; } } inexpect = 0; etimeout = 0; return c;}/* * Jump to a shell and run a command. */int shell(char *text){ laststatus = system(text); return OK;}/* * Send output to stdout ( = modem) */int dosend(char *text){#ifdef HAVE_USLEEP /* 200 ms delay. */ usleep(200000);#endif /* Before we send anything, flush input buffer. */ m_flush(0); memset(inbuf, 0, sizeof(inbuf)); newline = "\r"; return output(text, stdout);}/* * Exit from the script, possibly with a value. */int doexit(char *text){ char *w; int ret = 0; w = getword(&text); if (w != NULL) ret = getnum(w); curenv->exstat = ret; longjmp(curenv->ebuf, 1); return 0;}/* * Goto a specific label. */int dogoto(char *text){ char *w; struct line *l; char buf[32]; int len; w = getword(&text); if (w == NULL || *text) syntaxerr(_("(in goto/gosub label)")); snprintf(buf, sizeof(buf), "%s:", w); len = strlen(buf); for (l = curenv->lines; l; l = l->next) if (!strncmp(l->line, buf, len)) break; if (l == NULL) { fprintf(stderr, _("script \"%s\" line %d: label \"%s\" not found%s\n"), curenv->scriptname, thisline->lineno, w, "\r"); exit(1); } thisline = l; /* We return break, to automatically break out of expect loops. */ return BREAK;}/* * Goto a subroutine. */int dogosub(char *text){ struct line *oldline; int ret = OK; oldline = thisline; dogoto(text); while (ret != ERR) { if ((thisline = thisline->next) == NULL) { fprintf(stderr, _("script \"%s\": no return from gosub%s\n"), curenv->scriptname, "\r"); exit(1); } ret = s_exec(thisline->line); if (ret == RETURN) { ret = OK; thisline = oldline; break; } } return ret;}/* * Return from a subroutine. */int doreturn(char *text){ (void)text; return RETURN;}/* * Print text to stderr. */int print(char *text){ newline = "\r\n"; return output(text, stderr);}/* * Declare a variable (integer) */int doset(char *text){ char *w; struct var *v; w = getword(&text); if (w == NULL) syntaxerr(_("(missing var name)")); v = getvar(w, 1); if (*text) v->value = getnum(getword(&text)); return OK;}/* * Lower the value of a variable. */int dodec(char *text){ char *w; struct var *v; w = getword(&text); if (w == NULL) syntaxerr(_("(expected variable)")); v = getvar(w, 0); v->value--; return OK;}/* * Increase the value of a variable. */int doinc(char *text){ char *w; struct var *v; w = getword(&text); if (w == NULL) syntaxerr(_("(expected variable)")); v = getvar(w, 0); v->value++; return OK;}/* * If syntax: if n1 [><=] n2 command. */int doif(char *text){ char *w; int n1; int n2; char op; if ((w = getword(&text)) == NULL) syntaxerr("(if)"); n1 = getnum(w); if ((w = getword(&text)) == NULL) syntaxerr("(if)"); if (strcmp(w, "!=") == 0) op = '!'; else { if (*w == 0 || w[1] != 0) syntaxerr("(if)"); op = *w; } if ((w = getword(&text)) == NULL) syntaxerr("(if)"); n2 = getnum(w); if (!*text) syntaxerr(_("(expected command after if)")); if (op == '=') { if (n1 != n2) return OK; } else if (op == '!') { if (n1 == n2) return OK; } else if (op == '>') { if (n1 <= n2) return OK; } else if (op == '<') { if (n1 >= n2) return OK; } else syntaxerr(_("(unknown operator)")); return s_exec(text);}/* * Set the global timeout-time. */int dotimeout(char *text){ char *w; int val; w = getword(&text); if (w == NULL) syntaxerr(_("(argument expected)")); if ((val = getnum(w)) == 0) syntaxerr(_("(invalid argument)")); gtimeout = val; return OK;}/* * Turn verbose on/off (= echo stdin to stderr) */int doverbose(char *text){ char *w; curenv->verbose = 1; if ((w = getword(&text)) != NULL) { if (!strcmp(w, "on")) return OK; if (!strcmp(w, "off")) { curenv->verbose = 0; return OK; } } syntaxerr(_("(unexpected argument)")); return ERR;}/* * Sleep for a certain number of seconds. */int dosleep(char *text){ int foo, tm; tm = getnum(text); foo = gtimeout - tm; /* The alarm goes off every second.. */ while (gtimeout != foo) pause(); return OK;}/* * Break out of an expect loop. */int dobreak(char *dummy){ (void)dummy; if (!inexpect) { fprintf(stderr, _("script \"%s\" line %d: break outside of expect%s\n"), curenv->scriptname, thisline->lineno, "\r"); exit(1); } return BREAK;}/* * Call another script! */int docall(char *text){ struct line *oldline; struct env *oldenv; int er; if (*text == 0) syntaxerr(_("(argument expected)")); if (inexpect) { fprintf(stderr, _("script \"%s\" line %d: call inside expect%s\n"), curenv->scriptname, thisline->lineno, "\r"); exit(1); } oldline = thisline; oldenv = curenv; if ((er = execscript(text)) != 0) exit(er); /* freemem(); */ thisline = oldline; curenv = oldenv; return 0;}static int do_log_wrapper(char *s){ do_log("%s", s); return 0;}/* KEYWORDS */struct kw { const char *command; int (*fn)(char *);} keywords[] = { { "expect", expect }, { "send", dosend }, { "!", shell }, { "goto", dogoto }, { "gosub", dogosub }, { "return", doreturn }, { "exit", doexit }, { "print", print }, { "set", doset }, { "inc", doinc }, { "dec", dodec }, { "if", doif }, { "timeout", dotimeout }, { "verbose", doverbose }, { "sleep", dosleep }, { "break", dobreak }, { "call", docall }, { "log", do_log_wrapper }, { NULL, (int(*)(char *))0 }};/* * Execute one line. */int s_exec(char *text){ char *w; struct kw *k; w = getword(&text); /* If it is a label or a comment, skip it. */ if (w == NULL || *w == '#' || w[strlen(w) - 1] == ':') return OK; /* See which command it is. */ for (k = keywords; k->command; k++) if (!strcmp(w, k->command)) break; /* Command not found? */ if (k->command == NULL) { fprintf(stderr, _("script \"%s\" line %d: unknown command \"%s\"%s\n"), curenv->scriptname, thisline->lineno, w, "\r"); exit(1); } return (*(k->fn))(text);}/* * Run the script by continously executing "thisline". */int execscript(const char *s){ volatile int ret = OK; curenv = (struct env *)malloc(sizeof(struct env)); curenv->lines = NULL; curenv->vars = NULL; curenv->verbose = 1; curenv->scriptname = s; if (readscript(s) < 0) { freemem(); free(curenv); return ERR; } signal(SIGALRM, myclock); alarm(1); if (setjmp(curenv->ebuf) == 0) { thisline = curenv->lines; while (thisline != NULL && (ret = s_exec(thisline->line)) != ERR) thisline = thisline->next; } else ret = curenv->exstat ? ERR : 0; free(curenv); return ret;}void do_args(int argc, char **argv){ if (argc > 1 && !strcmp(argv[1], "--version")) { printf(_("runscript, part of minicom version %s\n"), VERSION); exit(0); } if (argc < 2) { fprintf(stderr, _("Usage: runscript <scriptfile> [logfile [homedir]]%s\n"),"\r"); exit(1); }}int main(int argc, char **argv){ char *s;#if 0 /* Shouldn't need this.. */ signal(SIGHUP, SIG_IGN);#endif /* initialize locale support */ setlocale(LC_ALL, ""); bindtextdomain(PACKAGE, LOCALEDIR); textdomain(PACKAGE); init_env(); do_args(argc, argv); memset(inbuf, 0, sizeof(inbuf)); if (argc > 2) { strncpy(logfname, argv[2], sizeof(logfname)); if (argc > 3) strncpy(homedir, argv[3], sizeof(homedir)); else if ((s = getenv("HOME")) != NULL) strncpy(homedir, s, sizeof(homedir)); else homedir[0] = 0; } else logfname[0] = 0; return execscript(argv[1]) != OK;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -