xref: /netbsd-src/sys/arch/ews4800mips/stand/common/devopen.c (revision c2e8ce644bcf0a6856a25f9a8b5bf45c845b918e)
1*c2e8ce64Stsutsui /*	$NetBSD: devopen.c,v 1.5 2011/12/25 06:09:09 tsutsui Exp $	*/
204faabf0Stsutsui 
304faabf0Stsutsui /*-
404faabf0Stsutsui  * Copyright (c) 2004 The NetBSD Foundation, Inc.
504faabf0Stsutsui  * All rights reserved.
604faabf0Stsutsui  *
704faabf0Stsutsui  * This code is derived from software contributed to The NetBSD Foundation
804faabf0Stsutsui  * by UCHIYAMA Yasushi.
904faabf0Stsutsui  *
1004faabf0Stsutsui  * Redistribution and use in source and binary forms, with or without
1104faabf0Stsutsui  * modification, are permitted provided that the following conditions
1204faabf0Stsutsui  * are met:
1304faabf0Stsutsui  * 1. Redistributions of source code must retain the above copyright
1404faabf0Stsutsui  *    notice, this list of conditions and the following disclaimer.
1504faabf0Stsutsui  * 2. Redistributions in binary form must reproduce the above copyright
1604faabf0Stsutsui  *    notice, this list of conditions and the following disclaimer in the
1704faabf0Stsutsui  *    documentation and/or other materials provided with the distribution.
1804faabf0Stsutsui  *
1904faabf0Stsutsui  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
2004faabf0Stsutsui  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
2104faabf0Stsutsui  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
2204faabf0Stsutsui  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
2304faabf0Stsutsui  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2404faabf0Stsutsui  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2504faabf0Stsutsui  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
2604faabf0Stsutsui  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
2704faabf0Stsutsui  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
2804faabf0Stsutsui  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
2904faabf0Stsutsui  * POSSIBILITY OF SUCH DAMAGE.
3004faabf0Stsutsui  */
3104faabf0Stsutsui 
3204faabf0Stsutsui #include <lib/libsa/stand.h>
3304faabf0Stsutsui #include <lib/libkern/libkern.h>
3404faabf0Stsutsui 
3504faabf0Stsutsui #include <netinet/in.h>
3604faabf0Stsutsui #include <lib/libsa/dev_net.h>
3704faabf0Stsutsui #include <lib/libsa/ufs.h>
3804faabf0Stsutsui #include <lib/libsa/nfs.h>
39d1b230abStsutsui #include <lib/libsa/dev_net.h>
4004faabf0Stsutsui #include <machine/sbd.h>
4104faabf0Stsutsui 
4204faabf0Stsutsui #include "local.h"
4304faabf0Stsutsui 
4404faabf0Stsutsui extern uint8_t kernel_binary[];
4504faabf0Stsutsui extern int kernel_binary_size;
4604faabf0Stsutsui 
4704faabf0Stsutsui extern struct fs_ops datafs_ops;
4804faabf0Stsutsui extern struct fs_ops bfs_ops;
49*c2e8ce64Stsutsui struct fs_ops ufs_ops = FS_OPS(ufs);
50*c2e8ce64Stsutsui struct fs_ops nfs_ops = FS_OPS(nfs);
5104faabf0Stsutsui 
5204faabf0Stsutsui extern struct devsw netdevsw;
5304faabf0Stsutsui extern struct devsw dkdevsw;
5404faabf0Stsutsui char fname[16];
5504faabf0Stsutsui 
5604faabf0Stsutsui /* Referenced by libsa/open.c */
5704faabf0Stsutsui struct fs_ops file_system[1];
5804faabf0Stsutsui int nfsys = 1;
5904faabf0Stsutsui struct devsw devsw[1];
6004faabf0Stsutsui int ndevs = 1;
6104faabf0Stsutsui 
6204faabf0Stsutsui int
devopen(struct open_file * f,const char * request,char ** file)6304faabf0Stsutsui devopen(struct open_file *f, const char *request, char **file)
6404faabf0Stsutsui {
6504faabf0Stsutsui 	char *p, *filename;
6604faabf0Stsutsui 	int disk, partition;
6704faabf0Stsutsui 	void *addr;
6804faabf0Stsutsui 	size_t size;
6904faabf0Stsutsui 
7004faabf0Stsutsui 	strcpy(fname, request);
7104faabf0Stsutsui 
7204faabf0Stsutsui 	filename = 0;
7304faabf0Stsutsui 	for (p = fname; *p; p++) {
7404faabf0Stsutsui 		if (*p == ':') {
7504faabf0Stsutsui 			filename = p + 1;
7604faabf0Stsutsui 			*p = '\0';
7704faabf0Stsutsui 			break;
7804faabf0Stsutsui 		}
7904faabf0Stsutsui 	}
8004faabf0Stsutsui 
8104faabf0Stsutsui 	if (filename == 0) {	/* not a loader's request. probably ufs_ls() */
8204faabf0Stsutsui 		printf("request=%s\n", request);
8304faabf0Stsutsui 		f->f_dev = &dkdevsw;
8404faabf0Stsutsui 		file_system[0] = ufs_ops;
8504faabf0Stsutsui 		devsw[0] = dkdevsw;
8604faabf0Stsutsui 		*file = "/";
8704faabf0Stsutsui 		return 0;
8804faabf0Stsutsui 	}
8904faabf0Stsutsui 
9004faabf0Stsutsui 	/* Data section */
9104faabf0Stsutsui 	if (strcmp(fname, "mem") == 0) {
9204faabf0Stsutsui 		data_attach(kernel_binary, kernel_binary_size);
9304faabf0Stsutsui 		*file = "noname";
9404faabf0Stsutsui 		f->f_flags |= F_NODEV;
9504faabf0Stsutsui 		file_system[0] = datafs_ops;
9604faabf0Stsutsui 		printf("data(compiled):noname\n");
9704faabf0Stsutsui 		return 0;
9804faabf0Stsutsui 	}
9904faabf0Stsutsui 
10004faabf0Stsutsui 	/* NFS boot */
10104faabf0Stsutsui 	if (strcmp(fname, "nfs") == 0) {
10204faabf0Stsutsui 		if (!DEVICE_CAPABILITY.network_enabled) {
10304faabf0Stsutsui 			printf("Network disabled.\n");
10404faabf0Stsutsui 			return -1;
10504faabf0Stsutsui 		}
10616ed6645Sthorpej 		try_bootp = true;
10704faabf0Stsutsui 		file_system[0] = nfs_ops;
10804faabf0Stsutsui 		f->f_dev = &netdevsw;
10904faabf0Stsutsui 		if (*filename == '\0') {
11004faabf0Stsutsui 			printf("set kernel filename. ex.) nfs:netbsd\n");
11104faabf0Stsutsui 			return 1;
11204faabf0Stsutsui 		}
11304faabf0Stsutsui 		*--filename = '/';
11404faabf0Stsutsui 		*file = filename;
11504faabf0Stsutsui 		printf("nfs:/%s\n", filename);
11604faabf0Stsutsui 		net_open(f);
11704faabf0Stsutsui 		return 0;
11804faabf0Stsutsui 	}
11904faabf0Stsutsui 
12004faabf0Stsutsui 	/* FD boot */
12104faabf0Stsutsui 	if (strcmp(fname, "fd") == 0) {
12204faabf0Stsutsui 		printf("floppy(boot):/%s (ustarfs)\n", filename);
12304faabf0Stsutsui 		f->f_dev = &dkdevsw;
12404faabf0Stsutsui 		file_system[0] = datafs_ops;
12504faabf0Stsutsui 		devsw[0] = dkdevsw;
12604faabf0Stsutsui 		device_attach(NVSRAM_BOOTDEV_FLOPPYDISK, -1, -1);
12704faabf0Stsutsui 		if (!ustarfs_load(filename, &addr, &size))
12804faabf0Stsutsui 			return -1;
12904faabf0Stsutsui 		data_attach(addr, size);
13004faabf0Stsutsui 		*file = filename;
13104faabf0Stsutsui 		return 0;
13204faabf0Stsutsui 	}
13304faabf0Stsutsui 
13404faabf0Stsutsui 	/* Disk boot */
13504faabf0Stsutsui 	if (strncmp(fname, "sd", 2) == 0) {
13604faabf0Stsutsui 		enum fstype fs;
13704faabf0Stsutsui 		if (!DEVICE_CAPABILITY.disk_enabled) {
13804faabf0Stsutsui 			printf("Disk disabled.\n");
13904faabf0Stsutsui 			return -1;
14004faabf0Stsutsui 		}
14104faabf0Stsutsui 
14204faabf0Stsutsui 		disk = fname[2] - '0';
14304faabf0Stsutsui 		partition = fname[3] - 'a';
14404faabf0Stsutsui 		if (disk < 0 || disk > 9 || partition < 0 || partition > 15) {
14504faabf0Stsutsui 			fs = FSTYPE_USTARFS;
14604faabf0Stsutsui 			printf("disk(boot):%s ", filename);
14704faabf0Stsutsui 			device_attach(NVSRAM_BOOTDEV_HARDDISK, -1, -1);
14804faabf0Stsutsui 		} else {
14904faabf0Stsutsui 			fs = fstype(partition);
15004faabf0Stsutsui 			printf("disk(%d,%d):/%s ",
15104faabf0Stsutsui 			    disk, partition, filename);
15204faabf0Stsutsui 			device_attach(NVSRAM_BOOTDEV_HARDDISK, disk, partition);
15304faabf0Stsutsui 		}
15404faabf0Stsutsui 
15504faabf0Stsutsui 		switch (fs) {
15604faabf0Stsutsui 		case FSTYPE_UFS:
15704faabf0Stsutsui 			printf(" (ufs)\n");
15804faabf0Stsutsui 			f->f_dev = &dkdevsw;
15904faabf0Stsutsui 			file_system[0] = ufs_ops;
16004faabf0Stsutsui 			devsw[0] = dkdevsw;
16104faabf0Stsutsui 			break;
16204faabf0Stsutsui 		case FSTYPE_BFS:
16304faabf0Stsutsui 			printf(" (bfs)\n");
16404faabf0Stsutsui 			f->f_flags |= F_NODEV;
16504faabf0Stsutsui 			file_system[0] = bfs_ops;
16604faabf0Stsutsui 			break;
16704faabf0Stsutsui 		case FSTYPE_USTARFS:
16804faabf0Stsutsui 			printf(" (ustarfs)\n");
16904faabf0Stsutsui 			f->f_dev = &dkdevsw;
17004faabf0Stsutsui 			file_system[0] = datafs_ops;
17104faabf0Stsutsui 			devsw[0] = dkdevsw;
17204faabf0Stsutsui 			if (!ustarfs_load(filename, &addr, &size))
17304faabf0Stsutsui 				return -1;
17404faabf0Stsutsui 			data_attach(addr, size);
17504faabf0Stsutsui 			break;
17604faabf0Stsutsui 		}
17704faabf0Stsutsui 		*file = filename;
17804faabf0Stsutsui 		return 0;
17904faabf0Stsutsui 	}
18004faabf0Stsutsui 
18104faabf0Stsutsui 	printf("%s invalid.\n", fname);
18204faabf0Stsutsui 
18304faabf0Stsutsui 	return -1;
18404faabf0Stsutsui }
185