xref: /netbsd-src/sys/arch/amiga/dev/ite.c (revision 4b30c543a0b21e3ba94f2c569e9a82b4fdb2075f)
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