home *** CD-ROM | disk | FTP | other *** search
/ InfoMagic Source Code 1993 July / THE_SOURCE_CODE_CD_ROM.iso / bsd_srcs / usr.bin / tn3270 / tools / dohits.c next >
Encoding:
C/C++ Source or Header  |  1991-04-26  |  7.7 KB  |  296 lines

  1. /*-
  2.  * Copyright (c) 1988 The Regents of the University of California.
  3.  * All rights reserved.
  4.  *
  5.  * Redistribution and use in source and binary forms, with or without
  6.  * modification, are permitted provided that the following conditions
  7.  * are met:
  8.  * 1. Redistributions of source code must retain the above copyright
  9.  *    notice, this list of conditions and the following disclaimer.
  10.  * 2. Redistributions in binary form must reproduce the above copyright
  11.  *    notice, this list of conditions and the following disclaimer in the
  12.  *    documentation and/or other materials provided with the distribution.
  13.  * 3. All advertising materials mentioning features or use of this software
  14.  *    must display the following acknowledgement:
  15.  *    This product includes software developed by the University of
  16.  *    California, Berkeley and its contributors.
  17.  * 4. Neither the name of the University nor the names of its contributors
  18.  *    may be used to endorse or promote products derived from this software
  19.  *    without specific prior written permission.
  20.  *
  21.  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  22.  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  23.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  24.  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  25.  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  26.  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  27.  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  28.  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  29.  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  30.  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  31.  * SUCH DAMAGE.
  32.  */
  33.  
  34. #ifndef lint
  35. static char sccsid[] = "@(#)dohits.c    4.2 (Berkeley) 4/26/91";
  36. #endif /* not lint */
  37.  
  38. /*
  39.  * This program scans a file which describes a keyboard.  The output
  40.  * of the program is a series of 'C' declarations which describe a
  41.  * mapping between (scancode, shiftstate, altstate) and 3270 functions,
  42.  * characters, and AIDs.
  43.  *
  44.  * The format of the input file is as follows:
  45.  *
  46.  * keynumber [ scancode [ unshifted [ shifted [ alted [ shiftalted ] ] ] ] ]
  47.  *
  48.  * keynumber is in decimal, and starts in column 1.
  49.  * scancode is hexadecimal.
  50.  * unshifted, etc. - these are either a single ascii character,
  51.  *            or the name of a function or an AID-generating key.
  52.  *
  53.  * all fields are separated by a single space.
  54.  */
  55.  
  56. #include <stdio.h>
  57. #if    defined(unix)
  58. #include <strings.h>
  59. #else    /* defined(unix) */
  60. #include <string.h>
  61. #endif    /* defined(unix) */
  62. #include <ctype.h>
  63. #include "../general/general.h"
  64. #include "../api/asc_ebc.h"
  65. #include "../api/ebc_disp.h"
  66. #include "../ctlr/function.h"
  67.  
  68. #include "dohits.h"
  69.  
  70. struct Hits Hits[256];        /* one for each of 0x00-0xff */
  71.  
  72. struct thing *table[100];
  73.  
  74. extern char *malloc();
  75.  
  76. unsigned int
  77. dohash(seed, string)
  78. unsigned int seed;
  79. char *string;
  80. {
  81.     register unsigned int i = seed;
  82.     register unsigned char c;
  83.  
  84.     while (c = *string++) {
  85.     if (c >= 0x60) {
  86.         c -= (0x60+0x20);
  87.     } else {
  88.         c -= 0x20;
  89.     }
  90.     i = (i>>26) + (i<<6) + (c&0x3f);
  91.     }
  92.     return i;
  93. }
  94.  
  95. void
  96. add(first, second, value)
  97. char *first, *second;
  98. int value;
  99. {
  100.     struct thing **item, *this;
  101.  
  102.     item = &firstentry(second);
  103.     this = (struct thing *) malloc(sizeof *this);
  104.     this->next = *item;
  105.     *item = this;
  106.     this->value = value;
  107.     strcpy(this->name, first);
  108.     strcpy(this->name+strlen(this->name), second);
  109. }
  110.  
  111. void
  112. scanwhite(file, prefix)
  113. char *file,        /* Name of file to scan for whitespace prefix */
  114.      *prefix;        /* prefix of what should be picked up */
  115. {
  116.     FILE *ourfile;
  117.     char compare[100];
  118.     char what[100], value[100];
  119.     char line[200];
  120.  
  121.     sprintf(compare, " %s%%[^,\t \n]", prefix);
  122.     if ((ourfile = fopen(file, "r")) == NULL) {
  123.     perror("fopen");
  124.     exit(1);
  125.     }
  126.     while (!feof(ourfile)) {
  127.     if (fscanf(ourfile, compare,  what) == 1) {
  128.         add(prefix, what, 0);
  129.     }
  130.     do {
  131.         if (fgets(line, sizeof line, ourfile) == NULL) {
  132.         if (!feof(ourfile)) {
  133.             perror("fgets");
  134.         }
  135.         break;
  136.         }
  137.     } while (line[strlen(line)-1] != '\n');
  138.     }
  139. }
  140.  
  141. void
  142. scandefine(file, prefix)
  143. char *file,        /* Name of file to scan for #define prefix */
  144.      *prefix;        /* prefix of what should be picked up */
  145. {
  146.     FILE *ourfile;
  147.     char compare[100];
  148.     char what[100], value[100];
  149.     char line[200];
  150.     int whatitis;
  151.  
  152.     sprintf(compare, "#define %s%%s %%s", prefix);
  153.     if ((ourfile = fopen(file, "r")) == NULL) {
  154.     perror("fopen");
  155.     exit(1);
  156.     }
  157.     while (!feof(ourfile)) {
  158.     if (fscanf(ourfile, compare,  what, value) == 2) {
  159.         if (value[0] == '0') {
  160.         if ((value[1] == 'x') || (value[1] == 'X')) {
  161.             sscanf(value, "0x%x", &whatitis);
  162.         } else {
  163.             sscanf(value, "0%o", &whatitis);
  164.         }
  165.         } else {
  166.         sscanf(value, "%d", &whatitis);
  167.         }
  168.         add(prefix, what, whatitis);
  169.     }
  170.     do {
  171.         if (fgets(line, sizeof line, ourfile) == NULL) {
  172.         if (!feof(ourfile)) {
  173.             perror("fgets");
  174.         }
  175.         break;
  176.         }
  177.     } while (line[strlen(line)-1] != '\n');
  178.     }
  179. }
  180.  
  181. char *savechr(c)
  182. unsigned char c;
  183. {
  184.     char *foo;
  185.  
  186.     foo = malloc(sizeof c);
  187.     if (foo == 0) {
  188.     fprintf(stderr, "No room for ascii characters!\n");
  189.     exit(1);
  190.     }
  191.     *foo = c;
  192.     return foo;
  193. }
  194.  
  195. char *
  196. doit(hit, type, hits)
  197. struct hit *hit;
  198. unsigned char *type;
  199. struct Hits *hits;
  200. {
  201.     struct thing *this;
  202.  
  203.     hit->ctlrfcn = FCN_NULL;
  204.     if (type[0] == 0) {
  205.     return 0;
  206.     }
  207.     if (type[1] == 0) {        /* character */
  208.     hit->ctlrfcn = FCN_CHARACTER;
  209.     hit->code = ebc_disp[asc_ebc[type[0]]];
  210.     return savechr(*type);        /* The character is the name */
  211.     } else {
  212.     for (this = firstentry(type); this; this = this->next) {
  213.         if ((type[0] == this->name[4])
  214.                 && (strcmp(type, this->name+4) == 0)) {
  215.         this->hits = hits;
  216.         if (this->name[0] == 'F') {
  217.             hit->ctlrfcn = FCN_NULL;    /* XXX */
  218.         } else {
  219.             hit->ctlrfcn = FCN_AID;
  220.         }
  221.         return this->name;
  222.         }
  223.     }
  224.     fprintf(stderr, "Error: Unknown type %s.\n", type);
  225.     return 0;
  226.     }
  227. }
  228.  
  229.  
  230. void
  231. dohits(aidfile, fcnfile)
  232. char    *aidfile, *fcnfile;
  233. {
  234.     unsigned char plain[100], shifted[100], alted[100], shiftalted[100];
  235.     unsigned char line[200];
  236.     int keynumber, scancode;
  237.     int empty;
  238.     int i;
  239.     struct hit *hit;
  240.     struct hits *ph;
  241.     struct Hits *Ph;
  242.  
  243.     memset((char *)Hits, 0, sizeof Hits);
  244.  
  245.     /*
  246.      * First, we read "host3270.h" to find the names/values of
  247.      * various AID; then we read kbd3270.h to find the names/values
  248.      * of various FCNs.
  249.      */
  250.  
  251.     if (aidfile == 0) {
  252.     aidfile = "../ctlr/hostctlr.h";
  253.     }
  254.     scandefine(aidfile, "AID_");
  255.     if (fcnfile == 0) {
  256.         fcnfile = "../ctlr/function.h";
  257.     }
  258.     scanwhite(fcnfile, "FCN_");
  259.  
  260.     while (gets(line) != NULL) {
  261.     if (!isdigit(line[0])) {
  262.         continue;
  263.     }
  264.     plain[0] = shifted[0] = alted[0] = shiftalted[0] = 0;
  265.     keynumber = -1;
  266.     scancode = -1;
  267.     (void) sscanf(line, "%d %x %s %s %s %s", &keynumber,
  268.             &scancode, plain, shifted, alted, shiftalted);
  269.     if ((keynumber == -1) || (scancode == -1)
  270.         || ((plain[0] == 0)
  271.             && (shifted[0] == 0)
  272.             && (alted[0] == 0)
  273.             && (shiftalted[0] == 0))) {
  274.         continue;
  275.     }
  276.     if (scancode >= 256) {
  277.         fprintf(stderr,
  278.         "Error: scancode 0x%02x for keynumber %d\n", scancode,
  279.             keynumber);
  280.         break;
  281.     }
  282.     if (Hits[scancode].hits.hit[0].ctlrfcn != undefined) {
  283.         fprintf(stderr,
  284.         "Error: duplicate scancode 0x%02x for keynumber %d\n",
  285.             scancode, keynumber);
  286.         break;
  287.     }
  288.     hit = Hits[scancode].hits.hit;
  289.     Hits[scancode].hits.keynumber = keynumber;
  290.     Hits[scancode].name[0] = doit(hit, plain, &Hits[scancode]);
  291.     Hits[scancode].name[1] = doit(hit+1, shifted, &Hits[scancode]);
  292.     Hits[scancode].name[2] = doit(hit+2, alted, &Hits[scancode]);
  293.     Hits[scancode].name[3] = doit(hit+3, shiftalted, &Hits[scancode]);
  294.     }
  295. }
  296.