Home | History | Annotate | Line # | Download | only in dev
ite.c revision 1.3
      1 /*
      2  * Copyright (c) 1988 University of Utah.
      3  * Copyright (c) 1990 The Regents of the University of California.
      4  * All rights reserved.
      5  *
      6  * This code is derived from software contributed to Berkeley by
      7  * the Systems Programming Group of the University of Utah Computer
      8  * Science Department.
      9  *
     10  * Redistribution and use in source and binary forms, with or without
     11  * modification, are permitted provided that the following conditions
     12  * are met:
     13  * 1. Redistributions of source code must retain the above copyright
     14  *    notice, this list of conditions and the following disclaimer.
     15  * 2. Redistributions in binary form must reproduce the above copyright
     16  *    notice, this list of conditions and the following disclaimer in the
     17  *    documentation and/or other materials provided with the distribution.
     18  * 3. All advertising materials mentioning features or use of this software
     19  *    must display the following acknowledgement:
     20  *	This product includes software developed by the University of
     21  *	California, Berkeley and its contributors.
     22  * 4. Neither the name of the University nor the names of its contributors
     23  *    may be used to endorse or promote products derived from this software
     24  *    without specific prior written permission.
     25  *
     26  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
     27  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
     28  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     29  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
     30  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     31  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
     32  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     33  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
     34  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
     35  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
     36  * SUCH DAMAGE.
     37  *
     38  *	from: Utah Hdr: ite.c 1.1 90/07/09
     39  *	from: @(#)ite.c	7.6 (Berkeley) 5/16/91
     40 <<<<<<< ite.c
     41  *	$Id: ite.c,v 1.3 1993/09/02 18:08:02 mw Exp $
     42 ||||||| 1.1.1.2
     43  *	$Id: ite.c,v 1.3 1993/09/02 18:08:02 mw Exp $
     44 =======
     45  *	$Id: ite.c,v 1.3 1993/09/02 18:08:02 mw Exp $
     46  *
     47  * Original author: unknown
     48  * Amiga author:: Markus Wild
     49  * Other contributors: Bryan Ford (improved vt100 compability)
     50 >>>>>>> /tmp/T4009622
     51  */
     52 
     53 /*
     54  * Bit-mapped display terminal emulator machine independent code.
     55  * This is a very rudimentary.  Much more can be abstracted out of
     56  * the hardware dependent routines.
     57  */
     58 #include "ite.h"
     59 #if NITE > 0
     60 
     61 #include "grf.h"
     62 
     63 #undef NITE
     64 #define NITE	NGRF
     65 
     66 #include "param.h"
     67 #include "conf.h"
     68 #include "proc.h"
     69 #include "ioctl.h"
     70 #include "tty.h"
     71 #include "systm.h"
     72 #include "malloc.h"
     73 
     74 #include "itevar.h"
     75 #include "iteioctl.h"
     76 #include "kbdmap.h"
     77 
     78 #include "machine/cpu.h"
     79 #include "../amiga/cons.h"
     80 
     81 #ifdef __STDC__
     82 /* automatically generated, as you might guess:-) */
     83 
     84 struct consdev;
     85 struct itesw;
     86 
     87 extern int iteon (dev_t dev, int flag);
     88 extern int iteinit (dev_t dev);
     89 extern int iteoff (dev_t dev, int flag);
     90 extern int iteopen (dev_t dev, int mode, int devtype, struct proc *p);
     91 extern int iteclose (dev_t dev, int flag, int mode, struct proc *p);
     92 extern int iteread (dev_t dev, struct uio *uio, int flag);
     93 extern int itewrite (dev_t dev, struct uio *uio, int flag);
     94 extern int iteioctl (dev_t dev, int cmd, caddr_t addr, int flag);
     95 extern int itestart (register struct tty *tp);
     96 extern int itefilter (register u_char c, enum caller caller);
     97 extern void iteputchar (register int c, dev_t dev);
     98 extern int iteprecheckwrap (register struct ite_softc *ip, register struct itesw *sp);
     99 extern int itecheckwrap (register struct ite_softc *ip, register struct itesw *sp);
    100 extern int itecnprobe (struct consdev *cp);
    101 extern int itecninit (struct consdev *cp);
    102 extern int itecngetc (dev_t dev);
    103 extern int itecnputc (dev_t dev, int c);
    104 static void repeat_handler (int a0, int a1);
    105 static void inline ite_reset(struct ite_softc *ip);
    106 static void ite_dnchar (struct ite_softc *ip, struct itesw *sp, int n);
    107 static void ite_inchar (struct ite_softc *ip, struct itesw *sp, int n);
    108 static void ite_clrtoeol (struct ite_softc *ip, struct itesw *sp);
    109 static void ite_clrtobol (struct ite_softc *ip, struct itesw *sp);
    110 static void ite_clrline (struct ite_softc *ip, struct itesw *sp);
    111 static void ite_clrtoeos (struct ite_softc *ip, struct itesw *sp);
    112 static void ite_clrtobos (struct ite_softc *ip, struct itesw *sp);
    113 static void ite_clrscreen (struct ite_softc *ip, struct itesw *sp);
    114 static void ite_dnline (struct ite_softc *ip, struct itesw *sp, int n);
    115 static void ite_inline (struct ite_softc *ip, struct itesw *sp, int n);
    116 static void ite_lf (struct ite_softc *ip, struct itesw *sp);
    117 static void ite_crlf (struct ite_softc *ip, struct itesw *sp);
    118 static void ite_cr (struct ite_softc *ip, struct itesw *sp);
    119 static void ite_rlf (struct ite_softc *ip, struct itesw *sp);
    120 static int atoi (const char *cp);
    121 static char *index (const char *cp, char ch);
    122 static int ite_argnum (struct ite_softc *ip);
    123 static int ite_zargnum (struct ite_softc *ip);
    124 static void ite_sendstr (struct ite_softc *ip, char *str);
    125 static int strncmp (const char *a, const char *b, int l);
    126 #endif
    127 
    128 
    129 #define set_attr(ip, attr)	((ip)->attribute |= (attr))
    130 #define clr_attr(ip, attr)	((ip)->attribute &= ~(attr))
    131 
    132 extern  int nodev();
    133 
    134 int customc_scroll(),	customc_init(),		customc_deinit();
    135 int customc_clear(),	customc_putc(),		customc_cursor();
    136 
    137 int tiga_scroll(),	tiga_init(),		tiga_deinit();
    138 int tiga_clear(),	tiga_putc(),		tiga_cursor();
    139 
    140 int retina_scroll(),	retina_init(),		retina_deinit();
    141 int retina_clear(),	retina_putc(),		retina_cursor();
    142 
    143 struct itesw itesw[] =
    144 {
    145 	customc_init,		customc_deinit,		0,
    146 	0,			0,			0,
    147 
    148 	tiga_init,		tiga_deinit,		tiga_clear,
    149 	tiga_putc,		tiga_cursor,		tiga_scroll,
    150 
    151 	retina_init,		retina_deinit,		retina_clear,
    152 	retina_putc,		retina_cursor,		retina_scroll,
    153 };
    154 
    155 /*
    156  * # of chars are output in a single itestart() call.
    157  * If this is too big, user processes will be blocked out for
    158  * long periods of time while we are emptying the queue in itestart().
    159  * If it is too small, console output will be very ragged.
    160  */
    161 int	iteburst = 64;
    162 
    163 int	nite = NITE;
    164 
    165 struct  tty *kbd_tty = NULL;
    166 struct	ite_softc *kbd_ip = NULL;
    167 
    168 struct	tty ite_cons1, ite_cons2;
    169 #if 0
    170 struct	tty *ite_tty[NITE] = { &ite_cons1, &ite_cons2 };
    171 #else
    172 struct	tty *ite_tty[NITE];
    173 /* ugh.. */
    174 static int delayed_con_tty = -1;  /* if >= 0 set cn_tp later to that tty.. */
    175 #endif
    176 struct  ite_softc ite_softc[NITE];
    177 
    178 int	itestart();
    179 extern	int ttrstrt();
    180 extern	struct tty *constty;
    181 
    182 /* These are (later..) settable via an ioctl */
    183 int	start_repeat_timo = 20;	/* /100: initial timeout till pressed key repeats */
    184 int	next_repeat_timo  = 3;  /* /100: timeout when repeating for next char */
    185 
    186 #ifdef DO_WEIRD_ATTRIBUTES
    187 /*
    188  * Primary attribute buffer to be used by the first bitmapped console
    189  * found. Secondary displays alloc the attribute buffer as needed.
    190  * Size is based on a 68x128 display, which is currently our largest.
    191  */
    192 u_char  console_attributes[0x2200];
    193 #endif
    194 u_char	console_tabs[256 * NITE];
    195 
    196 /*
    197  * Perform functions necessary to setup device as a terminal emulator.
    198  */
    199 iteon(dev, flag)
    200 	dev_t dev;
    201 {
    202 	int unit = UNIT(dev);
    203 	struct tty *tp = ite_tty[unit];
    204 	struct ite_softc *ip = &ite_softc[unit];
    205 
    206 	if (unit < 0 || unit >= NITE || (ip->flags&ITE_ALIVE) == 0)
    207 		return(ENXIO);
    208 	/* force ite active, overriding graphics mode */
    209 	if (flag & 1) {
    210 		ip->flags |= ITE_ACTIVE;
    211 		ip->flags &= ~(ITE_INGRF|ITE_INITED);
    212 	}
    213 	/* leave graphics mode */
    214 	if (flag & 2) {
    215 		ip->flags &= ~ITE_INGRF;
    216 		if ((ip->flags & ITE_ACTIVE) == 0)
    217 			return(0);
    218 	}
    219 	ip->flags |= ITE_ACTIVE;
    220 	if (ip->flags & ITE_INGRF)
    221 		return(0);
    222 	if (tp && (kbd_tty == NULL || kbd_tty == tp)) {
    223 		kbd_tty = tp;
    224 		kbd_ip = ip;
    225 		kbdenable();
    226 	}
    227 	iteinit(dev);
    228 	return(0);
    229 }
    230 
    231 /* used by the grf layer to reinitialize ite after changing fb parameters */
    232 itereinit(dev)
    233      dev_t dev;
    234 {
    235   int unit = UNIT(dev);
    236   struct ite_softc *ip = &ite_softc[unit];
    237 
    238   ip->flags &= ~ITE_INITED;
    239   iteinit (dev);
    240 }
    241 
    242 iteinit(dev)
    243      dev_t dev;
    244 {
    245 	int unit = UNIT(dev);
    246 	struct ite_softc *ip = &ite_softc[unit];
    247 
    248 	if (ip->flags & ITE_INITED)
    249 		return;
    250 
    251 	bcopy (&ascii_kbdmap, &kbdmap, sizeof (struct kbdmap));
    252 
    253 	ip->cursorx = 0;
    254 	ip->cursory = 0;
    255 	(*itesw[ip->type].ite_init)(ip);
    256 <<<<<<< ite.c
    257 	(*itesw[ip->type].ite_cursor)(ip, DRAW_CURSOR);
    258 ||||||| 1.1.1.2
    259 	(*itesw[ip->type].ite_cursor)(ip, DRAW_CURSOR);
    260 
    261 	/* ip->rows initialized by ite_init above */
    262 	ip->top_margin = 0; ip->bottom_margin = ip->rows - 1;
    263 =======
    264 >>>>>>> /tmp/T4009622
    265 
    266 <<<<<<< ite.c
    267 	/* ip->rows initialized by ite_init above */
    268 	ip->top_margin = 0; ip->bottom_margin = ip->rows - 1;
    269 
    270 	ip->attribute = 0;
    271 ||||||| 1.1.1.2
    272 	ip->attribute = 0;
    273 =======
    274 #ifdef DO_WEIRD_ATTRIBUTES
    275 >>>>>>> /tmp/T4009622
    276 	if (ip->attrbuf == NULL)
    277 		ip->attrbuf = (u_char *)
    278 			malloc(ip->rows * ip->cols, M_DEVBUF, M_WAITOK);
    279 	bzero(ip->attrbuf, (ip->rows * ip->cols));
    280 #endif
    281 	if (! ip->tabs)
    282 	  {
    283 	    /* can't use malloc, as this buffer might be used before
    284 	       the allocators are initialized (console!) */
    285 	    ip->tabs = &console_tabs[unit * 256];
    286 	  }
    287 
    288 	ite_reset (ip);
    289 
    290 	(*itesw[ip->type].ite_cursor)(ip, DRAW_CURSOR);
    291 	ip->flags |= ITE_INITED;
    292 }
    293 
    294 /*
    295  * "Shut down" device as terminal emulator.
    296  * Note that we do not deinit the console device unless forced.
    297  * Deinit'ing the console every time leads to a very active
    298  * screen when processing /etc/rc.
    299  */
    300 iteoff(dev, flag)
    301 	dev_t dev;
    302 {
    303 	register struct ite_softc *ip = &ite_softc[UNIT(dev)];
    304 
    305 	if (flag & 2)
    306 		ip->flags |= ITE_INGRF;
    307 	if ((ip->flags & ITE_ACTIVE) == 0)
    308 		return;
    309 	if ((flag & 1) ||
    310 	    (ip->flags & (ITE_INGRF|ITE_ISCONS|ITE_INITED)) == ITE_INITED)
    311 		(*itesw[ip->type].ite_deinit)(ip);
    312 	if ((flag & 2) == 0)
    313 		ip->flags &= ~ITE_ACTIVE;
    314 }
    315 
    316 /* ARGSUSED */
    317 #ifdef __STDC__
    318 iteopen(dev_t dev, int mode, int devtype, struct proc *p)
    319 #else
    320 iteopen(dev, mode, devtype, p)
    321 	dev_t dev;
    322 	int mode, devtype;
    323 	struct proc *p;
    324 #endif
    325 {
    326 	int unit = UNIT(dev);
    327 	register struct tty *tp;
    328 	register struct ite_softc *ip = &ite_softc[unit];
    329 	register int error;
    330 	int first = 0;
    331 
    332 	if (unit >= NITE)
    333 	  return ENXIO;
    334 
    335 	if(!ite_tty[unit]) {
    336 #if 0
    337 		MALLOC(tp, struct tty *, sizeof(struct tty), M_TTYS, M_WAITOK);
    338 		bzero(tp, sizeof(struct tty));
    339 		ite_tty[unit] = tp;
    340 #else
    341 		tp = ite_tty[unit] = ttymalloc();
    342 		/* HA! caught it finally... */
    343 		if (unit == delayed_con_tty)
    344 		  {
    345 		    extern struct consdev *cn_tab;
    346 		    extern struct tty *cn_tty;
    347 
    348 		    kbd_tty = tp;
    349 		    kbd_ip = ip;
    350 		    kbdenable ();
    351 		    cn_tty = cn_tab->cn_tp = tp;
    352 		    delayed_con_tty = -1;
    353 		  }
    354 #endif
    355 	} else
    356 		tp = ite_tty[unit];
    357 
    358 	if ((tp->t_state&(TS_ISOPEN|TS_XCLUDE)) == (TS_ISOPEN|TS_XCLUDE)
    359 	    && p->p_ucred->cr_uid != 0)
    360 		return (EBUSY);
    361 	if ((ip->flags & ITE_ACTIVE) == 0) {
    362 		error = iteon(dev, 0);
    363 		if (error)
    364 			return (error);
    365 		first = 1;
    366 	}
    367 	tp->t_oproc = itestart;
    368 	tp->t_param = NULL;
    369 	tp->t_dev = dev;
    370 	if ((tp->t_state&TS_ISOPEN) == 0) {
    371 		ttychars(tp);
    372 		tp->t_iflag = TTYDEF_IFLAG;
    373 		tp->t_oflag = TTYDEF_OFLAG;
    374 		tp->t_cflag = CS8|CREAD;
    375 		tp->t_lflag = TTYDEF_LFLAG;
    376 		tp->t_ispeed = tp->t_ospeed = TTYDEF_SPEED;
    377 		/* don't set TS_ISOPEN  here, or the tty queues won't
    378 		   be initialized in ttyopen()! */
    379 		tp->t_state = TS_CARR_ON;
    380 		ttsetwater(tp);
    381 	}
    382 	error = (*linesw[tp->t_line].l_open)(dev, tp);
    383 	if (error == 0) {
    384 		tp->t_winsize.ws_row = ip->rows;
    385 		tp->t_winsize.ws_col = ip->cols;
    386 		ip->open_cnt++;
    387 	} else if (first)
    388 		iteoff(dev, 0);
    389 	return (error);
    390 }
    391 
    392 /*ARGSUSED*/
    393 iteclose(dev, flag, mode, p)
    394 	dev_t dev;
    395 	int flag, mode;
    396 	struct proc *p;
    397 {
    398 	int unit = UNIT(dev);
    399 	register struct tty *tp = ite_tty[unit];
    400 	register struct ite_softc *ip = &ite_softc[unit];
    401 
    402 #if 0
    403 	/* aliasing with /dev/console can lead to such weird problems... */
    404 	if (ip->open_cnt-- > 0)
    405 	  return 0;
    406 #endif
    407 
    408 	if (tp)
    409 	  {
    410 	    (*linesw[tp->t_line].l_close)(tp, flag);
    411 	    ttyclose(tp);
    412 	  }
    413 	iteoff(dev, 0);
    414 #if 0
    415 	if (tp != &ite_cons)
    416 	  {
    417 #if 0
    418 	    FREE(tp, M_TTYS);
    419 #else
    420 	    ttyfree (tp);
    421 #endif
    422 	    ite_tty[UNIT(dev)] = (struct tty *)NULL;
    423 	  }
    424 #endif
    425 	return(0);
    426 }
    427 
    428 iteread(dev, uio, flag)
    429 	dev_t dev;
    430 	struct uio *uio;
    431 {
    432 	register struct tty *tp = ite_tty[UNIT(dev)];
    433 	int rc;
    434 
    435 	if (! tp)
    436 	  return ENXIO;
    437 
    438 	rc = ((*linesw[tp->t_line].l_read)(tp, uio, flag));
    439 	return rc;
    440 }
    441 
    442 itewrite(dev, uio, flag)
    443 	dev_t dev;
    444 	struct uio *uio;
    445 {
    446 	int unit = UNIT(dev);
    447 	register struct tty *tp = ite_tty[unit];
    448 
    449 	if (! tp)
    450 	  return ENXIO;
    451 
    452 	if ((ite_softc[unit].flags & ITE_ISCONS) && constty &&
    453 	    (constty->t_state&(TS_CARR_ON|TS_ISOPEN))==(TS_CARR_ON|TS_ISOPEN))
    454 		tp = constty;
    455 	return ((*linesw[tp->t_line].l_write)(tp, uio, flag));
    456 }
    457 
    458 iteioctl(dev, cmd, addr, flag)
    459 	dev_t dev;
    460 	caddr_t addr;
    461 {
    462 	register struct tty *tp = ite_tty[UNIT(dev)];
    463 	int error;
    464 
    465 	if (! tp)
    466 	  return ENXIO;
    467 
    468 
    469 	error = (*linesw[tp->t_line].l_ioctl)(tp, cmd, addr, flag);
    470 	if (error >= 0)
    471 		return (error);
    472 	error = ttioctl(tp, cmd, addr, flag);
    473 	if (error >= 0)
    474 		return (error);
    475 
    476 	switch (cmd)
    477 	  {
    478 	  case ITELOADKMAP:
    479 	    if (addr)
    480 	      {
    481 		bcopy (addr, &kbdmap, sizeof (struct kbdmap));
    482 		return 0;
    483 	      }
    484 	    else
    485 	      return EFAULT;
    486 
    487 	  case ITEGETKMAP:
    488 	    if (addr)
    489 	      {
    490 		bcopy (&kbdmap, addr, sizeof (struct kbdmap));
    491 		return 0;
    492 	      }
    493 	    else
    494 	      return EFAULT;
    495 	  }
    496 
    497 
    498 	return (ENOTTY);
    499 }
    500 
    501 itestart(tp)
    502 	register struct tty *tp;
    503 {
    504 	register int cc, s;
    505 	int unit = UNIT(tp->t_dev);
    506 	register struct ite_softc *ip = &ite_softc[unit];
    507 	int hiwat = 0;
    508 
    509 	s = spltty();
    510 	if (tp->t_state & (TS_TIMEOUT|TS_BUSY|TS_TTSTOP)) {
    511 		splx(s);
    512 		return;
    513 	}
    514 	tp->t_state |= TS_BUSY;
    515 	cc = tp->t_outq.c_cc;
    516 	if (cc <= tp->t_lowat) {
    517 		if (tp->t_state & TS_ASLEEP) {
    518 			tp->t_state &= ~TS_ASLEEP;
    519 			wakeup((caddr_t) &tp->t_outq);
    520 		}
    521 		selwakeup(&tp->t_wsel);
    522 	}
    523 	/*
    524 	 * Limit the amount of output we do in one burst
    525 	 * to prevent hogging the CPU.
    526 	 */
    527 	if (cc > iteburst) {
    528 		hiwat++;
    529 		cc = iteburst;
    530 	}
    531 	(*itesw[ip->type].ite_cursor)(ip, START_CURSOROPT);
    532 	while (--cc >= 0) {
    533 		register int c;
    534 
    535 		c = getc(&tp->t_outq);
    536 		/*
    537 		 * iteputchar() may take a long time and we don't want to
    538 		 * block all interrupts for long periods of time.  Since
    539 		 * there is no need to stay at high priority while outputing
    540 		 * the character (since we don't have to worry about
    541 		 * interrupts), we don't.  We just need to make sure that
    542 		 * we don't reenter iteputchar, which is guarenteed by the
    543 		 * earlier setting of TS_BUSY.
    544 		 */
    545 		splx(s);
    546 		iteputchar(c, tp->t_dev);
    547 		spltty();
    548 	}
    549 	(*itesw[ip->type].ite_cursor)(ip, END_CURSOROPT);
    550 	if (hiwat) {
    551 		tp->t_state |= TS_TIMEOUT;
    552 		timeout((timeout_t) ttrstrt, (caddr_t) tp, 1);
    553 	}
    554 	tp->t_state &= ~TS_BUSY;
    555 	splx(s);
    556 }
    557 
    558 /* these are used to implement repeating keys.. */
    559 static u_char last_char = 0;
    560 static u_char tout_pending = 0;
    561 
    562 static void
    563 repeat_handler (a0, a1)
    564     int a0, a1;
    565 {
    566   tout_pending = 0;
    567   /* leave it up to itefilter() to possibly install a new callout entry
    568      to reinvoke repeat_handler() */
    569   if (last_char)
    570     {
    571       /* don't call itefilter directly, we're at spl6 here, and have
    572 	 blocked out way too much stuff. Besides, the keyboard wouldn't
    573 	 even have a chance to tell us about key-up events if we
    574 	 did.. */
    575       add_sicallback (itefilter, last_char, ITEFILT_REPEATER);
    576 
    577       /* itefilter (last_char, ITEFILT_REPEATER); */
    578     }
    579 }
    580 
    581 static void inline
    582 itesendch (int ch)
    583 {
    584   (*linesw[kbd_tty->t_line].l_rint)(ch, kbd_tty);
    585 }
    586 
    587 
    588 int
    589 itefilter(c, caller)
    590      register u_char c;
    591      enum caller caller;
    592 {
    593   static u_char mod = 0;
    594   static u_char last_dead = 0;
    595   register unsigned char code, *str;
    596   u_char up, mask, i;
    597   struct key key;
    598   int s;
    599 
    600   if (caller != ITEFILT_CONSOLE && kbd_tty == NULL)
    601      return;
    602 
    603   /* have to make sure we're at spltty in here */
    604   s = spltty ();
    605 
    606   /* keyboard interrupts come at priority 2, while softint-
    607      generated keyboard-repeat interrupts come at level 1.
    608      So, to not allow a key-up event to get thru before
    609      a repeat for the key-down, we remove any outstanding
    610      callout requests.. */
    611   rem_sicallback (itefilter);
    612 
    613   up = c & 0x80 ? 1 : 0;
    614   c &= 0x7f;
    615   code = 0;
    616 
    617   mask = 0;
    618   if (c >= KBD_LEFT_SHIFT)
    619     {
    620       switch (c)
    621         {
    622         case KBD_LEFT_SHIFT:
    623           mask = KBD_MOD_LSHIFT;
    624           break;
    625 
    626         case KBD_RIGHT_SHIFT:
    627           mask = KBD_MOD_RSHIFT;
    628           break;
    629 
    630         case KBD_LEFT_ALT:
    631           mask = KBD_MOD_LALT;
    632           break;
    633 
    634         case KBD_RIGHT_ALT:
    635           mask = KBD_MOD_RALT;
    636           break;
    637 
    638         case KBD_LEFT_META:
    639           mask = KBD_MOD_LMETA;
    640           break;
    641 
    642         case KBD_RIGHT_META:
    643           mask = KBD_MOD_RMETA;
    644           break;
    645 
    646         case KBD_CAPS_LOCK:
    647           /* capslock already behaves `right', don't need to keep track of the
    648              state in here. */
    649           mask = KBD_MOD_CAPS;
    650           break;
    651 
    652         case KBD_CTRL:
    653           mask = KBD_MOD_CTRL;
    654           break;
    655         }
    656 
    657       if (mask)
    658         {
    659           if (up)
    660             mod &= ~mask;
    661           else
    662             mod |= mask;
    663         }
    664 
    665       /* these keys should not repeat, so it's the Right Thing dealing with
    666          repeaters only after this block. */
    667 
    668       /* return even if it wasn't a modifier key, the other codes up here
    669          are either special (like reset warning), or not yet defined */
    670       splx (s);
    671       return -1;
    672     }
    673 
    674   /* no matter which character we're repeating, stop it if we get a key-up
    675      event. I think this is the same thing amigados does. */
    676   if (up)
    677     {
    678       if (tout_pending)
    679         {
    680           untimeout ((timeout_t) repeat_handler, 0);
    681           tout_pending = 0;
    682 	  last_char = 0;
    683         }
    684       splx (s);
    685       return -1;
    686     }
    687 
    688 
    689   /* intercept Ctrl-LAlt-F1 here to switch back to original ascii-keymap.
    690      this should probably be configurable.. */
    691   if (mod == (KBD_MOD_LALT|KBD_MOD_SHIFT) && code == 0x50)
    692     {
    693       bcopy (&ascii_kbdmap, &kbdmap, sizeof (struct kbdmap));
    694       splx (s);
    695       return -1;
    696     }
    697 
    698 
    699   switch (mod & (KBD_MOD_ALT | KBD_MOD_SHIFT))
    700     {
    701     case 0:
    702 	key = kbdmap.keys[c];
    703 	if (!(mod & KBD_MOD_CAPS) || !(key.mode & KBD_MODE_CAPS))
    704 	  break;
    705 	/* FALL INTO */
    706 
    707     case KBD_MOD_LSHIFT:
    708     case KBD_MOD_RSHIFT:
    709     case KBD_MOD_SHIFT:
    710         key = kbdmap.shift_keys[c];
    711         break;
    712 
    713     case KBD_MOD_LALT:
    714     case KBD_MOD_RALT:
    715     case KBD_MOD_ALT:
    716 	key = kbdmap.alt_keys[c];
    717 	if (!(mod & KBD_MOD_CAPS) || !(key.mode & KBD_MODE_CAPS))
    718 	  break;
    719 	/* FALL INTO */
    720 
    721     case KBD_MOD_LALT|KBD_MOD_LSHIFT:
    722     case KBD_MOD_LALT|KBD_MOD_RSHIFT:
    723     case KBD_MOD_LALT|KBD_MOD_SHIFT:
    724     case KBD_MOD_RALT|KBD_MOD_RSHIFT:
    725     case KBD_MOD_RALT|KBD_MOD_SHIFT:
    726     case KBD_MOD_ALT|KBD_MOD_RSHIFT:
    727 	key = kbdmap.alt_shift_keys[c];
    728 	break;
    729     }
    730 
    731   code = key.code;
    732 
    733   /* arrange to repeat the keystroke. By doing this at the level of scan-codes,
    734      we can have function keys, and keys that send strings, repeat too. This
    735      also entitles an additional overhead, since we have to do the conversion
    736      each time, but I guess that's ok. */
    737   if (!tout_pending && caller == ITEFILT_TTY && kbd_ip->key_repeat)
    738     {
    739       tout_pending = 1;
    740       last_char = c;
    741       timeout ((timeout_t) repeat_handler, 0, start_repeat_timo);
    742     }
    743   else if (!tout_pending && caller == ITEFILT_REPEATER && kbd_ip->key_repeat)
    744     {
    745       tout_pending = 1;
    746       last_char = c;
    747       timeout ((timeout_t) repeat_handler, 0, next_repeat_timo);
    748     }
    749 
    750   /* handle dead keys */
    751   if (key.mode & KBD_MODE_DEAD)
    752     {
    753       /* if entered twice, send accent itself */
    754       if (last_dead == key.mode & KBD_MODE_ACCMASK)
    755         last_dead = 0;
    756       else
    757 	{
    758 	  last_dead = key.mode & KBD_MODE_ACCMASK;
    759 	  splx (s);
    760 	  return -1;
    761 	}
    762     }
    763   if (last_dead)
    764     {
    765       /* can't apply dead flag to string-keys */
    766       if (! (key.mode & KBD_MODE_STRING) && code >= '@' && code < 0x7f)
    767         code = acctable[KBD_MODE_ACCENT (last_dead)][code - '@'];
    768 
    769       last_dead = 0;
    770     }
    771 
    772   /* if not string, apply META and CTRL modifiers */
    773   if (! (key.mode & KBD_MODE_STRING))
    774     {
    775       if (mod & KBD_MOD_CTRL)
    776         code &= 0x1f;
    777 
    778       if (mod & KBD_MOD_META)
    779         code |= 0x80;
    780     }
    781   else
    782     {
    783       /* strings are only supported in normal tty mode, not in console mode */
    784       if (caller != ITEFILT_CONSOLE)
    785         {
    786           str = kbdmap.strings + code;
    787           /* using a length-byte instead of 0-termination allows to embed \0 into
    788              strings, although this is not used in the default keymap */
    789           for (i = *str++; i; i--)
    790             itesendch(*str++);
    791         }
    792       splx (s);
    793       return -1;
    794     }
    795 
    796   if (caller == ITEFILT_CONSOLE)
    797     {
    798       /* do the conversion here because raw console input doesn't go thru
    799 	 tty conversions */
    800       code = code == '\r' ? '\n' : code;
    801       splx (s);
    802       return code;
    803     }
    804   else
    805     /* NOTE: *don't* do any cr->crlf conversion here, this is input
    806 	     processing, the mentioned conversion should only be
    807 	     done for output processing (for input, it is not
    808 	     terminal-specific but depends on tty-settings!) */
    809     (*linesw[kbd_tty->t_line].l_rint)(code, kbd_tty);
    810 
    811   splx (s);
    812   return -1;
    813 }
    814 
    815 
    816 /* helper functions, makes the code below more readable */
    817 static void inline
    818 ite_sendstr (ip, str)
    819     struct ite_softc *ip;
    820     char *str;
    821 {
    822   while (*str)
    823     itesendch (*str++);
    824 }
    825 
    826 static void
    827 alignment_display(struct ite_softc *ip, struct itesw *sp)
    828 {
    829   int i, j;
    830 
    831   for (j = 0; j < ip->rows; j++)
    832     for (i = 0; i < ip->cols; i++)
    833       (*sp->ite_putc)(ip, 'E', j, i, ATTR_NOR);
    834   attrclr(ip, 0, 0, ip->rows, ip->cols);
    835   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    836 }
    837 
    838 static void inline
    839 snap_cury(struct ite_softc *ip, struct itesw *sp)
    840 {
    841   if (ip->inside_margins)
    842     {
    843       if (ip->cury < ip->top_margin)
    844 	ip->cury = ip->top_margin;
    845       if (ip->cury > ip->bottom_margin)
    846 	ip->cury = ip->bottom_margin;
    847     }
    848 }
    849 
    850 static void inline
    851 ite_dnchar(ip, sp, n)
    852      struct ite_softc *ip;
    853      struct itesw *sp;
    854      int n;
    855 {
    856   n = MIN(n, ip->cols - ip->curx);
    857   if (n < ip->cols - ip->curx)
    858     {
    859       (*sp->ite_scroll)(ip, ip->cury, ip->curx + n, n, SCROLL_LEFT);
    860       attrmov(ip, ip->cury, ip->curx + n, ip->cury, ip->curx,
    861 	      1, ip->cols - ip->curx - n);
    862       attrclr(ip, ip->cury, ip->cols - n, 1, n);
    863     }
    864   while (n-- > 0)
    865     (*sp->ite_putc)(ip, ' ', ip->cury, ip->cols - n - 1, ATTR_NOR);
    866   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    867 }
    868 
    869 static void inline
    870 ite_inchar(ip, sp, n)
    871      struct ite_softc *ip;
    872      struct itesw *sp;
    873      int n;
    874 {
    875   n = MIN(n, ip->cols - ip->curx);
    876   if (n < ip->cols - ip->curx)
    877     {
    878       (*sp->ite_scroll)(ip, ip->cury, ip->curx, n, SCROLL_RIGHT);
    879       attrmov(ip, ip->cury, ip->curx, ip->cury, ip->curx + n,
    880 	      1, ip->cols - ip->curx - n);
    881       attrclr(ip, ip->cury, ip->curx, 1, n);
    882     }
    883   while (n--)
    884     (*sp->ite_putc)(ip, ' ', ip->cury, ip->curx + n, ATTR_NOR);
    885   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    886 }
    887 
    888 static void inline
    889 ite_clrtoeol(ip, sp)
    890      struct ite_softc *ip;
    891      struct itesw *sp;
    892 {
    893   int y = ip->cury, x = ip->curx;
    894   if (ip->cols - x > 0)
    895     {
    896       (*sp->ite_clear)(ip, y, x, 1, ip->cols - x);
    897       attrclr(ip, y, x, 1, ip->cols - x);
    898       (*sp->ite_cursor)(ip, DRAW_CURSOR);
    899     }
    900 }
    901 
    902 static void inline
    903 ite_clrtobol(ip, sp)
    904      struct ite_softc *ip;
    905      struct itesw *sp;
    906 {
    907   int y = ip->cury, x = MIN(ip->curx + 1, ip->cols);
    908   (*sp->ite_clear)(ip, y, 0, 1, x);
    909   attrclr(ip, y, 0, 1, x);
    910   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    911 }
    912 
    913 static void inline
    914 ite_clrline(ip, sp)
    915      struct ite_softc *ip;
    916      struct itesw *sp;
    917 {
    918   int y = ip->cury;
    919   (*sp->ite_clear)(ip, y, 0, 1, ip->cols);
    920   attrclr(ip, y, 0, 1, ip->cols);
    921   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    922 }
    923 
    924 
    925 
    926 static void inline
    927 ite_clrtoeos(ip, sp)
    928      struct ite_softc *ip;
    929      struct itesw *sp;
    930 {
    931   ite_clrtoeol(ip, sp);
    932   if (ip->cury < ip->rows - 1)
    933     {
    934       (*sp->ite_clear)(ip, ip->cury + 1, 0, ip->rows - 1 - ip->cury, ip->cols);
    935       attrclr(ip, ip->cury, 0, ip->rows - ip->cury, ip->cols);
    936       (*sp->ite_cursor)(ip, DRAW_CURSOR);
    937     }
    938 }
    939 
    940 static void inline
    941 ite_clrtobos(ip, sp)
    942      struct ite_softc *ip;
    943      struct itesw *sp;
    944 {
    945   ite_clrtobol(ip, sp);
    946   if (ip->cury > 0)
    947     {
    948       (*sp->ite_clear)(ip, 0, 0, ip->cury, ip->cols);
    949       attrclr(ip, 0, 0, ip->cury, ip->cols);
    950       (*sp->ite_cursor)(ip, DRAW_CURSOR);
    951     }
    952 }
    953 
    954 static void inline
    955 ite_clrscreen(ip, sp)
    956      struct ite_softc *ip;
    957      struct itesw *sp;
    958 {
    959   (*sp->ite_clear)(ip, 0, 0, ip->rows, ip->cols);
    960   attrclr(ip, 0, 0, ip->rows, ip->cols);
    961   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    962 }
    963 
    964 
    965 
    966 static void inline
    967 ite_dnline(ip, sp, n)
    968      struct ite_softc *ip;
    969      struct itesw *sp;
    970      int n;
    971 {
    972   n = MIN(n, ip->bottom_margin + 1 - ip->cury);
    973   if (n <= ip->bottom_margin - ip->cury)
    974     {
    975       (*sp->ite_scroll)(ip, ip->cury + n, 0, n, SCROLL_UP);
    976       attrmov(ip, ip->cury + n, 0, ip->cury, 0,
    977 	      ip->bottom_margin + 1 - ip->cury - n, ip->cols);
    978     }
    979   (*sp->ite_clear)(ip, ip->bottom_margin - n + 1, 0, n, ip->cols);
    980   attrclr(ip, ip->bottom_margin - n + 1, 0, n, ip->cols);
    981   (*sp->ite_cursor)(ip, DRAW_CURSOR);
    982 }
    983 
    984 static void inline
    985 ite_inline(ip, sp, n)
    986      struct ite_softc *ip;
    987      struct itesw *sp;
    988      int n;
    989 {
    990   if ((ip->cury >= ip->top_margin) && (ip->cury <= ip->bottom_margin))
    991     {
    992       n = MIN(n, ip->bottom_margin + 1 - ip->cury);
    993       if (n <= ip->bottom_margin - ip->cury)
    994 	{
    995 	  (*sp->ite_scroll)(ip, ip->cury, 0, n, SCROLL_DOWN);
    996 	  attrmov(ip, ip->cury, 0, ip->cury + n, 0,
    997 		  ip->bottom_margin + 1 - ip->cury - n, ip->cols);
    998 	}
    999       (*sp->ite_clear)(ip, ip->cury, 0, n, ip->cols);
   1000       attrclr(ip, ip->cury, 0, n, ip->cols);
   1001       (*sp->ite_cursor)(ip, DRAW_CURSOR);
   1002     }
   1003 }
   1004 
   1005 static void inline
   1006 ite_lf (ip, sp)
   1007      struct ite_softc *ip;
   1008      struct itesw *sp;
   1009 {
   1010   if (ip->inside_margins)
   1011     {
   1012       ++ip->cury;
   1013       if ((ip->cury == ip->bottom_margin+1) || (ip->cury == ip->rows))
   1014         {
   1015           ip->cury--;
   1016           (*sp->ite_scroll)(ip, ip->top_margin + 1, 0, 1, SCROLL_UP);
   1017           ite_clrline(ip, sp);
   1018         }
   1019       (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1020     }
   1021   else
   1022     {
   1023       if (++ip->cury >= ip->rows)
   1024         {
   1025           ip->cury = ip->rows - 1;
   1026           (*sp->ite_scroll)(ip, 1, 0, 1, SCROLL_UP);
   1027           ite_clrline(ip, sp);
   1028         }
   1029       (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1030     }
   1031   clr_attr(ip, ATTR_INV);
   1032 }
   1033 
   1034 static void inline
   1035 ite_crlf (ip, sp)
   1036      struct ite_softc *ip;
   1037      struct itesw *sp;
   1038 {
   1039   ip->curx = 0;
   1040   ite_lf (ip, sp);
   1041 }
   1042 
   1043 static void inline
   1044 ite_cr (ip, sp)
   1045      struct ite_softc *ip;
   1046      struct itesw *sp;
   1047 {
   1048   if (ip->curx)
   1049     {
   1050       ip->curx = 0;
   1051       (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1052     }
   1053 }
   1054 
   1055 static void inline
   1056 ite_rlf (ip, sp)
   1057      struct ite_softc *ip;
   1058      struct itesw *sp;
   1059 {
   1060   int top = ip->inside_margins ? ip->top_margin : 0;
   1061 
   1062   ip->cury--;
   1063   if ((ip->cury < 0) || (ip->cury == top-1))
   1064     {
   1065       ip->cury++;
   1066       (*sp->ite_scroll)(ip, top, 0, 1, SCROLL_DOWN);
   1067       ite_clrline(ip, sp);
   1068     }
   1069   (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1070   clr_attr(ip, ATTR_INV);
   1071 }
   1072 
   1073 static int inline
   1074 atoi (cp)
   1075     const char *cp;
   1076 {
   1077   int n;
   1078 
   1079   for (n = 0; *cp && *cp >= '0' && *cp <= '9'; cp++)
   1080     n = n * 10 + *cp - '0';
   1081 
   1082   return n;
   1083 }
   1084 
   1085 static char *
   1086 index (cp, ch)
   1087     const char *cp;
   1088     char ch;
   1089 {
   1090   while (*cp && *cp != ch) cp++;
   1091   return *cp ? (char *) cp : 0;
   1092 }
   1093 
   1094 
   1095 
   1096 static int inline
   1097 ite_argnum (ip)
   1098     struct ite_softc *ip;
   1099 {
   1100   char ch;
   1101   int n;
   1102 
   1103   /* convert argument string into number */
   1104   if (ip->ap == ip->argbuf)
   1105     return 1;
   1106   ch = *ip->ap;
   1107   *ip->ap = 0;
   1108   n = atoi (ip->argbuf);
   1109   *ip->ap = ch;
   1110 
   1111   return n;
   1112 }
   1113 
   1114 static int inline
   1115 ite_zargnum (ip)
   1116     struct ite_softc *ip;
   1117 {
   1118   char ch, *cp;
   1119   int n;
   1120 
   1121   /* convert argument string into number */
   1122   if (ip->ap == ip->argbuf)
   1123     return 0;
   1124   ch = *ip->ap;
   1125   *ip->ap = 0;
   1126   n = atoi (ip->argbuf);
   1127   *ip->ap = ch;
   1128 
   1129   return n;	/* don't "n ? n : 1" here, <CSI>0m != <CSI>1m ! */
   1130 }
   1131 
   1132 static int inline
   1133 strncmp (a, b, l)
   1134     const char *a, *b;
   1135     int l;
   1136 {
   1137   for (;l--; a++, b++)
   1138     if (*a != *b)
   1139       return *a - *b;
   1140   return 0;
   1141 }
   1142 
   1143 static void inline
   1144 ite_reset(ip)
   1145     struct ite_softc *ip;
   1146 {
   1147   int i;
   1148 
   1149   ip->curx = 0;
   1150   ip->cury = 0;
   1151   ip->attribute = 0;
   1152   ip->save_curx = 0;
   1153   ip->save_cury = 0;
   1154   ip->save_attribute = 0;
   1155   ip->ap = ip->argbuf;
   1156   ip->emul_level = EMUL_VT300_7;
   1157   ip->eightbit_C1 = 0;
   1158   ip->top_margin = 0; ip->bottom_margin = ip->rows - 1;
   1159   ip->inside_margins = 1;
   1160   ip->linefeed_newline = 0;
   1161   ip->auto_wrap = 0;
   1162   ip->cursor_appmode = 0;
   1163   ip->keypad_appmode = 0;
   1164   ip->imode = 0;
   1165   ip->key_repeat = 1;
   1166 
   1167 #ifdef DO_WEIRD_ATTRIBUTES
   1168   bzero(ip->attrbuf, (ip->rows * ip->cols));
   1169 #endif
   1170   bzero (ip->tabs, ip->cols);
   1171   for (i = 0; i < ip->cols; i++)
   1172     ip->tabs[i] = (i & 7) == 0;
   1173 }
   1174 
   1175 
   1176 void
   1177 iteputchar(c, dev)
   1178 	register int c;
   1179 	dev_t dev;
   1180 {
   1181 	int unit = UNIT(dev);
   1182 	register struct ite_softc *ip = &ite_softc[unit];
   1183 	register struct itesw *sp = &itesw[ip->type];
   1184 	register int n;
   1185 	int x, y;
   1186 	char *cp;
   1187 
   1188 	if ((ip->flags & (ITE_ACTIVE|ITE_INGRF)) != ITE_ACTIVE)
   1189 	  	return;
   1190 
   1191 #if 0
   1192 	if (ite_tty[unit])
   1193 	  if ((ite_tty[unit]->t_cflag & CSIZE) == CS7
   1194 	      || (ite_tty[unit]->t_cflag & PARENB))
   1195 	    c &= 0x7f;
   1196 #endif
   1197 
   1198 	if (ip->escape)
   1199 	  {
   1200 doesc:
   1201 	    switch (ip->escape)
   1202 	      {
   1203 	      case ESC:
   1204 	        switch (c)
   1205 	          {
   1206 		  /* first 7bit equivalents for the 8bit control characters */
   1207 
   1208 	          case 'D':
   1209 		    c = IND;
   1210 		    ip->escape = 0;
   1211 		    break; /* and fall into the next switch below (same for all `break') */
   1212 
   1213 		  case 'E':
   1214 		    c = NEL;
   1215 		    ip->escape = 0;
   1216 		    break;
   1217 
   1218 		  case 'H':
   1219 		    c = HTS;
   1220 		    ip->escape = 0;
   1221 		    break;
   1222 
   1223 		  case 'M':
   1224 		    c = RI;
   1225 		    ip->escape = 0;
   1226 		    break;
   1227 
   1228 		  case 'N':
   1229 		    c = SS2;
   1230 		    ip->escape = 0;
   1231 		    break;
   1232 
   1233 		  case 'O':
   1234 		    c = SS3;
   1235 		    ip->escape = 0;
   1236 		    break;
   1237 
   1238 		  case 'P':
   1239 		    c = DCS;
   1240 		    ip->escape = 0;
   1241 		    break;
   1242 
   1243 		  case '[':
   1244 		    c = CSI;
   1245 		    ip->escape = 0;
   1246 		    break;
   1247 
   1248 		  case '\\':
   1249 		    c = ST;
   1250 		    ip->escape = 0;
   1251 		    break;
   1252 
   1253 		  case ']':
   1254 		    c = OSC;
   1255 		    ip->escape = 0;
   1256 		    break;
   1257 
   1258 		  case '^':
   1259 		    c = PM;
   1260 		    ip->escape = 0;
   1261 		    break;
   1262 
   1263 		  case '_':
   1264 		    c = APC;
   1265 		    ip->escape = 0;
   1266 		    break;
   1267 
   1268 
   1269 		  /* introduces 7/8bit control */
   1270 		  case ' ':
   1271 		     /* can be followed by either F or G */
   1272 		     ip->escape = ' ';
   1273 		     break;
   1274 
   1275 
   1276 		  /* a lot of character set selections, not yet used...
   1277 		     94-character sets: */
   1278 		  case '(':	/* G0 */
   1279 		  case ')':	/* G1 */
   1280 		    ip->escape = c;
   1281 		    return;
   1282 
   1283 		  case '*':	/* G2 */
   1284 		  case '+':	/* G3 */
   1285 		  case 'B':	/* ASCII */
   1286 		  case 'A':	/* ISO latin 1 */
   1287 		  case '<':	/* user preferred suplemental */
   1288 		  case '0':	/* dec special graphics */
   1289 
   1290 		  /* 96-character sets: */
   1291 		  case '-':	/* G1 */
   1292 		  case '.':	/* G2 */
   1293 		  case '/':	/* G3 */
   1294 
   1295 		  /* national character sets: */
   1296 		  case '4':	/* dutch */
   1297 		  case '5':
   1298 		  case 'C':	/* finnish */
   1299 		  case 'R':	/* french */
   1300 		  case 'Q':	/* french canadian */
   1301 		  case 'K':	/* german */
   1302 		  case 'Y':	/* italian */
   1303 		  case '6':	/* norwegian/danish */
   1304 		  /* note: %5 and %6 are not supported (two chars..) */
   1305 
   1306 		    ip->escape = 0;
   1307 		    /* just ignore for now */
   1308 		    return;
   1309 
   1310 
   1311 		  /* locking shift modes (as you might guess, not yet supported..) */
   1312 		  case '`':
   1313 		    ip->GR = ip->G1;
   1314 		    ip->escape = 0;
   1315 		    return;
   1316 
   1317 		  case 'n':
   1318 		    ip->GL = ip->G2;
   1319 		    ip->escape = 0;
   1320 		    return;
   1321 
   1322 		  case '}':
   1323 		    ip->GR = ip->G2;
   1324 		    ip->escape = 0;
   1325 		    return;
   1326 
   1327 		  case 'o':
   1328 		    ip->GL = ip->G3;
   1329 		    ip->escape = 0;
   1330 		    return;
   1331 
   1332 		  case '|':
   1333 		    ip->GR = ip->G3;
   1334 		    ip->escape = 0;
   1335 		    return;
   1336 
   1337 
   1338 		  /* font width/height control */
   1339 		  case '#':
   1340 		    ip->escape = '#';
   1341 		    return;
   1342 
   1343 
   1344 		  /* hard terminal reset .. */
   1345 		  case 'c':
   1346 		    ite_reset (ip);
   1347 		    (*itesw[ip->type].ite_cursor)(ip, MOVE_CURSOR);
   1348 		    ip->escape = 0;
   1349 		    return;
   1350 
   1351 
   1352 		  case '7':
   1353 		    ip->save_curx = ip->curx;
   1354 		    ip->save_cury = ip->cury;
   1355 		    ip->save_attribute = ip->attribute;
   1356 		    ip->escape = 0;
   1357 		    return;
   1358 
   1359 		  case '8':
   1360 		    ip->curx = ip->save_curx;
   1361 		    ip->cury = ip->save_cury;
   1362 		    ip->attribute = ip->save_attribute;
   1363 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1364 		    ip->escape = 0;
   1365 		    return;
   1366 
   1367 		  case '=':
   1368 		    ip->keypad_appmode = 1;
   1369 		    ip->escape = 0;
   1370 		    return;
   1371 
   1372 		  case '>':
   1373 		    ip->keypad_appmode = 0;
   1374 		    ip->escape = 0;
   1375 		    return;
   1376 
   1377 		  case 'Z':	/* request ID */
   1378 		    if (ip->emul_level == EMUL_VT100)
   1379 		      ite_sendstr (ip, "\033[61;0c");
   1380 		    else
   1381 		      ite_sendstr (ip, "\033[63;0c");
   1382 		    ip->escape = 0;
   1383 		    return;
   1384 
   1385 		  /* default catch all for not recognized ESC sequences */
   1386 		  default:
   1387 		    ip->escape = 0;
   1388 		    return;
   1389 		  }
   1390 		break;
   1391 
   1392 
   1393 	      case '(':
   1394 	      case ')':
   1395 		ip->escape = 0;
   1396 		return;
   1397 
   1398 
   1399 	      case ' ':
   1400 	        switch (c)
   1401 	          {
   1402 	          case 'F':
   1403 		    ip->eightbit_C1 = 0;
   1404 		    ip->escape = 0;
   1405 		    return;
   1406 
   1407 		  case 'G':
   1408 		    ip->eightbit_C1 = 1;
   1409 		    ip->escape = 0;
   1410 		    return;
   1411 
   1412 		  default:
   1413 		    /* not supported */
   1414 		    ip->escape = 0;
   1415 		    return;
   1416 		  }
   1417 		break;
   1418 
   1419 
   1420 	      case '#':
   1421 		switch (c)
   1422 		  {
   1423 		  case '5':
   1424 		    /* single height, single width */
   1425 		    ip->escape = 0;
   1426 		    return;
   1427 
   1428 		  case '6':
   1429 		    /* double width, single height */
   1430 		    ip->escape = 0;
   1431 		    return;
   1432 
   1433 		  case '3':
   1434 		    /* top half */
   1435 		    ip->escape = 0;
   1436 		    return;
   1437 
   1438 		  case '4':
   1439 		    /* bottom half */
   1440 		    ip->escape = 0;
   1441 		    return;
   1442 
   1443 		  case '8':
   1444 		    /* screen alignment pattern... */
   1445 		    ip->escape = 0;
   1446 		    return;
   1447 
   1448 		  default:
   1449 		    ip->escape = 0;
   1450 		    return;
   1451 		  }
   1452 		break;
   1453 
   1454 
   1455 
   1456 	      case CSI:
   1457 	        /* the biggie... */
   1458 	        switch (c)
   1459 	          {
   1460 	          case '0': case '1': case '2': case '3': case '4':
   1461 	          case '5': case '6': case '7': case '8': case '9':
   1462 	          case ';': case '\"': case '$': case '>':
   1463 	            if (ip->ap < ip->argbuf + ARGBUF_SIZE)
   1464 	              *ip->ap++ = c;
   1465 	            return;
   1466 
   1467 	          case 'p':
   1468 		    *ip->ap = 0;
   1469 	            if (! strncmp (ip->argbuf, "61\"", 3))
   1470 	              ip->emul_level = EMUL_VT100;
   1471 	            else if (! strncmp (ip->argbuf, "63;1\"", 5)
   1472 	            	     || ! strncmp (ip->argbuf, "62;1\"", 5))
   1473 	              ip->emul_level = EMUL_VT300_7;
   1474 	            else
   1475 	              ip->emul_level = EMUL_VT300_8;
   1476 	            ip->escape = 0;
   1477 	            return;
   1478 
   1479 
   1480 	          case '?':
   1481 		    *ip->ap = 0;
   1482 	            ip->escape = '?';
   1483 	            ip->ap = ip->argbuf;
   1484 	            return;
   1485 
   1486 
   1487 		  case 'c':
   1488   		    *ip->ap = 0;
   1489 		    if (ip->argbuf[0] == '>')
   1490 		      {
   1491 		        ite_sendstr (ip, "\033[>24;0;0;0c");
   1492 		      }
   1493 		    else switch (ite_zargnum(ip))
   1494 		      {
   1495 		      case 0:
   1496 			/* primary DA request, send primary DA response */
   1497 			if (ip->emul_level == EMUL_VT100)
   1498 		          ite_sendstr (ip, "\033[?1;1c");
   1499 		        else
   1500 		          ite_sendstr (ip, "\033[63;0c");
   1501 			break;
   1502 		      }
   1503 		    ip->escape = 0;
   1504 <<<<<<< ite.c
   1505 		    return -1;
   1506 ||||||| 1.1.1.2
   1507 		    return -1;
   1508 
   1509 =======
   1510 		    return;
   1511 >>>>>>> /tmp/T4009622
   1512 
   1513 
   1514 		  case 'n':
   1515 		    switch (ite_zargnum(ip))
   1516 		      {
   1517 		      case 5:
   1518 		        ite_sendstr (ip, "\033[0n");	/* no malfunction */
   1519 			break;
   1520 		      case 6:
   1521 			/* cursor position report */
   1522 		        sprintf (ip->argbuf, "\033[%d;%dR",
   1523 				 ip->cury + 1, ip->curx + 1);
   1524 			ite_sendstr (ip, ip->argbuf);
   1525 			break;
   1526 		      }
   1527 		    ip->escape = 0;
   1528 <<<<<<< ite.c
   1529 		    return -1;
   1530 
   1531 ||||||| 1.1.1.2
   1532 		    return -1;
   1533 =======
   1534 		    return;
   1535 >>>>>>> /tmp/T4009622
   1536 
   1537 <<<<<<< ite.c
   1538 	          case 'h': case 'l':
   1539 		    *ip->ap = 0;
   1540 		    if (ip->ap == &ip->argbuf[1] && ip->argbuf[0] == '4')
   1541 		      ip->imode = (c == 'h');	/* insert/replace mode */
   1542 ||||||| 1.1.1.2
   1543 
   1544 	          case 'h': case 'l':
   1545 		    *ip->ap = 0;
   1546 		    if (ip->ap == &ip->argbuf[1] && ip->argbuf[0] == '4')
   1547 		      ip->imode = (c == 'h');	/* insert/replace mode */
   1548 =======
   1549 
   1550 		  case 'x':
   1551 		    switch (ite_zargnum(ip))
   1552 		      {
   1553 		      case 0:
   1554 			/* Fake some terminal parameters.  */
   1555 		        ite_sendstr (ip, "\033[2;1;1;112;112;1;0x");
   1556 			break;
   1557 		      case 1:
   1558 		        ite_sendstr (ip, "\033[3;1;1;112;112;1;0x");
   1559 			break;
   1560 		      }
   1561 		    ip->escape = 0;
   1562 		    return;
   1563 >>>>>>> /tmp/T4009622
   1564 
   1565 
   1566 		  case 'g':
   1567 		    switch (ite_zargnum(ip))
   1568 		      {
   1569 		      case 0:
   1570 			if (ip->curx < ip->cols)
   1571 			  ip->tabs[ip->curx] = 0;
   1572 			break;
   1573 		      case 3:
   1574 		        for (n = 0; n < ip->cols; n++)
   1575 		          ip->tabs[n] = 0;
   1576 			break;
   1577 		      }
   1578 		    ip->escape = 0;
   1579 		    return;
   1580 
   1581 
   1582   	          case 'h': case 'l':
   1583 		    n = ite_zargnum (ip);
   1584 		    switch (n)
   1585 		      {
   1586 		      case 4:
   1587 		        ip->imode = (c == 'h');	/* insert/replace mode */
   1588 			break;
   1589 		      case 20:
   1590 			ip->linefeed_newline = (c == 'h');
   1591 			break;
   1592 		      }
   1593 		    ip->escape = 0;
   1594 		    return;
   1595 
   1596 
   1597 		  case 'M':
   1598 		    ite_dnline (ip, sp, ite_argnum (ip));
   1599 	            ip->escape = 0;
   1600 	            return;
   1601 
   1602 
   1603 		  case 'L':
   1604 		    ite_inline (ip, sp, ite_argnum (ip));
   1605 	            ip->escape = 0;
   1606 	            return;
   1607 
   1608 
   1609 		  case 'P':
   1610 		    ite_dnchar (ip, sp, ite_argnum (ip));
   1611 	            ip->escape = 0;
   1612 	            return;
   1613 
   1614 
   1615 		  case '@':
   1616 		    ite_inchar (ip, sp, ite_argnum (ip));
   1617 	            ip->escape = 0;
   1618 	            return;
   1619 
   1620 
   1621 		  case 'H':
   1622 		  case 'f':
   1623 		    *ip->ap = 0;
   1624 		    y = atoi (ip->argbuf);
   1625 		    x = 0;
   1626 		    cp = index (ip->argbuf, ';');
   1627 		    if (cp)
   1628 		      x = atoi (cp + 1);
   1629 		    if (x) x--;
   1630 		    if (y) y--;
   1631 		    ip->cury = MIN(y, ip->rows - 1);
   1632 		    ip->curx = MIN(x, ip->cols - 1);
   1633 		    ip->escape = 0;
   1634 		    snap_cury(ip, sp);
   1635 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1636 		    clr_attr (ip, ATTR_INV);
   1637 		    return;
   1638 
   1639 		  case 'A':
   1640 		    n = ip->cury - ite_argnum (ip);
   1641 		    if (n < 0) n = 0;
   1642 		    ip->cury = MAX(n, ip->inside_margins ? ip->top_margin : 0);
   1643 		    ip->escape = 0;
   1644 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1645 		    clr_attr (ip, ATTR_INV);
   1646 		    return;
   1647 
   1648 		  case 'B':
   1649 		    n = ite_argnum (ip) + ip->cury;
   1650 		    ip->cury = MIN(n, ip->inside_margins ? ip->bottom_margin : ip->rows - 1);
   1651 		    ip->escape = 0;
   1652 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1653 		    clr_attr (ip, ATTR_INV);
   1654 		    return;
   1655 
   1656 		  case 'C':
   1657 		    n = ite_argnum (ip);
   1658 		    ip->curx = MIN(ip->curx + n, ip->cols - 1);
   1659 		    ip->escape = 0;
   1660 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1661 		    clr_attr (ip, ATTR_INV);
   1662 		    return;
   1663 
   1664 		  case 'D':
   1665 		    n = ite_argnum (ip);
   1666 		    n = ip->curx - n;
   1667 		    ip->curx = n >= 0 ? n : 0;
   1668 		    ip->escape = 0;
   1669 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1670 		    clr_attr (ip, ATTR_INV);
   1671 		    return;
   1672 
   1673 
   1674 
   1675 
   1676 		  case 'J':
   1677 		    *ip->ap = 0;
   1678 		    n = ite_zargnum (ip);
   1679 		    if (n == 0)
   1680 	              ite_clrtoeos(ip, sp);
   1681 		    else if (n == 1)
   1682 		      ite_clrtobos(ip, sp);
   1683 		    else if (n == 2)
   1684 		      ite_clrscreen(ip, sp);
   1685 	            ip->escape = 0;
   1686 	            return;
   1687 
   1688 
   1689 		  case 'K':
   1690 		    n = ite_zargnum (ip);
   1691 		    if (n == 0)
   1692 		      ite_clrtoeol(ip, sp);
   1693 		    else if (n == 1)
   1694 		      ite_clrtobol(ip, sp);
   1695 		    else if (n == 2)
   1696 		      ite_clrline(ip, sp);
   1697 		    ip->escape = 0;
   1698 		    return;
   1699 
   1700 
   1701 		  case 'X':
   1702 		    n = ite_argnum(ip) - 1;
   1703 		    n = MIN(n, ip->cols - 1 - ip->curx);
   1704 		    for (; n >= 0; n--)
   1705 		      {
   1706 			attrclr(ip, ip->cury, ip->curx + n, 1, 1);
   1707 			(*sp->ite_putc)(ip, ' ', ip->cury, ip->curx + n, ATTR_NOR);
   1708 		      }
   1709 		    ip->escape = 0;
   1710 		    return;
   1711 
   1712 
   1713 	          case '}': case '`':
   1714 	            /* status line control */
   1715 	            ip->escape = 0;
   1716 	            return;
   1717 
   1718 
   1719 		  case 'r':
   1720 		    *ip->ap = 0;
   1721 		    x = atoi (ip->argbuf);
   1722 		    y = 0;
   1723 		    cp = index (ip->argbuf, ';');
   1724 		    if (cp)
   1725 		      y = atoi (cp + 1);
   1726 		    if ((x > 0) || (y > 1))
   1727 		      {
   1728 		        if (x) x--;
   1729 		        if (y) y--;
   1730 		        ip->top_margin = MIN(x, ip->rows - 1);
   1731 		        ip->bottom_margin = MIN(y, ip->rows - 1);
   1732 			if (ip->bottom_margin < ip->top_margin)
   1733 			  ip->bottom_margin = ip->top_margin;
   1734 		      }
   1735 		    else
   1736 		      {
   1737 			ip->top_margin = 0;
   1738 			ip->bottom_margin = ip->rows - 1;
   1739 		      }
   1740 		    ip->cury = ip->top_margin;
   1741 		    ip->curx = 0;
   1742 		    (*sp->ite_cursor)(ip, MOVE_CURSOR);
   1743 		    ip->escape = 0;
   1744 		    return;
   1745 
   1746 
   1747 		  case 'm':
   1748 		    /* big attribute setter/resetter */
   1749 		    {
   1750 		      char *cp;
   1751 		      *ip->ap = 0;
   1752 		      /* kludge to make CSIm work (== CSI0m) */
   1753 		      if (ip->ap == ip->argbuf)
   1754 		        ip->ap++;
   1755 		      for (cp = ip->argbuf; cp < ip->ap; )
   1756 		        {
   1757 			  switch (*cp)
   1758 			    {
   1759 			    case 0:
   1760 			    case '0':
   1761 			      clr_attr (ip, ATTR_ALL);
   1762 			      cp++;
   1763 			      break;
   1764 
   1765 			    case '1':
   1766 			      set_attr (ip, ATTR_BOLD);
   1767 			      cp++;
   1768 			      break;
   1769 
   1770 			    case '2':
   1771 			      switch (cp[1])
   1772 			        {
   1773 			        case '2':
   1774 			          clr_attr (ip, ATTR_BOLD);
   1775 			          cp += 2;
   1776 			          break;
   1777 
   1778 			        case '4':
   1779 			          clr_attr (ip, ATTR_UL);
   1780 			          cp += 2;
   1781 			          break;
   1782 
   1783 			        case '5':
   1784 			          clr_attr (ip, ATTR_BLINK);
   1785 			          cp += 2;
   1786 			          break;
   1787 
   1788 			        case '7':
   1789 			          clr_attr (ip, ATTR_INV);
   1790 			          cp += 2;
   1791 			          break;
   1792 
   1793 		        	default:
   1794 		        	  cp++;
   1795 		        	  break;
   1796 		        	}
   1797 			      break;
   1798 
   1799 			    case '4':
   1800 			      set_attr (ip, ATTR_UL);
   1801 			      cp++;
   1802 			      break;
   1803 
   1804 			    case '5':
   1805 			      set_attr (ip, ATTR_BLINK);
   1806 			      cp++;
   1807 			      break;
   1808 
   1809 			    case '7':
   1810 			      set_attr (ip, ATTR_INV);
   1811 			      cp++;
   1812 			      break;
   1813 
   1814 			    default:
   1815 			      cp++;
   1816 			      break;
   1817 			    }
   1818 		        }
   1819 
   1820 		    }
   1821 		    ip->escape = 0;
   1822 		    return;
   1823 
   1824 
   1825 		  case 'u':
   1826 		    /* DECRQTSR */
   1827 		    ite_sendstr (ip, "\033P\033\\");
   1828 		    ip->escape = 0;
   1829 		    return;
   1830 
   1831 
   1832 
   1833 		  default:
   1834 		    ip->escape = 0;
   1835 		    return;
   1836 		  }
   1837 		break;
   1838 
   1839 
   1840 
   1841 	      case '?':	/* CSI ? */
   1842 	      	switch (c)
   1843 	      	  {
   1844 	          case '0': case '1': case '2': case '3': case '4':
   1845 	          case '5': case '6': case '7': case '8': case '9':
   1846 	          case ';': case '\"': case '$':
   1847 		    /* Don't fill the last character; it's needed.  */
   1848 		    /* XXX yeah, where ?? */
   1849 	            if (ip->ap < ip->argbuf + ARGBUF_SIZE - 1)
   1850 	              *ip->ap++ = c;
   1851 	            return;
   1852 
   1853 
   1854 		  case 'n':
   1855 		    *ip->ap = 0;
   1856 		    if (ip->ap == &ip->argbuf[2])
   1857 		      {
   1858 		        if (! strncmp (ip->argbuf, "15", 2))
   1859 		          /* printer status: no printer */
   1860 		          ite_sendstr (ip, "\033[13n");
   1861 
   1862 		        else if (! strncmp (ip->argbuf, "25", 2))
   1863 		          /* udk status */
   1864 		          ite_sendstr (ip, "\033[20n");
   1865 
   1866 		        else if (! strncmp (ip->argbuf, "26", 2))
   1867 		          /* keyboard dialect: US */
   1868 		          ite_sendstr (ip, "\033[27;1n");
   1869 		      }
   1870 		    ip->escape = 0;
   1871 		    return;
   1872 
   1873 
   1874   		  case 'h': case 'l':
   1875 		    n = ite_zargnum (ip);
   1876 		    switch (n)
   1877 		      {
   1878 		      case 1:
   1879 		        ip->cursor_appmode = (c == 'h');
   1880 		        break;
   1881 
   1882 		      case 3:
   1883 		        /* 132/80 columns (132 == 'h') */
   1884 		        break;
   1885 
   1886 		      case 4: /* smooth scroll */
   1887 			break;
   1888 
   1889 		      case 5:
   1890 		        /* light background (=='h') /dark background(=='l') */
   1891 		        break;
   1892 
   1893 		      case 6: /* origin mode */
   1894 			ip->inside_margins = (c == 'h');
   1895 			break;
   1896 
   1897 		      case 7: /* auto wraparound */
   1898 			ip->auto_wrap = (c == 'h');
   1899 			break;
   1900 
   1901 		      case 8: /* keyboard repeat */
   1902 			ip->key_repeat = (c == 'h');
   1903 			break;
   1904 
   1905 		      case 20: /* newline mode */
   1906 			ip->linefeed_newline = (c == 'h');
   1907 			break;
   1908 
   1909 		      case 25: /* cursor on/off */
   1910 			(*itesw[ip->type].ite_cursor)(ip, (c == 'h') ? DRAW_CURSOR : ERASE_CURSOR);
   1911 			break;
   1912 		      }
   1913 		    ip->escape = 0;
   1914 		    return;
   1915 
   1916 		  default:
   1917 		    ip->escape = 0;
   1918 		    return;
   1919 		  }
   1920 		break;
   1921 
   1922 
   1923 	      default:
   1924 	        ip->escape = 0;
   1925 	        return;
   1926 	      }
   1927           }
   1928 
   1929 
   1930 	switch (c) {
   1931 
   1932 	case VT:	/* VT is treated like LF */
   1933 	case FF:	/* so is FF */
   1934 	case LF:
   1935 		/* cr->crlf distinction is done here, on output,
   1936 		   not on input! */
   1937 		if (ip->linefeed_newline)
   1938 		  ite_crlf (ip, sp);
   1939 		else
   1940 		  ite_lf (ip, sp);
   1941 		break;
   1942 
   1943 	case CR:
   1944 		ite_cr (ip, sp);
   1945 		break;
   1946 
   1947 	case BS:
   1948 		if (--ip->curx < 0)
   1949 			ip->curx = 0;
   1950 		else
   1951 			(*sp->ite_cursor)(ip, MOVE_CURSOR);
   1952 		break;
   1953 
   1954 	case HT:
   1955 		for (n = ip->curx + 1; n < ip->cols; n++) {
   1956 			if (ip->tabs[n]) {
   1957 				ip->curx = n;
   1958 				(*sp->ite_cursor)(ip, MOVE_CURSOR);
   1959 				break;
   1960 			}
   1961 		}
   1962 		break;
   1963 
   1964 	case BEL:
   1965 		if (kbd_tty && ite_tty[unit] == kbd_tty)
   1966 			kbdbell();
   1967 		break;
   1968 
   1969 	case SO:
   1970 		ip->GL = ip->G1;
   1971 		break;
   1972 
   1973 	case SI:
   1974 		ip->GL = ip->G0;
   1975 		break;
   1976 
   1977 	case ENQ:
   1978 		/* send answer-back message !! */
   1979 		break;
   1980 
   1981 	case CAN:
   1982 		ip->escape = 0;	/* cancel any escape sequence in progress */
   1983 		break;
   1984 
   1985 	case SUB:
   1986 		ip->escape = 0;	/* dito, but see below */
   1987 		/* should also display a reverse question mark!! */
   1988 		break;
   1989 
   1990 	case ESC:
   1991 		ip->escape = ESC;
   1992 		break;
   1993 
   1994 
   1995 	/* now it gets weird.. 8bit control sequences.. */
   1996 	case IND:	/* index: move cursor down, scroll */
   1997 		ite_lf (ip, sp);
   1998 		break;
   1999 
   2000 	case NEL:	/* next line. next line, first pos. */
   2001 		ite_crlf (ip, sp);
   2002 		break;
   2003 
   2004 	case HTS:	/* set horizontal tab */
   2005 		if (ip->curx < ip->cols)
   2006 		  ip->tabs[ip->curx] = 1;
   2007 		break;
   2008 
   2009 	case RI:	/* reverse index */
   2010 		ite_rlf (ip, sp);
   2011 		break;
   2012 
   2013 	case SS2:	/* go into G2 for one character */
   2014 		/* not yet supported */
   2015 		break;
   2016 
   2017 	case SS3:	/* go into G3 for one character */
   2018 		break;
   2019 
   2020 	case DCS:	/* device control string introducer */
   2021 		ip->escape = DCS;
   2022 		ip->ap = ip->argbuf;
   2023 		break;
   2024 
   2025 	case CSI:	/* control sequence introducer */
   2026 		ip->escape = CSI;
   2027 		ip->ap = ip->argbuf;
   2028 		break;
   2029 
   2030 	case ST:	/* string terminator */
   2031 		/* ignore, if not used as terminator */
   2032 		break;
   2033 
   2034 	case OSC:	/* introduces OS command. Ignore everything upto ST */
   2035 		ip->escape = OSC;
   2036 		break;
   2037 
   2038 	case PM:	/* privacy message, ignore everything upto ST */
   2039 		ip->escape = PM;
   2040 		break;
   2041 
   2042 	case APC:	/* application program command, ignore everything upto ST */
   2043 		ip->escape = APC;
   2044 		break;
   2045 
   2046 	default:
   2047 		if (c < ' ' || c == DEL)
   2048 			break;
   2049 		if (ip->imode)
   2050 			ite_inchar(ip, sp, 1);
   2051 		iteprecheckwrap(ip, sp);
   2052 #ifdef DO_WEIRD_ATTRIBUTES
   2053 		if ((ip->attribute & ATTR_INV) || attrtest(ip, ATTR_INV)) {
   2054 			attrset(ip, ATTR_INV);
   2055 			(*sp->ite_putc)(ip, c, ip->cury, ip->curx, ATTR_INV);
   2056 		}
   2057 		else
   2058 			(*sp->ite_putc)(ip, c, ip->cury, ip->curx, ATTR_NOR);
   2059 #else
   2060 		(*sp->ite_putc)(ip, c, ip->cury, ip->curx, ip->attribute);
   2061 #endif
   2062 		(*sp->ite_cursor)(ip, DRAW_CURSOR);
   2063 		itecheckwrap(ip, sp);
   2064 		break;
   2065 	}
   2066 }
   2067 
   2068 iteprecheckwrap(ip, sp)
   2069      register struct ite_softc *ip;
   2070      register struct itesw *sp;
   2071 {
   2072 	if (ip->auto_wrap && ip->curx == ip->cols) {
   2073 		ip->curx = 0;
   2074 		clr_attr(ip, ATTR_INV);
   2075 		if (++ip->cury >= ip->bottom_margin + 1) {
   2076 			ip->cury = ip->bottom_margin;
   2077 			(*sp->ite_cursor)(ip, MOVE_CURSOR);
   2078 			(*sp->ite_scroll)(ip, ip->top_margin + 1, 0, 1, SCROLL_UP);
   2079 			ite_clrtoeol(ip, sp);
   2080 		} else
   2081 			(*sp->ite_cursor)(ip, MOVE_CURSOR);
   2082 	}
   2083 }
   2084 
   2085 itecheckwrap(ip, sp)
   2086      register struct ite_softc *ip;
   2087      register struct itesw *sp;
   2088 {
   2089 #if 0
   2090 	if (++ip->curx == ip->cols) {
   2091 		if (ip->auto_wrap) {
   2092 			ip->curx = 0;
   2093 			clr_attr(ip, ATTR_INV);
   2094 			if (++ip->cury >= ip->bottom_margin + 1) {
   2095 				ip->cury = ip->bottom_margin;
   2096 				(*sp->ite_cursor)(ip, MOVE_CURSOR);
   2097 				(*sp->ite_scroll)(ip, ip->top_margin + 1, 0, 1, SCROLL_UP);
   2098 				ite_clrtoeol(ip, sp);
   2099 				return;
   2100 			}
   2101 		} else
   2102 			/* stay there if no autowrap.. */
   2103 			ip->curx--;
   2104 	}
   2105 #else
   2106 	if (ip->curx < ip->cols) {
   2107 		ip->curx++;
   2108 		(*sp->ite_cursor)(ip, MOVE_CURSOR);
   2109 	}
   2110 #endif
   2111 }
   2112 
   2113 /*
   2114  * Console functions
   2115  */
   2116 #include "grfioctl.h"
   2117 #include "grfvar.h"
   2118 
   2119 #ifdef DEBUG
   2120 /*
   2121  * Minimum ITE number at which to start looking for a console.
   2122  * Setting to 0 will do normal search, 1 will skip first ITE device,
   2123  * NITE will skip ITEs and use serial port.
   2124  */
   2125 int	whichconsole = 0;
   2126 #endif
   2127 
   2128 itecnprobe(cp)
   2129 	struct consdev *cp;
   2130 {
   2131 	register struct ite_softc *ip;
   2132 	int i, maj, unit, pri;
   2133 
   2134 	/* locate the major number */
   2135 	for (maj = 0; maj < nchrdev; maj++)
   2136 		if (cdevsw[maj].d_open == iteopen)
   2137 			break;
   2138 
   2139 	/* urk! */
   2140 	grfconfig();
   2141 
   2142 	/* check all the individual displays and find the best */
   2143 	unit = -1;
   2144 	pri = CN_DEAD;
   2145 	for (i = 0; i < NITE; i++) {
   2146 		struct grf_softc *gp = &grf_softc[i];
   2147 
   2148 		ip = &ite_softc[i];
   2149 		if ((gp->g_flags & GF_ALIVE) == 0)
   2150 			continue;
   2151 		ip->flags = (ITE_ALIVE|ITE_CONSOLE);
   2152 
   2153 		/* XXX - we need to do something about mapping these */
   2154 		switch (gp->g_type) {
   2155 		case GT_CUSTOMCHIPS:
   2156 		        ip->type = ITE_CUSTOMCHIPS;
   2157 		        break;
   2158 
   2159 		case GT_TIGA_A2410:
   2160 		        ip->type = ITE_TIGA_A2410;
   2161 		        break;
   2162 
   2163 		case GT_RETINA:
   2164 			ip->type = ITE_RETINA;
   2165 			break;
   2166 		}
   2167 #ifdef DEBUG
   2168 		if (i < whichconsole)
   2169 			continue;
   2170 #endif
   2171 		if ((int)gp->g_type == GT_CUSTOMCHIPS) {
   2172 			pri = CN_INTERNAL;
   2173 			unit = i;
   2174 		} else /* if (unit < 0) */ {
   2175 			pri = CN_NORMAL;
   2176 			unit = i;
   2177 		}
   2178 
   2179 	}
   2180 
   2181 	/* initialize required fields */
   2182 	cp->cn_dev = makedev(maj, unit);
   2183 #if 0
   2184 	cp->cn_tp = ite_tty[unit];
   2185 #else
   2186 	delayed_con_tty = unit;
   2187 #endif
   2188 	cp->cn_pri = pri;
   2189 }
   2190 
   2191 itecninit(cp)
   2192 	struct consdev *cp;
   2193 {
   2194 	int unit;
   2195 	struct ite_softc *ip;
   2196 
   2197 	iteinit(cp->cn_dev);
   2198 	unit = UNIT(cp->cn_dev);
   2199 	ip = &ite_softc[unit];
   2200 
   2201 #ifdef DO_WEIRD_ATTRIBUTES
   2202 	ip->attrbuf = console_attributes;
   2203 #endif
   2204 	ip->flags |= (ITE_ACTIVE|ITE_ISCONS);
   2205 	/* if this is the console, NEVER close the device! */
   2206 	ip->open_cnt++;
   2207 #if 0
   2208 	/* have to delay this too.. sigh.. */
   2209 	kbd_tty = ite_tty[unit];
   2210 	kbd_ip = ip;
   2211 	kbdenable();
   2212 #endif
   2213 }
   2214 
   2215 /*ARGSUSED*/
   2216 itecngetc(dev)
   2217 	dev_t dev;
   2218 {
   2219 	register int c;
   2220 
   2221         do
   2222           {
   2223             c = kbdgetcn ();
   2224             c = itefilter (c, ITEFILT_CONSOLE);
   2225           }
   2226         while (c == -1);
   2227 
   2228 	return(c);
   2229 }
   2230 
   2231 itecnputc(dev, c)
   2232 	dev_t dev;
   2233 	int c;
   2234 {
   2235 	static int paniced = 0;
   2236 	struct ite_softc *ip = &ite_softc[UNIT(dev)];
   2237 
   2238 	if (panicstr && !paniced &&
   2239 	    (ip->flags & (ITE_ACTIVE|ITE_INGRF)) != ITE_ACTIVE) {
   2240 		(void) iteon(dev, 3);
   2241 		paniced = 1;
   2242 	}
   2243 	iteputchar(c, dev);
   2244 }
   2245 #endif
   2246