[mod.sources] tvx: 8 of 10

sources-request@panda.UUCP (03/11/86)

Mod.sources:  Volume 4, Issue 22
Submitted by: gatech!unmvax!wampler (Bruce Wampler)

#--------CUT---------CUT---------CUT---------CUT--------#
#########################################################
#  TVX: File 8 of 10                                    #
#                                                       #
# This is a shell archive file.  To extract files:      #
#                                                       #
#    1)	Make a directory (like tvx) for the files.      #
#    2) Write a file, such as "filen.shar", containing  #
#       this archive file into the directory.           #
#    3) Type "sh file.shar".  Do not use csh.           #
#                                                       #
#########################################################
#
#
echo Extracting tvx_lex.c:
sed 's/^X//' >tvx_lex.c <<\SHAR_EOF
X/* -------------------------- tvx_lex.c --------------------------- */
X#include "tvx_defs.ic"
X
X/* -------------------------- GLOBALS GO HERE -------------------------------*/
X#define EXTERN
X
X#include "tvx_glbl.ic"
X
X   char clower(),cupper();
X
X/* =============================>>> CHECKOS <<<============================= */
X  checkos()
X  {
X	/* check if ok operating system */
X#ifdef MSDOS
X    if ((bdos(0x30,0) & 0xff) < 2)		/* !!! cii-86 dependent */
X      {
X	remark("TVX requires MS-DOS 2.0 or later");
X	exit();
X      }
X#endif
X  }
X
X/* =============================>>> STARTM <<<============================= */
X  startm()
X  {
X    prompt(START_IDM);
X    prompt(VERSION); prompt("Terminal: ");
X    remark(cversn);
X    remark("");
X    starthelp();
X  }
X
X/* =============================>>> STARTHELP <<<============================= */
X  starthelp()		/* print start help message */
X  {
X	remark(START_HELPM); remark("");
X  }
X
X
X/* =============================>>> MEMORY <<<============================= */
X  memory()
X  { /* memory - print memory left */
X 
X    SLOW int nxt;
X    SLOW unsigned int tmp;
X
X    char value[10],msg[85],*cp;
X 
X    if (bakflg)
X	return;			/* don't do this during logfile input */
X
X    nxt=0;			/* where message goes */
X    cp = (*dest_file ? dest_file : orig_file);
X    strcopy(cp,max(strlen(cp)-36,0),msg,&nxt);	/* the file name */
X    if (nxt <= 14)
X     {
X       strcopy(VERSION,0,msg,&nxt); /* TVX */
X       strcopy(cversn,0,msg,&nxt);  /* terminal type */
X     }
X 
X    strcopy(" Free chars:",0,msg,&nxt);	/* add ' Free chars: ' */
X
X#ifdef LASL
X    tmp = max(nxtsav - nxtchr - BUFFLIMIT,0);
X#else
X    tmp = nxtsav - nxtchr;
X#endif
X
X#ifdef INT16
X    if (tmp > 30000)		/* handle "neg" size */
X      {
X	msg[nxt++] = '+';
X	tmp -= 30000;
X      }
X#endif
X    itoa(tmp,value);
X    strcopy(value,0,msg,&nxt);	/* the value */
X 
X    strcopy(" Line:",0,msg,&nxt);	/* add ' Line: ' */
X    itoa(curlin,value);
X    strcopy(value,0,msg,&nxt);
X    strcopy(" of ",0,msg,&nxt);
X    itoa(nxtlin-1,value);
X    strcopy(value,0,msg,&nxt);	/* add the count */
X 
X 
X    tverr(msg); 	/* display line on screen */
X }
X 
X/* =============================>>> SHOSET  <<<============================= */
X  shoset()
X  {  /* show repeat buffer, help if available */
X
X#ifdef HELP
X    static char rp[2];
X    FAST int i;
X    SLOW char *cp, *msg;
X    SLOW int fields, oldtty, hnum;
X    SLOW unsigned tmp;
X
X#ifdef TVX_CMDSET
X#ifdef FULLHELP
X    struct help_msg 
X      {
X	char *hmsg;
X	char Vmsg;
X      };
X
X    static struct help_msg cmddes[] =	/* messages for help */
X      {
X	{"nApnd to sv buff", VSAPPEND},	{" Buffer beg     ",	VTOP},
X	{" File beg",	     VFBEGIN},	{"nChange chars   ",	VCHANGE},
X	{"nDown line      ", VDOWNLINE},{"nDown column",	VDOWNCOL},
X	{" Buffer end     ", VBOTTOM},	{"nEdit rpt buffer",	VEDITRPT},
X	{"nFind",            VSEARCH},	{" Find cross-buff",	VNEXT},
X	{" Get save buffer", VGET},	{" Unkill lastline",	VUNKILL},
X	{"nHalf page      ", VHALFP},	{"nInsert (to ESC)",	VINSERT},
X	{" Jump back",	     VJUMP},	{"nKill character ",	VDELNEXT},
X	{"nKill line      ", VKILLALL},	{"nLeft",		VLEFT},
X	{" Memory status  ", VMEMORY},	{"nNote location  ",	VNOTELOC},
X	{"nReset loc",	     VRETNOTE},	{"nOpen line      ",	VOPENLINE},
X	{" Call Opr system", VSYSTEM},	{"nPage",		VFLIP},
X	{" Print screen   ", VPRINTS},	{"nRight          ",    VRIGHT},
X	{" Restore rpt buf", VSTORERPT},{"nSave lines     ",	VSAVE},
X	{"nTidy, fill text", VTIDY},	{" Abort",		VABORT},
X	{"nUp             ", VUPLINE},	{"nUp column      ",	VUPCOL},
X	{" Verify screen",   VVERIFY},	{"nWrite buffer   ",	VWPAGE},
X	{" Exit, end edit ", VQUIT},	{"nYank file",		VYANK},
X	{"nDel prev char  ", VDELLAST},	{"nFind again     ",	VSAGAIN},
X	{" Del last",	     VREMOVE},	{" Change last    ",	VRMVINS},
X	{" Del to line beg", VKILLPREV},{" Del to line end",	VKILLREST},
X	{" Line begining  ", VBEGLINE},	{" Line end       ",	VENDLINE},
X	{"nWord right",	     VMVWORD},	{"nWord left      ",	VMVBWORD},
X	{"nRepeat again   ", VXREPEAT},	{"nk Exec rpt k n times",VEXECRPT},
X	{"n p Set param p ", VSETPARS},	{" Help           ",	VHELP},
X	{" Insert find pat", VINSPAT},	{"nToggle case    ",	VFOLDCASE},
X	{"/",0}			/* last variable entry */
X      };
X#endif
X#endif
X
X    if (bakflg)
X	return;			/* don't do this during logfile input */
X
X    oldtty = ttymode;
X    ttymode = FALSE;
X    if (!oldtty)
X	tvclr();
X
X    prompt("Parameter : cur val (1=y, 0=n)    Prev 16 cmds:");
X    for (hnum = 0,i = old_cindex ; hnum < 16 ; ++hnum)
X      {
X	shocout(old_cmds[i]);
X	i = ++i % 16;
X      }
X
X    remark("");
X    prompt("A-Autoindent: "); wtint(autoin);
X    prompt("  C-Cut mode: "); wtint(cut_mode);
X    prompt("  E-Expand tabs: "); wtint(tabspc);
X    prompt("  T-TTY mode: "); wtint(ttymode); remark("");
X
X    prompt("F-Find: ignore case: "); 
X	if (xcases)
X	    tvcout('0');
X	else
X	    tvcout('1');
X
X    prompt("    M-Match wild cards: "); wtint(use_wild); remark("");
X    prompt("U-User wild card set: |");
X    for (cp = user_set ; *cp ; ++cp)
X      {
X	shocout(*cp);
X      }
X    remark("|");
X
X    prompt("D disp line:"); wtint(dsplin); 
X    prompt("  S-Scroll window:"); wtint(scroll);
X    prompt("  V-Virtual window:"); wtint(tvlins); 
X	prompt("/"); wtint(tvhardlines);
X    prompt("  W-Wrap width:"); wtint(wraplm); remark("");
X    prompt("O-Output file: "); prompt(dest_file);
X    prompt("  (input file is: ");prompt(orig_file); remark(")");
X    remark("");
X
X    prompt("Find: |");
X    for (cp = sbuff ; *cp ; ++cp)
X      {
X	shocout(*cp);
X      }
X    remark("|");
X    remark("");
X    prompt("Max chars: ");
X    tmp = mxbuff;
X#ifdef INT16
X    if (tmp > 30000)		/* handle "neg" size */
X      {
X	prompt("30000+");
X	tmp -= 30000;
X      }
X#endif
X    wtint(tmp); prompt("  Max lines: ");    wtint(mxline);
X    prompt("  Cur line: "); wtint(curlin);
X    if (usecz)
X	prompt("    ^Z for EOF");
X    remark("");
X    remark("");
X
X    prompt("R-Repeat buffer: ");wtint(rptuse+1);
X    remark("   All repeat buffers : <contents>:");
X    for (i = 0 ; i < REPEATBUFS ; ++ i)
X      {
X	fields = 5;
X	shocout('#') ; shocout(i+'1') ; prompt(": <");
X	for (cp = &rptbuf[i][0] ; *cp ; ++cp)
X	  {
X	    shocout(*cp);
X	    ++fields;		/* how many letters */
X	    if (*cp < ' ')
X		++fields;
X	    if (fields >= (tvcols - 6))
X	      {
X		prompt("+more+");
X		break;
X	      }
X	  }
X	remark(">");
X      }
X
X    ttymode = oldtty;
X    memory();
X
X#ifdef FULLHELP
X    tvxy(1,22);
X
X    ask("Press space to exit, anything else for command list ",rp,1);
X
X    if (*rp == ' ')
X      {
X	ttymode = oldtty;
X	verify(1);
X	return;
X      }
X
X    if (!oldtty)
X	tvclr();
X
X/* ------------------------------ TVX ----------------------------------- */
X#ifdef TVX_EM
X    remark("Commands (n => count allowed):");
X#endif
X#ifdef TVX0M_EM
X    remark("Commands (n => count allowed) (Non ^ cmds prefixed by ESC):");
X#endif
X
X#ifdef TVX_CMDSET
X    for (hnum = fields = 0  ; ; ++hnum )
X      {
X	prompt("   ");
X	cp = cmddes[hnum].hmsg;
X	if (*cp == '/')	/* end of variable list */
X	    break;
X	else
X	    shocout(*cp);	/* show n or blank */
X	msg = ++cp;		/* where message is, skipping 'n' field */
X	while (*cp)		/* ship to lex value */
X	    ++cp;
X	i = cmddes[hnum].Vmsg;		/* get the lexical index */
X	shocout(cupper(lexsym[i]));	/* show the command */
X	if (lexsym[i] >= ' ')
X	    shocout(' ');	/* skip space for no '^' */
X
X	shocout(' ');		/* space to separate */
X	prompt(msg);		/* and show the message */
X	if (++fields == 3)	/* bump fields, see if need newline */
X	  {
X	    fields = 0;
X	    remark("");
X	  }
X      }
X    if (fields != 0)
X	remark("");
X#endif		
X#ifdef TVX_EM
X    remark("   n<>$$:Rpt loop        @:Invoke cmd file      $:Escape");
X#endif
X#ifdef TVX0M_EM
X    remark("  $n<>$$:Rpt loop       $@:Invoke cmd file      $:Escape");
X#endif
X
X/* ------------------------------ VI ----------------------------------- */
X#ifdef VI_EM
X    remark("Commands (n => count allowed):");
Xremark("");
Xremark("n^B:scrn up     n^D:half scrn   n^F:scrn dwn    ^G:status     ^L:refresh");
Xremark("n^U:up half scr n!:tidy         n#p:ex rpt p n   $:line end    *:ins last pat");
Xremark("/:search         =:help           ?:rev search  @:exec rpt lp");
Xremark("A:apnd ln end   C:chng rest ln  D:del rest line  nG:Goto ln n  H:buff beg");
Xremark("I:ins ln beg    J:join lines    nK:up: line beg  L:buff end    nM:ret to mark");
Xremark("N:rev find nxt  nO:open above   P:put sv buf abv");
Xremark("q:'tvx' prefix: q!:op system    qb:file begin    qu:limited undo"); 
Xremark("nq:p:set par p nqe:ed rpt buf   qj:jump back     qp:put file   qy: yank file");
Xremark("                qs:print scr    nqw:write buf   nqr:restore rpt q/:x-buff find");
Xremark("nX:del prev ch  nY:apnd sv buf  Z:[Z:exit,A:abort]             ^:line begin");
Xremark("a:append        nb:word left    c:chng [c,<sp>,^,$,/]      nd:del [d,<sp>,^,$,/]");
Xremark("ni:insert       nh:left         nj:down in col   nk:up line in col");
Xremark("nl:right        nm:mark loc     n:find next pat  no:open after");
Xremark("p:put sv buf after              r:replace 1 chr  ns:substitute");
Xremark("nw:word right   nx:delete chr   ny:yank to save buffer          n~:change case");
X    remark("");
Xremark("n<>$$:Rpt loop  _:Invoke cmd file   $:Escape");
X    remark("'c/' and 'd/' are used to change/delete last thing found");
X#endif
X
X/* ------------------------------ EMAX ----------------------------------- */
X#ifdef EMAX_EM
Xremark("(n means count allowed: counts entered after <esc> or <ctrl-u>)");
Xremark("");
Xremark("^A:line beg    n^B:back chrs                 n^C:extended tvx commands:");
Xremark("");
Xremark("[n^A:apnd sv   ^B: file beg   n^C:chng chrs  n^E:Ed rpt bf   n^F:fill        ]");
Xremark("[ ^G:no op    n^H:half scrn    ^J:jmp back    ^K:kill 'last'  n^N:next ln    ]");
Xremark("[n^M:mark loc n^P:Prev ln      ^R:Restore rbf ^W:write buff    ;:search again]");
Xremark("[n~:chng case  nG:Goto line    nH:Half pg up  nI:ins val n     L: Print scrn ]");
Xremark("[nM:rtn 2 mrk  nP:Put sv bf     S:x buff find  U:unkill 1 ln nVp:set val(par)]");
Xremark("[ R:Read file into sv buff      W:write sv buff to file   *:insert found pat ]");
Xremark("");
Xremark("n^D:del chr    ^E:line end    n^F:fwrd chr   n^H:del prev ch  n^K:kill line");
Xremark(" ^L:repaint   n^N:next ln     n^O:open ln    n^P:prev ln       ^R:rev search");
Xremark(" ^S:search     ^U:specify n  n^V:page dwn   ^X^C:abort edit");
Xremark("^X^B:status  n^XE:ex. rpt bf  ^Y:yank sv bf   ^Z:write, exit");
Xremark(" $%:cmd file   $!:op. sys.   n$#p:ex rpt p   n$(:rpt loop      $<:buff begin");
Xremark(" $>:buff end   $?:help        n$B:back word  n$F:fwd word     n$V:page up");
Xremark("");
Xremark("$ = <esc>,  ')$$' ends repeat loops");
X#endif
X
X
X#ifdef GEMDOS
X    remark("Find wild cards:  {TVX command '(' toggles 25/50 line display}");
X#else
X    remark("Find wild cards:");
X#endif
Xremark("^A-alphanumeric  ^D-digit  ^L-letter  ^O-other,(not-^A)  ^P-punctuation");
Xremark("^X-any character ^U-user set  -- ^W-word of ^..  ^N-not in word of ^..");
X
X#endif
X
X    if (!oldtty)
X	tvxy(1,24);
X    ask("Press any key to resume ",rp,1);
X
X    ttymode = oldtty;
X
X    verify(1);
X#else				/* HELP not defined */
X    tverr(&rptbuf[rptuse][0]);
X#endif
X  }
X
X/* =============================>>> SHOCOUT <<<============================= */
X  shocout(c)
X  char c;
X  {
X
X    if (c < ' ')
X      {
X	ttwt('^'); ttwt(c + '@');
X      }
X    else
X	ttwt(c);
X  }
X
X/* =============================>>> LEXGET <<<============================= */
X  lexget(chr)
X  char *chr;
X  {  /* lexget - get a character for lex, possibly from repeat buffer */
X
X    SLOW char tmp;
Xl10:
X    if (rptcnt[rptuse] > 0)	/* in a repeat buffer? */
X      {
X	*chr=rptbuf[rptuse][nxtrpt[rptuse]];	/* pick up from repeat buffer */
X	if (*chr == 0) 	/* at end of rpt buff */
X	  {
X	    nxtrpt[rptuse] = 0;	/* start <> loop over */
X	    if (--rptcnt[rptuse] == 0 && !echof)	/* all done with loop */
X	      {
X		echof = TRUE;	/* turn on echo again */
X		newscr();	/* update screen after repeat */
X	      }
X	    goto l10;		/* loop again */
X	  }
X	++nxtrpt[rptuse];	/* bump to next char in loop */
X      }
X    else			/* not in loop, get from keyboard */
X      {
X	gkbd(&tmp);	/* picks up one character from the keyboard */
X	*chr = old_cmds[old_cindex] = tmp;
X	old_cindex = ++old_cindex % 16;
X      }
X  }
X
X/* =============================>>> LEX    <<<============================= */
X  lex(lexval,lexcnt,lexchr,parsok)
X  int *lexval,*lexcnt,parsok;
X  char *lexchr;
X  { /* ##  lex - gets command input from terminal, and scans for
X       #  its lexical value.  Returns a count if given.  Also handles
X       #  repeat loops. */
X 
X    SLOW int count, lex_default;
X    FAST int i;
X    SLOW int neg, newln;
X
X    static char chr,cmdchr,tchr;
X#ifdef EMAX_EM
X    SLOW char had_cu;
X#endif
X
X    lex_default = TRUE;
X
X    if (!parsok)		/* abort if error in <> */
X      {
X	if (rptcnt[rptuse] > 0)	/* in loop? */
X	  {
X	    newscr();	/* clear screen, send message */
X	    tverrb("<> not complete ");
X	  }
X	rptcnt[rptuse]=0;	/* abort loop if going */
X	nxtrpt[rptuse]=0;
X      }
Xl10:
X    for (;;) 
X      { 			/* need this loop to support <> */
X	count = 1;		/* default count is 1 */
X	lexget(&chr);		/* fetch a character */
X#ifdef EMAX_EM
X	had_cu = FALSE;		/* not ^U initially */
XCU_COUNT:
X	if (chr == 21)		/* ctrl-u count detect */
X	  {
X	    if (had_cu)
X		fixend();
X	    count *= 4;		/* assume 4 by default */
X	    tvmsg("Arg: ",FALSE); /* echo Arg: 4' */
X	    wtint(count);
X	    had_cu = TRUE;	/* remember we had control-u */
X	    lex_default = FALSE; /* and not the default */
X	    lexget(&chr);
X	  }
X#endif
X#ifdef NOMODE_LEX
X	if ( ((chr & 0177) >= ' ' || chr == TAB || chr == CR)
X	  && (chr & 0200) == 0)
X	  {
X#ifdef EMAX_EM
X	    if (had_cu)
X	      {
X		had_cu = FALSE;
X		fixend();
X		if ((chr >= '0' && chr <= '9') || chr == '-')
X		    goto EMAX_CNT;
X	      }
X	    for (i = 0 ; i < count ; ++i)	/* ^U times */
X#endif
X	    ins_chr((int) chr);	/* simply insert the character */
X	    continue;		/* get next character */
X	  }
X	if (chr == escape_chr)	/* if an escape, simply get next char */
X	    lexget(&chr);
X#endif
X
X	if (rptcnt[rptuse]>0 && chr == loop_beg)	/* detect nesting */
X	  {
X	    nxtrpt[rptuse] = 0 ; rptcnt[rptuse] = 0 ; echof=TRUE;
X	    newscr();	/* update anything so far */
X	    tverrb("No loop nesting ");
X	    continue;
X	  }
X 
X#ifdef EMAX_EM
XEMAX_CNT:
X#endif
X	if ((chr>='0' && chr<='9') || chr=='-')	/* a number */
X	  {
X	    count = 0;  lex_default = FALSE;
X	    neg = FALSE;	/* handle negative counts */
X	    if (chr=='-')
X		neg=TRUE;
X	    else 
X		count = chr-'0';	/* convert to int value */
X	    for (;;) 
X	      {
X		if (rptcnt[rptuse] > 0)	/* have to handle rptbuf special */
X		  {
X		    if ((chr=rptbuf[rptuse][nxtrpt[rptuse]]) == 0)
X			break;
X		    ++nxtrpt[rptuse];
X		  }
X		else 
X		    lexget(&chr);
X		if (chr>='0' && chr<='9')	/* another number? */
X		    count = count*10+chr-'0';
X		else			/* done with number */
X		    break;
X	      }
X	    if (neg)			/* fix if it was negative */
X		count = min(-count ,-1);
X	  }	/* end count arg if */
X
X#ifdef EMAX_EM
X	if (chr == 21)		/* another ^U? */
X	    goto CU_COUNT;
X	if (had_cu)
X	    fixend();	/* count changes */
X#endif
X
X#ifdef VI_EM
X	cmdchr = chr;		/* vi emulator is case sensitive */
X#else
X	cmdchr = clower(chr);	/* fold to one case */
X#endif
X	if (cmdchr == loop_beg)	/* starting a loop? */
X	  {
X	    lex_default = TRUE;			/* don't let lex count be def */
X	    rptcnt[rptuse] = (count < 0) ? (-count) : count;	/* save count */
X	    ins_mode = TRUE;			/* so ttymode works */
X	    tvmsg("repeat[",FALSE);		/* echo 'repeat[k]: n<' */
X	    wtint(rptuse+1); prompt("]: ");
X	    wtint(rptcnt[rptuse]);
X
X	    tvcout(loop_beg);
X#ifdef SCR_BUF
X	    ttflush();
X#endif
X	    nxtrpt[rptuse]=0;	/* begin inserting at beginning */
X	    newln = FALSE;	/* no new line echo yet */
X	    do			/* fetch repeat chars until get > */
X	      {
X		gkbd(&chr);	/* fetch a char */
X		if (chr==delkey)	/* allow editing */
X		  {
X		    if (nxtrpt[rptuse] > 0)	/* don't go past start */
X		      {
X			--nxtrpt[rptuse];	/* wipe out last */
X			if ((tchr = rptbuf[rptuse][nxtrpt[rptuse]])==CR)
X			  {
X			    ctrlch(CR);	/* going to newline */
X			    newln = TRUE;		/* new line now */
X			  }
X			else if (!newln)
X			  {
X			    tvcout(BACKSPACE);	/* back over character */
X			    tvcout(' ');
X			    tvcout(BACKSPACE);
X			    if (tchr < ' ' && tchr != 27)
X			      {
X				tvcout(BACKSPACE);	/* back over char */
X				tvcout(' ');
X				tvcout(BACKSPACE);
X			      }
X			  }
X			else		/* have passed new line start */
X			  {
X			    ctrlch(rptbuf[rptuse][nxtrpt[rptuse]]);
X			    tvcout('\\');
X			  }
X		      }
X		    else
X			tvcout(BELL);	/* trying to rubout too much */
X#ifdef SCR_BUF
X		    ttflush();
X#endif
X		    continue;
X		  }
X		else		/* a control character detected */
X		    ctrlch(chr);	/* echo */
X#ifdef SCR_BUF
X		ttflush();
X#endif
X 
X		rptbuf[rptuse][nxtrpt[rptuse]]=chr;	/* stuff in current rpt buff. */
X		++nxtrpt[rptuse];	/* bump count */
X		if (nxtrpt[rptuse] >= 100)	/* only allow 100 chars! */
X		  {
X		    newscr();
X		    tverrb("100 chars only");
X		    nxtrpt[rptuse]=0 ; rptcnt[rptuse]=0;
X		    ins_mode = FALSE;
X		    goto l10;	/* bail out */
X		  }
X	      }
X	    while (!( chr==ESC && rptbuf[rptuse][nxtrpt[rptuse]-2]==ESC &&
X	      rptbuf[rptuse][nxtrpt[rptuse]-3]==loop_end));	/* end do loop */
X
X	    ins_mode = FALSE;		/* get ttymode right */
X
X	    if (rptcnt[rptuse] > 1)	/* positive count? */
X		echof = FALSE;	/* turn off echoing */
X	    else if (newln)
X		verify();	/* need to fix up screen because of newline */
X	    else		/* 0 or 1 count */
X	      {
X		fixend();
X		tvhdln();	/* get back where we were */
X	      }
X
X	    rptbuf[rptuse][nxtrpt[rptuse]-3] = 0;	/* mark with eos */
X	    nxtrpt[rptuse]=0;	/* back for scan now */
X	    continue;		/* now execute the loop */
X	  }
X#ifdef VB
X	else if (cmdchr == lexsym[0])	/*$$$	indirect files! */
X	  {
X	    opnatf();
X	    continue;
X	  }
X#endif
X	for (i=0 ; synofr[i]!=0 ; ++i)
X	  if (synofr[i]==cmdchr)
X	     cmdchr=synoto[i];		/* allow synonyms */
X 
X	*lexval = UNKNOWN;	/* assume unknown command */
X	for (i = 1 ; i<= LEXVALUES ; ++i)	/* scan all possible cmds */
X	    if (cmdchr == lexsym[i])	/* found it */
X	      {
X		*lexval = i;
X		break;
X	      }
X	*lexcnt = count;		/* return good stuff */
X	*lexchr = chr;
X	return (lex_default);		/* let know if gave back default */
X      }					/* end of for(;;) */
X  }
X/* -------------------------- tvx_lex.c --------------------------- */
SHAR_EOF
echo Extracting tvx_cfg.c:
sed 's/^X//' >tvx_cfg.c <<\SHAR_EOF
X
X/* -------------------------- tvx_cfg.c --------------------------- */
X#include "tvx_defs.ic"
X
X#define BL remark("")
X
X    char synofr[20] =	/* from table */
X      {' ',13,']',000,000,000,000,000,000,000,00,00,00,00,00,00,00,00,00,00};
X    char synoto[20] =		/* translate to table */
X      {'r','d','{',00,000,0,000,00,00,000,00,00,00,00,00,00,00,00,00,00};
X    char funkey = 0;		/* leading char for function key */
X    char funchar[50] =	/* code sent by function key */
X      {
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X      };
X    char funcmd[50] =	/* equivalent command */
X      {
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X	000, 000, 000, 000, 000, 000, 000, 000, 000, 000,
X      };
X
X/* define standard command set */
X
X    char lexsym[LEXVALUES+1] = { E0, 'r', 'l', 'd', 'u',
X      4, 21, 8, 'k', 'i', 11, '"', '\'', ',', '.', 'f', 6, 'p',
X      'b', 'e', 2, 'v', 'o', '/', 's', 'g', 23, 25, 24, ';', '&',
X      'm', ':', '=', 7, 9, '{', 'a', 16, '?', 'h', 20, 'c', 'j', 't',
X      'n', 14, 15, 5, 18, '#', '*', '(', ')','~' };
X
X
X    char autoin, dsplin, scroll, xcases, warplm, wildch, funesc, cut_mode;
X    char rp[80];
X
X    FILE *f, *fopen();
X    char cupper(), clower();
X
X  main()
X  {
X
X    SLOW int i, val, retcode;
X
X    cls();
X    remark("Standard TVX define a configuration file -- Version 2/27/86");
X    BL;
X    for (;;)
X      {
X	prompt("Enter name of file to save configuration in: ");
X	reply(rp,79);
X	if ((f = fopen(rp,FILEWRITE)) == 0)
X	    continue;
X	else
X	    break;
X      }
X
X
X    cls();
X    shoset();
X    BL;
X    for (;;)
X      {
X	BL;
X	prompt("Use standard command definitions? (y/n) ");
X	lreply(rp,10);
X	if (*rp == 'y')
X	  {
X	    goto LEXDONE;
X	  }
X	else if (*rp == 'n')
X	    break;
X      }
X
XCMDAGAIN:
X    retcode = 1;		/* start with things ok */
X    for (;;)
X      {
X	short_cls();
X	shoset();
X	if (retcode < 0)
X	    remark("Invalid value supplied for new command.  Try again!");
X	if ((retcode = set()) == 0)
X	    break;
X      }
X    short_cls();
X    shoset();
X    remark("");
X    prompt("Are you finished setting commands? (y/n) ");
X    ureply(rp,2);
X    if (*rp != 'Y')
X	goto CMDAGAIN;
X    
X
X    
X
XLEXDONE:
X    for (i=0 ; i <= LEXVALUES ; ++i)	/* write out lex symbols */
X      {
X	fputc(lexsym[i],f);		/* write to file */
X      }
X	syno();
X	funkeys();
X
X    cls();
X    prompt("Use autoindent (n default) (y/n): ");
X    lreply(rp,10);
X    if (*rp == 'y')
X	fputc(1,f);
X    else 
X	fputc(0,f);
X
X    BL;
X    prompt("Home display line: (1-66, 16 default): ");
X    rdint(&val);
X    if (val > 66 || val <= 0)
X	fputc(16,f);
X    else
X    	fputc(val,f);
X
X    BL;
X    prompt("Scroll window (0 default): ");
X    rdint(&val);
X    if (val > 24)
X	val = 0;
X    fputc(val,f);
X
X    BL;
X    prompt("Find case (e=exact,a=any, any default): "); 
X    lreply(rp,10);
X    if (*rp == 'e')
X        fputc(1,f);
X    else
X        fputc(0,f);
X
X    BL;
X
X    prompt("Auto line wrap width (0 default): ");
X    rdint(&val);
X    if (val > 79)
X	val = 0;
X    fputc(val,f);
X
X    BL;
X    prompt("Use wild cards (y default) (y/n)? ");
X    lreply(rp,10);
X    if (*rp == 'n')
X	fputc(0,f);
X    else 
X	fputc(1,f);
X
X    BL;
X    prompt("Use BACKUP.LOG file (n default) (y/n)? ");
X    lreply(rp,10);
X    if (*rp == 'y')
X        fputc(1,f);
X    else
X        fputc(0,f);
X    
X    BL;
Xprompt("Use 'cut mode' (killed lines to save buffer too)? (n default) (y/n)? ");
X    lreply(rp,10);
X    if (*rp == 'y')
X        fputc(1,f);
X    else
X        fputc(0,f);
X
X#ifdef MSDOS
X    BL;
X    remark("The editor can recognize Ctrl-z as EOF, or it can ignore ^Z and");
X    remark("just use the standard MS-DOS end of file mark.");
X    prompt("Should the editor recognize Ctrl-Z as EOF? (n default) (y/n) ");
X    lreply(rp,10);
X    if (*rp == 'y')
X        fputc(1,f);
X    else
X        fputc(0,f);
X#endif
X#ifdef GEMDOS
X    fputc(1,f);		/* use ^Z on gemdos by default */
X#endif
X
X    cls();
X    remark("Configuration file created.");
X    fclose(f);
X  }
X
X/* =============================>>> SHOSET  <<<============================= */
X  shoset()
X  {  /* show repeat buffer, help if available */
X
X    static char rp[2];
X    FAST int i;
X    SLOW char *cp, *msg;
X    SLOW int fields, oldtty, hnum;
X    SLOW unsigned tmp;
X
X    struct help_msg 
X      {
X	char *hmsg;
X	char Vmsg;
X      };
X
X    static struct help_msg cmddes[] =	/* messages for help */
X      {
X	{"nApnd to sv buff", VSAPPEND},	{" Buffer beg     ",	VTOP},
X	{" File beg",	     VFBEGIN},	{"nChange chars   ",	VCHANGE},
X	{"nDown line      ", VDOWNLINE},{"nDown column",	VDOWNCOL},
X	{" Buffer end     ", VBOTTOM},	{"nEdit rpt buffer",	VEDITRPT},
X	{"nFind",            VSEARCH},	{" Find cross-buff",	VNEXT},
X	{" Get save buffer", VGET},	{" Unkill lastline",	VUNKILL},
X	{"nHalf page      ", VHALFP},	{"nInsert (to ESC)",	VINSERT},
X	{" Jump back",	     VJUMP},	{"nKill character ",	VDELNEXT},
X	{"nKill line      ", VKILLALL},	{"nLeft",		VLEFT},
X	{" Memory status  ", VMEMORY},	{"nNote location  ",	VNOTELOC},
X	{"nReset loc",	     VRETNOTE},	{"nOpen line      ",	VOPENLINE},
X	{" Call Opr system", VSYSTEM},	{"nPage",		VFLIP},
X	{" Print screen   ", VPRINTS},	{"nRight          ",    VRIGHT},
X	{" Restore rpt buf", VSTORERPT},{"nSave lines     ",	VSAVE},
X	{"nTidy, fill text", VTIDY},	{" Abort",		VABORT},
X	{"nUp             ", VUPLINE},	{"nUp column      ",	VUPCOL},
X	{" Verify screen",   VVERIFY},	{"nWrite buffer   ",	VWPAGE},
X	{" Exit, end edit ", VQUIT},	{"nYank file",		VYANK},
X	{"nDel prev char  ", VDELLAST},	{"nFind again     ",	VSAGAIN},
X	{" Del last",	     VREMOVE},	{" Change last    ",	VRMVINS},
X	{" Del to line beg", VKILLPREV},{" Del to line end",	VKILLREST},
X	{" Line begining  ", VBEGLINE},	{" Line end       ",	VENDLINE},
X	{"nWord right",	     VMVWORD},	{"nWord left      ",	VMVBWORD},
X	{"nRepeat again   ", VXREPEAT},	{"nk Exec rpt k n times",VEXECRPT},
X	{"n p Set param p ", VSETPARS},	{" Help           ",	VHELP},
X	{" Insert find pat",	 VINSPAT},{"nChange case      ",VFOLDCASE},
X	{"/",0}			/* last variable entry */
X      };
X
Xremark("Commands settable by this program:  (n => count allowed):");
X    for (hnum = fields = 0  ; ; ++hnum )
X      {
X	prompt("   ");
X	cp = cmddes[hnum].hmsg;
X	if (*cp == '/')	/* end of variable list */
X	    break;
X	else
X	    shocout(*cp);	/* show n or blank */
X	msg = ++cp;		/* where message is, skipping 'n' field */
X	while (*cp)		/* ship to lex value */
X	    ++cp;
X	i = cmddes[hnum].Vmsg;		/* get the lexical index */
X	shocout(cupper(lexsym[i]));	/* show the command */
X	if (lexsym[i] >= ' ')
X	    shocout(' ');	/* skip space for no '^' */
X
X	shocout(' ');		/* space to separate */
X	prompt(msg);		/* and show the message */
X	if (++fields == 3)	/* bump fields, see if need newline */
X	  {
X	    fields = 0;
X	    remark("");
X	  }
X      }
X    remark("");
Xremark("Note: <> repeat, @ command file, and ESCAPE cannot be changed.");
X  }
X
X/* =============================>>> SHOCOUT <<<============================= */
X  shocout(c)
X  char c;
X  {
X
X    if (c < ' ')
X      {
X	printf("^%c",c + '@');
X      }
X    else
X	printf("%c",c);
X  }
X
X/* ===============================>>> FUNKEYS <<<========================*/
X  funkeys()
X  {
X
X    SLOW int j,i,val;
X    SLOW int fun;
X
XFAGAIN:
X    cls();
X    remark("You may now define up to 49 function keys to be translated to");
X    remark("commands OR letters.  This translation will take place before");
X    remark("the editor gets the character at any level  -- thus the translation");
X    remark("will apply equally to command mode and insert mode.  The translation");
X    remark("assumes each function key generates a 2 character sequence.  The");
X    remark("first character is an 'escape' character that must be the same for");
X    remark("each key.  If the 'escape' character is really ESC, then you must");
X    remark("also define one function key to have ESC as its translation value.");
X    remark("When asked for the function key, simply press the key, followed by");
X    remark("RETURN.  Enter either the character or decimal value of the translation.");
X
X    for (i = 0 ; i < 50 ; ++i)
X      {
X	funchar[i] = funcmd[i] = 0;
X      }
X
X    BL;
X    prompt("Do you want to define any function keys? (y/n) ");
X    lreply(rp,10);
X    if (*rp == 'n')
X	goto WTFUN;
X
X    BL;
X    remark("Now, please press ANY function key so the program can identify");
X    prompt("the 'function key escape' code (followed by a RETURN): ");
X    reply(rp,10);
X    funesc = *rp;		/* this should be the escape char */
X    if (funesc == 27)
X      {
X	BL;
X	remark("IMPORTANT:  You MUST define a function key to send an ESCAPE (decimal 27).");
X	remark("If you don't, then you won't be able to end insert mode or repeat loops.");
X	remark("The program doesn't have logic to make sure you do this, so don't forget!");
X	BL;
X      }
X
X    for (i = 0 ; i < 50 ; ++i)
X      {
XFUNAGAIN:
X	prompt("Press function key to define (RETURN only to exit): ");
X 	rp[1] = 0;
X	reply(rp,10);
X	fun = rp[1];
X	if (rp[1] == 0)
X	    break;
X	for (j = 0 ; j < 50 ; ++j)
X	  {
X	    if (fun == funchar[j])
X	      {
X		remark("That's been used already, try again.");
X		goto FUNAGAIN;
X	      }
X	  }
X	funchar[i] = fun;
X	prompt("Now enter the character/command it gets translated to: ");
X	reply(rp,10);
X	val = getval(rp);
X	funcmd[i] = val;
X      }
X
X    cls();
Xremark("Functions have been defined. You can start over if you made any mistakes.");
X    remark("");
X    prompt("Are they ok? (y/n) ");
X    lreply(rp,10);
X    if (*rp == 'n')
X	goto FAGAIN;
X
XWTFUN:
X    for (i = 0 ; i < 50 ; ++i)
X      {
X	fputc(funchar[i],f);
X      }
X    for (i = 0 ; i < 50 ; ++i)
X      {
X	fputc(funcmd[i],f);
X      }
X    fputc(funesc,f);
X  }
X  
X
X/* ===============================>>> GETVAL <<<========================*/
X  getval(str)
X  char *str;
X  {
X    /* return one byte value */
X
X    if (*str >= '0' && *str <= '9')
X	return (atoi(str));
X    else
X	return (*str & 0377);
X  }
X
X/* ===============================>>> SET <<<========================*/
X  set()
X  {
X	/* set newlex[indx] to a new value */
X
X    SLOW int val,i, oldi;
X
XSAGAIN:
Xprompt("Enter current command to change (key or decimal value, RETURN to exit) ");
X    reply(rp,10);
X    val = clower(getval(rp));
X
X    if (val == 0)
X      {
X	return 0;
X      }
X    for (oldi = 1 ; oldi <= LEXVALUES ; ++oldi)
X      {
X	if (val == lexsym[oldi])
X	  {
X	    goto HAVEIT;
X	  }
X      }
X    
X    return -1;	
X    
XHAVEIT:
X    prompt("Enter NEW command (key or decimal value, RETURN to exit) ");
X    reply(rp,10);
X    val = clower(getval(rp));
X    if (val == 0 || val == '@' || val == 27 || val == '<' || val == '>')
X	return -1;
X    for (i = 1 ; i <= LEXVALUES ; ++i)
X      {
X	if (val == lexsym[i])
X	  {
X	    return -1;		/* duplicate */
X	  }
X      }
X    lexsym[oldi] = val;
X    return 1;
X  }
X
X/* ===============================>>> SYNO <<<========================*/
X  syno()
X  {
X
X    SLOW int j, i, valfrom, valto, found;
X    
XSAGAIN:
X    cls();
X    remark("You may now define up to 19 synonyms.  For example, you might");
X    remark("want to define a space to be a synonym for right, or RETURN");
X    remark("the same as down.  You must use unused values, however.  You");
X    remark("can't use a existing command as a synonym.  You may enter the");
X    remark("character followed by a RETURN, or the decimal value of the key.");
X
X    for (i = 0 ; i < 20 ; ++i)
X      {
X	synofr[i] = synoto[i] = 0;
X      }
X
X    for (i = 0 ; i < 19 ; ++i)
X      {
XSYNAGAIN:
X	BL;
X	prompt("Enter the new synonym (RETURN when done): ");
X	reply(rp,10);
X	valfrom = getval(rp);
X	if (valfrom == 0)
X	    break;
X	for (j = 1 ; j <= LEXVALUES ; ++j)
X	  {
X	    if (lexsym[j] == valfrom)
X	      {
X		remark("That is already a command! Try again.");
X		goto SYNAGAIN;
X	      }
X	  }
X	prompt("Enter the equivalent command: ");
X	reply(rp,10);
X	valto = getval(rp);
X	for (j = 1, found = FALSE ; j <= LEXVALUES ; ++j)
X	  {
X	    if (lexsym[j] == valto)
X	        found = TRUE;
X	  }
X	if (!found)
X	  {
X	    remark("That is not a defined command. Try again.");
X	    goto SYNAGAIN;
X	  }
X
X	synofr[i] = valfrom;
X	synoto[i] = valto;
X      }
X    cls();
X
Xremark("Synonyms have been defined. You can start over if you made any mistakes.");
X    remark("");
X    prompt("Are they ok? (y/n) ");
X    lreply(rp,10);
X    if (*rp == 'n')
X	goto SAGAIN;
X
X    for (i = 0 ; i < 20 ; ++i)
X        fputc(synofr[i],f);
X    for (i = 0 ; i < 20 ; ++i)
X        fputc(synoto[i],f);
X
X  }
X
X/* ===============================>>> CLS <<<========================*/
X  cls()
X  {
X    int i;
X    for (i = 0 ; i < 25 ; ++i)
X	remark("");
X  }
X
X/* ===============================>>> short_CLS <<<========================*/
X  short_cls()
X  {
X    int i;
X    for (i = 0 ; i < 10 ; ++i)
X	remark("");
X  }
X
X#define EXTENDED	/* my own extended lib functions */
X/* #define STANDARD	/* the set of standard functions i use */
X#define LOCAL static	/* make all local globals, i think */
X
X#ifdef EXTENDED
X/*=============================>>> CLOWER  <<<================================*/
X  char clower(ch)
X  char ch;
X  {
X    return ((ch >='A' && ch<='Z') ? ch + ' ' : ch);
X  }
X
X/*=============================>>> CUPPER  <<<================================*/
X  char cupper(ch)
X  char ch;
X  {
X    return ((ch >= 'a' && ch <= 'z') ? ch - ' ' : ch);
X  }
X
X/* =========================>>> LOWER  <<<==============================*/
X  lower(str)
X  char str[];
X  {
X    SLOW int i;
X
X    for (i=0 ; str[i] ; ++i)
X	str[i]=clower(str[i]);
X
X  }
X
X/*=============================>>> PROMPT <<<================================*/
X  prompt(msg)
X  char msg[];
X  {
X    printf("%s",msg);
X  }
X
X
X/*=============================>>> REMARK <<<================================*/
X  remark(msg)
X  char msg[];
X  {
X    printf("%s\n",msg);
X  }
X
X/*=============================>>> UPPER  <<<================================*/
X  upper(str)
X  char str[];
X  {
X    static int i;
X
X    for (i=0 ; str[i] ; ++i)
X	str[i]=cupper(str[i]);
X  }
X
X
X/*=============================>>> LREPLY <<<================================*/
X  lreply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X    reply(msg,maxc);
X    lower(msg);
X  }
X
X/*=============================>>> UREPLY <<<================================*/
X  ureply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X    reply(msg,maxc);
X    upper(msg);
X  }
X
X/*=============================>>> REPLY <<<================================*/
X  reply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X#ifdef UNIX
X    gets(msg);
X#else
X    mreply(msg,maxc);
X#endif
X  }
X
X/*=============================>>> RDINT <<<================================*/
X  rdint(val)
X  int *val;
X  {
X    char chrrep[12];
X    reply(chrrep,11);
X    *val = atoi(chrrep);
X  }
X#endif
X#ifndef UNIX
X/*=============================>>> MREPLY <<<================================*/
X  mreply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X#define CBS 8		/* Backspace */
X#define CDL1 21		/* ^U */
X#define CDL2 24		/* ^X */
X#define CABORT 3	/* ^C */
X#define CRET 13		/* cr */
X#define BACKSPACE 8
X
X    static char ch, rp;
X    static int i;
X
X
X    for (i = 0 ; i < maxc ; )	/* i -> next char */
X      {
X	ch = ttrd_(); 	/* read the character */
X	if (ch == CBS)		/* back space */
X	  {
X	    if (i > 0)		/* must be something to delete */
X	      {
X		--i;		/* wipe out char */
X		ttwt_(BACKSPACE); ttwt_(' '); ttwt_(BACKSPACE);
X		if (msg[i] < ' ')	/* double echo ^ chrs */
X		  {
X		    ttwt_(BACKSPACE); ttwt_(' '); ttwt_(BACKSPACE);
X		  }
X	      }
X	  }
X#ifdef USE_WIPE
X	else if (ch == CDL1 || ch == CDL2)	/* wipe whole line */
X	  {
X	    i = 0;		/* set for loop ++ */
X	    remark("#");
X	    prompt("Re-enter? ");
X	  }
X#endif
X	else if (ch == CABORT)
X	  {
X	    remark("^C");
X	    prompt("Exit to operating system - are you sure? (y/n) ");
X	    rp = ttrd_();
X	    if (rp == 'y' || rp =='Y')
X	     {
X		remark("y");
X		exit(0);
X	     }
X	    remark("n");
X	    msg[i] = 0;
X	    prompt("Re-enter? "); prompt(msg);		/* re-echo */
X	  }
X	else if (ch == CRET)		/* ret, so done */
X	  {
X	    remark("");
X	    msg[i] = 0;
X	    return;
X	  }
X	else
X	  {
X	    msg[i++] = ch;
X	    msg[i] = 0;			/* always 0 terminate */
X	    if (ch < ' ')
X	      {
X		ch += '@';
X		ttwt_('^');
X	      }
X	    ttwt_(ch);			/* echo char */
X	  }
X      } /* end for */
X
X    remark("");
X  }
X
X/*=============================>>> ttrd_ <<<================================*/
X  ttrd_()
X  {
X#ifdef MSDOS
X	return (bdos(7,-1) & 0377);
X#endif
X#ifdef GEMDOS
X	return (gemdos(7) & 0377);
X#endif
X  }
X
X/*=============================>>> ttwt_ <<<================================*/
X  ttwt_(c)
X  char c;
X  {
X    fprintf(stderr,"%c",c);
X  }
X#endif
X/* -------------------------- tvx_cfg.c --------------------------- */
SHAR_EOF
echo Extracting tvx_ptch.c:
sed 's/^X//' >tvx_ptch.c <<\SHAR_EOF
X/* -------------------------- tvx_ptch.c --------------------------- */
X#include "tvx_defs.ic"
X
X#define EXTERN
X#include "tvx_glbl.ic"
X
X/*=======================================================================
X
X    tvpatch - program to patch tvx with config.tvx file
X
X	first version 6/19/84
X	7/25/84 - fixed to correspond to tvx version, add extra command
X	2/14/85 - version to correspond with rest
X	5/15/85 - again, batched to correspond
X	9/20/85 - fixed for new version of tvx, unix added
X
X======================================================================= */
X 
X#ifndef UNIX
X    char filein[] = "A:TVX.EXE";
X    char fileout[]= "A:TEMP1.$$$";
X#else
X    char filein[80] = "tvx";
X    char fileout[80]= "tvx_temp";
X#endif
X    char config[80];
X
X
X/*  define our general control item structure for general patching */
X
X#define BL remark("")
X#define RMK remark
X#define PR prompt
X 
X    char clower(), cupper();
X    extern char *malloc();
X    extern FILE *fopen();
X    FILE *tvxin, *cfgin, *tvxout;
X
X/* =============================>>> MAIN   <<<============================= */
X  main()
X  {
X 
X    char ans[80];
X
XTOP:
X    cls();
X    RMK("TVX_PTCH - Version 11/12/85");
X    BL;
XRMK("  This program is used to permanently alter TVX to match the options");
XRMK("selected with the TVX_CNFG program.  It will read in the configuration");
XRMK("file you specify (such as CONFIG.TVX), and patch TVX to reflect those");
XRMK("values.  Then you won't need to use the '-c' switch when using TVX.");
X    BL;
XRMK("*** You may press CONTROL-C at any time to cancel this installation. ***");
X
X    do 
X      {
X	BL;
X#ifndef UNIX
X	PR("On which drive is TVX.EXE located? (A, B, ...): ");
X	ureply(ans,10);
X	filein[0] = ans[0];
X#endif
X	if ( !(tvxin = fopen(filein,FILEREAD)))
X	  {
X	    PR("TVX not found on specified drive, try again: ");
X	    RMK(filein);
X#ifdef UNIX
X	    PR("Please enter name of tvx executable file: ");
X	    reply(filein,79);
X#endif
X	    continue;
X	  }
X	fclose(tvxin);
X	break;
X      }
X    while (1);
X
X#ifndef UNIX
X    fileout[0] = cupper(ans[0]);
X#endif
X 
X    do 
X      {
X	BL;
X	PR("Enter the name of the configuration file to use: ");
X	reply(config,79);
X	if ( !(cfgin = fopen(config,FILEREAD)))
X	  {
X	    RMK("Configuration not found on specified drive, try again.");
X	    continue;
X	  }
X
X	rdcfg(lexsym,LEXVALUES+1);
X	rdcfg(synofr,20);
X	rdcfg(synoto,20);
X	rdcfg(funchar,50);
X	rdcfg(funcmd,50);
X	rdcfg(&funkey,1);
X	rdcfg(&autoin,1);
X	rdcfg(&ddline,1);
X	rdcfg(&dscrl,1);
X	rdcfg(&dxcase,1);
X	rdcfg(&wraplm,1);
X	rdcfg(&use_wild,1);
X	rdcfg(&usebak,1);
X	logdef = usebak;
X	rdcfg(&cut_mode,1);
X#ifdef MSDOS
X	rdcfg(&usecz,1);
X#endif
X	fclose(cfgin);
X	break;
X      }
X    while (1);
X 
X    BL;
X    RMK("TVX is being modified to match your choices.");
X    RMK("This may take several minutes.");
X    BL;
X 
X    fpatch(filein);	/* patch tvx */
X 
X    cls();
X    RMK("Modification completed.  TVX is ready to use without the -c now.");
X    BL;
X  }
X
X/* =============================>>> RDCFG <<<============================= */
X  rdcfg(toset,cnt)
X  char *toset;
X  int cnt;
X    {	/* read cnt vals from cfgin */
X
X    FAST int i,val;
X
X    for (i = 0 ; i < cnt ; ++i)
X      {
X	if ((val = fgetc(cfgin)) == EOF)
X	 {
X	    remark("Invalid configuration file, aborting");
X	    fclose(cfgin);
X	    exit(999);
X	 }
X	*toset++ = val;	/* replace with new commands */
X      }
X  }
X
X/* =============================>>> FPATCH <<<============================= */
X  fpatch(fn)
X  char *fn;
X  {
X    static int byt;
X    static int i;
X    static int didpatch;
X    static char *begptr;	/* patch area pointers */
X 
X    prompt("Patching "); remark(filein);
X
X#ifndef UNIX
X    fn[0] = fileout[0];		/* set drive */
X#endif
X    didpatch = FALSE;
X    if (!(tvxin = fopen(fn,FILEREAD)))
X      {
X	PR("Unable to find file to patch: "); PR(fn);
X        RMK(".  Aborting to operating system.");
X	exit(999);
X      }
X    if (!(tvxout = fopen(fileout,FILEWRITE)))
X      {
X	PR("Unable to create new file, aborting: ");
X	RMK(fileout);
X	exit(999);
X      }
X 
X    while ((byt = fgetc(tvxin)) != EOF)
X      {
X	fputc(byt,tvxout);
X	if (byt == '#')			/* look for first sharp */
X	  {
X	    for (i = 1 ; i <= 4 ; ++i)
X	      {
X		if ((byt = fgetc(tvxin)) == EOF)
X		    goto l900;
X		fputc(byt,tvxout);	/* echo */
X		if (byt != '#')
X		    goto l800;
X	      }
X	    byt = fgetc(tvxin);		/* should be : next */
X	    fputc(byt,tvxout);
X	    if (byt != ':')
X		goto l800;
X
X/*   fall thru means found patch area -- code to patch follows */
X
X	    for (begptr = (char *) &addx ; begptr < (char *) &endpatch ;
X	      ++begptr)
X	      {
X		if ((byt = fgetc(tvxin)) == EOF) /* read byte from file */
X		    goto l900;
X		fputc(*begptr,tvxout); /* replace with byte from my area */
X	      }
X	    didpatch = TRUE;
X	  }
Xl800:	byt = byt;		/* compiler bug */
X      }
X
X
Xl900:
X    fclose(tvxin);
X    fclose(tvxout);
X    if (!didpatch)
X      {
X	RMK("*********  ERROR ********");
X	RMK("The file just checked was not a proper version of the program!");
X	RMK("Please check that your are using a valid copy of the");
X	RMK("program file supplied with this initialization program!");
X	RMK("Unable to make patch, aborting");
X	exit(999);
X      }
X    unlink(fn);
X    fn[0] = fileout[0];		/* fix the drive */
X    if (rename(fileout,fn) != 0)
X      {
X	RMK("Unable to rename temporary patch file");
X	exit(999);
X      }
X  }
X
X/* =============================>>> OK <<<============================= */
X  ok(msg)
X  char *msg;
X  {
X    char rp[11];
X    PR(msg); PR(" (y/n) ");
X    lreply(rp,10);
X    return (rp[0] == 'y');
X  }
X
X/* ============================>>> RVALID <<<=========================== */
X  rvalid(chr,okstr)
X  char chr,*okstr;
X  {
X    /* sees if chr is in okstr */
X   
X    SLOW int i;
X    SLOW char ch;
X
X    ch = clower(chr);
X    while (*okstr)
X      {
X	if (ch == clower(*okstr++))
X	    return TRUE;
X      }
X    return FALSE;
X  }
X  
X/* =============================>>> CLS  <<<============================= */
X  cls()
X  {
X    int i;
X 
X    for (i = 0  ; i < 25 ; ++i)
X	BL;
X  }
X
X#define EXTENDED	/* my own extended lib functions */
X/* #define STANDARD	/* the set of standard functions i use */
X#define LOCAL static	/* make all local globals, i think */
X
X
X#ifdef EXTENDED
X/*=============================>>> CLOWER  <<<================================*/
X  char clower(ch)
X  char ch;
X  {
X    return ((ch >='A' && ch<='Z') ? ch + ' ' : ch);
X  }
X
X/*=============================>>> CUPPER  <<<================================*/
X  char cupper(ch)
X  char ch;
X  {
X    return ((ch >= 'a' && ch <= 'z') ? ch - ' ' : ch);
X  }
X
X/* =========================>>> LOWER  <<<==============================*/
X  lower(str)
X  char str[];
X  {
X    FAST int i;
X
X    for (i=0 ; str[i] ; ++i)
X	str[i]=clower(str[i]);
X
X  }
X
X/*=============================>>> PROMPT <<<================================*/
X  prompt(msg)
X  char msg[];
X  {
X    printf("%s",msg);
X  }
X
X
X/*=============================>>> REMARK <<<================================*/
X  remark(msg)
X  char msg[];
X  {
X    printf("%s\n",msg);
X  }
X
X/*=============================>>> UPPER  <<<================================*/
X  upper(str)
X  char str[];
X  {
X    static int i;
X
X    for (i=0 ; str[i] ; ++i)
X	str[i]=cupper(str[i]);
X  }
X
X
X/*=============================>>> LREPLY <<<================================*/
X  lreply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X    reply(msg,maxc);
X    lower(msg);
X  }
X
X/*=============================>>> UREPLY <<<================================*/
X  ureply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X    reply(msg,maxc);
X    upper(msg);
X  }
X
X/*=============================>>> REPLY <<<================================*/
X  reply(msg,maxc)
X  char msg[];
X  int maxc;
X  {
X#ifdef UNIX
X    gets(msg);
X#endif
X#ifdef MSDOS
X    gets(msg,maxc,stdin);
X#endif
X#ifdef GEMDOS
X    gemdos(0x0a,msg);
X#endif
X  }
X
X/*=============================>>> RDINT <<<================================*/
X  rdint(val)
X  int *val;
X  {
X    char chrrep[12];
X    reply(chrrep,11);
X    *val = atoi(chrrep);
X  }
X#endif
X/* -------------------------- tvx_ptch.c --------------------------- */
SHAR_EOF
echo ALL DONE!
exit 0