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 * %sccs.include.redist.c% 11 * 12 * @(#)dcm.c 7.3 (Berkeley) 05/07/91 13 */ 14 15 #ifdef DCMCONSOLE 16 #include "sys/param.h" 17 #include "../hp300/cons.h" 18 #include "../dev/device.h" 19 #include "../dev/dcmreg.h" 20 21 struct dcmdevice *dcmcnaddr = NULL; 22 23 dcmprobe(cp) 24 struct consdev *cp; 25 { 26 extern struct hp_hw sc_table[]; 27 register struct hp_hw *hw; 28 register struct dcmdevice *dcm; 29 30 for (hw = sc_table; hw < &sc_table[MAXCTLRS]; hw++) 31 if (HW_ISDEV(hw, D_COMMDCM) && !badaddr((caddr_t)hw->hw_kva)) 32 break; 33 if (!HW_ISDEV(hw, D_COMMDCM)) { 34 cp->cn_pri = CN_DEAD; 35 return; 36 } 37 dcmcnaddr = (struct dcmdevice *) hw->hw_kva; 38 39 dcm = dcmcnaddr; 40 switch (dcm->dcm_rsid) { 41 case DCMID: 42 cp->cn_pri = CN_NORMAL; 43 break; 44 case DCMID|DCMCON: 45 cp->cn_pri = CN_REMOTE; 46 break; 47 default: 48 cp->cn_pri = CN_DEAD; 49 break; 50 } 51 } 52 53 dcminit(cp) 54 struct consdev *cp; 55 { 56 register struct dcmdevice *dcm = dcmcnaddr; 57 register int port = CONUNIT; 58 59 dcm->dcm_ic = IC_ID; 60 while (dcm->dcm_thead[port].ptr != dcm->dcm_ttail[port].ptr) 61 ; 62 dcm->dcm_data[port].dcm_baud = BR_9600; 63 dcm->dcm_data[port].dcm_conf = LC_8BITS | LC_1STOP; 64 SEM_LOCK(dcm); 65 dcm->dcm_cmdtab[port].dcm_data |= CT_CON; 66 dcm->dcm_cr |= (1 << port); 67 SEM_UNLOCK(dcm); 68 DELAY(15000); 69 } 70 71 #ifndef SMALL 72 dcmgetchar() 73 { 74 register struct dcmdevice *dcm = dcmcnaddr; 75 register struct dcmrfifo *fifo; 76 register struct dcmpreg *pp; 77 register unsigned head; 78 int c, stat, port; 79 80 port = CONUNIT; 81 pp = dcm_preg(dcm, port); 82 head = pp->r_head & RX_MASK; 83 if (head == (pp->r_tail & RX_MASK)) 84 return(0); 85 fifo = &dcm->dcm_rfifos[3-port][head>>1]; 86 c = fifo->data_char; 87 stat = fifo->data_stat; 88 pp->r_head = (head + 2) & RX_MASK; 89 SEM_LOCK(dcm); 90 stat = dcm->dcm_iir; 91 SEM_UNLOCK(dcm); 92 return(c); 93 } 94 #else 95 dcmgetchar() 96 { 97 return(0); 98 } 99 #endif 100 101 dcmputchar(c) 102 register int c; 103 { 104 register struct dcmdevice *dcm = dcmcnaddr; 105 register struct dcmpreg *pp; 106 register int timo; 107 unsigned tail; 108 int port, stat; 109 110 port = CONUNIT; 111 pp = dcm_preg(dcm, port); 112 tail = pp->t_tail & TX_MASK; 113 timo = 50000; 114 while (tail != (pp->t_head & TX_MASK) && --timo) 115 ; 116 dcm->dcm_tfifos[3-port][tail].data_char = c; 117 pp->t_tail = tail = (tail + 1) & TX_MASK; 118 SEM_LOCK(dcm); 119 dcm->dcm_cmdtab[port].dcm_data |= CT_TX; 120 dcm->dcm_cr |= (1 << port); 121 SEM_UNLOCK(dcm); 122 timo = 1000000; 123 while (tail != (pp->t_head & TX_MASK) && --timo) 124 ; 125 SEM_LOCK(dcm); 126 stat = dcm->dcm_iir; 127 SEM_UNLOCK(dcm); 128 } 129 #endif 130