Mercurial > hg > xemacs-beta
comparison src/keymap.c @ 412:697ef44129c6 r21-2-14
Import from CVS: tag r21-2-14
author | cvs |
---|---|
date | Mon, 13 Aug 2007 11:20:41 +0200 |
parents | b8cc9ab3f761 |
children | 41dbb7a9d5f2 |
comparison
equal
deleted
inserted
replaced
411:12e008d41344 | 412:697ef44129c6 |
---|---|
35 #include "events.h" | 35 #include "events.h" |
36 #include "frame.h" | 36 #include "frame.h" |
37 #include "insdel.h" | 37 #include "insdel.h" |
38 #include "keymap.h" | 38 #include "keymap.h" |
39 #include "window.h" | 39 #include "window.h" |
40 | |
41 #ifdef WINDOWSNT | |
42 /* Hmm, under unix we want X modifiers, under NT we want X modifiers if | |
43 we are running X and Windows modifiers otherwise. | |
44 gak. This is a kludge until we support multiple native GUIs! | |
45 */ | |
46 #undef MOD_ALT | |
47 #undef MOD_CONTROL | |
48 #undef MOD_SHIFT | |
49 #endif | |
50 | |
40 #include "events-mod.h" | 51 #include "events-mod.h" |
41 | 52 |
42 | 53 |
43 /* A keymap contains six slots: | 54 /* A keymap contains six slots: |
44 | 55 |
86 off of the main map. The hash key for a modifier combination is | 97 off of the main map. The hash key for a modifier combination is |
87 an integer, computed by MAKE_MODIFIER_HASH_KEY(). | 98 an integer, computed by MAKE_MODIFIER_HASH_KEY(). |
88 | 99 |
89 If the key `C-a' was bound to some command, the hierarchy would look like | 100 If the key `C-a' was bound to some command, the hierarchy would look like |
90 | 101 |
91 keymap-1: associates the integer XEMACS_MOD_CONTROL with keymap-2 | 102 keymap-1: associates the integer MOD_CONTROL with keymap-2 |
92 keymap-2: associates "a" with the command | 103 keymap-2: associates "a" with the command |
93 | 104 |
94 Similarly, if the key `C-H-a' was bound to some command, the hierarchy | 105 Similarly, if the key `C-H-a' was bound to some command, the hierarchy |
95 would look like | 106 would look like |
96 | 107 |
97 keymap-1: associates the integer (XEMACS_MOD_CONTROL | XEMACS_MOD_HYPER) | 108 keymap-1: associates the integer (MOD_CONTROL | MOD_HYPER) |
98 with keymap-2 | 109 with keymap-2 |
99 keymap-2: associates "a" with the command | 110 keymap-2: associates "a" with the command |
100 | 111 |
101 Note that a special exception is made for the meta modifier, in order | 112 Note that a special exception is made for the meta modifier, in order |
102 to deal with ESC/meta lossage. Any key combination containing the | 113 to deal with ESC/meta lossage. Any key combination containing the |
103 meta modifier is first indexed off of the main map into the meta | 114 meta modifier is first indexed off of the main map into the meta |
104 submap (with hash key XEMACS_MOD_META) and then indexed off of the | 115 submap (with hash key MOD_META) and then indexed off of the |
105 meta submap with the meta modifier removed from the key combination. | 116 meta submap with the meta modifier removed from the key combination. |
106 For example, when associating a command with C-M-H-a, we'd have | 117 For example, when associating a command with C-M-H-a, we'd have |
107 | 118 |
108 keymap-1: associates the integer XEMACS_MOD_META with keymap-2 | 119 keymap-1: associates the integer MOD_META with keymap-2 |
109 keymap-2: associates the integer (XEMACS_MOD_CONTROL | XEMACS_MOD_HYPER) | 120 keymap-2: associates the integer (MOD_CONTROL | MOD_HYPER) |
110 with keymap-3 | 121 with keymap-3 |
111 keymap-3: associates "a" with the command | 122 keymap-3: associates "a" with the command |
112 | 123 |
113 Note that keymap-2 might have normal bindings in it; these would be | 124 Note that keymap-2 might have normal bindings in it; these would be |
114 for key combinations containing only the meta modifier, such as | 125 for key combinations containing only the meta modifier, such as |
118 then that would make the key "C-M-H-a" be a prefix character. | 129 then that would make the key "C-M-H-a" be a prefix character. |
119 | 130 |
120 Note that this new model of keymaps takes much of the magic away from | 131 Note that this new model of keymaps takes much of the magic away from |
121 the Escape key: the value of the variable `esc-map' is no longer indexed | 132 the Escape key: the value of the variable `esc-map' is no longer indexed |
122 in the `global-map' under the ESC key. It's indexed under the integer | 133 in the `global-map' under the ESC key. It's indexed under the integer |
123 XEMACS_MOD_META. This is not user-visible, however; none of the "bucky" | 134 MOD_META. This is not user-visible, however; none of the "bucky" |
124 maps are. | 135 maps are. |
125 | 136 |
126 There is a hack in Flookup_key() that makes (lookup-key global-map "\^[") | 137 There is a hack in Flookup_key() that makes (lookup-key global-map "\^[") |
127 and (define-key some-random-map "\^[" my-esc-map) work as before, for | 138 and (define-key some-random-map "\^[" my-esc-map) work as before, for |
128 compatibility. | 139 compatibility. |
129 | 140 |
130 Since keymaps are opaque, the only way to extract information from them | 141 Since keymaps are opaque, the only way to extract information from them |
131 is with the functions lookup-key, key-binding, local-key-binding, and | 142 is with the functions lookup-key, key-binding, local-key-binding, and |
132 global-key-binding, which work just as before, and the new function | 143 global-key-binding, which work just as before, and the new function |
133 map-keymap, which is roughly analogous to maphash. | 144 map-keymap, which is roughly analagous to maphash. |
134 | 145 |
135 Note that map-keymap perpetuates the illusion that the "bucky" submaps | 146 Note that map-keymap perpetuates the illusion that the "bucky" submaps |
136 don't exist: if you map over a keymap with bucky submaps, it will also | 147 don't exist: if you map over a keymap with bucky submaps, it will also |
137 map over those submaps. It does not, however, map over other random | 148 map over those submaps. It does not, however, map over other random |
138 submaps of the keymap, just the bucky ones. | 149 submaps of the keymap, just the bucky ones. |
143 distinction between ESC and "meta" even more. "M-x" is no more a two- | 154 distinction between ESC and "meta" even more. "M-x" is no more a two- |
144 key sequence than "C-x" is. | 155 key sequence than "C-x" is. |
145 | 156 |
146 */ | 157 */ |
147 | 158 |
148 struct Lisp_Keymap | 159 typedef struct Lisp_Keymap |
149 { | 160 { |
150 struct lcrecord_header header; | 161 struct lcrecord_header header; |
151 Lisp_Object parents; /* Keymaps to be searched after this one. | 162 Lisp_Object parents; /* Keymaps to be searched after this one |
152 An ordered list */ | 163 * An ordered list */ |
153 Lisp_Object prompt; /* Qnil or a string to print in the minibuffer | 164 Lisp_Object prompt; /* Qnil or a string to print in the minibuffer |
154 when reading from this keymap */ | 165 * when reading from this keymap */ |
166 | |
155 Lisp_Object table; /* The contents of this keymap */ | 167 Lisp_Object table; /* The contents of this keymap */ |
156 Lisp_Object inverse_table; /* The inverse mapping of the above */ | 168 Lisp_Object inverse_table; /* The inverse mapping of the above */ |
169 | |
157 Lisp_Object default_binding; /* Use this if no other binding is found | 170 Lisp_Object default_binding; /* Use this if no other binding is found |
158 (this overrides parent maps and the | 171 * (this overrides parent maps and the |
159 normal global-map lookup). */ | 172 * normal global-map lookup). */ |
173 | |
174 | |
160 Lisp_Object sub_maps_cache; /* Cache of directly inferior keymaps; | 175 Lisp_Object sub_maps_cache; /* Cache of directly inferior keymaps; |
161 This holds an alist, of the key and the | 176 This holds an alist, of the key and the |
162 maps, or the modifier bit and the map. | 177 maps, or the modifier bit and the map. |
163 If this is the symbol t, then the cache | 178 If this is the symbol t, then the cache |
164 needs to be recomputed. */ | 179 needs to be recomputed. |
180 */ | |
181 int fullness; /* How many entries there are in this table. | |
182 This should be the same as the fullness | |
183 of the `table', but hash.c is broken. */ | |
165 Lisp_Object name; /* Just for debugging convenience */ | 184 Lisp_Object name; /* Just for debugging convenience */ |
166 }; | 185 } Lisp_Keymap; |
167 | 186 |
168 #define MAKE_MODIFIER_HASH_KEY(modifier) make_int (modifier) | 187 #define MAKE_MODIFIER_HASH_KEY(modifier) make_int (modifier) |
169 #define MODIFIER_HASH_KEY_BITS(x) (INTP (x) ? XINT (x) : 0) | 188 #define MODIFIER_HASH_KEY_BITS(x) (INTP (x) ? XINT (x) : 0) |
170 | 189 |
171 | 190 |
172 | 191 |
173 /* Actually allocate storage for these variables */ | 192 /* Actually allocate storage for these variables */ |
174 | 193 |
175 Lisp_Object Vcurrent_global_map; /* Always a keymap */ | 194 static Lisp_Object Vcurrent_global_map; /* Always a keymap */ |
176 | 195 |
177 static Lisp_Object Vmouse_grabbed_buffer; | 196 static Lisp_Object Vmouse_grabbed_buffer; |
178 | 197 |
179 /* Alist of minor mode variables and keymaps. */ | 198 /* Alist of minor mode variables and keymaps. */ |
180 static Lisp_Object Qminor_mode_map_alist; | 199 static Lisp_Object Qminor_mode_map_alist; |
209 void (*elt_describer) (Lisp_Object, Lisp_Object), | 228 void (*elt_describer) (Lisp_Object, Lisp_Object), |
210 int partial, | 229 int partial, |
211 Lisp_Object shadow, | 230 Lisp_Object shadow, |
212 int mice_only_p, | 231 int mice_only_p, |
213 Lisp_Object buffer); | 232 Lisp_Object buffer); |
214 static Lisp_Object keymap_submaps (Lisp_Object keymap); | |
215 | 233 |
216 Lisp_Object Qcontrol, Qctrl, Qmeta, Qsuper, Qhyper, Qalt, Qshift; | 234 Lisp_Object Qcontrol, Qctrl, Qmeta, Qsuper, Qhyper, Qalt, Qshift; |
217 Lisp_Object Qbutton0, Qbutton1, Qbutton2, Qbutton3; | 235 Lisp_Object Qbutton0, Qbutton1, Qbutton2, Qbutton3; |
218 Lisp_Object Qbutton4, Qbutton5, Qbutton6, Qbutton7; | 236 Lisp_Object Qbutton4, Qbutton5, Qbutton6, Qbutton7; |
219 Lisp_Object Qbutton0up, Qbutton1up, Qbutton2up, Qbutton3up; | 237 Lisp_Object Qbutton0up, Qbutton1up, Qbutton2up, Qbutton3up; |
232 /************************************************************************/ | 250 /************************************************************************/ |
233 /* The keymap Lisp object */ | 251 /* The keymap Lisp object */ |
234 /************************************************************************/ | 252 /************************************************************************/ |
235 | 253 |
236 static Lisp_Object | 254 static Lisp_Object |
237 mark_keymap (Lisp_Object obj) | 255 mark_keymap (Lisp_Object obj, void (*markobj) (Lisp_Object)) |
238 { | 256 { |
239 Lisp_Keymap *keymap = XKEYMAP (obj); | 257 Lisp_Keymap *keymap = XKEYMAP (obj); |
240 mark_object (keymap->parents); | 258 markobj (keymap->parents); |
241 mark_object (keymap->prompt); | 259 markobj (keymap->prompt); |
242 mark_object (keymap->inverse_table); | 260 markobj (keymap->inverse_table); |
243 mark_object (keymap->sub_maps_cache); | 261 markobj (keymap->sub_maps_cache); |
244 mark_object (keymap->default_binding); | 262 markobj (keymap->default_binding); |
245 mark_object (keymap->name); | 263 markobj (keymap->name); |
246 return keymap->table; | 264 return keymap->table; |
247 } | 265 } |
248 | 266 |
249 static void | 267 static void |
250 print_keymap (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag) | 268 print_keymap (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag) |
251 { | 269 { |
252 /* This function can GC */ | 270 /* This function can GC */ |
253 Lisp_Keymap *keymap = XKEYMAP (obj); | 271 Lisp_Keymap *keymap = XKEYMAP (obj); |
254 char buf[200]; | 272 char buf[200]; |
273 int size = XINT (Fkeymap_fullness (obj)); | |
255 if (print_readably) | 274 if (print_readably) |
256 error ("printing unreadable object #<keymap 0x%x>", keymap->header.uid); | 275 error ("printing unreadable object #<keymap 0x%x>", keymap->header.uid); |
257 write_c_string ("#<keymap ", printcharfun); | 276 write_c_string ("#<keymap ", printcharfun); |
258 if (!NILP (keymap->name)) | 277 if (!NILP (keymap->name)) |
259 { | 278 print_internal (keymap->name, printcharfun, 1); |
260 print_internal (keymap->name, printcharfun, 1); | 279 /* #### Yuck! This is no way to form plural! --hniksic */ |
261 write_c_string (" ", printcharfun); | 280 sprintf (buf, "%s%d entr%s 0x%x>", |
262 } | 281 ((NILP (keymap->name)) ? "" : " "), |
263 sprintf (buf, "size %ld 0x%x>", | 282 size, |
264 (long) XINT (Fkeymap_fullness (obj)), keymap->header.uid); | 283 ((size == 1) ? "y" : "ies"), |
284 keymap->header.uid); | |
265 write_c_string (buf, printcharfun); | 285 write_c_string (buf, printcharfun); |
266 } | 286 } |
267 | |
268 static const struct lrecord_description keymap_description[] = { | |
269 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, parents) }, | |
270 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, prompt) }, | |
271 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, table) }, | |
272 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, inverse_table) }, | |
273 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, default_binding) }, | |
274 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, sub_maps_cache) }, | |
275 { XD_LISP_OBJECT, offsetof (Lisp_Keymap, name) }, | |
276 { XD_END } | |
277 }; | |
278 | 287 |
279 /* No need for keymap_equal #### Why not? */ | 288 /* No need for keymap_equal #### Why not? */ |
280 DEFINE_LRECORD_IMPLEMENTATION ("keymap", keymap, | 289 DEFINE_LRECORD_IMPLEMENTATION ("keymap", keymap, |
281 mark_keymap, print_keymap, 0, 0, 0, | 290 mark_keymap, print_keymap, 0, 0, 0, |
282 keymap_description, | |
283 Lisp_Keymap); | 291 Lisp_Keymap); |
284 | 292 |
285 /************************************************************************/ | 293 /************************************************************************/ |
286 /* Traversing keymaps and their parents */ | 294 /* Traversing keymaps and their parents */ |
287 /************************************************************************/ | 295 /************************************************************************/ |
302 gcpro1.nvars = 0; | 310 gcpro1.nvars = 0; |
303 | 311 |
304 start_keymap = get_keymap (start_keymap, 1, 1); | 312 start_keymap = get_keymap (start_keymap, 1, 1); |
305 keymap = start_keymap; | 313 keymap = start_keymap; |
306 /* Hack special-case parents at top-level */ | 314 /* Hack special-case parents at top-level */ |
307 tail = !NILP (tail) ? tail : XKEYMAP (keymap)->parents; | 315 tail = ((!NILP (tail)) ? tail : XKEYMAP (keymap)->parents); |
308 | 316 |
309 for (;;) | 317 for (;;) |
310 { | 318 { |
311 Lisp_Object result; | 319 Lisp_Object result; |
312 | 320 |
313 QUIT; | 321 QUIT; |
314 result = mapper (keymap, mapper_arg); | 322 result = ((mapper) (keymap, mapper_arg)); |
315 if (!NILP (result)) | 323 if (!NILP (result)) |
316 { | 324 { |
317 while (CONSP (malloc_bites)) | 325 while (CONSP (malloc_bites)) |
318 { | 326 { |
319 Lisp_Cons *victim = XCONS (malloc_bites); | 327 struct Lisp_Cons *victim = XCONS (malloc_bites); |
320 malloc_bites = victim->cdr; | 328 malloc_bites = victim->cdr; |
321 free_cons (victim); | 329 free_cons (victim); |
322 } | 330 } |
323 UNGCPRO; | 331 UNGCPRO; |
324 return result; | 332 return result; |
331 return Qnil; /* Nothing found */ | 339 return Qnil; /* Nothing found */ |
332 } | 340 } |
333 stack_depth--; | 341 stack_depth--; |
334 if (CONSP (malloc_bites)) | 342 if (CONSP (malloc_bites)) |
335 { | 343 { |
336 Lisp_Cons *victim = XCONS (malloc_bites); | 344 struct Lisp_Cons *victim = XCONS (malloc_bites); |
337 tail = victim->car; | 345 tail = victim->car; |
338 malloc_bites = victim->cdr; | 346 malloc_bites = victim->cdr; |
339 free_cons (victim); | 347 free_cons (victim); |
340 } | 348 } |
341 else | 349 else |
393 | 401 |
394 /************************************************************************/ | 402 /************************************************************************/ |
395 /* Some low-level functions */ | 403 /* Some low-level functions */ |
396 /************************************************************************/ | 404 /************************************************************************/ |
397 | 405 |
398 static int | 406 static unsigned int |
399 bucky_sym_to_bucky_bit (Lisp_Object sym) | 407 bucky_sym_to_bucky_bit (Lisp_Object sym) |
400 { | 408 { |
401 if (EQ (sym, Qcontrol)) return XEMACS_MOD_CONTROL; | 409 if (EQ (sym, Qcontrol)) return MOD_CONTROL; |
402 if (EQ (sym, Qmeta)) return XEMACS_MOD_META; | 410 if (EQ (sym, Qmeta)) return MOD_META; |
403 if (EQ (sym, Qsuper)) return XEMACS_MOD_SUPER; | 411 if (EQ (sym, Qsuper)) return MOD_SUPER; |
404 if (EQ (sym, Qhyper)) return XEMACS_MOD_HYPER; | 412 if (EQ (sym, Qhyper)) return MOD_HYPER; |
405 if (EQ (sym, Qalt)) return XEMACS_MOD_ALT; | 413 if (EQ (sym, Qalt)) return MOD_ALT; |
406 if (EQ (sym, Qsymbol)) return XEMACS_MOD_ALT; /* #### - reverse compat */ | 414 if (EQ (sym, Qsymbol)) return MOD_ALT; /* #### - reverse compat */ |
407 if (EQ (sym, Qshift)) return XEMACS_MOD_SHIFT; | 415 if (EQ (sym, Qshift)) return MOD_SHIFT; |
408 | 416 |
409 return 0; | 417 return 0; |
410 } | 418 } |
411 | 419 |
412 static Lisp_Object | 420 static Lisp_Object |
413 control_meta_superify (Lisp_Object frob, int modifiers) | 421 control_meta_superify (Lisp_Object frob, unsigned int modifiers) |
414 { | 422 { |
415 if (modifiers == 0) | 423 if (modifiers == 0) |
416 return frob; | 424 return frob; |
417 frob = Fcons (frob, Qnil); | 425 frob = Fcons (frob, Qnil); |
418 if (modifiers & XEMACS_MOD_SHIFT) frob = Fcons (Qshift, frob); | 426 if (modifiers & MOD_SHIFT) frob = Fcons (Qshift, frob); |
419 if (modifiers & XEMACS_MOD_ALT) frob = Fcons (Qalt, frob); | 427 if (modifiers & MOD_ALT) frob = Fcons (Qalt, frob); |
420 if (modifiers & XEMACS_MOD_HYPER) frob = Fcons (Qhyper, frob); | 428 if (modifiers & MOD_HYPER) frob = Fcons (Qhyper, frob); |
421 if (modifiers & XEMACS_MOD_SUPER) frob = Fcons (Qsuper, frob); | 429 if (modifiers & MOD_SUPER) frob = Fcons (Qsuper, frob); |
422 if (modifiers & XEMACS_MOD_CONTROL) frob = Fcons (Qcontrol, frob); | 430 if (modifiers & MOD_CONTROL) frob = Fcons (Qcontrol, frob); |
423 if (modifiers & XEMACS_MOD_META) frob = Fcons (Qmeta, frob); | 431 if (modifiers & MOD_META) frob = Fcons (Qmeta, frob); |
424 return frob; | 432 return frob; |
425 } | 433 } |
426 | 434 |
427 static Lisp_Object | 435 static Lisp_Object |
428 make_key_description (const struct key_data *key, int prettify) | 436 make_key_description (CONST struct key_data *key, int prettify) |
429 { | 437 { |
430 Lisp_Object keysym = key->keysym; | 438 Lisp_Object keysym = key->keysym; |
431 int modifiers = key->modifiers; | 439 unsigned int modifiers = key->modifiers; |
432 | 440 |
433 if (prettify && CHARP (keysym)) | 441 if (prettify && CHARP (keysym)) |
434 { | 442 { |
435 /* This is a little slow, but (control a) is prettier than (control 65). | 443 /* This is a little slow, but (control a) is prettier than (control 65). |
436 It's now ok to do this for digit-chars too, since we've fixed the | 444 It's now ok to do this for digit-chars too, since we've fixed the |
451 /* Low-level keymap-store functions */ | 459 /* Low-level keymap-store functions */ |
452 /************************************************************************/ | 460 /************************************************************************/ |
453 | 461 |
454 static Lisp_Object | 462 static Lisp_Object |
455 raw_lookup_key (Lisp_Object keymap, | 463 raw_lookup_key (Lisp_Object keymap, |
456 const struct key_data *raw_keys, int raw_keys_count, | 464 CONST struct key_data *raw_keys, int raw_keys_count, |
457 int keys_so_far, int accept_default); | 465 int keys_so_far, int accept_default); |
458 | 466 |
459 /* Relies on caller to gc-protect args */ | 467 /* Relies on caller to gc-protect args */ |
460 static Lisp_Object | 468 static Lisp_Object |
461 keymap_lookup_directly (Lisp_Object keymap, | 469 keymap_lookup_directly (Lisp_Object keymap, |
462 Lisp_Object keysym, int modifiers) | 470 Lisp_Object keysym, unsigned int modifiers) |
463 { | 471 { |
464 Lisp_Keymap *k; | 472 Lisp_Keymap *k; |
465 | 473 |
466 if ((modifiers & ~(XEMACS_MOD_CONTROL | XEMACS_MOD_META | XEMACS_MOD_SUPER | XEMACS_MOD_HYPER | 474 if ((modifiers & ~(MOD_CONTROL | MOD_META | MOD_SUPER | MOD_HYPER |
467 | XEMACS_MOD_ALT | XEMACS_MOD_SHIFT)) != 0) | 475 | MOD_ALT | MOD_SHIFT)) != 0) |
468 abort (); | 476 abort (); |
469 | 477 |
470 k = XKEYMAP (keymap); | 478 k = XKEYMAP (keymap); |
471 | 479 |
472 /* If the keysym is a one-character symbol, use the char code instead. */ | 480 /* If the keysym is a one-character symbol, use the char code instead. */ |
475 Lisp_Object i_fart_on_gcc = | 483 Lisp_Object i_fart_on_gcc = |
476 make_char (string_char (XSYMBOL (keysym)->name, 0)); | 484 make_char (string_char (XSYMBOL (keysym)->name, 0)); |
477 keysym = i_fart_on_gcc; | 485 keysym = i_fart_on_gcc; |
478 } | 486 } |
479 | 487 |
480 if (modifiers & XEMACS_MOD_META) /* Utterly hateful ESC lossage */ | 488 if (modifiers & MOD_META) /* Utterly hateful ESC lossage */ |
481 { | 489 { |
482 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (XEMACS_MOD_META), | 490 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META), |
483 k->table, Qnil); | 491 k->table, Qnil); |
484 if (NILP (submap)) | 492 if (NILP (submap)) |
485 return Qnil; | 493 return Qnil; |
486 k = XKEYMAP (submap); | 494 k = XKEYMAP (submap); |
487 modifiers &= ~XEMACS_MOD_META; | 495 modifiers &= ~MOD_META; |
488 } | 496 } |
489 | 497 |
490 if (modifiers != 0) | 498 if (modifiers != 0) |
491 { | 499 { |
492 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (modifiers), | 500 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (modifiers), |
566 /* else the list's tail has been modified, so we don't need to | 574 /* else the list's tail has been modified, so we don't need to |
567 touch the hash table again (the pointer in there is ok). | 575 touch the hash table again (the pointer in there is ok). |
568 */ | 576 */ |
569 } | 577 } |
570 | 578 |
571 /* Prevent luser from shooting herself in the foot using something like | |
572 (define-key ctl-x-4-map "p" global-map) */ | |
573 static void | |
574 check_keymap_definition_loop (Lisp_Object def, Lisp_Keymap *to_keymap) | |
575 { | |
576 def = get_keymap (def, 0, 0); | |
577 | |
578 if (KEYMAPP (def)) | |
579 { | |
580 Lisp_Object maps; | |
581 | |
582 if (XKEYMAP (def) == to_keymap) | |
583 signal_simple_error ("Cyclic keymap definition", def); | |
584 | |
585 for (maps = keymap_submaps (def); | |
586 CONSP (maps); | |
587 maps = XCDR (maps)) | |
588 check_keymap_definition_loop (XCDR (XCAR (maps)), to_keymap); | |
589 } | |
590 } | |
591 | 579 |
592 static void | 580 static void |
593 keymap_store_internal (Lisp_Object keysym, Lisp_Keymap *keymap, | 581 keymap_store_internal (Lisp_Object keysym, Lisp_Keymap *keymap, |
594 Lisp_Object def) | 582 Lisp_Object value) |
595 { | 583 { |
596 Lisp_Object prev_def = Fgethash (keysym, keymap->table, Qnil); | 584 Lisp_Object prev_value = Fgethash (keysym, keymap->table, Qnil); |
597 | 585 |
598 if (EQ (prev_def, def)) | 586 if (EQ (prev_value, value)) |
599 return; | 587 return; |
600 | 588 if (!NILP (prev_value)) |
601 check_keymap_definition_loop (def, keymap); | |
602 | |
603 if (!NILP (prev_def)) | |
604 keymap_delete_inverse_internal (keymap->inverse_table, | 589 keymap_delete_inverse_internal (keymap->inverse_table, |
605 keysym, prev_def); | 590 keysym, prev_value); |
606 if (NILP (def)) | 591 if (NILP (value)) |
607 { | 592 { |
593 keymap->fullness--; | |
594 if (keymap->fullness < 0) abort (); | |
608 Fremhash (keysym, keymap->table); | 595 Fremhash (keysym, keymap->table); |
609 } | 596 } |
610 else | 597 else |
611 { | 598 { |
612 Fputhash (keysym, def, keymap->table); | 599 if (NILP (prev_value)) |
600 keymap->fullness++; | |
601 Fputhash (keysym, value, keymap->table); | |
613 keymap_store_inverse_internal (keymap->inverse_table, | 602 keymap_store_inverse_internal (keymap->inverse_table, |
614 keysym, def); | 603 keysym, value); |
615 } | 604 } |
616 keymap_tick++; | 605 keymap_tick++; |
617 } | 606 } |
618 | 607 |
619 | 608 |
620 static Lisp_Object | 609 static Lisp_Object |
621 create_bucky_submap (Lisp_Keymap *k, int modifiers, | 610 create_bucky_submap (Lisp_Keymap *k, unsigned int modifiers, |
622 Lisp_Object parent_for_debugging_info) | 611 Lisp_Object parent_for_debugging_info) |
623 { | 612 { |
624 Lisp_Object submap = Fmake_sparse_keymap (Qnil); | 613 Lisp_Object submap = Fmake_sparse_keymap (Qnil); |
625 /* User won't see this, but it is nice for debugging Emacs */ | 614 /* User won't see this, but it is nice for debugging Emacs */ |
626 XKEYMAP (submap)->name | 615 XKEYMAP (submap)->name |
632 } | 621 } |
633 | 622 |
634 | 623 |
635 /* Relies on caller to gc-protect keymap, keysym, value */ | 624 /* Relies on caller to gc-protect keymap, keysym, value */ |
636 static void | 625 static void |
637 keymap_store (Lisp_Object keymap, const struct key_data *key, | 626 keymap_store (Lisp_Object keymap, CONST struct key_data *key, |
638 Lisp_Object value) | 627 Lisp_Object value) |
639 { | 628 { |
640 Lisp_Object keysym = key->keysym; | 629 Lisp_Object keysym = key->keysym; |
641 int modifiers = key->modifiers; | 630 unsigned int modifiers = key->modifiers; |
642 Lisp_Keymap *k = XKEYMAP (keymap); | 631 Lisp_Keymap *k; |
643 | 632 |
644 assert ((modifiers & ~(XEMACS_MOD_CONTROL | XEMACS_MOD_META | 633 if ((modifiers & ~(MOD_CONTROL | MOD_META | MOD_SUPER | MOD_HYPER |
645 | XEMACS_MOD_SUPER | XEMACS_MOD_HYPER | 634 | MOD_ALT | MOD_SHIFT)) != 0) |
646 | XEMACS_MOD_ALT | XEMACS_MOD_SHIFT)) == 0); | 635 abort (); |
636 | |
637 k = XKEYMAP (keymap); | |
647 | 638 |
648 /* If the keysym is a one-character symbol, use the char code instead. */ | 639 /* If the keysym is a one-character symbol, use the char code instead. */ |
649 if (SYMBOLP (keysym) && string_char_length (XSYMBOL (keysym)->name) == 1) | 640 if (SYMBOLP (keysym) && string_char_length (XSYMBOL (keysym)->name) == 1) |
650 keysym = make_char (string_char (XSYMBOL (keysym)->name, 0)); | 641 { |
651 | 642 Lisp_Object run_the_gcc_developers_over_with_a_steamroller = |
652 if (modifiers & XEMACS_MOD_META) /* Utterly hateful ESC lossage */ | 643 make_char (string_char (XSYMBOL (keysym)->name, 0)); |
653 { | 644 keysym = run_the_gcc_developers_over_with_a_steamroller; |
654 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (XEMACS_MOD_META), | 645 } |
646 | |
647 if (modifiers & MOD_META) /* Utterly hateful ESC lossage */ | |
648 { | |
649 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META), | |
655 k->table, Qnil); | 650 k->table, Qnil); |
656 if (NILP (submap)) | 651 if (NILP (submap)) |
657 submap = create_bucky_submap (k, XEMACS_MOD_META, keymap); | 652 submap = create_bucky_submap (k, MOD_META, keymap); |
658 k = XKEYMAP (submap); | 653 k = XKEYMAP (submap); |
659 modifiers &= ~XEMACS_MOD_META; | 654 modifiers &= ~MOD_META; |
660 } | 655 } |
661 | 656 |
662 if (modifiers != 0) | 657 if (modifiers != 0) |
663 { | 658 { |
664 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (modifiers), | 659 Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (modifiers), |
755 keymap->prompt = Qnil; | 750 keymap->prompt = Qnil; |
756 keymap->table = Qnil; | 751 keymap->table = Qnil; |
757 keymap->inverse_table = Qnil; | 752 keymap->inverse_table = Qnil; |
758 keymap->default_binding = Qnil; | 753 keymap->default_binding = Qnil; |
759 keymap->sub_maps_cache = Qnil; /* No possible submaps */ | 754 keymap->sub_maps_cache = Qnil; /* No possible submaps */ |
755 keymap->fullness = 0; | |
760 keymap->name = Qnil; | 756 keymap->name = Qnil; |
761 | 757 |
762 if (size != 0) /* hack for copy-keymap */ | 758 if (size != 0) /* hack for copy-keymap */ |
763 { | 759 { |
764 keymap->table = | 760 keymap->table = |
1046 { | 1042 { |
1047 Lisp_Object idx = Fcdr (object); | 1043 Lisp_Object idx = Fcdr (object); |
1048 struct key_data indirection; | 1044 struct key_data indirection; |
1049 if (CHARP (idx)) | 1045 if (CHARP (idx)) |
1050 { | 1046 { |
1051 Lisp_Event event; | 1047 struct Lisp_Event event; |
1052 event.event_type = empty_event; | 1048 event.event_type = empty_event; |
1053 character_to_event (XCHAR (idx), &event, | 1049 character_to_event (XCHAR (idx), &event, |
1054 XCONSOLE (Vselected_console), 0, 0); | 1050 XCONSOLE (Vselected_console), 0, 0); |
1055 indirection = event.event.key; | 1051 indirection = event.event.key; |
1056 } | 1052 } |
1057 else if (CONSP (idx)) | 1053 else if (CONSP (idx)) |
1058 { | 1054 { |
1059 if (!INTP (XCDR (idx))) | 1055 if (!INTP (XCDR (idx))) |
1060 return Qnil; | 1056 return Qnil; |
1061 indirection.keysym = XCAR (idx); | 1057 indirection.keysym = XCAR (idx); |
1062 indirection.modifiers = (unsigned char) XINT (XCDR (idx)); | 1058 indirection.modifiers = XINT (XCDR (idx)); |
1063 } | 1059 } |
1064 else if (SYMBOLP (idx)) | 1060 else if (SYMBOLP (idx)) |
1065 { | 1061 { |
1066 indirection.keysym = idx; | 1062 indirection.keysym = idx; |
1067 indirection.modifiers = 0; | 1063 indirection.modifiers = 0; |
1088 return object; | 1084 return object; |
1089 } | 1085 } |
1090 } | 1086 } |
1091 | 1087 |
1092 static Lisp_Object | 1088 static Lisp_Object |
1093 keymap_lookup_1 (Lisp_Object keymap, const struct key_data *key, | 1089 keymap_lookup_1 (Lisp_Object keymap, CONST struct key_data *key, |
1094 int accept_default) | 1090 int accept_default) |
1095 { | 1091 { |
1096 /* This function can GC */ | 1092 /* This function can GC */ |
1097 return get_keyelt (keymap_lookup_directly (keymap, | 1093 return get_keyelt (keymap_lookup_directly (keymap, |
1098 key->keysym, key->modifiers), | 1094 key->keysym, key->modifiers), |
1132 Lisp_Keymap *new_keymap = XKEYMAP (nkm); | 1128 Lisp_Keymap *new_keymap = XKEYMAP (nkm); |
1133 struct copy_keymap_inverse_closure copy_keymap_inverse_closure; | 1129 struct copy_keymap_inverse_closure copy_keymap_inverse_closure; |
1134 copy_keymap_inverse_closure.inverse_table = keymap->inverse_table; | 1130 copy_keymap_inverse_closure.inverse_table = keymap->inverse_table; |
1135 | 1131 |
1136 new_keymap->parents = Fcopy_sequence (keymap->parents); | 1132 new_keymap->parents = Fcopy_sequence (keymap->parents); |
1133 new_keymap->fullness = keymap->fullness; | |
1137 new_keymap->sub_maps_cache = Qnil; /* No submaps */ | 1134 new_keymap->sub_maps_cache = Qnil; /* No submaps */ |
1138 new_keymap->table = Fcopy_hash_table (keymap->table); | 1135 new_keymap->table = Fcopy_hash_table (keymap->table); |
1139 new_keymap->inverse_table = Fcopy_hash_table (keymap->inverse_table); | 1136 new_keymap->inverse_table = Fcopy_hash_table (keymap->inverse_table); |
1140 new_keymap->default_binding = keymap->default_binding; | |
1141 /* After copying the inverse map, we need to copy the conses which | 1137 /* After copying the inverse map, we need to copy the conses which |
1142 are its values, lest they be shared by the copy, and mangled. | 1138 are its values, lest they be shared by the copy, and mangled. |
1143 */ | 1139 */ |
1144 elisp_maphash (copy_keymap_inverse_mapper, keymap->inverse_table, | 1140 elisp_maphash (copy_keymap_inverse_mapper, keymap->inverse_table, |
1145 ©_keymap_inverse_closure); | 1141 ©_keymap_inverse_closure); |
1209 int fullness; | 1205 int fullness; |
1210 Lisp_Object sub_maps; | 1206 Lisp_Object sub_maps; |
1211 struct gcpro gcpro1, gcpro2; | 1207 struct gcpro gcpro1, gcpro2; |
1212 | 1208 |
1213 keymap = get_keymap (keymap, 1, 1); | 1209 keymap = get_keymap (keymap, 1, 1); |
1214 fullness = XINT (Fhash_table_count (XKEYMAP (keymap)->table)); | 1210 fullness = XKEYMAP (keymap)->fullness; |
1211 sub_maps = keymap_submaps (keymap); | |
1215 GCPRO2 (keymap, sub_maps); | 1212 GCPRO2 (keymap, sub_maps); |
1216 for (sub_maps = keymap_submaps (keymap); | 1213 for (; !NILP (sub_maps); sub_maps = XCDR (sub_maps)) |
1217 !NILP (sub_maps); | |
1218 sub_maps = XCDR (sub_maps)) | |
1219 { | 1214 { |
1220 if (MODIFIER_HASH_KEY_BITS (XCAR (XCAR (sub_maps))) != 0) | 1215 if (MODIFIER_HASH_KEY_BITS (XCAR (XCAR (sub_maps))) != 0) |
1221 { | 1216 { |
1222 Lisp_Object bucky_map = XCDR (XCAR (sub_maps)); | 1217 Lisp_Object sub_map = XCDR (XCAR (sub_maps)); |
1223 fullness--; /* don't count bucky maps themselves. */ | 1218 fullness--; /* don't count bucky maps */ |
1224 fullness += keymap_fullness (bucky_map); | 1219 fullness += keymap_fullness (sub_map); |
1225 } | 1220 } |
1226 } | 1221 } |
1227 UNGCPRO; | 1222 UNGCPRO; |
1228 return fullness; | 1223 return fullness; |
1229 } | 1224 } |
1246 and perform any necessary canonicalization. */ | 1241 and perform any necessary canonicalization. */ |
1247 | 1242 |
1248 static void | 1243 static void |
1249 define_key_check_and_coerce_keysym (Lisp_Object spec, | 1244 define_key_check_and_coerce_keysym (Lisp_Object spec, |
1250 Lisp_Object *keysym, | 1245 Lisp_Object *keysym, |
1251 int modifiers) | 1246 unsigned int modifiers) |
1252 { | 1247 { |
1253 /* Now, check and massage the trailing keysym specifier. */ | 1248 /* Now, check and massage the trailing keysym specifier. */ |
1254 if (SYMBOLP (*keysym)) | 1249 if (SYMBOLP (*keysym)) |
1255 { | 1250 { |
1256 if (string_char_length (XSYMBOL (*keysym)->name) == 1) | 1251 if (string_char_length (XSYMBOL (*keysym)->name) == 1) |
1269 /* || (XCHAR (*keysym) >= 128 && XCHAR (*keysym) < 160) */) | 1264 /* || (XCHAR (*keysym) >= 128 && XCHAR (*keysym) < 160) */) |
1270 /* yuck! Can't make the above restriction; too many compatibility | 1265 /* yuck! Can't make the above restriction; too many compatibility |
1271 problems ... */ | 1266 problems ... */ |
1272 signal_simple_error ("keysym char must be printable", *keysym); | 1267 signal_simple_error ("keysym char must be printable", *keysym); |
1273 /* #### This bites! I want to be able to write (control shift a) */ | 1268 /* #### This bites! I want to be able to write (control shift a) */ |
1274 if (modifiers & XEMACS_MOD_SHIFT) | 1269 if (modifiers & MOD_SHIFT) |
1275 signal_simple_error | 1270 signal_simple_error |
1276 ("The `shift' modifier may not be applied to ASCII keysyms", | 1271 ("The `shift' modifier may not be applied to ASCII keysyms", |
1277 spec); | 1272 spec); |
1278 } | 1273 } |
1279 else | 1274 else |
1280 { | 1275 { |
1281 signal_simple_error ("Unknown keysym specifier", *keysym); | 1276 signal_simple_error ("Unknown keysym specifier", |
1277 *keysym); | |
1282 } | 1278 } |
1283 | 1279 |
1284 if (SYMBOLP (*keysym)) | 1280 if (SYMBOLP (*keysym)) |
1285 { | 1281 { |
1286 char *name = (char *) string_data (XSYMBOL (*keysym)->name); | 1282 char *name = (char *) |
1283 string_data (XSYMBOL (*keysym)->name); | |
1287 | 1284 |
1288 /* FSFmacs uses symbols with the printed representation of keysyms in | 1285 /* FSFmacs uses symbols with the printed representation of keysyms in |
1289 their names, like 'M-x, and we use the syntax '(meta x). So, to avoid | 1286 their names, like 'M-x, and we use the syntax '(meta x). So, to avoid |
1290 confusion, notice the M-x syntax and signal an error - because | 1287 confusion, notice the M-x syntax and signal an error - because |
1291 otherwise it would be interpreted as a regular keysym, and would even | 1288 otherwise it would be interpreted as a regular keysym, and would even |
1344 *keysym = QKreturn; | 1341 *keysym = QKreturn; |
1345 else if (EQ (*keysym, QESC)) | 1342 else if (EQ (*keysym, QESC)) |
1346 *keysym = QKescape; | 1343 *keysym = QKescape; |
1347 else if (EQ (*keysym, QDEL)) | 1344 else if (EQ (*keysym, QDEL)) |
1348 *keysym = QKdelete; | 1345 *keysym = QKdelete; |
1349 else if (EQ (*keysym, QSPC)) | |
1350 *keysym = QKspace; | |
1351 else if (EQ (*keysym, QBS)) | 1346 else if (EQ (*keysym, QBS)) |
1352 *keysym = QKbackspace; | 1347 *keysym = QKbackspace; |
1353 /* Emacs compatibility */ | 1348 /* Emacs compatibility */ |
1354 else if (EQ(*keysym, Qdown_mouse_1)) | 1349 else if (EQ(*keysym, Qdown_mouse_1)) |
1355 *keysym = Qbutton1; | 1350 *keysym = Qbutton1; |
1385 static void | 1380 static void |
1386 define_key_parser (Lisp_Object spec, struct key_data *returned_value) | 1381 define_key_parser (Lisp_Object spec, struct key_data *returned_value) |
1387 { | 1382 { |
1388 if (CHAR_OR_CHAR_INTP (spec)) | 1383 if (CHAR_OR_CHAR_INTP (spec)) |
1389 { | 1384 { |
1390 Lisp_Event event; | 1385 struct Lisp_Event event; |
1391 event.event_type = empty_event; | 1386 event.event_type = empty_event; |
1392 character_to_event (XCHAR_OR_CHAR_INT (spec), &event, | 1387 character_to_event (XCHAR_OR_CHAR_INT (spec), &event, |
1393 XCONSOLE (Vselected_console), 0, 0); | 1388 XCONSOLE (Vselected_console), 0, 0); |
1394 returned_value->keysym = event.event.key.keysym; | 1389 returned_value->keysym = event.event.key.keysym; |
1395 returned_value->modifiers = event.event.key.modifiers; | 1390 returned_value->modifiers = event.event.key.modifiers; |
1446 returned_value->keysym = spec; | 1441 returned_value->keysym = spec; |
1447 returned_value->modifiers = 0; | 1442 returned_value->modifiers = 0; |
1448 } | 1443 } |
1449 else if (CONSP (spec)) | 1444 else if (CONSP (spec)) |
1450 { | 1445 { |
1451 int modifiers = 0; | 1446 unsigned int modifiers = 0; |
1452 Lisp_Object keysym = Qnil; | 1447 Lisp_Object keysym = Qnil; |
1453 Lisp_Object rest = spec; | 1448 Lisp_Object rest = spec; |
1454 | 1449 |
1455 /* First, parse out the leading modifier symbols. */ | 1450 /* First, parse out the leading modifier symbols. */ |
1456 while (CONSP (rest)) | 1451 while (CONSP (rest)) |
1457 { | 1452 { |
1458 int modifier; | 1453 unsigned int modifier; |
1459 | 1454 |
1460 keysym = XCAR (rest); | 1455 keysym = XCAR (rest); |
1461 modifier = bucky_sym_to_bucky_bit (keysym); | 1456 modifier = bucky_sym_to_bucky_bit (keysym); |
1462 modifiers |= modifier; | 1457 modifiers |= modifier; |
1463 if (!NILP (XCDR (rest))) | 1458 if (!NILP (XCDR (rest))) |
1533 XEVENT (event)->event.key.modifiers = raw_key.modifiers; | 1528 XEVENT (event)->event.key.modifiers = raw_key.modifiers; |
1534 } | 1529 } |
1535 | 1530 |
1536 | 1531 |
1537 int | 1532 int |
1538 event_matches_key_specifier_p (Lisp_Event *event, Lisp_Object key_specifier) | 1533 event_matches_key_specifier_p (struct Lisp_Event *event, |
1534 Lisp_Object key_specifier) | |
1539 { | 1535 { |
1540 Lisp_Object event2; | 1536 Lisp_Object event2; |
1541 int retval; | 1537 int retval; |
1542 struct gcpro gcpro1; | 1538 struct gcpro gcpro1; |
1543 | 1539 |
1584 UNGCPRO; | 1580 UNGCPRO; |
1585 return retval; | 1581 return retval; |
1586 } | 1582 } |
1587 | 1583 |
1588 static int | 1584 static int |
1589 meta_prefix_char_p (const struct key_data *key) | 1585 meta_prefix_char_p (CONST struct key_data *key) |
1590 { | 1586 { |
1591 Lisp_Event event; | 1587 struct Lisp_Event event; |
1592 | 1588 |
1593 event.event_type = key_press_event; | 1589 event.event_type = key_press_event; |
1594 event.channel = Vselected_console; | 1590 event.channel = Vselected_console; |
1595 event.event.key.keysym = key->keysym; | 1591 event.event.key.keysym = key->keysym; |
1596 event.event.key.modifiers = key->modifiers; | 1592 event.event.key.modifiers = key->modifiers; |
1623 static void | 1619 static void |
1624 define_key_alternate_name (struct key_data *key, | 1620 define_key_alternate_name (struct key_data *key, |
1625 struct key_data *returned_value) | 1621 struct key_data *returned_value) |
1626 { | 1622 { |
1627 Lisp_Object keysym = key->keysym; | 1623 Lisp_Object keysym = key->keysym; |
1628 int modifiers = key->modifiers; | 1624 unsigned int modifiers = key->modifiers; |
1629 int modifiers_sans_control = (modifiers & (~XEMACS_MOD_CONTROL)); | 1625 unsigned int modifiers_sans_control = (modifiers & (~MOD_CONTROL)); |
1630 int modifiers_sans_meta = (modifiers & (~XEMACS_MOD_META)); | 1626 unsigned int modifiers_sans_meta = (modifiers & (~MOD_META)); |
1631 returned_value->keysym = Qnil; /* By default, no "alternate" key */ | 1627 returned_value->keysym = Qnil; /* By default, no "alternate" key */ |
1632 returned_value->modifiers = 0; | 1628 returned_value->modifiers = 0; |
1633 if (modifiers_sans_meta == XEMACS_MOD_CONTROL) | 1629 if (modifiers_sans_meta == MOD_CONTROL) |
1634 { | 1630 { |
1635 if EQ (keysym, QKspace) | 1631 if EQ (keysym, QKspace) |
1636 MACROLET (make_char ('@'), modifiers); | 1632 MACROLET (make_char ('@'), modifiers); |
1637 else if (!CHARP (keysym)) | 1633 else if (!CHARP (keysym)) |
1638 return; | 1634 return; |
1655 } | 1651 } |
1656 } | 1652 } |
1657 else if (modifiers_sans_meta != 0) | 1653 else if (modifiers_sans_meta != 0) |
1658 return; | 1654 return; |
1659 else if (EQ (keysym, QKbackspace)) /* backspace => c-h */ | 1655 else if (EQ (keysym, QKbackspace)) /* backspace => c-h */ |
1660 MACROLET (make_char ('h'), (modifiers | XEMACS_MOD_CONTROL)); | 1656 MACROLET (make_char ('h'), (modifiers | MOD_CONTROL)); |
1661 else if (EQ (keysym, QKtab)) /* tab => c-i */ | 1657 else if (EQ (keysym, QKtab)) /* tab => c-i */ |
1662 MACROLET (make_char ('i'), (modifiers | XEMACS_MOD_CONTROL)); | 1658 MACROLET (make_char ('i'), (modifiers | MOD_CONTROL)); |
1663 else if (EQ (keysym, QKlinefeed)) /* linefeed => c-j */ | 1659 else if (EQ (keysym, QKlinefeed)) /* linefeed => c-j */ |
1664 MACROLET (make_char ('j'), (modifiers | XEMACS_MOD_CONTROL)); | 1660 MACROLET (make_char ('j'), (modifiers | MOD_CONTROL)); |
1665 else if (EQ (keysym, QKreturn)) /* return => c-m */ | 1661 else if (EQ (keysym, QKreturn)) /* return => c-m */ |
1666 MACROLET (make_char ('m'), (modifiers | XEMACS_MOD_CONTROL)); | 1662 MACROLET (make_char ('m'), (modifiers | MOD_CONTROL)); |
1667 else if (EQ (keysym, QKescape)) /* escape => c-[ */ | 1663 else if (EQ (keysym, QKescape)) /* escape => c-[ */ |
1668 MACROLET (make_char ('['), (modifiers | XEMACS_MOD_CONTROL)); | 1664 MACROLET (make_char ('['), (modifiers | MOD_CONTROL)); |
1669 else | 1665 else |
1670 return; | 1666 return; |
1671 #undef MACROLET | 1667 #undef MACROLET |
1672 } | 1668 } |
1673 | 1669 |
1892 (define-key my-map "\M-a" 'my-command) | 1888 (define-key my-map "\M-a" 'my-command) |
1893 and then perhaps | 1889 and then perhaps |
1894 (defvar my-escape-map (lookup-key my-map "\e")) | 1890 (defvar my-escape-map (lookup-key my-map "\e")) |
1895 if the luser really wants the map in a variable. | 1891 if the luser really wants the map in a variable. |
1896 */ | 1892 */ |
1897 Lisp_Object meta_map; | 1893 Lisp_Object mmap; |
1898 struct gcpro ngcpro1; | 1894 struct gcpro ngcpro1; |
1899 | 1895 |
1900 NGCPRO1 (c); | 1896 NGCPRO1 (c); |
1901 meta_map = Fgethash (MAKE_MODIFIER_HASH_KEY (XEMACS_MOD_META), | 1897 mmap = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META), |
1902 XKEYMAP (keymap)->table, Qnil); | 1898 XKEYMAP (keymap)->table, Qnil); |
1903 if (!NILP (meta_map) | 1899 if (!NILP (mmap) |
1904 && keymap_fullness (meta_map) != 0) | 1900 && keymap_fullness (mmap) != 0) |
1905 signal_simple_error_2 | 1901 { |
1906 ("Map contains meta-bindings, can't bind", | 1902 Lisp_Object desc |
1907 Fsingle_key_description (Vmeta_prefix_char), keymap); | 1903 = Fsingle_key_description (Vmeta_prefix_char); |
1904 signal_simple_error_2 | |
1905 ("Map contains meta-bindings, can't bind", desc, keymap); | |
1906 } | |
1908 NUNGCPRO; | 1907 NUNGCPRO; |
1909 } | 1908 } |
1910 else | 1909 else |
1911 { | 1910 { |
1912 metized = 1; | 1911 metized = 1; |
1923 raw_key2.modifiers = 0; | 1922 raw_key2.modifiers = 0; |
1924 } | 1923 } |
1925 | 1924 |
1926 if (metized) | 1925 if (metized) |
1927 { | 1926 { |
1928 raw_key1.modifiers |= XEMACS_MOD_META; | 1927 raw_key1.modifiers |= MOD_META; |
1929 raw_key2.modifiers |= XEMACS_MOD_META; | 1928 raw_key2.modifiers |= MOD_META; |
1930 metized = 0; | 1929 metized = 0; |
1931 } | 1930 } |
1932 | 1931 |
1933 /* This crap is to make sure that someone doesn't bind something like | 1932 /* This crap is to make sure that someone doesn't bind something like |
1934 "C-x M-a" while "C-x ESC" has a non-keymap binding. */ | 1933 "C-x M-a" while "C-x ESC" has a non-keymap binding. */ |
1935 if (raw_key1.modifiers & XEMACS_MOD_META) | 1934 if (raw_key1.modifiers & MOD_META) |
1936 ensure_meta_prefix_char_keymapp (keys, idx, keymap); | 1935 ensure_meta_prefix_char_keymapp (keys, idx, keymap); |
1937 | 1936 |
1938 if (++idx == len) | 1937 if (++idx == len) |
1939 { | 1938 { |
1940 keymap_store (keymap, &raw_key1, def); | 1939 keymap_store (keymap, &raw_key1, def); |
1980 to make where-is-internal really fly. */ | 1979 to make where-is-internal really fly. */ |
1981 | 1980 |
1982 struct raw_lookup_key_mapper_closure | 1981 struct raw_lookup_key_mapper_closure |
1983 { | 1982 { |
1984 int remaining; | 1983 int remaining; |
1985 const struct key_data *raw_keys; | 1984 CONST struct key_data *raw_keys; |
1986 int raw_keys_count; | 1985 int raw_keys_count; |
1987 int keys_so_far; | 1986 int keys_so_far; |
1988 int accept_default; | 1987 int accept_default; |
1989 }; | 1988 }; |
1990 | 1989 |
1991 static Lisp_Object raw_lookup_key_mapper (Lisp_Object k, void *); | 1990 static Lisp_Object raw_lookup_key_mapper (Lisp_Object k, void *); |
1992 | 1991 |
1993 /* Caller should gc-protect args (keymaps may autoload) */ | 1992 /* Caller should gc-protect args (keymaps may autoload) */ |
1994 static Lisp_Object | 1993 static Lisp_Object |
1995 raw_lookup_key (Lisp_Object keymap, | 1994 raw_lookup_key (Lisp_Object keymap, |
1996 const struct key_data *raw_keys, int raw_keys_count, | 1995 CONST struct key_data *raw_keys, int raw_keys_count, |
1997 int keys_so_far, int accept_default) | 1996 int keys_so_far, int accept_default) |
1998 { | 1997 { |
1999 /* This function can GC */ | 1998 /* This function can GC */ |
2000 struct raw_lookup_key_mapper_closure c; | 1999 struct raw_lookup_key_mapper_closure c; |
2001 c.remaining = raw_keys_count - 1; | 2000 c.remaining = raw_keys_count - 1; |
2014 struct raw_lookup_key_mapper_closure *c = | 2013 struct raw_lookup_key_mapper_closure *c = |
2015 (struct raw_lookup_key_mapper_closure *) arg; | 2014 (struct raw_lookup_key_mapper_closure *) arg; |
2016 int accept_default = c->accept_default; | 2015 int accept_default = c->accept_default; |
2017 int remaining = c->remaining; | 2016 int remaining = c->remaining; |
2018 int keys_so_far = c->keys_so_far; | 2017 int keys_so_far = c->keys_so_far; |
2019 const struct key_data *raw_keys = c->raw_keys; | 2018 CONST struct key_data *raw_keys = c->raw_keys; |
2020 Lisp_Object cmd; | 2019 Lisp_Object cmd; |
2021 | 2020 |
2022 if (! meta_prefix_char_p (&(raw_keys[0]))) | 2021 if (! meta_prefix_char_p (&(raw_keys[0]))) |
2023 { | 2022 { |
2024 /* Normal case: every case except the meta-hack (see below). */ | 2023 /* Normal case: every case except the meta-hack (see below). */ |
2053 /* First look for the prefix-char directly */ | 2052 /* First look for the prefix-char directly */ |
2054 cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default); | 2053 cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default); |
2055 if (NILP (cmd)) | 2054 if (NILP (cmd)) |
2056 { | 2055 { |
2057 /* Do kludgy return of the meta-map */ | 2056 /* Do kludgy return of the meta-map */ |
2058 cmd = Fgethash (MAKE_MODIFIER_HASH_KEY (XEMACS_MOD_META), | 2057 cmd = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META), |
2059 XKEYMAP (k)->table, Qnil); | 2058 XKEYMAP (k)->table, Qnil); |
2060 } | 2059 } |
2061 } | 2060 } |
2062 else | 2061 else |
2063 { | 2062 { |
2065 cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default); | 2064 cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default); |
2066 cmd = get_keymap (cmd, 0, 1); | 2065 cmd = get_keymap (cmd, 0, 1); |
2067 if (!NILP (cmd)) | 2066 if (!NILP (cmd)) |
2068 cmd = raw_lookup_key (cmd, raw_keys + 1, remaining, | 2067 cmd = raw_lookup_key (cmd, raw_keys + 1, remaining, |
2069 keys_so_far + 1, accept_default); | 2068 keys_so_far + 1, accept_default); |
2070 else if ((raw_keys[1].modifiers & XEMACS_MOD_META) == 0) | 2069 else if ((raw_keys[1].modifiers & MOD_META) == 0) |
2071 { | 2070 { |
2072 struct key_data metified; | 2071 struct key_data metified; |
2073 metified.keysym = raw_keys[1].keysym; | 2072 metified.keysym = raw_keys[1].keysym; |
2074 metified.modifiers = raw_keys[1].modifiers | | 2073 metified.modifiers = raw_keys[1].modifiers | MOD_META; |
2075 (unsigned char) XEMACS_MOD_META; | |
2076 | 2074 |
2077 /* Search for meta-next-char sequence directly */ | 2075 /* Search for meta-next-char sequence directly */ |
2078 cmd = keymap_lookup_1 (k, &metified, accept_default); | 2076 cmd = keymap_lookup_1 (k, &metified, accept_default); |
2079 if (remaining == 1) | 2077 if (remaining == 1) |
2080 ; | 2078 ; |
2106 int i; | 2104 int i; |
2107 | 2105 |
2108 if (nkeys == 0) | 2106 if (nkeys == 0) |
2109 return Qnil; | 2107 return Qnil; |
2110 | 2108 |
2111 if (nkeys < countof (kkk)) | 2109 if (nkeys < (countof (kkk))) |
2112 raw_keys = kkk; | 2110 raw_keys = kkk; |
2113 else | 2111 else |
2114 raw_keys = alloca_array (struct key_data, nkeys); | 2112 raw_keys = alloca_array (struct key_data, nkeys); |
2115 | 2113 |
2116 for (i = 0; i < nkeys; i++) | 2114 for (i = 0; i < nkeys; i++) |
2136 | 2134 |
2137 CHECK_LIVE_EVENT (event_head); | 2135 CHECK_LIVE_EVENT (event_head); |
2138 | 2136 |
2139 nkeys = event_chain_count (event_head); | 2137 nkeys = event_chain_count (event_head); |
2140 | 2138 |
2141 if (nkeys < countof (kkk)) | 2139 if (nkeys < (countof (kkk))) |
2142 raw_keys = kkk; | 2140 raw_keys = kkk; |
2143 else | 2141 else |
2144 raw_keys = alloca_array (struct key_data, nkeys); | 2142 raw_keys = alloca_array (struct key_data, nkeys); |
2145 | 2143 |
2146 nkeys = 0; | 2144 nkeys = 0; |
2362 buffer); | 2360 buffer); |
2363 | 2361 |
2364 get_relevant_extent_keymaps | 2362 get_relevant_extent_keymaps |
2365 (Fevent_modeline_position (terminal), | 2363 (Fevent_modeline_position (terminal), |
2366 XBUFFER (buffer)->generated_modeline_string, | 2364 XBUFFER (buffer)->generated_modeline_string, |
2367 Fevent_glyph_extent (terminal), &closure); | 2365 /* #### third arg should maybe be a glyph. */ |
2366 Qnil, &closure); | |
2368 | 2367 |
2369 if (!UNBOUNDP (map) && !NILP (map)) | 2368 if (!UNBOUNDP (map) && !NILP (map)) |
2370 relevant_map_push (get_keymap (map, 1, 1), &closure); | 2369 relevant_map_push (get_keymap (map, 1, 1), &closure); |
2371 } | 2370 } |
2372 else | 2371 else |
2730 outside of this file doesn't need to know about. | 2729 outside of this file doesn't need to know about. |
2731 */ | 2730 */ |
2732 | 2731 |
2733 struct map_keymap_unsorted_closure | 2732 struct map_keymap_unsorted_closure |
2734 { | 2733 { |
2735 void (*fn) (const struct key_data *, Lisp_Object binding, void *arg); | 2734 void (*fn) (CONST struct key_data *, Lisp_Object binding, void *arg); |
2736 void *arg; | 2735 void *arg; |
2737 int modifiers; | 2736 unsigned int modifiers; |
2738 }; | 2737 }; |
2739 | 2738 |
2740 /* used by map_keymap() */ | 2739 /* used by map_keymap() */ |
2741 static int | 2740 static int |
2742 map_keymap_unsorted_mapper (Lisp_Object keysym, Lisp_Object value, | 2741 map_keymap_unsorted_mapper (Lisp_Object keysym, Lisp_Object value, |
2743 void *map_keymap_unsorted_closure) | 2742 void *map_keymap_unsorted_closure) |
2744 { | 2743 { |
2745 /* This function can GC */ | 2744 /* This function can GC */ |
2746 struct map_keymap_unsorted_closure *closure = | 2745 struct map_keymap_unsorted_closure *closure = |
2747 (struct map_keymap_unsorted_closure *) map_keymap_unsorted_closure; | 2746 (struct map_keymap_unsorted_closure *) map_keymap_unsorted_closure; |
2748 int modifiers = closure->modifiers; | 2747 unsigned int modifiers = closure->modifiers; |
2749 int mod_bit; | 2748 unsigned int mod_bit; |
2750 mod_bit = MODIFIER_HASH_KEY_BITS (keysym); | 2749 mod_bit = MODIFIER_HASH_KEY_BITS (keysym); |
2751 if (mod_bit != 0) | 2750 if (mod_bit != 0) |
2752 { | 2751 { |
2753 int omod = modifiers; | 2752 int omod = modifiers; |
2754 closure->modifiers = (modifiers | mod_bit); | 2753 closure->modifiers = (modifiers | mod_bit); |
2794 map_keymap_sort_predicate (Lisp_Object obj1, Lisp_Object obj2, | 2793 map_keymap_sort_predicate (Lisp_Object obj1, Lisp_Object obj2, |
2795 Lisp_Object pred) | 2794 Lisp_Object pred) |
2796 { | 2795 { |
2797 /* obj1 and obj2 are conses with keysyms in their cars. Cdrs are ignored. | 2796 /* obj1 and obj2 are conses with keysyms in their cars. Cdrs are ignored. |
2798 */ | 2797 */ |
2799 int bit1, bit2; | 2798 unsigned int bit1, bit2; |
2800 int sym1_p = 0; | 2799 int sym1_p = 0; |
2801 int sym2_p = 0; | 2800 int sym2_p = 0; |
2802 obj1 = XCAR (obj1); | 2801 obj1 = XCAR (obj1); |
2803 obj2 = XCAR (obj2); | 2802 obj2 = XCAR (obj2); |
2804 | 2803 |
2868 | 2867 |
2869 | 2868 |
2870 /* used by map_keymap() */ | 2869 /* used by map_keymap() */ |
2871 static void | 2870 static void |
2872 map_keymap_sorted (Lisp_Object keymap_table, | 2871 map_keymap_sorted (Lisp_Object keymap_table, |
2873 int modifiers, | 2872 unsigned int modifiers, |
2874 void (*function) (const struct key_data *key, | 2873 void (*function) (CONST struct key_data *key, |
2875 Lisp_Object binding, | 2874 Lisp_Object binding, |
2876 void *map_keymap_sorted_closure), | 2875 void *map_keymap_sorted_closure), |
2877 void *map_keymap_sorted_closure) | 2876 void *map_keymap_sorted_closure) |
2878 { | 2877 { |
2879 /* This function can GC */ | 2878 /* This function can GC */ |
2893 contents = list_sort (contents, Qnil, map_keymap_sort_predicate); | 2892 contents = list_sort (contents, Qnil, map_keymap_sort_predicate); |
2894 for (; !NILP (contents); contents = XCDR (contents)) | 2893 for (; !NILP (contents); contents = XCDR (contents)) |
2895 { | 2894 { |
2896 Lisp_Object keysym = XCAR (XCAR (contents)); | 2895 Lisp_Object keysym = XCAR (XCAR (contents)); |
2897 Lisp_Object binding = XCDR (XCAR (contents)); | 2896 Lisp_Object binding = XCDR (XCAR (contents)); |
2898 int sub_bits = MODIFIER_HASH_KEY_BITS (keysym); | 2897 unsigned int sub_bits = MODIFIER_HASH_KEY_BITS (keysym); |
2899 if (sub_bits != 0) | 2898 if (sub_bits != 0) |
2900 map_keymap_sorted (XKEYMAP (get_keymap (binding, | 2899 map_keymap_sorted (XKEYMAP (get_keymap (binding, |
2901 1, 1))->table, | 2900 1, 1))->table, |
2902 (modifiers | sub_bits), | 2901 (modifiers | sub_bits), |
2903 function, | 2902 function, |
2914 } | 2913 } |
2915 | 2914 |
2916 | 2915 |
2917 /* used by Fmap_keymap() */ | 2916 /* used by Fmap_keymap() */ |
2918 static void | 2917 static void |
2919 map_keymap_mapper (const struct key_data *key, | 2918 map_keymap_mapper (CONST struct key_data *key, |
2920 Lisp_Object binding, | 2919 Lisp_Object binding, |
2921 void *function) | 2920 void *function) |
2922 { | 2921 { |
2923 /* This function can GC */ | 2922 /* This function can GC */ |
2924 Lisp_Object fn; | 2923 Lisp_Object fn; |
2927 } | 2926 } |
2928 | 2927 |
2929 | 2928 |
2930 static void | 2929 static void |
2931 map_keymap (Lisp_Object keymap_table, int sort_first, | 2930 map_keymap (Lisp_Object keymap_table, int sort_first, |
2932 void (*function) (const struct key_data *key, | 2931 void (*function) (CONST struct key_data *key, |
2933 Lisp_Object binding, | 2932 Lisp_Object binding, |
2934 void *fn_arg), | 2933 void *fn_arg), |
2935 void *fn_arg) | 2934 void *fn_arg) |
2936 { | 2935 { |
2937 /* This function can GC */ | 2936 /* This function can GC */ |
2999 }; | 2998 }; |
3000 | 2999 |
3001 | 3000 |
3002 static void | 3001 static void |
3003 accessible_keymaps_mapper_1 (Lisp_Object keysym, Lisp_Object contents, | 3002 accessible_keymaps_mapper_1 (Lisp_Object keysym, Lisp_Object contents, |
3004 int modifiers, | 3003 unsigned int modifiers, |
3005 struct accessible_keymaps_closure *closure) | 3004 struct accessible_keymaps_closure *closure) |
3006 { | 3005 { |
3007 /* This function can GC */ | 3006 /* This function can GC */ |
3008 int subbits = MODIFIER_HASH_KEY_BITS (keysym); | 3007 unsigned int subbits = MODIFIER_HASH_KEY_BITS (keysym); |
3009 | 3008 |
3010 if (subbits != 0) | 3009 if (subbits != 0) |
3011 { | 3010 { |
3012 Lisp_Object submaps; | 3011 Lisp_Object submaps; |
3013 | 3012 |
3083 Lisp_Object accessible_keymaps = Qnil; | 3082 Lisp_Object accessible_keymaps = Qnil; |
3084 struct accessible_keymaps_closure c; | 3083 struct accessible_keymaps_closure c; |
3085 c.tail = Qnil; | 3084 c.tail = Qnil; |
3086 GCPRO4 (accessible_keymaps, c.tail, prefix, keymap); | 3085 GCPRO4 (accessible_keymaps, c.tail, prefix, keymap); |
3087 | 3086 |
3087 retry: | |
3088 keymap = get_keymap (keymap, 1, 1); | 3088 keymap = get_keymap (keymap, 1, 1); |
3089 | |
3090 retry: | |
3091 if (NILP (prefix)) | 3089 if (NILP (prefix)) |
3092 { | 3090 prefix = make_vector (0, Qnil); |
3093 prefix = make_vector (0, Qnil); | 3091 else if (!VECTORP (prefix) || STRINGP (prefix)) |
3094 } | 3092 { |
3095 else if (VECTORP (prefix) || STRINGP (prefix)) | 3093 prefix = wrong_type_argument (Qarrayp, prefix); |
3094 goto retry; | |
3095 } | |
3096 else | |
3096 { | 3097 { |
3097 int len = XINT (Flength (prefix)); | 3098 int len = XINT (Flength (prefix)); |
3098 Lisp_Object def; | 3099 Lisp_Object def = Flookup_key (keymap, prefix, Qnil); |
3099 Lisp_Object p; | 3100 Lisp_Object p; |
3100 int iii; | 3101 int iii; |
3101 struct gcpro ngcpro1; | 3102 struct gcpro ngcpro1; |
3102 | 3103 |
3103 if (len == 0) | |
3104 { | |
3105 prefix = Qnil; | |
3106 goto retry; | |
3107 } | |
3108 | |
3109 def = Flookup_key (keymap, prefix, Qnil); | |
3110 def = get_keymap (def, 0, 1); | 3104 def = get_keymap (def, 0, 1); |
3111 if (!KEYMAPP (def)) | 3105 if (!KEYMAPP (def)) |
3112 goto RETURN; | 3106 goto RETURN; |
3113 | 3107 |
3114 keymap = def; | 3108 keymap = def; |
3121 XVECTOR_DATA (p)[iii] = make_key_description (&key, 1); | 3115 XVECTOR_DATA (p)[iii] = make_key_description (&key, 1); |
3122 } | 3116 } |
3123 NUNGCPRO; | 3117 NUNGCPRO; |
3124 prefix = p; | 3118 prefix = p; |
3125 } | 3119 } |
3126 else | |
3127 { | |
3128 prefix = wrong_type_argument (Qarrayp, prefix); | |
3129 goto retry; | |
3130 } | |
3131 | 3120 |
3132 accessible_keymaps = list1 (Fcons (prefix, keymap)); | 3121 accessible_keymaps = list1 (Fcons (prefix, keymap)); |
3133 | 3122 |
3134 /* For each map in the list maps, look at any other maps it points | 3123 /* For each map in the list maps, |
3135 to and stick them at the end if they are not already in the list */ | 3124 look at any other maps it points to |
3125 and stick them at the end if they are not already in the list */ | |
3136 | 3126 |
3137 for (c.tail = accessible_keymaps; | 3127 for (c.tail = accessible_keymaps; |
3138 !NILP (c.tail); | 3128 !NILP (c.tail); |
3139 c.tail = XCDR (c.tail)) | 3129 c.tail = XCDR (c.tail)) |
3140 { | 3130 { |
3175 int i; | 3165 int i; |
3176 | 3166 |
3177 for (i = 0; i < size; i++) | 3167 for (i = 0; i < size; i++) |
3178 { | 3168 { |
3179 Lisp_Object s2 = Fsingle_key_description | 3169 Lisp_Object s2 = Fsingle_key_description |
3180 (STRINGP (keys) | 3170 (((STRINGP (keys)) |
3181 ? make_char (string_char (XSTRING (keys), i)) | 3171 ? make_char (string_char (XSTRING (keys), i)) |
3182 : XVECTOR_DATA (keys)[i]); | 3172 : XVECTOR_DATA (keys)[i])); |
3183 | 3173 |
3184 if (i == 0) | 3174 if (i == 0) |
3185 string = s2; | 3175 string = s2; |
3186 else | 3176 else |
3187 { | 3177 { |
3208 if (EVENTP (key) || CHAR_OR_CHAR_INTP (key)) | 3198 if (EVENTP (key) || CHAR_OR_CHAR_INTP (key)) |
3209 { | 3199 { |
3210 char buf [255]; | 3200 char buf [255]; |
3211 if (!EVENTP (key)) | 3201 if (!EVENTP (key)) |
3212 { | 3202 { |
3213 Lisp_Event event; | 3203 struct Lisp_Event event; |
3214 event.event_type = empty_event; | 3204 event.event_type = empty_event; |
3215 CHECK_CHAR_COERCE_INT (key); | 3205 CHECK_CHAR_COERCE_INT (key); |
3216 character_to_event (XCHAR (key), &event, | 3206 character_to_event (XCHAR (key), &event, |
3217 XCONSOLE (Vselected_console), 0, 1); | 3207 XCONSOLE (Vselected_console), 0, 1); |
3218 format_event_object (buf, &event, 1); | 3208 format_event_object (buf, &event, 1); |
3457 | 3447 |
3458 static void | 3448 static void |
3459 format_raw_keys (struct key_data *keys, int count, char *buf) | 3449 format_raw_keys (struct key_data *keys, int count, char *buf) |
3460 { | 3450 { |
3461 int i; | 3451 int i; |
3462 Lisp_Event event; | 3452 struct Lisp_Event event; |
3463 event.event_type = key_press_event; | 3453 event.event_type = key_press_event; |
3464 event.channel = Vselected_console; | 3454 event.channel = Vselected_console; |
3465 for (i = 0; i < count; i++) | 3455 for (i = 0; i < count; i++) |
3466 { | 3456 { |
3467 event.event.key.keysym = keys[i].keysym; | 3457 event.event.key.keysym = keys[i].keysym; |
3481 returning, then we reconsider. | 3471 returning, then we reconsider. |
3482 firstonly means give up after finding the first match; | 3472 firstonly means give up after finding the first match; |
3483 keys_so_far and modifiers_so_far describe which map we're looking in; | 3473 keys_so_far and modifiers_so_far describe which map we're looking in; |
3484 If we're in the "meta" submap of the map that "C-x 4" is bound to, | 3474 If we're in the "meta" submap of the map that "C-x 4" is bound to, |
3485 then keys_so_far will be {(control x), \4}, and modifiers_so_far | 3475 then keys_so_far will be {(control x), \4}, and modifiers_so_far |
3486 will be XEMACS_MOD_META. That is, keys_so_far is the chain of keys that we | 3476 will be MOD_META. That is, keys_so_far is the chain of keys that we |
3487 have followed, and modifiers_so_far_so_far is the bits (partial keys) | 3477 have followed, and modifiers_so_far_so_far is the bits (partial keys) |
3488 beyond that. | 3478 beyond that. |
3489 | 3479 |
3490 (keys_so_far is a global buffer and the keys_count arg says how much | 3480 (keys_so_far is a global buffer and the keys_count arg says how much |
3491 of it we're currently interested in.) | 3481 of it we're currently interested in.) |
3499 Lisp_Object definition; | 3489 Lisp_Object definition; |
3500 Lisp_Object *shadow; | 3490 Lisp_Object *shadow; |
3501 int shadow_count; | 3491 int shadow_count; |
3502 int firstonly; | 3492 int firstonly; |
3503 int keys_count; | 3493 int keys_count; |
3504 int modifiers_so_far; | 3494 unsigned int modifiers_so_far; |
3505 char *target_buffer; | 3495 char *target_buffer; |
3506 struct key_data *keys_so_far; | 3496 struct key_data *keys_so_far; |
3507 int keys_so_far_total_size; | 3497 int keys_so_far_total_size; |
3508 int keys_so_far_malloced; | 3498 int keys_so_far_malloced; |
3509 }; | 3499 }; |
3514 where_is_recursive_mapper (Lisp_Object map, void *arg) | 3504 where_is_recursive_mapper (Lisp_Object map, void *arg) |
3515 { | 3505 { |
3516 /* This function can GC */ | 3506 /* This function can GC */ |
3517 struct where_is_closure *c = (struct where_is_closure *) arg; | 3507 struct where_is_closure *c = (struct where_is_closure *) arg; |
3518 Lisp_Object definition = c->definition; | 3508 Lisp_Object definition = c->definition; |
3519 const int firstonly = c->firstonly; | 3509 CONST int firstonly = c->firstonly; |
3520 const int keys_count = c->keys_count; | 3510 CONST unsigned int keys_count = c->keys_count; |
3521 const int modifiers_so_far = c->modifiers_so_far; | 3511 CONST unsigned int modifiers_so_far = c->modifiers_so_far; |
3522 char *target_buffer = c->target_buffer; | 3512 char *target_buffer = c->target_buffer; |
3523 Lisp_Object keys = Fgethash (definition, | 3513 Lisp_Object keys = Fgethash (definition, |
3524 XKEYMAP (map)->inverse_table, | 3514 XKEYMAP (map)->inverse_table, |
3525 Qnil); | 3515 Qnil); |
3526 Lisp_Object submaps; | 3516 Lisp_Object submaps; |
3534 raw_lookup_key() means undefined. */ | 3524 raw_lookup_key() means undefined. */ |
3535 struct key_data *so_far = c->keys_so_far; | 3525 struct key_data *so_far = c->keys_so_far; |
3536 | 3526 |
3537 for (;;) /* loop over all keys that match */ | 3527 for (;;) /* loop over all keys that match */ |
3538 { | 3528 { |
3539 Lisp_Object k = CONSP (keys) ? XCAR (keys) : keys; | 3529 Lisp_Object k = ((CONSP (keys)) ? XCAR (keys) : keys); |
3540 int i; | 3530 int i; |
3541 | 3531 |
3542 so_far [keys_count].keysym = k; | 3532 so_far [keys_count].keysym = k; |
3543 so_far [keys_count].modifiers = modifiers_so_far; | 3533 so_far [keys_count].modifiers = modifiers_so_far; |
3544 | 3534 |
3589 !NILP (submaps); | 3579 !NILP (submaps); |
3590 submaps = XCDR (submaps)) | 3580 submaps = XCDR (submaps)) |
3591 { | 3581 { |
3592 Lisp_Object key = XCAR (XCAR (submaps)); | 3582 Lisp_Object key = XCAR (XCAR (submaps)); |
3593 Lisp_Object submap = XCDR (XCAR (submaps)); | 3583 Lisp_Object submap = XCDR (XCAR (submaps)); |
3594 int lower_modifiers; | 3584 unsigned int lower_modifiers; |
3595 int lower_keys_count = keys_count; | 3585 int lower_keys_count = keys_count; |
3596 int bucky; | 3586 unsigned int bucky; |
3597 | 3587 |
3598 submap = get_keymap (submap, 0, 0); | 3588 submap = get_keymap (submap, 0, 0); |
3599 | 3589 |
3600 if (EQ (submap, map)) | 3590 if (EQ (submap, map)) |
3601 /* Arrgh! Some loser has introduced a loop... */ | 3591 /* Arrgh! Some loser has introduced a loop... */ |
3632 { | 3622 { |
3633 int size = lower_keys_count + 50; | 3623 int size = lower_keys_count + 50; |
3634 if (! c->keys_so_far_malloced) | 3624 if (! c->keys_so_far_malloced) |
3635 { | 3625 { |
3636 struct key_data *new = xnew_array (struct key_data, size); | 3626 struct key_data *new = xnew_array (struct key_data, size); |
3637 memcpy ((void *)new, (const void *)c->keys_so_far, | 3627 memcpy ((void *)new, (CONST void *)c->keys_so_far, |
3638 c->keys_so_far_total_size * sizeof (struct key_data)); | 3628 c->keys_so_far_total_size * sizeof (struct key_data)); |
3639 } | 3629 } |
3640 else | 3630 else |
3641 XREALLOC_ARRAY (c->keys_so_far, struct key_data, size); | 3631 XREALLOC_ARRAY (c->keys_so_far, struct key_data, size); |
3642 | 3632 |
3885 int mice_only_p; /* whether we are to display only button bindings */ | 3875 int mice_only_p; /* whether we are to display only button bindings */ |
3886 }; | 3876 }; |
3887 | 3877 |
3888 struct describe_map_shadow_closure | 3878 struct describe_map_shadow_closure |
3889 { | 3879 { |
3890 const struct key_data *raw_key; | 3880 CONST struct key_data *raw_key; |
3891 Lisp_Object self; | 3881 Lisp_Object self; |
3892 }; | 3882 }; |
3893 | 3883 |
3894 static Lisp_Object | 3884 static Lisp_Object |
3895 describe_map_mapper_shadow_search (Lisp_Object map, void *arg) | 3885 describe_map_mapper_shadow_search (Lisp_Object map, void *arg) |
3914 return keymap_lookup_directly (km, k->keysym, k->modifiers); | 3904 return keymap_lookup_directly (km, k->keysym, k->modifiers); |
3915 } | 3905 } |
3916 | 3906 |
3917 | 3907 |
3918 static void | 3908 static void |
3919 describe_map_mapper (const struct key_data *key, | 3909 describe_map_mapper (CONST struct key_data *key, |
3920 Lisp_Object binding, | 3910 Lisp_Object binding, |
3921 void *describe_map_closure) | 3911 void *describe_map_closure) |
3922 { | 3912 { |
3923 /* This function can GC */ | 3913 /* This function can GC */ |
3924 struct describe_map_closure *closure = | 3914 struct describe_map_closure *closure = |
3925 (struct describe_map_closure *) describe_map_closure; | 3915 (struct describe_map_closure *) describe_map_closure; |
3926 Lisp_Object keysym = key->keysym; | 3916 Lisp_Object keysym = key->keysym; |
3927 int modifiers = key->modifiers; | 3917 unsigned int modifiers = key->modifiers; |
3928 | 3918 |
3929 /* Don't mention suppressed commands. */ | 3919 /* Don't mention suppressed commands. */ |
3930 if (SYMBOLP (binding) | 3920 if (SYMBOLP (binding) |
3931 && !NILP (closure->partial) | 3921 && !NILP (closure->partial) |
3932 && !NILP (Fget (binding, closure->partial, Qnil))) | 3922 && !NILP (Fget (binding, closure->partial, Qnil))) |
3996 { | 3986 { |
3997 /* obj1 and obj2 are conses of the form | 3987 /* obj1 and obj2 are conses of the form |
3998 ( ( <keysym> . <modifiers> ) . <binding> ) | 3988 ( ( <keysym> . <modifiers> ) . <binding> ) |
3999 keysym and modifiers are used, binding is ignored. | 3989 keysym and modifiers are used, binding is ignored. |
4000 */ | 3990 */ |
4001 int bit1, bit2; | 3991 unsigned int bit1, bit2; |
4002 obj1 = XCAR (obj1); | 3992 obj1 = XCAR (obj1); |
4003 obj2 = XCAR (obj2); | 3993 obj2 = XCAR (obj2); |
4004 bit1 = XINT (XCDR (obj1)); | 3994 bit1 = XINT (XCDR (obj1)); |
4005 bit2 = XINT (XCDR (obj2)); | 3995 bit2 = XINT (XCDR (obj2)); |
4006 if (bit1 != bit2) | 3996 if (bit1 != bit2) |
4116 buffer_insert_c_string (buf, "\n"); | 4106 buffer_insert_c_string (buf, "\n"); |
4117 while (!NILP (list)) | 4107 while (!NILP (list)) |
4118 { | 4108 { |
4119 Lisp_Object elt = XCAR (XCAR (list)); | 4109 Lisp_Object elt = XCAR (XCAR (list)); |
4120 Lisp_Object keysym = XCAR (elt); | 4110 Lisp_Object keysym = XCAR (elt); |
4121 int modifiers = XINT (XCDR (elt)); | 4111 unsigned int modifiers = XINT (XCDR (elt)); |
4122 | 4112 |
4123 if (!NILP (elt_prefix)) | 4113 if (!NILP (elt_prefix)) |
4124 buffer_insert_lisp_string (buf, elt_prefix); | 4114 buffer_insert_lisp_string (buf, elt_prefix); |
4125 | 4115 |
4126 if (modifiers & XEMACS_MOD_META) buffer_insert_c_string (buf, "M-"); | 4116 if (modifiers & MOD_META) buffer_insert_c_string (buf, "M-"); |
4127 if (modifiers & XEMACS_MOD_CONTROL) buffer_insert_c_string (buf, "C-"); | 4117 if (modifiers & MOD_CONTROL) buffer_insert_c_string (buf, "C-"); |
4128 if (modifiers & XEMACS_MOD_SUPER) buffer_insert_c_string (buf, "S-"); | 4118 if (modifiers & MOD_SUPER) buffer_insert_c_string (buf, "S-"); |
4129 if (modifiers & XEMACS_MOD_HYPER) buffer_insert_c_string (buf, "H-"); | 4119 if (modifiers & MOD_HYPER) buffer_insert_c_string (buf, "H-"); |
4130 if (modifiers & XEMACS_MOD_ALT) buffer_insert_c_string (buf, "Alt-"); | 4120 if (modifiers & MOD_ALT) buffer_insert_c_string (buf, "Alt-"); |
4131 if (modifiers & XEMACS_MOD_SHIFT) buffer_insert_c_string (buf, "Sh-"); | 4121 if (modifiers & MOD_SHIFT) buffer_insert_c_string (buf, "Sh-"); |
4132 if (SYMBOLP (keysym)) | 4122 if (SYMBOLP (keysym)) |
4133 { | 4123 { |
4134 Lisp_Object code = Fget (keysym, Vcharacter_set_property, Qnil); | 4124 Lisp_Object code = Fget (keysym, Vcharacter_set_property, Qnil); |
4135 Emchar c = (CHAR_OR_CHAR_INTP (code) | 4125 Emchar c = (CHAR_OR_CHAR_INTP (code) |
4136 ? XCHAR_OR_CHAR_INT (code) : (Emchar) -1); | 4126 ? XCHAR_OR_CHAR_INT (code) : (Emchar) -1); |
4193 | 4183 |
4194 | 4184 |
4195 void | 4185 void |
4196 syms_of_keymap (void) | 4186 syms_of_keymap (void) |
4197 { | 4187 { |
4198 INIT_LRECORD_IMPLEMENTATION (keymap); | |
4199 | |
4200 defsymbol (&Qminor_mode_map_alist, "minor-mode-map-alist"); | 4188 defsymbol (&Qminor_mode_map_alist, "minor-mode-map-alist"); |
4201 | 4189 |
4202 defsymbol (&Qkeymapp, "keymapp"); | 4190 defsymbol (&Qkeymapp, "keymapp"); |
4203 | 4191 |
4204 defsymbol (&Qsuppress_keymap, "suppress-keymap"); | 4192 defsymbol (&Qsuppress_keymap, "suppress-keymap"); |
4276 defsymbol (&QLFD, "LFD"); | 4264 defsymbol (&QLFD, "LFD"); |
4277 defsymbol (&QTAB, "TAB"); | 4265 defsymbol (&QTAB, "TAB"); |
4278 defsymbol (&QRET, "RET"); | 4266 defsymbol (&QRET, "RET"); |
4279 defsymbol (&QESC, "ESC"); | 4267 defsymbol (&QESC, "ESC"); |
4280 defsymbol (&QDEL, "DEL"); | 4268 defsymbol (&QDEL, "DEL"); |
4281 defsymbol (&QSPC, "SPC"); | |
4282 defsymbol (&QBS, "BS"); | 4269 defsymbol (&QBS, "BS"); |
4283 } | 4270 } |
4284 | 4271 |
4285 void | 4272 void |
4286 vars_of_keymap (void) | 4273 vars_of_keymap (void) |
4330 */ ); | 4317 */ ); |
4331 keymap_tick = 0; | 4318 keymap_tick = 0; |
4332 | 4319 |
4333 staticpro (&Vcurrent_global_map); | 4320 staticpro (&Vcurrent_global_map); |
4334 | 4321 |
4335 Vsingle_space_string = make_string ((const Bufbyte *) " ", 1); | 4322 Vsingle_space_string = make_string_nocopy ((CONST Bufbyte *) " ", 1); |
4336 staticpro (&Vsingle_space_string); | 4323 staticpro (&Vsingle_space_string); |
4337 } | 4324 } |
4338 | 4325 |
4339 void | 4326 void |
4340 complex_vars_of_keymap (void) | 4327 complex_vars_of_keymap (void) |
4346 Vcurrent_global_map = Fmake_keymap (Qnil); | 4333 Vcurrent_global_map = Fmake_keymap (Qnil); |
4347 | 4334 |
4348 meta_disgustitute = Fmake_keymap (Qnil); | 4335 meta_disgustitute = Fmake_keymap (Qnil); |
4349 Ffset (ESC_prefix, meta_disgustitute); | 4336 Ffset (ESC_prefix, meta_disgustitute); |
4350 /* no need to protect meta_disgustitute, though */ | 4337 /* no need to protect meta_disgustitute, though */ |
4351 keymap_store_internal (MAKE_MODIFIER_HASH_KEY (XEMACS_MOD_META), | 4338 keymap_store_internal (MAKE_MODIFIER_HASH_KEY (MOD_META), |
4352 XKEYMAP (Vcurrent_global_map), | 4339 XKEYMAP (Vcurrent_global_map), |
4353 meta_disgustitute); | 4340 meta_disgustitute); |
4354 XKEYMAP (Vcurrent_global_map)->sub_maps_cache = Qt; | 4341 XKEYMAP (Vcurrent_global_map)->sub_maps_cache = Qt; |
4355 | 4342 |
4356 Vkey_translation_map = Fmake_sparse_keymap (intern ("key-translation-map")); | 4343 Vkey_translation_map = Fmake_sparse_keymap (intern ("key-translation-map")); |