1 /*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License"). You may not use this file except in compliance
7 * with the License.
8 *
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
13 *
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
19 *
20 * CDDL HEADER END
21 */
22 /*
23 * Copyright 1997 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
25 */
26
27 /* Copyright (c) 1988 AT&T */
28 /* All Rights Reserved */
29
30 /*
31 * University Copyright- Copyright (c) 1982, 1986, 1988
32 * The Regents of the University of California
33 * All Rights Reserved
34 *
35 * University Acknowledgment- Portions of this document are derived from
36 * software developed by the University of California, Berkeley, and its
37 * contributors.
38 */
39
40 /*LINTLIBRARY*/
41
42 #include <sys/types.h>
43 #include <stdlib.h>
44 #include <string.h>
45 #include "curses_inc.h"
46
47 static short keycodes[] = {
48 KEY_BACKSPACE,
49 KEY_CATAB,
50 KEY_CLEAR,
51 KEY_CTAB,
52 KEY_DC,
53 KEY_DL,
54 KEY_DOWN,
55 KEY_EIC,
56 KEY_EOL,
57 KEY_EOS,
58 KEY_F(0),
59 KEY_F(1),
60 KEY_F(10),
61 KEY_F(2),
62 KEY_F(3),
63 KEY_F(4),
64 KEY_F(5),
65 KEY_F(6),
66 KEY_F(7),
67 KEY_F(8),
68 KEY_F(9),
69 KEY_HOME,
70 KEY_IC,
71 KEY_IL,
72 KEY_LEFT,
73 KEY_LL,
74 KEY_NPAGE,
75 KEY_PPAGE,
76 KEY_RIGHT,
77 KEY_SF,
78 KEY_SR,
79 KEY_STAB,
80 KEY_UP,
81 KEY_A1,
82 KEY_A3,
83 KEY_B2,
84 KEY_C1,
85 KEY_C3,
86 KEY_BTAB,
87 KEY_BEG,
88 KEY_CANCEL,
89 KEY_CLOSE,
90 KEY_COMMAND,
91 KEY_COPY,
92 KEY_CREATE,
93 KEY_END,
94 KEY_ENTER,
95 KEY_EXIT,
96 KEY_FIND,
97 KEY_HELP,
98 KEY_MARK,
99 KEY_MESSAGE,
100 KEY_MOVE,
101 KEY_NEXT,
102 KEY_OPEN,
103 KEY_OPTIONS,
104 KEY_PREVIOUS,
105 KEY_PRINT,
106 KEY_REDO,
107 KEY_REFERENCE,
108 KEY_REFRESH,
109 KEY_REPLACE,
110 KEY_RESTART,
111 KEY_RESUME,
112 KEY_SAVE,
113 KEY_SUSPEND,
114 KEY_UNDO,
115 KEY_SBEG,
116 KEY_SCANCEL,
117 KEY_SCOMMAND,
118 KEY_SCOPY,
119 KEY_SCREATE,
120 KEY_SDC,
121 KEY_SDL,
122 KEY_SELECT,
123 KEY_SEND,
124 KEY_SEOL,
125 KEY_SEXIT,
126 KEY_SFIND,
127 KEY_SHELP,
128 KEY_SHOME,
129 KEY_SIC,
130 KEY_SLEFT,
131 KEY_SMESSAGE,
132 KEY_SMOVE,
133 KEY_SNEXT,
134 KEY_SOPTIONS,
135 KEY_SPREVIOUS,
136 KEY_SPRINT,
137 KEY_SREDO,
138 KEY_SREPLACE,
139 KEY_SRIGHT,
140 KEY_SRSUME,
141 KEY_SSAVE,
142 KEY_SSUSPEND,
143 KEY_SUNDO,
144 KEY_MOUSE
145 };
146
147 static _KEY_MAP *p;
148 static bool *funckey;
149 static short *codeptr;
150
151 static void
_laddone(char * txt)152 _laddone(char *txt)
153 {
154 p->_sends = (txt);
155 p->_keyval = *codeptr;
156 funckey[(unsigned char)(txt)[0]] |= _KEY;
157 p++;
158 }
159
160 /* Map text into num, updating the map structure p. */
161
162 static void
_keyfunc(char ** keyptr,char ** lastkey)163 _keyfunc(char **keyptr, char **lastkey)
164 {
165 for (; keyptr <= lastkey; keyptr++, codeptr++)
166 if (*keyptr) {
167 p->_sends = (*keyptr);
168 p->_keyval = *codeptr;
169 funckey[(unsigned char)(*keyptr)[0]] |= _KEY;
170 p++;
171 }
172 }
173
174 /* Map text into num, updating the map structure p. */
175
176 static void
_keyfunc2(char ** keyptr,char ** lastkey)177 _keyfunc2(char **keyptr, char **lastkey)
178 {
179 short code_value = KEY_F(11);
180
181 for (; *keyptr && keyptr <= lastkey; keyptr++, code_value++) {
182 p->_sends = *keyptr;
183 p->_keyval = (short) code_value;
184 funckey[(unsigned char)*keyptr[0]] |= _KEY;
185 p++;
186 }
187 }
188
189 int
setkeymap(void)190 setkeymap(void)
191 {
192 _KEY_MAP keymap[((sizeof (keycodes) / sizeof (short)) +
193 ((KEY_F(63) - KEY_F(11)) + 1))], **key_ptrs;
194 short numkeys;
195 int numbytes, key_size = cur_term->_ksz;
196
197 if (cur_term->internal_keys != NULL)
198 return (ERR);
199 p = keymap;
200 codeptr = keycodes;
201 funckey = cur_term->funckeystarter;
202
203 /* If backspace key sends \b, don't map it. */
204 if (key_backspace && strcmp(key_backspace, "\b"))
205 _laddone(key_backspace);
206 codeptr++;
207
208 _keyfunc(&key_catab, &key_dl);
209
210 /* If down arrow key sends \n, don't map it. */
211 if (key_down && strcmp(key_down, "\n"))
212 _laddone(key_down);
213 codeptr++;
214
215 _keyfunc(&key_eic, &key_il);
216
217 /* If left arrow key sends \b, don't map it. */
218 if (key_left && strcmp(key_left, "\b"))
219 _laddone(key_left);
220 codeptr++;
221
222 _keyfunc(&key_ll, &key_up);
223 _keyfunc(&key_a1, &key_c3);
224 _keyfunc(&key_btab, &key_btab);
225 _keyfunc(&key_beg, &key_sundo);
226 _keyfunc2(&key_f11, &key_f63);
227 _keyfunc(&key_mouse, &key_mouse);
228
229 /*
230 * malloc returns the address of a list of pointers to
231 * (_KEY_MAP *) structures
232 */
233
234 if ((key_ptrs = (_KEY_MAP **)
235 /* LINTED */
236 malloc((key_size + (numkeys = (short)(p - keymap))) *
237 sizeof (_KEY_MAP *))) == NULL) {
238 goto out;
239 }
240
241 /*
242 * Number of bytes needed is the number of structures times their size
243 * malloc room for our array of _KEY_MAP structures
244 */
245
246 if ((p = (_KEY_MAP *) malloc((unsigned)
247 /* LINTED */
248 (numbytes = (int)(sizeof (_KEY_MAP) * numkeys)))) == NULL) {
249 /* Can't do it, free list of pointers, indicate */
250 /* error upon return. */
251 free((char *) key_ptrs);
252 out:
253 term_errno = TERM_BAD_MALLOC;
254 #ifdef DEBUG
255 strcpy(term_parm_err, "setkeymap");
256 termerr();
257 #endif /* DEBUG */
258 return (ERR);
259 }
260
261 if (key_size != 0) {
262 (void) memcpy((char *) &(key_ptrs[numkeys]),
263 (char *) cur_term->_keys, (key_size *
264 sizeof (_KEY_MAP *)));
265 free(cur_term->_keys);
266 }
267 (void) memcpy((char *) (cur_term->internal_keys = p),
268 (char *) keymap, numbytes);
269 cur_term->_keys = key_ptrs;
270 cur_term->_ksz += numkeys;
271 /*
272 * Reset _lastkey_ordered to -1 since we put the keys read in
273 * from terminfo at the beginning of the keys table.
274 */
275 cur_term->_lastkey_ordered = -1;
276 cur_term->_lastmacro_ordered += numkeys;
277 cur_term->_first_macro += numkeys;
278
279 /* Initialize our pointers to the structures */
280 while (numkeys--)
281 *key_ptrs++ = p++;
282 #ifdef DEBUG
283 if (outf)
284 fprintf(outf, "return key structure %x, ending at %x\n",
285 keymap, p);
286 #endif /* DEBUG */
287 return (OK);
288 }
289