xref: /inferno-os/os/port/devroot.c (revision 74a4d8c26dd3c1e9febcb717cfd6cb6512991a7a)
1*74a4d8c2SCharles.Forsyth #include	"u.h"
2*74a4d8c2SCharles.Forsyth #include	"../port/lib.h"
3*74a4d8c2SCharles.Forsyth #include	"mem.h"
4*74a4d8c2SCharles.Forsyth #include	"dat.h"
5*74a4d8c2SCharles.Forsyth #include	"fns.h"
6*74a4d8c2SCharles.Forsyth #include	"../port/error.h"
7*74a4d8c2SCharles.Forsyth 
8*74a4d8c2SCharles.Forsyth extern Rootdata rootdata[];
9*74a4d8c2SCharles.Forsyth extern Dirtab roottab[];
10*74a4d8c2SCharles.Forsyth extern int	rootmaxq;
11*74a4d8c2SCharles.Forsyth 
12*74a4d8c2SCharles.Forsyth static Chan*
rootattach(char * spec)13*74a4d8c2SCharles.Forsyth rootattach(char *spec)
14*74a4d8c2SCharles.Forsyth {
15*74a4d8c2SCharles.Forsyth 	int i;
16*74a4d8c2SCharles.Forsyth 	ulong len;
17*74a4d8c2SCharles.Forsyth 	Rootdata *r;
18*74a4d8c2SCharles.Forsyth 
19*74a4d8c2SCharles.Forsyth 	if(*spec)
20*74a4d8c2SCharles.Forsyth 		error(Ebadspec);
21*74a4d8c2SCharles.Forsyth 	for (i = 0; i < rootmaxq; i++){
22*74a4d8c2SCharles.Forsyth 		r = &rootdata[i];
23*74a4d8c2SCharles.Forsyth 		if (r->sizep){
24*74a4d8c2SCharles.Forsyth 			len = *r->sizep;
25*74a4d8c2SCharles.Forsyth 			r->size = len;
26*74a4d8c2SCharles.Forsyth 			roottab[i].length = len;
27*74a4d8c2SCharles.Forsyth 		}
28*74a4d8c2SCharles.Forsyth 	}
29*74a4d8c2SCharles.Forsyth 	return devattach('/', spec);
30*74a4d8c2SCharles.Forsyth }
31*74a4d8c2SCharles.Forsyth 
32*74a4d8c2SCharles.Forsyth static int
rootgen(Chan * c,char * name,Dirtab * tab,int nd,int s,Dir * dp)33*74a4d8c2SCharles.Forsyth rootgen(Chan *c, char *name, Dirtab *tab, int nd, int s, Dir *dp)
34*74a4d8c2SCharles.Forsyth {
35*74a4d8c2SCharles.Forsyth 	int p, i;
36*74a4d8c2SCharles.Forsyth 	Rootdata *r;
37*74a4d8c2SCharles.Forsyth 
38*74a4d8c2SCharles.Forsyth 	if(s == DEVDOTDOT){
39*74a4d8c2SCharles.Forsyth 		p = rootdata[c->qid.path].dotdot;
40*74a4d8c2SCharles.Forsyth 		c->qid.path = p;
41*74a4d8c2SCharles.Forsyth 		c->qid.type = QTDIR;
42*74a4d8c2SCharles.Forsyth 		name = "#/";
43*74a4d8c2SCharles.Forsyth 		if(p != 0){
44*74a4d8c2SCharles.Forsyth 			for(i = 0; i < rootmaxq; i++)
45*74a4d8c2SCharles.Forsyth 				if(roottab[i].qid.path == c->qid.path){
46*74a4d8c2SCharles.Forsyth 					name = roottab[i].name;
47*74a4d8c2SCharles.Forsyth 					break;
48*74a4d8c2SCharles.Forsyth 				}
49*74a4d8c2SCharles.Forsyth 		}
50*74a4d8c2SCharles.Forsyth 		devdir(c, c->qid, name, 0, eve, 0555, dp);
51*74a4d8c2SCharles.Forsyth 		return 1;
52*74a4d8c2SCharles.Forsyth 	}
53*74a4d8c2SCharles.Forsyth 	if(name != nil){
54*74a4d8c2SCharles.Forsyth 		isdir(c);
55*74a4d8c2SCharles.Forsyth 		r = &rootdata[(int)c->qid.path];
56*74a4d8c2SCharles.Forsyth 		tab = r->ptr;
57*74a4d8c2SCharles.Forsyth 		for(i=0; i<r->size; i++, tab++)
58*74a4d8c2SCharles.Forsyth 			if(strcmp(tab->name, name) == 0){
59*74a4d8c2SCharles.Forsyth 				devdir(c, tab->qid, tab->name, tab->length, eve, tab->perm, dp);
60*74a4d8c2SCharles.Forsyth 				return 1;
61*74a4d8c2SCharles.Forsyth 			}
62*74a4d8c2SCharles.Forsyth 		return -1;
63*74a4d8c2SCharles.Forsyth 	}
64*74a4d8c2SCharles.Forsyth 	if(s >= nd)
65*74a4d8c2SCharles.Forsyth 		return -1;
66*74a4d8c2SCharles.Forsyth 	tab += s;
67*74a4d8c2SCharles.Forsyth 	devdir(c, tab->qid, tab->name, tab->length, eve, tab->perm, dp);
68*74a4d8c2SCharles.Forsyth 	return 1;
69*74a4d8c2SCharles.Forsyth }
70*74a4d8c2SCharles.Forsyth 
71*74a4d8c2SCharles.Forsyth static Walkqid*
rootwalk(Chan * c,Chan * nc,char ** name,int nname)72*74a4d8c2SCharles.Forsyth rootwalk(Chan *c, Chan *nc, char **name, int nname)
73*74a4d8c2SCharles.Forsyth {
74*74a4d8c2SCharles.Forsyth 	ulong p;
75*74a4d8c2SCharles.Forsyth 
76*74a4d8c2SCharles.Forsyth 	p = c->qid.path;
77*74a4d8c2SCharles.Forsyth 	if(nname == 0)
78*74a4d8c2SCharles.Forsyth 		p = rootdata[p].dotdot;
79*74a4d8c2SCharles.Forsyth 	return devwalk(c, nc, name, nname, rootdata[p].ptr, rootdata[p].size, rootgen);
80*74a4d8c2SCharles.Forsyth }
81*74a4d8c2SCharles.Forsyth 
82*74a4d8c2SCharles.Forsyth static int
rootstat(Chan * c,uchar * dp,int n)83*74a4d8c2SCharles.Forsyth rootstat(Chan *c, uchar *dp, int n)
84*74a4d8c2SCharles.Forsyth {
85*74a4d8c2SCharles.Forsyth 	int p;
86*74a4d8c2SCharles.Forsyth 
87*74a4d8c2SCharles.Forsyth 	p = rootdata[c->qid.path].dotdot;
88*74a4d8c2SCharles.Forsyth 	return devstat(c, dp, n, rootdata[p].ptr, rootdata[p].size, rootgen);
89*74a4d8c2SCharles.Forsyth }
90*74a4d8c2SCharles.Forsyth 
91*74a4d8c2SCharles.Forsyth static Chan*
rootopen(Chan * c,int omode)92*74a4d8c2SCharles.Forsyth rootopen(Chan *c, int omode)
93*74a4d8c2SCharles.Forsyth {
94*74a4d8c2SCharles.Forsyth 	int p;
95*74a4d8c2SCharles.Forsyth 
96*74a4d8c2SCharles.Forsyth 	p = rootdata[c->qid.path].dotdot;
97*74a4d8c2SCharles.Forsyth 	return devopen(c, omode, rootdata[p].ptr, rootdata[p].size, rootgen);
98*74a4d8c2SCharles.Forsyth }
99*74a4d8c2SCharles.Forsyth 
100*74a4d8c2SCharles.Forsyth /*
101*74a4d8c2SCharles.Forsyth  * sysremove() knows this is a nop
102*74a4d8c2SCharles.Forsyth  */
103*74a4d8c2SCharles.Forsyth static void
rootclose(Chan *)104*74a4d8c2SCharles.Forsyth rootclose(Chan*)
105*74a4d8c2SCharles.Forsyth {
106*74a4d8c2SCharles.Forsyth }
107*74a4d8c2SCharles.Forsyth 
108*74a4d8c2SCharles.Forsyth static long
rootread(Chan * c,void * buf,long n,vlong offset)109*74a4d8c2SCharles.Forsyth rootread(Chan *c, void *buf, long n, vlong offset)
110*74a4d8c2SCharles.Forsyth {
111*74a4d8c2SCharles.Forsyth 	ulong p, len;
112*74a4d8c2SCharles.Forsyth 	uchar *data;
113*74a4d8c2SCharles.Forsyth 
114*74a4d8c2SCharles.Forsyth 	p = c->qid.path;
115*74a4d8c2SCharles.Forsyth 	if(c->qid.type & QTDIR)
116*74a4d8c2SCharles.Forsyth 		return devdirread(c, buf, n, rootdata[p].ptr, rootdata[p].size, rootgen);
117*74a4d8c2SCharles.Forsyth 	len = rootdata[p].size;
118*74a4d8c2SCharles.Forsyth 	if(offset < 0 || offset >= len)
119*74a4d8c2SCharles.Forsyth 		return 0;
120*74a4d8c2SCharles.Forsyth 	if(offset+n > len)
121*74a4d8c2SCharles.Forsyth 		n = len - offset;
122*74a4d8c2SCharles.Forsyth 	data = rootdata[p].ptr;
123*74a4d8c2SCharles.Forsyth 	memmove(buf, data+offset, n);
124*74a4d8c2SCharles.Forsyth 	return n;
125*74a4d8c2SCharles.Forsyth }
126*74a4d8c2SCharles.Forsyth 
127*74a4d8c2SCharles.Forsyth static long
rootwrite(Chan *,void *,long,vlong)128*74a4d8c2SCharles.Forsyth rootwrite(Chan*, void*, long, vlong)
129*74a4d8c2SCharles.Forsyth {
130*74a4d8c2SCharles.Forsyth 	error(Eperm);
131*74a4d8c2SCharles.Forsyth 	return 0;
132*74a4d8c2SCharles.Forsyth }
133*74a4d8c2SCharles.Forsyth 
134*74a4d8c2SCharles.Forsyth Dev rootdevtab = {
135*74a4d8c2SCharles.Forsyth 	'/',
136*74a4d8c2SCharles.Forsyth 	"root",
137*74a4d8c2SCharles.Forsyth 
138*74a4d8c2SCharles.Forsyth 	devreset,
139*74a4d8c2SCharles.Forsyth 	devinit,
140*74a4d8c2SCharles.Forsyth 	devshutdown,
141*74a4d8c2SCharles.Forsyth 	rootattach,
142*74a4d8c2SCharles.Forsyth 	rootwalk,
143*74a4d8c2SCharles.Forsyth 	rootstat,
144*74a4d8c2SCharles.Forsyth 	rootopen,
145*74a4d8c2SCharles.Forsyth 	devcreate,
146*74a4d8c2SCharles.Forsyth 	rootclose,
147*74a4d8c2SCharles.Forsyth 	rootread,
148*74a4d8c2SCharles.Forsyth 	devbread,
149*74a4d8c2SCharles.Forsyth 	rootwrite,
150*74a4d8c2SCharles.Forsyth 	devbwrite,
151*74a4d8c2SCharles.Forsyth 	devremove,
152*74a4d8c2SCharles.Forsyth 	devwstat,
153*74a4d8c2SCharles.Forsyth };
154