1/*	$OpenBSD: dev_i386.c,v 1.23 2019/05/10 21:20:43 mlarkin Exp $	*/
2
3/*
4 * Copyright (c) 1996-1999 Michael Shalayeff
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 *    notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 *    notice, this list of conditions and the following disclaimer in the
14 *    documentation and/or other materials provided with the distribution.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19 * IN NO EVENT SHALL THE AUTHOR OR HIS RELATIVES BE LIABLE FOR ANY DIRECT,
20 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22 * SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
24 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
25 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
26 * THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29#include <sys/param.h>
30#include <sys/queue.h>
31#include <sys/disklabel.h>
32#include <dev/cons.h>
33
34#include "libsa.h"
35#include "biosdev.h"
36#include "disk.h"
37
38#ifdef SOFTRAID
39#include <dev/biovar.h>
40#include <dev/softraidvar.h>
41#include <lib/libsa/softraid.h>
42#include "softraid_amd64.h"
43#endif
44
45extern int debug;
46
47/* XXX use slot for 'rd' for 'hd' pseudo-device */
48const char bdevs[][4] = {
49	"wd", "", "fd", "", "sd", "st", "cd", "",
50	"", "", "", "", "", "", "", "", "", "hd", ""
51};
52const int nbdevs = nitems(bdevs);
53
54const char cdevs[][4] = {
55	"cn", "", "", "", "", "", "", "",
56	"com", "", "", "", "pc"
57};
58const int ncdevs = nitems(cdevs);
59
60/* pass dev_t to the open routines */
61int
62devopen(struct open_file *f, const char *fname, char **file)
63{
64	struct devsw *dp = devsw;
65	register int i, rc = 1;
66
67	*file = (char *)fname;
68
69#ifdef DEBUG
70	if (debug)
71		printf("devopen:");
72#endif
73
74	for (i = 0; i < ndevs && rc != 0; dp++, i++) {
75#ifdef DEBUG
76		if (debug)
77			printf(" %s: ", dp->dv_name);
78#endif
79		if ((rc = (*dp->dv_open)(f, file)) == 0) {
80			f->f_dev = dp;
81			return 0;
82		}
83#ifdef DEBUG
84		else if (debug)
85			printf("%d", rc);
86#endif
87
88	}
89#ifdef DEBUG
90	if (debug)
91		putchar('\n');
92#endif
93
94	if ((f->f_flags & F_NODEV) == 0)
95		f->f_dev = dp;
96
97	return rc;
98}
99
100void
101devboot(dev_t bootdev, char *p)
102{
103#ifdef SOFTRAID
104	struct sr_boot_volume *bv;
105	struct sr_boot_chunk *bc;
106	struct diskinfo *dip = NULL;
107#endif
108	int sr_boot_vol = -1;
109	int part_type = FS_UNUSED;
110
111#ifdef SOFTRAID
112	/*
113	 * Determine the partition type for the 'a' partition of the
114	 * boot device.
115	 */
116	TAILQ_FOREACH(dip, &disklist, list)
117		if (dip->bios_info.bios_number == bootdev &&
118		    (dip->bios_info.flags & BDI_BADLABEL) == 0)
119			part_type = dip->disklabel.d_partitions[0].p_fstype;
120
121	/*
122	 * See if we booted from a disk that is a member of a bootable
123	 * softraid volume.
124	 */
125	SLIST_FOREACH(bv, &sr_volumes, sbv_link) {
126		if (bv->sbv_flags & BIOC_SCBOOTABLE)
127			SLIST_FOREACH(bc, &bv->sbv_chunks, sbc_link)
128				if (bc->sbc_disk == bootdev)
129					sr_boot_vol = bv->sbv_unit;
130		if (sr_boot_vol != -1)
131			break;
132	}
133#endif
134
135	if (sr_boot_vol != -1 && part_type != FS_BSDFFS) {
136		*p++ = 's';
137		*p++ = 'r';
138		*p++ = '0' + sr_boot_vol;
139	} else if (bootdev & 0x100) {
140		*p++ = 'c';
141		*p++ = 'd';
142		*p++ = '0';
143	} else {
144		if (bootdev & 0x80)
145			*p++ = 'h';
146		else
147			*p++ = 'f';
148		*p++ = 'd';
149		*p++ = '0' + (bootdev & 0x7f);
150	}
151	*p++ = 'a';
152	*p = '\0';
153}
154
155char ttyname_buf[8];
156
157char *
158ttyname(int fd)
159{
160	snprintf(ttyname_buf, sizeof ttyname_buf, "%s%d",
161	    cdevs[major(cn_tab->cn_dev)], minor(cn_tab->cn_dev));
162
163	return ttyname_buf;
164}
165
166dev_t
167ttydev(char *name)
168{
169	int i, unit = -1;
170	char *no = name + strlen(name) - 1;
171
172	while (no >= name && *no >= '0' && *no <= '9')
173		unit = (unit < 0 ? 0 : (unit * 10)) + *no-- - '0';
174	if (no < name || unit < 0)
175		return NODEV;
176	for (i = 0; i < ncdevs; i++)
177		if (strncmp(name, cdevs[i], no - name + 1) == 0)
178			return makedev(i, unit);
179	return NODEV;
180}
181
182int
183cnspeed(dev_t dev, int sp)
184{
185	if (major(dev) == 8)	/* comN */
186		return comspeed(dev, sp);
187
188	/* pc0 and anything else */
189	return 9600;
190}
191