157694Sbostic /*-
2*60663Sbostic * Copyright (c) 1992, 1993
3*60663Sbostic * The Regents of the University of California. All rights reserved.
457694Sbostic *
557694Sbostic * This code is derived from software contributed to Berkeley by
657694Sbostic * Rodney Ruddock of the University of Guelph.
757694Sbostic *
857694Sbostic * %sccs.include.redist.c%
957694Sbostic */
1057694Sbostic
1157694Sbostic #ifndef lint
12*60663Sbostic static char copyright[] =
13*60663Sbostic "@(#) Copyright (c) 1992, 1993\n\
14*60663Sbostic The Regents of the University of California. All rights reserved.\n";
1557694Sbostic #endif /* not lint */
1657694Sbostic
1759475Sbostic #ifndef lint
18*60663Sbostic static char sccsid[] = "@(#)main.c 8.1 (Berkeley) 05/31/93";
1959475Sbostic #endif /* not lint */
2059475Sbostic
2157710Sbostic #include <sys/types.h>
2258315Sbostic #include <sys/ioctl.h>
2357710Sbostic
2459477Sbostic #include <limits.h>
2557710Sbostic #include <regex.h>
2657710Sbostic #include <setjmp.h>
2757710Sbostic #include <signal.h>
2857710Sbostic #include <stdio.h>
2957710Sbostic #include <stdlib.h>
3057710Sbostic #include <string.h>
3159477Sbostic #include <unistd.h>
3257710Sbostic
3358315Sbostic #ifdef DBI
3458315Sbostic #include <db.h>
3558315Sbostic #endif
3658315Sbostic
3757694Sbostic #include "ed.h"
3857710Sbostic #include "extern.h"
3957694Sbostic
4057694Sbostic /*
4157694Sbostic * This is where all of the "global" variables are declared. They are
4257694Sbostic * set for extern in the ed.h header file (so everyone can get them).
4357694Sbostic */
4457694Sbostic
4558564Sralph int nn_max, nn_max_flag, Start_default, End_default, address_flag;
4658315Sbostic int zsnum, filename_flag, add_flag=0, join_flag=0;
4759558Sbostic int help_flag=0, gut_num=-1;
4858315Sbostic #ifdef STDIO
4958315Sbostic FILE *fhtmp;
5058315Sbostic int file_seek;
5158315Sbostic #endif
5257694Sbostic
5358315Sbostic #ifdef DBI
5457694Sbostic DB *dbhtmp;
5558315Sbostic #endif
5657694Sbostic
5757694Sbostic LINE *nn_max_start, *nn_max_end;
5857694Sbostic
5957694Sbostic struct MARK mark_matrix[26]; /* in init set all to null */
6057694Sbostic
6157694Sbostic char *text;
6259475Sbostic LINE **gut=NULL;
6357694Sbostic char *filename_current, *prompt_string=NULL, help_msg[130];
6457694Sbostic char *template=NULL;
6557694Sbostic int prompt_str_flg=0, start_up_flag=0, name_set=0;
6657694Sbostic
6758564Sralph LINE *top, *current, *bottom, *Start, *End;
6857694Sbostic struct u_layer *u_stk;
6957694Sbostic struct d_layer *d_stk;
7057694Sbostic LINE *u_current, *u_top, *u_bottom;
7157694Sbostic int u_set;
7257694Sbostic regex_t RE_comp;
7357694Sbostic regmatch_t RE_match[RE_SEC];
7457694Sbostic int RE_sol=0, RE_flag=0;
7557694Sbostic char *RE_patt=NULL;
7657694Sbostic
7757694Sbostic int ss; /* for the getc() */
7859475Sbostic int explain_flag=1, g_flag=0, GV_flag=0, printsfx=0, exit_code=0;
7957694Sbostic long change_flag=0L;
8057694Sbostic int line_length;
8158352Sbostic jmp_buf ctrl_position, ctrl_position2, ctrl_position3; /* For SIGnal handling. */
8258352Sbostic int sigint_flag, sighup_flag, sigspecial=0, sigspecial2=0, sigspecial3=0;
8357694Sbostic
8457710Sbostic static void sigint_handler __P((int));
8557710Sbostic static void sighup_handler __P((int));
8657710Sbostic
8757710Sbostic /*
8857710Sbostic * Starts the whole show going. Set things up as the arguments spec
8957710Sbostic * in the shell and set a couple of the global variables.
9057710Sbostic *
9157710Sbostic * Note naming viol'n with errnum for consistancy.
9257694Sbostic */
9357710Sbostic int
main(argc,argv)9457710Sbostic main(argc, argv)
9557710Sbostic int argc;
9657710Sbostic char *argv[];
9757694Sbostic {
9859915Sbostic int l_num, errnum=0, l_err=0;
9958710Sbostic char *l_fnametmp, *l_col, buf[2];
10058315Sbostic struct winsize win;
10157694Sbostic
10258710Sbostic setbuffer(stdin, buf, 1);
10358315Sbostic line_length = ((l_col = getenv("COLUMNS")) == NULL ? 0 : atoi(l_col));
10459475Sbostic if ((line_length == 0 && isatty(STDOUT_FILENO) &&
10559475Sbostic ioctl(STDOUT_FILENO, TIOCGWINSZ, &win) != -1))
10658315Sbostic line_length = win.ws_col;
10758315Sbostic if (line_length == 0)
10858315Sbostic line_length = 78;
10960656Sbostic line_length -= 3; /* for the octal to break properly in 'l' */
11057694Sbostic
11158564Sralph Start = End = NULL;
11257710Sbostic top = bottom = NULL;
11357710Sbostic current = NULL;
11457710Sbostic nn_max_flag = 0;
11557710Sbostic nn_max_start = nn_max_end = NULL;
11657710Sbostic l_fnametmp = calloc(FILENAME_LEN, sizeof(char));
11757710Sbostic if (l_fnametmp == NULL)
11857710Sbostic ed_exit(4);
11957710Sbostic text = calloc(NN_MAX_START + 2, sizeof(char));
12057710Sbostic if (text == NULL)
12157710Sbostic ed_exit(4);
12258564Sralph Start_default = End_default = 0;
12357710Sbostic zsnum = 22; /* for the 'z' command */
12459558Sbostic help_msg[0] = '\0';
12557710Sbostic u_stk = NULL;
12657710Sbostic d_stk = NULL;
12757710Sbostic u_current = u_top = u_bottom = NULL;
12857710Sbostic u_set = 0; /* for in d after a j */
12957710Sbostic filename_flag = 0;
13057710Sbostic filename_current = NULL;
13157694Sbostic
13257710Sbostic l_num = 1;
13357710Sbostic for (;;) {
13457710Sbostic /* Process the command line options */
13557710Sbostic if (l_num >= argc)
13657710Sbostic break;
13757710Sbostic switch (argv[l_num][0]) {
13857710Sbostic case '-':
13957710Sbostic switch (argv[l_num][1]) {
14057710Sbostic case '\0': /* this is why 'getopt' not used */
14157710Sbostic case 's':
14257710Sbostic explain_flag = 0;
14357710Sbostic break;
14457710Sbostic case 'p':
14557710Sbostic if (++l_num < argc) {
14657710Sbostic prompt_string =
14757710Sbostic calloc(strlen(argv[l_num]),
14857710Sbostic sizeof(char));
14957710Sbostic if (prompt_string == NULL)
15057710Sbostic ed_exit(4);
15157710Sbostic strcpy(prompt_string, argv[l_num]);
15257710Sbostic prompt_str_flg = 1;
15357710Sbostic break;
15457710Sbostic }
15557710Sbostic l_err = 1;
15658710Sbostic case 'v':
15758710Sbostic #ifdef BSD
15859558Sbostic (void)printf("ed: in BSD mode:\n");
15958710Sbostic #endif
16058710Sbostic #ifdef POSIX
16159558Sbostic (void)printf("ed: in POSIX mode:\n");
16258710Sbostic #endif
16359475Sbostic break;
16457710Sbostic default:
16557710Sbostic l_err++;
16657710Sbostic ed_exit(l_err);
16757710Sbostic }
16857710Sbostic break;
16957710Sbostic default:
17057710Sbostic if (name_set)
17157710Sbostic ed_exit(3);
17257710Sbostic strcpy(l_fnametmp, argv[l_num]);
17357710Sbostic filename_current = l_fnametmp;
17457710Sbostic name_set = 1;
17557710Sbostic if (prompt_str_flg)
17657710Sbostic break;
17757710Sbostic /* default ed prompt */
17857710Sbostic prompt_string = (char *) calloc(3, sizeof(char));
17957710Sbostic strcpy(prompt_string, "*");
18057710Sbostic break;
18157710Sbostic }
18257710Sbostic l_num++;
18357710Sbostic }
18457710Sbostic
18557710Sbostic start_up_flag = 1;
18657710Sbostic cmd_loop(stdin, &errnum);
18757710Sbostic /* NOTREACHED */
18857710Sbostic }
18957710Sbostic
19057694Sbostic /*
19157710Sbostic * The command loop. What the command is that the user has specified
19257694Sbostic * is determined here. This is not just for commands coming from
19357694Sbostic * the terminal but any standard i/o stream; see the global commands.
19457694Sbostic * Some of the commands are handled within here (i.e. 'H') while most
19557694Sbostic * are handled in their own functions (as called).
19657694Sbostic */
19757694Sbostic void
cmd_loop(inputt,errnum)19857694Sbostic cmd_loop(inputt, errnum)
19957710Sbostic FILE *inputt;
20057710Sbostic int *errnum;
20157694Sbostic {
20257710Sbostic LINE *l_tempp;
20357710Sbostic int l_last, l_jmp_flag;
20457694Sbostic
20558315Sbostic l_last = 0; /* value in l_last may be clobbered (reset to = 0) by longjump, but that's okay */
20657694Sbostic
20757710Sbostic if (g_flag == 0) { /* big, BIG trouble if we don't check! think. */
20857710Sbostic /* set the jump point for the signals */
20957710Sbostic l_jmp_flag = setjmp(ctrl_position);
21057710Sbostic signal(SIGINT, sigint_handler);
21157710Sbostic signal(SIGHUP, sighup_handler);
21257710Sbostic switch (l_jmp_flag) {
21357710Sbostic case JMP_SET:
21457710Sbostic break;
21557710Sbostic /* Some general cleanup not specific to the jmp pt. */
21657710Sbostic case INTERUPT:
21757710Sbostic sigint_flag = 0;
21857710Sbostic GV_flag = 0; /* safest place to do these flags */
21957710Sbostic g_flag = 0;
22059558Sbostic (void)printf("\n?\n");
22157710Sbostic break;
22257710Sbostic case HANGUP: /* shouldn't get here. */
22357710Sbostic break;
22457710Sbostic default:
22557710Sbostic (void)fprintf(stderr, "Signal jump problem\n");
22657710Sbostic }
22757710Sbostic /* Only do this once! */
22857710Sbostic if (start_up_flag) {
22957710Sbostic start_up_flag = 0;
23057710Sbostic /* simulate the 'e' at startup */
23157710Sbostic e2(inputt, errnum);
23259915Sbostic if (*errnum == 0)
23359915Sbostic goto errmsg2;
23457710Sbostic }
23557710Sbostic }
23657710Sbostic for (;;) {
23757710Sbostic if (prompt_str_flg == 1)
23857710Sbostic (void)printf("%s", prompt_string);
23957710Sbostic ss = getc(inputt);
24057710Sbostic *errnum = 0;
24158564Sralph l_tempp = Start = End = NULL;
24258564Sralph Start_default = End_default = 1;
24357694Sbostic
24457710Sbostic /*
24557710Sbostic * This isn't nice and alphabetical mainly because of
24657710Sbostic * restrictions with 'G' and 'V' (see ed(1)).
24757710Sbostic */
24857710Sbostic for (;;) {
24957710Sbostic switch (ss) {
25057710Sbostic case 'd':
25157710Sbostic d(inputt, errnum);
25257710Sbostic break;
25357710Sbostic case 'e':
25457710Sbostic case 'E':
25557710Sbostic e(inputt, errnum);
25659915Sbostic if (*errnum == 0)
25759915Sbostic goto errmsg2;
25857710Sbostic break;
25957710Sbostic case 'f':
26057710Sbostic f(inputt, errnum);
26157710Sbostic break;
26257710Sbostic case 'a':
26357710Sbostic case 'c':
26457710Sbostic case 'i':
26557710Sbostic case 'g':
26657710Sbostic case 'G':
26757710Sbostic case 'v':
26857710Sbostic case 'V':
26957710Sbostic if (GV_flag == 1) {
27057710Sbostic (void)sprintf(help_msg,
27157710Sbostic "command `%c' illegal in G/V", ss);
27257710Sbostic *errnum = -1;
27357710Sbostic break;
27457710Sbostic }
27557710Sbostic switch (ss) {
27657710Sbostic case 'a':
27757710Sbostic a(inputt, errnum);
27857710Sbostic break;
27957710Sbostic case 'c':
28057710Sbostic c(inputt, errnum);
28157710Sbostic break;
28257710Sbostic case 'i':
28357710Sbostic i(inputt, errnum);
28457710Sbostic break;
28557710Sbostic default:
28657710Sbostic g(inputt, errnum);
28757710Sbostic }
28857710Sbostic break;
28957710Sbostic case 'h':
29057710Sbostic if (rol(inputt, errnum))
29157710Sbostic break;
29259558Sbostic if (help_msg[0])
29359558Sbostic (void)printf("%s\n", help_msg);
29457710Sbostic *errnum = 1;
29557710Sbostic break;
29657710Sbostic case 'H':
29757710Sbostic if (rol(inputt, errnum))
29857710Sbostic break;
29957710Sbostic if (help_flag == 0) {
30057710Sbostic help_flag = 1;
30159558Sbostic if (help_msg[0])
30259558Sbostic (void)printf("%s\n",
30359558Sbostic help_msg);
30457710Sbostic } else
30557710Sbostic help_flag = 0;
30657710Sbostic *errnum = 1;
30757710Sbostic break;
30857710Sbostic case 'j':
30957710Sbostic j(inputt, errnum);
31057710Sbostic break;
31157710Sbostic case 'k':
31257710Sbostic set_mark(inputt, errnum);
31357710Sbostic break;
31457710Sbostic case 'l':
31557710Sbostic l(inputt, errnum);
31657710Sbostic break;
31757710Sbostic case 'm':
31857710Sbostic m(inputt, errnum);
31957710Sbostic break;
32057694Sbostic #ifdef POSIX
32157710Sbostic /* In POSIX-land 'P' toggles the prompt. */
32257710Sbostic case 'P':
32357710Sbostic if (rol(inputt, errnum))
32457710Sbostic break;
32557710Sbostic prompt_str_flg = prompt_str_flg ? 0 : 1;
32657710Sbostic *errnum = 1;
32757710Sbostic break;
32857694Sbostic #endif
32957710Sbostic case '\n':
33057710Sbostic if (GV_flag == 1)
33157710Sbostic return;
33257710Sbostic /* For 'p' to consume. */
33357710Sbostic ungetc(ss, inputt);
33457710Sbostic if ((current == bottom) && (End == NULL)) {
33557710Sbostic strcpy(help_msg, "at end of buffer");
33657710Sbostic *errnum = -1;
33757710Sbostic break;
33857710Sbostic }
33957710Sbostic current = current->below;
34057694Sbostic #ifdef BSD
34157710Sbostic /* In BSD 'P'=='p'. */
34257710Sbostic case 'P':
34357694Sbostic #endif
34457710Sbostic case 'p':
34557710Sbostic p(inputt, errnum, 0);
34657710Sbostic break;
34757710Sbostic case 'n':
34857710Sbostic p(inputt, errnum, 1);
34957710Sbostic break;
35057710Sbostic /*
35157710Sbostic * An EOF means 'q' unless we're still in the middle
35257710Sbostic * of a global command, in which case it was just the
35357710Sbostic * end of the command list found.
35457710Sbostic */
35557710Sbostic case EOF:
35657710Sbostic clearerr(inputt);
35757710Sbostic if (g_flag > 0)
35857710Sbostic return;
35958710Sbostic /*ss = 'q';*/
36057710Sbostic case 'q':
36157710Sbostic case 'Q':
36259915Sbostic if ((!isatty(STDIN_FILENO)) && (ss == 'q'))
36359915Sbostic ss = 'Q';
36457710Sbostic q(inputt, errnum);
36557710Sbostic break;
36657710Sbostic case 'r':
36757710Sbostic r(inputt, errnum);
36859915Sbostic if (*errnum == 0)
36959915Sbostic goto errmsg2;
37057710Sbostic break;
37157710Sbostic case 's':
37257710Sbostic s(inputt, errnum);
37357710Sbostic break;
37457710Sbostic case 't':
37557710Sbostic t(inputt, errnum);
37657710Sbostic break;
37757710Sbostic case 'u':
37857710Sbostic u(inputt, errnum);
37957710Sbostic break;
38057710Sbostic case 'w':
38157710Sbostic case 'W':
38257710Sbostic w(inputt, errnum);
38357710Sbostic break;
38457710Sbostic case 'z':
38557710Sbostic z(inputt, errnum);
38657710Sbostic break;
38757710Sbostic case '!':
38857710Sbostic bang(inputt, errnum);
38957710Sbostic break;
39057710Sbostic case '=':
39157710Sbostic equal(inputt, errnum);
39257710Sbostic break;
39357710Sbostic /*
39457710Sbostic * Control of address forms from here down.
39557710Sbostic *
39657710Sbostic * It's a head-game to understand why ";" and "," look
39757710Sbostic * as they do below, but a lot of it has to do with ";"
39857710Sbostic * and "," being special address pair forms themselves
39957710Sbostic * and the compatibility for address "chains".
40057710Sbostic */
40157710Sbostic case ';':
40258564Sralph if (End_default == 1 && Start_default == 1) {
40358564Sralph Start = current;
40457710Sbostic End = bottom;
40558564Sralph Start_default = End_default = 0;
40657710Sbostic } else {
40758564Sralph Start = current = End;
40858564Sralph Start_default = 0;
40957710Sbostic End_default = 1;
41057710Sbostic }
41157710Sbostic l_tempp = NULL;
41257710Sbostic break;
41357710Sbostic /*
41457710Sbostic * Note address ".,x" where x is a cmd is legal; not a
41557710Sbostic * bug - for backward compatability.
41657710Sbostic */
41757710Sbostic case ',':
41858564Sralph if (End_default == 1 && Start_default == 1) {
41958564Sralph Start = top;
42057710Sbostic End = bottom;
42158564Sralph Start_default = End_default = 0;
42257710Sbostic } else {
42358564Sralph Start = End;
42458564Sralph Start_default = 0;
42557710Sbostic End_default = 1;
42657710Sbostic }
42757710Sbostic l_tempp = NULL;
42857710Sbostic break;
42957710Sbostic case '%':
43057710Sbostic if (End_default == 0) {
43157710Sbostic strcpy(help_msg,
43257710Sbostic "'%' is an address pair");
43357710Sbostic *errnum = -1;
43457710Sbostic break;
43557710Sbostic }
43658564Sralph Start = top;
43757710Sbostic End = bottom;
43858564Sralph Start_default = End_default = 0;
43957710Sbostic l_tempp = NULL;
44057710Sbostic break;
44157710Sbostic /*
44257710Sbostic * Within address_conv => l_last = '+', foobar, but
44357710Sbostic * historical and now POSIX...
44457710Sbostic */
44557710Sbostic case ' ':
44657710Sbostic break;
44757710Sbostic case '0':
44857710Sbostic case '1':
44957710Sbostic case '2':
45057710Sbostic case '3':
45157710Sbostic case '4':
45257710Sbostic case '5':
45357710Sbostic case '6':
45457710Sbostic case '7':
45557710Sbostic case '8':
45657710Sbostic case '9':
45757710Sbostic case '-':
45857710Sbostic case '^':
45957710Sbostic case '+':
46057710Sbostic case '\'':
46157710Sbostic case '$':
46257710Sbostic case '?':
46357710Sbostic case '/':
46457710Sbostic case '.':
46557710Sbostic ungetc(ss, inputt);
46658564Sralph if (Start_default == 0 && End_default == 0) {
46757710Sbostic strcpy(help_msg,
46857710Sbostic "badly formed address");
46957710Sbostic *errnum = -1;
47057710Sbostic break;
47157710Sbostic }
47257710Sbostic ss = l_last;
47357710Sbostic l_tempp = address_conv(l_tempp, inputt, errnum);
47457710Sbostic if (*errnum < 0)
47557710Sbostic break;
47657710Sbostic End = l_tempp;
47757710Sbostic End_default = 0;
47858564Sralph if (Start_default == 0)
47958564Sralph *errnum = address_check(Start, End);
48057710Sbostic break;
48157710Sbostic default:
48257710Sbostic *errnum = -1;
48357710Sbostic strcpy(help_msg, "unknown command");
48457710Sbostic break;
48557710Sbostic } /* end-switch(ss) */
48657694Sbostic
48757710Sbostic /* Things came out okay with the last command. */
48857710Sbostic if (*errnum > 0) {
48957710Sbostic if (GV_flag == 1)
49057710Sbostic return;
49157710Sbostic /* Do the suffixes if there were any. */
49257710Sbostic if (printsfx > 0) {
49358564Sralph Start = End = current;
49457710Sbostic ungetc(ss, inputt);
49557710Sbostic if (printsfx == 1)
49657710Sbostic p(inputt, errnum, 0);
49757710Sbostic else
49857710Sbostic if (printsfx == 2)
49957710Sbostic p(inputt, errnum, 1);
50057710Sbostic else if (printsfx == 4)
50157710Sbostic l(inputt, errnum);
50257710Sbostic /* Unlikely it's needed, but... */
50357710Sbostic if (*errnum < 0)
50457710Sbostic goto errmsg;
50557710Sbostic }
50657710Sbostic break;
50757710Sbostic }
50857710Sbostic /* There was a problem with the last command. */
50957710Sbostic else if (*errnum < 0) {
51057710Sbostic errmsg: while (((ss = getc(inputt)) != '\n') &&
51157710Sbostic (ss != EOF));
51259915Sbostic (void)printf("?\n");
51359915Sbostic errmsg2: if (help_flag)
51459915Sbostic (void)printf("%s\n", help_msg);
51559475Sbostic exit_code = 4;
51659475Sbostic /* for people wanting scripts to carry on after a cmd error, then
51759475Sbostic * define NOENDONSCRIPT on the compile line.
51859475Sbostic */
51959475Sbostic #ifndef NOENDONSCRIPT
52059475Sbostic if (!isatty(STDIN_FILENO)) {
52159475Sbostic ss = 'Q';
52259475Sbostic ungetc('\n', inputt);
52359475Sbostic q(inputt, errnum);
52459475Sbostic }
52559475Sbostic #endif
52658315Sbostic break;
52757710Sbostic }
52857710Sbostic l_last = ss;
52957710Sbostic ss = getc(inputt);
53057710Sbostic }
53157710Sbostic }
53257710Sbostic }
53357694Sbostic
53457710Sbostic /*
53557710Sbostic * Exits ed and prints an appropriate message about the command line
53657694Sbostic * being malformed (see below).
53757694Sbostic */
53857694Sbostic void
ed_exit(err)53957694Sbostic ed_exit(err)
54057710Sbostic int err;
54157694Sbostic {
54257710Sbostic switch (err) {
54357710Sbostic case 1:
54457710Sbostic (void)fprintf(stderr, "ed: illegal option\n");
54557710Sbostic break;
54657710Sbostic case 2:
54757710Sbostic (void)fprintf(stderr, "ed: missing promptstring\n");
54857710Sbostic break;
54957710Sbostic case 3:
55057710Sbostic (void)fprintf(stderr, "ed: too many filenames\n");
55157710Sbostic break;
55257710Sbostic case 4:
55357710Sbostic (void)fprintf(stderr, "ed: out of memory error\n");
55457710Sbostic break;
55558315Sbostic case 5:
55658315Sbostic (void)fprintf(stderr, "ed: unable to create buffer\n");
55758315Sbostic break;
55857710Sbostic default:
55957710Sbostic (void)fprintf(stderr, "ed: command line error\n");
56057710Sbostic break;
56157710Sbostic }
56257710Sbostic (void)fprintf(stderr,
56357710Sbostic "ed: ed [ -s ] [ -p promptstring ] [ filename ]\n");
56457710Sbostic exit(1);
56557710Sbostic }
56657694Sbostic
56757694Sbostic /*
56857710Sbostic * SIGINT is never turned off. We flag it happened and then pay attention
56957710Sbostic * to it at certain logical locations in the code we don't do more here
57057710Sbostic * cause some of our buffer pointer's may be in an inbetween state at the
57157710Sbostic * time of the SIGINT. So we flag it happened, let the local fn handle it
57257710Sbostic * and do a jump back to the cmd_loop
57357694Sbostic */
57457710Sbostic static void
sigint_handler(signo)57557710Sbostic sigint_handler(signo)
57657710Sbostic int signo;
57757710Sbostic {
57857710Sbostic sigint_flag = 1;
57958352Sbostic if (sigspecial3) {
58058352Sbostic sigspecial3 = 0;
58158352Sbostic SIGINT_ILACTION;
58258352Sbostic }
58358315Sbostic else
58458315Sbostic if (sigspecial);
58558315Sbostic else
58658315Sbostic SIGINT_ACTION;
58757710Sbostic }
58857694Sbostic
58957710Sbostic static void
sighup_handler(signo)59057710Sbostic sighup_handler(signo)
59157710Sbostic int signo;
59257694Sbostic {
59357710Sbostic sighup_flag = 1;
59457710Sbostic undo();
59557710Sbostic do_hup();
59657710Sbostic /* NOTREACHED */
59757694Sbostic
59857710Sbostic SIGHUP_ACTION;
59957710Sbostic }
600