112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* $NetBSD: terminal.c,v 1.14 2012/05/30 18:21:14 christos Exp $ */ 212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/*- 412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Copyright (c) 1992, 1993 512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * The Regents of the University of California. All rights reserved. 612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * This code is derived from software contributed to Berkeley by 812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Christos Zoulas of Cornell University. 912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 1012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Redistribution and use in source and binary forms, with or without 1112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * modification, are permitted provided that the following conditions 1212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * are met: 1312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 1. Redistributions of source code must retain the above copyright 1412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * notice, this list of conditions and the following disclaimer. 1512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 2. Redistributions in binary form must reproduce the above copyright 1612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * notice, this list of conditions and the following disclaimer in the 1712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * documentation and/or other materials provided with the distribution. 1812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 3. Neither the name of the University nor the names of its contributors 1912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * may be used to endorse or promote products derived from this software 2012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * without specific prior written permission. 2112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 2212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 2312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 2412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 2612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 3012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 3112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 3212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * SUCH DAMAGE. 3312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 3412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 3512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include "config.h" 3612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#if !defined(lint) && !defined(SCCSID) 3712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#if 0 3812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialastatic char sccsid[] = "@(#)term.c 8.2 (Berkeley) 4/30/95"; 3912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#else 4012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala__RCSID("$NetBSD: terminal.c,v 1.14 2012/05/30 18:21:14 christos Exp $"); 4112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 4212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* not lint && not SCCSID */ 4312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 4412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* 4512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * terminal.c: Editor/termcap-curses interface 4612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * We have to declare a static variable here, since the 4712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * termcap putchar routine does not take an argument! 4812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 4912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <stdio.h> 5012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <signal.h> 5112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <string.h> 5212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <stdlib.h> 5312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <unistd.h> 5412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <limits.h> 5512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef HAVE_TERMCAP_H 5612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <termcap.h> 5712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 5812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef HAVE_CURSES_H 5912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <curses.h> 6012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#elif HAVE_NCURSES_H 6112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <ncurses.h> 6212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 6312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 6412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* Solaris's term.h does horrid things. */ 6512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#if defined(HAVE_TERM_H) && !defined(__sun) && !defined(HAVE_TERMCAP_H) 6612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <term.h> 6712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 6812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 6912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <sys/types.h> 7012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <sys/ioctl.h> 7112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 7212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef _REENTRANT 7312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include <pthread.h> 7412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 7512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 7612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#include "el.h" 7712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 7812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* 7912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * IMPORTANT NOTE: these routines are allowed to look at the current screen 8012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * and the current position assuming that it is correct. If this is not 8112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * true, then the update will be WRONG! This is (should be) a valid 8212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * assumption... 8312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 8412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 8512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define TC_BUFSIZE ((size_t)2048) 8612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 8712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define GoodStr(a) (el->el_terminal.t_str[a] != NULL && \ 8812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_str[a][0] != '\0') 8912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define Str(a) el->el_terminal.t_str[a] 9012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define Val(a) el->el_terminal.t_val[a] 9112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 9212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate const struct termcapstr { 9312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const char *name; 9412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const char *long_name; 9512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} tstr[] = { 9612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_al 0 9712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "al", "add new blank line" }, 9812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_bl 1 9912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "bl", "audible bell" }, 10012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_cd 2 10112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "cd", "clear to bottom" }, 10212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ce 3 10312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ce", "clear to end of line" }, 10412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ch 4 10512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ch", "cursor to horiz pos" }, 10612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_cl 5 10712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "cl", "clear screen" }, 10812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_dc 6 10912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "dc", "delete a character" }, 11012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_dl 7 11112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "dl", "delete a line" }, 11212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_dm 8 11312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "dm", "start delete mode" }, 11412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ed 9 11512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ed", "end delete mode" }, 11612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ei 10 11712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ei", "end insert mode" }, 11812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_fs 11 11912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "fs", "cursor from status line" }, 12012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ho 12 12112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ho", "home cursor" }, 12212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ic 13 12312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ic", "insert character" }, 12412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_im 14 12512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "im", "start insert mode" }, 12612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ip 15 12712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ip", "insert padding" }, 12812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_kd 16 12912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "kd", "sends cursor down" }, 13012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_kl 17 13112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "kl", "sends cursor left" }, 13212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_kr 18 13312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "kr", "sends cursor right" }, 13412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ku 19 13512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ku", "sends cursor up" }, 13612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_md 20 13712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "md", "begin bold" }, 13812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_me 21 13912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "me", "end attributes" }, 14012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_nd 22 14112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "nd", "non destructive space" }, 14212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_se 23 14312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "se", "end standout" }, 14412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_so 24 14512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "so", "begin standout" }, 14612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ts 25 14712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ts", "cursor to status line" }, 14812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_up 26 14912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "up", "cursor up one" }, 15012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_us 27 15112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "us", "begin underline" }, 15212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_ue 28 15312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "ue", "end underline" }, 15412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_vb 29 15512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "vb", "visible bell" }, 15612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_DC 30 15712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "DC", "delete multiple chars" }, 15812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_DO 31 15912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "DO", "cursor down multiple" }, 16012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_IC 32 16112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "IC", "insert multiple chars" }, 16212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_LE 33 16312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "LE", "cursor left multiple" }, 16412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_RI 34 16512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "RI", "cursor right multiple" }, 16612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_UP 35 16712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "UP", "cursor up multiple" }, 16812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_kh 36 16912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "kh", "send cursor home" }, 17012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_at7 37 17112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "@7", "send cursor end" }, 17212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_kD 38 17312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "kD", "send cursor delete" }, 17412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_str 39 17512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { NULL, NULL } 17612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala}; 17712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 17812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate const struct termcapval { 17912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const char *name; 18012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const char *long_name; 18112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} tval[] = { 18212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_am 0 18312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "am", "has automatic margins" }, 18412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_pt 1 18512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "pt", "has physical tabs" }, 18612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_li 2 18712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "li", "Number of lines" }, 18812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_co 3 18912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "co", "Number of columns" }, 19012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_km 4 19112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "km", "Has meta key" }, 19212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_xt 5 19312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "xt", "Tab chars destructive" }, 19412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_xn 6 19512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "xn", "newline ignored at right margin" }, 19612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_MT 7 19712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { "MT", "Has meta key" }, /* XXX? */ 19812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#define T_val 8 19912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { NULL, NULL, } 20012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala}; 20112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* do two or more of the attributes use me */ 20212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 20312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void terminal_setflags(EditLine *); 20412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate int terminal_rebuffer_display(EditLine *); 20512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void terminal_free_display(EditLine *); 20612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate int terminal_alloc_display(EditLine *); 20712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void terminal_alloc(EditLine *, const struct termcapstr *, 20812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const char *); 20912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void terminal_init_arrow(EditLine *); 21012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void terminal_reset_arrow(EditLine *); 21112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate int terminal_putc(int); 21212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void terminal_tputs(EditLine *, const char *, int); 21312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 21412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef _REENTRANT 21512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate pthread_mutex_t terminal_mutex = PTHREAD_MUTEX_INITIALIZER; 21612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 21712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate FILE *terminal_outfile = NULL; 21812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 21912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 22012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_setflags(): 22112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Set the terminal capability flags 22212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 22312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void 22412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_setflags(EditLine *el) 22512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 22612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS = 0; 22712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_tty.t_tabs) 22812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (Val(T_pt) && !Val(T_xt)) ? TERM_CAN_TAB : 0; 22912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 23012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (Val(T_km) || Val(T_MT)) ? TERM_HAS_META : 0; 23112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= GoodStr(T_ce) ? TERM_CAN_CEOL : 0; 23212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (GoodStr(T_dc) || GoodStr(T_DC)) ? TERM_CAN_DELETE : 0; 23312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (GoodStr(T_im) || GoodStr(T_ic) || GoodStr(T_IC)) ? 23412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala TERM_CAN_INSERT : 0; 23512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (GoodStr(T_up) || GoodStr(T_UP)) ? TERM_CAN_UP : 0; 23612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= Val(T_am) ? TERM_HAS_AUTO_MARGINS : 0; 23712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= Val(T_xn) ? TERM_HAS_MAGIC_MARGINS : 0; 23812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 23912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_me) && GoodStr(T_ue)) 24012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (strcmp(Str(T_me), Str(T_ue)) == 0) ? 24112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala TERM_CAN_ME : 0; 24212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else 24312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS &= ~TERM_CAN_ME; 24412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_me) && GoodStr(T_se)) 24512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_FLAGS |= (strcmp(Str(T_me), Str(T_se)) == 0) ? 24612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala TERM_CAN_ME : 0; 24712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 24812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 24912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_SCREEN 25012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!EL_CAN_UP) { 25112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 25212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "WARNING: Your terminal cannot move up.\n"); 25312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 25412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "Editing may be odd for long lines.\n"); 25512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 25612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!EL_CAN_CEOL) 25712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, "no clear EOL capability.\n"); 25812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!EL_CAN_DELETE) 25912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, "no delete char capability.\n"); 26012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!EL_CAN_INSERT) 26112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, "no insert char capability.\n"); 26212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_SCREEN */ 26312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 26412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 26512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_init(): 26612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Initialize the terminal stuff 26712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 26812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 26912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_init(EditLine *el) 27012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 27112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 27212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_buf = el_malloc(TC_BUFSIZE * 27312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_buf)); 27412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_buf == NULL) 27512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 27612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_cap = el_malloc(TC_BUFSIZE * 27712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_cap)); 27812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_cap == NULL) 27912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 28012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_fkey = el_malloc(A_K_NKEYS * 28112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_fkey)); 28212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_fkey == NULL) 28312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 28412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_loc = 0; 28512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_str = el_malloc(T_str * 28612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_str)); 28712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_str == NULL) 28812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 28912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) memset(el->el_terminal.t_str, 0, T_str * 29012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_str)); 29112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_val = el_malloc(T_val * 29212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_val)); 29312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_val == NULL) 29412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 29512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) memset(el->el_terminal.t_val, 0, T_val * 29612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sizeof(*el->el_terminal.t_val)); 29712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) terminal_set(el, NULL); 29812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_init_arrow(el); 29912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 30012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 30112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 30212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_end(): 30312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Clean up the terminal stuff 30412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 30512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 30612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_end(EditLine *el) 30712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 30812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 30912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(el->el_terminal.t_buf); 31012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_buf = NULL; 31112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(el->el_terminal.t_cap); 31212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_cap = NULL; 31312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_loc = 0; 31412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(el->el_terminal.t_str); 31512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_str = NULL; 31612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(el->el_terminal.t_val); 31712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_val = NULL; 31812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(el->el_terminal.t_fkey); 31912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_fkey = NULL; 32012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_free_display(el); 32112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 32212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 32312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 32412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_alloc(): 32512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Maintain a string pool for termcap strings 32612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 32712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void 32812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_alloc(EditLine *el, const struct termcapstr *t, const char *cap) 32912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 33012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char termbuf[TC_BUFSIZE]; 33112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala size_t tlen, clen; 33212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char **tlist = el->el_terminal.t_str; 33312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char **tmp, **str = &tlist[t - tstr]; 33412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 33512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) memset(termbuf, 0, sizeof(termbuf)); 33612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (cap == NULL || *cap == '\0') { 33712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *str = NULL; 33812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 33912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else 34012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala clen = strlen(cap); 34112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 34212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala tlen = *str == NULL ? 0 : strlen(*str); 34312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 34412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 34512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * New string is shorter; no need to allocate space 34612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 34712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (clen <= tlen) { 34812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*str) 34912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) strcpy(*str, cap); /* XXX strcpy is safe */ 35012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 35112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 35212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 35312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * New string is longer; see if we have enough space to append 35412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 35512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_loc + 3 < TC_BUFSIZE) { 35612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* XXX strcpy is safe */ 35712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) strcpy(*str = &el->el_terminal.t_buf[ 35812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_loc], cap); 35912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_loc += clen + 1; /* one for \0 */ 36012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 36112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 36212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 36312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Compact our buffer; no need to check compaction, cause we know it 36412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * fits... 36512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 36612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala tlen = 0; 36712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (tmp = tlist; tmp < &tlist[T_str]; tmp++) 36812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*tmp != NULL && *tmp != '\0' && *tmp != *str) { 36912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *ptr; 37012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 37112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (ptr = *tmp; *ptr != '\0'; termbuf[tlen++] = *ptr++) 37212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala continue; 37312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala termbuf[tlen++] = '\0'; 37412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 37512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala memcpy(el->el_terminal.t_buf, termbuf, TC_BUFSIZE); 37612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_loc = tlen; 37712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_loc + 3 >= TC_BUFSIZE) { 37812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 37912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "Out of termcap string space.\n"); 38012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 38112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 38212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* XXX strcpy is safe */ 38312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) strcpy(*str = &el->el_terminal.t_buf[el->el_terminal.t_loc], 38412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala cap); 38512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_loc += (size_t)clen + 1; /* one for \0 */ 38612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 38712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 38812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 38912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 39012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_rebuffer_display(): 39112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Rebuffer the display after the screen changed size 39212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 39312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate int 39412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_rebuffer_display(EditLine *el) 39512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 39612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala coord_t *c = &el->el_terminal.t_size; 39712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 39812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_free_display(el); 39912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 40012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala c->h = Val(T_co); 40112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala c->v = Val(T_li); 40212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 40312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (terminal_alloc_display(el) == -1) 40412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 40512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 40612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 40712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 40812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 40912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_alloc_display(): 41012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Allocate a new display. 41112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 41212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate int 41312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_alloc_display(EditLine *el) 41412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 41512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i; 41612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char **b; 41712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala coord_t *c = &el->el_terminal.t_size; 41812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 41912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b = el_malloc(sizeof(*b) * (size_t)(c->v + 1)); 42012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (b == NULL) 42112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 42212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < c->v; i++) { 42312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b[i] = el_malloc(sizeof(**b) * (size_t)(c->h + 1)); 42412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (b[i] == NULL) { 42512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (--i >= 0) 42612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(b[i]); 42712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(b); 42812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 42912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 43012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 43112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b[c->v] = NULL; 43212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_display = b; 43312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 43412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b = el_malloc(sizeof(*b) * (size_t)(c->v + 1)); 43512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (b == NULL) 43612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 43712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < c->v; i++) { 43812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b[i] = el_malloc(sizeof(**b) * (size_t)(c->h + 1)); 43912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (b[i] == NULL) { 44012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (--i >= 0) 44112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(b[i]); 44212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(b); 44312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 44412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 44512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 44612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b[c->v] = NULL; 44712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_vdisplay = b; 44812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 44912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 45012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 45112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 45212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_free_display(): 45312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Free the display buffers 45412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 45512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void 45612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_free_display(EditLine *el) 45712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 45812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char **b; 45912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char **bufp; 46012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 46112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b = el->el_display; 46212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_display = NULL; 46312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (b != NULL) { 46412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (bufp = b; *bufp != NULL; bufp++) 46512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(*bufp); 46612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(b); 46712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 46812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala b = el->el_vdisplay; 46912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_vdisplay = NULL; 47012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (b != NULL) { 47112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (bufp = b; *bufp != NULL; bufp++) 47212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(*bufp); 47312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_free(b); 47412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 47512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 47612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 47712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 47812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_move_to_line(): 47912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * move to line <where> (first line == 0) 48012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * as efficiently as possible 48112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 48212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 48312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_move_to_line(EditLine *el, int where) 48412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 48512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int del; 48612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 48712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (where == el->el_cursor.v) 48812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 48912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 49012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (where > el->el_terminal.t_size.v) { 49112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_SCREEN 49212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 49312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "terminal_move_to_line: where is ridiculous: %d\r\n", 49412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala where); 49512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_SCREEN */ 49612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 49712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 49812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((del = where - el->el_cursor.v) > 0) { 49912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (del > 0) { 50012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_HAS_AUTO_MARGINS && 50112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_display[el->el_cursor.v][0] != '\0') { 50212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala size_t h = (size_t) 50312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (el->el_terminal.t_size.h - 1); 50412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef WIDECHAR 50512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (; h > 0 && 50612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_display[el->el_cursor.v][h] == 50712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala MB_FILL_CHAR; 50812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala h--) 50912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala continue; 51012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 51112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* move without newline */ 51212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_move_to_char(el, (int)h); 51312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_overwrite(el, &el->el_display 51412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala [el->el_cursor.v][el->el_cursor.h], 51512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (size_t)(el->el_terminal.t_size.h - 51612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h)); 51712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* updates Cursor */ 51812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala del--; 51912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 52012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((del > 1) && GoodStr(T_DO)) { 52112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_DO), del, 52212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala del), del); 52312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala del = 0; 52412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 52512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (; del > 0; del--) 52612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\n'); 52712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* because the \n will become \r\n */ 52812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = 0; 52912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 53012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 53112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 53212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { /* del < 0 */ 53312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_UP) && (-del > 1 || !GoodStr(T_up))) 53412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_UP), -del, -del), -del); 53512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { 53612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_up)) 53712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (; del < 0; del++) 53812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_up), 1); 53912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 54012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 54112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.v = where;/* now where is here */ 54212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 54312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 54412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 54512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_move_to_char(): 54612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Move to the character position specified 54712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 54812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 54912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_move_to_char(EditLine *el, int where) 55012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 55112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int del, i; 55212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 55312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialamc_again: 55412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (where == el->el_cursor.h) 55512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 55612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 55712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (where > el->el_terminal.t_size.h) { 55812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_SCREEN 55912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 56012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "terminal_move_to_char: where is riduculous: %d\r\n", 56112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala where); 56212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_SCREEN */ 56312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 56412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 56512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!where) { /* if where is first column */ 56612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\r'); /* do a CR */ 56712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = 0; 56812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 56912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 57012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala del = where - el->el_cursor.h; 57112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 57212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((del < -4 || del > 4) && GoodStr(T_ch)) 57312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* go there directly */ 57412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_ch), where, where), where); 57512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { 57612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (del > 0) { /* moving forward */ 57712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((del > 4) && GoodStr(T_RI)) 57812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_RI), del, del), 57912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala del); 58012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { 58112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* if I can do tabs, use them */ 58212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_CAN_TAB) { 58312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((el->el_cursor.h & 0370) != 58412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (where & ~0x7) 58512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef WIDECHAR 58612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala && (el->el_display[ 58712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.v][where & 0370] != 58812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala MB_FILL_CHAR) 58912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 59012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ) { 59112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* if not within tab stop */ 59212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 59312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (el->el_cursor.h & 0370); 59412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i < (where & ~0x7); 59512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i += 8) 59612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, 59712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala '\t'); 59812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* then tab over */ 59912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = where & ~0x7; 60012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 60112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 60212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 60312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * it's usually cheaper to just write the 60412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * chars, so we do. 60512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 60612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 60712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * NOTE THAT terminal_overwrite() WILL CHANGE 60812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * el->el_cursor.h!!! 60912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 61012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_overwrite(el, &el->el_display[ 61112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.v][el->el_cursor.h], 61212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (size_t)(where - el->el_cursor.h)); 61312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 61412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 61512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { /* del < 0 := moving backward */ 61612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((-del > 4) && GoodStr(T_LE)) 61712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_LE), -del, -del), 61812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala -del); 61912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { /* can't go directly there */ 62012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 62112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * if the "cost" is greater than the "cost" 62212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * from col 0 62312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 62412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_CAN_TAB ? 62512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ((unsigned int)-del > 62612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (((unsigned int) where >> 3) + 62712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (where & 07))) 62812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala : (-del > where)) { 62912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\r');/* do a CR */ 63012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = 0; 63112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala goto mc_again; /* and try again */ 63212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 63312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < -del; i++) 63412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\b'); 63512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 63612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 63712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 63812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = where; /* now where is here */ 63912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 64012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 64112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 64212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_overwrite(): 64312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Overstrike num characters 64412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Assumes MB_FILL_CHARs are present to keep the column count correct 64512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 64612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 64712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_overwrite(EditLine *el, const Char *cp, size_t n) 64812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 64912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (n == 0) 65012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 65112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 65212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (n > (size_t)el->el_terminal.t_size.h) { 65312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_SCREEN 65412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 65512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "terminal_overwrite: n is riduculous: %d\r\n", n); 65612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_SCREEN */ 65712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 65812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 65912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 66012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala do { 66112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* terminal__putc() ignores any MB_FILL_CHARs */ 66212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, *cp++); 66312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h++; 66412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } while (--n); 66512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 66612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_cursor.h >= el->el_terminal.t_size.h) { /* wrap? */ 66712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_HAS_AUTO_MARGINS) { /* yes */ 66812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = 0; 66912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.v++; 67012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_HAS_MAGIC_MARGINS) { 67112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* force the wrap to avoid the "magic" 67212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * situation */ 67312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char c; 67412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((c = el->el_display[el->el_cursor.v] 67512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala [el->el_cursor.h]) != '\0') { 67612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_overwrite(el, &c, (size_t)1); 67712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef WIDECHAR 67812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (el->el_display[el->el_cursor.v] 67912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala [el->el_cursor.h] == MB_FILL_CHAR) 68012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h++; 68112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 68212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 68312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, ' '); 68412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = 1; 68512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 68612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 68712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else /* no wrap, but cursor stays on screen */ 68812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h = el->el_terminal.t_size.h - 1; 68912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 69012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 69112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 69212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 69312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_deletechars(): 69412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Delete num characters 69512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 69612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 69712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_deletechars(EditLine *el, int num) 69812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 69912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (num <= 0) 70012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 70112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 70212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!EL_CAN_DELETE) { 70312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_EDIT 70412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, " ERROR: cannot delete \n"); 70512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_EDIT */ 70612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 70712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 70812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (num > el->el_terminal.t_size.h) { 70912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_SCREEN 71012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 71112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "terminal_deletechars: num is riduculous: %d\r\n", num); 71212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_SCREEN */ 71312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 71412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 71512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_DC)) /* if I have multiple delete */ 71612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((num > 1) || !GoodStr(T_dc)) { /* if dc would be more 71712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * expen. */ 71812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_DC), num, num), num); 71912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 72012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 72112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_dm)) /* if I have delete mode */ 72212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_dm), 1); 72312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 72412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_dc)) /* else do one at a time */ 72512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (num--) 72612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_dc), 1); 72712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 72812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_ed)) /* if I have delete mode */ 72912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ed), 1); 73012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 73112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 73212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 73312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_insertwrite(): 73412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Puts terminal in insert character mode or inserts num 73512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * characters in the line 73612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Assumes MB_FILL_CHARs are present to keep column count correct 73712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 73812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 73912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_insertwrite(EditLine *el, Char *cp, int num) 74012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 74112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (num <= 0) 74212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 74312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!EL_CAN_INSERT) { 74412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_EDIT 74512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, " ERROR: cannot insert \n"); 74612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_EDIT */ 74712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 74812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 74912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (num > el->el_terminal.t_size.h) { 75012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef DEBUG_SCREEN 75112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 75212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "StartInsert: num is riduculous: %d\r\n", num); 75312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif /* DEBUG_SCREEN */ 75412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 75512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 75612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_IC)) /* if I have multiple insert */ 75712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if ((num > 1) || !GoodStr(T_ic)) { 75812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* if ic would be more expensive */ 75912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(Str(T_IC), num, num), num); 76012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_overwrite(el, cp, (size_t)num); 76112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* this updates el_cursor.h */ 76212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 76312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 76412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_im) && GoodStr(T_ei)) { /* if I have insert mode */ 76512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_im), 1); 76612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 76712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h += num; 76812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala do 76912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, *cp++); 77012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (--num); 77112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 77212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_ip)) /* have to make num chars insert */ 77312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ip), 1); 77412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 77512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ei), 1); 77612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 77712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 77812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala do { 77912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_ic)) /* have to make num chars insert */ 78012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ic), 1); 78112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 78212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, *cp++); 78312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 78412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h++; 78512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 78612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_ip)) /* have to make num chars insert */ 78712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ip), 1); 78812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* pad the inserted char */ 78912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 79012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } while (--num); 79112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 79212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 79312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 79412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_clear_EOL(): 79512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * clear to end of line. There are num characters to clear 79612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 79712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 79812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_clear_EOL(EditLine *el, int num) 79912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 80012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i; 80112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 80212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_CAN_CEOL && GoodStr(T_ce)) 80312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ce), 1); 80412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { 80512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < num; i++) 80612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, ' '); 80712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_cursor.h += num; /* have written num spaces */ 80812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 80912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 81012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 81112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 81212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_clear_screen(): 81312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Clear the screen 81412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 81512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 81612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_clear_screen(EditLine *el) 81712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ /* clear the whole screen and home */ 81812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 81912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_cl)) 82012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* send the clear screen code */ 82112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_cl), Val(T_li)); 82212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else if (GoodStr(T_ho) && GoodStr(T_cd)) { 82312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_ho), Val(T_li)); /* home */ 82412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* clear to bottom of screen */ 82512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_cd), Val(T_li)); 82612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 82712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\r'); 82812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\n'); 82912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 83012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 83112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 83212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 83312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_beep(): 83412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Beep the way the terminal wants us 83512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 83612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 83712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_beep(EditLine *el) 83812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 83912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (GoodStr(T_bl)) 84012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* what termcap says we should use */ 84112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, Str(T_bl), 1); 84212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else 84312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__putc(el, '\007'); /* an ASCII bell; ^G */ 84412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 84512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 84612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 84712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 84812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_get(EditLine *el, const char **term) 84912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 85012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *term = el->el_terminal.t_name; 85112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 85212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 85312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 85412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_set(): 85512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Read in the terminal capabilities from the requested terminal 85612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 85712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 85812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_set(EditLine *el, const char *term) 85912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 86012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i; 86112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char buf[TC_BUFSIZE]; 86212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *area; 86312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapstr *t; 86412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala sigset_t oset, nset; 86512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int lins, cols; 86612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 86712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) sigemptyset(&nset); 86812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) sigaddset(&nset, SIGWINCH); 86912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) sigprocmask(SIG_BLOCK, &nset, &oset); 87012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 87112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala area = buf; 87212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 87312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 87412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (term == NULL) 87512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala term = getenv("TERM"); 87612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 87712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!term || !term[0]) 87812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala term = "dumb"; 87912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 88012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(term, "emacs") == 0) 88112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_flags |= EDIT_DISABLED; 88212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 88312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) memset(el->el_terminal.t_cap, 0, TC_BUFSIZE); 88412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 88512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i = tgetent(el->el_terminal.t_cap, term); 88612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 88712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (i <= 0) { 88812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (i == -1) 88912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 89012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "Cannot read termcap database;\n"); 89112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else if (i == 0) 89212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 89312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "No entry for terminal type \"%s\";\n", term); 89412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 89512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "using dumb terminal settings.\n"); 89612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_co) = 80; /* do a dumb terminal */ 89712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_pt) = Val(T_km) = Val(T_li) = 0; 89812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_xt) = Val(T_MT); 89912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (t = tstr; t->name != NULL; t++) 90012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_alloc(el, t, NULL); 90112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 90212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* auto/magic margins */ 90312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_am) = tgetflag("am"); 90412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_xn) = tgetflag("xn"); 90512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* Can we tab */ 90612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_pt) = tgetflag("pt"); 90712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_xt) = tgetflag("xt"); 90812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* do we have a meta? */ 90912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_km) = tgetflag("km"); 91012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_MT) = tgetflag("MT"); 91112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* Get the size */ 91212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_co) = tgetnum("co"); 91312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_li) = tgetnum("li"); 91412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (t = tstr; t->name != NULL; t++) { 91512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* XXX: some systems' tgetstr needs non const */ 91612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_alloc(el, t, tgetstr(strchr(t->name, *t->name), 91712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala &area)); 91812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 91912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 92012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 92112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (Val(T_co) < 2) 92212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_co) = 80; /* just in case */ 92312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (Val(T_li) < 1) 92412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_li) = 24; 92512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 92612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_size.v = Val(T_co); 92712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_size.h = Val(T_li); 92812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 92912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_setflags(el); 93012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 93112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* get the correct window size */ 93212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) terminal_get_size(el, &lins, &cols); 93312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (terminal_change_size(el, lins, cols) == -1) 93412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 93512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) sigprocmask(SIG_SETMASK, &oset, NULL); 93612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_bind_arrow(el); 93712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_name = term; 93812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return i <= 0 ? -1 : 0; 93912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 94012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 94112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 94212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_get_size(): 94312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Return the new window size in lines and cols, and 94412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * true if the size was changed. 94512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 94612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 94712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_get_size(EditLine *el, int *lins, int *cols) 94812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 94912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 95012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *cols = Val(T_co); 95112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *lins = Val(T_li); 95212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 95312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef TIOCGWINSZ 95412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { 95512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala struct winsize ws; 95612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ioctl(el->el_infd, TIOCGWINSZ, &ws) != -1) { 95712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ws.ws_col) 95812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *cols = ws.ws_col; 95912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ws.ws_row) 96012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *lins = ws.ws_row; 96112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 96212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 96312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 96412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef TIOCGSIZE 96512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala { 96612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala struct ttysize ts; 96712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ioctl(el->el_infd, TIOCGSIZE, &ts) != -1) { 96812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ts.ts_cols) 96912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *cols = ts.ts_cols; 97012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ts.ts_lines) 97112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *lins = ts.ts_lines; 97212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 97312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 97412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 97512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return Val(T_co) != *cols || Val(T_li) != *lins; 97612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 97712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 97812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 97912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_change_size(): 98012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Change the size of the terminal 98112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 98212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 98312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_change_size(EditLine *el, int lins, int cols) 98412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 98512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 98612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Just in case 98712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 98812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_co) = (cols < 2) ? 80 : cols; 98912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_li) = (lins < 1) ? 24 : lins; 99012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 99112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* re-make display buffers */ 99212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (terminal_rebuffer_display(el) == -1) 99312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 99412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala re_clear_display(el); 99512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 99612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 99712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 99812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 99912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_init_arrow(): 100012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Initialize the arrow key bindings from termcap 100112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 100212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void 100312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_init_arrow(EditLine *el) 100412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 100512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala funckey_t *arrow = el->el_terminal.t_fkey; 100612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 100712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DN].name = STR("down"); 100812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DN].key = T_kd; 100912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DN].fun.cmd = ED_NEXT_HISTORY; 101012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DN].type = XK_CMD; 101112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 101212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_UP].name = STR("up"); 101312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_UP].key = T_ku; 101412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_UP].fun.cmd = ED_PREV_HISTORY; 101512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_UP].type = XK_CMD; 101612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 101712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_LT].name = STR("left"); 101812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_LT].key = T_kl; 101912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_LT].fun.cmd = ED_PREV_CHAR; 102012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_LT].type = XK_CMD; 102112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 102212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_RT].name = STR("right"); 102312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_RT].key = T_kr; 102412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_RT].fun.cmd = ED_NEXT_CHAR; 102512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_RT].type = XK_CMD; 102612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 102712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_HO].name = STR("home"); 102812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_HO].key = T_kh; 102912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_HO].fun.cmd = ED_MOVE_TO_BEG; 103012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_HO].type = XK_CMD; 103112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 103212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_EN].name = STR("end"); 103312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_EN].key = T_at7; 103412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_EN].fun.cmd = ED_MOVE_TO_END; 103512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_EN].type = XK_CMD; 103612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 103712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DE].name = STR("delete"); 103812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DE].key = T_kD; 103912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DE].fun.cmd = ED_DELETE_NEXT_CHAR; 104012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[A_K_DE].type = XK_CMD; 104112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 104212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 104312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 104412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_reset_arrow(): 104512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Reset arrow key bindings 104612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 104712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void 104812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_reset_arrow(EditLine *el) 104912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 105012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala funckey_t *arrow = el->el_terminal.t_fkey; 105112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char strA[] = {033, '[', 'A', '\0'}; 105212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char strB[] = {033, '[', 'B', '\0'}; 105312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char strC[] = {033, '[', 'C', '\0'}; 105412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char strD[] = {033, '[', 'D', '\0'}; 105512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char strH[] = {033, '[', 'H', '\0'}; 105612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char strF[] = {033, '[', 'F', '\0'}; 105712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char stOA[] = {033, 'O', 'A', '\0'}; 105812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char stOB[] = {033, 'O', 'B', '\0'}; 105912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char stOC[] = {033, 'O', 'C', '\0'}; 106012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char stOD[] = {033, 'O', 'D', '\0'}; 106112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char stOH[] = {033, 'O', 'H', '\0'}; 106212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const Char stOF[] = {033, 'O', 'F', '\0'}; 106312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 106412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, strA, &arrow[A_K_UP].fun, arrow[A_K_UP].type); 106512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, strB, &arrow[A_K_DN].fun, arrow[A_K_DN].type); 106612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, strC, &arrow[A_K_RT].fun, arrow[A_K_RT].type); 106712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, strD, &arrow[A_K_LT].fun, arrow[A_K_LT].type); 106812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, strH, &arrow[A_K_HO].fun, arrow[A_K_HO].type); 106912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, strF, &arrow[A_K_EN].fun, arrow[A_K_EN].type); 107012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, stOA, &arrow[A_K_UP].fun, arrow[A_K_UP].type); 107112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, stOB, &arrow[A_K_DN].fun, arrow[A_K_DN].type); 107212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, stOC, &arrow[A_K_RT].fun, arrow[A_K_RT].type); 107312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, stOD, &arrow[A_K_LT].fun, arrow[A_K_LT].type); 107412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, stOH, &arrow[A_K_HO].fun, arrow[A_K_HO].type); 107512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, stOF, &arrow[A_K_EN].fun, arrow[A_K_EN].type); 107612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 107712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_map.type != MAP_VI) 107812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 107912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &strA[1], &arrow[A_K_UP].fun, arrow[A_K_UP].type); 108012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &strB[1], &arrow[A_K_DN].fun, arrow[A_K_DN].type); 108112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &strC[1], &arrow[A_K_RT].fun, arrow[A_K_RT].type); 108212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &strD[1], &arrow[A_K_LT].fun, arrow[A_K_LT].type); 108312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &strH[1], &arrow[A_K_HO].fun, arrow[A_K_HO].type); 108412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &strF[1], &arrow[A_K_EN].fun, arrow[A_K_EN].type); 108512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &stOA[1], &arrow[A_K_UP].fun, arrow[A_K_UP].type); 108612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &stOB[1], &arrow[A_K_DN].fun, arrow[A_K_DN].type); 108712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &stOC[1], &arrow[A_K_RT].fun, arrow[A_K_RT].type); 108812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &stOD[1], &arrow[A_K_LT].fun, arrow[A_K_LT].type); 108912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &stOH[1], &arrow[A_K_HO].fun, arrow[A_K_HO].type); 109012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, &stOF[1], &arrow[A_K_EN].fun, arrow[A_K_EN].type); 109112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 109212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 109312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 109412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_set_arrow(): 109512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Set an arrow key binding 109612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 109712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 109812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_set_arrow(EditLine *el, const Char *name, keymacro_value_t *fun, 109912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int type) 110012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 110112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala funckey_t *arrow = el->el_terminal.t_fkey; 110212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i; 110312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 110412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < A_K_NKEYS; i++) 110512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (Strcmp(name, arrow[i].name) == 0) { 110612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[i].fun = *fun; 110712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[i].type = type; 110812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 110912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 111012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 111112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 111212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 111312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 111412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_clear_arrow(): 111512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Clear an arrow key binding 111612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 111712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 111812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_clear_arrow(EditLine *el, const Char *name) 111912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 112012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala funckey_t *arrow = el->el_terminal.t_fkey; 112112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i; 112212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 112312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < A_K_NKEYS; i++) 112412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (Strcmp(name, arrow[i].name) == 0) { 112512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[i].type = XK_NOD; 112612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 112712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 112812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 112912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 113012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 113112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 113212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_print_arrow(): 113312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Print the arrow key bindings 113412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 113512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 113612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_print_arrow(EditLine *el, const Char *name) 113712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 113812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i; 113912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala funckey_t *arrow = el->el_terminal.t_fkey; 114012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 114112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < A_K_NKEYS; i++) 114212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*name == '\0' || Strcmp(name, arrow[i].name) == 0) 114312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (arrow[i].type != XK_NOD) 114412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_kprint(el, arrow[i].name, 114512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala &arrow[i].fun, arrow[i].type); 114612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 114712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 114812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 114912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_bind_arrow(): 115012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Bind the arrow keys 115112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 115212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 115312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_bind_arrow(EditLine *el) 115412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 115512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el_action_t *map; 115612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const el_action_t *dmap; 115712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int i, j; 115812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *p; 115912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala funckey_t *arrow = el->el_terminal.t_fkey; 116012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 116112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* Check if the components needed are initialized */ 116212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_buf == NULL || el->el_map.key == NULL) 116312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return; 116412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 116512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala map = el->el_map.type == MAP_VI ? el->el_map.alt : el->el_map.key; 116612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala dmap = el->el_map.type == MAP_VI ? el->el_map.vic : el->el_map.emacs; 116712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 116812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_reset_arrow(el); 116912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 117012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (i = 0; i < A_K_NKEYS; i++) { 117112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char wt_str[VISUAL_WIDTH_MAX]; 117212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char *px; 117312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala size_t n; 117412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 117512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala p = el->el_terminal.t_str[arrow[i].key]; 117612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!p || !*p) 117712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala continue; 117812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (n = 0; n < VISUAL_WIDTH_MAX && p[n]; ++n) 117912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala wt_str[n] = p[n]; 118012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala while (n < VISUAL_WIDTH_MAX) 118112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala wt_str[n++] = '\0'; 118212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala px = wt_str; 118312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala j = (unsigned char) *p; 118412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 118512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Assign the arrow keys only if: 118612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 118712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 1. They are multi-character arrow keys and the user 118812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * has not re-assigned the leading character, or 118912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * has re-assigned the leading character to be 119012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * ED_SEQUENCE_LEAD_IN 119112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * 2. They are single arrow keys pointing to an 119212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * unassigned key. 119312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 119412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (arrow[i].type == XK_NOD) 119512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_clear(el, map, px); 119612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { 119712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (p[1] && (dmap[j] == map[j] || 119812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala map[j] == ED_SEQUENCE_LEAD_IN)) { 119912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, px, &arrow[i].fun, 120012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[i].type); 120112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala map[j] = ED_SEQUENCE_LEAD_IN; 120212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (map[j] == ED_UNASSIGNED) { 120312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_clear(el, map, px); 120412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (arrow[i].type == XK_CMD) 120512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala map[j] = arrow[i].fun.cmd; 120612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else 120712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala keymacro_add(el, px, &arrow[i].fun, 120812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arrow[i].type); 120912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 121012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 121112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 121212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 121312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 121412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_putc(): 121512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Add a character 121612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 121712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate int 121812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_putc(int c) 121912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 122012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (terminal_outfile == NULL) 122112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 122212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return fputc(c, terminal_outfile); 122312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 122412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 122512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprivate void 122612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_tputs(EditLine *el, const char *cap, int affcnt) 122712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 122812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef _REENTRANT 122912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala pthread_mutex_lock(&terminal_mutex); 123012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 123112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_outfile = el->el_outfile; 123212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void)tputs(cap, affcnt, terminal_putc); 123312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#ifdef _REENTRANT 123412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala pthread_mutex_unlock(&terminal_mutex); 123512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala#endif 123612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 123712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 123812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal__putc(): 123912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Add a character 124012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 124112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 124212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal__putc(EditLine *el, Int c) 124312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 124412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char buf[MB_LEN_MAX +1]; 124512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ssize_t i; 124612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (c == (Int)MB_FILL_CHAR) 124712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 124812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i = ct_encode_char(buf, (size_t)MB_LEN_MAX, c); 124912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (i <= 0) 125012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return (int)i; 125112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala buf[i] = '\0'; 125212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return fputs(buf, el->el_outfile); 125312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 125412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 125512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal__flush(): 125612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Flush output 125712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 125812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 125912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal__flush(EditLine *el) 126012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 126112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 126212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fflush(el->el_outfile); 126312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 126412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 126512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_writec(): 126612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Write the given character out, in a human readable form 126712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 126812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected void 126912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_writec(EditLine *el, Int c) 127012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 127112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char visbuf[VISUAL_WIDTH_MAX +1]; 127212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ssize_t vcnt = ct_visual_char(visbuf, VISUAL_WIDTH_MAX, c); 127312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (vcnt < 0) 127412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala vcnt = 0; 127512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala visbuf[vcnt] = '\0'; 127612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_overwrite(el, visbuf, (size_t)vcnt); 127712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal__flush(el); 127812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 127912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 128012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 128112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_telltc(): 128212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Print the current termcap characteristics 128312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 128412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 128512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/*ARGSUSED*/ 128612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_telltc(EditLine *el, int argc __attribute__((__unused__)), 128712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const Char **argv __attribute__((__unused__))) 128812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 128912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapstr *t; 129012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char **ts; 129112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 129212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, "\n\tYour terminal has the\n"); 129312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, "\tfollowing characteristics:\n\n"); 129412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, "\tIt has %d columns and %d lines\n", 129512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Val(T_co), Val(T_li)); 129612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, 129712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "\tIt has %s meta key\n", EL_HAS_META ? "a" : "no"); 129812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, 129912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "\tIt can%suse tabs\n", EL_CAN_TAB ? " " : "not "); 130012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, "\tIt %s automatic margins\n", 130112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_HAS_AUTO_MARGINS ? "has" : "does not have"); 130212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (EL_HAS_AUTO_MARGINS) 130312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, "\tIt %s magic margins\n", 130412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala EL_HAS_MAGIC_MARGINS ? "has" : "does not have"); 130512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 130612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (t = tstr, ts = el->el_terminal.t_str; t->name != NULL; t++, ts++) { 130712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const char *ub; 130812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*ts && **ts) { 130912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ub = ct_encode_string(ct_visual_string( 131012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ct_decode_string(*ts, &el->el_scratch)), 131112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala &el->el_scratch); 131212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 131312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ub = "(empty)"; 131412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 131512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, "\t%25s (%s) == %s\n", 131612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala t->long_name, t->name, ub); 131712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 131812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fputc('\n', el->el_outfile); 131912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 132012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 132112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 132212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 132312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_settc(): 132412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Change the current terminal characteristics 132512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 132612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 132712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/*ARGSUSED*/ 132812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_settc(EditLine *el, int argc __attribute__((__unused__)), 132912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const Char **argv) 133012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 133112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapstr *ts; 133212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapval *tv; 133312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char what[8], how[8]; 133412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 133512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (argv == NULL || argv[1] == NULL || argv[2] == NULL) 133612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 133712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 133812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala strncpy(what, ct_encode_string(argv[1], &el->el_scratch), sizeof(what)); 133912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala what[sizeof(what) - 1] = '\0'; 134012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala strncpy(how, ct_encode_string(argv[2], &el->el_scratch), sizeof(how)); 134112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala how[sizeof(how) - 1] = '\0'; 134212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 134312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 134412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Do the strings first 134512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 134612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (ts = tstr; ts->name != NULL; ts++) 134712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(ts->name, what) == 0) 134812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 134912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 135012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ts->name != NULL) { 135112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_alloc(el, ts, how); 135212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_setflags(el); 135312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 135412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 135512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 135612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Do the numeric ones second 135712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 135812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (tv = tval; tv->name != NULL; tv++) 135912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(tv->name, what) == 0) 136012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 136112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 136212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (tv->name != NULL) 136312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 136412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 136512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (tv == &tval[T_pt] || tv == &tval[T_km] || 136612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala tv == &tval[T_am] || tv == &tval[T_xn]) { 136712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(how, "yes") == 0) 136812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_val[tv - tval] = 1; 136912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else if (strcmp(how, "no") == 0) 137012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_val[tv - tval] = 0; 137112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else { 137212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 137312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "" FSTR ": Bad value `%s'.\n", argv[0], how); 137412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 137512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 137612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_setflags(el); 137712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (terminal_change_size(el, Val(T_li), Val(T_co)) == -1) 137812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 137912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 138012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 138112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala long i; 138212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *ep; 138312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 138412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i = strtol(how, &ep, 10); 138512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*ep != '\0') { 138612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 138712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "" FSTR ": Bad value `%s'.\n", argv[0], how); 138812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 138912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 139012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_val[tv - tval] = (int) i; 139112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_size.v = Val(T_co); 139212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala el->el_terminal.t_size.h = Val(T_li); 139312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (tv == &tval[T_co] || tv == &tval[T_li]) 139412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (terminal_change_size(el, Val(T_li), Val(T_co)) 139512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala == -1) 139612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 139712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 139812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 139912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 140012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 140112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 140212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_gettc(): 140312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Get the current terminal characteristics 140412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 140512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 140612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/*ARGSUSED*/ 140712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_gettc(EditLine *el, int argc __attribute__((__unused__)), char **argv) 140812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 140912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapstr *ts; 141012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapval *tv; 141112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *what; 141212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala void *how; 141312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 141412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (argv == NULL || argv[1] == NULL || argv[2] == NULL) 141512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 141612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 141712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala what = argv[1]; 141812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala how = argv[2]; 141912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 142012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 142112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Do the strings first 142212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 142312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (ts = tstr; ts->name != NULL; ts++) 142412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(ts->name, what) == 0) 142512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 142612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 142712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (ts->name != NULL) { 142812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *(char **)how = el->el_terminal.t_str[ts - tstr]; 142912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 143012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 143112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 143212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Do the numeric ones second 143312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 143412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (tv = tval; tv->name != NULL; tv++) 143512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(tv->name, what) == 0) 143612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 143712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 143812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (tv->name == NULL) 143912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 144012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 144112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (tv == &tval[T_pt] || tv == &tval[T_km] || 144212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala tv == &tval[T_am] || tv == &tval[T_xn]) { 144312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static char yes[] = "yes"; 144412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static char no[] = "no"; 144512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (el->el_terminal.t_val[tv - tval]) 144612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *(char **)how = yes; 144712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala else 144812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *(char **)how = no; 144912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 145012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else { 145112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *(int *)how = el->el_terminal.t_val[tv - tval]; 145212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 145312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 145412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 145512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 145612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/* terminal_echotc(): 145712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Print the termcap string out with variable substitution 145812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 145912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaprotected int 146012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala/*ARGSUSED*/ 146112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fialaterminal_echotc(EditLine *el, int argc __attribute__((__unused__)), 146212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const Char **argv) 146312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala{ 146412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *cap, *scap; 146512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Char *ep; 146612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int arg_need, arg_cols, arg_rows; 146712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala int verbose = 0, silent = 0; 146812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char *area; 146912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala static const char fmts[] = "%s\n", fmtd[] = "%d\n"; 147012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala const struct termcapstr *t; 147112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala char buf[TC_BUFSIZE]; 147212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala long i; 147312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 147412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala area = buf; 147512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 147612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (argv == NULL || argv[1] == NULL) 147712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 147812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 147912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 148012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (argv[0][0] == '-') { 148112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala switch (argv[0][1]) { 148212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'v': 148312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala verbose = 1; 148412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 148512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 's': 148612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala silent = 1; 148712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 148812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala default: 148912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* stderror(ERR_NAME | ERR_TCUSAGE); */ 149012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 149112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 149212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 149312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 149412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!*argv || *argv[0] == '\0') 149512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 149612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (Strcmp(*argv, STR("tabs")) == 0) { 149712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmts, EL_CAN_TAB ? "yes" : "no"); 149812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 149912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (Strcmp(*argv, STR("meta")) == 0) { 150012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmts, Val(T_km) ? "yes" : "no"); 150112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 150212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (Strcmp(*argv, STR("xn")) == 0) { 150312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmts, EL_HAS_MAGIC_MARGINS ? 150412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "yes" : "no"); 150512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 150612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (Strcmp(*argv, STR("am")) == 0) { 150712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmts, EL_HAS_AUTO_MARGINS ? 150812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "yes" : "no"); 150912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 151012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (Strcmp(*argv, STR("baud")) == 0) { 151112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmtd, (int)el->el_tty.t_speed); 151212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 151312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (Strcmp(*argv, STR("rows")) == 0 || 151412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala Strcmp(*argv, STR("lines")) == 0) { 151512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmtd, Val(T_li)); 151612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 151712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } else if (Strcmp(*argv, STR("cols")) == 0) { 151812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_outfile, fmtd, Val(T_co)); 151912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 152012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 152112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 152212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Try to use our local definition first 152312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 152412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala scap = NULL; 152512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (t = tstr; t->name != NULL; t++) 152612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (strcmp(t->name, 152712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala ct_encode_string(*argv, &el->el_scratch)) == 0) { 152812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala scap = el->el_terminal.t_str[t - tstr]; 152912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 153012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 153112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (t->name == NULL) { 153212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* XXX: some systems' tgetstr needs non const */ 153312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala scap = tgetstr(ct_encode_string((Char*)*argv, &el->el_scratch), &area); 153412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 153512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!scap || scap[0] == '\0') { 153612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 153712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 153812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Termcap parameter `" FSTR "' not found.\n", 153912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *argv); 154012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 154112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 154212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 154312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * Count home many values we need for this capability. 154412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 154512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala for (cap = scap, arg_need = 0; *cap; cap++) 154612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*cap == '%') 154712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala switch (*++cap) { 154812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'd': 154912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case '2': 155012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case '3': 155112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case '.': 155212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case '+': 155312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arg_need++; 155412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 155512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case '%': 155612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case '>': 155712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'i': 155812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'r': 155912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'n': 156012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'B': 156112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 'D': 156212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 156312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala default: 156412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* 156512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala * hpux has lot's of them... 156612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala */ 156712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (verbose) 156812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 156912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: unknown termcap %% `%c'.\n", 157012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *cap); 157112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* This is bad, but I won't complain */ 157212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 157312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 157412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala 157512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala switch (arg_need) { 157612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 0: 157712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 157812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*argv && *argv[0]) { 157912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 158012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 158112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Extra argument `" FSTR "'.\n", 158212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *argv); 158312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 158412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 158512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, scap, 1); 158612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 158712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 1: 158812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 158912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!*argv || *argv[0] == '\0') { 159012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 159112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 159212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Missing argument.\n"); 159312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 159412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 159512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arg_cols = 0; 159612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i = Strtol(*argv, &ep, 10); 159712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*ep != '\0' || i < 0) { 159812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 159912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 160012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Bad value `" FSTR "' for rows.\n", 160112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *argv); 160212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 160312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 160412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arg_rows = (int) i; 160512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 160612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*argv && *argv[0]) { 160712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 160812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 160912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Extra argument `" FSTR 161012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "'.\n", *argv); 161112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 161212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 161312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(scap, arg_cols, arg_rows), 1); 161412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 161512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala default: 161612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* This is wrong, but I will ignore it... */ 161712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (verbose) 161812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 161912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Too many required arguments (%d).\n", 162012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arg_need); 162112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala /* FALLTHROUGH */ 162212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala case 2: 162312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 162412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!*argv || *argv[0] == '\0') { 162512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 162612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 162712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Missing argument.\n"); 162812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 162912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 163012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i = Strtol(*argv, &ep, 10); 163112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*ep != '\0' || i < 0) { 163212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 163312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 163412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Bad value `" FSTR "' for cols.\n", 163512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *argv); 163612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 163712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 163812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arg_cols = (int) i; 163912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 164012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!*argv || *argv[0] == '\0') { 164112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 164212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 164312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Missing argument.\n"); 164412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 164512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 164612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala i = Strtol(*argv, &ep, 10); 164712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*ep != '\0' || i < 0) { 164812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 164912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 165012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Bad value `" FSTR "' for rows.\n", 165112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala *argv); 165212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 165312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 165412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala arg_rows = (int) i; 165512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*ep != '\0') { 165612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 165712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 165812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Bad value `" FSTR "'.\n", *argv); 165912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 166012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 166112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala argv++; 166212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (*argv && *argv[0]) { 166312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala if (!silent) 166412e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala (void) fprintf(el->el_errfile, 166512e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "echotc: Warning: Extra argument `" FSTR 166612e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala "'.\n", *argv); 166712e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return -1; 166812e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 166912e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala terminal_tputs(el, tgoto(scap, arg_cols, arg_rows), arg_rows); 167012e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala break; 167112e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala } 167212e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala return 0; 167312e21689bc88a77c7b5b9b220fec31e049e5ec0fTodd Fiala} 1674