[BACK]Return to common.c CVS log [TXT][DIR] Up to [cvs.NetBSD.org] / src / lib / libedit

Annotation of src/lib/libedit/common.c, Revision 1.11

1.11    ! christos    1: /*     $NetBSD: common.c,v 1.10 2001/01/10 07:45:41 jdolecek Exp $     */
1.2       lukem       2:
1.1       cgd         3: /*-
                      4:  * Copyright (c) 1992, 1993
                      5:  *     The Regents of the University of California.  All rights reserved.
                      6:  *
                      7:  * This code is derived from software contributed to Berkeley by
                      8:  * Christos Zoulas of Cornell University.
                      9:  *
                     10:  * Redistribution and use in source and binary forms, with or without
                     11:  * modification, are permitted provided that the following conditions
                     12:  * are met:
                     13:  * 1. Redistributions of source code must retain the above copyright
                     14:  *    notice, this list of conditions and the following disclaimer.
                     15:  * 2. Redistributions in binary form must reproduce the above copyright
                     16:  *    notice, this list of conditions and the following disclaimer in the
                     17:  *    documentation and/or other materials provided with the distribution.
                     18:  * 3. All advertising materials mentioning features or use of this software
                     19:  *    must display the following acknowledgement:
                     20:  *     This product includes software developed by the University of
                     21:  *     California, Berkeley and its contributors.
                     22:  * 4. Neither the name of the University nor the names of its contributors
                     23:  *    may be used to endorse or promote products derived from this software
                     24:  *    without specific prior written permission.
                     25:  *
                     26:  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
                     27:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     28:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     29:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
                     30:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     31:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     32:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     33:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     34:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     35:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     36:  * SUCH DAMAGE.
                     37:  */
                     38:
1.11    ! christos   39: #include "config.h"
1.1       cgd        40: #if !defined(lint) && !defined(SCCSID)
1.2       lukem      41: #if 0
1.1       cgd        42: static char sccsid[] = "@(#)common.c   8.1 (Berkeley) 6/4/93";
1.2       lukem      43: #else
1.11    ! christos   44: __RCSID("$NetBSD: common.c,v 1.10 2001/01/10 07:45:41 jdolecek Exp $");
1.2       lukem      45: #endif
1.1       cgd        46: #endif /* not lint && not SCCSID */
                     47:
                     48: /*
                     49:  * common.c: Common Editor functions
                     50:  */
                     51: #include "el.h"
                     52:
1.8       simonb     53: /* ed_end_of_file():
1.1       cgd        54:  *     Indicate end of file
                     55:  *     [^D]
                     56:  */
                     57: protected el_action_t
                     58: /*ARGSUSED*/
1.9       lukem      59: ed_end_of_file(EditLine *el, int c)
                     60: {
                     61:
                     62:        re_goto_bottom(el);
                     63:        *el->el_line.lastchar = '\0';
                     64:        return (CC_EOF);
1.1       cgd        65: }
                     66:
                     67:
1.8       simonb     68: /* ed_insert():
1.1       cgd        69:  *     Add character to the line
                     70:  *     Insert a character [bound to all insert keys]
                     71:  */
                     72: protected el_action_t
1.9       lukem      73: ed_insert(EditLine *el, int c)
                     74: {
                     75:        int i;
1.1       cgd        76:
1.9       lukem      77:        if (c == '\0')
                     78:                return (CC_ERROR);
1.1       cgd        79:
1.9       lukem      80:        if (el->el_line.lastchar + el->el_state.argument >=
1.10      jdolecek   81:            el->el_line.limit) {
                     82:                /* end of buffer space, try to allocate more */
                     83:                if (!ch_enlargebufs(el, (size_t) el->el_state.argument))
                     84:                        return CC_ERROR;        /* error allocating more */
                     85:        }
1.9       lukem      86:
                     87:        if (el->el_state.argument == 1) {
                     88:                if (el->el_state.inputmode != MODE_INSERT) {
                     89:                        el->el_chared.c_undo.buf[el->el_chared.c_undo.isize++] =
                     90:                            *el->el_line.cursor;
                     91:                        el->el_chared.c_undo.buf[el->el_chared.c_undo.isize] =
                     92:                            '\0';
                     93:                        c_delafter(el, 1);
                     94:                }
                     95:                c_insert(el, 1);
                     96:
                     97:                *el->el_line.cursor++ = c;
                     98:                el->el_state.doingarg = 0;      /* just in case */
                     99:                re_fastaddc(el);                /* fast refresh for one char. */
                    100:        } else {
                    101:                if (el->el_state.inputmode != MODE_INSERT) {
                    102:                        for (i = 0; i < el->el_state.argument; i++)
                    103:                                el->el_chared.c_undo.buf[el->el_chared.c_undo.isize++] =
                    104:                                    el->el_line.cursor[i];
                    105:
                    106:                        el->el_chared.c_undo.buf[el->el_chared.c_undo.isize] =
                    107:                            '\0';
                    108:                        c_delafter(el, el->el_state.argument);
                    109:                }
                    110:                c_insert(el, el->el_state.argument);
                    111:
                    112:                while (el->el_state.argument--)
                    113:                        *el->el_line.cursor++ = c;
                    114:                re_refresh(el);
                    115:        }
1.1       cgd       116:
1.9       lukem     117:        if (el->el_state.inputmode == MODE_REPLACE_1)
                    118:                (void) vi_command_mode(el, 0);
1.1       cgd       119:
1.9       lukem     120:        return (CC_NORM);
1.1       cgd       121: }
                    122:
                    123:
1.8       simonb    124: /* ed_delete_prev_word():
1.1       cgd       125:  *     Delete from beginning of current word to cursor
                    126:  *     [M-^?] [^W]
                    127:  */
                    128: protected el_action_t
                    129: /*ARGSUSED*/
1.9       lukem     130: ed_delete_prev_word(EditLine *el, int c)
                    131: {
                    132:        char *cp, *p, *kp;
                    133:
                    134:        if (el->el_line.cursor == el->el_line.buffer)
                    135:                return (CC_ERROR);
                    136:
                    137:        cp = c__prev_word(el->el_line.cursor, el->el_line.buffer,
                    138:            el->el_state.argument, ce__isword);
                    139:
                    140:        for (p = cp, kp = el->el_chared.c_kill.buf; p < el->el_line.cursor; p++)
                    141:                *kp++ = *p;
                    142:        el->el_chared.c_kill.last = kp;
                    143:
                    144:        c_delbefore(el, el->el_line.cursor - cp);       /* delete before dot */
                    145:        el->el_line.cursor = cp;
                    146:        if (el->el_line.cursor < el->el_line.buffer)
                    147:                el->el_line.cursor = el->el_line.buffer; /* bounds check */
                    148:        return (CC_REFRESH);
1.1       cgd       149: }
                    150:
                    151:
1.8       simonb    152: /* ed_delete_next_char():
1.1       cgd       153:  *     Delete character under cursor
                    154:  *     [^D] [x]
                    155:  */
                    156: protected el_action_t
                    157: /*ARGSUSED*/
1.9       lukem     158: ed_delete_next_char(EditLine *el, int c)
1.1       cgd       159: {
1.9       lukem     160: #ifdef notdef                  /* XXX */
                    161: #define        EL      el->el_line
1.6       christos  162:        (void) fprintf(el->el_errlfile,
1.8       simonb    163:            "\nD(b: %x(%s)  c: %x(%s) last: %x(%s) limit: %x(%s)\n",
1.6       christos  164:            EL.buffer, EL.buffer, EL.cursor, EL.cursor, EL.lastchar,
                    165:            EL.lastchar, EL.limit, EL.limit);
1.1       cgd       166: #endif
1.9       lukem     167:        if (el->el_line.cursor == el->el_line.lastchar) {
                    168:                        /* if I'm at the end */
                    169:                if (el->el_map.type == MAP_VI) {
                    170:                        if (el->el_line.cursor == el->el_line.buffer) {
                    171:                                /* if I'm also at the beginning */
1.1       cgd       172: #ifdef KSHVI
1.9       lukem     173:                                return (CC_ERROR);
1.1       cgd       174: #else
1.9       lukem     175:                                term_overwrite(el, STReof, 4);
                    176:                                        /* then do a EOF */
                    177:                                term__flush();
                    178:                                return (CC_EOF);
1.1       cgd       179: #endif
1.9       lukem     180:                        } else {
1.1       cgd       181: #ifdef KSHVI
1.9       lukem     182:                                el->el_line.cursor--;
1.1       cgd       183: #else
1.9       lukem     184:                                return (CC_ERROR);
1.1       cgd       185: #endif
1.9       lukem     186:                        }
                    187:                } else {
                    188:                        if (el->el_line.cursor != el->el_line.buffer)
                    189:                                el->el_line.cursor--;
                    190:                        else
                    191:                                return (CC_ERROR);
                    192:                }
1.1       cgd       193:        }
1.9       lukem     194:        c_delafter(el, el->el_state.argument);  /* delete after dot */
                    195:        if (el->el_line.cursor >= el->el_line.lastchar &&
                    196:            el->el_line.cursor > el->el_line.buffer)
                    197:                        /* bounds check */
                    198:                el->el_line.cursor = el->el_line.lastchar - 1;
                    199:        return (CC_REFRESH);
1.1       cgd       200: }
                    201:
                    202:
1.8       simonb    203: /* ed_kill_line():
1.1       cgd       204:  *     Cut to the end of line
                    205:  *     [^K] [^K]
                    206:  */
                    207: protected el_action_t
                    208: /*ARGSUSED*/
1.9       lukem     209: ed_kill_line(EditLine *el, int c)
                    210: {
                    211:        char *kp, *cp;
                    212:
                    213:        cp = el->el_line.cursor;
                    214:        kp = el->el_chared.c_kill.buf;
                    215:        while (cp < el->el_line.lastchar)
                    216:                *kp++ = *cp++;  /* copy it */
                    217:        el->el_chared.c_kill.last = kp;
                    218:                        /* zap! -- delete to end */
                    219:        el->el_line.lastchar = el->el_line.cursor;
                    220:        return (CC_REFRESH);
1.1       cgd       221: }
                    222:
                    223:
1.8       simonb    224: /* ed_move_to_end():
1.1       cgd       225:  *     Move cursor to the end of line
                    226:  *     [^E] [^E]
                    227:  */
                    228: protected el_action_t
                    229: /*ARGSUSED*/
1.9       lukem     230: ed_move_to_end(EditLine *el, int c)
1.1       cgd       231: {
1.9       lukem     232:
                    233:        el->el_line.cursor = el->el_line.lastchar;
                    234:        if (el->el_map.type == MAP_VI) {
1.1       cgd       235: #ifdef VI_MOVE
1.9       lukem     236:                el->el_line.cursor--;
1.1       cgd       237: #endif
1.9       lukem     238:                if (el->el_chared.c_vcmd.action & DELETE) {
                    239:                        cv_delfini(el);
                    240:                        return (CC_REFRESH);
                    241:                }
1.1       cgd       242:        }
1.9       lukem     243:        return (CC_CURSOR);
1.1       cgd       244: }
                    245:
                    246:
1.8       simonb    247: /* ed_move_to_beg():
1.1       cgd       248:  *     Move cursor to the beginning of line
                    249:  *     [^A] [^A]
                    250:  */
                    251: protected el_action_t
                    252: /*ARGSUSED*/
1.9       lukem     253: ed_move_to_beg(EditLine *el, int c)
                    254: {
                    255:
                    256:        el->el_line.cursor = el->el_line.buffer;
                    257:
                    258:        if (el->el_map.type == MAP_VI) {
                    259:                        /* We want FIRST non space character */
                    260:                while (isspace((unsigned char) *el->el_line.cursor))
                    261:                        el->el_line.cursor++;
                    262:                if (el->el_chared.c_vcmd.action & DELETE) {
                    263:                        cv_delfini(el);
                    264:                        return (CC_REFRESH);
                    265:                }
1.1       cgd       266:        }
1.9       lukem     267:        return (CC_CURSOR);
1.1       cgd       268: }
                    269:
                    270:
1.8       simonb    271: /* ed_transpose_chars():
1.1       cgd       272:  *     Exchange the character to the left of the cursor with the one under it
                    273:  *     [^T] [^T]
                    274:  */
                    275: protected el_action_t
1.9       lukem     276: ed_transpose_chars(EditLine *el, int c)
                    277: {
                    278:
                    279:        if (el->el_line.cursor < el->el_line.lastchar) {
                    280:                if (el->el_line.lastchar <= &el->el_line.buffer[1])
                    281:                        return (CC_ERROR);
                    282:                else
                    283:                        el->el_line.cursor++;
                    284:        }
                    285:        if (el->el_line.cursor > &el->el_line.buffer[1]) {
                    286:                /* must have at least two chars entered */
                    287:                c = el->el_line.cursor[-2];
                    288:                el->el_line.cursor[-2] = el->el_line.cursor[-1];
                    289:                el->el_line.cursor[-1] = c;
                    290:                return (CC_REFRESH);
                    291:        } else
                    292:                return (CC_ERROR);
1.1       cgd       293: }
                    294:
                    295:
1.8       simonb    296: /* ed_next_char():
1.1       cgd       297:  *     Move to the right one character
                    298:  *     [^F] [^F]
                    299:  */
                    300: protected el_action_t
                    301: /*ARGSUSED*/
1.9       lukem     302: ed_next_char(EditLine *el, int c)
1.1       cgd       303: {
                    304:
1.9       lukem     305:        if (el->el_line.cursor >= el->el_line.lastchar)
                    306:                return (CC_ERROR);
1.1       cgd       307:
1.9       lukem     308:        el->el_line.cursor += el->el_state.argument;
                    309:        if (el->el_line.cursor > el->el_line.lastchar)
                    310:                el->el_line.cursor = el->el_line.lastchar;
1.1       cgd       311:
1.9       lukem     312:        if (el->el_map.type == MAP_VI)
                    313:                if (el->el_chared.c_vcmd.action & DELETE) {
                    314:                        cv_delfini(el);
                    315:                        return (CC_REFRESH);
                    316:                }
                    317:        return (CC_CURSOR);
1.1       cgd       318: }
                    319:
                    320:
1.8       simonb    321: /* ed_prev_word():
1.1       cgd       322:  *     Move to the beginning of the current word
                    323:  *     [M-b] [b]
                    324:  */
                    325: protected el_action_t
                    326: /*ARGSUSED*/
1.9       lukem     327: ed_prev_word(EditLine *el, int c)
1.1       cgd       328: {
                    329:
1.9       lukem     330:        if (el->el_line.cursor == el->el_line.buffer)
                    331:                return (CC_ERROR);
1.1       cgd       332:
1.9       lukem     333:        el->el_line.cursor = c__prev_word(el->el_line.cursor,
                    334:            el->el_line.buffer,
                    335:            el->el_state.argument,
                    336:            ce__isword);
1.1       cgd       337:
1.9       lukem     338:        if (el->el_map.type == MAP_VI)
                    339:                if (el->el_chared.c_vcmd.action & DELETE) {
                    340:                        cv_delfini(el);
                    341:                        return (CC_REFRESH);
                    342:                }
                    343:        return (CC_CURSOR);
1.1       cgd       344: }
                    345:
                    346:
1.8       simonb    347: /* ed_prev_char():
1.1       cgd       348:  *     Move to the left one character
                    349:  *     [^B] [^B]
                    350:  */
                    351: protected el_action_t
                    352: /*ARGSUSED*/
1.9       lukem     353: ed_prev_char(EditLine *el, int c)
1.1       cgd       354: {
                    355:
1.9       lukem     356:        if (el->el_line.cursor > el->el_line.buffer) {
                    357:                el->el_line.cursor -= el->el_state.argument;
                    358:                if (el->el_line.cursor < el->el_line.buffer)
                    359:                        el->el_line.cursor = el->el_line.buffer;
                    360:
                    361:                if (el->el_map.type == MAP_VI)
                    362:                        if (el->el_chared.c_vcmd.action & DELETE) {
                    363:                                cv_delfini(el);
                    364:                                return (CC_REFRESH);
                    365:                        }
                    366:                return (CC_CURSOR);
                    367:        } else
                    368:                return (CC_ERROR);
1.1       cgd       369: }
                    370:
                    371:
1.8       simonb    372: /* ed_quoted_insert():
1.1       cgd       373:  *     Add the next character typed verbatim
                    374:  *     [^V] [^V]
                    375:  */
                    376: protected el_action_t
1.9       lukem     377: ed_quoted_insert(EditLine *el, int c)
                    378: {
                    379:        int num;
                    380:        char tc;
                    381:
                    382:        tty_quotemode(el);
                    383:        num = el_getc(el, &tc);
                    384:        c = (unsigned char) tc;
                    385:        tty_noquotemode(el);
                    386:        if (num == 1)
                    387:                return (ed_insert(el, c));
                    388:        else
                    389:                return (ed_end_of_file(el, 0));
1.1       cgd       390: }
                    391:
                    392:
1.8       simonb    393: /* ed_digit():
1.1       cgd       394:  *     Adds to argument or enters a digit
                    395:  */
                    396: protected el_action_t
1.9       lukem     397: ed_digit(EditLine *el, int c)
                    398: {
                    399:
                    400:        if (!isdigit(c))
                    401:                return (CC_ERROR);
                    402:
                    403:        if (el->el_state.doingarg) {
                    404:                        /* if doing an arg, add this in... */
                    405:                if (el->el_state.lastcmd == EM_UNIVERSAL_ARGUMENT)
                    406:                        el->el_state.argument = c - '0';
                    407:                else {
                    408:                        if (el->el_state.argument > 1000000)
                    409:                                return (CC_ERROR);
                    410:                        el->el_state.argument =
                    411:                            (el->el_state.argument * 10) + (c - '0');
                    412:                }
                    413:                return (CC_ARGHACK);
                    414:        } else {
1.10      jdolecek  415:                if (el->el_line.lastchar + 1 >= el->el_line.limit) {
                    416:                        if (!ch_enlargebufs(el, 1))
                    417:                                return (CC_ERROR);
                    418:                }
1.9       lukem     419:
                    420:                if (el->el_state.inputmode != MODE_INSERT) {
                    421:                        el->el_chared.c_undo.buf[el->el_chared.c_undo.isize++] =
                    422:                            *el->el_line.cursor;
                    423:                        el->el_chared.c_undo.buf[el->el_chared.c_undo.isize] =
                    424:                            '\0';
                    425:                        c_delafter(el, 1);
                    426:                }
                    427:                c_insert(el, 1);
                    428:                *el->el_line.cursor++ = c;
                    429:                el->el_state.doingarg = 0;
                    430:                re_fastaddc(el);
                    431:        }
                    432:        return (CC_NORM);
1.1       cgd       433: }
                    434:
                    435:
1.8       simonb    436: /* ed_argument_digit():
1.1       cgd       437:  *     Digit that starts argument
                    438:  *     For ESC-n
                    439:  */
                    440: protected el_action_t
1.9       lukem     441: ed_argument_digit(EditLine *el, int c)
                    442: {
                    443:
                    444:        if (!isdigit(c))
                    445:                return (CC_ERROR);
                    446:
                    447:        if (el->el_state.doingarg) {
                    448:                if (el->el_state.argument > 1000000)
                    449:                        return (CC_ERROR);
                    450:                el->el_state.argument = (el->el_state.argument * 10) +
                    451:                    (c - '0');
                    452:        } else {                /* else starting an argument */
                    453:                el->el_state.argument = c - '0';
                    454:                el->el_state.doingarg = 1;
                    455:        }
                    456:        return (CC_ARGHACK);
1.1       cgd       457: }
                    458:
                    459:
1.8       simonb    460: /* ed_unassigned():
1.1       cgd       461:  *     Indicates unbound character
                    462:  *     Bound to keys that are not assigned
                    463:  */
                    464: protected el_action_t
                    465: /*ARGSUSED*/
1.9       lukem     466: ed_unassigned(EditLine *el, int c)
                    467: {
                    468:
                    469:        term_beep(el);
                    470:        term__flush();
                    471:        return (CC_NORM);
1.1       cgd       472: }
                    473:
                    474:
                    475: /**
                    476:  ** TTY key handling.
                    477:  **/
                    478:
1.8       simonb    479: /* ed_tty_sigint():
1.1       cgd       480:  *     Tty interrupt character
                    481:  *     [^C]
                    482:  */
                    483: protected el_action_t
                    484: /*ARGSUSED*/
1.9       lukem     485: ed_tty_sigint(EditLine *el, int c)
1.8       simonb    486: {
1.9       lukem     487:
                    488:        return (CC_NORM);
1.1       cgd       489: }
                    490:
                    491:
1.8       simonb    492: /* ed_tty_dsusp():
1.1       cgd       493:  *     Tty delayed suspend character
                    494:  *     [^Y]
                    495:  */
                    496: protected el_action_t
                    497: /*ARGSUSED*/
1.9       lukem     498: ed_tty_dsusp(EditLine *el, int c)
1.1       cgd       499: {
1.9       lukem     500:
                    501:        return (CC_NORM);
1.1       cgd       502: }
                    503:
                    504:
1.8       simonb    505: /* ed_tty_flush_output():
1.1       cgd       506:  *     Tty flush output characters
                    507:  *     [^O]
                    508:  */
                    509: protected el_action_t
                    510: /*ARGSUSED*/
1.9       lukem     511: ed_tty_flush_output(EditLine *el, int c)
1.1       cgd       512: {
1.9       lukem     513:
                    514:        return (CC_NORM);
1.1       cgd       515: }
                    516:
                    517:
1.8       simonb    518: /* ed_tty_sigquit():
1.1       cgd       519:  *     Tty quit character
                    520:  *     [^\]
                    521:  */
                    522: protected el_action_t
                    523: /*ARGSUSED*/
1.9       lukem     524: ed_tty_sigquit(EditLine *el, int c)
1.1       cgd       525: {
1.9       lukem     526:
                    527:        return (CC_NORM);
1.1       cgd       528: }
                    529:
                    530:
1.8       simonb    531: /* ed_tty_sigtstp():
1.1       cgd       532:  *     Tty suspend character
                    533:  *     [^Z]
                    534:  */
                    535: protected el_action_t
                    536: /*ARGSUSED*/
1.9       lukem     537: ed_tty_sigtstp(EditLine *el, int c)
1.1       cgd       538: {
1.9       lukem     539:
                    540:        return (CC_NORM);
1.1       cgd       541: }
                    542:
                    543:
1.8       simonb    544: /* ed_tty_stop_output():
1.1       cgd       545:  *     Tty disallow output characters
                    546:  *     [^S]
                    547:  */
                    548: protected el_action_t
                    549: /*ARGSUSED*/
1.9       lukem     550: ed_tty_stop_output(EditLine *el, int c)
1.1       cgd       551: {
1.9       lukem     552:
                    553:        return (CC_NORM);
1.1       cgd       554: }
                    555:
                    556:
1.8       simonb    557: /* ed_tty_start_output():
1.1       cgd       558:  *     Tty allow output characters
                    559:  *     [^Q]
                    560:  */
                    561: protected el_action_t
                    562: /*ARGSUSED*/
1.9       lukem     563: ed_tty_start_output(EditLine *el, int c)
1.1       cgd       564: {
1.9       lukem     565:
                    566:        return (CC_NORM);
1.1       cgd       567: }
                    568:
                    569:
1.8       simonb    570: /* ed_newline():
1.1       cgd       571:  *     Execute command
                    572:  *     [^J]
                    573:  */
                    574: protected el_action_t
                    575: /*ARGSUSED*/
1.9       lukem     576: ed_newline(EditLine *el, int c)
                    577: {
                    578:
                    579:        re_goto_bottom(el);
                    580:        *el->el_line.lastchar++ = '\n';
                    581:        *el->el_line.lastchar = '\0';
                    582:        if (el->el_map.type == MAP_VI)
                    583:                el->el_chared.c_vcmd.ins = el->el_line.buffer;
                    584:        return (CC_NEWLINE);
1.1       cgd       585: }
                    586:
                    587:
1.8       simonb    588: /* ed_delete_prev_char():
1.1       cgd       589:  *     Delete the character to the left of the cursor
                    590:  *     [^?]
                    591:  */
                    592: protected el_action_t
                    593: /*ARGSUSED*/
1.9       lukem     594: ed_delete_prev_char(EditLine *el, int c)
                    595: {
                    596:
                    597:        if (el->el_line.cursor <= el->el_line.buffer)
                    598:                return (CC_ERROR);
                    599:
                    600:        c_delbefore(el, el->el_state.argument);
                    601:        el->el_line.cursor -= el->el_state.argument;
                    602:        if (el->el_line.cursor < el->el_line.buffer)
                    603:                el->el_line.cursor = el->el_line.buffer;
                    604:        return (CC_REFRESH);
1.1       cgd       605: }
                    606:
                    607:
1.8       simonb    608: /* ed_clear_screen():
1.1       cgd       609:  *     Clear screen leaving current line at the top
                    610:  *     [^L]
                    611:  */
                    612: protected el_action_t
                    613: /*ARGSUSED*/
1.9       lukem     614: ed_clear_screen(EditLine *el, int c)
                    615: {
                    616:
                    617:        term_clear_screen(el);  /* clear the whole real screen */
                    618:        re_clear_display(el);   /* reset everything */
                    619:        return (CC_REFRESH);
1.1       cgd       620: }
                    621:
                    622:
1.8       simonb    623: /* ed_redisplay():
1.1       cgd       624:  *     Redisplay everything
                    625:  *     ^R
                    626:  */
                    627: protected el_action_t
                    628: /*ARGSUSED*/
1.9       lukem     629: ed_redisplay(EditLine *el, int c)
1.1       cgd       630: {
1.9       lukem     631:
                    632:        return (CC_REDISPLAY);
1.1       cgd       633: }
                    634:
                    635:
1.8       simonb    636: /* ed_start_over():
1.1       cgd       637:  *     Erase current line and start from scratch
                    638:  *     [^G]
                    639:  */
                    640: protected el_action_t
                    641: /*ARGSUSED*/
1.9       lukem     642: ed_start_over(EditLine *el, int c)
1.1       cgd       643: {
1.9       lukem     644:
                    645:        ch_reset(el);
                    646:        return (CC_REFRESH);
1.1       cgd       647: }
                    648:
                    649:
1.8       simonb    650: /* ed_sequence_lead_in():
1.1       cgd       651:  *     First character in a bound sequence
                    652:  *     Placeholder for external keys
                    653:  */
                    654: protected el_action_t
                    655: /*ARGSUSED*/
1.9       lukem     656: ed_sequence_lead_in(EditLine *el, int c)
1.1       cgd       657: {
1.9       lukem     658:
                    659:        return (CC_NORM);
1.1       cgd       660: }
                    661:
                    662:
1.8       simonb    663: /* ed_prev_history():
1.1       cgd       664:  *     Move to the previous history line
                    665:  *     [^P] [k]
                    666:  */
                    667: protected el_action_t
                    668: /*ARGSUSED*/
1.9       lukem     669: ed_prev_history(EditLine *el, int c)
                    670: {
                    671:        char beep = 0;
                    672:
                    673:        el->el_chared.c_undo.action = NOP;
                    674:        *el->el_line.lastchar = '\0';           /* just in case */
                    675:
                    676:        if (el->el_history.eventno == 0) {      /* save the current buffer
                    677:                                                 * away */
                    678:                (void) strncpy(el->el_history.buf, el->el_line.buffer,
                    679:                    EL_BUFSIZ);
                    680:                el->el_history.last = el->el_history.buf +
                    681:                    (el->el_line.lastchar - el->el_line.buffer);
                    682:        }
                    683:        el->el_history.eventno += el->el_state.argument;
                    684:
                    685:        if (hist_get(el) == CC_ERROR) {
                    686:                beep = 1;
                    687:                /* el->el_history.eventno was fixed by first call */
                    688:                (void) hist_get(el);
                    689:        }
                    690:        re_refresh(el);
                    691:        if (beep)
                    692:                return (CC_ERROR);
                    693:        else
                    694:                return (CC_NORM);       /* was CC_UP_HIST */
1.1       cgd       695: }
                    696:
                    697:
1.8       simonb    698: /* ed_next_history():
1.1       cgd       699:  *     Move to the next history line
                    700:  *     [^N] [j]
                    701:  */
                    702: protected el_action_t
                    703: /*ARGSUSED*/
1.9       lukem     704: ed_next_history(EditLine *el, int c)
1.1       cgd       705: {
                    706:
1.9       lukem     707:        el->el_chared.c_undo.action = NOP;
                    708:        *el->el_line.lastchar = '\0';   /* just in case */
1.1       cgd       709:
1.9       lukem     710:        el->el_history.eventno -= el->el_state.argument;
1.1       cgd       711:
1.9       lukem     712:        if (el->el_history.eventno < 0) {
                    713:                el->el_history.eventno = 0;
                    714:                return (CC_ERROR);/* make it beep */
                    715:        }
                    716:        return (hist_get(el));
1.1       cgd       717: }
                    718:
                    719:
1.8       simonb    720: /* ed_search_prev_history():
1.1       cgd       721:  *     Search previous in history for a line matching the current
                    722:  *     next search history [M-P] [K]
                    723:  */
                    724: protected el_action_t
                    725: /*ARGSUSED*/
1.9       lukem     726: ed_search_prev_history(EditLine *el, int c)
                    727: {
                    728:        const char *hp;
                    729:        int h;
                    730:        bool_t found = 0;
                    731:
                    732:        el->el_chared.c_vcmd.action = NOP;
                    733:        el->el_chared.c_undo.action = NOP;
                    734:        *el->el_line.lastchar = '\0';   /* just in case */
                    735:        if (el->el_history.eventno < 0) {
1.1       cgd       736: #ifdef DEBUG_EDIT
1.9       lukem     737:                (void) fprintf(el->el_errfile,
                    738:                    "e_prev_search_hist(): eventno < 0;\n");
1.1       cgd       739: #endif
1.9       lukem     740:                el->el_history.eventno = 0;
                    741:                return (CC_ERROR);
                    742:        }
                    743:        if (el->el_history.eventno == 0) {
                    744:                (void) strncpy(el->el_history.buf, el->el_line.buffer,
                    745:                    EL_BUFSIZ);
                    746:                el->el_history.last = el->el_history.buf +
                    747:                    (el->el_line.lastchar - el->el_line.buffer);
                    748:        }
                    749:        if (el->el_history.ref == NULL)
                    750:                return (CC_ERROR);
1.1       cgd       751:
1.9       lukem     752:        hp = HIST_FIRST(el);
                    753:        if (hp == NULL)
                    754:                return (CC_ERROR);
1.1       cgd       755:
1.9       lukem     756:        c_setpat(el);           /* Set search pattern !! */
1.1       cgd       757:
1.9       lukem     758:        for (h = 1; h <= el->el_history.eventno; h++)
                    759:                hp = HIST_NEXT(el);
1.1       cgd       760:
1.9       lukem     761:        while (hp != NULL) {
1.1       cgd       762: #ifdef SDEBUG
1.9       lukem     763:                (void) fprintf(el->el_errfile, "Comparing with \"%s\"\n", hp);
1.1       cgd       764: #endif
1.9       lukem     765:                if ((strncmp(hp, el->el_line.buffer, (size_t)
                    766:                            (el->el_line.lastchar - el->el_line.buffer)) ||
                    767:                        hp[el->el_line.lastchar - el->el_line.buffer]) &&
                    768:                    c_hmatch(el, hp)) {
                    769:                        found++;
                    770:                        break;
                    771:                }
                    772:                h++;
                    773:                hp = HIST_NEXT(el);
                    774:        }
1.1       cgd       775:
1.9       lukem     776:        if (!found) {
1.1       cgd       777: #ifdef SDEBUG
1.9       lukem     778:                (void) fprintf(el->el_errfile, "not found\n");
1.1       cgd       779: #endif
1.9       lukem     780:                return (CC_ERROR);
                    781:        }
                    782:        el->el_history.eventno = h;
1.1       cgd       783:
1.9       lukem     784:        return (hist_get(el));
1.1       cgd       785: }
                    786:
                    787:
1.8       simonb    788: /* ed_search_next_history():
1.1       cgd       789:  *     Search next in history for a line matching the current
                    790:  *     [M-N] [J]
                    791:  */
                    792: protected el_action_t
                    793: /*ARGSUSED*/
1.9       lukem     794: ed_search_next_history(EditLine *el, int c)
1.1       cgd       795: {
1.9       lukem     796:        const char *hp;
                    797:        int h;
                    798:        bool_t found = 0;
1.1       cgd       799:
1.9       lukem     800:        el->el_chared.c_vcmd.action = NOP;
                    801:        el->el_chared.c_undo.action = NOP;
                    802:        *el->el_line.lastchar = '\0';   /* just in case */
1.1       cgd       803:
1.9       lukem     804:        if (el->el_history.eventno == 0)
                    805:                return (CC_ERROR);
1.1       cgd       806:
1.9       lukem     807:        if (el->el_history.ref == NULL)
                    808:                return (CC_ERROR);
1.1       cgd       809:
1.9       lukem     810:        hp = HIST_FIRST(el);
                    811:        if (hp == NULL)
                    812:                return (CC_ERROR);
1.1       cgd       813:
1.9       lukem     814:        c_setpat(el);           /* Set search pattern !! */
1.1       cgd       815:
1.9       lukem     816:        for (h = 1; h < el->el_history.eventno && hp; h++) {
1.1       cgd       817: #ifdef SDEBUG
1.9       lukem     818:                (void) fprintf(el->el_errfile, "Comparing with \"%s\"\n", hp);
1.1       cgd       819: #endif
1.9       lukem     820:                if ((strncmp(hp, el->el_line.buffer, (size_t)
                    821:                            (el->el_line.lastchar - el->el_line.buffer)) ||
                    822:                        hp[el->el_line.lastchar - el->el_line.buffer]) &&
                    823:                    c_hmatch(el, hp))
                    824:                        found = h;
                    825:                hp = HIST_NEXT(el);
                    826:        }
1.1       cgd       827:
1.9       lukem     828:        if (!found) {           /* is it the current history number? */
                    829:                if (!c_hmatch(el, el->el_history.buf)) {
1.1       cgd       830: #ifdef SDEBUG
1.9       lukem     831:                        (void) fprintf(el->el_errfile, "not found\n");
1.1       cgd       832: #endif
1.9       lukem     833:                        return (CC_ERROR);
                    834:                }
1.1       cgd       835:        }
1.9       lukem     836:        el->el_history.eventno = found;
1.1       cgd       837:
1.9       lukem     838:        return (hist_get(el));
1.1       cgd       839: }
                    840:
                    841:
                    842: /* ed_prev_line():
                    843:  *     Move up one line
                    844:  *     Could be [k] [^p]
                    845:  */
                    846: protected el_action_t
                    847: /*ARGSUSED*/
1.9       lukem     848: ed_prev_line(EditLine *el, int c)
                    849: {
                    850:        char *ptr;
                    851:        int nchars = c_hpos(el);
1.8       simonb    852:
1.9       lukem     853:        /*
                    854:          * Move to the line requested
                    855:          */
                    856:        if (*(ptr = el->el_line.cursor) == '\n')
                    857:                ptr--;
                    858:
                    859:        for (; ptr >= el->el_line.buffer; ptr--)
                    860:                if (*ptr == '\n' && --el->el_state.argument <= 0)
                    861:                        break;
                    862:
                    863:        if (el->el_state.argument > 0)
                    864:                return (CC_ERROR);
                    865:
                    866:        /*
                    867:          * Move to the beginning of the line
                    868:          */
                    869:        for (ptr--; ptr >= el->el_line.buffer && *ptr != '\n'; ptr--)
                    870:                continue;
                    871:
                    872:        /*
                    873:          * Move to the character requested
                    874:          */
                    875:        for (ptr++;
                    876:            nchars-- > 0 && ptr < el->el_line.lastchar && *ptr != '\n';
                    877:            ptr++)
                    878:                continue;
                    879:
                    880:        el->el_line.cursor = ptr;
                    881:        return (CC_CURSOR);
1.1       cgd       882: }
                    883:
                    884:
                    885: /* ed_next_line():
                    886:  *     Move down one line
                    887:  *     Could be [j] [^n]
                    888:  */
                    889: protected el_action_t
                    890: /*ARGSUSED*/
1.9       lukem     891: ed_next_line(EditLine *el, int c)
                    892: {
                    893:        char *ptr;
                    894:        int nchars = c_hpos(el);
1.8       simonb    895:
1.9       lukem     896:        /*
                    897:          * Move to the line requested
                    898:          */
                    899:        for (ptr = el->el_line.cursor; ptr < el->el_line.lastchar; ptr++)
                    900:                if (*ptr == '\n' && --el->el_state.argument <= 0)
                    901:                        break;
                    902:
                    903:        if (el->el_state.argument > 0)
                    904:                return (CC_ERROR);
                    905:
                    906:        /*
                    907:          * Move to the character requested
                    908:          */
                    909:        for (ptr++;
                    910:            nchars-- > 0 && ptr < el->el_line.lastchar && *ptr != '\n';
                    911:            ptr++)
                    912:                continue;
                    913:
                    914:        el->el_line.cursor = ptr;
                    915:        return (CC_CURSOR);
1.1       cgd       916: }
                    917:
                    918:
1.8       simonb    919: /* ed_command():
1.1       cgd       920:  *     Editline extended command
                    921:  *     [M-X] [:]
                    922:  */
                    923: protected el_action_t
                    924: /*ARGSUSED*/
1.9       lukem     925: ed_command(EditLine *el, int c)
                    926: {
                    927:        char tmpbuf[EL_BUFSIZ];
                    928:        int tmplen;
                    929:
                    930:        el->el_line.buffer[0] = '\0';
                    931:        el->el_line.lastchar = el->el_line.buffer;
                    932:        el->el_line.cursor = el->el_line.buffer;
                    933:
                    934:        c_insert(el, 3);        /* prompt + ": " */
                    935:        *el->el_line.cursor++ = '\n';
                    936:        *el->el_line.cursor++ = ':';
                    937:        *el->el_line.cursor++ = ' ';
                    938:        re_refresh(el);
                    939:
                    940:        tmplen = c_gets(el, tmpbuf);
                    941:        tmpbuf[tmplen] = '\0';
                    942:
                    943:        el->el_line.buffer[0] = '\0';
                    944:        el->el_line.lastchar = el->el_line.buffer;
                    945:        el->el_line.cursor = el->el_line.buffer;
                    946:
                    947:        if (parse_line(el, tmpbuf) == -1)
                    948:                return (CC_ERROR);
                    949:        else
                    950:                return (CC_REFRESH);
1.1       cgd       951: }

CVSweb <webmaster@jp.NetBSD.org>