|
|
1.1 root 1: /* main.c */
2:
3: /* Author:
4: * Steve Kirkendall
5: * 16820 SW Tallac Way
6: * Beaverton, OR 97006
7: * [email protected], or ...uunet!tektronix!psueea!jove!kirkenda
8: */
9:
10:
11: /* This file contains the main() function of vi */
12:
13: #include "config.h"
14: #include <signal.h>
15: #include <setjmp.h>
16: #include "vi.h"
17:
18: extern trapint(); /* defined below */
19: extern char *getenv();
20: jmp_buf jmpenv;
21:
22: #ifndef NO_DIGRAPH
23: static init_digraphs();
24: #endif
25:
26: /*---------------------------------------------------------------------*/
27:
28: void main(argc, argv)
29: int argc;
30: char *argv[];
31: {
32: int i;
33: char *cmd = (char *)0;
34: char *tag = (char *)0;
35: char *err = (char *)0;
36: char *str;
37: #if MSDOS || TOS
38: char firstarg[256];
39: #else
40: char *firstarg;
41: #endif
42:
43: /* set mode to MODE_VI or MODE_EX depending on program name */
44: switch (argv[0][strlen(argv[0]) - 1])
45: {
46: case 'x': /* "ex" */
47: mode = MODE_EX;
48: break;
49:
50: case 'w': /* "view" */
51: mode = MODE_VI;
52: *o_readonly = TRUE;
53: break;
54: #ifndef NO_EXTENSIONS
55: case 't': /* "edit" or "input" */
56: mode = MODE_VI;
57: *o_inputmode = TRUE;
58: break;
59: #endif
60: default: /* "vi" or "elvis" */
61: mode = MODE_VI;
62: }
63:
64: #ifndef DEBUG
65: # ifdef SIGQUIT
66: /* normally, we ignore SIGQUIT. SIGINT is trapped later */
67: signal(SIGQUIT, SIG_IGN);
68: # endif
69: #endif
70:
71: /* temporarily ignore SIGINT */
72: signal(SIGINT, SIG_IGN);
73:
74: /* start curses */
75: initscr();
76: cbreak();
77: noecho();
78: scrollok(stdscr, TRUE);
79:
80: /* initialize the options */
81: initopts();
82:
83: /* map the arrow keys. The KU,KD,KL,and KR variables correspond to
84: * the :ku=: (etc.) termcap capabilities. The variables are defined
85: * as part of the curses package.
86: */
87: if (has_KU) mapkey(has_KU, "k", WHEN_VICMD|WHEN_INMV, "<Up>");
88: if (has_KD) mapkey(has_KD, "j", WHEN_VICMD|WHEN_INMV, "<Down>");
89: if (has_KL) mapkey(has_KL, "h", WHEN_VICMD|WHEN_INMV, "<Left>");
90: if (has_KR) mapkey(has_KR, "l", WHEN_VICMD|WHEN_INMV, "<Right>");
91: if (has_HM) mapkey(has_HM, "^", WHEN_VICMD|WHEN_INMV, "<Home>");
92: if (has_EN) mapkey(has_EN, "$", WHEN_VICMD|WHEN_INMV, "<End>");
93: if (has_PU) mapkey(has_PU, "\002", WHEN_VICMD|WHEN_INMV, "<PgUp>");
94: if (has_PD) mapkey(has_PD, "\006", WHEN_VICMD|WHEN_INMV, "<PgDn>");
95: #if MSDOS
96: if (*o_pcbios)
97: {
98: mapkey("#R", "i", WHEN_VICMD|WHEN_INMV, "<Insrt>");
99: mapkey("#S", "x", WHEN_VICMD|WHEN_INMV, "<Del>");
100: mapkey("#s", "B", WHEN_VICMD|WHEN_INMV, "^<left>");
101: mapkey("#t", "W", WHEN_VICMD|WHEN_INMV, "^<right>");
102: }
103: #else
104: if (ERASEKEY != '\177')
105: {
106: mapkey("\177", "x", WHEN_VICMD|WHEN_INMV, "<Del>");
107: }
108: #endif
109:
110: #ifndef NO_DIGRAPH
111: init_digraphs();
112: #endif /* NO_DIGRAPH */
113:
114: /* process any flags */
115: for (i = 1; i < argc && *argv[i] == '-'; i++)
116: {
117: switch (argv[i][1])
118: {
119: case 'R': /* readonly */
120: *o_readonly = TRUE;
121: break;
122:
123: case 'r': /* recover */
124: msg("Use the `virec` program to recover lost files");
125: endmsgs();
126: refresh();
127: endwin();
128: exit(0);
129: break;
130:
131: case 't': /* tag */
132: if (argv[i][2])
133: {
134: tag = argv[i] + 2;
135: }
136: else
137: {
138: i++;
139: tag = argv[i];
140: }
141: break;
142:
143: case 'v': /* vi mode */
144: mode = MODE_VI;
145: break;
146:
147: case 'e': /* ex mode */
148: mode = MODE_EX;
149: break;
150: #ifndef NO_EXTENSIONS
151: case 'i': /* input mode */
152: *o_inputmode = TRUE;
153: break;
154: #endif
155: #ifndef NO_ERRLIST
156: case 'm': /* use "errlist" as the errlist */
157: if (argv[i][2])
158: {
159: err = argv[i] + 2;
160: }
161: else if (i + 1 < argc)
162: {
163: i++;
164: err = argv[i];
165: }
166: else
167: {
168: err = "";
169: }
170: break;
171: #endif
172: default:
173: msg("Ignoring unknown flag \"%s\"", argv[i]);
174: }
175: }
176:
177: /* if we were given an initial ex command, save it... */
178: if (i < argc && *argv[i] == '+')
179: {
180: if (argv[i][1])
181: {
182: cmd = argv[i++] + 1;
183: }
184: else
185: {
186: cmd = "$"; /* "vi + file" means start at EOF */
187: i++;
188: }
189: }
190:
191: /* the remaining args are file names. */
192: nargs = argc - i;
193: if (nargs > 0)
194: {
195: #if ! ( MSDOS || TOS )
196: firstarg = argv[i];
197: #endif
198: strcpy(args, argv[i]);
199: while (++i < argc && strlen(args) + 1 + strlen(argv[i]) < sizeof args)
200: {
201: strcat(args, " ");
202: strcat(args, argv[i]);
203: }
204: }
205: #if ! ( MSDOS || TOS )
206: else
207: {
208: firstarg = "";
209: }
210: #endif
211: argno = 0;
212:
213: #if MSDOS || TOS
214: if (nargs > 0)
215: {
216: strcpy(args, wildcard(args));
217: nargs = 1;
218: for (i = 0; args[i]; i++)
219: {
220: if (args[i] == ' ')
221: {
222: nargs++;
223: }
224: }
225: for (i = 0; args[i] && args[i] != ' '; i++)
226: {
227: firstarg[i] = args[i];
228: }
229: firstarg[i] = '\0';
230: }
231: else
232: {
233: firstarg[0] = '\0';
234: }
235: #endif
236:
237: /* perform the .exrc files and EXINIT environment variable */
238: #ifdef SYSEXRC
239: doexrc(SYSEXRC);
240: #endif
241: #ifdef HMEXRC
242: str = getenv("HOME");
243: if (str)
244: {
245: sprintf(tmpblk.c, "%s%c%s", str, SLASH, HMEXRC);
246: doexrc(tmpblk.c);
247: }
248: #endif
249: doexrc(EXRC);
250: #ifdef EXINIT
251: str = getenv(EXINIT);
252: if (str)
253: {
254: exstring(str, strlen(str));
255: }
256: #endif
257:
258: /* search for a tag (or an error) now, if desired */
259: blkinit();
260: if (tag)
261: {
262: cmd_tag(MARK_FIRST, MARK_FIRST, CMD_TAG, 0, tag);
263: }
264: #ifndef NO_ERRLIST
265: else if (err)
266: {
267: cmd_errlist(MARK_FIRST, MARK_FIRST, CMD_ERRLIST, 0, err);
268: }
269: #endif
270:
271: /* if no tag/err, or tag failed, then start with first arg */
272: if (tmpfd < 0 && tmpstart(firstarg) == 0 && *origname)
273: {
274: ChangeText
275: {
276: }
277: clrflag(file, MODIFIED);
278: }
279:
280: /* now we do the immediate ex command that we noticed before */
281: if (cmd)
282: {
283: doexcmd(cmd);
284: }
285:
286: /* repeatedly call ex() or vi() (depending on the mode) until the
287: * mode is set to MODE_QUIT
288: */
289: while (mode != MODE_QUIT)
290: {
291: if (setjmp(jmpenv))
292: {
293: /* Maybe we just aborted a change? */
294: abortdo();
295: }
296: #if TURBOC
297: signal(SIGINT, (void(*)()) trapint);
298: #else
299: signal(SIGINT, trapint);
300: #endif
301:
302: switch (mode)
303: {
304: case MODE_VI:
305: vi();
306: break;
307:
308: case MODE_EX:
309: ex();
310: break;
311: #ifdef DEBUG
312: default:
313: msg("mode = %d?", mode);
314: mode = MODE_QUIT;
315: #endif
316: }
317: }
318:
319: /* free up the cut buffers */
320: cutend();
321:
322: /* end curses */
323: #ifndef NO_CURSORSHAPE
324: if (has_CQ)
325: do_CQ();
326: #endif
327: endmsgs();
328: move(LINES - 1, 0);
329: clrtoeol();
330: refresh();
331: endwin();
332:
333: exit(0);
334: /*NOTREACHED*/
335: }
336:
337:
338: /*ARGSUSED*/
339: int trapint(signo)
340: int signo;
341: {
342: resume_curses(FALSE);
343: abortdo();
344: #if OSK
345: sigmask(-1);
346: #endif
347: #if TURBO_C
348: signal(signo, (void (*)())trapint);
349: #else
350: signal(signo, trapint);
351: #endif
352: longjmp(jmpenv, 1);
353:
354: return 0;
355: }
356:
357:
358: #ifndef NO_DIGRAPH
359:
360: /* This stuff us used to build the default digraphs table. */
361: static char digtable[][4] =
362: {
363: # if CS_IBMPC
364: "C,\200", "u\"\1", "e'\2", "a^\3",
365: "a\"\4", "a`\5", "a@\6", "c,\7",
366: "e^\10", "e\"\211", "e`\12", "i\"\13",
367: "i^\14", "i`\15", "A\"\16", "A@\17",
368: "E'\20", "ae\21", "AE\22", "o^\23",
369: "o\"\24", "o`\25", "u^\26", "u`\27",
370: "y\"\30", "O\"\31", "U\"\32", "a'\240",
371: "i'!", "o'\"", "u'#", "n~$",
372: "N~%", "a-&", "o-'", "~?(",
373: "~!-", "\"<.", "\">/",
374: # endif /* CS_IBMPC */
375: # if CS_LATIN1
376: "~!!", "a-*", "\">+", "o-:",
377: "\"<>", "~??",
378:
379: "A`@", "A'A", "A^B", "A~C",
380: "A\"D", "A@E", "AEF", "C,G",
381: "E`H", "E'I", "E^J", "E\"K",
382: "I`L", "I'M", "I^N", "I\"O",
383: "-DP", "N~Q", "O`R", "O'S",
384: "O^T", "O~U", "O\"V", "O/X",
385: "U`Y", "U'Z", "U^[", "U\"\\",
386: "Y'_",
387:
388: "a``", "a'a", "a^b", "a~c",
389: "a\"d", "a@e", "aef", "c,g",
390: "e`h", "e'i", "e^j", "e\"k",
391: "i`l", "i'm", "i^n", "i\"o",
392: "-dp", "n~q", "o`r", "o's",
393: "o^t", "o~u", "o\"v", "o/x",
394: "u`y", "u'z", "u^{", "u\"|",
395: "y'~",
396: # endif /* CS_LATIN1 */
397: ""
398: };
399:
400: static init_digraphs()
401: {
402: int i;
403:
404: for (i = 0; *digtable[i]; i++)
405: {
406: do_digraph(FALSE, digtable[i]);
407: }
408: do_digraph(FALSE, (char *)0);
409: }
410: #endif /* NO_DIGRAPH */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.