1 /* $NetBSD: dohits.c,v 1.13 2003/08/07 11:16:42 agc Exp $ */
4 * Copyright (c) 1988 The Regents of the University of California.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. Neither the name of the University nor the names of its contributors
16 * may be used to endorse or promote products derived from this software
17 * without specific prior written permission.
19 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
23 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
38 #if defined(__RCSID) && !defined(lint)
40 static char sccsid
[] = "@(#)dohits.c 4.2 (Berkeley) 4/26/91";
42 __RCSID("$NetBSD: dohits.c,v 1.13 2003/08/07 11:16:42 agc Exp $");
47 * This program scans a file which describes a keyboard. The output
48 * of the program is a series of 'C' declarations which describe a
49 * mapping between (scancode, shiftstate, altstate) and 3270 functions,
50 * characters, and AIDs.
52 * The format of the input file is as follows:
54 * keynumber [ scancode [ unshifted [ shifted [ alted [ shiftalted ] ] ] ] ]
56 * keynumber is in decimal, and starts in column 1.
57 * scancode is hexadecimal.
58 * unshifted, etc. - these are either a single ascii character,
59 * or the name of a function or an AID-generating key.
61 * all fields are separated by a single space.
64 #include "../general/general.h"
65 #include "../api/asc_ebc.h"
66 #include "../api/ebc_disp.h"
67 #include "../ctlr/function.h"
71 struct Hits Hits
[256]; /* one for each of 0x00-0xff */
73 struct thing
*table
[100];
75 static void add(const char *, const char *, int);
76 static void scanwhite(const char *, const char *);
77 static void scandefine(const char *, const char *);
78 static char *savechr(unsigned int);
79 static char *doit(struct hit
*, unsigned char *, struct Hits
*);
86 unsigned int i
= seed
;
89 while ((c
= *string
++) != '\0') {
95 i
= (i
>>26) + (i
<<6) + (c
&0x3f);
101 add(first
, second
, value
)
102 const char *first
, *second
;
105 struct thing
**item
, *this;
107 item
= &firstentry(second
);
108 this = (struct thing
*) malloc(sizeof *this);
113 strcpy(this->name
, first
);
114 strcpy(this->name
+strlen(this->name
), second
);
118 scanwhite(file
, prefix
)
119 const char *file
, /* Name of file to scan for whitespace prefix */
120 *prefix
; /* prefix of what should be picked up */
127 (void) snprintf(compare
, sizeof(compare
), " %s%%[^,\t \n]", prefix
);
128 if ((ourfile
= fopen(file
, "r")) == NULL
) {
129 fprintf(stderr
, "Cannot open `%s': %s\n", file
, strerror(errno
));
132 while (!feof(ourfile
)) {
133 if (fscanf(ourfile
, compare
, what
) == 1) {
134 add(prefix
, what
, 0);
137 if (fgets(line
, sizeof line
, ourfile
) == NULL
) {
138 if (!feof(ourfile
)) {
139 fprintf(stderr
, "fgets failed: %s\n", strerror(errno
));
143 } while (line
[strlen(line
)-1] != '\n');
145 (void)fclose(ourfile
);
149 scandefine(file
, prefix
)
150 const char *file
, /* Name of file to scan for #define prefix */
151 *prefix
; /* prefix of what should be picked up */
155 char what
[100], value
[100];
159 snprintf(compare
, sizeof(compare
), "#define %s%%s %%s", prefix
);
160 if ((ourfile
= fopen(file
, "r")) == NULL
) {
161 fprintf(stderr
, "Cannot open `%s': %s\n", file
, strerror(errno
));
165 while (!feof(ourfile
)) {
166 if (fscanf(ourfile
, compare
, what
, value
) == 2) {
167 if (value
[0] == '0') {
168 if ((value
[1] == 'x') || (value
[1] == 'X')) {
169 sscanf(value
, "0x%x", &whatitis
);
171 sscanf(value
, "0%o", &whatitis
);
174 sscanf(value
, "%d", &whatitis
);
176 add(prefix
, what
, whatitis
);
179 if (fgets(line
, sizeof line
, ourfile
) == NULL
) {
180 if (!feof(ourfile
)) {
181 fprintf(stderr
, "End of file with error: %s\n",
186 } while (line
[strlen(line
)-1] != '\n');
188 (void)fclose(ourfile
);
191 static char *savechr(c
)
194 char *foo
= malloc(sizeof(unsigned char));
196 fprintf(stderr
, "No room for ascii characters\n");
204 doit(hit
, type
, hits
)
211 hit
->ctlrfcn
= FCN_NULL
;
215 if (type
[1] == 0) { /* character */
216 hit
->ctlrfcn
= FCN_CHARACTER
;
217 hit
->code
= ebc_disp
[asc_ebc
[type
[0]]];
218 return savechr(*type
); /* The character is the name */
220 for (this = firstentry(type
); this; this = this->next
) {
221 if ((type
[0] == this->name
[4])
222 && (strcmp(type
, this->name
+4) == 0)) {
224 if (this->name
[0] == 'F') {
225 hit
->ctlrfcn
= FCN_NULL
; /* XXX */
227 hit
->ctlrfcn
= FCN_AID
;
232 fprintf(stderr
, "Unknown type %s.\n", type
);
239 dohits(aidfile
, fcnfile
)
240 const char *aidfile
, *fcnfile
;
242 unsigned char plain
[100], shifted
[100], alted
[100], shiftalted
[100];
243 unsigned char line
[200];
244 int keynumber
, scancode
;
247 memset((char *)Hits
, 0, sizeof Hits
);
250 * First, we read "host3270.h" to find the names/values of
251 * various AID; then we read kbd3270.h to find the names/values
256 aidfile
= "../ctlr/hostctlr.h";
258 scandefine(aidfile
, "AID_");
260 fcnfile
= "../ctlr/function.h";
262 scanwhite(fcnfile
, "FCN_");
264 while (fgets(line
, sizeof(line
), stdin
) != NULL
) {
265 if (line
[strlen(line
)-1] == '\n')
266 line
[strlen(line
)-1] = '\0';
267 if (!isdigit(line
[0])) {
270 plain
[0] = shifted
[0] = alted
[0] = shiftalted
[0] = 0;
273 (void) sscanf(line
, "%d %x %s %s %s %s", &keynumber
,
274 &scancode
, plain
, shifted
, alted
, shiftalted
);
275 if ((keynumber
== -1) || (scancode
== -1)
279 && (shiftalted
[0] == 0))) {
282 if (scancode
>= 256) {
283 fprintf(stderr
, "Scancode 0x%02x for keynumber %d\n", scancode
,
287 if (Hits
[scancode
].hits
.hit
[0].ctlrfcn
!= undefined
) {
288 fprintf(stderr
, "Duplicate scancode 0x%02x for keynumber %d\n",
289 scancode
, keynumber
);
292 hit
= Hits
[scancode
].hits
.hit
;
293 Hits
[scancode
].hits
.keynumber
= keynumber
;
294 Hits
[scancode
].name
[0] = doit(hit
, plain
, &Hits
[scancode
]);
295 Hits
[scancode
].name
[1] = doit(hit
+1, shifted
, &Hits
[scancode
]);
296 Hits
[scancode
].name
[2] = doit(hit
+2, alted
, &Hits
[scancode
]);
297 Hits
[scancode
].name
[3] = doit(hit
+3, shiftalted
, &Hits
[scancode
]);