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