rsalz@bbn.com (Rich Salz) (05/11/88)
Submitted-by: Paul Lew <harvard!gsg!lew@a.cs.uiuc.edu> Posting-number: Volume 14, Issue 93 Archive-name: shellforms/part02 #! /bin/sh # This is a shell archive, meaning: # 1. Remove everything above the #! /bin/sh line. # 2. Save the resulting text in a file. # 3. Execute the file with /bin/sh (not csh) to create the files: # sf.c form.c load.c field.c selection.c keyword.c option.c # msg.c term.c io.c summary.c export PATH; PATH=/bin:$PATH echo shar: extracting "'sf.c'" '(4115 characters)' if test -f 'sf.c' then echo shar: will not over-write existing file "'sf.c'" else sed 's/^X//' << \SHAR_EOF > 'sf.c' X/************************************************************************** X* X* File name: sf.c X* X* Author: Paul Lew, General Systems Group, Inc. Salem NH X* Created at: 05/08/86 10:11 AM X* Last update: 02/08/88 00:23 AM (Edition: 29) X* X* Description: This program will take standard input (if no argument X* specified in command line) or the specified file as X* form template and display it on the terminal to X* perform basic form editing function. It then generate X* the Csh or Bourne shell set script on stdout to be X* executed (ala tset -s). X* X* This program is designed to give programmer an easy X* way of doing form filling in shell level. X* X* Update History: X* X* Date Modification Description By X* -------- ------------------------------------------------------ --- X* 05/08/86 Initial version Lew X* 08/04/87 added Help_display flag Lew X* 12/29/87 modify to add Bourne shell output flag, use getopt() Lew X* 01/12/88 added init_sno(), added CTRL L redisplay function, Lew X* added signal trap handling. X* 01/26/88 added AUTOTAB at end of a field, added NUMERIC field Lew X* attribute X* 02/08/88 modified to add perl script output flag Lew X* X***************************************************************************/ X#define EXTERN X#include <stdio.h> X#include <ctype.h> X#include "form.h" X#include "basic.h" X Xchar *Version = "1.8 02/08/88 00:21 AM"; Xchar *Bugs = "Bug report send to: decvax!gsg!lew (UUCP)"; Xchar *Copyright = "Copyright by Paul Lew (1987,1988) All rights reserved"; Xchar *Prgname; /* program name */ X Xextern unsigned char Shell; Xextern int Help_display; Xint Debug = NO; X X/*------------------------------------------------------------07/13/84--+ X| | X| M a i n R o u t i n e S t a r t s H e r e | X| | X+----------------------------------------------------------------------*/ Xmain (argc, argv) Xint argc; /* number of argument passed */ Xchar **argv; /* pointer to argument list */ X { X int n; /* number of files (so far 2) */ X char *fname; /* form file name */ X X Prgname = *argv; X n = procarg (argc, argv); X if (n == argc) fname = NULL; /* read from stdin if no input */ X else fname = argv[n]; X edit_form (fname, (int (*)())NULL); X exit (0); X } X X/*----------------------------------------------------------------------+ X| | X| proc_arg : process input argument and set global flags | X| | X+----------------------------------------------------------------------*/ Xprocarg (argc, argv) Xint argc; Xchar **argv; X { X int rvideo = 0; X int undline = 0; X int hilite = 0; X char *fname = NULL; X int c; X extern char *optarg; /* ptr to argument */ X extern int optind; /* remember which one to process next */ X X ENTER (procarg); X while ((c = getopt (argc, argv, "Hbdhmo:pru")) != EOF) { X switch (c) { X when 'b': Shell = BOURNE; X when 'd': Debug = YES; X when 'h': hilite = YES; X when 'm': Help_display = YES; X when 'o': fname = optarg; X when 'p': Shell = PERL; X when 'r': rvideo = YES; X when 'u': undline = YES; X otherwise:help (); X exit (1); X } X } X set_options (hilite, rvideo, undline, fname); X RETURN (optind); X } X X/*-------------------------------------------------------------05/08/86-+ X| | X| help : display help message | X| | X+----------------------------------------------------------------------*/ Xhelp () X { X ENTER(help); X fprintf (stderr, "%s Version %s\r\n", Prgname, Version); X fprintf (stderr, "Command Options:\r\n"); X fprintf (stderr, " -H display this help message\r\n"); X fprintf (stderr, " -b generate Bourne shell output [Csh]\r\n"); X fprintf (stderr, " -d debug mode, will show CTRL chars\r\n"); X fprintf (stderr, " -h input in highlight mode\r\n"); X fprintf (stderr, " -m display selection help automatically\r\n"); X fprintf (stderr, " -o file use file as output file\r\n"); X fprintf (stderr, " -p generate perl script output\r\n"); X fprintf (stderr, " -r input in reverse video mode\r\n"); X fprintf (stderr, " -u input in underline mode\r\n"); X EXIT; X } SHAR_EOF if test 4115 -ne "`wc -c < 'sf.c'`" then echo shar: error transmitting "'sf.c'" '(should have been 4115 characters)' fi fi # end of overwriting check echo shar: extracting "'form.c'" '(5898 characters)' if test -f 'form.c' then echo shar: will not over-write existing file "'form.c'" else sed 's/^X//' << \SHAR_EOF > 'form.c' X/* Last update: 02/08/88 00:18 AM (Edition: 56) */ X#include <stdio.h> X#include <ctype.h> X#include <signal.h> X#include "form.h" X#include "field.h" X#include "term.h" X#include "basic.h" X Xchar Screen [SCRLINE][SCRCOL+1]; Xchar Form_name[20] = ""; /* current form name */ Xchar Exitc; /* field exit char */ X Xchar Enter_mode [20]; /* display before input field */ Xchar Exit_mode [20]; /* display after input field */ X Xstruct field Field[MAXFIELD]; /* field nodes */ Xint Fno; /* next field to use (or count) */ Xunsigned char Fhead[SCRLINE]; /* 1st field index on each line */ Xunsigned char Flcount[SCRLINE]; /* number of fields on this line */ Xunsigned char Lastdata = 24; /* last line with data on form */ X Xchar Varfile [MAXFNAME]; /* output variable file name */ X Xextern int Form_msg; /* defined in msg.c */ Xextern unsigned char Shell; /* output shell script type */ X Xint sig_interrupt(); Xint sig_stop(); X X/*----------------------------------------------------------------------+ X| | X| show_form : display a given form file | X| | X+----------------------------------------------------------------------*/ Xshow_form (fname) Xchar *fname; /* name of form file, NULL = stdin, 1 = redisplay */ X { X int i, j; X int idx; /* index to current field */ X unsigned size; X unsigned off; X unsigned len; /* string length */ X int pend; /* previous end position */ X char *lp; /* line pointer (for speed) */ X char *p; X extern char *Prgname; X X ENTER(show_form); X if (fname != (char *)1 && /* redisplay */ X (fname == NULL || strcmp (fname, Form_name) != 0)) { X if (!load_form (fname)) RETURN (0); X } X X screen (SCR_ERASE); X for (i=0; i<SCRLINE; i++) { X p = lp = Screen[i]; X if (Flcount[i] != 0) { X pend = 0; X for (j=0, idx=Fhead[i]; j<Flcount[i]; j++, idx++) { X size = Field[idx].f_len; X off = Field[idx].f_off; X put_string (p, off-pend); X put_string (Enter_mode, 0); X put_string (lp + off, size); X put_string (Exit_mode, 0); X p = lp + off + size; X pend = off + size; X } X } X if ((len = strlen (p)) == 0) continue; X put_string (p, len); X put_char ('\r'); X } X RETURN (1); X } X X/*----------------------------------------------------------------------+ X| | X| edit_form : edit a form on all the input fields | X| | X+----------------------------------------------------------------------*/ Xedit_form (fname, action) Xchar *fname; /* name of the form to edit */ Xint (*action) (); /* action routine to check at end of each field */ X { X unsigned fdx = 0; /* current cursor in field index */ X struct field *fp; /* pointer to current edit field */ X int n; /* action routine return status */ X int efopt; /* option to edit field */ X X ENTER(edit_form); X signal (SIGINT, sig_interrupt); X signal (SIGTSTP, sig_stop); X X term_init (); X cbreakio (1); X if (!show_form (fname)) goto end; X if (Fno == 0) goto end; X X form_msg ((char *)NULL, 1, 1); X screen (SCR_KEYXMIT); X while (1) { X fp = &Field[fdx]; X efopt = EF_BOF; X do { X if (fp->f_attr & FA_SELECTION) sel_field (fdx); X else edit_field (fdx, efopt); X if (!action) break; X n = (*action) (fdx, &Screen[fp->f_line-1][fp->f_off], X fp->f_len, Exitc); X switch (n) { X when EF_ERR: efopt = EF_BOF; X when EF_FILL: efopt = EF_FILL; X } X } while (n != EF_OK); X X if ((Exitc & 0x80) == 0x80) { X switch (Exitc & 0x7f) { X when KU: Exitc = CTRL('P'); X when KD: Exitc = CTRL('N'); X } X } X switch (Exitc) { X when CTRL('L'): show_form ((char *)1); X when CTRL('M'): goto wrout; X when CTRL('J'): goto wrout; X when CTRL('P'): fdx = closest (fdx, -1); X when CTRL('N'): fdx = closest (fdx, 1); X when CTRL('T'): fdx = (fdx == 0) ? Fno-1 : (fdx-1); X when CTRL('I'): if (++fdx == Fno) fdx = 0; X otherwise: show_summary (); X show_form ((char *)1); X } X } Xwrout: write_var (); X poscur (Lastdata, (unsigned char)1, "\n"); screen (SCR_EEOL); Xend: X screen (SCR_NOKEYXMIT); X cbreakio (0); X term_close (); X EXIT; X } X X/*-------------------------------------------------------------05/08/86-+ X| | X| write_var : write field variables to a file | X| | X+----------------------------------------------------------------------*/ Xwrite_var () X { X register int i; X FILE *fd; /* output file pointer */ X char *p; X char *op; X char c; X char buf[80+1]; X char obuf[80+1]; X struct field *f; X X ENTER(write_var); X if (!strlen (Varfile)) EXIT; X X if ((fd = fopen (Varfile, "w")) == NULL) { X fprintf (stderr, "write_var: can not open file %s for write\r\n", X Varfile); X exit (1); X } X X for (i=0; i<Fno; i++) { X f = &Field[i]; X if (f-> f_var != NULL) { X get_field (i, buf); X p = buf; op = obuf; X while (c = *p++) { X switch (c) { X when '\'': if (Shell== PERL) *op++ = '\\'; X else { X *op++ ='\'';*op++ ='"'; X *op++ ='\'';*op++ ='"'; X } X when '!': if (Shell == CSH) *op++ = '\\'; X } X *op++ = c; X } X *op = EOS; X fprintf (fd, "%s%s='%s'%s\n", X (Shell==CSH)?"set ":((Shell==PERL)?"$":""), X f-> f_var, obuf, X (Shell == PERL) ? ";" : ""); X } X } X fclose (fd); X EXIT; X } X X/*-------------------------------------------------------------01/12/88-+ X| | X| sig_interrupt : Interrupt signal handler | X| | X+----------------------------------------------------------------------*/ Xsig_interrupt () X { X ENTER (sig_interrupt); X form_msg ("Aborted by user\n", 24+1, 1); X screen (SCR_NORMAL); X cbreakio (1); X exit (1); X } X X/*-------------------------------------------------------------01/12/88-+ X| | X| sig_stop : Stop signal handler | X| | X+----------------------------------------------------------------------*/ Xsig_stop () X { X ENTER (sig_stop); X form_msg ("stopped by user\n", 24+1, 1); X screen (SCR_NORMAL); X cbreakio (0); X kill (getpid(), SIGSTOP); X put_string ("Press CTRL L to refresh display: ", 33); X cbreakio (1); X } SHAR_EOF if test 5898 -ne "`wc -c < 'form.c'`" then echo shar: error transmitting "'form.c'" '(should have been 5898 characters)' fi fi # end of overwriting check echo shar: extracting "'load.c'" '(8779 characters)' if test -f 'load.c' then echo shar: will not over-write existing file "'load.c'" else sed 's/^X//' << \SHAR_EOF > 'load.c' X/* Last update: 01/26/88 10:53 PM (Edition: 63) */ X#include <stdio.h> X#include <strings.h> X#include "form.h" X#include "field.h" X#include "basic.h" X X#define TOKENSIZE 256 X Xchar Varname [MAXVNAME]; /* variable name string pool */ Xchar *Varwp = Varname; /* next write position */ X Xextern char Screen[SCRLINE][SCRCOL+1]; Xextern char Form_name[]; Xextern unsigned char Fhead[]; /* 1st field index on each line */ Xextern unsigned char Flcount[]; /* number of fields on this line */ Xextern unsigned char Lastdata; Xextern struct field Field[]; /* field nodes */ Xextern int Fno; /* next field to use (or count) */ X X/*----------------------------------------------------------------------+ X| | X| load_form : load a form from disk file | X| | X+----------------------------------------------------------------------*/ Xload_form (fname) Xchar *fname; X { X FILE *fp; X register unsigned char i; X X ENTER (load_form); X if (fname == NULL) fp = stdin; X else if ((fp = fopen (fname, "r")) == 0) { X fprintf (stderr, "Can not open form file %s\r\n", fname); X RETURN (0); X } X for (i=0; i<SCRLINE; i++) Screen[i][0] = '\0'; X init_field (); X for (i=0; i<SCRLINE; i++) { X if (fgets (Screen[i], SCRCOL+1, fp) == 0) break; X if (Screen[i][0] == CTRL('L')) { X Screen[i][0] = EOS; X field_attr (fp); X break; X } X make_field (i+1, Screen[i]); X } X init_sno (); /* fill data for field with selections */ X Lastdata = i; X if (fname != NULL) { X strcpy (Form_name, fname); X } X RETURN (1); X } X X/*----------------------------------------------------------------------+ X| | X| bcopy : copy len byte from src to dest (extra fill with blanks) | X| | X+----------------------------------------------------------------------*/ Xbcopy (dest, src, len) Xchar *dest; Xchar *src; Xunsigned len; X { X char c = ' '; X X ENTER (bcopy); X while (len-- != 0) { X if (c == EOS) *dest++ = ' '; /* fill blanks to end */ X else if ((c = *src++) != EOS) X *dest++ = c; X else *dest++ = ' '; X } X EXIT; X } X X/*-------------------------------------------------------------05/08/86-+ X| | X| add_var : add a variable name to field structure | X| | X+----------------------------------------------------------------------*/ Xadd_var (fno, name) Xint fno; Xchar *name; X { X int len = strlen (name) + 1; X X ENTER (add_var); X if (Varwp + len >= &Varname[MAXVNAME]) { X fprintf (stderr, "add_var: no more space for variable name\r\n"); X exit (1); X } X Field[fno].f_var = Varwp; X strcpy (Varwp, name); X Varwp += len; X EXIT; X } X X/*-------------------------------------------------------------05/08/86-+ X| | X| field_attr : read in field attribute of the form | X| | X+----------------------------------------------------------------------*/ Xfield_attr (fd) XFILE *fd; X { X int field = -1; X char tokbuf [TOKENSIZE]; /* token value */ X char token; /* token specifier */ X int i, n; X unsigned len, size; X struct field *f; X char *p; X X ENTER (field_attr); X while (token = get_token (fd, tokbuf)) { X switch (token) { X when 'v': if (++field >= Fno) RETURN (0); X add_var (field, tokbuf); X when 's': n = (field < 0) ? 0 : field; X f = &Field[n]; X size = strlen(tokbuf); X build_selection (f, tokbuf, size); X when 'h': n = (field < 0) ? 0 : field; X f = &Field[n]; X build_help_msg (f, tokbuf); X when 'd': n = (field < 0) ? 0 : field; X f = &Field[n]; X size = strlen(tokbuf); X len = (size > f-> f_len) ? f-> f_len : size; X for (p=tokbuf, i=0; i<len; i++) { X Screen[f-> f_line - 1][f-> f_off + i] = *p++; X } X when 'a': n = (field < 0) ? 0 : field; X f = &Field[n]; X set_field_attr (f, tokbuf); X otherwise:fprintf (stderr, "unknown token %c (field %d)\r\n", X token, field); X } X } X RETURN (1); X } X X/*-------------------------------------------------------------05/08/86-+ X| | X| get_token : return next token in field description section | X| | X+----------------------------------------------------------------------*/ Xget_token (fd, tokbuf) XFILE *fd; Xchar *tokbuf; X { X static char buf[TOKENSIZE]; X static char *p; X static int len = 0; X static char dchar; X register char *tp; /* temp pointer */ X char token; X X ENTER (get_token); X if (len == 0) { X do { X if (!fgets (buf, sizeof (buf), fd)) RETURN ((char)0); X len = strlen (buf) - 1; /* no NL */ X } while (len == 0); X dchar = buf[0]; /* delimiter char */ X p = buf + 1; /* 1st char */ X } X X for (tp=p; tp < &buf[len]; ) { X if (*tp++ == dchar) break; X } X X token = *p++; /* return token char */ X p++; /* skip =, actually ignore it */ X while (p < tp-1) X *tokbuf++ = *p++; X *tokbuf = EOS; X X if ((p = tp) == &buf[len]) len = 0; X RETURN (token); X } X X/*----------------------------------------------------------------------+ X| | X| make_field : extract input fields to make field structure | X| | X+----------------------------------------------------------------------*/ Xmake_field (lno, line) Xunsigned lno; /* line number of this line */ Xchar *line; X { X char *p; X unsigned col = 1; /* current column position */ X unsigned in_field = 0; /* number of input field char */ X unsigned cno; X X ENTER (make_field); X for (p=line; *p != EOS; p++) { X switch (*p) { X case '~': /* input field */ X *p = ' '; X if (in_field++ == 0) cno = col; X col++; X break; X case '\t': X col = ((col-1)/8 + 1) * 8 + 1; X goto lab; X default: X col++; Xlab: if (in_field) X add_field (lno, cno, p-line-in_field, X in_field); X in_field = 0; X } X } X EXIT; X } X X/*----------------------------------------------------------------------+ X| | X| init_field : initialize all field control related data | X| | X+----------------------------------------------------------------------*/ Xinit_field () X { X int i; X X ENTER (init_field); X Fno = 0; X for (i=0; i<SCRLINE; i++) { X Fhead[i] = 0; X Flcount[i] = 0; X } X EXIT; X } X X/*----------------------------------------------------------------------+ X| | X| add_field : add a given field to field structure | X| | X+----------------------------------------------------------------------*/ Xadd_field (line, column, offset, len) Xunsigned line; /* line of the field */ Xunsigned column; /* column of the field */ Xunsigned offset; /* char offset from beginning of the line */ Xunsigned len; /* field size */ X { X struct field *fp; X X ENTER (add_field); X if (Fno >= MAXFIELD) { X fprintf (stderr, "Too many fields in a screen max=%d\r\n", X MAXFIELD); X exit (1); X } X fp = &Field[Fno]; X fp-> f_line = line; X fp-> f_col = column; X fp-> f_off = offset; X fp-> f_len = len; X fp-> f_attr = 0; /* 'a' -- attribute */ X fp-> f_sel = NULL; /* 's' -- selection */ X fp-> f_help = NULL; /* 'h' -- help message */ X fp-> f_sno = 0; X fp-> f_var = NULL; X X if (Flcount[line-1]++ == 0) { X Fhead[line-1] = Fno; X } X Fno++; X EXIT; X } X X#define STRNEQ(x,y,n) ((*(x) == *(y)) && strncmp (x,y,n) == 0) X#define BADINIT "Field %d, Init value: [%.*s] no in selection list, ignored\n" X/*-------------------------------------------------------------01/11/88-+ X| | X| init_sno : initialize selection number for preloaded fields | X| | X+----------------------------------------------------------------------*/ Xinit_sno () X { X register int idx, j; X int field_count; X int init_size; /* initial default data size */ X struct field *f; X char *p; X X ENTER (init_sno); X for (idx=0; idx<Fno; idx++) { X X f = &Field[idx]; X p = &Screen[f-> f_line - 1][f-> f_off]; X init_size = fldlen (p, f-> f_len); X X if (f-> f_sel != NULL) { X if (init_size) { X field_count = sel_num (f); X /* check if default data is in the selection list */ X for (j=0; j<field_count; j++) { X register char *selp; X selp = f-> f_sel[j]; X if (STRNEQ (p, selp, strlen(selp))) { X f-> f_sno = j; X break; X } X } X if (j >= field_count) { X fprintf (stderr, BADINIT, idx, init_size, p); X j = 0; goto mv_1st; X } X } X else { X /* move the first selection into the field */ X j = 0; Xmv_1st: strncpy (p, f-> f_sel[j], strlen(f-> f_sel[j])); X } X } X } X EXIT; X } X X/*-------------------------------------------------------------01/26/88-+ X| | X| set_field_attr : set attributes for a given field | X| | X+----------------------------------------------------------------------*/ Xset_field_attr (fieldp, buf) Xstruct field *fieldp; Xchar *buf; X { X char c; X X ENTER (set_field_attr); X while ((c = *buf++) != EOS) { X switch (c) { X when 'd': fieldp-> f_attr |= FA_NUMERIC; X when 'a': fieldp-> f_attr |= FA_AUTOTAB; X when 'b': fieldp-> f_attr |= FA_BLOCK; X otherwise: fprintf (stderr, X "unknown field attribute: %c\r\n", c); X exit (1); X } X } X EXIT; X } SHAR_EOF if test 8779 -ne "`wc -c < 'load.c'`" then echo shar: error transmitting "'load.c'" '(should have been 8779 characters)' fi fi # end of overwriting check echo shar: extracting "'field.c'" '(6631 characters)' if test -f 'field.c' then echo shar: will not over-write existing file "'field.c'" else sed 's/^X//' << \SHAR_EOF > 'field.c' X/* Last update: 01/26/88 11:26 PM (Edition: 25) */ X#include <stdio.h> X#include <signal.h> X#include <strings.h> X#include <ctype.h> X#include "term.h" X#include "form.h" X#include "field.h" X#include "basic.h" X Xextern int Fno; Xextern struct field Field[]; Xextern char Screen[SCRLINE][SCRCOL+1]; Xextern char Enter_mode[]; Xextern char Exit_mode[]; Xextern int Form_msg; Xextern char Exitc; X X/*-------------------------------------------------------------05/09/86-+ X| | X| get_field : get a copy of field data to buffer | X| | X+----------------------------------------------------------------------*/ Xget_field (fno, buf) Xint fno; /* field number */ Xchar *buf; /* buffer to be filled */ X { X struct field *f; X char *p; X int size; X X ENTER(get_field); X if (fno < 0 || fno >= Fno) EXIT; X f = &Field[fno]; X p = &Screen [f-> f_line -1][f-> f_off]; X size = fldlen (p, f-> f_len); X strncpy (buf, p, size); X buf[size] = EOS; /* mark the end */ X EXIT; X } X/*----------------------------------------------------------------------+ X| | X| fldlen : return the number of data in a field (skip trailing blanks) | X| | X+----------------------------------------------------------------------*/ Xfldlen (buf, size) Xchar *buf; /* pointer to field buffer */ Xunsigned size; /* size of the field */ X { X int blank; X X ENTER(fldlen); X for (blank=0; buf[size-1-blank] == ' '; blank++) { X if (blank >= size) break; X } X RETURN (size - blank); /* return length of field */ X } X X/*----------------------------------------------------------------------+ X| | X| upd_field : move data into a field and display it | X| | X+----------------------------------------------------------------------*/ Xupd_field (idx, type, data) Xunsigned idx; /* field number (0 to Fno-1) */ Xint type; /* type of output */ Xint data; /* data, type may vary */ X { X struct field *fp; X char *fmt; X char *scp; /* pointer to screen buffer */ X char buf[81]; X int data2; /* cents */ X X ENTER(upd_field); X if (idx >= Fno) { X fprintf (stderr, X "Field number: %d out of range, max %d\r\n", X idx, Fno); X EXIT; X } X X fp = &Field[idx]; X switch (type) { X case UF_MONEY: fmt = "%5d.%02d"; X data2 = data % 100; X data = data / 100; break; X case UF_NUMBER: fmt = "%d"; break; X case UF_STRING: X default: fmt = "%s"; break; X } X X sprintf (buf, fmt, data, data2); X scp = &Screen[fp-> f_line - 1][fp-> f_off]; X bcopy (scp, buf, (unsigned)fp-> f_len); X poscur (fp-> f_line, fp-> f_col, (char *)NULL); X put_string (scp, fp-> f_len); X poscur (fp-> f_line, fp-> f_col, (char *)NULL); X EXIT; X } X X/*-------------------------------------------------------------07/14/87-+ X| | X| closest : find the closest field above/below current line | X| | X+----------------------------------------------------------------------*/ Xclosest (fno, direction) Xunsigned fno; /* current field number */ Xint direction; /* compare direction: 1=below, -1=above */ X { X struct field *fp = &Field[fno]; X int col; /* target column */ X int line; /* current line */ X int diff; /* current difference */ X int mindiff = 100; /* minimal difference */ X int mini = 0; /* minimal field index */ X register int i; X X ENTER(closest); X col = fp->f_col; X line = fp->f_line; X X for (i=fno+direction; i != fno; i += direction) { X if (i < 0) i = Fno-1; X else if (i >= Fno) i = 0; X fp = &Field[i]; X if (fp->f_line != line) break; X } X mini = i; X for (line = fp->f_line; ; i += direction) { X if (i < 0) i = Fno-1; X else if (i >= Fno) i = 0; X fp = &Field[i]; X if (fp->f_line != line) break; X if ((diff = abs ((int)fp->f_col - (int)col)) == 0) RETURN (i); X if (diff < mindiff) { X mindiff = diff; X mini = i; X } X } X RETURN (mini); X } X X/*----------------------------------------------------------------------+ X| | X| edit_field : edit a given field in a form | X| | X+----------------------------------------------------------------------*/ Xedit_field (idx, efopt) Xunsigned idx; /* index to Field array */ Xint efopt; /* option */ X { X struct field *fp; X char c; X char *p; X char *s; /* beginning of field buffer */ X unsigned n; X register int i; X X ENTER (edit_field); X fp = &Field[idx]; X poscur (fp-> f_line, fp-> f_col, Enter_mode); X p = s = &Screen [fp-> f_line - 1][fp-> f_off]; X switch (efopt) { X case EF_FILL: X case EF_EOF: n = fldlen (s, fp-> f_len); X if (n != 0) { X if (efopt == EF_FILL) X put_string (p, n); X p += n; X } X break; X default: ; /* start at beginning of field */ X } X while (1) { X c = getkey (); X if (Form_msg) { X form_msg ((char *)NULL, fp-> f_line, fp-> f_col + (p-s)); X put_string (Enter_mode, 0); X } X if ((c & 0x80) == 0x80) { X switch (c & 0x7f) { X case KL: goto cur_left; X case KR: goto cur_right; X } X } X switch (c) { X case '\177': /* delete char */ X if (p > s) { *(--p) = ' '; screen (SCR_DEL); } X continue; X case CTRL('W'): /* delete prev word */ X while (p > s) { X if (*(p-1) != ' ') break; X p--; screen (SCR_DEL); X } X while (p > s) { X if (*(p-1) == ' ') break; X *(--p) = ' '; X screen (SCR_DEL); X } X continue; X case CTRL('K'): X n = fldlen (s, fp-> f_len); X for (i=0; i<n; i++) put_char (*(p+i) = ' '); X for (i=0; i<n; i++) screen (SCR_BACKSPACE); X continue; X case CTRL('H'): X case CTRL('B'): Xcur_left: if (p > s) { p--; screen (SCR_BACKSPACE); } X continue; X case CTRL('F'): Xcur_right: if (p < s + fp-> f_len) { X put_char (*p++); X } X continue; X case CTRL('G'): X case CTRL('U'): X while (p > s) { X *(--p) = ' '; screen (SCR_DEL); X } X continue; X case CTRL('E'): /* goto end of field */ X n = fldlen (s, fp-> f_len); X p = s + n; X poscur (fp-> f_line, fp-> f_col + n, (char *)NULL); X continue; X case CTRL('A'): /* emacs style */ X p = s; X poscur (fp-> f_line, fp-> f_col, (char *)NULL); X continue; X case CTRL('O'): X prev_msg (); X continue; X default: X if ((fp-> f_attr & FA_NUMERIC) != 0 && X isprint (c) && !isdigit (c)) { X put_char (CTRL('G')); X form_msg ("Numeric field, 0-9 only", X fp-> f_line, X fp-> f_col + (p-s)); X continue; X } X if (c < LOW_GCHAR || c > HIGH_GCHAR) { X Exitc = c; /* save exit char */ X goto eoe; X } X } X if (p - s >= fp-> f_len) { put_char (CTRL('G')); continue; } X *p++ = c; X put_char (c); X if ((fp-> f_attr & FA_AUTOTAB) != 0 && p - s == fp-> f_len) { X Exitc = TAB; /* tab to next field */ X break; X } X } X /* *p = EOS will put a marker at the end of buffer */ Xeoe: put_string (Exit_mode, 0); X RETURN (p-s); X } SHAR_EOF if test 6631 -ne "`wc -c < 'field.c'`" then echo shar: error transmitting "'field.c'" '(should have been 6631 characters)' fi fi # end of overwriting check echo shar: extracting "'selection.c'" '(5773 characters)' if test -f 'selection.c' then echo shar: will not over-write existing file "'selection.c'" else sed 's/^X//' << \SHAR_EOF > 'selection.c' X/* Last update: 01/27/88 00:04 AM (Edition: 45) */ X#include <stdio.h> X#include <sys/ioctl.h> X#include <ctype.h> X#include <strings.h> X#include "term.h" X#include "form.h" X#include "field.h" X#include "basic.h" X Xint Help_display = NO; /* if YES, display help */ X Xextern struct field Field[]; Xextern char Enter_mode[]; Xextern char Exit_mode[]; Xextern int Form_msg; Xextern char Exitc; Xextern char *malloc(); Xextern char *calloc(); X/* X Selection buffer looks like: X X <delchr> string1 <delchr> string2 <delchr> ... stringn <delchr> X X The first character in the buffer will be used as the delimiter to X separate selection strings. The last delimiter character is optional, X i.e., EOS will also terminate the last selection string. X*/ X X/*-------------------------------------------------------------08/01/87-+ X| | X| build_selection : take selection definition and create a list | X| | X+----------------------------------------------------------------------*/ Xbuild_selection (fldp, buf, len) Xstruct field *fldp; /* ptr to field structure */ Xchar *buf; /* selection strings */ Xunsigned len; /* length of string */ X { X register char *p = (char *)malloc(len+1); X register char **tp; X register int i; X char delimiter = buf[0]; /* selection delimiter */ X char c; X unsigned cnt = 0; /* # of selections */ X char *tmp[50]; /* temp array */ X X ENTER(build_selection); X if (len == 0) len = strlen (buf); X while (len-- != 0) { X if ((c = *buf++) == delimiter) { X *p++ = EOS; X if (cnt >= 50) { X /* silent ignored extra for now */ X } X else tmp[cnt++] = p; X } X else *p++ = c; X } X fldp->f_sel = tp = (char **) malloc (sizeof (char *) * (cnt + 1)); X for (i=0; i<cnt; i++) *tp++ = tmp[i]; X *tp = NULL; X fldp->f_attr |= FA_SELECTION; X RETURN (0); X } X X/*-------------------------------------------------------------08/01/87-+ X| | X| sel_num : return the number of selections in a given field | X| | X+----------------------------------------------------------------------*/ Xsel_num (fldp) Xstruct field *fldp; X { X register int i = 0; X register char **pp = fldp-> f_sel; X X ENTER(sel_num); X while (*pp++ != NULL) i++; X RETURN (i); X } X X/*-------------------------------------------------------------08/01/87-+ X| | X| sel_field : allow user to select a selection from the list | X| | X+----------------------------------------------------------------------*/ Xsel_field (idx) Xunsigned idx; /* index to Field array */ X { X struct field *fldp = &Field[idx]; X int n = fldp-> f_sno; /* selection number */ X int selno; /* # of possible selections */ X int i = -1; X char c; X X ENTER(sel_field); X selno = sel_num (fldp); X poscur (fldp-> f_line, fldp-> f_col, Enter_mode); X upd_field (idx, UF_STRING, fldp-> f_sel[n]); X while (1) { X int might_tab; X if (Help_display) display_help (fldp, n); X c = getkey (); X might_tab = 0; X if (Form_msg) { X form_msg ((char *)NULL, fldp->f_line, fldp->f_col); X put_string (Enter_mode, 0); X } X if ((c & 0x80) == 0x80) { X switch (c & 0x7f) { X case KL: goto prev_sel; X case KR: goto next_sel; X } X } X switch (c) { X case ' ': X case CTRL('F'): Xnext_sel: if (++n >= selno) n = 0; break; X case CTRL('H'): Xprev_sel: if (--n < 0) n = selno-1; break; X case '?': X if (!Help_display) { X display_help (fldp, n); X break; X } X default:if (c < LOW_GCHAR || c > HIGH_GCHAR) { X Exitc = c; X goto eoe; X } X i = cmp1st (c, fldp->f_sel, i+1); X if (i < 0) continue; X might_tab = 1; X n = i; X } X upd_field (idx, UF_STRING, fldp-> f_sel[n]); X if (might_tab && (fldp->f_attr & FA_AUTOTAB) != 0) { X Exitc = TAB; X break; X } X } Xeoe: put_string (Exit_mode, 0); X fldp-> f_sno = n; /* save selection number */ X EXIT; X } X X/*-------------------------------------------------------------08/03/87-+ X| | X| cmp1st : compare 1st character in a keyword list | X| | X+----------------------------------------------------------------------*/ Xcmp1st (c, list, start) Xchar c; /* char to compare */ Xchar **list; /* keyword list */ Xint start; /* start entry index */ X { X register int i, j; X register int n; X X ENTER(cmp1st); X if (list == NULL || list[0] == NULL) RETURN (-1); X for (n=0; list[n] != NULL; n++); X for (i=start, j=0; j<n; i++, j++) { X if (i >= n) i = 0; X if ((c | 0x20) == (list[i][0] | 0x20)) RETURN (i); X } X RETURN (-1); /* no match */ X } X X/*-------------------------------------------------------------08/04/87-+ X| | X| build_help_msg : build help message list | X| | X+----------------------------------------------------------------------*/ Xbuild_help_msg (fldp, buf) Xstruct field *fldp; /* field where the msg belongs */ Xchar *buf; /* message stores here */ X { X unsigned len = strlen (buf); X unsigned n; X register int i; X register char *p; X X ENTER(build_help_msg); X n = sel_num (fldp); X if (fldp-> f_help == NULL) { /* first time call */ X fldp-> f_help = (char **) calloc(n+1, sizeof(char *)); X } X for (i=0; i<n; i++) { X if (fldp-> f_help[i] == NULL) break; X } X if (i < n) { X fldp-> f_help[i] = p = (char *) malloc (len + 1); X strcpy (p, buf); X } X EXIT; X } X X/*-------------------------------------------------------------08/04/87-+ X| | X| display_help : display help message on message line | X| | X+----------------------------------------------------------------------*/ Xdisplay_help (fldp, i) Xstruct field *fldp; /* field pointer */ Xint i; /* index to help message */ X { X char *p; X int numchar; /* # of pending input chars */ X X ENTER(display_help); X if (fldp-> f_help == NULL) EXIT; X p = fldp-> f_help[i]; X if (p != NULL) { X ioctl (0, FIONREAD, &numchar); X if (numchar == 0) form_msg (p, fldp->f_line, fldp->f_col); X } X EXIT; X } SHAR_EOF if test 5773 -ne "`wc -c < 'selection.c'`" then echo shar: error transmitting "'selection.c'" '(should have been 5773 characters)' fi fi # end of overwriting check echo shar: extracting "'keyword.c'" '(1253 characters)' if test -f 'keyword.c' then echo shar: will not over-write existing file "'keyword.c'" else sed 's/^X//' << \SHAR_EOF > 'keyword.c' X/* Last update: 01/13/88 10:43 AM (Edition: 5) */ X#include <stdio.h> X#include "basic.h" X/*----------------------------------------------------------------------+ X| | X| fill_keyword : fill the field with possible matched keyword | X| | X+----------------------------------------------------------------------*/ Xfill_keyword (buf, len, list) Xchar *buf; Xunsigned len; /* size of input field */ Xchar **list; X { X int i, j; X unsigned flen; /* field length */ X unsigned char match[80]; X X ENTER (fill_keyword); X flen = fldlen (buf, len); X X for (i=j=0; list[i] != NULL; i++) { X if (kwcmp (buf, list[i], flen) == 0) { X /* find a match */ X match[j++] = i; X } X } X if (j == 1) bcopy (buf, list[match[0]], len); X else if (j > 1) bcopy (buf, list[match[0]], flen); X X RETURN (j); X } X X/*----------------------------------------------------------------------+ X| | X| kwcmp : compare a word with keyword (case insensitive) | X| | X+----------------------------------------------------------------------*/ Xkwcmp (src, dest, len) Xchar *src; Xchar *dest; Xunsigned len; X { X ENTER (kwcmp); X while (len-- != 0) { X if ((*src++ | 0x20) != (*dest++ | 0x20)) X RETURN (1); /* no match */ X } X RETURN (0); /* match found */ X } SHAR_EOF if test 1253 -ne "`wc -c < 'keyword.c'`" then echo shar: error transmitting "'keyword.c'" '(should have been 1253 characters)' fi fi # end of overwriting check echo shar: extracting "'option.c'" '(1317 characters)' if test -f 'option.c' then echo shar: will not over-write existing file "'option.c'" else sed 's/^X//' << \SHAR_EOF > 'option.c' X/* Last update: 01/13/88 11:17 AM (Edition: 5) */ X#include <stdio.h> X#include <strings.h> X#include "form.h" X#include "basic.h" X Xunsigned char Rvideo; /* reverse video */ Xunsigned char Undline; /* under line */ Xunsigned char Hilite; /* high light */ Xunsigned char Shell = CSH; /* output script type */ X Xextern char Varfile[]; Xextern char Enter_mode[]; Xextern char Exit_mode[]; X X/*-------------------------------------------------------------05/08/86-+ X| | X| set_options : set form editor options | X| | X+----------------------------------------------------------------------*/ Xset_options (hilite, rvideo, undline, fname) Xint hilite; /* highlight attribute */ Xint rvideo; /* reverse video attribute */ Xint undline; /* underline attribute */ Xchar *fname; /* output variable file name */ X { X char sbuf [80]; /* set mode */ X char ebuf [80]; /* exit mode */ X X ENTER(set_options); X X sbuf[0] = ebuf[0] = EOS; X if (hilite) { X get_hilite (sbuf, ebuf); X strcat (Enter_mode, sbuf); X strcat (Exit_mode, ebuf); X } X if (undline) { X get_undline (sbuf, ebuf); X strcat (Enter_mode, sbuf); X strcat (Exit_mode, ebuf); X } X if (rvideo) { X get_rvideo (sbuf, ebuf); X strcat (Enter_mode, sbuf); X strcat (Exit_mode, ebuf); X } X if (fname) strncpy (Varfile, fname, MAXFNAME); X EXIT; X } SHAR_EOF if test 1317 -ne "`wc -c < 'option.c'`" then echo shar: error transmitting "'option.c'" '(should have been 1317 characters)' fi fi # end of overwriting check echo shar: extracting "'msg.c'" '(2999 characters)' if test -f 'msg.c' then echo shar: will not over-write existing file "'msg.c'" else sed 's/^X//' << \SHAR_EOF > 'msg.c' X/* Last update: 01/13/88 10:59 AM (Edition: 11) */ X#include <stdio.h> X#include <strings.h> X#include "basic.h" X#include "form.h" X/* X Two flavors to display message: X X form_msg display message then position cursor at given X position, this allows form filling on terminal X without cursor save restore capability. X X formmsg display message and return to the caller's X position using terminal's save/restore cursor X ability. This is designed to be used by field X checking routine where user don't know where X the field is. X*/ X X#define MAXSMSG 5 X#define MSGSIZE 132 X Xint Form_msg = 0; /* form message on screen flag */ X Xstatic char Savemsg [MAXSMSG][MSGSIZE]; Xstatic int Sdx = 0; /* number of next entry to use */ Xstatic int Smcount = 0; /* number of messages saved */ X/*----------------------------------------------------------------------+ X| | X| form_msg : display message on the message line | X| | X+----------------------------------------------------------------------*/ Xform_msg (s, line, col) Xchar *s; /* message to display, if NULL, clear message */ Xunsigned char line; /* line to go at end */ Xunsigned char col; /* column to go at end */ X { X ENTER (form_msg); X poscur ((unsigned char)24, (unsigned char)1, (char *)NULL); X screen (SCR_REVERSE); X screen (SCR_EEOL); X if (s) { X Form_msg = 1; X put_string (s, 0); X save_msg (s); X } X else Form_msg = 0; X poscur (line, col, (char *)NULL); X EXIT; X } X X/*----------------------------------------------------------------------+ X| | X| formmsg : form_msg () use terminal SC, RC feature | X| | X+----------------------------------------------------------------------*/ Xformmsg (s) Xchar *s; /* message to display, if NULL, clear message */ X { X ENTER (formmsg); X screen (SCR_SAVE); X poscur ((unsigned char)24, (unsigned char)1, (char *)NULL); X screen (SCR_REVERSE); X screen (SCR_EEOL); X if (s) { X Form_msg = 1; X put_string (s, 0); X save_msg (s); X } X else Form_msg = 0; X screen (SCR_RESTORE); X EXIT; X } X X/*----------------------------------------------------------------------+ X| | X| save_msg : save a message on the message buffer | X| | X+----------------------------------------------------------------------*/ Xsave_msg (s) Xchar *s; X { X ENTER (save_msg); X strncpy (Savemsg[Sdx], s, MSGSIZE); X if (++Sdx >= MAXSMSG) Sdx = 0; X if (Smcount < MAXSMSG) Smcount++; X EXIT; X } X X/*----------------------------------------------------------------------+ X| | X| prev_msg : display previously displayed message | X| | X+----------------------------------------------------------------------*/ Xprev_msg () X { X ENTER (prev_msg); X if (!Smcount) return (0); X /* This routine actually pop the message stored */ X if (--Sdx < 0) Sdx = MAXSMSG-1; X screen (SCR_SAVE); X poscur ((unsigned char)24, (unsigned char)1, (char *)NULL); X screen (SCR_REVERSE); X screen (SCR_EEOL); X put_string (Savemsg[Sdx], 0); X Form_msg = 1; X screen (SCR_RESTORE); X RETURN (1); X } SHAR_EOF if test 2999 -ne "`wc -c < 'msg.c'`" then echo shar: error transmitting "'msg.c'" '(should have been 2999 characters)' fi fi # end of overwriting check echo shar: extracting "'term.c'" '(6575 characters)' if test -f 'term.c' then echo shar: will not over-write existing file "'term.c'" else sed 's/^X//' << \SHAR_EOF > 'term.c' X/* Last update: 01/13/88 11:16 AM (Edition: 9) */ X#include <stdio.h> X#include <ctype.h> X#include <strings.h> X#include "form.h" X X#define YES (1) X#define NO (0) X#define EOS '\0' X#define when break; case X#define otherwise break;default X Xstatic char *Erase = "\010 \010"; /* erase string */ X Xstruct tcap { X char *tc_id; /* key for capability */ X char *tc_str; /* ptr to Tc_str area */ X unsigned char tc_delay; /* # of msec to delay */ X unsigned char tc_len; /* length of tc_str */ X }; X Xstatic char Termcap [1024]; Xstatic char Tstr [1024]; /* buffer for real escape sequence */ Xstatic char *Tsp = Tstr; /* pointer to be used by tgetstr */ Xstatic int Tcap_count = 0; /* # of entries extracted */ X X/*-------- You may want to modify the following (also term.h) ----------*/ X#include "term.h" X Xstatic struct tcap Tcap [] = { X { "bc", 0, NULL, 0 }, /* cursor backspace */ X { "cm", 0, NULL, 0 }, /* cursor motion */ X { "cl", 0, NULL, 0 }, /* clear entire screen */ X { "cd", 0, NULL, 0 }, /* clear to end of display */ X { "ce", 0, NULL, 0 }, /* clear to end of line */ X { "ho", 0, NULL, 0 }, /* home cursor */ X { "ks", 0, NULL, 0 }, /* start keypad xmit mode */ X { "ke", 0, NULL, 0 }, /* end keypad xmit mode */ X { "ku", 0, NULL, 0 }, /* (input) cursor upper */ X { "kd", 0, NULL, 0 }, /* (input) cursor down */ X { "kl", 0, NULL, 0 }, /* (input) cursor left */ X { "kr", 0, NULL, 0 }, /* (input) cursor right */ X { "md", 0, NULL, 0 }, /* mode dim (or highlite) */ X { "me", 0, NULL, 0 }, /* mode end (return to normal) */ X { "rc", 0, NULL, 0 }, /* restore cursor */ X { "sc", 0, NULL, 0 }, /* save cursor */ X { "so", 0, NULL, 0 }, /* start reverse video mode */ X { "se", 0, NULL, 0 }, /* end */ X { "us", 0, NULL, 0 }, /* start underline mode */ X { "ue", 0, NULL, 0 }, /* end */ X { NULL, 0, NULL, 0 } X }; X Xchar *getenv (); Xchar *tgetstr (); Xchar *tgoto (); X X/*-------------------------------------------------------------05/10/86-+ X| | X| tcap_init : initialize termcap data structure | X| | X+----------------------------------------------------------------------*/ Xtcap_init () X { X struct tcap *p; X char *tp; X unsigned int delay; X int status; X char *termtype = getenv ("TERM"); X X if ((status = tgetent (Termcap, termtype)) != 1) { X if (status == 0) { X fprintf (stderr, "No entry for %s in termcap\r\n", X termtype); X } X else fprintf (stderr, "Can not open termcap file\r\n"); X exit (1); X } X X for (p= &Tcap[0]; p->tc_id != EOS; p++) { X tp = tgetstr (p-> tc_id, &Tsp); X if (tp == NULL) { /* no such capability */ X if (p == &Tcap[BC]) tp = "\010"; X else tp = ""; X } X delay = 0; X while (isdigit (*tp)) { X delay = delay*10 + (*tp++) - '0'; X } X p->tc_str = tp; X p->tc_delay = delay; X p->tc_len = strlen (tp); X Tcap_count++; X } X } X X/*----------------------------------------------------------------------+ X| | X| screen : common screen operation routine | X| | X+----------------------------------------------------------------------*/ Xscreen (code) Xint code; /* operation code */ X { X int n = BAD; /* init to not valid entry */ X struct tcap *te; X X if (Tcap_count == 0) tcap_init (); X switch (code) { X when SCR_DEL: put_string (Erase, 0); X when SCR_BACKSPACE: n = BC; X when SCR_ERASE: n = CL; X when SCR_HOME: n = HO; X when SCR_EEOL: n = CE; X when SCR_SAVE: n = SC; X when SCR_KEYXMIT: n = KS; X when SCR_NOKEYXMIT: n = KE; X when SCR_RESTORE: n = RC; X when SCR_REVERSE: n = SO; X when SCR_NORMAL: n = SE; X otherwise: ; /* ignore it */ X } X if (n != BAD) { X te = &Tcap[n]; X delay (te-> tc_delay); X put_string (te-> tc_str, (unsigned)te-> tc_len); X } X } X X/*----------------------------------------------------------------------+ X| | X| poscur : position cursor on line, column on screen | X| | X+----------------------------------------------------------------------*/ Xposcur (line, column, s) Xunsigned char line; Xunsigned char column; Xchar *s; /* option string to output at line, column */ X { X char *p; X X if (Tcap_count == 0) tcap_init (); X p = tgoto (Tcap[CM].tc_str, column-1, line-1); X delay (Tcap[CM].tc_delay); X put_string (p, 0); X if (s != NULL) put_string (s, 0); X } X X/*-------------------------------------------------------------05/10/86-+ X| | X| delay : delay output for n msec (actually write NULL) | X| | X+----------------------------------------------------------------------*/ Xstatic Xdelay (n) Xunsigned char n; /* # of msec to delay */ X { X static char c = EOS; X register int i; X X if (n == 0) return; X X for (i=0; i<n; i++) { X write (fileno (stdout), &c, 1); X } X } X X/*-------------------------------------------------------------05/11/86-+ X| | X| Routines to get mode-specific strings | X| | X+----------------------------------------------------------------------*/ Xget_undline (sbuf, ebuf) Xchar *sbuf; /* enter mode buffer */ Xchar *ebuf; /* exit mode buffer */ X { X if (Tcap_count == 0) tcap_init (); X strcpy (sbuf, Tcap[US].tc_str); X strcpy (ebuf, Tcap[UE].tc_str); X } X Xget_hilite (sbuf, ebuf) Xchar *sbuf; /* enter mode buffer */ Xchar *ebuf; /* exit mode buffer */ X { X if (Tcap_count == 0) tcap_init (); X strcpy (sbuf, Tcap[MD].tc_str); X strcpy (ebuf, Tcap[ME].tc_str); X } X Xget_rvideo (sbuf, ebuf) Xchar *sbuf; /* enter mode buffer */ Xchar *ebuf; /* exit mode buffer */ X { X if (Tcap_count == 0) tcap_init (); X strcpy (sbuf, Tcap[SO].tc_str); X strcpy (ebuf, Tcap[SE].tc_str); X } X X/*-------------------------------------------------------------07/05/87-+ X| | X| getkey : get user entered key (handle cursor key) | X| | X+----------------------------------------------------------------------*/ Xgetkey () X { X char buf[20]; /* temporary hold the input stream */ X char c; X register int i = 0; X register int ci = 0; /* current matched index */ X int idx; X char match; /* flag, YES/NO */ X char kmatch [4]; /* record how may char matched in X each key (KU, KD, KL, KR) */ X extern char get_char(); X X for (i=0; i<4; i++) kmatch[i] = 0; Xloop: X c = get_char () & 0x7f; /* make it ASCII */ X for (match=NO, i=0; i<4; i++) { X if (kmatch[i] < ci) continue; X switch (i) { X when 0: idx = KU; X when 1: idx = KD; X when 2: idx = KL; X when 3: idx = KR; X } X if (c == Tcap[idx].tc_str[ci]) { X kmatch[i]++; X if (Tcap[idx].tc_len == ci+1) { X ci = 0; X return (0x80 | idx); X } X match = YES; X } X } X buf[ci++] = c; /* save input char in temp buffer */ X if (match == YES) goto loop; X X pushback (&buf[1], ci-1); X return (buf[0]); X } SHAR_EOF if test 6575 -ne "`wc -c < 'term.c'`" then echo shar: error transmitting "'term.c'" '(should have been 6575 characters)' fi fi # end of overwriting check echo shar: extracting "'io.c'" '(4106 characters)' if test -f 'io.c' then echo shar: will not over-write existing file "'io.c'" else sed 's/^X//' << \SHAR_EOF > 'io.c' X/* Last update: 01/13/88 11:26 AM (Edition: 5) */ X#include <stdio.h> X#include <ctype.h> X#include <sys/file.h> X X#ifndef _SGTTYB_ X#include <sgtty.h> X#endif X Xint Term_input; Xint Term_output; Xextern int Debug; X/*-------------------------------------------------------------05/07/86-+ X| | X| put_string : write out a string to Term_output | X| | X+----------------------------------------------------------------------*/ Xput_string (s, len) Xchar *s; Xunsigned len; X { X if (len == 0) len = strlen (s); X if (Debug) { X register int i; X register char *p = s; X X for (i=0; i<len; i++) put_char (*p++); X } X else write (Term_output, s, (int)len); X } X X/*-------------------------------------------------------------05/07/86-+ X| | X| put_char : write out one char to Term_output | X| | X+----------------------------------------------------------------------*/ Xput_char (c) Xchar c; X { X if (Debug) { X if (isprint(c)) write (Term_output, &c, 1); X else { X char buf [2]; X buf[0] = (c < ' ') ? '^' : '~'; X buf[1] = (c | 0x40) & 0x5f; X write (Term_output, buf, 2); X } X } X else write (Term_output, &c, 1); X } X Xstatic char Pushbuf [80]; Xstatic int Pushi = 0; X/*-------------------------------------------------------------05/07/86-+ X| | X| get_char : get a char from Term_input | X| | X+----------------------------------------------------------------------*/ Xchar Xget_char () X { X char c; X register int i; X X if (Pushi > 0) { /* push buffer not empty */ X c = Pushbuf[0]; X Pushi--; X for (i=0; i<Pushi; i++) { X Pushbuf[i] = Pushbuf[i+1]; X } X return (c); X } X read (Term_input, &c, 1); X c &= 0x7f; /* make it ASCII */ X return (c); X } X Xpushback (buf, len) Xchar *buf; Xint len; X { X register char *p = &Pushbuf [Pushi]; X X Pushi += len; X while (len-- > 0) { X *p++ = *buf++; X } X } X Xstatic int Old_flags; Xstatic struct sgttyb Mode_tty; X/*-------------------------------------------------------------05/07/86-+ X| | X| cbreakio : enter/exit cbreak I/O mode | X| | X+----------------------------------------------------------------------*/ Xcbreakio (n) Xint n; /* 1 -- enter, 0 -- exit */ X { X static int cbreak_io = 0; X int ostate; X X ostate = cbreak_io; X if (n) { X if (!cbreak_io) { X open_tty (); X cbreak_io = 1; X } X } X else { X if (cbreak_io) { X close_tty (); X cbreak_io = 0; X } X } X return (ostate); X } X X/*-------------------------------------------------------------01/12/88-+ X| | X| term_init : open terminal for read/write | X| | X+----------------------------------------------------------------------*/ Xterm_init () X { X extern char *Prgname; X X if ((Term_input = open ("/dev/tty", O_RDONLY)) < 0) { X perror ("term_init: open(/dev/tty,r)"); X exit (1); X } X if ((Term_output = open ("/dev/tty", O_WRONLY)) < 0) { X perror ("term_init: open(/dev/tty,r)"); X exit (1); X } X X if (!isatty(Term_input) || !isatty(Term_output)) { X fprintf (stderr, "You have to run %s interactively\n", X Prgname); X exit (1); X } X } X X/*-------------------------------------------------------------01/12/88-+ X| | X| term_close : close terminal descriptors | X| | X+----------------------------------------------------------------------*/ Xterm_close () X { X close (Term_input); X close (Term_output); X } X/*------------------------------------------------------------07/10/84--+ X| | X| open_tty : open terminal in CBREAK mode without ECHO | X| | X+----------------------------------------------------------------------*/ Xstatic open_tty () X { X gtty (Term_input, &Mode_tty); X Old_flags = Mode_tty.sg_flags; /* save old setting */ X Mode_tty.sg_flags |= CBREAK; X Mode_tty.sg_flags &= ~(ECHO | CRMOD); X stty (Term_input, &Mode_tty); X } X X/*------------------------------------------------------------07/10/84--+ X| | X| close_tty : close terminal and restore original setting | X| | X+----------------------------------------------------------------------*/ Xstatic close_tty () X { X Mode_tty.sg_flags = Old_flags; X stty (Term_input, &Mode_tty); /* restore original setting */ X } SHAR_EOF if test 4106 -ne "`wc -c < 'io.c'`" then echo shar: error transmitting "'io.c'" '(should have been 4106 characters)' fi fi # end of overwriting check echo shar: extracting "'summary.c'" '(1880 characters)' if test -f 'summary.c' then echo shar: will not over-write existing file "'summary.c'" else sed 's/^X//' << \SHAR_EOF > 'summary.c' X/* Last update: 01/14/88 00:30 AM (Edition: 14) */ X#include <stdio.h> X#include "basic.h" X#include "form.h" X Xstatic char *Summary[] = { X" RETURN - terminate CTRL P or up arrow - vertical up one field", X" TAB - next field CTRL N or down arrow - vertical down one field", X" CTRL T - prev field Intr char - abort", X" CTRL L - refresh screen Stop char - stop process", X"", X"--- Editable Field --- --- Selection Field ---", X" Movement:", X" CTRL A - beginning of field SPACE - show next selection", X" CTRL E - end of field CTRL H - show prev selection", X" CTRL F - forward one char x - find next selection starts", X" or --> key with character 'x'", X" CTRL B - backword one char ? - get help message (-m flag)", X" or <-- key or CTRL H", X" Editing:", X" CTRL U - delete to start of field", X" CTRL K - delete to end of field", X" CTRL W - delete prev word", XNULL X}; X Xstatic char *Newline = "\r\n\r\n"; Xstatic char *Header = "Shell Form Version: "; Xextern char *Version; Xextern char *Copyright; Xextern char *Bugs; Xextern char get_char(); X/*-------------------------------------------------------------01/13/88-+ X| | X| show_summary : display on-line summary | X| | X+----------------------------------------------------------------------*/ Xshow_summary () X { X char **pp = Summary; X char *p; X X ENTER (show_summary); X screen (SCR_ERASE); X put_string (Header, 0); put_string (Version, 0); X put_string (Newline, 2); X put_string (Copyright, 0); put_string (Newline, 2); X put_string (Bugs, 0); put_string (Newline, 4); X while ((p = *pp++) != NULL) { X put_string (p, 0); X put_string (Newline, 2); X } X put_string ("\r\n Press SPACE to continue: ", 0); X while (get_char() != ' '); X EXIT; X } SHAR_EOF if test 1880 -ne "`wc -c < 'summary.c'`" then echo shar: error transmitting "'summary.c'" '(should have been 1880 characters)' fi fi # end of overwriting check # End of shell archive exit 0 -- Please send comp.sources.unix-related mail to rsalz@uunet.uu.net.