home *** CD-ROM | disk | FTP | other *** search
/ Linux Cubed Series 2: Applications / Linux Cubed Series 2 - Applications.iso / editors / emacs / xemacs / xemacs-1.004 / xemacs-1 / xemacs-19.13 / src / keymap.c < prev    next >
Encoding:
C/C++ Source or Header  |  1995-08-07  |  127.2 KB  |  4,171 lines

  1. /* Manipulation of keymaps
  2.    Copyright (C) 1985, 1991, 1992, 1993, 1994 Free Software Foundation, Inc.
  3.    Copyright (C) 1995 Board of Trustees, University of Illinois
  4.    Totally redesigned by jwz in 1991.
  5.  
  6. This file is part of XEmacs.
  7.  
  8. XEmacs is free software; you can redistribute it and/or modify it
  9. under the terms of the GNU General Public License as published by the
  10. Free Software Foundation; either version 2, or (at your option) any
  11. later version.
  12.  
  13. XEmacs is distributed in the hope that it will be useful, but WITHOUT
  14. ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  15. FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  16. for more details.
  17.  
  18. You should have received a copy of the GNU General Public License
  19. along with XEmacs; see the file COPYING.  If not, write to the Free
  20. Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
  21.  
  22. /* Synched up with: Mule 2.0.  Not synched with FSF.  Substantially
  23.    different from FSF. */
  24.  
  25.  
  26. #include <config.h>
  27. #include "lisp.h"
  28.  
  29. #include "buffer.h"
  30. #include "bytecode.h"
  31. #include "commands.h"
  32. #include "elhash.h"
  33. #include "events.h"
  34. #include "device.h"
  35. #include "frame.h"
  36. #include "insdel.h"
  37. #include "keymap.h"
  38. #include "window.h"
  39.  
  40.  
  41. /* A keymap contains four slots:
  42.  
  43.    parents       Ordered list of keymaps to search after
  44.                    this one if no match is found.
  45.            Keymaps can thus be arranged in a hierarchy.
  46.  
  47.    table       A hash table, hashing keysyms to their bindings.
  48.            As in the rest of emacs, a keysym is either a symbol or
  49.            an integer, which is an ASCII code (of one of the printing
  50.            ASCII characters: not 003 meaning C-c, for instance).
  51.            It can also be an integer representing a modifier
  52.            combination; this will be greater than or equal to
  53.            (1 << 16).
  54.  
  55.    inverse_table   A hash table, hashing bindings to the list of keysyms
  56.            in this keymap which are bound to them.  This is to make
  57.            the Fwhere_is_internal() function be fast.  It needs to be
  58.            fast because we want to be able to call it in realtime to
  59.            update the keyboard-equivalents on the pulldown menus.
  60.                    Values of the table are either atoms (keysyms)
  61.                    or a dotted list of keysyms.
  62.  
  63.    sub_maps_cache  An alist; for each entry in this keymap whose binding is
  64.            a keymap (that is, Fkeymapp()) this alist associates that
  65.            keysym with that binding.  This is used to optimize both
  66.            Fwhere_is_internal() and Faccessible_keymaps().  This slot
  67.            gets set to the symbol `t' every time a change is made to
  68.            this keymap, causing it to be recomputed when next needed.
  69.  
  70.    prompt          See `set-keymap-prompt'.
  71.  
  72.    default_binding See `set-keymap-default-binding'.
  73.  
  74.    Sequences of keys are stored in the obvious way: if the sequence of keys
  75.    "abc" was bound to some command `foo', the hierarchy would look like
  76.  
  77.       keymap-1: associates "a" with keymap-2
  78.       keymap-2: associates "b" with keymap-3
  79.       keymap-3: associates "c" with foo
  80.  
  81.    However, bucky bits ("modifiers" to the X-minded) are represented in the
  82.    keymap hierarchy as well. (This lets us use EQable objects as hash keys.)
  83.    Each combination of modifiers (e.g. control-hyper) gets its own submap
  84.    off of the main map.  The hash key for a modifier combination is
  85.    a large integer, computed by MAKE_MODIFIER_HASH_KEY().
  86.    
  87.    If the key `C-a' was bound to some command, the hierarchy would look like
  88.  
  89.       keymap-1: associates the integer (MOD_CONTROL << 16) with keymap-2
  90.       keymap-2: associates "a" with the command
  91.  
  92.    Similarly, if the key `C-H-a' was bound to some command, the hierarchy
  93.    would look like
  94.  
  95.       keymap-1: associates the integer ((MOD_CONTROL | MOD_HYPER) << 16)
  96.                 with keymap-2
  97.       keymap-2: associates "a" with the command
  98.  
  99.    Note that a special exception is made for the meta modifier, in order
  100.    to deal with ESC/meta lossage.  Any key combination containing the
  101.    meta modifier is first indexed off of the main map into the meta
  102.    submap (with hash key (MOD_META << 16)) and then indexed off of the
  103.    meta submap with the meta modifier removed from the key combination.
  104.    For example, when associating a command with C-M-H-a, we'd have
  105.  
  106.       keymap-1: associates the integer (MOD_META << 16) with keymap-2
  107.       keymap-2: associates the integer ((MOD_CONTROL | MOD_HYPER) << 16)
  108.                 with keymap-3
  109.       keymap-3: associates "a" with the command
  110.  
  111.    Note that keymap-2 might have normal bindings in it; these would be
  112.    for key combinations containing only the meta modifier, such as
  113.    M-y or meta-backspace.
  114.  
  115.    If the command that "a" was bound to in keymap-3 was itself a keymap,
  116.    then that would make the key "C-M-H-a" be a prefix character.
  117.  
  118.    Note that this new model of keymaps takes much of the magic away from
  119.    the Escape key: the value of the variable `esc-map' is no longer indexed
  120.    in the `global-map' under the ESC key.  It's indexed under the integer
  121.    (MOD_META << 16).  This is not user-visible, however; none of the "bucky"
  122.    maps are.
  123.  
  124.    There is a hack in Flookup_key() that makes (lookup-key global-map "\^[")
  125.    and (define-key some-random-map "\^[" my-esc-map) work as before, for
  126.    compatibility.
  127.  
  128.    Since keymaps are opaque, the only way to extract information from them
  129.    is with the functions lookup-key, key-binding, local-key-binding, and
  130.    global-key-binding, which work just as before, and the new function
  131.    map-keymap, which is roughly analagous to maphash.  
  132.  
  133.    Note that map-keymap perpetuates the illusion that the "bucky" submaps
  134.    don't exist: if you map over a keymap with bucky submaps, it will also
  135.    map over those submaps.  It does not, however, map over other random
  136.    submaps of the keymap, just the bucky ones.
  137.  
  138.    One implication of this is that when you map over `global-map', you will
  139.    also map over `esc-map'.  It is merely for compatibility that the esc-map
  140.    is accessible at all; I think that's a bad thing, since it blurs the
  141.    distinction between ESC and "meta" even more.  "M-x" is no more a two-
  142.    key sequence than "C-x" is.
  143.  
  144.  */
  145.  
  146. struct keymap
  147. {
  148.   struct lcrecord_header header;
  149.   Lisp_Object parents;        /* Keymaps to be searched after this one
  150.                  *  An ordered list */
  151.   Lisp_Object prompt;           /* Qnil or a string to print in the minibuffer
  152.                                  *  when reading from this keymap */
  153.                                    
  154.   Lisp_Object table;        /* The contents of this keymap */
  155.   Lisp_Object inverse_table;    /* The inverse mapping of the above */
  156.  
  157.   Lisp_Object default_binding;  /* Use this if no other binding is found
  158.                                  *  (this overrides parent maps and the
  159.                                  *   normal global-map lookup). */
  160.  
  161.  
  162.   Lisp_Object sub_maps_cache;    /* Cache of directly inferior keymaps;
  163.                    This holds an alist, of the key and the
  164.                    maps, or the modifier bit and the map.
  165.                    If this is the symbol t, then the cache
  166.                    needs to be recomputed.
  167.                  */
  168.   int fullness;            /* How many entries there are in this table.
  169.                     This should be the same as the fullness
  170.                     of the `table', but hash.c is broken. */
  171.   Lisp_Object name;             /* Just for debugging convenience */
  172. };
  173.  
  174. DECLARE_LRECORD (keymap, struct keymap);
  175. #define XKEYMAP(x) XRECORD (x, keymap, struct keymap)
  176. #define XSETKEYMAP(x, p) XSETRECORD (x, p, keymap)
  177. #define KEYMAPP(x) RECORDP (x, keymap)
  178. #define CHECK_KEYMAP(x, i) CHECK_RECORD (x, keymap)
  179.  
  180. /* Hash key is shifted so it can't conflict with eight-bit
  181.    string-char constituents */
  182. #define MAKE_MODIFIER_HASH_KEY(modifier) (make_number ((modifier) << 16))
  183. #define MODIFIER_HASH_KEY_P(x) ((INTP((x))) ? (XINT ((x)) >> 16) : 0)
  184.  
  185.  
  186.  
  187. /* Actually allocate storage for these variables */
  188.  
  189. static Lisp_Object Vcurrent_global_map; /* Always a keymap */
  190.  
  191. static Lisp_Object Vmouse_grabbed_buffer;
  192.  
  193. /* Alist of minor mode variables and keymaps.  */
  194. static Lisp_Object Qminor_mode_map_alist;
  195.  
  196. static Lisp_Object Voverriding_local_map;
  197.  
  198.  
  199. /* This is incremented whenever a change is made to a keymap.  This is
  200.    so that things which care (such as the menubar code) can recompute
  201.    privately-cached data when the user has changed keybindings.
  202.  */
  203. int keymap_tick;
  204.  
  205. /* Prefixing a key with this character is the same as sending a meta bit. */
  206. Lisp_Object Vmeta_prefix_char;
  207.  
  208. Lisp_Object Qkeymap;
  209. Lisp_Object Qkeymapp;
  210.  
  211. Lisp_Object Vsingle_space_string;
  212.  
  213. Lisp_Object Qsuppress_keymap;
  214.  
  215. Lisp_Object Qmodeline_map;
  216. Lisp_Object Qtoolbar_map;
  217.  
  218. static void describe_command (Lisp_Object definition);
  219. static void describe_map (Lisp_Object keymap, Lisp_Object elt_prefix,
  220.               void (*elt_describer) (Lisp_Object),
  221.               int partial, 
  222.               Lisp_Object shadow, 
  223.               int mice_only_p);
  224. Lisp_Object Qcontrol, Qctrl, Qmeta, Qsuper, Qhyper, Qalt, Qshift;
  225. /* Lisp_Object Qsymbol;    defined in general.c */
  226. Lisp_Object Qbutton0, Qbutton1, Qbutton2, Qbutton3, Qbutton4, Qbutton5,
  227.   Qbutton6, Qbutton7;
  228. Lisp_Object Qbutton0up, Qbutton1up, Qbutton2up, Qbutton3up, Qbutton4up,
  229.   Qbutton5up, Qbutton6up, Qbutton7up;
  230. Lisp_Object Qmenu_selection;
  231.  
  232. /* Kludge kludge kludge */
  233. Lisp_Object QLFD, QTAB, QRET, QESC, QDEL, QSPC, QBS;
  234.  
  235.  
  236. /************************************************************************/
  237. /*                     The keymap Lisp object                           */
  238. /************************************************************************/
  239.  
  240. static Lisp_Object mark_keymap (Lisp_Object, void (*) (Lisp_Object));
  241. static void print_keymap (Lisp_Object, Lisp_Object, int);
  242. /* No need for keymap_equal #### Why not? */
  243. DEFINE_LRECORD_IMPLEMENTATION ("keymap", keymap,
  244.                                mark_keymap, print_keymap, 0, 0, 0,
  245.                    struct keymap);
  246. static Lisp_Object
  247. mark_keymap (Lisp_Object obj, void (*markobj) (Lisp_Object))
  248. {
  249.   struct keymap *keymap = XKEYMAP (obj);
  250.   ((markobj) (keymap->parents));
  251.   ((markobj) (keymap->prompt));
  252.   ((markobj) (keymap->inverse_table));
  253.   ((markobj) (keymap->sub_maps_cache));
  254.   ((markobj) (keymap->default_binding));
  255.   ((markobj) (keymap->name));
  256.   return (keymap->table);
  257. }
  258.   
  259. static void
  260. print_keymap (Lisp_Object obj, Lisp_Object printcharfun, int escapeflag)
  261. {
  262.   /* This function can GC */
  263.   struct keymap *keymap = XKEYMAP (obj);
  264.   char buf[200];
  265.   int size = XINT (Fkeymap_fullness (obj));
  266.   if (print_readably)
  267.     error ("printing unreadable object #<keymap 0x%x>", keymap->header.uid);
  268.   write_c_string ("#<keymap ", printcharfun);
  269.   if (!NILP (keymap->name))
  270.     print_internal (keymap->name, printcharfun, 1);
  271.   sprintf (buf, "%s%d entr%s 0x%x>",
  272.            ((NILP (keymap->name)) ? "" : " "),
  273.            size,
  274.            ((size == 1) ? "y" : "ies"),
  275.            keymap->header.uid);
  276.   write_c_string (buf, printcharfun);
  277. }
  278.  
  279.  
  280. /************************************************************************/
  281. /*                Traversing keymaps and their parents                  */
  282. /************************************************************************/
  283.  
  284. static Lisp_Object
  285. traverse_keymaps (Lisp_Object start_keymap, Lisp_Object start_parents,
  286.                   Lisp_Object (*mapper) (Lisp_Object keymap, void *mapper_arg),
  287.                   void *mapper_arg)
  288. {
  289.   /* This function can GC */
  290.   Lisp_Object keymap;
  291.   Lisp_Object tail = start_parents;
  292.   Lisp_Object malloc_sucks[10];
  293.   Lisp_Object malloc_bites = Qnil;
  294.   int stack_depth = 0;
  295.   struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
  296.   GCPRO4 (*malloc_sucks, malloc_bites, start_keymap, tail);
  297.   gcpro1.nvars = 0;
  298.  
  299.   start_keymap = get_keymap (start_keymap, 1, 1);
  300.   keymap = start_keymap;
  301.   /* Hack special-case parents at top-level */
  302.   tail = ((!NILP (tail)) ? tail : XKEYMAP (keymap)->parents);
  303.  
  304.   for (;;)
  305.     {
  306.       Lisp_Object result;
  307.  
  308.       QUIT;
  309.       result = ((mapper) (keymap, mapper_arg));
  310.       if (!NILP (result))
  311.     {
  312.       while (CONSP (malloc_bites))
  313.         {
  314.           struct Lisp_Cons *victim = XCONS (malloc_bites);
  315.           malloc_bites = victim->cdr;
  316.           free_cons (victim);
  317.         }
  318.       UNGCPRO;
  319.       return (result);
  320.     }
  321.       if (NILP (tail))
  322.     {
  323.       if (stack_depth == 0)
  324.         {
  325.           UNGCPRO;
  326.           return (Qnil);          /* Nothing found */
  327.         }
  328.       stack_depth--;
  329.       if (CONSP (malloc_bites))
  330.         {
  331.           struct Lisp_Cons *victim = XCONS (malloc_bites);
  332.           tail = victim->car;
  333.           malloc_bites = victim->cdr;
  334.           free_cons (victim);
  335.         }
  336.       else
  337.         {
  338.           tail = malloc_sucks[stack_depth];
  339.           gcpro1.nvars = stack_depth;
  340.         }
  341.       keymap = XCAR (tail);
  342.       tail = XCDR (tail);
  343.     }
  344.       else
  345.     {
  346.       Lisp_Object parents;
  347.  
  348.       keymap = XCAR (tail);
  349.       tail = XCDR (tail);
  350.       parents = XKEYMAP (keymap)->parents;
  351.       if (!CONSP (parents))
  352.         ;
  353.       else if (NILP (tail))
  354.         /* Tail-recurse */
  355.         tail = parents;
  356.       else
  357.         {
  358.           if (CONSP (malloc_bites))
  359.         malloc_bites = Fcons (tail, malloc_bites);
  360.           else if (stack_depth < countof (malloc_sucks))
  361.         {
  362.           malloc_sucks[stack_depth++] = tail;
  363.           gcpro1.nvars = stack_depth;
  364.         }
  365.           else
  366.         {
  367.           /* *&@##[*&^$ C. @#[$*&@# Unix.  Losers all. */
  368.           int i;
  369.           for (i = 0, malloc_bites = Qnil;
  370.                i < countof (malloc_sucks);
  371.                i++)
  372.             malloc_bites = Fcons (malloc_sucks[i], malloc_bites);
  373.           gcpro1.nvars = 0;
  374.         }
  375.           tail = parents;
  376.         }
  377.     }
  378.       keymap = get_keymap (keymap, 1, 1);
  379.       if (EQ (keymap, start_keymap))
  380.     {
  381.       signal_simple_error ("Cyclic keymap indirection",
  382.                    start_keymap);
  383.     }
  384.     }
  385. }
  386.  
  387.  
  388. /************************************************************************/
  389. /*                     Some low-level functions                         */
  390. /************************************************************************/
  391.  
  392. static unsigned int
  393. bucky_sym_to_bucky_bit (Lisp_Object sym)
  394. {
  395.   if (EQ (sym, Qcontrol))
  396.     return MOD_CONTROL;
  397.   else if (EQ (sym, Qmeta))
  398.     return MOD_META;
  399.   else if (EQ (sym, Qsuper))
  400.     return MOD_SUPER;
  401.   else if (EQ (sym, Qhyper))
  402.     return MOD_HYPER;
  403.   else if (EQ (sym, Qalt) || EQ (sym, Qsymbol))    /* #### - reverse compat */
  404.     return MOD_ALT;
  405.   else if (EQ (sym, Qshift))
  406.     return MOD_SHIFT;
  407.   else
  408.     return 0;
  409. }
  410.  
  411. static Lisp_Object
  412. control_meta_superify (Lisp_Object frob, unsigned int modifiers)
  413. {
  414.   if (modifiers == 0)
  415.     return frob;
  416.   frob = Fcons (frob, Qnil);
  417.   if (modifiers & MOD_SHIFT)
  418.     frob = Fcons (Qshift, frob);
  419.   if (modifiers & MOD_ALT)
  420.     frob = Fcons (Qalt, frob);
  421.   if (modifiers & MOD_HYPER)
  422.     frob = Fcons (Qhyper, frob);
  423.   if (modifiers & MOD_SUPER)
  424.     frob = Fcons (Qsuper, frob);
  425.   if (modifiers & MOD_CONTROL)
  426.     frob = Fcons (Qcontrol, frob);
  427.   if (modifiers & MOD_META)
  428.     frob = Fcons (Qmeta, frob);
  429.   return (frob);
  430. }
  431.  
  432. static Lisp_Object
  433. make_key_description (CONST struct key_data *key, int prettify)
  434. {
  435.   Lisp_Object keysym = key->keysym;
  436.   unsigned int modifiers = key->modifiers;
  437.  
  438.   if (prettify && INTP (keysym))
  439.     {
  440.       /* This is a little slow, but (control a) is prettier than (control 65).
  441.      It's now ok to do this for digit-chars too, since we've fixed the
  442.      bug where \9 read as the integer 9 instead of as the symbol with
  443.      "9" as its name.
  444.        */
  445.       /* !!#### I'm not sure how correct this is. */
  446.       Bufbyte str [1 + MAX_EMCHAR_LEN];
  447.       Bytecount count = emchar_to_charptr (XINT (keysym), str);
  448.       str[count] = 0;
  449.       keysym = intern ((char *) str);
  450.     }
  451.   return (control_meta_superify (keysym, modifiers));
  452. }
  453.  
  454.  
  455. /************************************************************************/
  456. /*                   Low-level keymap-store functions                   */
  457. /************************************************************************/
  458.  
  459. static Lisp_Object
  460. raw_lookup_key (Lisp_Object keymap,
  461.                 CONST struct key_data *raw_keys, int raw_keys_count,
  462.                 int keys_so_far, int accept_default);
  463.  
  464. /* Relies on caller to gc-protect args */
  465. static Lisp_Object
  466. keymap_lookup_directly (Lisp_Object keymap,
  467.                         Lisp_Object keysym, unsigned int modifiers)
  468. {
  469.   struct keymap *k;
  470.  
  471.   if ((modifiers & ~(MOD_CONTROL | MOD_META | MOD_SUPER | MOD_HYPER
  472.                      | MOD_ALT | MOD_SHIFT)) != 0)
  473.     abort ();
  474.  
  475.   k = XKEYMAP (keymap);
  476.  
  477.   /* If the keysym is a one-character symbol, use the char code instead. */
  478.   if (SYMBOLP (keysym) && string_length (XSYMBOL (keysym)->name) == 1)
  479.     keysym = make_number (string_char (XSYMBOL (keysym)->name, 0));
  480.  
  481.   if (modifiers & MOD_META)     /* Utterly hateful ESC lossage */
  482.   {
  483.     Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META),
  484.                                    k->table, Qnil);
  485.     if (NILP (submap))
  486.       return (Qnil);
  487.     k = XKEYMAP (submap);
  488.     modifiers &= ~MOD_META;
  489.   }
  490.  
  491.   if (modifiers != 0)
  492.   {
  493.     Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (modifiers),
  494.                                    k->table, Qnil);
  495.     if (NILP (submap))
  496.       return (Qnil);
  497.     k = XKEYMAP (submap);
  498.   }
  499.   return (Fgethash (keysym, k->table, Qnil));
  500. }
  501.  
  502. static void
  503. keymap_store_inverse_internal (Lisp_Object inverse_table,
  504.                                Lisp_Object keysym,
  505.                                Lisp_Object value)
  506. {
  507.   Lisp_Object keys = Fgethash (value, inverse_table, Qunbound);
  508.  
  509.   if (EQ (keys, Qunbound))
  510.     {
  511.       keys = keysym;
  512.       /* Don't cons this unless necessary */
  513.       /* keys = Fcons (keysym, Qnil); */
  514.       Fputhash (value, keys, inverse_table);
  515.     }
  516.  
  517.   else if (!CONSP (keys))
  518.     {
  519.       /* Now it's necessary to cons */
  520.       keys = Fcons (keys, keysym);
  521.       Fputhash (value, keys, inverse_table);
  522.     }
  523.   else
  524.     {
  525.       while (CONSP (Fcdr (keys)))
  526.     keys = XCDR (keys);
  527.       XCDR (keys) = Fcons (XCDR (keys), keysym);
  528.       /* No need to call puthash because we've destructively
  529.          modified the list tail in place */
  530.     }
  531. }
  532.  
  533.  
  534. static void
  535. keymap_delete_inverse_internal (Lisp_Object inverse_table,
  536.                                 Lisp_Object keysym, 
  537.                                 Lisp_Object value)
  538. {
  539.   Lisp_Object keys = Fgethash (value, inverse_table, Qunbound);
  540.   Lisp_Object new_keys = keys;
  541.   Lisp_Object tail;
  542.   Lisp_Object *prev;
  543.  
  544.   if (EQ (keys, Qunbound))
  545.     abort ();
  546.  
  547.   for (prev = &new_keys, tail = new_keys;
  548.        ;
  549.        prev = &(XCDR (tail)), tail = XCDR (tail))
  550.     {
  551.       if (EQ (tail, keysym))
  552.     {
  553.       *prev = Qnil;
  554.       break;
  555.     }
  556.       else if (EQ (keysym, XCAR (tail)))
  557.     {
  558.       *prev = XCDR (tail);
  559.       break;
  560.     }
  561.     }
  562.  
  563.   if (NILP (new_keys))
  564.     Fremhash (value, inverse_table);
  565.   else if (!EQ (keys, new_keys))
  566.     /* Removed the first elt */
  567.     Fputhash (value, new_keys, inverse_table);
  568.   /* else the list's tail has been modified, so we don't need to
  569.      touch the hash table again (the pointer in there is ok).
  570.    */
  571. }
  572.  
  573.  
  574. static void
  575. keymap_store_internal (Lisp_Object keysym, struct keymap *keymap,
  576.                Lisp_Object value)
  577. {
  578.   Lisp_Object prev_value = Fgethash (keysym, keymap->table, Qnil);
  579.  
  580.   if (EQ (prev_value, value))
  581.       return;
  582.   if (!NILP (prev_value))
  583.     keymap_delete_inverse_internal (keymap->inverse_table, 
  584.                                     keysym, prev_value);
  585.   if (NILP (value))
  586.     {
  587.       keymap->fullness--;
  588.       if (keymap->fullness < 0) abort ();
  589.       Fremhash (keysym, keymap->table);
  590.     }
  591.   else
  592.     {
  593.       if (NILP (prev_value))
  594.     keymap->fullness++;
  595.       Fputhash (keysym, value, keymap->table);
  596.       keymap_store_inverse_internal (keymap->inverse_table, 
  597.                                      keysym, value);
  598.     }
  599.   keymap_tick++;
  600. }
  601.  
  602.  
  603. static Lisp_Object
  604. create_bucky_submap (struct keymap *k, unsigned int modifiers,
  605.                      Lisp_Object parent_for_debugging_info)
  606. {
  607.   Lisp_Object submap = Fmake_sparse_keymap ();
  608.   /* User won't see this, but it is nice for debugging Emacs */
  609.   XKEYMAP (submap)->name
  610.     = control_meta_superify (parent_for_debugging_info, modifiers);
  611.   /* Invalidate cache */
  612.   k->sub_maps_cache = Qt;
  613.   keymap_store_internal (MAKE_MODIFIER_HASH_KEY (modifiers), k, submap);
  614.   return (submap);
  615. }
  616.  
  617.  
  618. /* Relies on caller to gc-protect keymap, keysym, value */
  619. static void
  620. keymap_store (Lisp_Object keymap, CONST struct key_data *key,
  621.               Lisp_Object value)
  622. {
  623.   Lisp_Object keysym = key->keysym;
  624.   unsigned int modifiers = key->modifiers;
  625.   struct keymap *k;
  626.  
  627.   if ((modifiers & ~(MOD_CONTROL | MOD_META | MOD_SUPER | MOD_HYPER
  628.                      | MOD_ALT | MOD_SHIFT)) != 0)
  629.     abort ();
  630.  
  631.   k = XKEYMAP (keymap);
  632.  
  633.   /* If the keysym is a one-character symbol, use the char code instead. */
  634.   if (SYMBOLP (keysym) && string_length (XSYMBOL (keysym)->name) == 1)
  635.     keysym = make_number (string_char (XSYMBOL (keysym)->name, 0));
  636.  
  637.   if (modifiers & MOD_META)     /* Utterly hateful ESC lossage */
  638.     {
  639.       Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META),
  640.                      k->table, Qnil);
  641.       if (NILP (submap))
  642.     submap = create_bucky_submap (k, MOD_META, keymap);
  643.       k = XKEYMAP (submap);
  644.       modifiers &= ~MOD_META;
  645.     }
  646.  
  647.   if (modifiers != 0)
  648.     {
  649.       Lisp_Object submap = Fgethash (MAKE_MODIFIER_HASH_KEY (modifiers),
  650.                      k->table, Qnil);
  651.       if (NILP (submap))
  652.     submap = create_bucky_submap (k, modifiers, keymap);
  653.       k = XKEYMAP (submap);
  654.     }
  655.   k->sub_maps_cache = Qt; /* Invalidate cache */
  656.   keymap_store_internal (keysym, k, value);
  657. }
  658.  
  659.  
  660. /************************************************************************/
  661. /*                   Listing the submaps of a keymap                    */
  662. /************************************************************************/
  663.  
  664. struct keymap_submaps_closure
  665. {
  666.   Lisp_Object *result_locative;
  667. };
  668.  
  669. static void
  670. keymap_submaps_mapper_0 (CONST void *hash_key, void *hash_contents, 
  671.                          void *keymap_submaps_closure)
  672. {
  673.   /* This function can GC */
  674.   Lisp_Object contents;
  675.   VOID_TO_LISP (contents, hash_contents);
  676.   /* Perform any autoloads, etc */
  677.   (void) Fkeymapp (contents);
  678. }
  679.  
  680. static void
  681. keymap_submaps_mapper (CONST void *hash_key, void *hash_contents, 
  682.                        void *keymap_submaps_closure)
  683. {
  684.   /* This function can GC */
  685.   Lisp_Object key, contents;
  686.   Lisp_Object *result_locative;
  687.   struct keymap_submaps_closure *cl = keymap_submaps_closure;
  688.   CVOID_TO_LISP (key, hash_key);
  689.   VOID_TO_LISP (contents, hash_contents);
  690.   result_locative = cl->result_locative;
  691.  
  692.   if (!NILP (Fkeymapp (contents)))
  693.     *result_locative = Fcons (Fcons (key, contents), *result_locative);
  694. }
  695.  
  696. static int map_keymap_sort_predicate (Lisp_Object obj1, Lisp_Object obj2, 
  697.                                       Lisp_Object pred);
  698.  
  699. static Lisp_Object
  700. keymap_submaps (Lisp_Object keymap)
  701. {
  702.   /* This function can GC */
  703.   struct keymap *k = XKEYMAP (keymap);
  704.  
  705.   if (EQ (k->sub_maps_cache, Qt)) /* Unknown */
  706.     {
  707.       Lisp_Object result = Qnil;
  708.       struct gcpro gcpro1, gcpro2;
  709.       struct keymap_submaps_closure keymap_submaps_closure;
  710.  
  711.       GCPRO2 (keymap, result);
  712.       keymap_submaps_closure.result_locative = &result;
  713.       /* Do this first pass to touch (and load) any autoloaded maps */
  714.       elisp_maphash (keymap_submaps_mapper_0, k->table,
  715.              &keymap_submaps_closure);
  716.       result = Qnil;
  717.       elisp_maphash (keymap_submaps_mapper, k->table,
  718.              &keymap_submaps_closure);
  719.       /* keep it sorted so that the result of accessible-keymaps is ordered */
  720.       k->sub_maps_cache = list_sort (result, 
  721.                      Qnil,
  722.                      map_keymap_sort_predicate);
  723.       UNGCPRO;
  724.     }
  725.   return (k->sub_maps_cache);
  726. }
  727.  
  728.  
  729. /************************************************************************/
  730. /*                    Basic operations on keymaps                       */
  731. /************************************************************************/
  732.  
  733. static Lisp_Object
  734. make_keymap (int size)
  735. {
  736.   Lisp_Object result = Qnil;
  737.   struct keymap *keymap = alloc_lcrecord (sizeof (struct keymap), 
  738.                                           lrecord_keymap);
  739.  
  740.   XSETKEYMAP (result, keymap);
  741.  
  742.   keymap->parents = Qnil;
  743.   keymap->table = Qnil;
  744.   keymap->prompt = Qnil;
  745.   keymap->default_binding = Qnil;
  746.   keymap->inverse_table = Qnil;
  747.   keymap->sub_maps_cache = Qnil; /* No possible submaps */
  748.   keymap->fullness = 0;
  749.   if (size != 0) /* hack for copy-keymap */
  750.     {
  751.       keymap->table = Fmake_hashtable (make_number (size));
  752.       /* Inverse table is often less dense because of duplicate key-bindings.
  753.          If not, it will grow anyway. */
  754.       keymap->inverse_table = Fmake_hashtable (make_number (size * 3 / 4));
  755.     }
  756.   keymap->name = Qnil;
  757.   return (result);
  758. }
  759.  
  760. DEFUN ("make-keymap", Fmake_keymap, Smake_keymap, 0, 0, 0,
  761.   "Construct and return a new keymap object.\n\
  762. All entries in it are nil, meaning \"command undefined\".")
  763.   ()
  764. {
  765.   return make_keymap (60);
  766. }
  767.  
  768. DEFUN ("make-sparse-keymap", Fmake_sparse_keymap, Smake_sparse_keymap, 0, 0, 0,
  769.   "Construct and return a new keymap object.\n\
  770. All entries in it are nil, meaning \"command undefined\".  The only\n\
  771. difference between this function and make-keymap is that this function\n\
  772. returns a \"smaller\" keymap (one that is expected to contain fewer\n\
  773. entries).  As keymaps dynamically resize, the distinction is not great.")
  774.   ()
  775. {
  776.   return make_keymap (8);
  777. }
  778.  
  779. DEFUN ("keymap-parents", Fkeymap_parents, Skeymap_parents, 1, 1, 0,
  780.        "Return the `parent' keymaps of the given keymap, or nil.\n\
  781. The parents of a keymap are searched for keybindings when a key sequence\n\
  782. isn't bound in this one.  `(current-global-map)' is the default parent\n\
  783. of all keymaps.")
  784.      (keymap)
  785.      Lisp_Object keymap;
  786. {
  787.   keymap = get_keymap (keymap, 1, 1);
  788.   return (Fcopy_sequence (XKEYMAP (keymap)->parents));
  789. }
  790.  
  791.   
  792.   
  793. static Lisp_Object
  794. traverse_keymaps_noop (Lisp_Object keymap, void *arg)
  795. {
  796.   return (Qnil);
  797. }
  798.  
  799. DEFUN ("set-keymap-parents", Fset_keymap_parents, Sset_keymap_parents, 2, 2, 0,
  800.        "Sets the `parent' keymaps of the given keymap.\n\
  801. The parents of a keymap are searched for keybindings when a key sequence\n\
  802. isn't bound in this one.  `(current-global-map)' is the default parent\n\
  803. of all keymaps.")
  804.      (keymap, parents)
  805.      Lisp_Object keymap, parents;
  806. {
  807.   /* This function can GC */
  808.   Lisp_Object k;
  809.   struct gcpro gcpro1, gcpro2;
  810.  
  811.   GCPRO2 (keymap, parents);
  812.   keymap = get_keymap (keymap, 1, 1);
  813.  
  814.   if (KEYMAPP (parents))    /* backwards-compatibility */
  815.     parents = list1 (parents);
  816.   if (!NILP (parents))
  817.     {
  818.       Lisp_Object tail = parents;
  819.       while (!NILP (tail))
  820.     {
  821.       QUIT;
  822.       CHECK_CONS (tail, 0);
  823.       k = XCAR (tail);
  824.       /* Require that it be an actual keymap object, rather than a symbol
  825.          with a (crockish) symbol-function which is a keymap */
  826.       CHECK_KEYMAP (k, 1); /* get_keymap (k, 1, 1); */
  827.       tail = XCDR (tail);
  828.     }
  829.     }
  830.  
  831.   /* Check for circularities */
  832.   traverse_keymaps (keymap, parents, traverse_keymaps_noop, 0);
  833.   keymap_tick++;
  834.   XKEYMAP (keymap)->parents = Fcopy_sequence (parents);
  835.   UNGCPRO;
  836.   return (parents);
  837. }
  838.  
  839. DEFUN ("set-keymap-name", Fset_keymap_name, Sset_keymap_name, 2, 2, 0,
  840.   "Sets the `name' of the KEYMAP to NEW-NAME\n\
  841. The name is only a debugging convenience; it is not used except\n\
  842. when printing the keymap.")
  843.      (keymap, new_name)
  844.      Lisp_Object keymap, new_name;
  845. {
  846.   keymap = get_keymap (keymap, 1, 1);
  847.  
  848.   XKEYMAP (keymap)->name = new_name;
  849.   return (new_name);
  850. }
  851.  
  852. /*
  853.  * DEFUN ("keymap-name", Fkeymap_name, Skeymap_name, 1, 1, 0,
  854.  *   "Return the `name' of KEYMAP.\n\
  855.  * The name is only a debugging convenience; it is not used except\n\
  856.  * when printing the keymap.")
  857.  *      (keymap)
  858.  *      Lisp_Object keymap;
  859.  * {
  860.  *   keymap = get_keymap (keymap, 1, 1);
  861.  * 
  862.  *   return (XKEYMAP (keymap)->name);
  863.  * }
  864.  */
  865.  
  866. DEFUN ("set-keymap-prompt", Fset_keymap_prompt, Sset_keymap_prompt, 2, 2, 0,
  867.   "Sets the `prompt' of KEYMAP to string NEW-PROMPT, or `nil'\n\
  868. if no prompt is desired.  The prompt is shown in the echo-area\n\
  869. when reading a key-sequence to be looked-up in this keymap.")
  870.      (keymap, new_prompt)
  871.      Lisp_Object keymap, new_prompt;
  872. {
  873.   keymap = get_keymap (keymap, 1, 1);
  874.   
  875.   if (!NILP (new_prompt))
  876.     CHECK_STRING (new_prompt, 1);
  877.  
  878.   XKEYMAP (keymap)->prompt = new_prompt;
  879.   return (new_prompt);
  880. }
  881.  
  882. static Lisp_Object
  883. keymap_prompt_mapper (Lisp_Object keymap, void *arg)
  884. {
  885.   return (XKEYMAP (keymap)->prompt);
  886. }
  887.  
  888.  
  889. DEFUN ("keymap-prompt", Fkeymap_prompt, Skeymap_prompt, 1, 2, 0,
  890.   "Return the `prompt' of the given keymap.\n\
  891. If non-nil, the prompt is shown in the echo-area\n\
  892. when reading a key-sequence to be looked-up in this keymap.")
  893.      (keymap, use_inherited)
  894.      Lisp_Object keymap, use_inherited;
  895. {
  896.   /* This function can GC */
  897.   Lisp_Object prompt;
  898.  
  899.   keymap = get_keymap (keymap, 1, 1);
  900.   prompt = XKEYMAP (keymap)->prompt;
  901.   if (!NILP (prompt) || NILP (use_inherited))
  902.     return (prompt);
  903.   else
  904.     return (traverse_keymaps (keymap, Qnil,
  905.                   keymap_prompt_mapper, 0));
  906. }
  907.  
  908. DEFUN ("set-keymap-default-binding",
  909.        Fset_keymap_default_binding, Sset_keymap_default_binding, 2, 2, 0,
  910.   "Sets the default binding of KEYMAP to COMMAND, or `nil'\n\
  911. if no default is desired.  The default-binding is returned when\n\
  912. no other binding for a key-sequence is found in the keymap.\n\
  913. If a keymap has a non-nil default-binding, neither the keymap's\n\
  914. parents nor the current global map are searched for key bindings.")
  915.      (keymap, command)
  916.      Lisp_Object keymap, command;
  917. {
  918.   /* This function can GC */
  919.   keymap = get_keymap (keymap, 1, 1);
  920.   
  921.   XKEYMAP (keymap)->default_binding = command;
  922.   return (command);
  923. }
  924.  
  925. DEFUN ("keymap-default-binding",
  926.        Fkeymap_default_binding, Skeymap_default_binding, 1, 1, 0,
  927.   "Return the default binding of KEYMAP, or `nil' if it has none.\n\
  928. The default-binding is returned when no other binding for a key-sequence\n\
  929. is found in the keymap.\n\
  930. If a keymap has a non-nil default-binding, neither the keymap's\n\
  931. parents nor the current global map are searched for key bindings.")
  932.      (keymap)
  933.      Lisp_Object keymap;
  934. {
  935.   /* This function can GC */
  936.   keymap = get_keymap (keymap, 1, 1);
  937.   return (XKEYMAP (keymap)->default_binding);
  938. }
  939.  
  940. DEFUN ("keymapp", Fkeymapp, Skeymapp, 1, 1, 0,
  941.   "Return t if ARG is a keymap object.\n\
  942. The keymap may be autoloaded first if necessary.")
  943.   (object)
  944.      Lisp_Object object;
  945. {
  946.   /* This function can GC */
  947.   Lisp_Object tem = get_keymap (object, 0, 1);
  948.   return ((KEYMAPP (tem)) ? Qt : Qnil);
  949. }
  950.  
  951. /* Check that OBJECT is a keymap (after dereferencing through any
  952.    symbols).  If it is, return it.
  953.  
  954.    If AUTOLOAD is non-zero and OBJECT is a symbol whose function value
  955.    is an autoload form, do the autoload and try again.
  956.  
  957.    ERRORP controls how we respond if OBJECT isn't a keymap.
  958.    If ERRORP is non-zero, signal an error; otherwise, just return Qnil. 
  959.  */
  960. Lisp_Object
  961. get_keymap (Lisp_Object object, int errorp, int autoload)
  962. {
  963.   /* This function can GC */
  964.   while (1)
  965.     {
  966.       Lisp_Object tem = indirect_function (object, 0);
  967.       
  968.       if (KEYMAPP (tem))
  969.     return tem;
  970.       /* Should we do an autoload?  */
  971.       else if (autoload
  972.                /* (autoload "filename" doc nil keymap) */
  973.                && SYMBOLP (object)
  974.                && CONSP (tem)
  975.                && EQ (XCAR (tem), Qautoload)
  976.                && EQ (Fcar (Fcdr (Fcdr (Fcdr (Fcdr (tem))))), Qkeymap))
  977.     {
  978.       struct gcpro gcpro1, gcpro2;
  979.       GCPRO2 (tem, object);
  980.       do_autoload (tem, object);
  981.       UNGCPRO;
  982.     }
  983.       else if (errorp)
  984.     object = wrong_type_argument (Qkeymapp, object);
  985.       else
  986.     return Qnil;
  987.     }
  988. }
  989.  
  990. /* Given OBJECT which was found in a slot in a keymap,
  991.    trace indirect definitions to get the actual definition of that slot.
  992.    An indirect definition is a list of the form
  993.    (KEYMAP . INDEX), where KEYMAP is a keymap or a symbol defined as one
  994.    and INDEX is an ASCII code, or a cons of (KEYSYM . MODIFIERS).
  995.  */
  996. static Lisp_Object
  997. get_keyelt (Lisp_Object object, int accept_default)
  998. {
  999.   /* This function can GC */
  1000.   Lisp_Object map;
  1001.  
  1002.  tail_recurse:
  1003.   if (!CONSP (object))
  1004.     return (object);
  1005.  
  1006.   {
  1007.     struct gcpro gcpro1;
  1008.     GCPRO1 (object);
  1009.     map = XCAR (object);
  1010.     map = get_keymap (map, 0, 1);
  1011.     UNGCPRO;
  1012.   }
  1013.   /* If the contents are (KEYMAP . ELEMENT), go indirect.  */
  1014.   if (!NILP (map))
  1015.     {
  1016.       Lisp_Object idx = Fcdr (object);
  1017.       struct key_data indirection;
  1018.       if (INTP (idx))
  1019.     {
  1020.       struct Lisp_Event event;
  1021.       event.event_type = empty_event;
  1022.       character_to_event (XINT (idx), &event, 0);
  1023.       indirection = event.event.key;
  1024.     }
  1025.       else if (CONSP (idx))
  1026.     {
  1027.       if (!INTP (XCDR (idx)))
  1028.         return (Qnil);
  1029.       indirection.keysym = XCAR (idx);
  1030.       indirection.modifiers = XINT (XCDR (idx));
  1031.     }
  1032.       else if (SYMBOLP (idx))
  1033.     {
  1034.       indirection.keysym = idx;
  1035.       indirection.modifiers = 0;
  1036.     }
  1037.       else
  1038.     {
  1039.       /* Random junk */
  1040.       return (Qnil);
  1041.     }
  1042.       return (raw_lookup_key (map, &indirection, 1, 0,
  1043.                   accept_default));
  1044.     }
  1045.   else if (STRINGP (XCAR (object)))
  1046.     {
  1047.       /* If the keymap contents looks like (STRING . DEFN),
  1048.      use DEFN.
  1049.      Keymap alist elements like (CHAR MENUSTRING . DEFN)
  1050.      will be used by HierarKey menus.  */
  1051.       object = XCDR (object);
  1052.       goto tail_recurse;
  1053.     }
  1054.   else
  1055.     {
  1056.       /* Anything else is really the value.  */
  1057.       return (object);
  1058.     }
  1059. }
  1060.  
  1061. static Lisp_Object
  1062. keymap_lookup_1 (Lisp_Object keymap, CONST struct key_data *key,
  1063.                  int accept_default)
  1064. {
  1065.   /* This function can GC */
  1066.   return (get_keyelt (keymap_lookup_directly (keymap,
  1067.                                               key->keysym, key->modifiers),
  1068.                       accept_default));
  1069. }
  1070.  
  1071.  
  1072. /************************************************************************/
  1073. /*                          Copying keymaps                             */
  1074. /************************************************************************/
  1075.  
  1076. struct copy_keymap_inverse_closure
  1077. {
  1078.   Lisp_Object inverse_table;
  1079. };
  1080.  
  1081. static void
  1082. copy_keymap_inverse_mapper (CONST void *hash_key, void *hash_contents, 
  1083.                             void *copy_keymap_inverse_closure)
  1084. {
  1085.   Lisp_Object key, inverse_table, inverse_contents;
  1086.   struct copy_keymap_inverse_closure *closure = copy_keymap_inverse_closure;
  1087.  
  1088.   VOID_TO_LISP (inverse_table, closure);
  1089.   VOID_TO_LISP (inverse_contents, hash_contents);
  1090.   CVOID_TO_LISP (key, hash_key);
  1091.   /* copy-sequence deals with dotted lists. */
  1092.   if (CONSP (inverse_contents))
  1093.     inverse_contents = Fcopy_sequence (inverse_contents);
  1094.   Fputhash (key, inverse_contents, closure->inverse_table);
  1095. }
  1096.  
  1097.  
  1098. static Lisp_Object
  1099. copy_keymap_internal (struct keymap *keymap)
  1100. {
  1101.   Lisp_Object nkm = make_keymap (0);
  1102.   struct keymap *new_keymap = XKEYMAP (nkm);
  1103.   struct copy_keymap_inverse_closure copy_keymap_inverse_closure;
  1104.   copy_keymap_inverse_closure.inverse_table = keymap->inverse_table;
  1105.  
  1106.   new_keymap->parents = Fcopy_sequence (keymap->parents);
  1107.   new_keymap->fullness = keymap->fullness;
  1108.   new_keymap->sub_maps_cache = Qnil; /* No submaps */
  1109.   new_keymap->table = Fcopy_hashtable (keymap->table);
  1110.   new_keymap->inverse_table = Fcopy_hashtable (keymap->inverse_table);
  1111.   /* After copying the inverse map, we need to copy the conses which
  1112.      are its values, lest they be shared by the copy, and mangled.
  1113.    */
  1114.   elisp_maphash (copy_keymap_inverse_mapper, keymap->inverse_table,
  1115.          ©_keymap_inverse_closure);
  1116.   return nkm;
  1117. }
  1118.  
  1119.  
  1120. static Lisp_Object copy_keymap (Lisp_Object keymap);
  1121.  
  1122. struct copy_keymap_closure
  1123. {
  1124.   struct keymap *self;
  1125. };
  1126.  
  1127. static void
  1128. copy_keymap_mapper (CONST void *hash_key, void *hash_contents, 
  1129.                     void *copy_keymap_closure)
  1130. {
  1131.   /* This function can GC */
  1132.   Lisp_Object key, contents;
  1133.   struct copy_keymap_closure *closure = copy_keymap_closure;
  1134.  
  1135.   CVOID_TO_LISP (key, hash_key);
  1136.   VOID_TO_LISP (contents, hash_contents);
  1137.   /* When we encounter a keymap which is indirected through a
  1138.      symbol, we need to copy the sub-map.  In v18, the form
  1139.        (lookup-key (copy-keymap global-map) "\C-x")
  1140.      returned a new keymap, not the symbol 'Control-X-prefix.
  1141.    */
  1142.   contents = get_keymap (contents,
  1143.              0, 1); /* #### autoload GC-safe here? */
  1144.   if (KEYMAPP (contents))
  1145.     keymap_store_internal (key, closure->self,
  1146.                copy_keymap (contents));
  1147. }
  1148.  
  1149. static Lisp_Object
  1150. copy_keymap (Lisp_Object keymap)
  1151. {
  1152.   /* This function can GC */
  1153.   struct copy_keymap_closure copy_keymap_closure;
  1154.  
  1155.   keymap = copy_keymap_internal (XKEYMAP (keymap));
  1156.   copy_keymap_closure.self = XKEYMAP (keymap);
  1157.   elisp_maphash (copy_keymap_mapper,
  1158.          XKEYMAP (keymap)->table,
  1159.          ©_keymap_closure);
  1160.   return keymap;
  1161. }
  1162.  
  1163. DEFUN ("copy-keymap", Fcopy_keymap, Scopy_keymap, 1, 1, 0,
  1164.   "Return a copy of the keymap KEYMAP.\n\
  1165. The copy starts out with the same definitions of KEYMAP,\n\
  1166. but changing either the copy or KEYMAP does not affect the other.\n\
  1167. Any key definitions that are subkeymaps are recursively copied.")
  1168.   (keymap)
  1169.      Lisp_Object keymap;
  1170. {
  1171.   /* This function can GC */
  1172.   keymap = get_keymap (keymap, 1, 1);
  1173.   return copy_keymap (keymap);
  1174. }
  1175.  
  1176.  
  1177. static int
  1178. keymap_fullness (Lisp_Object keymap)
  1179. {
  1180.   /* This function can GC */
  1181.   int fullness;
  1182.   Lisp_Object sub_maps;
  1183.   struct gcpro gcpro1, gcpro2;
  1184.  
  1185.   keymap = get_keymap (keymap, 1, 1);
  1186.   fullness = XKEYMAP (keymap)->fullness;
  1187.   sub_maps = keymap_submaps (keymap);
  1188.   GCPRO2 (keymap, sub_maps);
  1189.   for (; !NILP (sub_maps); sub_maps = XCDR (sub_maps))
  1190.     {
  1191.       if (MODIFIER_HASH_KEY_P (XCAR (XCAR (sub_maps))) != 0)
  1192.     {
  1193.       Lisp_Object sub_map = XCDR (XCAR (sub_maps));
  1194.       fullness--; /* don't count bucky maps */
  1195.       fullness += keymap_fullness (sub_map);
  1196.     }
  1197.     }
  1198.   UNGCPRO;
  1199.   return (fullness);
  1200. }
  1201.  
  1202. DEFUN ("keymap-fullness", Fkeymap_fullness, Skeymap_fullness, 1, 1, 0,
  1203.        "Return the number of bindings in the keymap.")
  1204.      (keymap)
  1205.   Lisp_Object keymap;
  1206. {
  1207.   /* This function can GC */
  1208.   return (make_number (keymap_fullness
  1209.                (get_keymap (keymap, 1, 1))));
  1210. }
  1211.  
  1212.  
  1213. /************************************************************************/
  1214. /*                        Defining keys in keymaps                      */
  1215. /************************************************************************/
  1216.  
  1217. static void
  1218. define_key_check_keysym (Lisp_Object spec,
  1219.                          Lisp_Object keysym, unsigned int modifiers)
  1220. {
  1221.   /* Now, check and massage the trailing keysym specifier. */
  1222.   if (SYMBOLP (keysym))
  1223.     {
  1224.       if (string_length (XSYMBOL (keysym)->name) == 1)
  1225.     {
  1226.       keysym = make_number (string_char (XSYMBOL (keysym)->name, 0));
  1227.       goto fixnum_keysym;
  1228.     }
  1229.     }
  1230.   else if (INTP (keysym))
  1231.     {
  1232.     fixnum_keysym:
  1233.       /* #### needs to be fixed for Mule */
  1234.       if (XINT (keysym) < ' ' || XINT (keysym) > 255)
  1235.     signal_simple_error ("keysym must be in the range 32 - 255",
  1236.                  keysym);
  1237.       /* #### This bites!  I want to be able to write (control shift a) */
  1238.       if (modifiers & MOD_SHIFT)
  1239.     signal_simple_error ("the `shift' modifier may not be applied to ASCII keysyms",
  1240.                  spec);
  1241.     }
  1242.   else
  1243.     {
  1244.       signal_simple_error ("unknown keysym specifier",
  1245.                keysym);
  1246.     }
  1247. }
  1248.  
  1249.  
  1250. /* Given any kind of key-specifier, return a keysym and modifier mask.
  1251.  */
  1252. static void
  1253. define_key_parser (Lisp_Object spec, struct key_data *returned_value)
  1254. {
  1255.   if (INTP (spec))
  1256.     {
  1257.       struct Lisp_Event event;
  1258.       event.event_type = empty_event;
  1259.       character_to_event (XINT (spec), &event, 0);
  1260.       returned_value->keysym = event.event.key.keysym;
  1261.       returned_value->modifiers = event.event.key.modifiers;
  1262.     }
  1263.   else if (EVENTP (spec))
  1264.     {
  1265.       switch (XEVENT (spec)->event_type)
  1266.     {
  1267.     case key_press_event:
  1268.           {
  1269.             returned_value->keysym = XEVENT (spec)->event.key.keysym;
  1270.             returned_value->modifiers = XEVENT (spec)->event.key.modifiers;
  1271.         break;
  1272.           }
  1273.     case button_press_event:
  1274.     case button_release_event:
  1275.       {
  1276.         int down = (XEVENT (spec)->event_type == button_press_event);
  1277.         switch (XEVENT (spec)->event.button.button)
  1278.           {
  1279.           case 1:
  1280.         returned_value->keysym = (down ? Qbutton1 : Qbutton1up); break;
  1281.           case 2:
  1282.         returned_value->keysym = (down ? Qbutton2 : Qbutton2up); break;
  1283.           case 3:
  1284.         returned_value->keysym = (down ? Qbutton3 : Qbutton3up); break;
  1285.           case 4:
  1286.         returned_value->keysym = (down ? Qbutton4 : Qbutton4up); break;
  1287.           case 5:
  1288.         returned_value->keysym = (down ? Qbutton5 : Qbutton5up); break;
  1289.           case 6:
  1290.         returned_value->keysym = (down ? Qbutton6 : Qbutton6up); break;
  1291.           case 7:
  1292.         returned_value->keysym = (down ? Qbutton7 : Qbutton7up); break;
  1293.           default:
  1294.         returned_value->keysym =(down ? Qbutton0 : Qbutton0up); break;
  1295.           }
  1296.         returned_value->modifiers = XEVENT (spec)->event.button.modifiers;
  1297.         break;
  1298.       }
  1299.     default:
  1300.       signal_error (Qwrong_type_argument,
  1301.             list2 (build_translated_string
  1302.                    ("unable to bind this type of event"),
  1303.                    spec));
  1304.     }
  1305.     }
  1306.   else if (SYMBOLP (spec))
  1307.     {
  1308.       /* Be nice, allow = to mean (=) */
  1309.       if (bucky_sym_to_bucky_bit (spec) != 0)
  1310.         signal_simple_error ("Key is a modifier name", spec);
  1311.       define_key_check_keysym (spec, spec, 0);
  1312.       returned_value->keysym = spec;
  1313.       returned_value->modifiers = 0;
  1314.     }
  1315.   else if (CONSP (spec))
  1316.     {
  1317.       unsigned int modifiers = 0;
  1318.       Lisp_Object keysym = Qnil;
  1319.       Lisp_Object rest = spec;
  1320.  
  1321.       /* First, parse out the leading modifier symbols. */
  1322.       while (CONSP (rest))
  1323.     {
  1324.       unsigned int modifier;
  1325.  
  1326.       keysym = XCAR (rest);
  1327.       modifier = bucky_sym_to_bucky_bit (keysym);
  1328.       modifiers |= modifier;
  1329.       if (!NILP (XCDR (rest)))
  1330.         {
  1331.           if (! modifier)
  1332.         signal_simple_error ("unknown modifier", keysym);
  1333.         }
  1334.       else
  1335.         {
  1336.           if (modifier)
  1337.         signal_simple_error ("nothing but modifiers here",
  1338.                      spec);
  1339.         }
  1340.       rest = XCDR (rest);
  1341.       QUIT;
  1342.     }
  1343.       if (!NILP (rest))
  1344.         signal_simple_error ("dotted list", spec);
  1345.  
  1346.       define_key_check_keysym (spec, keysym, modifiers);
  1347.       returned_value->keysym = keysym;
  1348.       returned_value->modifiers = modifiers;
  1349.     }
  1350.   else
  1351.     {
  1352.       signal_simple_error ("unknown key-sequence specifier",
  1353.                spec);
  1354.     }
  1355.  
  1356.   /* Convert single-character symbols into ints, since that's the
  1357.      way the events arrive from the keyboard... */
  1358.   if (SYMBOLP (returned_value->keysym) &&
  1359.       string_length (XSYMBOL (returned_value->keysym)->name) == 1)
  1360.     {
  1361.       returned_value->keysym =
  1362.     make_number (string_char (XSYMBOL (returned_value->keysym)->name, 0));
  1363.  
  1364.       /* Detect bogus (user-provided) keysyms like '\?C-a;
  1365.          We can't do that for '\?M-a because that interferes with
  1366.          legitimate 8-bit input. */
  1367.       if (XINT (returned_value->keysym) < ' ' ||
  1368.       XINT (returned_value->keysym) > 255)
  1369.     signal_simple_error ("keysym must be in the range 32 - 255",
  1370.                  returned_value->keysym);
  1371.     }
  1372.  
  1373.   if (SYMBOLP (returned_value->keysym))
  1374.     {
  1375.       char *name = (char *) string_data (XSYMBOL (returned_value->keysym)->name);
  1376.  
  1377.       /* FSFmacs uses symbols with the printed representation of keysyms in
  1378.      their names, like 'M-x, and we use the syntax '(meta x).  So, to avoid
  1379.      confusion, notice the M-x syntax and signal an error - because
  1380.      otherwise it would be interpreted as a regular keysym, and would even
  1381.      show up in the list-buffers output, causing confusion to the naive.
  1382.  
  1383.      We can get away with this because none of the X keysym names contain
  1384.      a hyphen (some contain underscore, however).
  1385.  
  1386.      It might be useful to reject keysyms which are not x-valid-keysym-
  1387.      name-p, but that would interfere with various tricks we do to
  1388.      sanitize the Sun keyboards, and would make it trickier to
  1389.      conditionalize a .emacs file for multiple X servers.
  1390.      */
  1391.       if (strchr (name, '-')
  1392. #if 1
  1393.           ||
  1394.       /* Ok, this is a bit more dubious - prevent people from doing things
  1395.          like (global-set-key 'RET 'something) because that will have the
  1396.          same problem as above.  (Gag!)  Maybe we should just silently
  1397.          accept these as aliases for the "real" names?
  1398.          */
  1399.       (string_length (XSYMBOL (returned_value->keysym)->name) < 4 &&
  1400.        (!strcmp (name, "LFD") ||
  1401.         !strcmp (name, "TAB") ||
  1402.         !strcmp (name, "RET") ||
  1403.         !strcmp (name, "ESC") ||
  1404.         !strcmp (name, "DEL") ||
  1405.         !strcmp (name, "SPC") ||
  1406.         !strcmp (name, "BS")))
  1407. #endif /* unused */
  1408.           )
  1409.     signal_simple_error ("invalid keysym (see doc of define-key)",
  1410.                  returned_value->keysym);
  1411.  
  1412.       /* #### Ok, this is a bit more dubious - make people not lose if they
  1413.      do things like (global-set-key 'RET 'something) because that would
  1414.      otherwise have the same problem as above.  (Gag!)  We silently
  1415.      accept these as aliases for the "real" names.
  1416.      */
  1417.       else if (EQ (returned_value->keysym, QLFD))
  1418.     returned_value->keysym = QKlinefeed;
  1419.       else if (EQ (returned_value->keysym, QTAB))
  1420.     returned_value->keysym = QKtab;
  1421.       else if (EQ (returned_value->keysym, QRET))
  1422.     returned_value->keysym = QKreturn;
  1423.       else if (EQ (returned_value->keysym, QESC))
  1424.     returned_value->keysym = QKescape;
  1425.       else if (EQ (returned_value->keysym, QDEL))
  1426.     returned_value->keysym = QKdelete;
  1427.       else if (EQ (returned_value->keysym, QBS))
  1428.     returned_value->keysym = QKbackspace;
  1429.     }
  1430. }
  1431.  
  1432. /* This piece of crap is used by macros.c */
  1433. void
  1434. key_desc_list_to_event (Lisp_Object list, Lisp_Object event,
  1435.                         int allow_menu_events)
  1436. {
  1437.   struct key_data raw_key;
  1438.  
  1439.   /* #### Temporary multi-device kludge. */
  1440.   if (NILP (EVENT_DEVICE (XEVENT (event))))
  1441.     EVENT_DEVICE (XEVENT (event)) = Fselected_device ();
  1442.  
  1443.   if (allow_menu_events &&
  1444.       CONSP (list) &&
  1445.       /* #### where the hell does this come from? */
  1446.       EQ (XCAR (list), Qmenu_selection))
  1447.     {
  1448.       Lisp_Object fn, arg;
  1449.       if (! NILP (Fcdr (Fcdr (list))))
  1450.     signal_simple_error ("invalid menu event desc", list);
  1451.       arg = Fcar (Fcdr (list));
  1452.       if (SYMBOLP (arg))
  1453.     fn = Qcall_interactively;
  1454.       else
  1455.     fn = Qeval;
  1456.       XEVENT (event)->channel = Qnil;
  1457.       XEVENT (event)->event_type = misc_user_event;
  1458.       XEVENT (event)->event.eval.function = fn;
  1459.       XEVENT (event)->event.eval.object = arg;
  1460.       return;
  1461.     }
  1462.  
  1463.   define_key_parser (list, &raw_key);
  1464.  
  1465.   if (EQ (raw_key.keysym, Qbutton0) || EQ (raw_key.keysym, Qbutton0up) ||
  1466.       EQ (raw_key.keysym, Qbutton1) || EQ (raw_key.keysym, Qbutton1up) ||
  1467.       EQ (raw_key.keysym, Qbutton2) || EQ (raw_key.keysym, Qbutton2up) ||
  1468.       EQ (raw_key.keysym, Qbutton3) || EQ (raw_key.keysym, Qbutton3up) ||
  1469.       EQ (raw_key.keysym, Qbutton4) || EQ (raw_key.keysym, Qbutton4up) ||
  1470.       EQ (raw_key.keysym, Qbutton5) || EQ (raw_key.keysym, Qbutton5up) ||
  1471.       EQ (raw_key.keysym, Qbutton6) || EQ (raw_key.keysym, Qbutton6up) ||
  1472.       EQ (raw_key.keysym, Qbutton7) || EQ (raw_key.keysym, Qbutton7up))
  1473.     error ("Mouse-clicks can't appear in saved keyboard macros.");
  1474.  
  1475.   XEVENT (event)->channel = Qnil;
  1476.   XEVENT (event)->event_type = key_press_event;
  1477.   XEVENT (event)->event.key.keysym = raw_key.keysym;
  1478.   XEVENT (event)->event.key.modifiers = raw_key.modifiers;
  1479. }
  1480.  
  1481.  
  1482. int
  1483. event_matches_key_specifier_p (struct Lisp_Event *event,
  1484.                    Lisp_Object key_specifier)
  1485. {
  1486.   Lisp_Object event2;
  1487.   int retval;
  1488.   struct gcpro gcpro1;
  1489.  
  1490.   if (event->event_type != key_press_event || NILP (key_specifier) ||
  1491.       (INTP (key_specifier) && XINT (key_specifier) < 0))
  1492.     return 0;
  1493.  
  1494.   /* if the specifier is an integer such as 27, then it should match
  1495.      both of the events 'escape' and 'control ['.  Calling
  1496.      Fcharacter_to_event() will only match 'escape'. */
  1497.   if (INTP (key_specifier))
  1498.     return XINT (key_specifier) == event_to_character (event, 0, 0, 0);
  1499.  
  1500.   /* Otherwise, we cannot call event_to_character() because we may
  1501.      be dealing with non-ASCII keystrokes.  In any case, if I ask
  1502.      for 'control [' then I should get exactly that, and not
  1503.      'escape'.
  1504.  
  1505.      However, we have to behave differently on TTY's, where 'control ['
  1506.      is silently converted into 'escape' by the keyboard driver.
  1507.      In this case, ASCII is the only thing we know about, so we have
  1508.      to compare the ASCII values. */
  1509.  
  1510.   GCPRO1 (event2);
  1511.   event2 = Fallocate_event ();
  1512.   Fcharacter_to_event (key_specifier, event2, Qnil);
  1513.   if (XEVENT (event2)->event_type != key_press_event)
  1514.     retval = 0;
  1515.   else if (DEVICE_IS_TTY (XDEVICE (EVENT_DEVICE (event))))
  1516.     {
  1517.       int ch1, ch2;
  1518.  
  1519.       ch1 = event_to_character (event, 0, 0, 0);
  1520.       ch2 = event_to_character (XEVENT (event2), 0, 0, 0);
  1521.       retval = (ch1 >= 0 && ch2 >= 0 && ch1 == ch2);
  1522.     }
  1523.   else if (EQ (event->event.key.keysym, XEVENT (event2)->event.key.keysym) &&
  1524.        event->event.key.modifiers == XEVENT (event2)->event.key.modifiers)
  1525.     retval = 1;
  1526.   else
  1527.     retval = 0;
  1528.   Fdeallocate_event (event2);
  1529.   UNGCPRO;
  1530.   return retval;
  1531. }
  1532.  
  1533. static int
  1534. meta_prefix_char_p (CONST struct key_data *key)
  1535. {
  1536.   struct Lisp_Event event;
  1537.  
  1538.   event.event_type = key_press_event;
  1539.   event.event.key.keysym = key->keysym;
  1540.   event.event.key.modifiers = key->modifiers;
  1541.   return event_matches_key_specifier_p (&event, Vmeta_prefix_char);
  1542. }
  1543.  
  1544. DEFUN ("event-matches-key-specifier-p",
  1545.        Fevent_matches_key_specifier_p,
  1546.        Sevent_matches_key_specifier_p,
  1547.        2, 2, 0,
  1548.   "Return non-nil if EVENT matches KEY-SPECIFIER.\n\
  1549. This can be useful, e.g., to determine if the user pressed `help-char' or\n\
  1550. `quit-char'.")
  1551.   (event, key_specifier)
  1552.      Lisp_Object event, key_specifier;
  1553. {
  1554.   CHECK_LIVE_EVENT (event, 0);
  1555.   return (event_matches_key_specifier_p (XEVENT (event), key_specifier)
  1556.       ? Qt : Qnil);
  1557. }
  1558.  
  1559. /* ASCII grunge.
  1560.    Given a keysym, return another keysym/modifier pair which could be 
  1561.    considered the same key in an ASCII world.  Backspace returns ^H, for 
  1562.    example.
  1563.  */
  1564. static void
  1565. define_key_alternate_name (struct key_data *key,
  1566.                            struct key_data *returned_value)
  1567. {
  1568.   Lisp_Object keysym = key->keysym;
  1569.   unsigned int modifiers = key->modifiers;
  1570.   unsigned int modifiers_sans_control = (modifiers & (~MOD_CONTROL));
  1571.   unsigned int modifiers_sans_meta = (modifiers & (~MOD_META));
  1572.   returned_value->keysym = Qnil; /* By default, no "alternate" key */
  1573.   returned_value->modifiers = 0;
  1574. #define MACROLET(k,m) do { returned_value->keysym = (k); \
  1575.                returned_value->modifiers = (m); \
  1576.                            return; } while (0)
  1577.   if (modifiers_sans_meta == MOD_CONTROL)
  1578.     {
  1579.       if EQ (keysym, QKspace)
  1580.         MACROLET (make_number ('@'), modifiers);
  1581.       else if (!INTP (keysym))
  1582.         return;
  1583.       else switch (XINT (keysym))
  1584.         {
  1585.         case '@':               /* c-@ => c-space */
  1586.           MACROLET (QKspace, modifiers);
  1587.         case 'h':               /* c-h => backspace */
  1588.           MACROLET (QKbackspace, modifiers_sans_control);
  1589.         case 'i':               /* c-i => tab */
  1590.           MACROLET (QKtab, modifiers_sans_control);
  1591.         case 'j':               /* c-j => linefeed */
  1592.           MACROLET (QKlinefeed, modifiers_sans_control);
  1593.         case 'm':               /* c-m => return */
  1594.           MACROLET (QKreturn, modifiers_sans_control);
  1595.         case '[':               /* c-[ => escape */
  1596.           MACROLET (QKescape, modifiers_sans_control);
  1597.         default:
  1598.           return;
  1599.     }
  1600.     }
  1601.   else if (modifiers_sans_meta != 0)
  1602.     return;
  1603.   else if (EQ (keysym, QKbackspace)) /* backspace => c-h */
  1604.     MACROLET (make_number ('h'), (modifiers | MOD_CONTROL));
  1605.   else if (EQ (keysym, QKtab))       /* tab => c-i */
  1606.     MACROLET (make_number ('i'), (modifiers | MOD_CONTROL));
  1607.   else if (EQ (keysym, QKlinefeed))  /* linefeed => c-j */
  1608.     MACROLET (make_number ('j'), (modifiers | MOD_CONTROL));
  1609.   else if (EQ (keysym, QKreturn))    /* return => c-m */
  1610.     MACROLET (make_number ('m'), (modifiers | MOD_CONTROL));
  1611.   else if (EQ (keysym, QKescape))    /* escape => c-[ */
  1612.     MACROLET (make_number ('['), (modifiers | MOD_CONTROL));
  1613.   else
  1614.     return;
  1615. #undef MACROLET
  1616. }
  1617.  
  1618.  
  1619. static void
  1620. ensure_meta_prefix_char_keymapp (Lisp_Object keys, int index,
  1621.                                  Lisp_Object keymap)
  1622. {
  1623.   /* This function can GC */
  1624.   char buf [255];
  1625.   Lisp_Object new_keys;
  1626.   int i;
  1627.   Lisp_Object mpc_binding;
  1628.   struct key_data meta_key;
  1629.  
  1630.   if (NILP (Vmeta_prefix_char) ||
  1631.       (INTP (Vmeta_prefix_char) && XINT (Vmeta_prefix_char) < 0))
  1632.     return;
  1633.  
  1634.   define_key_parser (Vmeta_prefix_char, &meta_key);
  1635.   mpc_binding = keymap_lookup_1 (keymap, &meta_key, 0);
  1636.   if (NILP (mpc_binding) || !NILP (Fkeymapp (mpc_binding)))
  1637.     return;
  1638.  
  1639.   if (index == 0)
  1640.     new_keys = keys;
  1641.   else if (STRINGP (keys))
  1642.     new_keys = Fsubstring (keys, Qzero, make_number (index));
  1643.   else if (VECTORP (keys))
  1644.     {
  1645.       new_keys = make_vector (index, Qnil);
  1646.       for (i = 0; i < index; i++)
  1647.     vector_data (XVECTOR (new_keys)) [i] =
  1648.       vector_data (XVECTOR (keys)) [i];
  1649.     }
  1650.   else
  1651.     abort ();
  1652.   if (EQ (keys, new_keys))
  1653.     sprintf (buf, GETTEXT ("can't bind %s: %s has a non-keymap binding"),
  1654.          (char *) string_data (XSTRING (Fkey_description (keys))),
  1655.          (char *) string_data (XSTRING
  1656.                    (Fsingle_key_description 
  1657.                     (Vmeta_prefix_char))));
  1658.   else
  1659.     sprintf (buf, GETTEXT ("can't bind %s: %s %s has a non-keymap binding"),
  1660.          (char *) string_data (XSTRING (Fkey_description (keys))),
  1661.          (char *) string_data (XSTRING (Fkey_description (new_keys))),
  1662.          (char *) string_data (XSTRING
  1663.                    (Fsingle_key_description
  1664.                     (Vmeta_prefix_char))));
  1665.   signal_simple_error (buf, mpc_binding);
  1666. }
  1667.  
  1668. DEFUN ("define-key", Fdefine_key, Sdefine_key, 3, 3, 0,
  1669.   "Define key sequence KEYS, in KEYMAP, as DEF.\n\
  1670. KEYMAP is a keymap object.\n\
  1671. KEYS is the sequence of keystrokes to bind, described below.\n\
  1672. DEF is anything that can be a key's definition:\n\
  1673.  nil (means key is undefined in this keymap);\n\
  1674.  a command (a Lisp function suitable for interactive calling);\n\
  1675.  a string or key sequence vector (treated as a keyboard macro);\n\
  1676.  a keymap (to define a prefix key);\n\
  1677.  a symbol; when the key is looked up, the symbol will stand for its\n\
  1678.     function definition, that should at that time be one of the above,\n\
  1679.     or another symbol whose function definition is used, and so on.\n\
  1680.  a cons (STRING . DEFN), meaning that DEFN is the definition\n\
  1681.     (DEFN should be a valid definition in its own right);\n\
  1682.  or a cons (KEYMAP . CHAR), meaning use definition of CHAR in map KEYMAP.\n\
  1683. \n\
  1684. Contrary to popular belief, the world is not ASCII.  When running under a\n\
  1685. window manager, Emacs can tell the difference between, for example, the\n\
  1686. keystrokes control-h, control-shift-h, and backspace.  You can, in fact,\n\
  1687. bind different commands to each of these.\n\
  1688. \n\
  1689. A `key sequence' is a set of keystrokes.  A `keystroke' is a keysym and some\n\
  1690. set of modifiers (such as control and meta).  A `keysym' is what is printed\n\
  1691. on the keys on your keyboard.\n\
  1692. \n\
  1693. A keysym may be represented by a symbol, or (if and only if it is equivalent\n\
  1694. to an ASCII character in the range 32 - 255) by its ASCII code.  The `A' key\n\
  1695. may be represented by the symbol `A' or by the number 65.  The `break' key\n\
  1696. may be represented only by the symbol `break'.\n\
  1697. \n\
  1698. A keystroke may be represented by a list: the last element of the list is\n\
  1699. the key (a symbol or number, as above) and the preceding elements are the\n\
  1700. symbolic names of modifier keys (control, meta, super, hyper, alt, and shift).\n\
  1701. Thus, the sequence control-b is represented by the forms `(control b)' \n\
  1702. and `(control 98)'.  A keystroke may also be represented by an event object,\n\
  1703. as returned by the `next-command-event' and `read-key-sequence' functions.\n\
  1704. \n\
  1705. Note that in this context, the keystroke `control-b' is *not* represented\n\
  1706. by the number 2 (the ASCII code for ^B).  See below.\n\
  1707. \n\
  1708. The `shift' modifier is somewhat of a special case.  You should not (and\n\
  1709. cannot) use `(meta shift a)' to mean `(meta A)', since for characters that\n\
  1710. have ASCII equivalents, the state of the shift key is implicit in the\n\
  1711. keysym (a vs. A).  You also cannot say `(shift =)' to mean `+', as that\n\
  1712. sort of thing varies from keyboard to keyboard.  The shift modifier is for\n\
  1713. use only with characters that do not have a second keysym on the same key,\n\
  1714. such as `backspace' and `tab'.\n\
  1715. \n\
  1716. A key sequence is a vector of keystrokes.  As a degenerate case, elements\n\
  1717. of this vector may also be keysyms if they have no modifiers.  That is,\n\
  1718. the `A' keystroke is represented by all of these forms:\n\
  1719.     A    65    (A)    (65)    [A]    [65]    [(A)]    [(65)]\n\
  1720. the `control-a' keystroke is represented by these forms:\n\
  1721.     (control A)    (control 65)    [(control A)]    [(control 65)]\n\
  1722. the key sequence `control-c control-a' is represented by these forms:\n\
  1723.     [(control c) (control a)]    [(control 99) (control 65)]\n\
  1724. \n\
  1725. Mouse button clicks work just like keypresses: (control button1) means\n\
  1726. pressing the left mouse button while holding down the control key.\n\
  1727. [(control c) (shift button3)] means control-c, hold shift, click right.\n\
  1728. \n\
  1729. Commands may be bound to the mouse-button up-stroke rather than the down-\n\
  1730. stroke as well.  `button1' means the down-stroke, and `button1up' means the\n\
  1731. up-stroke.  Different commands may be bound to the up and down strokes,\n\
  1732. though that is probably not what you want, so be careful.\n\
  1733. \n\
  1734. For backward compatibility, a key sequence may also be represented by a\n\
  1735. string.  In this case, it represents the key sequence(s) that would\n\
  1736. produce that sequence of ASCII characters in a purely ASCII world.  For\n\
  1737. example, a string containing the ASCII backspace character, \"\\^H\", would\n\
  1738. represent two key sequences: `(control h)' and `backspace'.  Binding a\n\
  1739. command to this will actually bind both of those key sequences.  Likewise\n\
  1740. for the following pairs:\n\
  1741. \n\
  1742.         control h    backspace\n\
  1743.         control i       tab\n\
  1744.         control m       return\n\
  1745.         control j       linefeed\n\
  1746.         control [       escape\n\
  1747.         control @    control space\n\
  1748. \n\
  1749. After binding a command to two key sequences with a form like\n\
  1750. \n\
  1751.     (define-key global-map \"\\^X\\^I\" \'command-1)\n\
  1752. \n\
  1753. it is possible to redefine only one of those sequences like so:\n\
  1754. \n\
  1755.     (define-key global-map [(control x) (control i)] \'command-2)\n\
  1756.     (define-key global-map [(control x) tab] \'command-3)\n\
  1757. \n\
  1758. Of course, all of this applies only when running under a window system.  If\n\
  1759. you're talking to emacs through an ASCII-only channel, you don't get any of\n\
  1760. these features.")
  1761.   (keymap, keys, def)
  1762.      Lisp_Object keymap;
  1763.      Lisp_Object keys;
  1764.      Lisp_Object def;
  1765. {
  1766.   /* This function can GC */
  1767.   int idx;
  1768.   int metized = 0;
  1769.   int size;
  1770.   int ascii_hack;
  1771.   struct gcpro gcpro1, gcpro2, gcpro3;
  1772.  
  1773.   if (VECTORP (keys))
  1774.     size = vector_length (XVECTOR (keys));
  1775.   else if (STRINGP (keys))
  1776.     size = string_length (XSTRING (keys));
  1777.   else if (INTP (keys) || SYMBOLP (keys) || CONSP (keys))
  1778.     {
  1779.       if (!CONSP (keys)) keys = list1 (keys);
  1780.       size = 1;
  1781.       keys = make_vector (1, keys); /* this is kinda sleazy. */
  1782.     }
  1783.   else
  1784.     {
  1785.       keys = wrong_type_argument (Qsequencep, keys);
  1786.       size = XINT (Flength (keys));
  1787.     }
  1788.   if (size == 0)
  1789.     return (Qnil);
  1790.  
  1791.   GCPRO3 (keymap, keys, def);
  1792.  
  1793.   /* ASCII grunge.
  1794.      When the user defines a key which, in a strictly ASCII world, would be
  1795.      produced by two different keys (^J and linefeed, or ^H and backspace,
  1796.      for example) then the binding will be made for both keysyms.
  1797.  
  1798.      This is done if the user binds a command to a string, as in
  1799.      (define-key map "\^H" 'something), but not when using one of the new
  1800.      syntaxes, like (define-key map '(control h) 'something).
  1801.      */
  1802.   ascii_hack = (STRINGP (keys));
  1803.  
  1804.   keymap = get_keymap (keymap, 1, 1);
  1805.  
  1806.   idx = 0;
  1807.   while (1)
  1808.     {
  1809.       Lisp_Object c;
  1810.       struct key_data raw_key1;
  1811.       struct key_data raw_key2;
  1812.  
  1813.       if (STRINGP (keys))
  1814.     c = make_number (string_char (XSTRING (keys), idx));
  1815.       else
  1816.     {
  1817.       c = vector_data (XVECTOR (keys)) [idx];
  1818.       if (INTP (c) &&
  1819.           (XINT (c) < ' ' || XINT (c) > 127))
  1820.         args_out_of_range_3 (c, make_number (32), make_number (127));
  1821.     }
  1822.  
  1823.       define_key_parser (c, &raw_key1);
  1824.  
  1825.       if (!metized && ascii_hack && meta_prefix_char_p (&raw_key1))
  1826.     {
  1827.       if (idx == (size - 1))
  1828.         {
  1829.           /* This is a hack to prevent a binding for the meta-prefix-char
  1830.          from being made in a map which already has a non-empty "meta"
  1831.          submap.  That is, we can't let both "escape" and "meta" have
  1832.          a binding in the same keymap.  This implies that the idiom
  1833.          (define-key my-map "\e" my-escape-map)
  1834.          (define-key my-escape-map "a" 'my-command)
  1835.          no longer works.  That's ok.  Instead the luser should do
  1836.          (define-key my-map "\ea" 'my-command)
  1837.          or, more correctly
  1838.          (define-key my-map "\M-a" 'my-command)
  1839.          and then perhaps
  1840.          (defvar my-escape-map (lookup-key my-map "\e"))
  1841.          if the luser really wants the map in a variable.
  1842.          */
  1843.           Lisp_Object mmap;
  1844.               struct gcpro gcpro1;
  1845.  
  1846.               GCPRO1 (c);
  1847.               mmap = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META),
  1848.                                XKEYMAP (keymap)->table, Qnil);
  1849.           if (!NILP (mmap)
  1850.           && keymap_fullness (mmap) != 0)
  1851.         {
  1852.                   Lisp_Object desc
  1853.                     = Fsingle_key_description (Vmeta_prefix_char);
  1854.           signal_simple_error_2
  1855.             ("Map contains meta-bindings, can't bind", desc, keymap);
  1856.         }
  1857.               UNGCPRO;
  1858.         }
  1859.       else
  1860.         {
  1861.           metized = 1;
  1862.           idx++;
  1863.           continue;
  1864.         }
  1865.     }
  1866.  
  1867.       if (ascii_hack)
  1868.     define_key_alternate_name (&raw_key1, &raw_key2);
  1869.       else
  1870.     {
  1871.       raw_key2.keysym = Qnil;
  1872.       raw_key2.modifiers = 0;
  1873.     }
  1874.       
  1875.       if (metized)
  1876.     {
  1877.       raw_key1.modifiers  |= MOD_META;
  1878.       raw_key2.modifiers |= MOD_META;
  1879.       metized = 0;
  1880.     }
  1881.  
  1882.       /* This crap is to make sure that someone doesn't bind something like
  1883.      "C-x M-a" while "C-x ESC" has a non-keymap binding. */
  1884.       if (raw_key1.modifiers & MOD_META)
  1885.     ensure_meta_prefix_char_keymapp (keys, idx, keymap);
  1886.  
  1887.       if (++idx == size)
  1888.     {
  1889.       keymap_store (keymap, &raw_key1, def);
  1890.       if (ascii_hack && !NILP (raw_key2.keysym))
  1891.         keymap_store (keymap, &raw_key2, def);
  1892.       UNGCPRO;
  1893.       return def;
  1894.     }
  1895.       
  1896.       {
  1897.         Lisp_Object cmd;
  1898.         struct gcpro gcpro1;
  1899.         GCPRO1 (c);
  1900.  
  1901.         cmd = keymap_lookup_1 (keymap, &raw_key1, 0);
  1902.     if (NILP (cmd))
  1903.       {
  1904.         cmd = Fmake_sparse_keymap ();
  1905.         XKEYMAP (cmd)->name /* for debugging */
  1906.           = list2 (make_key_description (&raw_key1, 1), keymap);
  1907.         keymap_store (keymap, &raw_key1, cmd);
  1908.       }
  1909.     if (NILP (Fkeymapp (cmd)))
  1910.           signal_simple_error_2 ("invalid prefix keys in sequence",
  1911.                  c, keys);
  1912.  
  1913.     if (ascii_hack && !NILP (raw_key2.keysym) &&
  1914.         NILP (keymap_lookup_1 (keymap, &raw_key2, 0)))
  1915.       keymap_store (keymap, &raw_key2, cmd);
  1916.  
  1917.     keymap = get_keymap (cmd, 1, 1);
  1918.         UNGCPRO;
  1919.       }
  1920.     }
  1921. }
  1922.  
  1923.  
  1924. /************************************************************************/
  1925. /*                      Looking up keys in keymaps                      */
  1926. /************************************************************************/
  1927.  
  1928. /* We need a very fast (i.e., non-consing) version of lookup-key in order 
  1929.    to make where-is-internal really fly.
  1930.  */
  1931.  
  1932. struct raw_lookup_key_mapper_closure
  1933.   {
  1934.     int remaining;
  1935.     CONST struct key_data *raw_keys;
  1936.     int raw_keys_count;
  1937.     int keys_so_far;
  1938.     int accept_default;
  1939.   };
  1940.  
  1941. static Lisp_Object raw_lookup_key_mapper (Lisp_Object k, void *);
  1942.  
  1943. /* Caller should gc-protect args (keymaps may autoload) */
  1944. static Lisp_Object
  1945. raw_lookup_key (Lisp_Object keymap,
  1946.                 CONST struct key_data *raw_keys, int raw_keys_count,
  1947.                 int keys_so_far, int accept_default)
  1948. {
  1949.   /* This function can GC */
  1950.   struct raw_lookup_key_mapper_closure c;
  1951.   c.remaining = raw_keys_count - 1;
  1952.   c.raw_keys = raw_keys;
  1953.   c.raw_keys_count = raw_keys_count;
  1954.   c.keys_so_far = keys_so_far;
  1955.   c.accept_default = accept_default;
  1956.  
  1957.   return (traverse_keymaps (keymap, Qnil, raw_lookup_key_mapper,
  1958.                 &c));
  1959. }
  1960.  
  1961. static Lisp_Object
  1962. raw_lookup_key_mapper (Lisp_Object k, void *arg)
  1963. {
  1964.   /* This function can GC */
  1965.   struct raw_lookup_key_mapper_closure *c = arg;
  1966.   int accept_default = c->accept_default;
  1967.   int remaining = c->remaining;
  1968.   int keys_so_far = c->keys_so_far;
  1969.   CONST struct key_data *raw_keys = c->raw_keys;
  1970.   Lisp_Object cmd;
  1971.       
  1972.   if (! meta_prefix_char_p (&(raw_keys[0])))
  1973.     {
  1974.       /* Normal case: every case except the meta-hack (see below). */
  1975.       cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default);
  1976.       
  1977.       if (remaining == 0)
  1978.     /* Return whatever we found if we're out of keys */
  1979.     ;
  1980.       else if (NILP (cmd))
  1981.     /* Found nothing (though perhaps parent map may have binding) */
  1982.     ;
  1983.       else if (NILP (Fkeymapp (cmd)))
  1984.     /* Didn't find a keymap, and we have more keys.
  1985.      * Return a fixnum to indicate that keys were too long.
  1986.      */
  1987.     cmd = make_number (keys_so_far + 1);
  1988.       else
  1989.     cmd = raw_lookup_key (cmd, raw_keys + 1, remaining, 
  1990.                   keys_so_far + 1, accept_default);
  1991.     }
  1992.   else
  1993.     {
  1994.       /* This is a hack so that looking up a key-sequence whose last
  1995.        * element is the meta-prefix-char will return the keymap that
  1996.        * the "meta" keys are stored in, if there is no binding for
  1997.        * the meta-prefix-char (and if this map has a "meta" submap).
  1998.        * If this map doesnt have a "meta" submap, then the
  1999.        * meta-prefix-char is looked up just like any other key.
  2000.        */
  2001.       if (remaining == 0)
  2002.     {
  2003.       /* First look for the prefix-char directly */
  2004.       cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default);
  2005.       if (NILP (cmd))
  2006.         {
  2007.           /* Do kludgy return of the meta-map */ 
  2008.           cmd = Fgethash (MAKE_MODIFIER_HASH_KEY (MOD_META),
  2009.                   XKEYMAP (k)->table, Qnil);
  2010.         }
  2011.     }
  2012.       else
  2013.     {
  2014.       /* Search for the prefix-char-prefixed sequence directly */
  2015.       cmd = keymap_lookup_1 (k, &(raw_keys[0]), accept_default);
  2016.       cmd = get_keymap (cmd, 0, 1);
  2017.       if (!NILP (cmd))
  2018.         cmd = raw_lookup_key (cmd, raw_keys + 1, remaining, 
  2019.                   keys_so_far + 1, accept_default);
  2020.       else if ((raw_keys[1].modifiers & MOD_META) == 0)
  2021.         {
  2022.           struct key_data metified;
  2023.           metified.keysym = raw_keys[1].keysym;
  2024.           metified.modifiers = raw_keys[1].modifiers | MOD_META;
  2025.  
  2026.           /* Search for meta-next-char sequence directly */
  2027.           cmd = keymap_lookup_1 (k, &metified, accept_default);
  2028.           if (remaining == 1)
  2029.         ;
  2030.           else
  2031.         {
  2032.           cmd = get_keymap (cmd, 0, 1);
  2033.           if (!NILP (cmd))
  2034.             cmd = raw_lookup_key (cmd, raw_keys + 2, remaining - 1,
  2035.                       keys_so_far + 2,
  2036.                       accept_default);
  2037.         }
  2038.         }
  2039.     }
  2040.     }
  2041.   if (accept_default && NILP (cmd))
  2042.     cmd = XKEYMAP (k)->default_binding;
  2043.   return (cmd);
  2044. }
  2045.  
  2046. /* Value is number if `keys' is too long; NIL if valid but has no definition.*/
  2047. /* Caller should gc-protect arguments */
  2048. static Lisp_Object
  2049. lookup_keys (Lisp_Object keymap, int nkeys, Lisp_Object *keys,
  2050.              int accept_default)
  2051. {
  2052.   /* This function can GC */
  2053.   struct key_data kkk[20];
  2054.   struct key_data *raw_keys;
  2055.   int i;
  2056.  
  2057.   if (nkeys == 0)
  2058.     return Qnil;
  2059.  
  2060.   if (nkeys > (countof (kkk)))
  2061.     raw_keys = kkk;
  2062.   else
  2063.     raw_keys = (struct key_data *) alloca (sizeof (struct key_data) * nkeys);
  2064.  
  2065.   for (i = 0; i < nkeys; i++)
  2066.     {
  2067.       define_key_parser (keys[i], &(raw_keys[i]));
  2068.     }
  2069.   return (raw_lookup_key (keymap, raw_keys, nkeys, 0,
  2070.               accept_default));
  2071. }
  2072.  
  2073. static Lisp_Object
  2074. lookup_events (Lisp_Object event_head, int nmaps, Lisp_Object keymaps[],
  2075.                int accept_default)
  2076. {
  2077.   /* This function can GC */
  2078.   struct key_data kkk[20];
  2079.  
  2080.   int nkeys;
  2081.   struct key_data *raw_keys;
  2082.   struct Lisp_Event *e;
  2083.   Lisp_Object tem = Qnil;
  2084.   struct gcpro gcpro1, gcpro2;
  2085.   int iii;
  2086.  
  2087.   CHECK_LIVE_EVENT (event_head, 0);
  2088.  
  2089.   for (e = XEVENT (event_head), nkeys = 0; e; e = event_next (e), nkeys++)
  2090.     ;
  2091.  
  2092.   if (nkeys < (countof (kkk)))
  2093.     raw_keys = kkk;
  2094.   else
  2095.     raw_keys = (struct key_data *) alloca (sizeof (struct key_data) * nkeys);
  2096.  
  2097.   for (e = XEVENT (event_head), nkeys = 0; e; e = event_next (e), nkeys++)
  2098.     {
  2099.       Lisp_Object c = Qnil;
  2100.       
  2101.       XSETEVENT (c, e);
  2102.       define_key_parser (c, &(raw_keys[nkeys]));
  2103.     }
  2104.   GCPRO2 (keymaps[0], event_head);
  2105.   gcpro1.nvars = nmaps;
  2106.   /* ####raw_keys[].keysym slots aren't gc-protected.  We rely (but shouldn't)
  2107.    * on somebody else somewhere (obarray) having a pointer to all keysyms. */
  2108.   for (iii = 0; iii < nmaps; iii++)
  2109.     {
  2110.       tem = raw_lookup_key (keymaps[iii], raw_keys, nkeys, 0,
  2111.                 accept_default);
  2112.       if (INTP (tem))
  2113.     {
  2114.       /* Too long in some local map means don't look at global map */
  2115.       tem = Qnil;
  2116.       break;
  2117.     }
  2118.       else if (!NILP (tem))
  2119.     break;
  2120.     }
  2121.   UNGCPRO;
  2122.   return (tem);
  2123. }
  2124.  
  2125. DEFUN ("lookup-key", Flookup_key, Slookup_key, 2, 3, 0,
  2126.   "In keymap KEYMAP, look up key-sequence KEYS.  Return the definition.\n\
  2127. Nil is returned if KEYS is unbound.  See documentation of `define-key'\n\
  2128. for valid key definitions and key-sequence specifications.\n\
  2129. A number is returned if KEYS is \"too long\"; that is, the leading\n\
  2130. characters fail to be a valid sequence of prefix characters in KEYMAP.\n\
  2131. The number is how many characters at the front of KEYS\n\
  2132. it takes to reach a non-prefix command.")
  2133.   (keymap, keys, accept_default)
  2134.      Lisp_Object keymap, keys, accept_default;
  2135. {
  2136.   /* This function can GC */
  2137.   if (VECTORP (keys))
  2138.     {
  2139.       return lookup_keys (keymap,
  2140.               vector_length (XVECTOR (keys)),
  2141.                           vector_data (XVECTOR (keys)),
  2142.                           !NILP (accept_default));
  2143.     }
  2144.   else if (SYMBOLP (keys) || INTP (keys) || CONSP (keys))
  2145.     {
  2146.       return lookup_keys (keymap, 1, &keys,
  2147.               !NILP (accept_default));
  2148.     }
  2149.   else if (!STRINGP (keys))
  2150.     {
  2151.       keys = wrong_type_argument (Qsequencep, keys);
  2152.       return Flookup_key (keymap, keys, accept_default);
  2153.     }
  2154.   else
  2155.     {
  2156.       int length = string_length (XSTRING (keys));
  2157.       int i;
  2158.       struct key_data *raw_keys
  2159.     = (struct key_data *) alloca (sizeof (struct key_data) * length);
  2160.       if (length == 0)
  2161.     return Qnil;
  2162.  
  2163.       for (i = 0; i < length; i++)
  2164.     {
  2165.           unsigned char n = (unsigned char) string_char (XSTRING (keys), i);
  2166.       define_key_parser (make_number (n), &(raw_keys[i]));
  2167.     }
  2168.       return (raw_lookup_key (keymap, raw_keys, length, 0,
  2169.                               !NILP (accept_default)));
  2170.     }
  2171. }
  2172.  
  2173. /* Given a key sequence, returns a list of keymaps to search for bindings.
  2174.    Does all manner of semi-hairy heuristics, like looking in the current
  2175.    buffer's map before looking in the global map and looking in the local
  2176.    map of the buffer in which the mouse was clicked in event0 is a click.
  2177.  
  2178.    It would be kind of nice if this were in Lisp so that this semi-hairy
  2179.    semi-heuristic command-lookup behaviour could be readily understood and
  2180.    customised.  However, this needs to be pretty fast, or performance of
  2181.    keyboard macros goes to shit; putting this in lisp slows macros down
  2182.    2-3x.  And they're already slower than v18 by 5-6x. 
  2183.  */
  2184.  
  2185. struct relevant_maps
  2186.   {
  2187.     int nmaps;
  2188.     unsigned int max_maps;
  2189.     Lisp_Object *maps;
  2190.     struct gcpro *gcpro;
  2191.   };
  2192.  
  2193. static void get_relevant_extent_keymaps (Lisp_Object pos,
  2194.                                          Lisp_Object buffer,
  2195.                                          Lisp_Object glyph,
  2196.                                          struct relevant_maps *closure);
  2197. static void get_relevant_minor_maps (Lisp_Object buffer,
  2198.                                      struct relevant_maps *closure);
  2199.  
  2200. static void
  2201. relevant_map_push (Lisp_Object map, struct relevant_maps *closure)
  2202.   unsigned int nmaps = closure->nmaps;
  2203.  
  2204.   if (!KEYMAPP (map))
  2205.     return;
  2206.   closure->nmaps = nmaps + 1;
  2207.   if (nmaps < closure->max_maps)
  2208.     {
  2209.       closure->maps[nmaps] = map;
  2210.       closure->gcpro->nvars = nmaps;
  2211.     }
  2212. }
  2213.  
  2214. static int
  2215. get_relevant_keymaps (Lisp_Object keys,
  2216.                       int max_maps, Lisp_Object maps[])
  2217. {
  2218.   /* This function can GC */
  2219.   Lisp_Object terminal = Qnil;
  2220.   struct gcpro gcpro1;
  2221.   struct relevant_maps closure;
  2222.  
  2223.   GCPRO1 (*maps);
  2224.   gcpro1.nvars = 0;
  2225.   closure.nmaps = 0;
  2226.   closure.max_maps = max_maps;
  2227.   closure.maps = maps;
  2228.   closure.gcpro = &gcpro1;
  2229.  
  2230.   if (EVENTP (keys))
  2231.     {
  2232.       struct Lisp_Event *e = XEVENT (keys);
  2233.       for (e = XEVENT (keys);
  2234.        event_next (e);
  2235.        e = event_next (e))
  2236.     ;
  2237.       XSETEVENT (terminal, e);
  2238.     }
  2239.   else if (VECTORP (keys))
  2240.     {
  2241.       int len = vector_length (XVECTOR (keys));
  2242.       if (len > 1)
  2243.     terminal = vector_data (XVECTOR (keys))[len - 1];
  2244.     }
  2245.   
  2246.   if (KEYMAPP (Voverriding_local_map))
  2247.     {
  2248.       relevant_map_push (Voverriding_local_map, &closure);
  2249.     }
  2250.   else if (!EVENTP (terminal)
  2251.            || (XEVENT (terminal)->event_type != button_press_event 
  2252.                && XEVENT (terminal)->event_type != button_release_event))
  2253.     {
  2254.       Lisp_Object tem;
  2255.       XSETBUFFER (tem, current_buffer);
  2256.       /* It's not a mouse event; order of keymaps searched is:
  2257.      o  keymap of any/all extents under the mouse
  2258.      o  minor-mode maps
  2259.      o  local-map of current-buffer
  2260.      o  global-map
  2261.      */
  2262.       /* The terminal element of the lookup may be nil or a keysym.
  2263.          In those cases we don't want to check for an extent
  2264.          keymap. */
  2265.       if (EVENTP (terminal))
  2266.     {
  2267.       get_relevant_extent_keymaps (make_number (BUF_PT (current_buffer)),
  2268.                        tem, Qnil, &closure);
  2269.     }
  2270.       get_relevant_minor_maps (tem, &closure);
  2271.  
  2272.       tem = current_buffer->keymap;
  2273.       if (!NILP (tem))
  2274.     relevant_map_push (tem, &closure);
  2275.     }
  2276. #ifdef HAVE_WINDOW_SYSTEM
  2277.   else
  2278.     {
  2279.       /* It's a mouse event; order of keymaps searched is:
  2280.      o  local-map of mouse-grabbed-buffer
  2281.      o  keymap of any/all extents under the mouse
  2282.      if the mouse is over a modeline:
  2283.      o  modeline-map of buffer corresponding to that modeline
  2284.      o  else, local-map of buffer under the mouse
  2285.      o  minor-mode maps
  2286.      o  local-map of current-buffer
  2287.      o  global-map
  2288.      */
  2289.       Lisp_Object window = Fevent_window (terminal);
  2290.  
  2291.       if (BUFFERP (Vmouse_grabbed_buffer))
  2292.     {
  2293.       Lisp_Object map = XBUFFER (Vmouse_grabbed_buffer)->keymap;
  2294.  
  2295.       get_relevant_minor_maps (Vmouse_grabbed_buffer, &closure);
  2296.       if (!NILP (map))
  2297.         relevant_map_push (map, &closure);
  2298.     }
  2299.  
  2300.       if (!NILP (window))
  2301.     {
  2302.       Lisp_Object buffer = Fwindow_buffer (window);
  2303.  
  2304.       if (!NILP (buffer))
  2305.         {
  2306.           if (!NILP (Fevent_over_modeline_p (terminal)))
  2307.         {
  2308.           Lisp_Object map = symbol_value_in_buffer (Qmodeline_map,
  2309.                                 buffer);
  2310.  
  2311.           if (!EQ (map, Qunbound) && !NILP (map))
  2312.             relevant_map_push (map, &closure);
  2313.         }
  2314.           else
  2315.         {
  2316.           /* if it was a modeline hit, then it can't have been over
  2317.              an extent with a keymap. */
  2318.           get_relevant_extent_keymaps (Fevent_point (terminal), buffer,
  2319.                            Fevent_glyph_extent (terminal),
  2320.                            &closure);
  2321.         }
  2322.  
  2323.           if (!EQ (buffer, Vmouse_grabbed_buffer)) /* already pushed */
  2324.         {
  2325.           get_relevant_minor_maps (buffer, &closure);
  2326.           relevant_map_push (XBUFFER (buffer)->keymap, &closure);
  2327.         }
  2328.         }
  2329.     }
  2330.       else if (!NILP (Fevent_over_toolbar_p (terminal)))
  2331.     {
  2332.       Lisp_Object map = Fsymbol_value (Qtoolbar_map);
  2333.  
  2334.       if (!EQ (map, Qunbound) && !NILP (map))
  2335.         relevant_map_push (map, &closure);
  2336.     }
  2337.     }
  2338. #endif /* HAVE_WINDOW_SYSTEM */
  2339.  
  2340.   {
  2341.     int nmaps = closure.nmaps;
  2342.     /* Silently truncate at 100 keymaps to prevent infinite losssage */
  2343.     if (nmaps >= max_maps && max_maps > 0)
  2344.       maps[max_maps - 1] = Vcurrent_global_map;
  2345.     else
  2346.       maps[nmaps] = Vcurrent_global_map;
  2347.     UNGCPRO;
  2348.     return (nmaps + 1);
  2349.   }
  2350. }
  2351.  
  2352. /* Returns a set of keymaps extracted from the extents at POS in BUFFER.
  2353.    The GLYPH arg, if specified, is one more extent to look for a keymap in,
  2354.    and if it has one, its keymap will be the first element in the list 
  2355.    returned.  This is so we can correctly search the keymaps associated
  2356.    with glyphs which may be physically disjoint from their extents: for
  2357.    example, if a glyph is out in the margin, we should still consult the
  2358.    kemyap of that glyph's extent, which may not itself be under the mouse.
  2359.  */
  2360. static void
  2361. get_relevant_extent_keymaps (Lisp_Object pos, Lisp_Object buffer,
  2362.                              Lisp_Object glyph,
  2363.                              struct relevant_maps *closure)
  2364. {
  2365.   /* This function can GC */
  2366.   /* the glyph keymap, if any, comes first.
  2367.      (Processing it twice is no big deal: noop.) */
  2368.   if (!NILP (glyph))
  2369.     {
  2370.       Lisp_Object keymap = Fextent_property (glyph, Qkeymap);
  2371.       if (!NILP (keymap))
  2372.     relevant_map_push (get_keymap (keymap, 1, 1), closure);
  2373.     }
  2374.   
  2375.   /* Next check the extents at the text position, if any */
  2376.   if (!NILP (pos))
  2377.     {
  2378.       Lisp_Object extent;
  2379.       for (extent = Fextent_at (pos, buffer, Qkeymap, Qnil);
  2380.        !NILP (extent);
  2381.        extent = Fextent_at (pos, buffer, Qkeymap, extent))
  2382.     {
  2383.       Lisp_Object keymap = Fextent_property (extent, Qkeymap);
  2384.       if (!NILP (keymap))
  2385.         relevant_map_push (get_keymap (keymap, 1, 1), closure);
  2386.       QUIT;
  2387.     }
  2388.     }
  2389. }
  2390.  
  2391. static Lisp_Object
  2392. minor_mode_keymap_predicate (Lisp_Object assoc, Lisp_Object buffer)
  2393. {
  2394.   /* This function can GC */
  2395.   if (CONSP (assoc))
  2396.     {
  2397.       Lisp_Object sym = XCAR (assoc);
  2398.       if (SYMBOLP (sym))
  2399.     {
  2400.       Lisp_Object val = symbol_value_in_buffer (sym, buffer);
  2401.       if (!EQ (val, Qnil) && !EQ (val, Qunbound))
  2402.         {
  2403.           Lisp_Object map = get_keymap (XCDR (assoc), 0, 1);
  2404.           return (map);
  2405.         }
  2406.     }
  2407.     }
  2408.   return (Qnil);
  2409. }
  2410.  
  2411. static void
  2412. get_relevant_minor_maps (Lisp_Object buffer, struct relevant_maps *closure)
  2413. {
  2414.   /* This function can GC */
  2415.   Lisp_Object alist;
  2416.  
  2417.   /* Will you ever lose badly if you make this circular! */
  2418.   for (alist = symbol_value_in_buffer (Qminor_mode_map_alist, buffer);
  2419.        CONSP (alist);
  2420.        alist = XCDR (alist))
  2421.     {
  2422.       Lisp_Object m = minor_mode_keymap_predicate (XCAR (alist),
  2423.                            buffer);
  2424.       if (!NILP (m)) relevant_map_push (m, closure);
  2425.       QUIT;
  2426.     }
  2427. }
  2428.  
  2429. /* #### Would map-current-keymaps be a better thing?? */
  2430. DEFUN ("current-keymaps", Fcurrent_keymaps, Scurrent_keymaps, 0, 1, 0,
  2431.   "Return a list of the current keymaps that will be searched for bindings.\n\
  2432. This lists keymaps such as the current local map and the minor-mode maps,\n\
  2433.  but does not list the parents of those keymaps.\n\
  2434. EVENT-OR-KEYS controls which keymaps will be listed.\n\
  2435. If EVENT-OR-KEYS is a mouse event (or a vector whose last element is a\n\
  2436.  mouse event), the keymaps for that mouse event will be listed (see\n\
  2437.  `key-binding').  Otherwise, the keymaps for key presses will be listed.")
  2438.   (event_or_keys)
  2439.      Lisp_Object event_or_keys;
  2440. {
  2441.   /* This function can GC */
  2442.   struct gcpro gcpro1;
  2443.   Lisp_Object maps[100];
  2444.   Lisp_Object *gubbish = maps;
  2445.   int nmaps;
  2446.  
  2447.   GCPRO1 (event_or_keys);
  2448.   nmaps = get_relevant_keymaps (event_or_keys, countof (maps),
  2449.                 gubbish);
  2450.   if (nmaps > countof (maps))
  2451.     {
  2452.       gubbish = (Lisp_Object *) alloca (nmaps * sizeof (Lisp_Object));
  2453.       nmaps = get_relevant_keymaps (event_or_keys, nmaps, gubbish);
  2454.     }
  2455.   UNGCPRO;
  2456.   return (Flist (nmaps, gubbish));
  2457. }
  2458.  
  2459. DEFUN ("key-binding", Fkey_binding, Skey_binding, 1, 2, 0,
  2460.   "Return the binding for command KEYS in current keymaps.\n\
  2461. KEYS is a string, a vector of events, or a vector of key-description lists\n\
  2462. as described in the documentation for the `define-key' function.\n\
  2463. The binding is probably a symbol with a function definition; see\n\
  2464. the documentation for `lookup-key' for more information.\n\
  2465. \n\
  2466. For key-presses, the order of keymaps searched is:\n\
  2467.   - the `keymap' property of any extent(s) at point;\n\
  2468.   - any applicable minor-mode maps;\n\
  2469.   - the current-local-map of the current-buffer;\n\
  2470.   - the current global map.\n\
  2471. \n\
  2472. For mouse-clicks, the order of keymaps searched is:\n\
  2473.   - the current-local-map of the `mouse-grabbed-buffer' if any;\n\
  2474.   - the `keymap' property of any extent(s) at the position of the click;\n\
  2475.   - the modeline-map of the buffer corresponding to the modeline under\n\
  2476.     the mouse (if the click happened over a modeline);\n\
  2477.   - the current-local-map of the buffer under the mouse;\n\
  2478.   - any applicable minor-mode maps;\n\
  2479.   - the current global map.\n\
  2480. \n\
  2481. Note that if `overriding-local-map' is non-nil, *only* it and the current\n\
  2482.  global map are searched.")
  2483.   (keys, accept_default)
  2484.     Lisp_Object keys, accept_default;
  2485. {
  2486.   /* This function can GC */
  2487.   int i;
  2488.   Lisp_Object maps[100];
  2489.   int nmaps;
  2490.   struct gcpro gcpro1, gcpro2;
  2491.   GCPRO2 (keys, accept_default); /* get_relevant_keymaps may autoload */
  2492.  
  2493.   nmaps = get_relevant_keymaps (keys, countof (maps), maps);
  2494.  
  2495.   UNGCPRO;
  2496.  
  2497.   if (EVENTP (keys))           /* unadvertised "feature" for the future */
  2498.     return (lookup_events (keys, nmaps, maps,
  2499.                !NILP (accept_default)));
  2500.  
  2501.   for (i = 0; i < nmaps; i++)
  2502.     {
  2503.       Lisp_Object tem = Flookup_key (maps[i], keys,
  2504.                      accept_default);
  2505.       if (INTP (tem))
  2506.     {
  2507.       /* Too long in some local map means don't look at global map */
  2508.       return (Qnil);
  2509.     }
  2510.       else if (!NILP (tem))
  2511.     return (tem);
  2512.     }
  2513.   return (Qnil);
  2514. }
  2515.  
  2516. /* Attempts to find a command corresponding to the event-sequence
  2517.    whose head is event0 (sequence is threaded though event_next).
  2518.    Returns either a command symbol or Qnil.
  2519.  */
  2520. Lisp_Object
  2521. event_binding (Lisp_Object event0, int accept_default)
  2522. {
  2523.   /* This function can GC */
  2524.   Lisp_Object maps[100];
  2525.   int nmaps;
  2526.  
  2527.   if (!EVENTP (event0)) abort ();
  2528.  
  2529.   nmaps = get_relevant_keymaps (event0, countof (maps), maps);
  2530.   return (lookup_events (event0, nmaps, maps, accept_default));
  2531. }
  2532.  
  2533. /* Attempts to find a function key mapping corresponding to the
  2534.    event-sequence whose head is event0 (sequence is threaded through
  2535.    event_next).  Returns either a command symbol or Qnil. */
  2536. Lisp_Object
  2537. function_key_map_event_binding (Lisp_Object event0)
  2538. {
  2539.   struct device *d = XDEVICE (EVENT_DEVICE (XEVENT (event0)));
  2540.   Lisp_Object maps[1];
  2541.  
  2542.   if (NILP (DEVICE_FUNCTION_KEY_MAP (d)))
  2543.     return Qnil;
  2544.  
  2545.   maps[0] = DEVICE_FUNCTION_KEY_MAP (d);
  2546.   return (lookup_events (event0, 1, maps, 1));
  2547. }
  2548.  
  2549.  
  2550. /************************************************************************/
  2551. /*               Setting/querying the global and local maps             */
  2552. /************************************************************************/
  2553.  
  2554. DEFUN ("use-global-map", Fuse_global_map, Suse_global_map, 1, 1, 0,
  2555.   "Select KEYMAP as the global keymap.")
  2556.   (keymap)
  2557.      Lisp_Object keymap;
  2558. {
  2559.   /* This function can GC */
  2560.   keymap = get_keymap (keymap, 1, 1);
  2561.   Vcurrent_global_map = keymap;
  2562.   return Qnil;
  2563. }
  2564.  
  2565. DEFUN ("use-local-map", Fuse_local_map, Suse_local_map, 1, 2, 0,
  2566.   "Select KEYMAP as the local keymap in BUFFER.\n\
  2567. If KEYMAP is nil, that means no local keymap.\n\
  2568. If BUFFER is nil, the current buffer is assumed.")
  2569.   (keymap, buffer)
  2570.      Lisp_Object keymap, buffer;
  2571. {
  2572.   /* This function can GC */
  2573.   struct buffer *b = decode_buffer (buffer, 0);
  2574.   if (!NILP (keymap))
  2575.     keymap = get_keymap (keymap, 1, 1);
  2576.  
  2577.   b->keymap = keymap;
  2578.  
  2579.   return Qnil;
  2580. }
  2581.  
  2582. DEFUN ("current-local-map", Fcurrent_local_map, Scurrent_local_map, 0, 1, 0,
  2583.   "Return BUFFER's local keymap, or nil if it has none.\n\
  2584. If BUFFER is nil, the current buffer is assumed.")
  2585.   (buffer)
  2586.   Lisp_Object buffer;
  2587. {
  2588.   struct buffer *b = decode_buffer (buffer, 0);
  2589.   return b->keymap;
  2590. }
  2591.  
  2592. DEFUN ("current-global-map", Fcurrent_global_map, Scurrent_global_map, 0, 0, 0,
  2593.   "Return the current global keymap.")
  2594.   ()
  2595. {
  2596.   return (Vcurrent_global_map);
  2597. }
  2598.  
  2599.  
  2600. /************************************************************************/
  2601. /*                    Mapping over keymap elements                      */
  2602. /************************************************************************/
  2603.  
  2604. /* Since keymaps are arranged in a hierarchy, one keymap per bucky bit or
  2605.    prefix key, it's not entirely objvious what map-keymap should do, but 
  2606.    what it does is: map over all keys in this map; then recursively map
  2607.    over all submaps of this map that are "bucky" submaps.  This means that,
  2608.    when mapping over a keymap, it appears that "x" and "C-x" are in the
  2609.    same map, although "C-x" is really in the "control" submap of this one.
  2610.    However, since we don't recursively descend the submaps that are bound
  2611.    to prefix keys (like C-x, C-h, etc) the caller will have to recurse on
  2612.    those explicitly, if that's what they want.
  2613.  
  2614.    So the end result of this is that the bucky keymaps (the ones indexed
  2615.    under the large integers returned from MAKE_MODIFIER_HASH_KEY()) are
  2616.    invisible from elisp.  They're just an implementation detail that code
  2617.    outside of this file doesn't need to know about.
  2618.  */
  2619.  
  2620. struct map_keymap_unsorted_closure
  2621. {
  2622.   void (*fn) (CONST struct key_data *, Lisp_Object binding, void *arg);
  2623.   void *arg;
  2624.   unsigned int modifiers;
  2625. };
  2626.  
  2627. /* used by map_keymap() */
  2628. static void
  2629. map_keymap_unsorted_mapper (CONST void *hash_key, void *hash_contents, 
  2630.                             void *map_keymap_unsorted_closure)
  2631. {
  2632.   /* This function can GC */
  2633.   Lisp_Object keysym;
  2634.   Lisp_Object contents;
  2635.   struct map_keymap_unsorted_closure *closure = map_keymap_unsorted_closure;
  2636.   unsigned int modifiers = closure->modifiers;
  2637.   unsigned int mod_bit;
  2638.   CVOID_TO_LISP (keysym, hash_key);
  2639.   VOID_TO_LISP (contents, hash_contents);
  2640.   mod_bit = MODIFIER_HASH_KEY_P (keysym);
  2641.   if (mod_bit != 0)
  2642.     {
  2643.       int omod = modifiers;
  2644.       closure->modifiers = (modifiers | mod_bit);
  2645.       contents = get_keymap (contents, 1, 1);
  2646.       elisp_maphash (map_keymap_unsorted_mapper,
  2647.              XKEYMAP (contents)->table,
  2648.              map_keymap_unsorted_closure);
  2649.       closure->modifiers = omod;
  2650.     }
  2651.   else
  2652.     {
  2653.       struct key_data key;
  2654.       key.keysym = keysym;
  2655.       key.modifiers = modifiers;
  2656.       ((*closure->fn) (&key, contents, closure->arg));
  2657.     }
  2658. }
  2659.  
  2660.  
  2661. struct map_keymap_sorted_closure
  2662. {
  2663.   Lisp_Object *result_locative;
  2664. };
  2665.  
  2666. /* used by map_keymap_sorted() */
  2667. static void
  2668. map_keymap_sorted_mapper (CONST void *hash_key, void *hash_contents, 
  2669.                           void *map_keymap_sorted_closure)
  2670. {
  2671.   struct map_keymap_sorted_closure *cl = map_keymap_sorted_closure;
  2672.   Lisp_Object key, contents;
  2673.   Lisp_Object *list = cl->result_locative;
  2674.   CVOID_TO_LISP (key, hash_key);
  2675.   VOID_TO_LISP (contents, hash_contents);
  2676.   *list = Fcons (Fcons (key, contents), *list);
  2677. }
  2678.  
  2679.  
  2680. /* used by map_keymap_sorted(), describe_map_sort_predicate(),
  2681.    and keymap_submaps().
  2682.  */
  2683. static int
  2684. map_keymap_sort_predicate (Lisp_Object obj1, Lisp_Object obj2, 
  2685.                            Lisp_Object pred)
  2686. {
  2687.   /* obj1 and obj2 are conses with keysyms in their cars.  Cdrs are ignored.
  2688.    */
  2689.   unsigned int bit1, bit2;
  2690.   int sym1_p = 0;
  2691.   int sym2_p = 0;
  2692.   obj1 = XCAR (obj1);
  2693.   obj2 = XCAR (obj2);
  2694.  
  2695.   if (EQ (obj1, obj2))
  2696.     return -1;
  2697.   bit1 = MODIFIER_HASH_KEY_P (obj1);
  2698.   bit2 = MODIFIER_HASH_KEY_P (obj2);
  2699.   
  2700.   /* If either is a symbol with a character-set-property, then sort it by
  2701.      that code instead of alphabetically.
  2702.      */
  2703.   if (! bit1 && SYMBOLP (obj1))
  2704.     {
  2705.       Lisp_Object code = Fget (obj1, Vcharacter_set_property, Qnil);
  2706.       if (INTP (code))
  2707.     obj1 = code, sym1_p = 1;
  2708.     }
  2709.   if (! bit2 && SYMBOLP (obj2))
  2710.     {
  2711.       Lisp_Object code = Fget (obj2, Vcharacter_set_property, Qnil);
  2712.       if (INTP (code))
  2713.     obj2 = code, sym2_p = 1;
  2714.     }
  2715.  
  2716.   /* all symbols (non-ASCIIs) come after integers (ASCIIs) */
  2717.   if (XTYPE (obj1) != XTYPE (obj2))
  2718.     return ((SYMBOLP (obj2)) ? 1 : -1);
  2719.  
  2720.   if (! bit1 && INTP (obj1)) /* they're both ASCII */
  2721.     {
  2722.       int o1 = XINT (obj1);
  2723.       int o2 = XINT (obj2);
  2724.       if (o1 == o2 &&        /* If one started out as a symbol and the */
  2725.       sym1_p != sym2_p)    /* other didn't, the symbol comes last. */
  2726.     return (sym2_p ? 1 : -1);
  2727.  
  2728.       return ((o1 < o2) ? 1 : -1); /* else just compare them */
  2729.     }
  2730.  
  2731.   /* else they're both symbols.  If they're both buckys, then order them. */
  2732.   if (bit1 && bit2)
  2733.     return ((bit1 < bit2) ? 1 : -1);
  2734.   
  2735.   /* if only one is a bucky, then it comes later */
  2736.   if (bit1 || bit2)
  2737.     return (bit2 ? 1 : -1);
  2738.  
  2739.   /* otherwise, string-sort them. */
  2740.   {
  2741.     char *s1 = (char *) string_data (XSYMBOL (obj1)->name);
  2742.     char *s2 = (char *) string_data (XSYMBOL (obj2)->name);
  2743.     return (
  2744. #ifdef I18N2
  2745.         (0 > strcoll (s1, s2))
  2746. #else
  2747.         (0 > strcmp (s1, s2))
  2748. #endif
  2749.         ? 1 : -1);
  2750.   }
  2751. }
  2752.  
  2753.  
  2754. /* used by map_keymap() */
  2755. static void
  2756. map_keymap_sorted (Lisp_Object keymap_table,
  2757.                    unsigned int modifiers, 
  2758.                    void (*function) (CONST struct key_data *key,
  2759.                                      Lisp_Object binding, 
  2760.                                      void *map_keymap_sorted_closure),
  2761.                    void *map_keymap_sorted_closure)
  2762. {
  2763.   /* This function can GC */
  2764.   struct gcpro gcpro1;
  2765.   Lisp_Object contents = Qnil;
  2766.  
  2767.   if (XINT (Fhashtable_fullness (keymap_table)) == 0)
  2768.     return;
  2769.  
  2770.   GCPRO1 (contents);
  2771.  
  2772.   {
  2773.     struct map_keymap_sorted_closure c1;
  2774.     c1.result_locative = &contents;
  2775.     elisp_maphash (map_keymap_sorted_mapper, keymap_table, &c1);
  2776.   }
  2777.   contents = list_sort (contents, Qnil, map_keymap_sort_predicate);
  2778.   for (; !NILP (contents); contents = XCDR (contents))
  2779.     {
  2780.       Lisp_Object keysym = XCAR (XCAR (contents));
  2781.       Lisp_Object binding = XCDR (XCAR (contents));
  2782.       unsigned int sub_bits = MODIFIER_HASH_KEY_P (keysym);
  2783.       if (sub_bits != 0)
  2784.     map_keymap_sorted (XKEYMAP (get_keymap (binding,
  2785.                         1, 1))->table,
  2786.                (modifiers | sub_bits),
  2787.                function,
  2788.                map_keymap_sorted_closure);
  2789.       else
  2790.     {
  2791.       struct key_data k;
  2792.       k.keysym = keysym;
  2793.       k.modifiers = modifiers;
  2794.       ((*function) (&k, binding, map_keymap_sorted_closure));
  2795.     }
  2796.     }
  2797.   UNGCPRO;
  2798. }
  2799.  
  2800.  
  2801. /* used by Fmap_keymap() */
  2802. static void
  2803. map_keymap_mapper (CONST struct key_data *key,
  2804.                    Lisp_Object binding, 
  2805.                    void *function)
  2806. {
  2807.   /* This function can GC */
  2808.   Lisp_Object fn;
  2809.   VOID_TO_LISP (fn, function);
  2810.   call2 (fn, make_key_description (key, 1), binding);
  2811. }
  2812.  
  2813.  
  2814. static void
  2815. map_keymap (Lisp_Object keymap_table, int sort_first,
  2816.             void (*function) (CONST struct key_data *key,
  2817.                               Lisp_Object binding,
  2818.                               void *fn_arg),
  2819.             void *fn_arg)
  2820. {
  2821.   /* This function can GC */
  2822.   if (sort_first)
  2823.     map_keymap_sorted (keymap_table, 0, function, fn_arg);
  2824.   else
  2825.     {
  2826.       struct map_keymap_unsorted_closure map_keymap_unsorted_closure;
  2827.       map_keymap_unsorted_closure.fn = function;
  2828.       map_keymap_unsorted_closure.arg = fn_arg;
  2829.       map_keymap_unsorted_closure.modifiers = 0;
  2830.       elisp_maphash (map_keymap_unsorted_mapper, keymap_table,
  2831.              &map_keymap_unsorted_closure);
  2832.     }
  2833. }
  2834.  
  2835. DEFUN ("map-keymap", Fmap_keymap, Smap_keymap, 2, 3, 0,
  2836.   "Apply FUNCTION to each element of KEYMAP.\n\
  2837. FUNCTION will be called with two arguments: a key-description list, and\n\
  2838. the binding.  The order in which the elements of the keymap are passed to\n\
  2839. the function is unspecified.  If the function inserts new elements into\n\
  2840. the keymap, it may or may not be called with them later.  No element of\n\
  2841. the keymap will ever be passed to the function more than once.\n\
  2842. \n\
  2843. The function will not be called on elements of this keymap's parents\n\
  2844. (see the function `keymap-parents') or upon keymaps which are contained\n\
  2845. within this keymap (multi-character definitions).\n\
  2846. It will be called on \"meta\" characters since they are not really\n\
  2847. two-character sequences.\n\
  2848. \n\
  2849. If the optional third argument SORT-FIRST is non-nil, then the elements of\n\
  2850. the keymap will be passed to the mapper function in a canonical order.\n\
  2851. Otherwise, they will be passed in hash (that is, random) order, which is\n\
  2852. faster.")
  2853.      (function, keymap, sort_first)
  2854.     Lisp_Object function, keymap, sort_first;
  2855. {
  2856.   /* This function can GC */
  2857.   struct gcpro gcpro1, gcpro2;
  2858.  
  2859.  /* tolerate obviously transposed args */
  2860.   if (!NILP (Fkeymapp (function)))
  2861.     {
  2862.       Lisp_Object tmp = function;
  2863.       function = keymap;
  2864.       keymap = tmp;
  2865.     }
  2866.   GCPRO2 (function, keymap);
  2867.   keymap = get_keymap (keymap, 1, 1);
  2868.   map_keymap (XKEYMAP (keymap)->table, !NILP (sort_first),
  2869.           map_keymap_mapper, LISP_TO_VOID (function));
  2870.   UNGCPRO;
  2871.   return Qnil;
  2872. }
  2873.  
  2874.  
  2875.  
  2876. /************************************************************************/
  2877. /*                          Accessible keymaps                          */
  2878. /************************************************************************/
  2879.  
  2880. struct accessible_keymaps_closure
  2881.   {
  2882.     Lisp_Object tail;
  2883.   };
  2884.  
  2885.  
  2886. static void
  2887. accessible_keymaps_mapper_1 (Lisp_Object keysym, Lisp_Object contents,
  2888.                              unsigned int modifiers,
  2889.                              struct accessible_keymaps_closure *closure)
  2890. {
  2891.   /* This function can GC */
  2892.   unsigned int subbits = MODIFIER_HASH_KEY_P (keysym);
  2893.  
  2894.   if (subbits != 0)
  2895.     {
  2896.       Lisp_Object submaps;
  2897.  
  2898.       contents = get_keymap (contents, 1, 1);
  2899.       submaps = keymap_submaps (contents);
  2900.       for (; !NILP (submaps); submaps = XCDR (submaps))
  2901.     {
  2902.       accessible_keymaps_mapper_1 (XCAR (XCAR (submaps)),
  2903.                                        XCDR (XCAR (submaps)),
  2904.                                        (subbits | modifiers),
  2905.                                        closure);
  2906.     }
  2907.     }
  2908.   else
  2909.     {
  2910.       Lisp_Object thisseq = Fcar (Fcar (closure->tail));
  2911.       Lisp_Object cmd = get_keyelt (contents, 1);
  2912.       Lisp_Object vec;
  2913.       int j;
  2914.       struct key_data key;
  2915.       key.keysym = keysym;
  2916.       key.modifiers = modifiers;
  2917.  
  2918.       if (NILP (cmd))
  2919.     abort ();
  2920.       cmd = get_keymap (cmd, 0, 1);
  2921.       if (!KEYMAPP (cmd))
  2922.     abort ();
  2923.  
  2924.       vec = make_vector (vector_length (XVECTOR (thisseq)) + 1, Qnil);
  2925.       for (j = 0; j < vector_length (XVECTOR (thisseq)); j++)
  2926.     vector_data (XVECTOR (vec)) [j] = vector_data (XVECTOR (thisseq)) [j];
  2927.       vector_data (XVECTOR (vec)) [j] = make_key_description (&key, 1);
  2928.  
  2929.       nconc2 (closure->tail, list1 (Fcons (vec, cmd)));
  2930.     }
  2931. }
  2932.  
  2933.  
  2934. static Lisp_Object
  2935. accessible_keymaps_keymap_mapper (Lisp_Object thismap, void *arg)
  2936. {
  2937.   /* This function can GC */
  2938.   struct accessible_keymaps_closure *closure = arg;
  2939.   Lisp_Object submaps = keymap_submaps (thismap);
  2940.  
  2941.   for (; !NILP (submaps); submaps = XCDR (submaps))
  2942.     {
  2943.       accessible_keymaps_mapper_1 (XCAR (XCAR (submaps)),
  2944.                    XCDR (XCAR (submaps)),
  2945.                    0,
  2946.                    closure);
  2947.     }
  2948.   return (Qnil);
  2949. }
  2950.  
  2951.  
  2952. DEFUN ("accessible-keymaps", Faccessible_keymaps, Saccessible_keymaps,
  2953.   1, 2, 0,
  2954.   "Find all keymaps accessible via prefix characters from STARTMAP.\n\
  2955. Returns a list of elements of the form (KEYS . MAP), where the sequence\n\
  2956. KEYS starting from STARTMAP gets you to MAP.  These elements are ordered\n\
  2957. so that the KEYS increase in length.  The first element is ([] . STARTMAP).\n\
  2958. An optional argument PREFIX, if non-nil, should be a key sequence;\n\
  2959. then the value includes only maps for prefixes that start with PREFIX.")
  2960.   (startmap, prefix)
  2961.      Lisp_Object startmap, prefix;
  2962. {
  2963.   /* This function can GC */
  2964.   struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
  2965.   Lisp_Object accessible_keymaps = Qnil;
  2966.   struct accessible_keymaps_closure c;
  2967.   c.tail = Qnil;
  2968.   GCPRO4 (accessible_keymaps, c.tail, prefix, startmap);
  2969.  
  2970.  retry:
  2971.   startmap = get_keymap (startmap, 1, 1);
  2972.   if (NILP (prefix))
  2973.     prefix = make_vector (0, Qnil);
  2974.   else if (!VECTORP (prefix) || STRINGP (prefix))
  2975.     {
  2976.       prefix = wrong_type_argument (Qarrayp, prefix);
  2977.       goto retry;
  2978.     }
  2979.   else
  2980.     {
  2981.       int len = XINT (Flength (prefix));
  2982.       Lisp_Object def = Flookup_key (startmap, prefix, Qnil);
  2983.       Lisp_Object p;
  2984.       int iii;
  2985.       struct gcpro gcpro1;
  2986.  
  2987.       def = get_keymap (def, 0, 1);
  2988.       if (!KEYMAPP (def))
  2989.     goto RETURN;
  2990.  
  2991.       startmap = def;
  2992.       p = make_vector (len, Qnil);
  2993.       GCPRO1 (p);
  2994.       for (iii = 0; iii < len; iii++)
  2995.     {
  2996.       struct key_data key;
  2997.       define_key_parser (Faref (prefix, make_number (iii)), &key);
  2998.       vector_data (XVECTOR (p))[iii] = make_key_description (&key, 1);
  2999.     }
  3000.       UNGCPRO;
  3001.       prefix = p;
  3002.     }
  3003.   
  3004.   accessible_keymaps = list1 (Fcons (prefix, startmap));
  3005.  
  3006.   /* For each map in the list maps,
  3007.      look at any other maps it points to
  3008.      and stick them at the end if they are not already in the list */
  3009.  
  3010.   for (c.tail = accessible_keymaps;
  3011.        !NILP (c.tail);
  3012.        c.tail = XCDR (c.tail))
  3013.     {
  3014.       Lisp_Object thismap = Fcdr (Fcar (c.tail));
  3015.       CHECK_KEYMAP (thismap, 0);
  3016.       traverse_keymaps (thismap, Qnil,
  3017.                         accessible_keymaps_keymap_mapper, &c);
  3018.     }
  3019.  RETURN:
  3020.   UNGCPRO;
  3021.   return (accessible_keymaps);
  3022. }
  3023.  
  3024.  
  3025.  
  3026. /************************************************************************/
  3027. /*              Pretty descriptions of key sequences                    */
  3028. /************************************************************************/
  3029.  
  3030. DEFUN ("key-description", Fkey_description, Skey_description, 1, 1, 0,
  3031.   "Return a pretty description of key-sequence KEYS.\n\
  3032. Control characters turn into \"C-foo\" sequences, meta into \"M-foo\"\n\
  3033.  spaces are put between sequence elements, etc.")
  3034.   (keys)
  3035.      Lisp_Object keys;
  3036. {
  3037.   if (INTP (keys) || CONSP (keys) || SYMBOLP (keys) || EVENTP (keys))
  3038.     {
  3039.       return Fsingle_key_description (keys);
  3040.     }
  3041.   else if (VECTORP (keys) ||
  3042.        STRINGP (keys))
  3043.     {
  3044.       Lisp_Object string = Qnil;
  3045.       /* Lisp_Object sep = Qnil; */
  3046.       int size = XINT (Flength (keys));
  3047.       int i;
  3048.  
  3049.       for (i = 0; i < size; i++)
  3050.     {
  3051.       Lisp_Object s2 = Fsingle_key_description
  3052.         (((STRINGP (keys))
  3053.           ? make_number ((unsigned char) string_char (XSTRING (keys), i))
  3054.           : vector_data (XVECTOR (keys))[i]));
  3055.  
  3056.       if (i == 0)
  3057.         string = s2;
  3058.       else
  3059.         {
  3060.           /* if (NILP (sep)) Lisp_Object sep = build_string (" ") */;
  3061.           string = concat2 (string, concat2 (Vsingle_space_string, s2));
  3062.         }
  3063.     }
  3064.       return (string);
  3065.     }
  3066.   return Fkey_description (wrong_type_argument (Qsequencep, keys));
  3067. }
  3068.  
  3069. DEFUN ("single-key-description", Fsingle_key_description,
  3070.        Ssingle_key_description, 1, 1, 0,
  3071.   "Return a pretty description of command character KEY.\n\
  3072. Control characters turn into C-whatever, etc.\n\
  3073. This differs from `text-char-description' in that it returns a description\n\
  3074. of a key read from the user rather than a character from a buffer.")
  3075.   (key)
  3076.      Lisp_Object key;
  3077. {
  3078.   if (SYMBOLP (key))
  3079.     key = Fcons (key, Qnil); /* sleaze sleaze */
  3080.  
  3081.   if (EVENTP (key) || CHARP (key))
  3082.     {
  3083.       char buf [255];
  3084.       if (INTP (key))
  3085.     {
  3086.       struct Lisp_Event event;
  3087.       event.event_type = empty_event;
  3088.       character_to_event (XINT (key), &event, 0);
  3089.       format_event_object (buf, &event, 1);
  3090.     }
  3091.       else
  3092.     format_event_object (buf, XEVENT (key), 1);
  3093.       return (build_string (buf));
  3094.     }
  3095.  
  3096.   if (CONSP (key))
  3097.     {
  3098.       char buf [255];
  3099.       char *bufp = buf;
  3100.       Lisp_Object rest;
  3101.       buf[0]=0;
  3102.       LIST_LOOP (rest, key)
  3103.     {
  3104.       Lisp_Object keysym = XCAR (rest);
  3105.       if (EQ (keysym, Qcontrol))    strcpy (bufp, "C-"), bufp += 2;
  3106.       else if (EQ (keysym, Qctrl))  strcpy (bufp, "C-"), bufp += 2;
  3107.       else if (EQ (keysym, Qmeta))  strcpy (bufp, "M-"), bufp += 2;
  3108.       else if (EQ (keysym, Qsuper)) strcpy (bufp, "S-"), bufp += 2;
  3109.       else if (EQ (keysym, Qhyper)) strcpy (bufp, "H-"), bufp += 2;
  3110.       else if (EQ (keysym, Qalt))    strcpy (bufp, "A-"), bufp += 2;
  3111.       else if (EQ (keysym, Qshift)) strcpy (bufp, "Sh-"), bufp += 3;
  3112.       else if (INTP (keysym))
  3113.         *bufp = XINT (keysym), bufp++, *bufp = 0;
  3114.       else
  3115.         {
  3116.           CHECK_SYMBOL (keysym, 0);
  3117. #if 0                           /* This is bogus */
  3118.           if (EQ (keysym, QKlinefeed))    strcpy (bufp, "LFD");
  3119.           else if (EQ (keysym, QKtab))    strcpy (bufp, "TAB");
  3120.           else if (EQ (keysym, QKreturn))    strcpy (bufp, "RET");
  3121.           else if (EQ (keysym, QKescape))    strcpy (bufp, "ESC");
  3122.           else if (EQ (keysym, QKdelete))    strcpy (bufp, "DEL");
  3123.           else if (EQ (keysym, QKspace))    strcpy (bufp, "SPC");
  3124.           else if (EQ (keysym, QKbackspace))    strcpy (bufp, "BS");
  3125.           else
  3126. #endif
  3127.         strcpy (bufp, (char *) string_data (XSYMBOL (keysym)->name));
  3128.           if (!NILP (XCDR (rest)))
  3129.         signal_simple_error ("invalid key description",
  3130.                      key);
  3131.         }
  3132.     }
  3133.       return build_string (buf);
  3134.     }
  3135.   return Fsingle_key_description
  3136.     (wrong_type_argument (intern ("char-or-event-p"), key));
  3137. }
  3138.  
  3139. DEFUN ("text-char-description", Ftext_char_description, Stext_char_description,
  3140.        1, 1, 0,
  3141.   "Return a pretty description of file-character CHAR.\n\
  3142. Unprintable characters turn into \"^char\" or \\NNN, depending on the value\n\
  3143. of the `ctl-arrow' variable.\n\
  3144. This differs from `single-key-description' in that it returns a description\n\
  3145. of a character from a buffer rather than a key read from the user.")
  3146.   (chr)
  3147.      Lisp_Object chr;
  3148. {
  3149.   Bufbyte buf[200];
  3150.   Bufbyte *p;
  3151.   unsigned int c;
  3152.   Lisp_Object ctl_arrow = current_buffer->ctl_arrow;
  3153.   int ctl_p = !NILP (ctl_arrow);
  3154.   int printable_min = (INTP (ctl_arrow)
  3155.                ? XINT (ctl_arrow)
  3156.                : ((EQ (ctl_arrow, Qt) || EQ (ctl_arrow, Qnil))
  3157.               ? 256 : 160));
  3158.  
  3159.   if (EVENTP (chr))
  3160.     {
  3161.       Lisp_Object ch = Fevent_to_character (chr, Qnil, Qnil, Qt);
  3162.       if (NILP (ch))
  3163.     return
  3164.       signal_simple_continuable_error
  3165.         ("character has no ASCII equivalent", Fcopy_event (chr, Qnil));
  3166.       chr = ch;
  3167.     }
  3168.  
  3169.   CHECK_COERCE_CHAR (chr, 0);
  3170.  
  3171.   c = XINT (chr);
  3172.   p = buf;
  3173.  
  3174.   if (c >= printable_min)
  3175.     {
  3176.       p += emchar_to_charptr (c, p);
  3177.     }
  3178.   else if (c < 040 && ctl_p)
  3179.     {
  3180.       *p++ = '^';
  3181.       *p++ = c + 64;        /* 'A' - 1 */
  3182.     }
  3183.   else if (c == 0177)
  3184.     {
  3185.       *p++ = '^';
  3186.       *p++ = '?';
  3187.     }
  3188.   else if (c >= 0200 || c < 040)
  3189.     {
  3190.       *p++ = '\\';
  3191. #ifdef MULE
  3192.       /* !!#### This syntax is not readable.  It will
  3193.      be interpreted as a 3-digit octal number rather
  3194.      than a 7-digit octal number. */
  3195.       if (c >= 0400)
  3196.     {
  3197.       *p++ = '0' + ((c & 07000000) >> 18);
  3198.       *p++ = '0' + ((c & 0700000) >> 15);
  3199.       *p++ = '0' + ((c & 070000) >> 12);
  3200.       *p++ = '0' + ((c & 07000) >> 9);
  3201.     }
  3202. #endif
  3203.       *p++ = '0' + ((c & 0700) >> 6);
  3204.       *p++ = '0' + ((c & 0070) >> 3);
  3205.       *p++ = '0' + ((c & 0007));
  3206.     }
  3207.   else
  3208.     {
  3209.       p += emchar_to_charptr (c, p);
  3210.     }
  3211.  
  3212.   *p = 0;
  3213.   return build_string ((char *) buf);
  3214. }
  3215.  
  3216.  
  3217. /************************************************************************/
  3218. /*              where-is (mapping bindings to keys)                     */
  3219. /************************************************************************/
  3220.  
  3221. static Lisp_Object
  3222. where_is_internal (Lisp_Object definition, Lisp_Object *maps, int nmaps,
  3223.                    Lisp_Object firstonly, char *target_buffer);
  3224.  
  3225. DEFUN ("where-is-internal", Fwhere_is_internal, Swhere_is_internal, 1, 5, 0,
  3226.   "Return list of keys that invoke DEFINITION in KEYMAPS.\n\
  3227. KEYMAPS can be either a keymap (meaning search in that keymap and the\n\
  3228. current global keymap) or a list of keymaps (meaning search in exactly\n\
  3229. those keymaps and no others).  If KEYMAPS is nil, search in the currently\n\
  3230. applicable maps for EVENT-OR-KEYS (this is equivalent to specifying\n\
  3231. `(current-keymaps EVENT-OR-KEYS)' as the argument to KEYMAPS).\n\
  3232. \n\
  3233. If optional 3rd arg FIRSTONLY is non-nil, return a vector representing\n\
  3234.  the first key sequence found, rather than a list of all possible key\n\
  3235.  sequences.\n\
  3236. \n\
  3237. If optional 4th arg NOINDIRECT is non-nil, don't follow indirections\n\
  3238.  to other keymaps or slots.  This makes it possible to search for an\n\
  3239.  indirect definition itself.")
  3240.   (definition, keymaps, firstonly, noindirect, event_or_keys)
  3241.      Lisp_Object definition, keymaps, firstonly, noindirect, event_or_keys;
  3242. {
  3243.   /* This function can GC */
  3244.   Lisp_Object maps[100];
  3245.   Lisp_Object *gubbish = maps;
  3246.   int nmaps;
  3247.  
  3248.   /* Get keymaps as an array */
  3249.   if (NILP (keymaps))
  3250.     {
  3251.       nmaps = get_relevant_keymaps (event_or_keys, countof (maps),
  3252.                     gubbish);
  3253.       if (nmaps > countof (maps))
  3254.     {
  3255.       gubbish = (Lisp_Object *) alloca (nmaps * sizeof (Lisp_Object));
  3256.       nmaps = get_relevant_keymaps (event_or_keys, nmaps, gubbish);
  3257.     }
  3258.     }
  3259.   else if (CONSP (keymaps))
  3260.     {
  3261.       Lisp_Object rest;
  3262.       int i;
  3263.  
  3264.       nmaps = XINT (Flength (keymaps));
  3265.       if (nmaps > countof (maps))
  3266.     {
  3267.       gubbish = (Lisp_Object *) alloca (nmaps * sizeof (Lisp_Object));
  3268.     }
  3269.       for (rest = keymaps, i = 0; !NILP (rest);
  3270.        rest = XCDR (keymaps), i++)
  3271.     {
  3272.       gubbish[i] = get_keymap (XCAR (keymaps), 1, 1);
  3273.     }
  3274.     }
  3275.   else
  3276.     {
  3277.       nmaps = 1;
  3278.       gubbish[0] = get_keymap (keymaps, 1, 1);
  3279.       if (!EQ (gubbish[0], Vcurrent_global_map))
  3280.     {
  3281.       gubbish[1] = Vcurrent_global_map;
  3282.       nmaps++;
  3283.     }
  3284.     }
  3285.       
  3286.   return where_is_internal (definition, gubbish, nmaps, firstonly, 0);
  3287. }
  3288.  
  3289. /* This function is like
  3290.    (key-description (where-is-internal definition nil t))
  3291.    except that it writes its output into a (char *) buffer that you 
  3292.    provide; it doesn't cons (or allocate memory) at all, so it's
  3293.    very fast.  This is used by menubar.c.
  3294.  */
  3295. void
  3296. where_is_to_char (Lisp_Object definition, char *buffer)
  3297. {
  3298.   /* This function can GC */
  3299.   Lisp_Object maps[100];
  3300.   Lisp_Object *gubbish = maps;
  3301.   int nmaps;
  3302.  
  3303.   /* Get keymaps as an array */
  3304.   nmaps = get_relevant_keymaps (Qnil, countof (maps), gubbish);
  3305.   if (nmaps > countof (maps))
  3306.     {
  3307.       gubbish = (Lisp_Object *) alloca (nmaps * sizeof (Lisp_Object));
  3308.       nmaps = get_relevant_keymaps (Qnil, nmaps, gubbish);
  3309.     }
  3310.  
  3311.   buffer[0] = 0;
  3312.   where_is_internal (definition, maps, nmaps, Qt, buffer);
  3313. }
  3314.  
  3315.  
  3316. static Lisp_Object 
  3317. raw_keys_to_keys (struct key_data *keys, int count)
  3318. {
  3319.   Lisp_Object result = make_vector (count, Qnil);
  3320.   while (count--)
  3321.     vector_data (XVECTOR (result)) [count] =
  3322.       make_key_description (&(keys[count]), 1);
  3323.   return (result);
  3324. }
  3325.  
  3326.  
  3327. static void
  3328. format_raw_keys (struct key_data *keys, int count, char *buf)
  3329. {
  3330.   int i;
  3331.   struct Lisp_Event event;
  3332.   event.event_type = key_press_event;
  3333.   for (i = 0; i < count; i++)
  3334.     {
  3335.       event.event.key.keysym    = keys[i].keysym;
  3336.       event.event.key.modifiers = keys[i].modifiers;
  3337.       format_event_object (buf, &event, 1);
  3338.       buf += strlen (buf);
  3339.       if (i < count-1)
  3340.     buf[0] = ' ', buf++;
  3341.     }
  3342. }
  3343.  
  3344.  
  3345. /* definition is the thing to look for.
  3346.    map is a keymap.
  3347.    shadow is an array of shadow_count keymaps; if there is a different
  3348.    binding in any of the keymaps of a key that we are considering
  3349.    returning, then we reconsider.
  3350.    firstonly means give up after finding the first match;
  3351.    keys_so_far and modifiers_so_far describe which map we're looking in;
  3352.    If we're in the "meta" submap of the map that "C-x 4" is bound to,
  3353.    then keys_so_far will be {(control x), \4}, and modifiers_so_far
  3354.    will be MOD_META.  That is, keys_so_far is the chain of keys that we
  3355.    have followed, and modifiers_so_far_so_far is the bits (partial keys)
  3356.    beyond that.
  3357.    
  3358.    (keys_so_far is a global buffer and the keys_count arg says how much
  3359.    of it we're currently interested in.)
  3360.    
  3361.    If target_buffer is provided, then we write a key-description into it,
  3362.    to avoid consing a string.  This only works with firstonly on.
  3363.    */
  3364.  
  3365. struct where_is_closure
  3366.   {
  3367.     Lisp_Object definition;
  3368.     Lisp_Object *shadow;
  3369.     int shadow_count;
  3370.     int firstonly;
  3371.     int keys_count;
  3372.     unsigned int modifiers_so_far;
  3373.     char *target_buffer;
  3374.     struct key_data *keys_so_far;
  3375.     int keys_so_far_total_size;
  3376.     int keys_so_far_malloced;
  3377.   };
  3378.  
  3379. static Lisp_Object where_is_recursive_mapper (Lisp_Object map, void *arg);
  3380.  
  3381. static Lisp_Object
  3382. where_is_recursive_mapper (Lisp_Object map, void *arg)
  3383. {
  3384.   /* This function can GC */
  3385.   struct where_is_closure *c = arg;
  3386.   Lisp_Object definition = c->definition;
  3387.   CONST int firstonly = c->firstonly;
  3388.   CONST unsigned int keys_count = c->keys_count;
  3389.   CONST unsigned int modifiers_so_far = c->modifiers_so_far;
  3390.   char *target_buffer = c->target_buffer;
  3391.   Lisp_Object keys = Fgethash (definition,
  3392.                                XKEYMAP (map)->inverse_table,
  3393.                                Qnil);
  3394.   Lisp_Object submaps;
  3395.   Lisp_Object result = Qnil;
  3396.  
  3397.   if (!NILP (keys))
  3398.     {
  3399.       /* One or more keys in this map match the definition we're looking
  3400.      for.  Verify that these bindings aren't shadowed by other bindings
  3401.      in the shadow maps.  Either nil or number as value from
  3402.      raw_lookup_key() means undefined.
  3403.      */
  3404.       struct key_data *so_far = c->keys_so_far;
  3405.  
  3406.       for (;;) /* loop over all keys that match */
  3407.     {
  3408.       Lisp_Object k = ((CONSP (keys)) ? XCAR (keys) : keys);
  3409.       int i;
  3410.       
  3411.       so_far [keys_count].keysym = k;
  3412.       so_far [keys_count].modifiers = modifiers_so_far;
  3413.  
  3414.       /* now loop over all shadow maps */
  3415.       for (i = 0; i < c->shadow_count; i++)
  3416.         {
  3417.           Lisp_Object shadowed = raw_lookup_key (c->shadow[i],
  3418.                              so_far,
  3419.                              keys_count + 1, 
  3420.                              0, 1);
  3421.  
  3422.           if (NILP (shadowed) || INTP (shadowed) ||
  3423.           EQ (shadowed, definition))
  3424.         continue; /* we passed this test; it's not shadowed here. */
  3425.           else
  3426.         /* ignore this key binding, since it actually has a
  3427.            different binding in a shadowing map */
  3428.         goto c_doesnt_have_proper_loop_exit_statements;
  3429.         }
  3430.  
  3431.       /* OK, the key is for real */
  3432.       if (target_buffer)
  3433.         {
  3434.           if (!firstonly) abort ();
  3435.           format_raw_keys (so_far, keys_count + 1, target_buffer);
  3436.           return (make_number (1));
  3437.         }
  3438.       else if (firstonly)
  3439.         return raw_keys_to_keys (so_far, keys_count + 1);
  3440.       else
  3441.         result = Fcons (raw_keys_to_keys (so_far, keys_count + 1),
  3442.                 result);
  3443.  
  3444.     c_doesnt_have_proper_loop_exit_statements:
  3445.       /* now on to the next matching key ... */
  3446.       if (!CONSP (keys)) break;
  3447.       keys = XCDR (keys);
  3448.     }
  3449.     }
  3450.  
  3451.   /* Now search the sub-keymaps of this map.
  3452.      If we're in "firstonly" mode and have already found one, this 
  3453.      point is not reached.  If we get one from lower down, either
  3454.      return it immediately (in firstonly mode) or tack it onto the
  3455.      end of the ones we've gotten so far.
  3456.      */
  3457.   for (submaps = keymap_submaps (map);
  3458.        !NILP (submaps);
  3459.        submaps = XCDR (submaps))
  3460.     {
  3461.       Lisp_Object key    = XCAR (XCAR (submaps));
  3462.       Lisp_Object submap = XCDR (XCAR (submaps));
  3463.       unsigned int lower_modifiers;
  3464.       int lower_keys_count = keys_count;
  3465.       unsigned int bucky;
  3466.  
  3467.       submap = get_keymap (submap, 0, 1);
  3468.  
  3469.       if (EQ (submap, map))
  3470.     /* Arrgh!  Some loser has introduced a loop... */
  3471.     continue;
  3472.  
  3473.       /* If this is not a keymap, then that's probably because someone
  3474.      did an `fset' of a symbol that used to point to a map such that
  3475.      it no longer does.  Sigh.  Ignore this, and invalidate the cache
  3476.      so that it doesn't happen to us next time too.
  3477.      */
  3478.       if (NILP (submap))
  3479.     {
  3480.       XKEYMAP (map)->sub_maps_cache = Qt;
  3481.       continue;
  3482.     }
  3483.  
  3484.       /* If the map is a "bucky" map, then add a bit to the
  3485.      modifiers_so_far list.
  3486.      Otherwise, add a new raw_key onto the end of keys_so_far.
  3487.      */
  3488.       bucky = MODIFIER_HASH_KEY_P (key);
  3489.       if (bucky != 0)
  3490.     lower_modifiers = (modifiers_so_far | bucky);
  3491.       else
  3492.     {
  3493.       struct key_data *so_far = c->keys_so_far;
  3494.       lower_modifiers = 0;
  3495.       so_far [lower_keys_count].keysym = key;
  3496.       so_far [lower_keys_count].modifiers = modifiers_so_far;
  3497.       lower_keys_count++;
  3498.     }
  3499.  
  3500.       if (lower_keys_count >= c->keys_so_far_total_size)
  3501.     {
  3502.       int size = lower_keys_count + 50;
  3503.       if (! c->keys_so_far_malloced)
  3504.         {
  3505.           struct key_data *new = xmalloc (size * sizeof (struct key_data));
  3506.           memcpy ((void *)new, (const void *)c->keys_so_far,
  3507.               c->keys_so_far_total_size * sizeof (struct key_data));
  3508.         }
  3509.       else
  3510.         c->keys_so_far = xrealloc (c->keys_so_far,
  3511.                        size * sizeof (struct key_data));
  3512.  
  3513.       c->keys_so_far_total_size = size;
  3514.       c->keys_so_far_malloced = 1;
  3515.     }
  3516.  
  3517.       {
  3518.     Lisp_Object lower;
  3519.  
  3520.     c->keys_count = lower_keys_count;
  3521.     c->modifiers_so_far = lower_modifiers;
  3522.  
  3523.     lower = traverse_keymaps (submap, Qnil, where_is_recursive_mapper,
  3524.                   c);
  3525.     c->keys_count = keys_count;
  3526.     c->modifiers_so_far = modifiers_so_far;
  3527.  
  3528.     if (!firstonly)
  3529.       result = nconc2 (lower, result);
  3530.     else if (!NILP (lower))
  3531.       return (lower);
  3532.       }
  3533.     }
  3534.   return (result);
  3535. }
  3536.  
  3537.  
  3538. static Lisp_Object
  3539. where_is_internal (Lisp_Object definition, Lisp_Object *maps, int nmaps,
  3540.                    Lisp_Object firstonly, char *target_buffer)
  3541. {
  3542.   /* This function can GC */
  3543.   Lisp_Object result = Qnil;
  3544.   int i;
  3545.   struct key_data raw[20];
  3546.   struct where_is_closure c;
  3547.  
  3548.   c.definition = definition;
  3549.   c.shadow = maps;
  3550.   c.firstonly = !NILP (firstonly);
  3551.   c.target_buffer = target_buffer;
  3552.   c.keys_so_far = raw;
  3553.   c.keys_so_far_total_size = countof (raw);
  3554.   c.keys_so_far_malloced = 0;
  3555.  
  3556.   /* Loop over each of the maps, accumulating the keys found.
  3557.      For each map searched, all previous maps shadow this one
  3558.      so that bogus keys aren't listed. */
  3559.   for (i = 0; i < nmaps; i++)
  3560.     {
  3561.       Lisp_Object this_result;
  3562.       c.shadow_count = i;
  3563.       /* Reset the things set in each iteration */
  3564.       c.keys_count = 0;
  3565.       c.modifiers_so_far = 0;
  3566.  
  3567.       this_result = traverse_keymaps (maps[i], Qnil, where_is_recursive_mapper,
  3568.                       &c);
  3569.       if (!NILP (firstonly))
  3570.     {
  3571.       result = this_result;
  3572.       if (!NILP (result))
  3573.         break;
  3574.     }
  3575.       else
  3576.     result = nconc2 (this_result, result);
  3577.     }
  3578.  
  3579.   if (NILP (firstonly))
  3580.     result = Fnreverse (result);
  3581.  
  3582.   if (c.keys_so_far_malloced)
  3583.     xfree (c.keys_so_far);
  3584.   return (result);
  3585. }
  3586.  
  3587.  
  3588. /************************************************************************/
  3589. /*                         Describing keymaps                           */
  3590. /************************************************************************/
  3591.  
  3592. DEFUN ("describe-bindings-internal",
  3593.        Fdescribe_bindings_internal, Sdescribe_bindings_internal, 1, 5, 0,
  3594.   "Insert a list of all defined keys and their definitions in MAP.\n\
  3595. Optional second argument ALL says whether to include even \"uninteresting\"\n\
  3596. definitions (ie symbols with a non-nil `suppress-keymap' property.\n\
  3597. Third argument SHADOW is a list of keymaps whose bindings shadow those\n\
  3598. of map; if a binding is present in any shadowing map, it is not printed.\n\
  3599. Fourth argument PREFIX, if non-nil, should be a key sequence;\n\
  3600. only bindings which start with that key sequence will be printed.\n\
  3601. Fifth argument MOUSE-ONLY-P says to only print bindings for mouse clicks.")
  3602.   (map, all, shadow, prefix, mouse_only_p)
  3603.   Lisp_Object map, all, shadow, prefix, mouse_only_p;
  3604. {
  3605.   /* This function can GC */
  3606.   describe_map_tree (map, NILP (all), shadow, prefix,
  3607.              !NILP (mouse_only_p));
  3608.   return (Qnil);
  3609. }
  3610.  
  3611.  
  3612. /* Insert a desription of the key bindings in STARTMAP,
  3613.     followed by those of all maps reachable through STARTMAP.
  3614.    If PARTIAL is nonzero, omit certain "uninteresting" commands
  3615.     (such as `undefined').
  3616.    If SHADOW is non-nil, it is a list of other maps;
  3617.     don't mention keys which would be shadowed by any of them
  3618.    If PREFIX is non-nil, only list bindings which start with those keys
  3619.  */
  3620.  
  3621. void
  3622. describe_map_tree (Lisp_Object startmap, int partial, Lisp_Object shadow,
  3623.                    Lisp_Object prefix, int mice_only_p)
  3624. {
  3625.   /* This function can GC */
  3626.   Lisp_Object maps = Qnil;
  3627.   struct gcpro gcpro1, gcpro2;  /* get_keymap may autoload */
  3628.   GCPRO2 (maps, shadow);
  3629.  
  3630.   maps = Faccessible_keymaps (startmap, prefix);
  3631.  
  3632.   for (; !NILP (maps); maps = Fcdr (maps))
  3633.     {
  3634.       Lisp_Object sub_shadow = Qnil;
  3635.       Lisp_Object elt = Fcar (maps);
  3636.       Lisp_Object tail = shadow;
  3637.       int no_prefix = (VECTORP (Fcar (elt))
  3638.                        && XINT (Flength (Fcar (elt))) == 0);
  3639.       struct gcpro gcpro1, gcpro2, gcpro3;
  3640.       GCPRO3 (sub_shadow, elt, tail);
  3641.  
  3642.       for (; CONSP (tail); tail = XCDR (tail))
  3643.     {
  3644.       Lisp_Object sh = XCAR (tail);
  3645.  
  3646.       /* If the sequence by which we reach this keymap is zero-length,
  3647.          then the shadow maps for this keymap are just SHADOW.  */
  3648.       if (no_prefix)
  3649.         ;
  3650.       /* If the sequence by which we reach this keymap actually has
  3651.          some elements, then the sequence's definition in SHADOW is
  3652.          what we should use.  */
  3653.       else
  3654.         {
  3655.           sh = Flookup_key (sh, Fcar (elt), Qt);
  3656.           if (INTP (sh))
  3657.         sh = Qnil;
  3658.         }
  3659.  
  3660.       if (!NILP (sh))
  3661.         {
  3662.           Lisp_Object shm = get_keymap (sh, 0, 1);
  3663.           if (!KEYMAPP (shm))
  3664.         /* If sh is not nil and not a keymap, it completely shadows
  3665.            this map, so don't describe this map at all.  */
  3666.         goto SKIP;
  3667.           sub_shadow = Fcons (shm, sub_shadow);
  3668.         }
  3669.     }
  3670.  
  3671.       {
  3672.         /* Describe the contents of map MAP, assuming that this map
  3673.            itself is reached by the sequence of prefix keys KEYS (a vector).
  3674.            PARTIAL and SHADOW are as in `describe_map_tree'.  */
  3675.         Lisp_Object keysdesc
  3676.           = ((!no_prefix)
  3677.              ? concat2 (Fkey_description (Fcar (elt)), Vsingle_space_string)
  3678.              : Qnil);
  3679.         describe_map (Fcdr (elt), keysdesc,
  3680.                       describe_command,
  3681.                       partial,
  3682.                       sub_shadow,
  3683.                       mice_only_p);
  3684.       }
  3685.     SKIP:
  3686.       ;
  3687.     }
  3688.   UNGCPRO;
  3689. }
  3690.  
  3691.  
  3692. static void
  3693. describe_command (Lisp_Object definition)
  3694. {
  3695.   /* This function can GC */
  3696.   Lisp_Object buffer;
  3697.   int keymapp = !NILP (Fkeymapp (definition));
  3698.   struct gcpro gcpro1, gcpro2;
  3699.   GCPRO2 (definition, buffer);
  3700.  
  3701.   XSETBUFFER (buffer, current_buffer);
  3702.   Findent_to (make_number (16), make_number (3), buffer);
  3703.   if (keymapp)
  3704.     buffer_insert_c_string (XBUFFER (buffer), "<< ");
  3705.  
  3706.   if (SYMBOLP (definition))
  3707.     {
  3708.       buffer_insert1 (XBUFFER (buffer), Fsymbol_name (definition));
  3709.     }
  3710.   else if (STRINGP (definition) || VECTORP (definition))
  3711.     {
  3712.       buffer_insert_c_string (XBUFFER (buffer), "Kbd Macro: ");
  3713.       buffer_insert1 (XBUFFER (buffer), Fkey_description (definition));
  3714.     }
  3715.   else if (BYTECODEP (definition))
  3716.     buffer_insert_c_string (XBUFFER (buffer), "Anonymous Compiled Function");
  3717.   else if (CONSP (definition) && EQ (XCAR (definition), Qlambda))
  3718.     buffer_insert_c_string (XBUFFER (buffer), "Anonymous Lambda");
  3719.   else if (KEYMAPP (definition))
  3720.     {
  3721.       Lisp_Object name = XKEYMAP (definition)->name;
  3722.       if (STRINGP (name) || (SYMBOLP (name) && !NILP (name)))
  3723.     {
  3724.       buffer_insert_c_string (XBUFFER (buffer), "Prefix command ");
  3725.       if (SYMBOLP (name) 
  3726.           && EQ (find_symbol_value (name), definition))
  3727.         buffer_insert1 (XBUFFER (buffer), Fsymbol_name (name));
  3728.       else
  3729.         {
  3730.           buffer_insert1 (XBUFFER (buffer), Fprin1_to_string (name, Qnil));
  3731.         }
  3732.     }
  3733.       else
  3734.     buffer_insert_c_string (XBUFFER (buffer), "Prefix Command");
  3735.     }
  3736.   else
  3737.     buffer_insert_c_string (XBUFFER (buffer), "??");
  3738.  
  3739.   if (keymapp)
  3740.     buffer_insert_c_string (XBUFFER (buffer), " >>");
  3741.   buffer_insert_c_string (XBUFFER (buffer), "\n");
  3742.   UNGCPRO;
  3743. }
  3744.  
  3745. struct describe_map_closure
  3746.   {
  3747.     Lisp_Object *list;     /* pointer to the list to update */
  3748.     Lisp_Object partial; /* whether to ignore suppressed commands */
  3749.     Lisp_Object shadow;     /* list of maps shadowing this one */
  3750.     Lisp_Object self;     /* this map */
  3751.     Lisp_Object self_root; /* this map, or some map that has this map as
  3752.                               a parent.  this is the base of the tree */
  3753.     int mice_only_p;     /* whether we are to display only button bindings */
  3754.   };
  3755.  
  3756. struct describe_map_shadow_closure
  3757.   {
  3758.     CONST struct key_data *raw_key;
  3759.     Lisp_Object self;
  3760.   };
  3761.  
  3762. static Lisp_Object
  3763. describe_map_mapper_shadow_search (Lisp_Object map, void *arg)
  3764. {
  3765.   struct describe_map_shadow_closure *c = arg;
  3766.  
  3767.   if (EQ (map, c->self))
  3768.     return (Qzero);              /* Not shadowed; terminate search */
  3769.   else if (!NILP (keymap_lookup_directly (map,
  3770.                                           c->raw_key->keysym,
  3771.                                           c->raw_key->modifiers)))
  3772.     return (Qt);
  3773.   else
  3774.     return (Qnil);
  3775. }
  3776.      
  3777.  
  3778. static Lisp_Object
  3779. keymap_lookup_inherited_mapper (Lisp_Object km, void *arg)
  3780. {
  3781.   struct key_data *k = arg;
  3782.   return (keymap_lookup_directly (km, k->keysym, k->modifiers));
  3783. }
  3784.  
  3785.  
  3786. static void
  3787. describe_map_mapper (CONST struct key_data *key,
  3788.                      Lisp_Object binding,
  3789.              void *describe_map_closure)
  3790. {
  3791.   /* This function can GC */
  3792.   struct describe_map_closure *closure = describe_map_closure;
  3793.   Lisp_Object keysym = key->keysym;
  3794.   unsigned int modifiers = key->modifiers;
  3795.  
  3796.   /* Dont mention suppressed commands.  */
  3797.   if (SYMBOLP (binding)
  3798.       && !NILP (closure->partial)
  3799.       && !NILP (Fget (binding, closure->partial, Qnil)))
  3800.     return;
  3801.           
  3802.   /* If we're only supposed to display mouse bindings and this isn't one,
  3803.      then bug out. */
  3804.   if (closure->mice_only_p &&
  3805.       (! (EQ (keysym, Qbutton0) || EQ (keysym, Qbutton1)
  3806.           || EQ (keysym, Qbutton2) || EQ (keysym, Qbutton3)
  3807.           || EQ (keysym, Qbutton4) || EQ (keysym, Qbutton5)
  3808.           || EQ (keysym, Qbutton6) || EQ (keysym, Qbutton7))))
  3809.     return;
  3810.  
  3811.   /* If this command in this map is shadowed by some other map, ignore it. */
  3812.   {
  3813.     Lisp_Object tail;
  3814.  
  3815.     for (tail = closure->shadow; CONSP (tail); tail = XCDR (tail))
  3816.       {
  3817.     QUIT;
  3818.     if (!NILP (traverse_keymaps (XCAR (tail), Qnil,
  3819.                      keymap_lookup_inherited_mapper,
  3820.                      /* Cast to discard `const' */
  3821.                      (void *)key)))
  3822.       return;
  3823.       }
  3824.   }
  3825.  
  3826.   /* If this key is in some map of which this map is a parent, then ignore
  3827.      it (in that case, it has been shadowed).
  3828.      */
  3829.   {
  3830.     Lisp_Object sh;
  3831.     struct describe_map_shadow_closure c;
  3832.     c.raw_key = key;
  3833.     c.self = closure->self;
  3834.  
  3835.     sh = traverse_keymaps (closure->self_root, Qnil,
  3836.                            describe_map_mapper_shadow_search, &c);
  3837.     if (!NILP (sh) && !EQ (sh, Qzero))
  3838.       return;
  3839.   }
  3840.  
  3841.   /* Otherwise add it to the list to be sorted. */
  3842.   *(closure->list) = Fcons (Fcons (Fcons (keysym, make_number (modifiers)),
  3843.                                    binding),
  3844.                 *(closure->list));
  3845. }
  3846.  
  3847.  
  3848. static int
  3849. describe_map_sort_predicate (Lisp_Object obj1, Lisp_Object obj2, 
  3850.                  Lisp_Object pred)
  3851. {
  3852.   /* obj1 and obj2 are conses of the form
  3853.      ( ( <keysym> . <modifiers> ) . <binding> )
  3854.      keysym and modifiers are used, binding is ignored.
  3855.    */
  3856.   unsigned int bit1, bit2;
  3857.   obj1 = XCAR (obj1);
  3858.   obj2 = XCAR (obj2);
  3859.   bit1 = XINT (XCDR (obj1));
  3860.   bit2 = XINT (XCDR (obj2));
  3861.   if (bit1 != bit2)
  3862.     return ((bit1 < bit2) ? 1 : -1);
  3863.   else
  3864.     return map_keymap_sort_predicate (obj1, obj2, pred);
  3865. }
  3866.  
  3867. /* Elide 2 or more consecutive numeric keysyms bound to the same thing,
  3868.    or 2 or more symbolic keysyms that are bound to the same thing and
  3869.    have consecutive character-set-properties.
  3870.  */
  3871. static int
  3872. elide_next_two_p (Lisp_Object list)
  3873. {
  3874.   Lisp_Object s1, s2;
  3875.  
  3876.   if (NILP (XCDR (list)))
  3877.     return 0;
  3878.  
  3879.   /* next two bindings differ */
  3880.   if (!EQ (XCDR (XCAR (list)),
  3881.        XCDR (XCAR (XCDR (list)))))
  3882.     return 0;
  3883.  
  3884.   /* next two modifier-sets differ */
  3885.   if (!EQ (XCDR (XCAR (XCAR (list))),
  3886.        XCDR (XCAR (XCAR (XCDR (list))))))
  3887.     return 0;
  3888.  
  3889.   s1 = XCAR (XCAR (XCAR (list)));
  3890.   s2 = XCAR (XCAR (XCAR (XCDR (list))));
  3891.  
  3892.   if (SYMBOLP (s1))
  3893.     {
  3894.       Lisp_Object code = Fget (s1, Vcharacter_set_property, Qnil);
  3895.       if (INTP (code)) s1 = code;
  3896.       else return 0;
  3897.     }
  3898.   if (SYMBOLP (s2))
  3899.     {
  3900.       Lisp_Object code = Fget (s2, Vcharacter_set_property, Qnil);
  3901.       if (INTP (code)) s2 = code;
  3902.       else return 0;
  3903.     }
  3904.  
  3905.   if (XINT (s1) == XINT (s2) ||
  3906.       XINT (s1) + 1 == XINT (s2))
  3907.     return 1;
  3908.   return 0;
  3909. }
  3910.  
  3911.  
  3912. static Lisp_Object
  3913. describe_map_parent_mapper (Lisp_Object keymap, void *arg)
  3914. {
  3915.   /* This function can GC */
  3916.   struct describe_map_closure *describe_map_closure = arg;
  3917.   describe_map_closure->self = keymap;
  3918.   map_keymap (XKEYMAP (keymap)->table,
  3919.               0, /* don't sort: we'll do it later */
  3920.               describe_map_mapper, describe_map_closure);
  3921.   return (Qnil);
  3922. }
  3923.  
  3924.  
  3925. static void
  3926. describe_map (Lisp_Object keymap, Lisp_Object elt_prefix,
  3927.           void (*elt_describer) (Lisp_Object),
  3928.           int partial, 
  3929.           Lisp_Object shadow,
  3930.           int mice_only_p)
  3931. {
  3932.   /* This function can GC */
  3933.   struct describe_map_closure describe_map_closure;
  3934.   Lisp_Object list = Qnil;
  3935.   struct buffer *buf = current_buffer;
  3936.   int printable_min = (INTP (buf->ctl_arrow)
  3937.                ? XINT (buf->ctl_arrow)
  3938.                : ((EQ (buf->ctl_arrow, Qt)
  3939.                            || EQ (buf->ctl_arrow, Qnil))
  3940.               ? 256 : 160));
  3941.   int elided = 0;
  3942.   struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
  3943.  
  3944.   keymap = get_keymap (keymap, 1, 1);
  3945.   describe_map_closure.partial = (partial ? Qsuppress_keymap : Qnil);
  3946.   describe_map_closure.shadow = shadow;
  3947.   describe_map_closure.list = &list;
  3948.   describe_map_closure.self_root = keymap;
  3949.   describe_map_closure.mice_only_p = mice_only_p;
  3950.  
  3951.   GCPRO4 (keymap, elt_prefix, shadow, list);
  3952.  
  3953.   traverse_keymaps (keymap, Qnil,
  3954.                     describe_map_parent_mapper, &describe_map_closure);
  3955.  
  3956.   if (!NILP (list))
  3957.     {
  3958.       list = list_sort (list, Qnil, describe_map_sort_predicate);
  3959.       buffer_insert_c_string (buf, "\n");
  3960.       while (!NILP (list))
  3961.     {
  3962.           Lisp_Object elt = XCAR (XCAR (list));
  3963.       Lisp_Object keysym = XCAR (elt);
  3964.       unsigned int modifiers = XINT (XCDR (elt));
  3965.  
  3966.       if (!NILP (elt_prefix))
  3967.         buffer_insert_lisp_string (buf, elt_prefix);
  3968.  
  3969.       if (modifiers & MOD_META)    buffer_insert_c_string (buf, "M-");
  3970.       if (modifiers & MOD_CONTROL) buffer_insert_c_string (buf, "C-");
  3971.       if (modifiers & MOD_SUPER)   buffer_insert_c_string (buf, "S-");
  3972.       if (modifiers & MOD_HYPER)   buffer_insert_c_string (buf, "H-");
  3973.       if (modifiers & MOD_ALT)     buffer_insert_c_string (buf, "Alt-");
  3974.       if (modifiers & MOD_SHIFT)   buffer_insert_c_string (buf, "Sh-");
  3975.       if (SYMBOLP (keysym))
  3976.         {
  3977.           Lisp_Object code = Fget (keysym, Vcharacter_set_property, Qnil);
  3978.           Emchar c = (INTP (code) ? XINT (code) : -1);
  3979.           /* Calling Fsingle_key_description() would cons more */
  3980. #if 0                           /* This is bogus */
  3981.           if (EQ (keysym, QKlinefeed))
  3982.         buffer_insert_c_string (buf, "LFD");
  3983.           else if (EQ (keysym, QKtab))
  3984.         buffer_insert_c_string (buf, "TAB");
  3985.           else if (EQ (keysym, QKreturn))
  3986.         buffer_insert_c_string (buf, "RET");
  3987.           else if (EQ (keysym, QKescape))
  3988.         buffer_insert_c_string (buf, "ESC");
  3989.           else if (EQ (keysym, QKdelete))
  3990.         buffer_insert_c_string (buf, "DEL");
  3991.           else if (EQ (keysym, QKspace))
  3992.         buffer_insert_c_string (buf, "SPC");
  3993.           else if (EQ (keysym, QKbackspace))
  3994.         buffer_insert_c_string (buf, "BS");
  3995.           else 
  3996. #endif
  3997.                 if (c >= printable_min)     buffer_insert_emacs_char (buf, c);
  3998.         else buffer_insert1 (buf, Fsymbol_name (keysym));
  3999.         }
  4000.       else if (INTP (keysym))
  4001.         buffer_insert_emacs_char (buf, XINT (keysym));
  4002.       else
  4003.         buffer_insert_c_string (buf, "---bad keysym---");
  4004.  
  4005.       if (elided)
  4006.         elided = 0;
  4007.       else
  4008.         {
  4009.           int k = 0;
  4010.  
  4011.           while (elide_next_two_p (list))
  4012.         {
  4013.           k++;
  4014.           list = XCDR (list);
  4015.         }
  4016.           if (k != 0)
  4017.         {
  4018.           if (k == 1)
  4019.             buffer_insert_c_string (buf, ", ");
  4020.           else
  4021.             buffer_insert_c_string (buf, " .. ");
  4022.           elided = 1;
  4023.           continue;
  4024.         }
  4025.         }
  4026.  
  4027.       /* Print a description of the definition of this character.  */
  4028.       (*elt_describer) (XCDR (XCAR (list)));
  4029.       list = XCDR (list);
  4030.     }
  4031.     }
  4032.   UNGCPRO;
  4033. }
  4034.  
  4035.  
  4036. void
  4037. syms_of_keymap (void)
  4038. {
  4039.   defsymbol (&Qminor_mode_map_alist, "minor-mode-map-alist");
  4040.  
  4041.   defsymbol (&Qkeymap, "keymap");
  4042.   defsymbol (&Qkeymapp, "keymapp");
  4043.  
  4044.   defsymbol (&Qsuppress_keymap, "suppress-keymap");
  4045.  
  4046.   defsymbol (&Qmodeline_map, "modeline-map");
  4047.   defsymbol (&Qtoolbar_map, "toolbar-map");
  4048.  
  4049.   defsubr (&Skeymap_parents);
  4050.   defsubr (&Sset_keymap_parents);
  4051. /*defsubr (&Skeymap_name); */
  4052.   defsubr (&Sset_keymap_name);
  4053.   defsubr (&Skeymap_prompt);
  4054.   defsubr (&Sset_keymap_prompt);
  4055.   defsubr (&Skeymap_default_binding);
  4056.   defsubr (&Sset_keymap_default_binding);
  4057.  
  4058.   defsubr (&Skeymapp);
  4059.   defsubr (&Smake_keymap);
  4060.   defsubr (&Smake_sparse_keymap);
  4061.  
  4062.   defsubr (&Scopy_keymap);
  4063.   defsubr (&Skeymap_fullness);
  4064.   defsubr (&Smap_keymap);
  4065.   defsubr (&Sevent_matches_key_specifier_p);
  4066.   defsubr (&Sdefine_key);
  4067.   defsubr (&Slookup_key);
  4068.   defsubr (&Skey_binding);
  4069.   defsubr (&Suse_global_map);
  4070.   defsubr (&Suse_local_map);
  4071.   defsubr (&Scurrent_local_map);
  4072.   defsubr (&Scurrent_global_map);
  4073.   defsubr (&Scurrent_keymaps);
  4074.   defsubr (&Saccessible_keymaps);
  4075.   defsubr (&Skey_description);
  4076.   defsubr (&Ssingle_key_description);
  4077.   defsubr (&Swhere_is_internal);
  4078.   defsubr (&Sdescribe_bindings_internal);
  4079.  
  4080.   defsubr (&Stext_char_description);
  4081.  
  4082.   defsymbol (&Qcontrol, "control");
  4083.   defsymbol (&Qctrl, "ctrl");
  4084.   defsymbol (&Qmeta, "meta"); 
  4085.   defsymbol (&Qsuper, "super"); 
  4086.   defsymbol (&Qhyper, "hyper"); 
  4087.   defsymbol (&Qalt, "alt");
  4088.   defsymbol (&Qshift, "shift");
  4089.   defsymbol (&Qbutton0, "button0");
  4090.   defsymbol (&Qbutton1, "button1");
  4091.   defsymbol (&Qbutton2, "button2");
  4092.   defsymbol (&Qbutton3, "button3");
  4093.   defsymbol (&Qbutton4, "button4");
  4094.   defsymbol (&Qbutton5, "button5");
  4095.   defsymbol (&Qbutton6, "button6");
  4096.   defsymbol (&Qbutton7, "button7");
  4097.   defsymbol (&Qbutton0up, "button0up");
  4098.   defsymbol (&Qbutton1up, "button1up");
  4099.   defsymbol (&Qbutton2up, "button2up");
  4100.   defsymbol (&Qbutton3up, "button3up");
  4101.   defsymbol (&Qbutton4up, "button4up");
  4102.   defsymbol (&Qbutton5up, "button5up");
  4103.   defsymbol (&Qbutton6up, "button6up");
  4104.   defsymbol (&Qbutton7up, "button7up");
  4105.   defsymbol (&Qmenu_selection, "menu-selection");
  4106.   defsymbol (&QLFD, "LFD");
  4107.   defsymbol (&QTAB, "TAB");
  4108.   defsymbol (&QRET, "RET");
  4109.   defsymbol (&QESC, "ESC");
  4110.   defsymbol (&QDEL, "DEL");
  4111.   defsymbol (&QBS, "BS");
  4112. }
  4113.  
  4114. void
  4115. vars_of_keymap (void)
  4116. {
  4117.   DEFVAR_LISP ("meta-prefix-char", &Vmeta_prefix_char,
  4118.     "Meta-prefix character.\n\
  4119. This character followed by some character `foo' turns into `Meta-foo'.\n\
  4120. This can be any form recognized as a single key specifier.\n\
  4121. To disable the meta-prefix-char, set it to a negative number.");
  4122.   Vmeta_prefix_char = make_number (033);
  4123.  
  4124.   DEFVAR_LISP ("mouse-grabbed-buffer", &Vmouse_grabbed_buffer,
  4125.   "A buffer which should be consulted first for all mouse activity.\n\
  4126. When a mouse-clicked it processed, it will first be looked up in the\n\
  4127. local-map of this buffer, and then through the normal mechanism if there\n\
  4128. is no binding for that click.  This buffer's value of `mode-motion-hook'\n\
  4129. will be consulted instead of the `mode-motion-hook' of the buffer of the\n\
  4130. window under the mouse.  You should *bind* this, not set it.");
  4131.   Vmouse_grabbed_buffer = Qnil;
  4132.  
  4133.   /* defsymbol (&Qoverriding_local_map, "overriding-local-map"); */
  4134.   DEFVAR_LISP ("overriding-local-map", &Voverriding_local_map,
  4135.     "Keymap that overrides all other local keymaps.\n\
  4136. If this variable is non-nil, it is used as a keymap instead of the\n\
  4137. buffer's local map, and the minor mode keymaps and extent-local keymaps.\n\
  4138. You should *bind* this, not set it.");
  4139.   Voverriding_local_map = Qnil;
  4140.  
  4141.   Fset (Qminor_mode_map_alist, Qnil);
  4142.  
  4143.   DEFVAR_INT ("keymap-tick", &keymap_tick,
  4144.           "Incremented for each change to any keymap.");
  4145.   keymap_tick = 0;
  4146.  
  4147.   staticpro (&Vcurrent_global_map);
  4148.  
  4149.   Vsingle_space_string = make_pure_string ((Bufbyte *) " ", 1, 1);
  4150.   staticpro (&Vsingle_space_string);
  4151. }
  4152.  
  4153. void
  4154. complex_vars_of_keymap (void)
  4155. {
  4156.   /* This function can GC */
  4157.   Lisp_Object ESC_prefix = intern ("ESC-prefix");
  4158.   Lisp_Object meta_disgustitute;
  4159.  
  4160.   Vcurrent_global_map = Fmake_keymap ();
  4161.  
  4162.   meta_disgustitute = Fmake_keymap ();
  4163.   Ffset (ESC_prefix, meta_disgustitute);
  4164.   /* no need to protect meta_disgustitute, though */
  4165.   keymap_store_internal (MAKE_MODIFIER_HASH_KEY (MOD_META),
  4166.                          XKEYMAP (Vcurrent_global_map),
  4167.                          meta_disgustitute);
  4168.   XKEYMAP (Vcurrent_global_map)->sub_maps_cache = Qt;
  4169. }
  4170.