[BACK]Return to keymap.c CVS log [TXT][DIR] Up to [local] / src / usr.bin / mg

Annotation of src/usr.bin/mg/keymap.c, Revision 1.1

1.1     ! deraadt     1: /*
        !             2:  * Keyboard maps.  This is character set dependent.
        !             3:  * The terminal specific parts of building the
        !             4:  * keymap has been moved to a better place.
        !             5:  */
        !             6: #include       "def.h"
        !             7: #include       "kbd.h"
        !             8:
        !             9: /*
        !            10:  * Defined by "basic.c".
        !            11:  */
        !            12: extern int     gotobol();              /* Move to start of line        */
        !            13: extern int     backchar();             /* Move backward by characters  */
        !            14: extern int     gotoeol();              /* Move to end of line          */
        !            15: extern int     forwchar();             /* Move forward by characters   */
        !            16: extern int     gotobob();              /* Move to start of buffer      */
        !            17: extern int     gotoeob();              /* Move to end of buffer        */
        !            18: extern int     forwline();             /* Move forward by lines        */
        !            19: extern int     backline();             /* Move backward by lines       */
        !            20: extern int     forwpage();             /* Move forward by pages        */
        !            21: extern int     backpage();             /* Move backward by pages       */
        !            22: extern int     pagenext();             /* Page forward next window     */
        !            23: extern int     setmark();              /* Set mark                     */
        !            24: extern int     swapmark();             /* Swap "." and mark            */
        !            25: extern int     gotoline();             /* Go to a specified line.      */
        !            26: #ifdef GOSMACS
        !            27: extern int     forw1page();            /* move forward by lines        */
        !            28: extern int     back1page();            /* move back by lines           */
        !            29: #endif
        !            30:
        !            31: /*
        !            32:  * Defined by "buffer.c".
        !            33:  */
        !            34: extern int     listbuffers();          /* Display list of buffers      */
        !            35: extern int     usebuffer();            /* Switch a window to a buffer  */
        !            36: extern int     poptobuffer();          /* Other window to a buffer     */
        !            37: extern int     killbuffer();           /* Make a buffer go away.       */
        !            38: extern int     savebuffers();          /* Save unmodified buffers      */
        !            39: extern int     bufferinsert();         /* Insert buffer into another   */
        !            40: extern int     notmodified();          /* Reset modification flag      */
        !            41:
        !            42: #ifndef NO_DIR
        !            43: /*
        !            44:  * Defined by "dir.c"
        !            45:  */
        !            46: extern int     changedir();            /* change current directory     */
        !            47: extern int     showcwdir();            /* show current directory       */
        !            48:
        !            49: #ifndef NO_DIRED
        !            50: /*
        !            51:  * defined by "dired.c"
        !            52:  */
        !            53: extern int     dired();                /* dired                        */
        !            54: extern int     d_findfile();           /* dired find file              */
        !            55: extern int     d_del();                /* dired mark for deletion      */
        !            56: extern int     d_undel();              /* dired unmark                 */
        !            57: extern int     d_undelbak();           /* dired unmark backwards       */
        !            58: extern int     d_expunge();            /* dired expunge                */
        !            59: extern int     d_copy();               /* dired copy                   */
        !            60: extern int     d_rename();             /* dired rename                 */
        !            61: extern int     d_otherwindow();        /* dired other window           */
        !            62: extern int     d_ffotherwindow();      /* dired find file other window */
        !            63: #endif
        !            64: #endif
        !            65:
        !            66: /*
        !            67:  * Defined by "extend.c".
        !            68:  */
        !            69: extern int     extend();               /* Extended commands.           */
        !            70: extern int     bindtokey();            /* Modify global key bindings.  */
        !            71: extern int     localbind();            /* Modify mode key bindings.    */
        !            72: extern int     define_key();           /* modify any key map           */
        !            73: extern int     unbindtokey();          /* delete global binding        */
        !            74: extern int     localunbind();          /* delete local binding         */
        !            75: extern int     insert();               /* insert string                */
        !            76: #ifndef NO_STARTUP
        !            77: extern int     evalexpr();             /* Extended commands (again)    */
        !            78: extern int     evalbuffer();           /* Evaluate current buffer      */
        !            79: extern int     evalfile();             /* Evaluate a file              */
        !            80: #endif
        !            81:
        !            82: /*
        !            83:  * Defined by "file.c".
        !            84:  */
        !            85: extern int     filevisit();            /* Get a file, read write       */
        !            86: extern int     poptofile();            /* Get a file, other window     */
        !            87: extern int     filewrite();            /* Write a file                 */
        !            88: extern int     filesave();             /* Save current file            */
        !            89: extern int     fileinsert();           /* Insert file into buffer      */
        !            90: #ifndef NO_BACKUP
        !            91: extern int     makebkfile();           /* Control backups on saves     */
        !            92: #endif
        !            93:
        !            94: /*
        !            95:  * defined by help.c
        !            96:  */
        !            97: #ifndef NO_HELP
        !            98: extern int     desckey();              /* describe key                 */
        !            99: extern int     wallchart();            /* Make wall chart.             */
        !           100: extern int     help_help();            /* help help                    */
        !           101: extern int     apropos_command();      /* apropos                      */
        !           102: #endif
        !           103:
        !           104: /*
        !           105:  * defined by "kbd.c"
        !           106:  */
        !           107: #ifdef DO_METAKEY
        !           108: extern int     do_meta();              /* interpret meta keys          */
        !           109: #endif
        !           110: #ifdef BSMAP
        !           111: extern int     bsmap();                /* backspace mapping            */
        !           112: #endif
        !           113: extern int     universal_argument();   /* Ctrl-U                       */
        !           114: extern int     digit_argument();       /* M-1, etc.                    */
        !           115: extern int     negative_argument();    /* M--                          */
        !           116: extern int     selfinsert();           /* Insert character             */
        !           117: extern int     rescan();               /* internal try again function  */
        !           118:
        !           119: /*
        !           120:  * defined by "macro.c"
        !           121:  */
        !           122: #ifndef NO_MACRO
        !           123: extern int     definemacro();          /* Begin macro                  */
        !           124: extern int     finishmacro();          /* End macro                    */
        !           125: extern int     executemacro();         /* Execute macro                */
        !           126: #endif
        !           127:
        !           128: /*
        !           129:  * Defined by "main.c".
        !           130:  */
        !           131: extern int     ctrlg();                /* Abort out of things          */
        !           132: extern int     quit();                 /* Quit                         */
        !           133:
        !           134: /*
        !           135:  * Defined by "match.c"
        !           136:  */
        !           137: extern int     showmatch();            /* Hack to show matching paren   */
        !           138:
        !           139: /* defined by "modes.c" */
        !           140:
        !           141: extern int     indentmode();           /* set auto-indent mode         */
        !           142: extern int     fillmode();             /* set word-wrap mode           */
        !           143: extern int     blinkparen();           /* Fake blink-matching-paren var */
        !           144: #ifdef NOTAB
        !           145: extern int     notabmode();            /* no tab mode                  */
        !           146: #endif
        !           147: extern int     overwrite();            /* overwrite mode               */
        !           148: extern int     set_default_mode();     /* set default modes            */
        !           149:
        !           150: /*
        !           151:  * defined by "paragraph.c" - the paragraph justification code.
        !           152:  */
        !           153: extern int     gotobop();              /* Move to start of paragraph.  */
        !           154: extern int     gotoeop();              /* Move to end of paragraph.    */
        !           155: extern int     fillpara();             /* Justify a paragraph.         */
        !           156: extern int     killpara();             /* Delete a paragraph.          */
        !           157: extern int     setfillcol();           /* Set fill column for justify. */
        !           158: extern int     fillword();             /* Insert char with word wrap.  */
        !           159:
        !           160: /*
        !           161:  * Defined by "random.c".
        !           162:  */
        !           163: extern int     showcpos();             /* Show the cursor position     */
        !           164: extern int     twiddle();              /* Twiddle characters           */
        !           165: extern int     quote();                /* Insert literal               */
        !           166: extern int     openline();             /* Open up a blank line         */
        !           167: extern int     newline();              /* Insert newline               */
        !           168: extern int     deblank();              /* Delete blank lines           */
        !           169: extern int     justone();              /* Delete extra whitespace      */
        !           170: extern int     delwhite();             /* Delete all whitespace        */
        !           171: extern int     indent();               /* Insert newline, then indent  */
        !           172: extern int     forwdel();              /* Forward delete               */
        !           173: extern int     backdel();              /* Backward delete in           */
        !           174: extern int     killline();             /* Kill forward                 */
        !           175: extern int     yank();                 /* Yank back from killbuffer.   */
        !           176: #ifdef NOTAB
        !           177: extern int     space_to_tabstop();
        !           178: #endif
        !           179:
        !           180: #ifdef REGEX
        !           181: /*
        !           182:  * Defined by "re_search.c"
        !           183:  */
        !           184: extern int     re_forwsearch();        /* Regex search forward          */
        !           185: extern int     re_backsearch();        /* Regex search backwards        */
        !           186: extern int     re_searchagain();       /* Repeat regex search command   */
        !           187: extern int     re_queryrepl();         /* Regex query replace           */
        !           188: extern int     setcasefold();          /* Set case fold in searches     */
        !           189: extern int     delmatchlines();        /* Delete all lines matching     */
        !           190: extern int     delnonmatchlines();     /* Delete all lines not matching */
        !           191: extern int     cntmatchlines();        /* Count matching lines          */
        !           192: extern int     cntnonmatchlines();     /* Count nonmatching lines       */
        !           193: #endif
        !           194:
        !           195: /*
        !           196:  * Defined by "region.c".
        !           197:  */
        !           198: extern int     killregion();           /* Kill region.                 */
        !           199: extern int     copyregion();           /* Copy region to kill buffer.  */
        !           200: extern int     lowerregion();          /* Lower case region.           */
        !           201: extern int     upperregion();          /* Upper case region.           */
        !           202: #ifdef PREFIXREGION
        !           203: extern int     prefixregion();         /* Prefix all lines in region   */
        !           204: extern int     setprefix();            /* Set line prefix string       */
        !           205: #endif
        !           206:
        !           207: /*
        !           208:  * Defined by "search.c".
        !           209:  */
        !           210: extern int     forwsearch();           /* Search forward               */
        !           211: extern int     backsearch();           /* Search backwards             */
        !           212: extern int     searchagain();          /* Repeat last search command   */
        !           213: extern int     forwisearch();          /* Incremental search forward   */
        !           214: extern int     backisearch();          /* Incremental search backwards */
        !           215: extern int     queryrepl();            /* Query replace                */
        !           216:
        !           217: /*
        !           218:  * Defined by "spawn.c".
        !           219:  */
        !           220: extern int     spawncli();             /* Run CLI in a subjob.         */
        !           221: extern int     attachtoparent();       /* Attach to parent process     */
        !           222:
        !           223: /* defined by "version.c" */
        !           224:
        !           225: extern int     showversion();          /* Show version numbers, etc.   */
        !           226:
        !           227: /*
        !           228:  * Defined by "window.c".
        !           229:  */
        !           230: extern int     reposition();           /* Reposition window            */
        !           231: extern int     refresh();              /* Refresh the screen           */
        !           232: extern int     nextwind();             /* Move to the next window      */
        !           233: #ifdef GOSMACS
        !           234: extern int     prevwind();             /* Move to the previous window  */
        !           235: #endif
        !           236: extern int     onlywind();             /* Make current window only one */
        !           237: extern int     splitwind();            /* Split current window         */
        !           238: extern int     delwind();              /* Delete current window        */
        !           239: extern int     enlargewind();          /* Enlarge display window.      */
        !           240: extern int     shrinkwind();           /* Shrink window.               */
        !           241:
        !           242: /*
        !           243:  * Defined by "word.c".
        !           244:  */
        !           245: extern int     backword();             /* Backup by words              */
        !           246: extern int     forwword();             /* Advance by words             */
        !           247: extern int     upperword();            /* Upper case word.             */
        !           248: extern int     lowerword();            /* Lower case word.             */
        !           249: extern int     capword();              /* Initial capitalize word.     */
        !           250: extern int     delfword();             /* Delete forward word.         */
        !           251: extern int     delbword();             /* Delete backward word.        */
        !           252:
        !           253: #ifdef AMIGA
        !           254: #ifdef DO_ICONIFY
        !           255: extern int tticon();
        !           256: #endif
        !           257: #ifdef DO_MENU
        !           258: extern int     amigamenu();            /* Menu function                */
        !           259: #endif
        !           260: #ifdef MOUSE
        !           261: extern int     amigamouse();           /* Amiga mouse functions        */
        !           262: extern int     mgotobob();
        !           263: extern int     mforwdel();
        !           264: extern int     mdelwhite();
        !           265: extern int     mdelwind();
        !           266: extern int     mgotoeob();
        !           267: extern int     menlargewind();
        !           268: extern int     mkillline();
        !           269: extern int     mkillregion();
        !           270: extern int     mdelfword();
        !           271: extern int     mreposition();
        !           272: extern int     mbackpage();
        !           273: extern int     mforwpage();
        !           274: extern int     mshrinkwind();
        !           275: extern int     msplitwind();
        !           276: extern int     myank();
        !           277: #endif MOUSE
        !           278:
        !           279: extern int     togglewindow();         /* Defined by "ttyio.c"         */
        !           280: extern int     togglezooms();          /*    ""         ""             */
        !           281:
        !           282: #ifdef CHANGE_FONT
        !           283: extern int     setfont();              /* Defined by "ttyio.c"         */
        !           284: #endif
        !           285:
        !           286: #ifdef CHANGE_COLOR
        !           287:        /* functions to mess with the mode line rendition, window colors*/
        !           288: extern int     ttmode();               /* Defined by "tty.c"           */
        !           289: extern int     tttext();               /*  ""                          */
        !           290: extern int     textforeground();       /*  ""                          */
        !           291: extern int     textbackground();       /*  ""                          */
        !           292: extern int     modeforeground();       /*  ""                          */
        !           293: extern int     modebackground();       /*  ""                          */
        !           294: #endif
        !           295:
        !           296: /*
        !           297:  * This file contains map segment definitions for adding function keys to
        !           298:  * keymap declarations.  Currently you can add things to the fundamental
        !           299:  * mode keymap and the dired mode keymap.  See the declaration of
        !           300:  * diredmap and fundmap for details.
        !           301:  */
        !           302: #include "amiga_maps.c"
        !           303:
        !           304: #endif /* AMIGA */
        !           305:
        !           306: /* initial keymap declarations, deepest first */
        !           307:
        !           308: #ifndef NO_HELP
        !           309: static PF      cHcG[] = {
        !           310:        ctrlg,          /* ^G */
        !           311:        help_help,      /* ^H */
        !           312: };
        !           313: static PF      cHa[]   = {
        !           314:        apropos_command,/* a */
        !           315:        wallchart,      /* b */
        !           316:        desckey,        /* c */
        !           317: };
        !           318: static struct  KEYMAPE(2+IMAPEXT)      helpmap = {
        !           319:        2,
        !           320:        2+IMAPEXT,
        !           321:        rescan,
        !           322:        {
        !           323:                {CCHR('G'),CCHR('H'),   cHcG,   (KEYMAP *)NULL},
        !           324:                {'a',   'c',            cHa,    (KEYMAP *)NULL},
        !           325:        }
        !           326: };
        !           327: #endif
        !           328:
        !           329: static struct  KEYMAPE(1+IMAPEXT)      extramap1 = {
        !           330:        0,
        !           331:        1+IMAPEXT,
        !           332:        rescan
        !           333: };
        !           334:
        !           335: static struct  KEYMAPE(1+IMAPEXT)      extramap2 = {
        !           336:        0,
        !           337:        1+IMAPEXT,
        !           338:        rescan
        !           339: };
        !           340:
        !           341: static struct  KEYMAPE(1+IMAPEXT)      extramap3 = {
        !           342:        0,
        !           343:        1+IMAPEXT,
        !           344:        rescan
        !           345: };
        !           346:
        !           347: static struct  KEYMAPE(1+IMAPEXT)      extramap4 = {
        !           348:        0,
        !           349:        1+IMAPEXT,
        !           350:        rescan
        !           351: };
        !           352:
        !           353: static struct  KEYMAPE(1+IMAPEXT)      extramap5 = {
        !           354:        0,
        !           355:        1+IMAPEXT,
        !           356:        rescan
        !           357: };
        !           358:
        !           359: static PF      cX4cF[] = {
        !           360:        poptofile,      /* ^f */
        !           361:        ctrlg,          /* ^g */
        !           362: };
        !           363: static PF      cX4b[] = {
        !           364:        poptobuffer,    /* b */
        !           365:        rescan,         /* c */
        !           366:        rescan,         /* d */
        !           367:        rescan,         /* e */
        !           368:        poptofile,      /* f */
        !           369: };
        !           370: static struct  KEYMAPE(2+IMAPEXT)      cX4map  = {
        !           371:        2,
        !           372:        2+IMAPEXT,
        !           373:        rescan,
        !           374:        {
        !           375:                {CCHR('F'),CCHR('G'),   cX4cF,  (KEYMAP *)NULL},
        !           376:                {'b',   'f',            cX4b,   (KEYMAP *)NULL},
        !           377:        }
        !           378: };
        !           379:
        !           380: static PF      cXcB[] = {
        !           381:        listbuffers,    /* ^B */
        !           382:        quit,           /* ^C */
        !           383:        rescan,         /* ^D */
        !           384:        rescan,         /* ^E */
        !           385:        filevisit,      /* ^F */
        !           386:        ctrlg,          /* ^G */
        !           387: };
        !           388: static PF      cXcL[] = {
        !           389:        lowerregion,    /* ^L */
        !           390:        rescan,         /* ^M */
        !           391:        rescan,         /* ^N */
        !           392:        deblank,        /* ^O */
        !           393:        rescan,         /* ^P */
        !           394:        rescan,         /* ^Q */
        !           395:        rescan,         /* ^R */
        !           396:        filesave,       /* ^S */
        !           397:        rescan,         /* ^T */
        !           398:        upperregion,    /* ^U */
        !           399:        rescan,         /* ^V */
        !           400:        filewrite,      /* ^W */
        !           401:        swapmark,       /* ^X */
        !           402: };
        !           403: #ifndef NO_MACRO
        !           404: static PF      cXlp[]  = {
        !           405:        definemacro,    /* ( */
        !           406:        finishmacro,    /* ) */
        !           407: };
        !           408: #endif
        !           409: static PF      cX0[]   = {
        !           410:        delwind,        /* 0 */
        !           411:        onlywind,       /* 1 */
        !           412:        splitwind,      /* 2 */
        !           413:        rescan,         /* 3 */
        !           414:        prefix,         /* 4 */
        !           415: };
        !           416: static PF      cXeq[]  = {
        !           417:        showcpos,       /* = */
        !           418: };
        !           419: static PF      cXcar[] = {
        !           420:        enlargewind,    /* ^ */
        !           421:        rescan,         /* _ */
        !           422:        rescan,         /* ` */
        !           423:        rescan,         /* a */
        !           424:        usebuffer,      /* b */
        !           425:        rescan,         /* c */
        !           426: #ifndef NO_DIRED
        !           427:        dired,          /* d */
        !           428: #else
        !           429:        rescan,         /* d */
        !           430: #endif
        !           431: #ifndef NO_MACRO
        !           432:        executemacro,   /* e */
        !           433: #else
        !           434:        rescan,         /* e */
        !           435: #endif
        !           436:        setfillcol,     /* f */
        !           437:        rescan,         /* g */
        !           438:        rescan,         /* h */
        !           439:        fileinsert,     /* i */
        !           440:        rescan,         /* j */
        !           441:        killbuffer,     /* k */
        !           442:        rescan,         /* l */
        !           443:        rescan,         /* m */
        !           444:        rescan,         /* n */
        !           445:        nextwind,       /* o */
        !           446:        rescan,         /* p */
        !           447:        rescan,         /* q */
        !           448:        rescan,         /* r */
        !           449:        savebuffers,    /* s */
        !           450: };
        !           451: #ifndef NO_MACRO
        !           452: static struct  KEYMAPE(6+IMAPEXT)      cXmap = {
        !           453:        6,
        !           454:        6+IMAPEXT,
        !           455: #else
        !           456: static struct  KEYMAPE(5+IMAPEXT)      cXmap = {
        !           457:        5,
        !           458:        5+IMAPEXT,
        !           459: #endif
        !           460:        rescan,
        !           461:        {
        !           462:                {CCHR('B'),CCHR('G'),   cXcB,   (KEYMAP *)NULL},
        !           463:                {CCHR('L'),CCHR('X'),   cXcL,   (KEYMAP *)NULL},
        !           464: #ifndef NO_MACRO
        !           465:                {'(',   ')',            cXlp,   (KEYMAP *)NULL},
        !           466: #endif
        !           467:                {'0',   '4',            cX0,    (KEYMAP *)&cX4map},
        !           468:                {'=',   '=',            cXeq,   (KEYMAP *)NULL},
        !           469:                {'^',   's',            cXcar,  (KEYMAP *)NULL},
        !           470:        }
        !           471: };
        !           472:
        !           473: static PF      metacG[] = {
        !           474:        ctrlg,          /* ^G */
        !           475: };
        !           476: static PF      metacV[] = {
        !           477:        pagenext,       /* ^V */
        !           478: };
        !           479: static PF      metasp[] = {
        !           480:        justone,        /* space */
        !           481: };
        !           482: static PF      metapct[] = {
        !           483:        queryrepl,      /* % */
        !           484: };
        !           485: static PF      metami[] = {
        !           486:        negative_argument,      /* - */
        !           487:        rescan,         /* . */
        !           488:        rescan,         /* / */
        !           489:        digit_argument, /* 0 */
        !           490:        digit_argument, /* 1 */
        !           491:        digit_argument, /* 2 */
        !           492:        digit_argument, /* 3 */
        !           493:        digit_argument, /* 4 */
        !           494:        digit_argument, /* 5 */
        !           495:        digit_argument, /* 6 */
        !           496:        digit_argument, /* 7 */
        !           497:        digit_argument, /* 8 */
        !           498:        digit_argument, /* 9 */
        !           499:        rescan,         /* : */
        !           500:        rescan,         /* ; */
        !           501:        gotobob,        /* < */
        !           502:        rescan,         /* = */
        !           503:        gotoeob,        /* > */
        !           504: };
        !           505: static PF      metalb[] = {
        !           506:        gotobop,        /* [ */
        !           507:        delwhite,       /* \ */
        !           508:        gotoeop,        /* ] */
        !           509:        rescan,         /* ^ */
        !           510:        rescan,         /* _ */
        !           511:        rescan,         /* ` */
        !           512:        rescan,         /* a */
        !           513:        backword,       /* b */
        !           514:        capword,        /* c */
        !           515:        delfword,       /* d */
        !           516:        rescan,         /* e */
        !           517:        forwword,       /* f */
        !           518: };
        !           519: static PF      metal[] = {
        !           520:        lowerword,      /* l */
        !           521:        rescan,         /* m */
        !           522:        rescan,         /* n */
        !           523:        rescan,         /* o */
        !           524:        rescan,         /* p */
        !           525:        fillpara,       /* q */
        !           526:        backsearch,     /* r */
        !           527:        forwsearch,     /* s */
        !           528:        rescan,         /* t */
        !           529:        upperword,      /* u */
        !           530:        backpage,       /* v */
        !           531:        copyregion,     /* w */
        !           532:        extend,         /* x */
        !           533: };
        !           534: static PF      metatilde[] = {
        !           535:        notmodified,    /* ~ */
        !           536:        delbword,       /* DEL */
        !           537: };
        !           538: static struct  KEYMAPE(8+IMAPEXT)      metamap = {
        !           539:        8,
        !           540:        8+IMAPEXT,
        !           541:        rescan,
        !           542:        {
        !           543:                {CCHR('G'),CCHR('G'),   metacG, (KEYMAP *)NULL},
        !           544:                {CCHR('V'),CCHR('V'),   metacV, (KEYMAP *)NULL},
        !           545:                {' ',   ' ',            metasp, (KEYMAP *)NULL},
        !           546:                {'%',   '%',            metapct,(KEYMAP *)NULL},
        !           547:                {'-',   '>',            metami, (KEYMAP *)NULL},
        !           548:                {'[',   'f',            metalb, (KEYMAP *)NULL},
        !           549:                {'l',   'x',            metal,  (KEYMAP *)NULL},
        !           550:                {'~',   CCHR('?'),      metatilde,(KEYMAP *)NULL},
        !           551:        }
        !           552: };
        !           553:
        !           554: static PF      fund_at[] = {
        !           555:        setmark,        /* ^@ */
        !           556:        gotobol,        /* ^A */
        !           557:        backchar,       /* ^B */
        !           558:        rescan,         /* ^C */
        !           559:        forwdel,        /* ^D */
        !           560:        gotoeol,        /* ^E */
        !           561:        forwchar,       /* ^F */
        !           562:        ctrlg,          /* ^G */
        !           563: #ifndef NO_HELP
        !           564:        prefix,         /* ^H */
        !           565: #else
        !           566:        rescan,         /* ^H */
        !           567: #endif
        !           568: };
        !           569: /* ^I is selfinsert */
        !           570: static PF      fund_CJ[] = {
        !           571:        indent,         /* ^J */
        !           572:        killline,       /* ^K */
        !           573:        reposition,     /* ^L */
        !           574:        newline,        /* ^M */
        !           575:        forwline,       /* ^N */
        !           576:        openline,       /* ^O */
        !           577:        backline,       /* ^P */
        !           578:        quote,          /* ^Q */
        !           579:        backisearch,    /* ^R */
        !           580:        forwisearch,    /* ^S */
        !           581:        twiddle,        /* ^T */
        !           582:        universal_argument,     /* ^U */
        !           583:        forwpage,       /* ^V */
        !           584:        killregion,     /* ^W */
        !           585:        prefix,         /* ^X */
        !           586:        yank,           /* ^Y */
        !           587:        attachtoparent, /* ^Z */
        !           588: };
        !           589: static PF      fund_esc[] = {
        !           590:        prefix,         /* esc */
        !           591:        rescan,         /* ^\ */        /* selfinsert is default on fundamental */
        !           592:        rescan,         /* ^] */
        !           593:        rescan,         /* ^^ */
        !           594:        rescan,         /* ^_ */
        !           595: };
        !           596: static PF      fund_del[] = {
        !           597:        backdel,        /* DEL */
        !           598: };
        !           599:
        !           600: #ifndef        FUND_XMAPS
        !           601: #define NFUND_XMAPS    0       /* extra map sections after normal ones */
        !           602: #endif
        !           603:
        !           604: static struct  KEYMAPE(4+NFUND_XMAPS+IMAPEXT)  fundmap = {
        !           605:        4 + NFUND_XMAPS,
        !           606:        4 + NFUND_XMAPS + IMAPEXT,
        !           607:        selfinsert,
        !           608:        {
        !           609: #ifndef NO_HELP
        !           610:                {CCHR('@'),CCHR('H'),   fund_at, (KEYMAP *)&helpmap},
        !           611: #else
        !           612:                {CCHR('@'),CCHR('H'),   fund_at, (KEYMAP *)NULL},
        !           613: #endif
        !           614:                {CCHR('J'),CCHR('Z'),   fund_CJ, (KEYMAP *)&cXmap},
        !           615:                {CCHR('['),CCHR('_'),   fund_esc,(KEYMAP *)&metamap},
        !           616:                {CCHR('?'),CCHR('?'),   fund_del,(KEYMAP *)NULL},
        !           617: #ifdef FUND_XMAPS
        !           618:                FUND_XMAPS,
        !           619: #endif
        !           620:        }
        !           621: };
        !           622:
        !           623: static PF      fill_sp[] = {
        !           624:        fillword,       /* ' ' */
        !           625: };
        !           626: static struct KEYMAPE(1+IMAPEXT)       fillmap = {
        !           627:        1,
        !           628:        1+IMAPEXT,
        !           629:        rescan,
        !           630:        {
        !           631:                {' ',   ' ',    fill_sp,        (KEYMAP *)NULL},
        !           632:        }
        !           633: };
        !           634:
        !           635: static PF      indent_lf[] = {
        !           636:        newline,        /* ^J */
        !           637:        rescan,         /* ^K */
        !           638:        rescan,         /* ^L */
        !           639:        indent,         /* ^M */
        !           640: };
        !           641: static struct  KEYMAPE(1+IMAPEXT)      indntmap = {
        !           642:        1,
        !           643:        1+IMAPEXT,
        !           644:        rescan,
        !           645:        {
        !           646:                {CCHR('J'), CCHR('M'),  indent_lf,      (KEYMAP *)NULL},
        !           647:        }
        !           648: };
        !           649: static PF      blink_rp[] = {
        !           650:        showmatch,      /* ) */
        !           651: };
        !           652: static struct  KEYMAPE(1+IMAPEXT)      blinkmap = {
        !           653:        1,
        !           654:        1+IMAPEXT,
        !           655:        rescan,
        !           656:        {
        !           657:                {')',   ')',    blink_rp,       (KEYMAP *)NULL},
        !           658:        }
        !           659: };
        !           660:
        !           661: #ifdef NOTAB
        !           662: static PF      notab_tab[] = {
        !           663:        space_to_tabstop,       /* ^I */
        !           664: };
        !           665: static struct  KEYMAPE(1+IMAPEXT)      notabmap = {
        !           666:        1,
        !           667:        1+IMAPEXT,
        !           668:        rescan,
        !           669:        {
        !           670:                {CCHR('I'),CCHR('I'),   notab_tab,      (KEYMAP *)NULL},
        !           671:        }
        !           672: };
        !           673: #endif
        !           674:
        !           675: static struct  KEYMAPE(1+IMAPEXT)      overwmap = {
        !           676:        0,
        !           677:        1+IMAPEXT,                      /* 1 to avoid 0 sized array */
        !           678:        rescan,
        !           679:        {
        !           680:                /* unused dummy entry for VMS C */
        !           681:                {(KCHAR)0,      (KCHAR)0, (PF *)NULL,   (KEYMAP *)NULL},
        !           682:        }
        !           683: };
        !           684:
        !           685: #ifndef NO_DIRED
        !           686: static PF      dirednul[] = {
        !           687:        setmark,        /* ^@ */
        !           688:        gotobol,        /* ^A */
        !           689:        backchar,       /* ^B */
        !           690:        rescan,         /* ^C */
        !           691:        d_del,          /* ^D */
        !           692:        gotoeol,        /* ^E */
        !           693:        forwchar,       /* ^F */
        !           694:        ctrlg,          /* ^G */
        !           695: #ifndef NO_HELP
        !           696:        prefix,         /* ^H */
        !           697: #endif
        !           698: };
        !           699: static PF      diredcl[] = {
        !           700:        reposition,     /* ^L */
        !           701:        forwline,       /* ^M */
        !           702:        forwline,       /* ^N */
        !           703:        rescan,         /* ^O */
        !           704:        backline,       /* ^P */
        !           705:        rescan,         /* ^Q */
        !           706:        backisearch,    /* ^R */
        !           707:        forwisearch,    /* ^S */
        !           708:        rescan,         /* ^T */
        !           709:        universal_argument, /* ^U */
        !           710:        forwpage,       /* ^V */
        !           711:        rescan,         /* ^W */
        !           712:        prefix,         /* ^X */
        !           713: };
        !           714: static PF      diredcz[] = {
        !           715:        attachtoparent, /* ^Z */
        !           716:        prefix,         /* esc */
        !           717:        rescan,         /* ^\ */
        !           718:        rescan,         /* ^] */
        !           719:        rescan,         /* ^^ */
        !           720:        rescan,         /* ^_ */
        !           721:        forwline,       /* SP */
        !           722: };
        !           723: static PF      diredc[] = {
        !           724:        d_copy,         /* c */
        !           725:        d_del,          /* d */
        !           726:        d_findfile,     /* e */
        !           727:        d_findfile,     /* f */
        !           728: };
        !           729: static PF      diredn[] = {
        !           730:        forwline,       /* n */
        !           731:        d_ffotherwindow,/* o */
        !           732:        backline,       /* p */
        !           733:        rescan,         /* q */
        !           734:        d_rename,       /* r */
        !           735:        rescan,         /* s */
        !           736:        rescan,         /* t */
        !           737:        d_undel,        /* u */
        !           738:        rescan,         /* v */
        !           739:        rescan,         /* w */
        !           740:        d_expunge,      /* x */
        !           741: };
        !           742: static PF      direddl[] = {
        !           743:        d_undelbak,     /* del */
        !           744: };
        !           745:
        !           746: #ifndef        DIRED_XMAPS
        !           747: #define        NDIRED_XMAPS    0       /* number of extra map sections */
        !           748: #endif
        !           749:
        !           750: static struct  KEYMAPE(6 + NDIRED_XMAPS + IMAPEXT)     diredmap = {
        !           751:        6 + NDIRED_XMAPS,
        !           752:        6 + NDIRED_XMAPS + IMAPEXT,
        !           753:        rescan,
        !           754:        {
        !           755: #ifndef NO_HELP
        !           756:                {CCHR('@'),     CCHR('H'),      dirednul, (KEYMAP *)&helpmap},
        !           757: #else
        !           758:                {CCHR('@'),     CCHR('G'),      dirednul, (KEYMAP *)NULL},
        !           759: #endif
        !           760:                {CCHR('L'),     CCHR('X'),      diredcl,  (KEYMAP *)&cXmap},
        !           761:                {CCHR('Z'),     ' ',            diredcz,  (KEYMAP *)&metamap},
        !           762:                {'c',           'f',            diredc,   (KEYMAP *)NULL},
        !           763:                {'n',           'x',            diredn,   (KEYMAP *)NULL},
        !           764:                {CCHR('?'),     CCHR('?'),      direddl,  (KEYMAP *)NULL},
        !           765: #ifdef DIRED_XMAPS
        !           766:                DIRED_XMAPS,    /* map sections for dired mode keys     */
        !           767: #endif
        !           768:        }
        !           769: };
        !           770: #endif
        !           771:
        !           772: /* give names to the maps, for use by help etc.
        !           773:  * If the map is to be bindable, it must also be listed in the
        !           774:  * function name table below with the same name.
        !           775:  * Maps created dynamicly currently don't get added here, thus are unnamed.
        !           776:  * Modes are just named keymaps with functions to add/subtract them from
        !           777:  * a buffer's list of modes.  If you change a mode name, change it in
        !           778:  * modes.c also.
        !           779:  */
        !           780:
        !           781: MAPS   map_table[] = {
        !           782:        /* fundamental map MUST be first entry */
        !           783:        {(KEYMAP *)&fundmap,    "fundamental"},
        !           784:        {(KEYMAP *)&fillmap,    "fill"},
        !           785:        {(KEYMAP *)&indntmap,   "indent"},
        !           786:        {(KEYMAP *)&blinkmap,   "blink"},
        !           787: #ifdef NOTAB
        !           788:        {(KEYMAP *)&notabmap,   "notab"},
        !           789: #endif
        !           790:        {(KEYMAP *)&overwmap,   "overwrite"},
        !           791:        {(KEYMAP *)&metamap,    "esc prefix"},
        !           792:        {(KEYMAP *)&cXmap,      "c-x prefix"},
        !           793:        {(KEYMAP *)&cX4map,     "c-x 4 prefix"},
        !           794:        {(KEYMAP *)&extramap1,  "extra prefix 1"},
        !           795:        {(KEYMAP *)&extramap2,  "extra prefix 2"},
        !           796:        {(KEYMAP *)&extramap3,  "extra prefix 3"},
        !           797:        {(KEYMAP *)&extramap4,  "extra prefix 4"},
        !           798:        {(KEYMAP *)&extramap5,  "extra prefix 5"},
        !           799: #ifndef NO_HELP
        !           800:        {(KEYMAP *)&helpmap,    "help"},
        !           801: #endif
        !           802: #ifndef NO_DIRED
        !           803:        {(KEYMAP *)&diredmap,   "dired"},
        !           804: #endif
        !           805: };
        !           806:
        !           807: #define NMAPS  (sizeof map_table/sizeof(MAPS))
        !           808: int    nmaps = NMAPS;          /* for use by rebind in extend.c */
        !           809:
        !           810: char *map_name(map)
        !           811: KEYMAP *map;
        !           812: {
        !           813:        MAPS *mp = &map_table[0];
        !           814:
        !           815:        do {
        !           816:            if(mp->p_map == map) return mp->p_name;
        !           817:        } while(++mp < &map_table[NMAPS]);
        !           818:        return (char *)NULL;
        !           819: }
        !           820:
        !           821: MAPS *name_mode(name)
        !           822: char *name;
        !           823: {
        !           824:        MAPS *mp = &map_table[0];
        !           825:
        !           826:        do {
        !           827:            if(strcmp(mp->p_name,name)==0) return mp;
        !           828:        } while(++mp < &map_table[NMAPS]);
        !           829:        return (MAPS *)NULL;
        !           830: }
        !           831:
        !           832: KEYMAP *name_map(name)
        !           833: char *name;
        !           834: {
        !           835:        MAPS *mp;
        !           836:        return (mp=name_mode(name))==NULL ? (KEYMAP *)NULL : mp->p_map;
        !           837: }
        !           838:
        !           839: /* Warning: functnames MUST be in alphabetical order!  (due to binary
        !           840:  * search in name_function.)  If the function is prefix, it must be listed
        !           841:  * with the same name in the map_table above.
        !           842:  */
        !           843:
        !           844: FUNCTNAMES     functnames[] = {
        !           845: #ifdef AMIGA
        !           846: #ifdef DO_ICONIFY
        !           847:        {tticon,        "amiga-iconify"},
        !           848: #endif
        !           849: #ifdef DO_MENU
        !           850:        {amigamenu,     "amiga-menu"},
        !           851: #endif
        !           852: #ifdef CHANGE_COLOR
        !           853:        {modebackground,"amiga-mode-background"},
        !           854:        {modeforeground,"amiga-mode-foreground"},
        !           855:        {ttmode,        "amiga-mode-rendition"},
        !           856: #endif
        !           857: #ifdef CHANGE_FONT
        !           858:        {setfont,       "amiga-set-font"},
        !           859: #endif
        !           860: #ifdef CHANGE_COLOR
        !           861:        {textbackground,"amiga-text-background"},
        !           862:        {textforeground,"amiga-text-foreground"},
        !           863:        {tttext,        "amiga-text-rendition"},
        !           864: #endif
        !           865:        {togglewindow,  "amiga-toggle-border"},
        !           866:        {togglezooms,   "amiga-zoom-mode"},
        !           867: #endif /* AMIGA */
        !           868: #ifndef        NO_HELP
        !           869:        {apropos_command, "apropos"},
        !           870: #endif
        !           871:        {fillmode,      "auto-fill-mode"},
        !           872:        {indentmode,    "auto-indent-mode"},
        !           873:        {backchar,      "backward-char"},
        !           874:        {delbword,      "backward-kill-word"},
        !           875:        {gotobop,       "backward-paragraph"},
        !           876:        {backword,      "backward-word"},
        !           877:        {gotobob,       "beginning-of-buffer"},
        !           878:        {gotobol,       "beginning-of-line"},
        !           879:        {blinkparen,    "blink-matching-paren"},
        !           880:        {showmatch,     "blink-matching-paren-hack"},
        !           881: #ifdef BSMAP
        !           882:        {bsmap,         "bsmap-mode"},
        !           883: #endif
        !           884:        {prefix,        "c-x 4 prefix"},
        !           885:        {prefix,        "c-x prefix"},
        !           886: #ifndef NO_MACRO
        !           887:        {executemacro,  "call-last-kbd-macro"},
        !           888: #endif
        !           889:        {capword,       "capitalize-word"},
        !           890: #ifndef NO_DIR
        !           891:        {changedir,     "cd"},
        !           892: #endif
        !           893:        {copyregion,    "copy-region-as-kill"},
        !           894: #ifdef REGEX
        !           895:        {cntmatchlines, "count-matches"},
        !           896:        {cntnonmatchlines,"count-non-matches"},
        !           897: #endif
        !           898:        {define_key,    "define-key"},
        !           899:        {backdel,       "delete-backward-char"},
        !           900:        {deblank,       "delete-blank-lines"},
        !           901:        {forwdel,       "delete-char"},
        !           902:        {delwhite,      "delete-horizontal-space"},
        !           903: #ifdef REGEX
        !           904:        {delmatchlines, "delete-matching-lines"},
        !           905:        {delnonmatchlines,"delete-non-matching-lines"},
        !           906: #endif
        !           907:        {onlywind,      "delete-other-windows"},
        !           908:        {delwind,       "delete-window"},
        !           909: #ifndef NO_HELP
        !           910:        {wallchart,     "describe-bindings"},
        !           911:        {desckey,       "describe-key-briefly"},
        !           912: #endif
        !           913:        {digit_argument,"digit-argument"},
        !           914: #ifndef NO_DIRED
        !           915:        {dired,         "dired"},
        !           916:        {d_undelbak,    "dired-backup-unflag"},
        !           917:        {d_copy,        "dired-copy-file"},
        !           918:        {d_expunge,     "dired-do-deletions"},
        !           919:        {d_findfile,    "dired-find-file"},
        !           920:        {d_ffotherwindow, "dired-find-file-other-window"},
        !           921:        {d_del,         "dired-flag-file-deleted"},
        !           922:        {d_otherwindow, "dired-other-window"},
        !           923:        {d_rename,      "dired-rename-file"},
        !           924:        {d_undel,       "dired-unflag"},
        !           925: #endif
        !           926:        {lowerregion,   "downcase-region"},
        !           927:        {lowerword,     "downcase-word"},
        !           928:        {showversion,   "emacs-version"},
        !           929: #ifndef NO_MACRO
        !           930:        {finishmacro,   "end-kbd-macro"},
        !           931: #endif
        !           932:        {gotoeob,       "end-of-buffer"},
        !           933:        {gotoeol,       "end-of-line"},
        !           934:        {enlargewind,   "enlarge-window"},
        !           935:        {prefix,        "esc prefix"},
        !           936: #ifndef NO_STARTUP
        !           937:        {evalbuffer,    "eval-current-buffer"},
        !           938:        {evalexpr,      "eval-expression"},
        !           939: #endif
        !           940:        {swapmark,      "exchange-point-and-mark"},
        !           941:        {extend,        "execute-extended-command"},
        !           942:        {prefix,        "extra prefix 1"},
        !           943:        {prefix,        "extra prefix 2"},
        !           944:        {prefix,        "extra prefix 3"},
        !           945:        {prefix,        "extra prefix 4"},
        !           946:        {prefix,        "extra prefix 5"},
        !           947:        {fillpara,      "fill-paragraph"},
        !           948:        {filevisit,     "find-file"},
        !           949:        {poptofile,     "find-file-other-window"},
        !           950:        {forwchar,      "forward-char"},
        !           951:        {gotoeop,       "forward-paragraph"},
        !           952:        {forwword,      "forward-word"},
        !           953:        {bindtokey,     "global-set-key"},
        !           954:        {unbindtokey,   "global-unset-key"},
        !           955:        {gotoline,      "goto-line"},
        !           956: #ifndef NO_HELP
        !           957:        {prefix,        "help"},
        !           958:        {help_help,     "help-help"},
        !           959: #endif
        !           960:        {insert,        "insert"},
        !           961:        {bufferinsert,  "insert-buffer"},
        !           962:        {fileinsert,    "insert-file"},
        !           963:        {fillword,      "insert-with-wrap"},
        !           964:        {backisearch,   "isearch-backward"},
        !           965:        {forwisearch,   "isearch-forward"},
        !           966:        {justone,       "just-one-space"},
        !           967:        {ctrlg,         "keyboard-quit"},
        !           968:        {killbuffer,    "kill-buffer"},
        !           969:        {killline,      "kill-line"},
        !           970:        {killpara,      "kill-paragraph"},
        !           971:        {killregion,    "kill-region"},
        !           972:        {delfword,      "kill-word"},
        !           973:        {listbuffers,   "list-buffers"},
        !           974: #ifndef NO_STARTUP
        !           975:        {evalfile,      "load"},
        !           976: #endif
        !           977:        {localbind,     "local-set-key"},
        !           978:        {localunbind,   "local-unset-key"},
        !           979: #ifndef NO_BACKUP
        !           980:        {makebkfile,    "make-backup-files"},
        !           981: #endif
        !           982: #ifdef DO_METAKEY
        !           983:        {do_meta,       "meta-key-mode"},       /* better name, anyone? */
        !           984: #endif
        !           985: #ifdef AMIGA
        !           986: #ifdef MOUSE
        !           987:        {mgotobob,      "mouse-beginning-of-buffer"},
        !           988:        {mforwdel,      "mouse-delete-char"},
        !           989:        {mdelwhite,     "mouse-delete-horizontal-space"},
        !           990:        {mdelwind,      "mouse-delete-window"},
        !           991:        {mgotoeob,      "mouse-end-of-buffer"},
        !           992:        {menlargewind,  "mouse-enlarge-window"},
        !           993:        {mkillline,     "mouse-kill-line"},
        !           994:        {mkillregion,   "mouse-kill-region"},
        !           995:        {mdelfword,     "mouse-kill-word"},
        !           996:        {mreposition,   "mouse-recenter"},
        !           997:        {mbackpage,     "mouse-scroll-down"},
        !           998:        {mforwpage,     "mouse-scroll-up"},
        !           999:        {amigamouse,    "mouse-set-point"},
        !          1000:        {mshrinkwind,   "mouse-shrink-window"},
        !          1001:        {msplitwind,    "mouse-split-window-vertically"},
        !          1002:        {myank,         "mouse-yank"},
        !          1003: #endif
        !          1004: #endif
        !          1005:        {negative_argument, "negative-argument"},
        !          1006:        {newline,       "newline"},
        !          1007:        {indent,        "newline-and-indent"},
        !          1008:        {forwline,      "next-line"},
        !          1009: #ifdef NOTAB
        !          1010:        {notabmode,     "no-tab-mode"},
        !          1011: #endif
        !          1012:        {notmodified,   "not-modified"},
        !          1013:        {openline,      "open-line"},
        !          1014:        {nextwind,      "other-window"},
        !          1015:        {overwrite,     "overwrite-mode"},
        !          1016: #ifdef PREFIXREGION
        !          1017:        {prefixregion,  "prefix-region"},
        !          1018: #endif
        !          1019:        {backline,      "previous-line"},
        !          1020: #ifdef GOSMACS
        !          1021:        {prevwind,      "previous-window"},
        !          1022: #endif
        !          1023: #ifdef VMS
        !          1024:        {spawncli,      "push-to-dcl"},
        !          1025: #else
        !          1026:        {spawncli,      "push-shell"},
        !          1027: #endif
        !          1028: #ifndef NO_DIR
        !          1029:        {showcwdir,     "pwd"},
        !          1030: #endif
        !          1031:        {queryrepl,     "query-replace"},
        !          1032: #ifdef REGEX
        !          1033:        {re_queryrepl,  "query-replace-regexp"},
        !          1034: #endif
        !          1035:        {quote,         "quoted-insert"},
        !          1036: #ifdef REGEX
        !          1037:        {re_searchagain,"re-search-again"},
        !          1038:        {re_backsearch, "re-search-backward"},
        !          1039:        {re_forwsearch, "re-search-forward"},
        !          1040: #endif
        !          1041:        {reposition,    "recenter"},
        !          1042:        {refresh,       "redraw-display"},
        !          1043:        {filesave,      "save-buffer"},
        !          1044:        {quit,          "save-buffers-kill-emacs"},
        !          1045:        {savebuffers,   "save-some-buffers"},
        !          1046:        {backpage,      "scroll-down"},
        !          1047: #ifdef GOSMACS
        !          1048:        {back1page,     "scroll-one-line-down"},
        !          1049:        {forw1page,     "scroll-one-line-up"},
        !          1050: #endif
        !          1051:        {pagenext,      "scroll-other-window"},
        !          1052:        {forwpage,      "scroll-up"},
        !          1053:        {searchagain,   "search-again"},
        !          1054:        {backsearch,    "search-backward"},
        !          1055:        {forwsearch,    "search-forward"},
        !          1056:        {selfinsert,    "self-insert-command"},
        !          1057: #ifdef REGEX
        !          1058:        {setcasefold,   "set-case-fold-search"},
        !          1059: #endif
        !          1060:        {set_default_mode, "set-default-mode"},
        !          1061:        {setfillcol,    "set-fill-column"},
        !          1062:        {setmark,       "set-mark-command"},
        !          1063: #ifdef PREFIXREGION
        !          1064:        {setprefix,     "set-prefix-string"},
        !          1065: #endif
        !          1066:        {shrinkwind,    "shrink-window"},
        !          1067: #ifdef NOTAB
        !          1068:        {space_to_tabstop, "space-to-tabstop"},
        !          1069: #endif
        !          1070:        {splitwind,     "split-window-vertically"},
        !          1071: #ifndef NO_MACRO
        !          1072:        {definemacro,   "start-kbd-macro"},
        !          1073: #endif
        !          1074:        {attachtoparent,"suspend-emacs"},
        !          1075:        {usebuffer,     "switch-to-buffer"},
        !          1076:        {poptobuffer,   "switch-to-buffer-other-window"},
        !          1077:        {twiddle,       "transpose-chars"},
        !          1078:        {universal_argument, "universal-argument"},
        !          1079:        {upperregion,   "upcase-region"},
        !          1080:        {upperword,     "upcase-word"},
        !          1081:        {showcpos,      "what-cursor-position"},
        !          1082:        {filewrite,     "write-file"},
        !          1083:        {yank,          "yank"},
        !          1084: };
        !          1085:
        !          1086: #define NFUNCT (sizeof(functnames)/sizeof(FUNCTNAMES))
        !          1087:
        !          1088: int    nfunct = NFUNCT;                /* used by help.c */
        !          1089:
        !          1090: /*
        !          1091:  * The general-purpose version of ROUND2 blows osk C (2.0) out of the water.
        !          1092:  * (reboot required)  If you need to build a version of mg with less than 32
        !          1093:  * or more than 511 functions, something better must be done.
        !          1094:  * The version that should work, but doesn't is:
        !          1095:  * #define ROUND2(x) (1+((x>>1)|(x>>2)|(x>>3)|(x>>4)|(x>>5)|(x>>6)|(x>>7)|\
        !          1096:  *     (x>>8)|(x>>9)|(x>>10)|(x>>11)|(x>>12)|(x>>13)|(x>>14)|(x>>15)))
        !          1097:  */
        !          1098: #define ROUND2(x) (x<128?(x<64?32:64):(x<256?128:256))
        !          1099:
        !          1100: static name_fent(fname, flag)
        !          1101: register char *fname;
        !          1102: int    flag;
        !          1103: {
        !          1104:        register int    try;
        !          1105:        register int    x = ROUND2(NFUNCT);
        !          1106:        register int    base = 0;
        !          1107:        register int    notit;
        !          1108:
        !          1109:        do {
        !          1110:            /* + can be used instead of | here if more efficent.        */
        !          1111:            if((try = base | x) < NFUNCT) {
        !          1112:                if((notit = strcmp(fname, functnames[try].n_name)) >= 0) {
        !          1113:                    if(!notit) return try;
        !          1114:                    base = try;
        !          1115:                }
        !          1116:            }
        !          1117:        } while((x>>=1) || (try==1 && base==0));    /* try 0 once if needed */
        !          1118:        return flag ? base : -1;
        !          1119: }
        !          1120:
        !          1121: /*
        !          1122:  * Translate from function name to function pointer, using binary search.
        !          1123:  */
        !          1124:
        !          1125: PF     name_function(fname)
        !          1126: char   *fname;
        !          1127: {
        !          1128:        int i;
        !          1129:        if((i = name_fent(fname, FALSE)) >= 0) return functnames[i].n_funct;
        !          1130:        return (PF)NULL;
        !          1131: }
        !          1132:
        !          1133: /* complete function name */
        !          1134:
        !          1135: complete_function(fname, c)
        !          1136: register char  *fname;
        !          1137: {
        !          1138:        register int i, j, k, l;
        !          1139:        int     oj;
        !          1140:
        !          1141:        i = name_fent(fname, TRUE);
        !          1142:        for(j=0; (l=fname[j]) && functnames[i].n_name[j]==l; j++) {}
        !          1143:        if(fname[j]!='\0') {
        !          1144:            if(++i >= NFUNCT) return -2;        /* no match */
        !          1145:            for(j=0; (l=fname[j]) && functnames[i].n_name[j]==l; j++) {}
        !          1146:            if(fname[j]!='\0') return -2;       /* no match */
        !          1147:        }
        !          1148:        if(c==CCHR('M') && functnames[i].n_name[j]=='\0') return -1;
        !          1149:        for(k=i+1; k<NFUNCT; k++) {             /* find last match */
        !          1150:            for(l=0; functnames[k].n_name[l]==fname[l]; l++) {}
        !          1151:            if(l<j) break;
        !          1152:        }
        !          1153:        k--;
        !          1154:        oj = j;
        !          1155:        if(k>i) {                                       /* multiple matches */
        !          1156:            while((l = functnames[i].n_name[j]) == functnames[k].n_name[j]) {
        !          1157:                fname[j++] = l;
        !          1158:                if(l=='-' && c==' ') break;
        !          1159:            }
        !          1160:            if(j==oj) return -3;                        /* ambiguous    */
        !          1161:        } else {                                        /* single match */
        !          1162:            while(l = functnames[i].n_name[j]) {
        !          1163:                fname[j++] = l;
        !          1164:                if(l=='-' && c==' ') break;
        !          1165:            }
        !          1166:        }
        !          1167:        fname[j] = '\0';
        !          1168:        return j - oj;
        !          1169: }
        !          1170:
        !          1171: /* list possible function name completions */
        !          1172:
        !          1173: LIST *complete_function_list(fname, c)
        !          1174: register char  *fname;
        !          1175: {
        !          1176:        register int i, j, k, l;
        !          1177:        int     oj;
        !          1178:        LIST *current,*last;
        !          1179:
        !          1180:        i = name_fent(fname, TRUE);
        !          1181:        for(j=0; (l=fname[j]) && functnames[i].n_name[j]==l; j++) {}
        !          1182:        if(fname[j]!='\0') {
        !          1183:            if(++i >= NFUNCT) return NULL;      /* no match */
        !          1184:            for(j=0; (l=fname[j]) && functnames[i].n_name[j]==l; j++) {}
        !          1185:            if(fname[j]!='\0') return NULL;     /* no match */
        !          1186:        }
        !          1187: /*
        !          1188:  *     if(c==CCHR('M') && functnames[i].n_name[j]=='\0') return -1;
        !          1189:  */
        !          1190:        for(k=i+1; k<NFUNCT; k++) {             /* find last match */
        !          1191:            for(l=0; functnames[k].n_name[l]==fname[l]; l++) {}
        !          1192:            if(l<j) break;
        !          1193:        }
        !          1194:        k--;
        !          1195:        last = NULL;
        !          1196:        for (; k >= i; k--) {
        !          1197:            current = (LIST *)malloc(sizeof(LIST));
        !          1198:            current->l_next = last;
        !          1199:            current->l_name = functnames[k].n_name;
        !          1200:            last = current;
        !          1201:        }
        !          1202:        return(last);
        !          1203: }
        !          1204:
        !          1205: /* translate from function pointer to function name. */
        !          1206:
        !          1207: char *function_name(fpoint)
        !          1208: register PF fpoint;
        !          1209: {
        !          1210:        register FUNCTNAMES     *fnp = &functnames[0];
        !          1211:
        !          1212:        if(fpoint == prefix) return (char *)NULL;       /* ambiguous */
        !          1213:        do {
        !          1214:            if(fnp->n_funct == fpoint) return fnp->n_name;
        !          1215:        } while(++fnp < &functnames[NFUNCT]);
        !          1216:        return (char *)NULL;
        !          1217: }