xref: /illumos-gate/usr/src/uts/common/os/swapgeneric.c (revision 843c398e8904ed9d833d2af3103894f909fb4b52)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 /*
22  * Copyright (c) 1982, 2010, Oracle and/or its affiliates. All rights reserved.
23  * Copyright 2015 Nexenta Systems, Inc. All rights reserved.
24  */
25 
26 /*
27  * Configure root, swap and dump devices.
28  */
29 
30 #include <sys/types.h>
31 #include <sys/param.h>
32 #include <sys/sysmacros.h>
33 #include <sys/signal.h>
34 #include <sys/cred.h>
35 #include <sys/proc.h>
36 #include <sys/user.h>
37 #include <sys/conf.h>
38 #include <sys/buf.h>
39 #include <sys/systm.h>
40 #include <sys/vm.h>
41 #include <sys/reboot.h>
42 #include <sys/file.h>
43 #include <sys/vfs.h>
44 #include <sys/vnode.h>
45 #include <sys/errno.h>
46 #include <sys/kmem.h>
47 #include <sys/uio.h>
48 #include <sys/open.h>
49 #include <sys/mount.h>
50 #include <sys/kobj.h>
51 #include <sys/bootconf.h>
52 #include <sys/sysconf.h>
53 #include <sys/modctl.h>
54 #include <sys/autoconf.h>
55 #include <sys/debug.h>
56 #include <sys/fs/snode.h>
57 #include <fs/fs_subr.h>
58 #include <sys/socket.h>
59 #include <net/if.h>
60 
61 #include <sys/mkdev.h>
62 #include <sys/cmn_err.h>
63 #include <sys/console.h>
64 
65 #include <sys/conf.h>
66 #include <sys/ddi.h>
67 #include <sys/sunddi.h>
68 #include <sys/hwconf.h>
69 #include <sys/dc_ki.h>
70 #include <sys/promif.h>
71 #include <sys/bootprops.h>
72 
73 /*
74  * Local routines
75  */
76 static int preload_module(struct sysparam *, void *);
77 static struct vfssw *getfstype(char *, char *, size_t);
78 static int getphysdev(char *, char *, size_t);
79 static int load_bootpath_drivers(char *bootpath);
80 static int load_boot_driver(char *drv);
81 static int load_boot_platform_modules(char *drv);
82 static dev_info_t *path_to_devinfo(char *path);
83 static boolean_t netboot_over_ib(char *bootpath);
84 static boolean_t netboot_over_iscsi(void);
85 
86 /*
87  * Module linkage information for the kernel.
88  */
89 static struct modlmisc modlmisc = {
90 	&mod_miscops, "root and swap configuration"
91 };
92 
93 static struct modlinkage modlinkage = {
94 	MODREV_1, (void *)&modlmisc, NULL
95 };
96 
97 int
98 _init(void)
99 {
100 	return (mod_install(&modlinkage));
101 }
102 
103 int
104 _fini(void)
105 {
106 	return (mod_remove(&modlinkage));
107 }
108 
109 int
110 _info(struct modinfo *modinfop)
111 {
112 	return (mod_info(&modlinkage, modinfop));
113 }
114 
115 extern ib_boot_prop_t *iscsiboot_prop;
116 /*
117  * Configure root file system.
118  */
119 int
120 rootconf(void)
121 {
122 	int		error;
123 	struct vfssw	*vsw;
124 	extern void pm_init(void);
125 	int ret = -1;
126 	BMDPRINTF(("rootconf: fstype %s\n", rootfs.bo_fstype));
127 	BMDPRINTF(("rootconf: name %s\n", rootfs.bo_name));
128 	BMDPRINTF(("rootconf: flags 0x%x\n", rootfs.bo_flags));
129 	BMDPRINTF(("rootconf: obp_bootpath %s\n", obp_bootpath));
130 
131 	/*
132 	 * Install cluster modules that were only loaded during
133 	 * loadrootmodules().
134 	 */
135 	if (error = clboot_rootconf())
136 		return (error);
137 
138 	if (root_is_svm) {
139 		(void) strncpy(rootfs.bo_name, obp_bootpath, BO_MAXOBJNAME);
140 
141 		BMDPRINTF(("rootconf: svm: rootfs name %s\n", rootfs.bo_name));
142 		BMDPRINTF(("rootconf: svm: svm name %s\n", svm_bootpath));
143 	}
144 
145 	/*
146 	 * Run _init on the root filesystem (we already loaded it
147 	 * but we've been waiting until now to _init it) which will
148 	 * have the side-effect of running vsw_init() on this vfs.
149 	 * Because all the nfs filesystems are lumped into one
150 	 * module we need to special case it.
151 	 */
152 	if (strncmp(rootfs.bo_fstype, "nfs", 3) == 0) {
153 		if (modload("fs", "nfs") == -1) {
154 			cmn_err(CE_CONT, "Cannot initialize %s filesystem\n",
155 			    rootfs.bo_fstype);
156 			return (ENXIO);
157 		}
158 	} else {
159 		if (modload("fs", rootfs.bo_fstype) == -1) {
160 			cmn_err(CE_CONT, "Cannot initialize %s filesystem\n",
161 			    rootfs.bo_fstype);
162 			return (ENXIO);
163 		}
164 	}
165 	RLOCK_VFSSW();
166 	vsw = vfs_getvfsswbyname(rootfs.bo_fstype);
167 	RUNLOCK_VFSSW();
168 	if (vsw == NULL) {
169 		cmn_err(CE_CONT, "Cannot find %s filesystem\n",
170 		    rootfs.bo_fstype);
171 		return (ENXIO);
172 	}
173 	VFS_INIT(rootvfs, &vsw->vsw_vfsops, (caddr_t)0);
174 	VFS_HOLD(rootvfs);
175 
176 	if (root_is_svm) {
177 		rootvfs->vfs_flag |= VFS_RDONLY;
178 	}
179 
180 	/*
181 	 * This pm-releated call has to occur before root is mounted since we
182 	 * need to power up all devices.  It is placed after VFS_INIT() such
183 	 * that opening a device via ddi_lyr_ interface just before root has
184 	 * been mounted would work.
185 	 */
186 	pm_init();
187 
188 	if (netboot && iscsiboot_prop) {
189 		cmn_err(CE_WARN, "NFS boot and iSCSI boot"
190 		    " shouldn't happen in the same time");
191 		return (EINVAL);
192 	}
193 
194 	if (netboot || iscsiboot_prop) {
195 		ret = strplumb();
196 		if (ret != 0) {
197 			cmn_err(CE_WARN, "Cannot plumb network device %d", ret);
198 			return (EFAULT);
199 		}
200 	}
201 
202 	if ((ret == 0) && iscsiboot_prop) {
203 		ret = modload("drv", "iscsi");
204 		/* -1 indicates fail */
205 		if (ret == -1) {
206 			cmn_err(CE_WARN, "Failed to load iscsi module");
207 			iscsi_boot_prop_free();
208 			return (EINVAL);
209 		} else {
210 			if (!i_ddi_attach_pseudo_node("iscsi")) {
211 				cmn_err(CE_WARN,
212 				    "Failed to attach iscsi driver");
213 				iscsi_boot_prop_free();
214 				return (ENODEV);
215 			}
216 		}
217 	}
218 
219 	/*
220 	 * ufs_mountroot() ends up calling getrootdev()
221 	 * (below) which actually triggers the _init, identify,
222 	 * probe and attach of the drivers that make up root device
223 	 * bush; these are also quietly waiting in memory.
224 	 */
225 	BMDPRINTF(("rootconf: calling VFS_MOUNTROOT %s\n", rootfs.bo_fstype));
226 
227 	error = VFS_MOUNTROOT(rootvfs, ROOT_INIT);
228 	vfs_unrefvfssw(vsw);
229 	rootdev = rootvfs->vfs_dev;
230 
231 	if (error)
232 		cmn_err(CE_CONT, "Cannot mount root on %s fstype %s\n",
233 		    rootfs.bo_name, rootfs.bo_fstype);
234 	else
235 		cmn_err(CE_CONT, "?root on %s fstype %s\n",
236 		    rootfs.bo_name, rootfs.bo_fstype);
237 	return (error);
238 }
239 
240 /*
241  * Remount root on an SVM mirror root device
242  * Only supported on UFS filesystems at present
243  */
244 int
245 svm_rootconf(void)
246 {
247 	int	error;
248 	extern int ufs_remountroot(struct vfs *vfsp);
249 
250 	ASSERT(root_is_svm == 1);
251 
252 	if (strcmp(rootfs.bo_fstype, "ufs") != 0) {
253 		cmn_err(CE_CONT, "Mounting root on %s with filesystem "
254 		    "type %s is not supported\n",
255 		    rootfs.bo_name, rootfs.bo_fstype);
256 		return (EINVAL);
257 	}
258 
259 	(void) strncpy(rootfs.bo_name, svm_bootpath, BO_MAXOBJNAME);
260 
261 	BMDPRINTF(("svm_rootconf: rootfs %s\n", rootfs.bo_name));
262 
263 	error = ufs_remountroot(rootvfs);
264 
265 	if (error) {
266 		cmn_err(CE_CONT, "Cannot remount root on %s fstype %s\n",
267 		    rootfs.bo_name, rootfs.bo_fstype);
268 	} else {
269 		cmn_err(CE_CONT, "?root remounted on %s fstype %s\n",
270 		    rootfs.bo_name, rootfs.bo_fstype);
271 	}
272 	return (error);
273 }
274 
275 /*
276  * Under the assumption that our root file system is on a
277  * disk partition, get the dev_t of the partition in question.
278  *
279  * By now, boot has faithfully loaded all our modules into memory, and
280  * we've taken over resource management.  Before we go any further, we
281  * have to fire up the device drivers and stuff we need to mount the
282  * root filesystem.  That's what we do here.  Fingers crossed.
283  */
284 dev_t
285 getrootdev(void)
286 {
287 	dev_t	d;
288 
289 	d = ddi_pathname_to_dev_t(rootfs.bo_name);
290 	if ((d == NODEV) && (iscsiboot_prop != NULL)) {
291 		/* Give it another try with the 'disk' path */
292 		get_iscsi_bootpath_phy(rootfs.bo_name);
293 		d = ddi_pathname_to_dev_t(rootfs.bo_name);
294 	}
295 	if (d == NODEV)
296 		cmn_err(CE_CONT, "Cannot assemble drivers for root %s\n",
297 		    rootfs.bo_name);
298 	return (d);
299 }
300 
301 /*
302  * If booted with ASKNAME, prompt on the console for a filesystem
303  * name and return it.
304  */
305 void
306 getfsname(char *askfor, char *name, size_t namelen)
307 {
308 	if (boothowto & RB_ASKNAME) {
309 		printf("%s name: ", askfor);
310 		console_gets(name, namelen);
311 	}
312 }
313 
314 /*ARGSUSED1*/
315 static int
316 preload_module(struct sysparam *sysp, void *p)
317 {
318 	static char *wmesg = "forceload of %s failed";
319 	char *name;
320 
321 	name = sysp->sys_ptr;
322 	BMDPRINTF(("preload_module: %s\n", name));
323 	if (modloadonly(NULL, name) < 0)
324 		cmn_err(CE_WARN, wmesg, name);
325 	return (0);
326 }
327 
328 /*
329  * We want to load all the modules needed to mount the root filesystem,
330  * so that when we start the ball rolling in 'getrootdev', every module
331  * should already be in memory, just waiting to be init-ed.
332  */
333 
334 int
335 loadrootmodules(void)
336 {
337 	struct vfssw	*vsw;
338 	char		*this;
339 	char		*name;
340 	int		err;
341 	int		i, proplen;
342 	extern char	*impl_module_list[];
343 	extern char	*platform_module_list[];
344 
345 	/* Make sure that the PROM's devinfo tree has been created */
346 	ASSERT(ddi_root_node());
347 
348 	BMDPRINTF(("loadrootmodules: fstype %s\n", rootfs.bo_fstype));
349 	BMDPRINTF(("loadrootmodules: name %s\n", rootfs.bo_name));
350 	BMDPRINTF(("loadrootmodules: flags 0x%x\n", rootfs.bo_flags));
351 
352 	/*
353 	 * zzz We need to honor what's in rootfs if it's not null.
354 	 * non-null means use what's there.  This way we can
355 	 * change rootfs with /etc/system AND with tunetool.
356 	 */
357 	if (root_is_svm) {
358 		/* user replaced rootdev, record obp_bootpath */
359 		obp_bootpath[0] = '\0';
360 		(void) getphysdev("root", obp_bootpath, BO_MAXOBJNAME);
361 		BMDPRINTF(("loadrootmodules: obp_bootpath %s\n", obp_bootpath));
362 	} else {
363 		/*
364 		 * Get the root fstype and root device path from boot.
365 		 */
366 		rootfs.bo_fstype[0] = '\0';
367 		rootfs.bo_name[0] = '\0';
368 	}
369 
370 	/*
371 	 * This lookup will result in modloadonly-ing the root
372 	 * filesystem module - it gets _init-ed in rootconf()
373 	 */
374 	if ((vsw = getfstype("root", rootfs.bo_fstype, BO_MAXFSNAME)) == NULL)
375 		return (ENXIO);	/* in case we have no file system types */
376 
377 	(void) strcpy(rootfs.bo_fstype, vsw->vsw_name);
378 
379 	vfs_unrefvfssw(vsw);
380 
381 	/*
382 	 * Load the favored drivers of the implementation.
383 	 * e.g. 'sbus' and possibly 'zs' (even).
384 	 *
385 	 * Called whilst boot is still loaded (because boot does
386 	 * the i/o for us), and DDI services are unavailable.
387 	 */
388 	BMDPRINTF(("loadrootmodules: impl_module_list\n"));
389 	for (i = 0; (this = impl_module_list[i]) != NULL; i++) {
390 		if ((err = load_boot_driver(this)) != 0) {
391 			cmn_err(CE_WARN, "Cannot load drv/%s", this);
392 			return (err);
393 		}
394 	}
395 	/*
396 	 * Now load the platform modules (if any)
397 	 */
398 	BMDPRINTF(("loadrootmodules: platform_module_list\n"));
399 	for (i = 0; (this = platform_module_list[i]) != NULL; i++) {
400 		if ((err = load_boot_platform_modules(this)) != 0) {
401 			cmn_err(CE_WARN, "Cannot load drv/%s", this);
402 			return (err);
403 		}
404 	}
405 
406 loop:
407 	(void) getphysdev("root", rootfs.bo_name, BO_MAXOBJNAME);
408 	/*
409 	 * Given a physical pathname, load the correct set of driver
410 	 * modules into memory, including all possible parents.
411 	 *
412 	 * NB: The code sets the variable 'name' for error reporting.
413 	 */
414 	err = 0;
415 	BMDPRINTF(("loadrootmodules: rootfs %s\n", rootfs.bo_name));
416 	if (root_is_svm == 0) {
417 		BMDPRINTF(("loadrootmodules: rootfs %s\n", rootfs.bo_name));
418 		name = rootfs.bo_name;
419 		err = load_bootpath_drivers(rootfs.bo_name);
420 	}
421 
422 	/*
423 	 * Load driver modules in obp_bootpath, this is always
424 	 * required for mountroot to succeed. obp_bootpath is
425 	 * is set if rootdev is set via /etc/system, which is
426 	 * the case if booting of a SVM/VxVM mirror.
427 	 */
428 	if ((err == 0) && obp_bootpath[0] != '\0') {
429 		BMDPRINTF(("loadrootmodules: obp_bootpath %s\n", obp_bootpath));
430 		name = obp_bootpath;
431 		err = load_bootpath_drivers(obp_bootpath);
432 	}
433 
434 	if (err != 0) {
435 		cmn_err(CE_CONT, "Cannot load drivers for %s\n", name);
436 		goto out;
437 	}
438 
439 	/*
440 	 * Check to see if the booter performed DHCP configuration
441 	 * ("bootp-response" boot property exists). If so, then before
442 	 * bootops disappears we need to save the value of this property
443 	 * such that the userland dhcpagent can adopt the DHCP management
444 	 * of our primary network interface.
445 	 */
446 	proplen = BOP_GETPROPLEN(bootops, "bootp-response");
447 	if (proplen > 0) {
448 		dhcack = kmem_zalloc(proplen, KM_SLEEP);
449 		if (BOP_GETPROP(bootops, "bootp-response", dhcack) == -1) {
450 			cmn_err(CE_WARN, "BOP_GETPROP of  "
451 			    "\"bootp-response\" failed\n");
452 			kmem_free(dhcack, dhcacklen);
453 			dhcack = NULL;
454 			goto out;
455 		}
456 		dhcacklen = proplen;
457 
458 		/*
459 		 * Fetch the "netdev-path" boot property (if it exists), and
460 		 * stash it for later use by sysinfo(SI_DHCP_CACHE, ...).
461 		 */
462 		proplen = BOP_GETPROPLEN(bootops, "netdev-path");
463 		if (proplen > 0) {
464 			netdev_path = kmem_zalloc(proplen, KM_SLEEP);
465 			if (BOP_GETPROP(bootops, "netdev-path",
466 			    (uchar_t *)netdev_path) == -1) {
467 				cmn_err(CE_WARN, "BOP_GETPROP of  "
468 				    "\"netdev-path\" failed\n");
469 				kmem_free(netdev_path, proplen);
470 				goto out;
471 			}
472 		}
473 	}
474 
475 	/*
476 	 * Preload (load-only, no init) all modules which
477 	 * were added to the /etc/system file with the
478 	 * FORCELOAD keyword.
479 	 */
480 	BMDPRINTF(("loadrootmodules: preload_module\n"));
481 	(void) mod_sysctl_type(MOD_FORCELOAD, preload_module, NULL);
482 
483 	/*
484 	 * If we booted otw then load in the plumbing
485 	 * routine now while we still can. If we didn't
486 	 * boot otw then we will load strplumb in main().
487 	 *
488 	 * NFS is actually a set of modules, the core routines,
489 	 * a diskless helper module, rpcmod, and the tli interface.  Load
490 	 * them now while we still can.
491 	 *
492 	 * Because we glomb all versions of nfs into a single module
493 	 * we check based on the initial string "nfs".
494 	 *
495 	 * XXX: A better test for this is to see if device_type
496 	 * XXX: from the PROM is "network".
497 	 */
498 
499 	if (strncmp(rootfs.bo_fstype, "nfs", 3) == 0) {
500 		++netboot;
501 
502 		/*
503 		 * Preload (load-only, no init) the dacf module. We cannot
504 		 * init the module because one of its requisite modules is
505 		 * dld whose _init function will call taskq_create(), which
506 		 * will panic the system at this point.
507 		 */
508 		if ((err = modloadonly("dacf", "net_dacf")) < 0)  {
509 			cmn_err(CE_CONT, "Cannot load dacf/net_dacf\n");
510 			goto out;
511 		}
512 		if ((err = modload("misc", "tlimod")) < 0)  {
513 			cmn_err(CE_CONT, "Cannot load misc/tlimod\n");
514 			goto out;
515 		}
516 		if ((err = modload("strmod", "rpcmod")) < 0)  {
517 			cmn_err(CE_CONT, "Cannot load strmod/rpcmod\n");
518 			goto out;
519 		}
520 		if ((err = modload("misc", "nfs_dlboot")) < 0)  {
521 			cmn_err(CE_CONT, "Cannot load misc/nfs_dlboot\n");
522 			goto out;
523 		}
524 		if ((err = modload("mac", "mac_ether")) < 0)  {
525 			cmn_err(CE_CONT, "Cannot load mac/mac_ether\n");
526 			goto out;
527 		}
528 		if ((err = modload("misc", "strplumb")) < 0)  {
529 			cmn_err(CE_CONT, "Cannot load misc/strplumb\n");
530 			goto out;
531 		}
532 		if ((err = strplumb_load()) < 0) {
533 			goto out;
534 		}
535 	}
536 	if (netboot_over_iscsi() == B_TRUE) {
537 		/* iscsi boot */
538 		if ((err = modloadonly("dacf", "net_dacf")) < 0) {
539 			cmn_err(CE_CONT, "Cannot load dacf/net_dacf\n");
540 			goto out;
541 		}
542 		if ((err = modload("misc", "tlimod")) < 0) {
543 			cmn_err(CE_CONT, "Cannot load misc/tlimod\n");
544 			goto out;
545 		}
546 		if ((err = modload("mac", "mac_ether")) < 0) {
547 			cmn_err(CE_CONT, "Cannot load mac/mac_ether\n");
548 			goto out;
549 		}
550 		if ((err = modloadonly("drv", "iscsi")) < 0) {
551 			cmn_err(CE_CONT, "Cannot load drv/iscsi\n");
552 			goto out;
553 		}
554 		if ((err = modloadonly("drv", "ssd")) < 0) {
555 			cmn_err(CE_CONT, "Cannot load drv/ssd\n");
556 			goto out;
557 		}
558 		if ((err = modloadonly("drv", "sd")) < 0) {
559 			cmn_err(CE_CONT, "Cannot load drv/sd\n");
560 			goto out;
561 		}
562 		if ((err = modload("misc", "strplumb")) < 0) {
563 			cmn_err(CE_CONT, "Cannot load misc/strplumb\n");
564 			goto out;
565 		}
566 		if ((err = strplumb_load()) < 0) {
567 			goto out;
568 		}
569 	}
570 	/*
571 	 * Preload modules needed for booting as a cluster.
572 	 */
573 	err = clboot_loadrootmodules();
574 
575 out:
576 	if (err != 0 && (boothowto & RB_ASKNAME))
577 		goto loop;
578 
579 	return (err);
580 }
581 
582 static int
583 get_bootpath_prop(char *bootpath)
584 {
585 	if (root_is_ramdisk) {
586 		if (BOP_GETPROP(bootops, "bootarchive", bootpath) == -1)
587 			return (-1);
588 		(void) strlcat(bootpath, ":a", BO_MAXOBJNAME);
589 	} else {
590 		/*
591 		 * Look for the 1275 compliant name 'bootpath' first,
592 		 * but make certain it has a non-NULL value as well.
593 		 */
594 		if ((BOP_GETPROP(bootops, "bootpath", bootpath) == -1) ||
595 		    strlen(bootpath) == 0) {
596 			if (BOP_GETPROP(bootops,
597 			    "boot-path", bootpath) == -1)
598 				return (-1);
599 		}
600 		if (memcmp(bootpath, BP_ISCSI_DISK,
601 		    strlen(BP_ISCSI_DISK)) == 0) {
602 			/* iscsi boot */
603 			get_iscsi_bootpath_vhci(bootpath);
604 		}
605 	}
606 	return (0);
607 }
608 
609 static int
610 get_fstype_prop(char *fstype)
611 {
612 	char *prop = (root_is_ramdisk) ? "archive-fstype" : "fstype";
613 
614 	return (BOP_GETPROP(bootops, prop, fstype));
615 }
616 
617 /*
618  * Get the name of the root or swap filesystem type, and return
619  * the corresponding entry in the vfs switch.
620  *
621  * If we're not asking the user, and we're trying to find the
622  * root filesystem type, we ask boot for the filesystem
623  * type that it came from and use that.  Similarly, if we're
624  * trying to find the swap filesystem, we try and derive it from
625  * the root filesystem type.
626  *
627  * If we are booting via NFS we currently have these options:
628  *	nfs -	dynamically choose NFS V2. V3, or V4 (default)
629  *	nfs2 -	force NFS V2
630  *	nfs3 -	force NFS V3
631  *	nfs4 -	force NFS V4
632  * Because we need to maintain backward compatibility with the naming
633  * convention that the NFS V2 filesystem name is "nfs" (see vfs_conf.c)
634  * we need to map "nfs" => "nfsdyn" and "nfs2" => "nfs".  The dynamic
635  * nfs module will map the type back to either "nfs", "nfs3", or "nfs4".
636  * This is only for root filesystems, all other uses will expect
637  * that "nfs" == NFS V2.
638  *
639  * If the filesystem isn't already loaded, vfs_getvfssw() will load
640  * it for us, but if (at the time we call it) modrootloaded is
641  * still not set, it won't run the filesystems _init routine (and
642  * implicitly it won't run the filesystems vsw_init() entry either).
643  * We do that explicitly in rootconf().
644  */
645 static struct vfssw *
646 getfstype(char *askfor, char *fsname, size_t fsnamelen)
647 {
648 	struct vfssw *vsw;
649 	static char defaultfs[BO_MAXFSNAME];
650 	int root = 0;
651 
652 	if (strcmp(askfor, "root") == 0) {
653 		(void) get_fstype_prop(defaultfs);
654 		root++;
655 	} else {
656 		(void) strcpy(defaultfs, "swapfs");
657 	}
658 
659 	if (boothowto & RB_ASKNAME) {
660 		for (*fsname = '\0'; *fsname == '\0'; *fsname = '\0') {
661 			printf("%s filesystem type [%s]: ", askfor, defaultfs);
662 			console_gets(fsname, fsnamelen);
663 			if (*fsname == '\0')
664 				(void) strcpy(fsname, defaultfs);
665 			if (root) {
666 				if (strcmp(fsname, "nfs2") == 0)
667 					(void) strcpy(fsname, "nfs");
668 				else if (strcmp(fsname, "nfs") == 0)
669 					(void) strcpy(fsname, "nfsdyn");
670 			}
671 			if ((vsw = vfs_getvfssw(fsname)) != NULL)
672 				return (vsw);
673 			printf("Unknown filesystem type '%s'\n", fsname);
674 		}
675 	} else if (*fsname == '\0') {
676 		fsname = defaultfs;
677 	}
678 	if (*fsname == '\0') {
679 		return (NULL);
680 	}
681 
682 	if (root) {
683 		if (strcmp(fsname, "nfs2") == 0)
684 			(void) strcpy(fsname, "nfs");
685 		else if (strcmp(fsname, "nfs") == 0)
686 			(void) strcpy(fsname, "nfsdyn");
687 	}
688 
689 	return (vfs_getvfssw(fsname));
690 }
691 
692 
693 /*
694  * Get a physical device name, and maybe load and attach
695  * the driver.
696  *
697  * XXX	Need better checking of whether or not a device
698  *	actually exists if the user typed in a pathname.
699  *
700  * XXX	Are we sure we want to expose users to this sort
701  *	of physical namespace gobbledygook (now there's
702  *	a word to conjure with..)
703  *
704  * XXX	Note that on an OBP machine, we can easily ask the
705  *	prom and pretty-print some plausible set of bootable
706  *	devices.  We can also user the prom to verify any
707  *	such device.  Later tim.. later.
708  */
709 static int
710 getphysdev(char *askfor, char *name, size_t namelen)
711 {
712 	static char fmt[] = "Enter physical name of %s device\n[%s]: ";
713 	dev_t dev;
714 	static char defaultpath[BO_MAXOBJNAME];
715 
716 	/*
717 	 * Establish 'default' values - we get the root device from
718 	 * boot, and we infer the swap device is the same but with
719 	 * a 'b' on the end instead of an 'a'.  A first stab at
720 	 * ease-of-use ..
721 	 */
722 	if (strcmp(askfor, "root") == 0) {
723 		if (get_bootpath_prop(defaultpath) == -1)
724 			boothowto |= RB_ASKNAME | RB_VERBOSE;
725 	} else {
726 		(void) strcpy(defaultpath, rootfs.bo_name);
727 		defaultpath[strlen(defaultpath) - 1] = 'b';
728 	}
729 
730 retry:
731 	if (boothowto & RB_ASKNAME) {
732 		printf(fmt, askfor, defaultpath);
733 		console_gets(name, namelen);
734 	}
735 	if (*name == '\0')
736 		(void) strcpy(name, defaultpath);
737 
738 	if (strcmp(askfor, "swap") == 0)   {
739 
740 		/*
741 		 * Try to load and install the swap device driver.
742 		 */
743 		dev = ddi_pathname_to_dev_t(name);
744 
745 		if (dev == (dev_t)-1)  {
746 			printf("Not a supported device for swap.\n");
747 			boothowto |= RB_ASKNAME | RB_VERBOSE;
748 			goto retry;
749 		}
750 
751 		/*
752 		 * Ensure that we're not trying to swap on the floppy.
753 		 */
754 		if (strncmp(ddi_major_to_name(getmajor(dev)), "fd", 2) == 0) {
755 			printf("Too dangerous to swap on the floppy\n");
756 			if (boothowto & RB_ASKNAME)
757 				goto retry;
758 			return (-1);
759 		}
760 	}
761 
762 	return (0);
763 }
764 
765 
766 /*
767  * Load a driver needed to boot.
768  */
769 static int
770 load_boot_driver(char *drv)
771 {
772 	char		*drvname;
773 	major_t		major;
774 #ifdef	sparc
775 	struct devnames *dnp;
776 	ddi_prop_t	*propp;
777 	char		*module;
778 	char		*dir, *mf;
779 	int		plen;
780 	int		mlen;
781 #endif	/* sparc */
782 
783 	if ((major = ddi_name_to_major(drv)) == DDI_MAJOR_T_NONE) {
784 		cmn_err(CE_CONT, "%s: no major number\n", drv);
785 		return (-1);
786 	}
787 	/*
788 	 * resolve aliases
789 	 */
790 	drvname = ddi_major_to_name(major);
791 
792 #ifdef	DEBUG
793 	if (strcmp(drv, drvname) == 0) {
794 		BMDPRINTF(("load_boot_driver: %s\n", drv));
795 	} else {
796 		BMDPRINTF(("load_boot_driver: %s -> %s\n", drv, drvname));
797 	}
798 #endif	/* DEBUG */
799 
800 	if (modloadonly("drv", drvname) == -1) {
801 		cmn_err(CE_CONT, "%s: cannot load driver\n", drvname);
802 		return (-1);
803 	}
804 
805 #ifdef	sparc
806 	/*
807 	 * NOTE: this can be removed when newboot-sparc is delivered.
808 	 *
809 	 * Check to see if the driver had a 'ddi-forceload' global driver.conf
810 	 * property to identify additional modules that need to be loaded.
811 	 * The driver still needs to use ddi_modopen() to open these modules,
812 	 * but the 'ddi-forceload' property allows the modules to be loaded
813 	 * into memory prior to lights-out, so that driver ddi_modopen()
814 	 * calls during lights-out (when mounting root) will work correctly.
815 	 * Use of 'ddi-forceload' is only required for drivers involved in
816 	 * getting root mounted.
817 	 */
818 	dnp = &devnamesp[major];
819 	if (dnp->dn_global_prop_ptr && dnp->dn_global_prop_ptr->prop_list &&
820 	    ((propp = i_ddi_prop_search(DDI_DEV_T_ANY,
821 	    "ddi-forceload", DDI_PROP_TYPE_STRING,
822 	    &dnp->dn_global_prop_ptr->prop_list)) != NULL)) {
823 
824 		module = (char *)propp->prop_val;
825 		plen = propp->prop_len;
826 		while (plen > 0) {
827 			mlen = strlen(module);
828 			mf = strrchr(module, '/');
829 			if (mf) {
830 				dir = module;
831 				*mf++ = '\0';		/* '/' -> '\0' */
832 			} else {
833 				dir = "misc";
834 				mf = module;
835 			}
836 			if (modloadonly(dir, mf) == -1)
837 				cmn_err(CE_CONT,
838 				    "misc/%s: can't load module\n", mf);
839 			if (mf != module)
840 				*(mf - 1) = '/';	/* '\0' -> '/' */
841 
842 			module += mlen + 1;
843 			plen -= mlen + 1;
844 		}
845 	}
846 #endif	/* sparc */
847 
848 	return (0);
849 }
850 
851 
852 /*
853  * For a given instance, load that driver and its parents
854  */
855 static int
856 load_parent_drivers(dev_info_t *dip, char *path)
857 {
858 	int	rval = 0;
859 	major_t	major = DDI_MAJOR_T_NONE;
860 	char	*drv;
861 	char	*p;
862 
863 	while (dip) {
864 		/* check for path-oriented alias */
865 		if (path)
866 			major = ddi_name_to_major(path);
867 		else
868 			major = DDI_MAJOR_T_NONE;
869 
870 		if (major != DDI_MAJOR_T_NONE)
871 			drv = ddi_major_to_name(major);
872 		else
873 			drv = ddi_binding_name(dip);
874 
875 		if (load_boot_driver(drv) != 0)
876 			rval = -1;
877 
878 		dip = ddi_get_parent(dip);
879 		if (path) {
880 			p = strrchr(path, '/');
881 			if (p)
882 				*p = 0;
883 		}
884 	}
885 
886 	return (rval);
887 }
888 
889 
890 /*
891  * For a given path to a boot device,
892  * load that driver and all its parents.
893  */
894 static int
895 load_bootpath_drivers(char *bootpath)
896 {
897 	dev_info_t	*dip;
898 	char		*pathcopy;
899 	int		pathcopy_len;
900 	int		rval;
901 	char		*p;
902 	int		proplen;
903 	char		iscsi_network_path[BO_MAXOBJNAME];
904 
905 	if (bootpath == NULL || *bootpath == 0)
906 		return (-1);
907 
908 	BMDPRINTF(("load_bootpath_drivers: %s\n", bootpath));
909 #ifdef _OBP
910 	if (netboot_over_iscsi()) {
911 		/* iscsi boot */
912 		if (root_is_ramdisk) {
913 			if (modloadonly("drv", "ramdisk") < 0)
914 				return (-1);
915 		}
916 		proplen = BOP_GETPROPLEN(bootops, BP_ISCSI_NETWORK_BOOTPATH);
917 		if (proplen > 0) {
918 			if (BOP_GETPROP(bootops, BP_ISCSI_NETWORK_BOOTPATH,
919 			    iscsi_network_path) > 0) {
920 				p = strchr(iscsi_network_path, ':');
921 				if (p != NULL) {
922 					*p = '\0';
923 				}
924 				pathcopy = i_ddi_strdup(iscsi_network_path,
925 				    KM_SLEEP);
926 				pathcopy_len = strlen(pathcopy) + 1;
927 			} else {
928 				return (-1);
929 			}
930 		} else {
931 			return (-1);
932 		}
933 	} else {
934 #endif
935 		pathcopy = i_ddi_strdup(bootpath, KM_SLEEP);
936 		pathcopy_len = strlen(pathcopy) + 1;
937 #ifdef _OBP
938 	}
939 #endif
940 	dip = path_to_devinfo(pathcopy);
941 
942 #if defined(__i386) || defined(__amd64)
943 	/*
944 	 * i386 does not provide stub nodes for all boot devices,
945 	 * but we should be able to find the node for the parent,
946 	 * and the leaf of the boot path should be the driver name,
947 	 * which we go ahead and load here.
948 	 */
949 	if (dip == NULL) {
950 		char	*leaf;
951 
952 		/*
953 		 * Find last slash to build the full path to the
954 		 * parent of the leaf boot device
955 		 */
956 		p = strrchr(pathcopy, '/');
957 		*p++ = 0;
958 
959 		/*
960 		 * Now isolate the driver name of the leaf device
961 		 */
962 		leaf = p;
963 		p = strchr(leaf, '@');
964 		*p = 0;
965 
966 		BMDPRINTF(("load_bootpath_drivers: parent=%s leaf=%s\n",
967 		    bootpath, leaf));
968 
969 		dip = path_to_devinfo(pathcopy);
970 		if (leaf) {
971 			rval = load_boot_driver(leaf, NULL);
972 			if (rval == -1) {
973 				kmem_free(pathcopy, pathcopy_len);
974 				return (NULL);
975 			}
976 		}
977 	}
978 #endif
979 
980 	if (dip == NULL) {
981 		cmn_err(CE_WARN, "can't bind driver for boot path <%s>",
982 		    bootpath);
983 		kmem_free(pathcopy, pathcopy_len);
984 		return (NULL);
985 	}
986 
987 	/*
988 	 * Load IP over IB driver when netbooting over IB.
989 	 * As per IB 1275 binding, IP over IB is represented as
990 	 * service on the top of the HCA node. So, there is no
991 	 * PROM node and generic framework cannot pre-load
992 	 * IP over IB driver based on the bootpath. The following
993 	 * code preloads IP over IB driver when doing netboot over
994 	 * InfiniBand.
995 	 */
996 	if (netboot_over_ib(bootpath) &&
997 	    modloadonly("drv", "ibp") == -1) {
998 		cmn_err(CE_CONT, "ibp: cannot load platform driver\n");
999 		kmem_free(pathcopy, pathcopy_len);
1000 		return (NULL);
1001 	}
1002 
1003 	/*
1004 	 * The PROM node for hubs have incomplete compatible
1005 	 * properties and therefore do not bind to the hubd driver.
1006 	 * As a result load_bootpath_drivers() loads the usb_mid driver
1007 	 * for hub nodes rather than the hubd driver. This causes
1008 	 * mountroot failures when booting off USB storage. To prevent
1009 	 * this, if we are booting via USB hubs, we preload the hubd driver.
1010 	 */
1011 	if (strstr(bootpath, "/hub@") && modloadonly("drv", "hubd") == -1) {
1012 		cmn_err(CE_WARN, "bootpath contains a USB hub, "
1013 		    "but cannot load hubd driver");
1014 	}
1015 
1016 	/* get rid of minor node at end of copy (if not already done above) */
1017 	p = strrchr(pathcopy, '/');
1018 	if (p) {
1019 		p = strchr(p, ':');
1020 		if (p)
1021 			*p = 0;
1022 	}
1023 
1024 	rval = load_parent_drivers(dip, pathcopy);
1025 	kmem_free(pathcopy, pathcopy_len);
1026 	return (rval);
1027 }
1028 
1029 
1030 
1031 
1032 /*
1033  * Load drivers required for a platform
1034  * Since all hardware nodes should be available in the device
1035  * tree, walk the per-driver list and load the parents of
1036  * each node found. If not a hardware node, try to load it.
1037  * Pseudo nexus is already loaded.
1038  */
1039 static int
1040 load_boot_platform_modules(char *drv)
1041 {
1042 	major_t	major;
1043 	dev_info_t *dip;
1044 	char	*drvname;
1045 	int	rval = 0;
1046 
1047 	if ((major = ddi_name_to_major(drv)) == DDI_MAJOR_T_NONE) {
1048 		cmn_err(CE_CONT, "%s: no major number\n", drv);
1049 		return (-1);
1050 	}
1051 
1052 	/*
1053 	 * resolve aliases
1054 	 */
1055 	drvname = ddi_major_to_name(major);
1056 	if ((major = ddi_name_to_major(drvname)) == DDI_MAJOR_T_NONE)
1057 		return (-1);
1058 
1059 #ifdef	DEBUG
1060 	if (strcmp(drv, drvname) == 0) {
1061 		BMDPRINTF(("load_boot_platform_modules: %s\n", drv));
1062 	} else {
1063 		BMDPRINTF(("load_boot_platform_modules: %s -> %s\n",
1064 		    drv, drvname));
1065 	}
1066 #endif	/* DEBUG */
1067 
1068 	dip = devnamesp[major].dn_head;
1069 	if (dip == NULL) {
1070 		/* pseudo node, not-enumerated, needs to be loaded */
1071 		if (modloadonly("drv", drvname) == -1) {
1072 			cmn_err(CE_CONT, "%s: cannot load platform driver\n",
1073 			    drvname);
1074 			rval = -1;
1075 		}
1076 	} else {
1077 		while (dip) {
1078 			if (load_parent_drivers(dip, NULL) != 0)
1079 				rval = -1;
1080 			dip = ddi_get_next(dip);
1081 		}
1082 	}
1083 
1084 	return (rval);
1085 }
1086 
1087 
1088 /*
1089  * i_find_node: Internal routine used by path_to_devinfo
1090  * to locate a given nodeid in the device tree.
1091  */
1092 struct i_path_findnode {
1093 	pnode_t nodeid;
1094 	dev_info_t *dip;
1095 };
1096 
1097 static int
1098 i_path_find_node(dev_info_t *dev, void *arg)
1099 {
1100 	struct i_path_findnode *f = (struct i_path_findnode *)arg;
1101 
1102 
1103 	if (ddi_get_nodeid(dev) == (int)f->nodeid) {
1104 		f->dip = dev;
1105 		return (DDI_WALK_TERMINATE);
1106 	}
1107 	return (DDI_WALK_CONTINUE);
1108 }
1109 
1110 /*
1111  * Return the devinfo node to a boot device
1112  */
1113 static dev_info_t *
1114 path_to_devinfo(char *path)
1115 {
1116 	struct i_path_findnode fn;
1117 	extern dev_info_t *top_devinfo;
1118 
1119 	/*
1120 	 * Get the nodeid of the given pathname, if such a mapping exists.
1121 	 */
1122 	fn.dip = NULL;
1123 	fn.nodeid = prom_finddevice(path);
1124 	if (fn.nodeid != OBP_BADNODE) {
1125 		/*
1126 		 * Find the nodeid in our copy of the device tree and return
1127 		 * whatever name we used to bind this node to a driver.
1128 		 */
1129 		ddi_walk_devs(top_devinfo, i_path_find_node, (void *)(&fn));
1130 	}
1131 
1132 #ifdef	DEBUG
1133 	/*
1134 	 * If we're bound to something other than the nodename,
1135 	 * note that in the message buffer and system log.
1136 	 */
1137 	if (fn.dip) {
1138 		char *p, *q;
1139 
1140 		p = ddi_binding_name(fn.dip);
1141 		q = ddi_node_name(fn.dip);
1142 		if (p && q && (strcmp(p, q) != 0)) {
1143 			BMDPRINTF(("path_to_devinfo: %s bound to %s\n",
1144 			    path, p));
1145 		}
1146 	}
1147 #endif	/* DEBUG */
1148 
1149 	return (fn.dip);
1150 }
1151 
1152 /*
1153  * This routine returns B_TRUE if the bootpath corresponds to
1154  * IP over IB driver.
1155  *
1156  * The format of the bootpath for the IP over IB looks like
1157  * /pci@1f,700000/pci@1/ib@0:port=1,pkey=8001,protocol=ip
1158  *
1159  * The minor node portion "port=1,pkey=8001,protocol=ip" represents
1160  * IP over IB driver.
1161  */
1162 static boolean_t
1163 netboot_over_ib(char *bootpath)
1164 {
1165 
1166 	char		*temp;
1167 	boolean_t	ret = B_FALSE;
1168 	pnode_t		node = prom_finddevice(bootpath);
1169 	int		len;
1170 	char		devicetype[OBP_MAXDRVNAME];
1171 
1172 	/* Is this IB node ? */
1173 	if (node == OBP_BADNODE || node == OBP_NONODE) {
1174 		return (B_FALSE);
1175 	}
1176 	len = prom_getproplen(node, OBP_DEVICETYPE);
1177 	if (len <= 1 || len >= OBP_MAXDRVNAME)
1178 		return (B_FALSE);
1179 
1180 	(void) prom_getprop(node, OBP_DEVICETYPE, (caddr_t)devicetype);
1181 
1182 	if (strncmp("ib", devicetype, 2) == 0) {
1183 		/* Check for proper IP over IB string */
1184 		if ((temp = strstr(bootpath, ":port=")) != NULL) {
1185 			if ((temp = strstr(temp, ",pkey=")) != NULL)
1186 				if ((temp = strstr(temp,
1187 				    ",protocol=ip")) != NULL) {
1188 					ret = B_TRUE;
1189 				}
1190 		}
1191 	}
1192 	return (ret);
1193 }
1194 
1195 static boolean_t
1196 netboot_over_iscsi(void)
1197 {
1198 	int proplen;
1199 	boolean_t	ret = B_FALSE;
1200 	char	bootpath[OBP_MAXPATHLEN];
1201 
1202 	proplen = BOP_GETPROPLEN(bootops, BP_BOOTPATH);
1203 	if (proplen > 0) {
1204 		if (BOP_GETPROP(bootops, BP_BOOTPATH, bootpath) > 0) {
1205 			if (memcmp(bootpath, BP_ISCSI_DISK,
1206 			    strlen(BP_ISCSI_DISK)) == 0) {
1207 				ret = B_TRUE;
1208 			}
1209 		}
1210 	}
1211 	return (ret);
1212 }
1213