xref: /titanic_44/usr/src/common/fs/bootfsops.c (revision 1d9cde1dcd9c3d71413dae0f9e9b3845a667cd9c)
1*1d9cde1dSKeith M Wesolowski /*
2*1d9cde1dSKeith M Wesolowski  * This file and its contents are supplied under the terms of the
3*1d9cde1dSKeith M Wesolowski  * Common Development and Distribution License ("CDDL"), version 1.0.
4*1d9cde1dSKeith M Wesolowski  * You may only use this file in accordance with the terms of version
5*1d9cde1dSKeith M Wesolowski  * 1.0 of the CDDL.
6*1d9cde1dSKeith M Wesolowski  *
7*1d9cde1dSKeith M Wesolowski  * A full copy of the text of the CDDL should have accompanied this
8*1d9cde1dSKeith M Wesolowski  * source.  A copy of the CDDL is also available via the Internet at
9*1d9cde1dSKeith M Wesolowski  * http://www.illumos.org/license/CDDL.
10*1d9cde1dSKeith M Wesolowski  */
11*1d9cde1dSKeith M Wesolowski 
12*1d9cde1dSKeith M Wesolowski /*
13*1d9cde1dSKeith M Wesolowski  * Copyright 2013 Joyent, Inc.  All rights reserved.
14*1d9cde1dSKeith M Wesolowski  */
15*1d9cde1dSKeith M Wesolowski 
16*1d9cde1dSKeith M Wesolowski #include <sys/bootconf.h>
17*1d9cde1dSKeith M Wesolowski #include <sys/types.h>
18*1d9cde1dSKeith M Wesolowski #include <sys/param.h>
19*1d9cde1dSKeith M Wesolowski #include <sys/vnode.h>
20*1d9cde1dSKeith M Wesolowski #include <sys/fs/ufs_fsdir.h>
21*1d9cde1dSKeith M Wesolowski #include <sys/fs/ufs_fs.h>
22*1d9cde1dSKeith M Wesolowski #include <sys/fs/ufs_inode.h>
23*1d9cde1dSKeith M Wesolowski #include <sys/sysmacros.h>
24*1d9cde1dSKeith M Wesolowski #include <sys/bootvfs.h>
25*1d9cde1dSKeith M Wesolowski #include <sys/bootinfo.h>
26*1d9cde1dSKeith M Wesolowski #include <sys/filep.h>
27*1d9cde1dSKeith M Wesolowski 
28*1d9cde1dSKeith M Wesolowski #ifdef	_BOOT
29*1d9cde1dSKeith M Wesolowski #include "../common/util.h"
30*1d9cde1dSKeith M Wesolowski #else
31*1d9cde1dSKeith M Wesolowski #include <sys/sunddi.h>
32*1d9cde1dSKeith M Wesolowski #endif
33*1d9cde1dSKeith M Wesolowski 
34*1d9cde1dSKeith M Wesolowski #define	MAX_FILES	MAX_BOOT_MODULES
35*1d9cde1dSKeith M Wesolowski #define	MAX_FDS		256
36*1d9cde1dSKeith M Wesolowski 
37*1d9cde1dSKeith M Wesolowski extern void *bkmem_alloc(size_t);
38*1d9cde1dSKeith M Wesolowski extern void bkmem_free(void *, size_t);
39*1d9cde1dSKeith M Wesolowski 
40*1d9cde1dSKeith M Wesolowski /*
41*1d9cde1dSKeith M Wesolowski  * TODO: Replace these declarations with inclusion of the ordinary userland
42*1d9cde1dSKeith M Wesolowski  * bootfs headers once they're available.
43*1d9cde1dSKeith M Wesolowski  */
44*1d9cde1dSKeith M Wesolowski typedef struct bfile {
45*1d9cde1dSKeith M Wesolowski 	char bf_name[MAXPATHLEN];
46*1d9cde1dSKeith M Wesolowski 	caddr_t bf_addr;
47*1d9cde1dSKeith M Wesolowski 	size_t bf_size;
48*1d9cde1dSKeith M Wesolowski 	struct bfile *bf_next;
49*1d9cde1dSKeith M Wesolowski 	uint64_t bf_ino;
50*1d9cde1dSKeith M Wesolowski } bfile_t;
51*1d9cde1dSKeith M Wesolowski 
52*1d9cde1dSKeith M Wesolowski typedef struct bf_fd {
53*1d9cde1dSKeith M Wesolowski 	bfile_t *fd_file;
54*1d9cde1dSKeith M Wesolowski 	off_t fd_pos;
55*1d9cde1dSKeith M Wesolowski } bf_fd_t;
56*1d9cde1dSKeith M Wesolowski 
57*1d9cde1dSKeith M Wesolowski static bfile_t *head;
58*1d9cde1dSKeith M Wesolowski static uint_t init_done;
59*1d9cde1dSKeith M Wesolowski static bf_fd_t fds[MAX_FDS];
60*1d9cde1dSKeith M Wesolowski 
61*1d9cde1dSKeith M Wesolowski static char cpath[MAXPATHLEN];	/* For canonicalising filenames */
62*1d9cde1dSKeith M Wesolowski 
63*1d9cde1dSKeith M Wesolowski static void bbootfs_closeall(int);
64*1d9cde1dSKeith M Wesolowski 
65*1d9cde1dSKeith M Wesolowski static void
canonicalise(const char * fn,char * out)66*1d9cde1dSKeith M Wesolowski canonicalise(const char *fn, char *out)
67*1d9cde1dSKeith M Wesolowski {
68*1d9cde1dSKeith M Wesolowski 	const char *p;
69*1d9cde1dSKeith M Wesolowski 	char *q, *s;
70*1d9cde1dSKeith M Wesolowski 	char *last;
71*1d9cde1dSKeith M Wesolowski 	char *oc;
72*1d9cde1dSKeith M Wesolowski 	int is_slash = 0;
73*1d9cde1dSKeith M Wesolowski 	static char scratch[MAXPATHLEN];
74*1d9cde1dSKeith M Wesolowski 
75*1d9cde1dSKeith M Wesolowski 	if (fn == NULL) {
76*1d9cde1dSKeith M Wesolowski 		*out = '\0';
77*1d9cde1dSKeith M Wesolowski 		return;
78*1d9cde1dSKeith M Wesolowski 	}
79*1d9cde1dSKeith M Wesolowski 
80*1d9cde1dSKeith M Wesolowski 	/*
81*1d9cde1dSKeith M Wesolowski 	 * Remove leading slashes and condense all multiple slashes into one.
82*1d9cde1dSKeith M Wesolowski 	 */
83*1d9cde1dSKeith M Wesolowski 	p = fn;
84*1d9cde1dSKeith M Wesolowski 	while (*p == '/')
85*1d9cde1dSKeith M Wesolowski 		++p;
86*1d9cde1dSKeith M Wesolowski 
87*1d9cde1dSKeith M Wesolowski 	for (q = scratch; *p != '\0'; p++) {
88*1d9cde1dSKeith M Wesolowski 		if (*p == '/' && !is_slash) {
89*1d9cde1dSKeith M Wesolowski 			*q++ = '/';
90*1d9cde1dSKeith M Wesolowski 			is_slash = 1;
91*1d9cde1dSKeith M Wesolowski 		} else if (*p != '/') {
92*1d9cde1dSKeith M Wesolowski 			*q++ = *p;
93*1d9cde1dSKeith M Wesolowski 			is_slash = 0;
94*1d9cde1dSKeith M Wesolowski 		}
95*1d9cde1dSKeith M Wesolowski 	}
96*1d9cde1dSKeith M Wesolowski 	*q = '\0';
97*1d9cde1dSKeith M Wesolowski 
98*1d9cde1dSKeith M Wesolowski 	if (strncmp(scratch, "system/boot/", 12) == 0 ||
99*1d9cde1dSKeith M Wesolowski 	    strcmp(scratch, "system/boot") == 0) {
100*1d9cde1dSKeith M Wesolowski 		s = scratch + 12;
101*1d9cde1dSKeith M Wesolowski 	} else {
102*1d9cde1dSKeith M Wesolowski 		s = scratch;
103*1d9cde1dSKeith M Wesolowski 	}
104*1d9cde1dSKeith M Wesolowski 
105*1d9cde1dSKeith M Wesolowski 	for (last = strsep(&s, "/"), q = oc = out; last != NULL;
106*1d9cde1dSKeith M Wesolowski 	    last = strsep(&s, "/")) {
107*1d9cde1dSKeith M Wesolowski 		if (strcmp(last, ".") == 0)
108*1d9cde1dSKeith M Wesolowski 			continue;
109*1d9cde1dSKeith M Wesolowski 		if (strcmp(last, "..") == 0) {
110*1d9cde1dSKeith M Wesolowski 			for (oc = q; oc > out && *oc != '/'; oc--)
111*1d9cde1dSKeith M Wesolowski 				;
112*1d9cde1dSKeith M Wesolowski 			q = oc;
113*1d9cde1dSKeith M Wesolowski 			continue;
114*1d9cde1dSKeith M Wesolowski 		}
115*1d9cde1dSKeith M Wesolowski 		if (q > out)
116*1d9cde1dSKeith M Wesolowski 			*q++ = '/';
117*1d9cde1dSKeith M Wesolowski 		q += snprintf(q, MAXPATHLEN - (q - out), "%s", last);
118*1d9cde1dSKeith M Wesolowski 	}
119*1d9cde1dSKeith M Wesolowski 
120*1d9cde1dSKeith M Wesolowski 	*q = '\0';
121*1d9cde1dSKeith M Wesolowski }
122*1d9cde1dSKeith M Wesolowski 
123*1d9cde1dSKeith M Wesolowski /* ARGSUSED */
124*1d9cde1dSKeith M Wesolowski static int
bbootfs_mountroot(char * str)125*1d9cde1dSKeith M Wesolowski bbootfs_mountroot(char *str)
126*1d9cde1dSKeith M Wesolowski {
127*1d9cde1dSKeith M Wesolowski 	return (-1);
128*1d9cde1dSKeith M Wesolowski }
129*1d9cde1dSKeith M Wesolowski 
130*1d9cde1dSKeith M Wesolowski static int
bbootfs_unmountroot(void)131*1d9cde1dSKeith M Wesolowski bbootfs_unmountroot(void)
132*1d9cde1dSKeith M Wesolowski {
133*1d9cde1dSKeith M Wesolowski 	return (-1);
134*1d9cde1dSKeith M Wesolowski }
135*1d9cde1dSKeith M Wesolowski 
136*1d9cde1dSKeith M Wesolowski static int
bbootfs_init(void)137*1d9cde1dSKeith M Wesolowski bbootfs_init(void)
138*1d9cde1dSKeith M Wesolowski {
139*1d9cde1dSKeith M Wesolowski 	bfile_t *fp;
140*1d9cde1dSKeith M Wesolowski 	char propname[32];
141*1d9cde1dSKeith M Wesolowski 	uint64_t propval;
142*1d9cde1dSKeith M Wesolowski 	uint_t i;
143*1d9cde1dSKeith M Wesolowski 
144*1d9cde1dSKeith M Wesolowski 	for (i = 0; i < MAX_FILES; i++) {
145*1d9cde1dSKeith M Wesolowski 		(void) snprintf(propname, sizeof (propname),
146*1d9cde1dSKeith M Wesolowski 		    "module-name-%u", i);
147*1d9cde1dSKeith M Wesolowski 		if (do_bsys_getproplen(NULL, propname) < 0)
148*1d9cde1dSKeith M Wesolowski 			break;
149*1d9cde1dSKeith M Wesolowski 
150*1d9cde1dSKeith M Wesolowski 		if ((fp = bkmem_alloc(sizeof (bfile_t))) == NULL) {
151*1d9cde1dSKeith M Wesolowski 			bbootfs_closeall(1);
152*1d9cde1dSKeith M Wesolowski 			return (-1);
153*1d9cde1dSKeith M Wesolowski 		}
154*1d9cde1dSKeith M Wesolowski 
155*1d9cde1dSKeith M Wesolowski 		(void) do_bsys_getprop(NULL, propname, cpath);
156*1d9cde1dSKeith M Wesolowski 		canonicalise(cpath, fp->bf_name);
157*1d9cde1dSKeith M Wesolowski 
158*1d9cde1dSKeith M Wesolowski 		(void) snprintf(propname, sizeof (propname),
159*1d9cde1dSKeith M Wesolowski 		    "module-addr-%u", i);
160*1d9cde1dSKeith M Wesolowski 		if (do_bsys_getproplen(NULL, propname) != sizeof (uint64_t)) {
161*1d9cde1dSKeith M Wesolowski 			bkmem_free(fp, sizeof (bfile_t));
162*1d9cde1dSKeith M Wesolowski 			continue;
163*1d9cde1dSKeith M Wesolowski 		}
164*1d9cde1dSKeith M Wesolowski 		(void) do_bsys_getprop(NULL, propname, &propval);
165*1d9cde1dSKeith M Wesolowski 		fp->bf_addr = (void *)(uintptr_t)propval;
166*1d9cde1dSKeith M Wesolowski 
167*1d9cde1dSKeith M Wesolowski 		(void) snprintf(propname, sizeof (propname),
168*1d9cde1dSKeith M Wesolowski 		    "module-size-%u", i);
169*1d9cde1dSKeith M Wesolowski 		if (do_bsys_getproplen(NULL, propname) != sizeof (uint64_t)) {
170*1d9cde1dSKeith M Wesolowski 			bkmem_free(fp, sizeof (bfile_t));
171*1d9cde1dSKeith M Wesolowski 			continue;
172*1d9cde1dSKeith M Wesolowski 		}
173*1d9cde1dSKeith M Wesolowski 		(void) do_bsys_getprop(NULL, propname, &propval);
174*1d9cde1dSKeith M Wesolowski 		fp->bf_size = (size_t)propval;
175*1d9cde1dSKeith M Wesolowski 		fp->bf_ino = i;
176*1d9cde1dSKeith M Wesolowski 
177*1d9cde1dSKeith M Wesolowski 		fp->bf_next = head;
178*1d9cde1dSKeith M Wesolowski 		head = fp;
179*1d9cde1dSKeith M Wesolowski 	}
180*1d9cde1dSKeith M Wesolowski 
181*1d9cde1dSKeith M Wesolowski 	return (0);
182*1d9cde1dSKeith M Wesolowski }
183*1d9cde1dSKeith M Wesolowski 
184*1d9cde1dSKeith M Wesolowski /*ARGSUSED*/
185*1d9cde1dSKeith M Wesolowski static int
bbootfs_open(char * fn,int flags)186*1d9cde1dSKeith M Wesolowski bbootfs_open(char *fn, int flags)
187*1d9cde1dSKeith M Wesolowski {
188*1d9cde1dSKeith M Wesolowski 	uint_t i;
189*1d9cde1dSKeith M Wesolowski 	bfile_t *fp;
190*1d9cde1dSKeith M Wesolowski 
191*1d9cde1dSKeith M Wesolowski 	if (!init_done) {
192*1d9cde1dSKeith M Wesolowski 		if (bbootfs_init() != 0)
193*1d9cde1dSKeith M Wesolowski 			return (-1);
194*1d9cde1dSKeith M Wesolowski 
195*1d9cde1dSKeith M Wesolowski 		init_done = 1;
196*1d9cde1dSKeith M Wesolowski 	}
197*1d9cde1dSKeith M Wesolowski 
198*1d9cde1dSKeith M Wesolowski 	canonicalise(fn, cpath);
199*1d9cde1dSKeith M Wesolowski 
200*1d9cde1dSKeith M Wesolowski 	for (fp = head; fp != NULL; fp = fp->bf_next) {
201*1d9cde1dSKeith M Wesolowski 		if (strcmp(fp->bf_name, cpath) == 0)
202*1d9cde1dSKeith M Wesolowski 			break;
203*1d9cde1dSKeith M Wesolowski 	}
204*1d9cde1dSKeith M Wesolowski 
205*1d9cde1dSKeith M Wesolowski 	if (fp == NULL)
206*1d9cde1dSKeith M Wesolowski 		return (-1);
207*1d9cde1dSKeith M Wesolowski 
208*1d9cde1dSKeith M Wesolowski 	for (i = 0; i < MAX_FDS; i++) {
209*1d9cde1dSKeith M Wesolowski 		if (fds[i].fd_file == NULL) {
210*1d9cde1dSKeith M Wesolowski 			fds[i].fd_file = fp;
211*1d9cde1dSKeith M Wesolowski 			fds[i].fd_pos = 0;
212*1d9cde1dSKeith M Wesolowski 			return (i);
213*1d9cde1dSKeith M Wesolowski 		}
214*1d9cde1dSKeith M Wesolowski 	}
215*1d9cde1dSKeith M Wesolowski 
216*1d9cde1dSKeith M Wesolowski 	return (-1);
217*1d9cde1dSKeith M Wesolowski }
218*1d9cde1dSKeith M Wesolowski 
219*1d9cde1dSKeith M Wesolowski static int
bbootfs_close(int fd)220*1d9cde1dSKeith M Wesolowski bbootfs_close(int fd)
221*1d9cde1dSKeith M Wesolowski {
222*1d9cde1dSKeith M Wesolowski 	if (fds[fd].fd_file == NULL)
223*1d9cde1dSKeith M Wesolowski 		return (-1);
224*1d9cde1dSKeith M Wesolowski 
225*1d9cde1dSKeith M Wesolowski 	fds[fd].fd_file = NULL;
226*1d9cde1dSKeith M Wesolowski 	fds[fd].fd_pos = 0;
227*1d9cde1dSKeith M Wesolowski 
228*1d9cde1dSKeith M Wesolowski 	return (0);
229*1d9cde1dSKeith M Wesolowski }
230*1d9cde1dSKeith M Wesolowski 
231*1d9cde1dSKeith M Wesolowski static ssize_t
bbootfs_read(int fd,caddr_t buf,size_t size)232*1d9cde1dSKeith M Wesolowski bbootfs_read(int fd, caddr_t buf, size_t size)
233*1d9cde1dSKeith M Wesolowski {
234*1d9cde1dSKeith M Wesolowski 	ssize_t len;
235*1d9cde1dSKeith M Wesolowski 	bf_fd_t *fdp = &fds[fd];
236*1d9cde1dSKeith M Wesolowski 
237*1d9cde1dSKeith M Wesolowski 	if (fdp->fd_file == NULL)
238*1d9cde1dSKeith M Wesolowski 		return (-1);
239*1d9cde1dSKeith M Wesolowski 
240*1d9cde1dSKeith M Wesolowski 	if (fdp->fd_pos >= fdp->fd_file->bf_size)
241*1d9cde1dSKeith M Wesolowski 		return (-1);
242*1d9cde1dSKeith M Wesolowski 
243*1d9cde1dSKeith M Wesolowski 	if (fdp->fd_pos + size > fdp->fd_file->bf_size)
244*1d9cde1dSKeith M Wesolowski 		len = fdp->fd_file->bf_size - fdp->fd_pos;
245*1d9cde1dSKeith M Wesolowski 	else
246*1d9cde1dSKeith M Wesolowski 		len = size;
247*1d9cde1dSKeith M Wesolowski 
248*1d9cde1dSKeith M Wesolowski 	bcopy(fdp->fd_file->bf_addr + fdp->fd_pos, buf, len);
249*1d9cde1dSKeith M Wesolowski 
250*1d9cde1dSKeith M Wesolowski 	fdp->fd_pos += len;
251*1d9cde1dSKeith M Wesolowski 
252*1d9cde1dSKeith M Wesolowski 	return (len);
253*1d9cde1dSKeith M Wesolowski }
254*1d9cde1dSKeith M Wesolowski 
255*1d9cde1dSKeith M Wesolowski static off_t
bbootfs_lseek(int fd,off_t addr,int whence)256*1d9cde1dSKeith M Wesolowski bbootfs_lseek(int fd, off_t addr, int whence)
257*1d9cde1dSKeith M Wesolowski {
258*1d9cde1dSKeith M Wesolowski 	bf_fd_t *fdp = &fds[fd];
259*1d9cde1dSKeith M Wesolowski 
260*1d9cde1dSKeith M Wesolowski 	if (fdp->fd_file == NULL)
261*1d9cde1dSKeith M Wesolowski 		return (-1);
262*1d9cde1dSKeith M Wesolowski 
263*1d9cde1dSKeith M Wesolowski 	switch (whence) {
264*1d9cde1dSKeith M Wesolowski 	case SEEK_CUR:
265*1d9cde1dSKeith M Wesolowski 		fdp->fd_pos += addr;
266*1d9cde1dSKeith M Wesolowski 		break;
267*1d9cde1dSKeith M Wesolowski 	case SEEK_SET:
268*1d9cde1dSKeith M Wesolowski 		fdp->fd_pos = addr;
269*1d9cde1dSKeith M Wesolowski 		break;
270*1d9cde1dSKeith M Wesolowski 	case SEEK_END:
271*1d9cde1dSKeith M Wesolowski 		fdp->fd_pos = fdp->fd_file->bf_size;
272*1d9cde1dSKeith M Wesolowski 		break;
273*1d9cde1dSKeith M Wesolowski 	default:
274*1d9cde1dSKeith M Wesolowski 		return (-1);
275*1d9cde1dSKeith M Wesolowski 	}
276*1d9cde1dSKeith M Wesolowski 
277*1d9cde1dSKeith M Wesolowski 	return (0);
278*1d9cde1dSKeith M Wesolowski }
279*1d9cde1dSKeith M Wesolowski 
280*1d9cde1dSKeith M Wesolowski static int
bbootfs_fstat(int fd,struct bootstat * bsp)281*1d9cde1dSKeith M Wesolowski bbootfs_fstat(int fd, struct bootstat *bsp)
282*1d9cde1dSKeith M Wesolowski {
283*1d9cde1dSKeith M Wesolowski 	bf_fd_t *fdp = &fds[fd];
284*1d9cde1dSKeith M Wesolowski 
285*1d9cde1dSKeith M Wesolowski 	if (fdp->fd_file == NULL)
286*1d9cde1dSKeith M Wesolowski 		return (-1);
287*1d9cde1dSKeith M Wesolowski 
288*1d9cde1dSKeith M Wesolowski 	bsp->st_dev = 1;
289*1d9cde1dSKeith M Wesolowski 	bsp->st_ino = fdp->fd_file->bf_ino;
290*1d9cde1dSKeith M Wesolowski 	bsp->st_mode = 0444;
291*1d9cde1dSKeith M Wesolowski 	bsp->st_nlink = 1;
292*1d9cde1dSKeith M Wesolowski 	bsp->st_uid = bsp->st_gid = 0;
293*1d9cde1dSKeith M Wesolowski 	bsp->st_rdev = 0;
294*1d9cde1dSKeith M Wesolowski 	bsp->st_size = fdp->fd_file->bf_size;
295*1d9cde1dSKeith M Wesolowski 	bsp->st_blksize = 1;
296*1d9cde1dSKeith M Wesolowski 	bsp->st_blocks = fdp->fd_file->bf_size;
297*1d9cde1dSKeith M Wesolowski 	(void) strcpy(bsp->st_fstype, "bootfs");
298*1d9cde1dSKeith M Wesolowski 
299*1d9cde1dSKeith M Wesolowski 	return (0);
300*1d9cde1dSKeith M Wesolowski }
301*1d9cde1dSKeith M Wesolowski 
302*1d9cde1dSKeith M Wesolowski /* ARGSUSED */
303*1d9cde1dSKeith M Wesolowski static void
bbootfs_closeall(int flag)304*1d9cde1dSKeith M Wesolowski bbootfs_closeall(int flag)
305*1d9cde1dSKeith M Wesolowski {
306*1d9cde1dSKeith M Wesolowski 	bfile_t *fp;
307*1d9cde1dSKeith M Wesolowski 
308*1d9cde1dSKeith M Wesolowski 	while (head != NULL) {
309*1d9cde1dSKeith M Wesolowski 		fp = head;
310*1d9cde1dSKeith M Wesolowski 		head = head->bf_next;
311*1d9cde1dSKeith M Wesolowski 
312*1d9cde1dSKeith M Wesolowski 		bkmem_free(fp, sizeof (bfile_t));
313*1d9cde1dSKeith M Wesolowski 	}
314*1d9cde1dSKeith M Wesolowski 
315*1d9cde1dSKeith M Wesolowski 	init_done = 0;
316*1d9cde1dSKeith M Wesolowski }
317*1d9cde1dSKeith M Wesolowski 
318*1d9cde1dSKeith M Wesolowski struct boot_fs_ops bbootfs_ops = {
319*1d9cde1dSKeith M Wesolowski 	"bootfs",
320*1d9cde1dSKeith M Wesolowski 	bbootfs_mountroot,
321*1d9cde1dSKeith M Wesolowski 	bbootfs_unmountroot,
322*1d9cde1dSKeith M Wesolowski 	bbootfs_open,
323*1d9cde1dSKeith M Wesolowski 	bbootfs_close,
324*1d9cde1dSKeith M Wesolowski 	bbootfs_read,
325*1d9cde1dSKeith M Wesolowski 	bbootfs_lseek,
326*1d9cde1dSKeith M Wesolowski 	bbootfs_fstat,
327*1d9cde1dSKeith M Wesolowski 	bbootfs_closeall,
328*1d9cde1dSKeith M Wesolowski 	NULL
329*1d9cde1dSKeith M Wesolowski };
330