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 are permitted provided 11 * that: (1) source distributions retain this entire copyright notice and 12 * comment, and (2) distributions including binaries display the following 13 * acknowledgement: ``This product includes software developed by the 14 * University of California, Berkeley and its contributors'' in the 15 * documentation or other materials provided with the distribution and in 16 * all advertising materials mentioning features or use of this software. 17 * Neither the name of the University nor the names of its contributors may 18 * be used to endorse or promote products derived from this software without 19 * specific prior written permission. 20 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED 21 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF 22 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 23 * 24 * from: Utah $Hdr: cons.c 1.1 90/07/09$ 25 * 26 * @(#)cons.c 7.5 (Berkeley) 12/16/90 27 */ 28 29 #include "sys/param.h" 30 #include "sys/user.h" 31 #include "sys/systm.h" 32 #include "sys/buf.h" 33 #include "sys/ioctl.h" 34 #include "sys/tty.h" 35 #include "sys/file.h" 36 #include "sys/conf.h" 37 38 #include "cons.h" 39 40 /* XXX - all this could be autoconfig()ed */ 41 #include "ite.h" 42 #if NITE > 0 43 int itecnprobe(), itecninit(), itecngetc(), itecnputc(); 44 #endif 45 #include "dca.h" 46 #if NDCA > 0 47 int dcacnprobe(), dcacninit(), dcacngetc(), dcacnputc(); 48 #endif 49 #include "dcm.h" 50 #if NDCM > 0 51 int dcmcnprobe(), dcmcninit(), dcmcngetc(), dcmcnputc(); 52 #endif 53 54 struct consdev constab[] = { 55 #if NITE > 0 56 { itecnprobe, itecninit, itecngetc, itecnputc }, 57 #endif 58 #if NDCA > 0 59 { dcacnprobe, dcacninit, dcacngetc, dcacnputc }, 60 #endif 61 #if NDCM > 0 62 { dcmcnprobe, dcmcninit, dcmcngetc, dcmcnputc }, 63 #endif 64 { 0 }, 65 }; 66 /* end XXX */ 67 68 struct tty *constty = 0; /* virtual console output device */ 69 struct consdev *cn_tab; /* physical console device info */ 70 struct tty *cn_tty; /* XXX: console tty struct for tprintf */ 71 72 cninit() 73 { 74 register struct consdev *cp; 75 76 /* 77 * Collect information about all possible consoles 78 * and find the one with highest priority 79 */ 80 for (cp = constab; cp->cn_probe; cp++) { 81 (*cp->cn_probe)(cp); 82 if (cp->cn_pri > CN_DEAD && 83 (cn_tab == NULL || cp->cn_pri > cn_tab->cn_pri)) 84 cn_tab = cp; 85 } 86 /* 87 * No console, we can handle it 88 */ 89 if ((cp = cn_tab) == NULL) 90 return; 91 /* 92 * Turn on console 93 */ 94 cn_tty = cp->cn_tp; 95 (*cp->cn_init)(cp); 96 } 97 98 cnopen(dev, flag) 99 dev_t dev; 100 { 101 if (cn_tab == NULL) 102 return(0); 103 dev = cn_tab->cn_dev; 104 return ((*cdevsw[major(dev)].d_open)(dev, flag)); 105 } 106 107 cnclose(dev, flag) 108 dev_t dev; 109 { 110 if (cn_tab == NULL) 111 return(0); 112 dev = cn_tab->cn_dev; 113 return ((*cdevsw[major(dev)].d_close)(dev, flag)); 114 } 115 116 cnread(dev, uio, flag) 117 dev_t dev; 118 struct uio *uio; 119 { 120 if (cn_tab == NULL) 121 return(0); 122 dev = cn_tab->cn_dev; 123 return ((*cdevsw[major(dev)].d_read)(dev, uio, flag)); 124 } 125 126 cnwrite(dev, uio, flag) 127 dev_t dev; 128 struct uio *uio; 129 { 130 if (cn_tab == NULL) 131 return(0); 132 dev = cn_tab->cn_dev; 133 return ((*cdevsw[major(dev)].d_write)(dev, uio, flag)); 134 } 135 136 cnioctl(dev, cmd, data, flag) 137 dev_t dev; 138 caddr_t data; 139 { 140 int error; 141 142 if (cn_tab == NULL) 143 return(0); 144 /* 145 * Superuser can always use this to wrest control of console 146 * output from the "virtual" console. 147 */ 148 if (cmd == TIOCCONS && constty) { 149 error = suser(u.u_cred, &u.u_acflag); 150 if (error) 151 return (error); 152 constty = NULL; 153 return (0); 154 } 155 dev = cn_tab->cn_dev; 156 return ((*cdevsw[major(dev)].d_ioctl)(dev, cmd, data, flag)); 157 } 158 159 /*ARGSUSED*/ 160 cnselect(dev, rw) 161 dev_t dev; 162 int rw; 163 { 164 if (cn_tab == NULL) 165 return(1); 166 return(ttselect(cn_tab->cn_dev, rw)); 167 } 168 169 cngetc() 170 { 171 if (cn_tab == NULL) 172 return(0); 173 return((*cn_tab->cn_getc)(cn_tab->cn_dev)); 174 } 175 176 cnputc(c) 177 register int c; 178 { 179 if (cn_tab == NULL) 180 return; 181 if (c) { 182 (*cn_tab->cn_putc)(cn_tab->cn_dev, c); 183 if (c == '\n') 184 (*cn_tab->cn_putc)(cn_tab->cn_dev, '\r'); 185 } 186 } 187