1 /* $NetBSD: consinit.c,v 1.5 2024/02/02 22:33:42 andvar Exp $ */ 2 /* 3 * Copyright (c) 2009 KIYOHARA Takashi 4 * All rights reserved. 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions 8 * are met: 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 17 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 18 * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, 19 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 20 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 21 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 23 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 24 * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 25 * POSSIBILITY OF SUCH DAMAGE. 26 */ 27 #include <sys/cdefs.h> 28 __KERNEL_RCSID(0, "$NetBSD: consinit.c,v 1.5 2024/02/02 22:33:42 andvar Exp $"); 29 30 #include <sys/param.h> 31 #include <sys/device.h> 32 #include <sys/termios.h> 33 34 #include <machine/bus.h> 35 #include <machine/dig64.h> 36 #include <machine/md_var.h> 37 38 #include <dev/acpi/acpica.h> 39 40 #include "com.h" 41 #include "vga.h" 42 #include "ssccons.h" 43 44 #include <dev/cons.h> 45 #if NCOM > 0 46 #include <dev/ic/comvar.h> 47 #endif 48 #if NVGA > 0 49 #include <dev/ic/vgareg.h> 50 #include <dev/ic/vgavar.h> 51 #endif 52 53 54 static void pcdp_cnprobe(struct consdev *); 55 static void pcdp_cninit(struct consdev *); 56 57 cons_decl(ssc); 58 59 struct consdev constab[] = { 60 { pcdp_cnprobe, pcdp_cninit, 61 NULL, NULL, NULL, NULL, NULL, NULL, NODEV, CN_DEAD }, 62 #if NSSCCONS > 0 63 cons_init(ssc), 64 #endif 65 { NULL } 66 }; 67 68 69 void 70 consinit(void) 71 { 72 73 cninit(); 74 } 75 76 static void 77 pcdp_cnprobe(struct consdev *cn) 78 { 79 struct dig64_hcdp_table *tbl; 80 union dev_desc *desc; 81 uint64_t hcdp; 82 int n, m; 83 84 hcdp = ia64_get_hcdp(); 85 if (hcdp != 0) { 86 tbl = (void*)IA64_PHYS_TO_RR7(hcdp); 87 n = 0; 88 m = tbl->length - sizeof(struct dig64_hcdp_table); 89 while (n < m) { 90 desc = (union dev_desc *)((char *)tbl->entry + n); 91 #if NVGA > 0 92 if (devdesc->type == 93 (DIG64_ENTRYTYPE_VGA | DIG64_ENTRYTYPE_OUTONLY)) { 94 #if defined(DIAGNOSTIC) 95 if (tbl->revision < 3) 96 panic("PCDP found in HCDP rev.%d." 97 " Maybe unsupported PCDP", 98 tbl->revision); 99 #endif 100 cn->cn_pri = CN_NORMAL; 101 break; 102 } 103 #endif 104 #if NCOM > 0 105 if (desc->type == DIG64_HCDP_CONSOLE) { 106 cn->cn_pri = CN_REMOTE; 107 break; 108 } 109 #endif 110 111 if (desc->type == DIG64_ENTRYTYPE_TYPE0 || 112 desc->type == DIG64_ENTRYTYPE_TYPE1) 113 n += sizeof(struct dig64_hcdp_entry); 114 else 115 n += desc->pcdp.length; 116 } 117 } 118 if (cn->cn_pri != CN_DEAD) 119 cn->cn_dev = ~NODEV; /* Shall we makedev()? */ 120 } 121 122 static void 123 pcdp_cninit(struct consdev *cn) 124 { 125 struct dig64_hcdp_table *tbl; 126 #if NVGA > 0 || NCOM > 0 127 union dev_desc *desc; 128 #endif 129 uint64_t hcdp; 130 int n, m; 131 132 hcdp = ia64_get_hcdp(); 133 if (hcdp == 0) 134 panic("lost console...\n"); 135 136 tbl = (void *)IA64_PHYS_TO_RR7(hcdp); 137 n = 0; 138 m = tbl->length - sizeof(struct dig64_hcdp_table); 139 while (n < m) { 140 #if NVGA > 0 || NCOM > 0 141 desc = (union dev_desc *)((char *)tbl->entry + n); 142 #endif 143 144 /* not yet... */ 145 /* Our VGA is Framebuffer? */ 146 #if NVGA > 0 147 if (cn->cn_pri == CN_NORMAL && 148 desc->type == 149 (DIG64_ENTRYTYPE_VGA | DIG64_ENTRYTYPE_OUTONLY)) { 150 struct dig64_pcdp_entry *ent = &desc->pcdp; 151 152 if (ent->specs.type == DIG64_PCDP_SPEC_PCI) { 153 struct dig64_pci_spec *spec = ent->specs.pci; 154 155 if (spec->flags & DIG64_FLAGS_MMIO_TRA_VALID) 156 (void*)spec->mmio_tra; 157 if (spec->flags & DIG64_FLAGS_IOPORT_TRA_VALID) 158 (void*)spec->ioport_tra; 159 } 160 161 break; 162 } 163 #endif 164 #if NCOM > 0 165 if (cn->cn_pri == CN_REMOTE && 166 desc->type == DIG64_HCDP_CONSOLE) { 167 struct dig64_hcdp_entry *ent = &desc->uart; 168 bus_addr_t ioaddr; 169 bus_space_tag_t iot; 170 const uint64_t rate = 171 ((uint64_t)ent->baud_high << 32) | ent->baud_low; 172 tcflag_t cflag = 173 TTYDEF_CFLAG & ~(CSIZE | PARENB | PARODD); 174 175 switch (ent->databits) { 176 case 5: 177 cflag = CS5; 178 break; 179 case 6: 180 cflag = CS6; 181 break; 182 case 7: 183 cflag = CS7; 184 break; 185 case 8: 186 cflag = CS8; 187 break; 188 default: 189 panic("unsupported databits %d\n", 190 ent->databits); 191 } 192 switch (ent->parity) { 193 case DIG64_HCDP_PARITY_NO: 194 break; 195 case DIG64_HCDP_PARITY_ODD: 196 cflag |= PARODD; 197 198 /* FALLTHROUGH */ 199 200 case DIG64_HCDP_PARITY_EVEN: 201 cflag |= PARENB; 202 break; 203 case DIG64_HCDP_PARITY_MARK: 204 case DIG64_HCDP_PARITY_SPACE: 205 default: 206 panic("unsupported parity type %d\n", 207 ent->parity); 208 } 209 if (ent->stopbits == DIG64_HCDP_STOPBITS_1) 210 cflag &= ~CSTOPB; 211 else if (ent->stopbits == DIG64_HCDP_STOPBITS_2) 212 cflag |= CSTOPB; 213 else 214 panic("unsupported stopbits type %d\n", 215 ent->stopbits); 216 iot = (ent->address.addr_space == 217 ACPI_ADR_SPACE_SYSTEM_MEMORY) ? 218 IA64_BUS_SPACE_MEM : IA64_BUS_SPACE_IO; 219 ioaddr = ((uint64_t)ent->address.addr_high << 32) | 220 ent->address.addr_low; 221 comcnattach(iot, ioaddr, rate, 222 (ent->pclock != 0) ? ent->pclock : COM_FREQ, 223 COM_TYPE_NORMAL, cflag); 224 break; 225 } 226 #endif 227 } 228 } 229