Blame


1 7763a61a 2003-11-23 devnull #include "stdinc.h"
2 7763a61a 2003-11-23 devnull #include <auth.h>
3 7763a61a 2003-11-23 devnull #include <fcall.h>
4 7763a61a 2003-11-23 devnull #include "vac.h"
5 7763a61a 2003-11-23 devnull
6 7763a61a 2003-11-23 devnull typedef struct Fid Fid;
7 7763a61a 2003-11-23 devnull typedef struct DirBuf DirBuf;
8 7763a61a 2003-11-23 devnull
9 7763a61a 2003-11-23 devnull enum
10 7763a61a 2003-11-23 devnull {
11 7763a61a 2003-11-23 devnull OPERM = 0x3, /* mask of all permission types in open mode */
12 7763a61a 2003-11-23 devnull };
13 7763a61a 2003-11-23 devnull
14 7763a61a 2003-11-23 devnull enum
15 7763a61a 2003-11-23 devnull {
16 7763a61a 2003-11-23 devnull DirBufSize = 20,
17 7763a61a 2003-11-23 devnull };
18 7763a61a 2003-11-23 devnull
19 7763a61a 2003-11-23 devnull struct Fid
20 7763a61a 2003-11-23 devnull {
21 7763a61a 2003-11-23 devnull short busy;
22 7763a61a 2003-11-23 devnull short open;
23 7763a61a 2003-11-23 devnull int fid;
24 7763a61a 2003-11-23 devnull char *user;
25 7763a61a 2003-11-23 devnull Qid qid;
26 7763a61a 2003-11-23 devnull VacFile *file;
27 7763a61a 2003-11-23 devnull
28 7763a61a 2003-11-23 devnull DirBuf *db;
29 7763a61a 2003-11-23 devnull
30 7763a61a 2003-11-23 devnull Fid *next;
31 7763a61a 2003-11-23 devnull };
32 7763a61a 2003-11-23 devnull
33 7763a61a 2003-11-23 devnull struct DirBuf
34 7763a61a 2003-11-23 devnull {
35 7763a61a 2003-11-23 devnull VacDirEnum *vde;
36 7763a61a 2003-11-23 devnull VacDir buf[DirBufSize];
37 7763a61a 2003-11-23 devnull int i, n;
38 7763a61a 2003-11-23 devnull int eof;
39 7763a61a 2003-11-23 devnull };
40 7763a61a 2003-11-23 devnull
41 7763a61a 2003-11-23 devnull enum
42 7763a61a 2003-11-23 devnull {
43 7763a61a 2003-11-23 devnull Pexec = 1,
44 7763a61a 2003-11-23 devnull Pwrite = 2,
45 7763a61a 2003-11-23 devnull Pread = 4,
46 7763a61a 2003-11-23 devnull Pother = 1,
47 7763a61a 2003-11-23 devnull Pgroup = 8,
48 7763a61a 2003-11-23 devnull Powner = 64,
49 7763a61a 2003-11-23 devnull };
50 7763a61a 2003-11-23 devnull
51 7763a61a 2003-11-23 devnull Fid *fids;
52 7763a61a 2003-11-23 devnull uchar *data;
53 7763a61a 2003-11-23 devnull int mfd[2];
54 7763a61a 2003-11-23 devnull char *user;
55 7763a61a 2003-11-23 devnull uchar mdata[8192+IOHDRSZ];
56 7763a61a 2003-11-23 devnull int messagesize = sizeof mdata;
57 7763a61a 2003-11-23 devnull Fcall rhdr;
58 7763a61a 2003-11-23 devnull Fcall thdr;
59 7763a61a 2003-11-23 devnull VacFS *fs;
60 7763a61a 2003-11-23 devnull VtSession *session;
61 7763a61a 2003-11-23 devnull int noperm;
62 7763a61a 2003-11-23 devnull
63 7763a61a 2003-11-23 devnull Fid * newfid(int);
64 7763a61a 2003-11-23 devnull void error(char*);
65 7763a61a 2003-11-23 devnull void io(void);
66 7763a61a 2003-11-23 devnull void shutdown(void);
67 7763a61a 2003-11-23 devnull void usage(void);
68 7763a61a 2003-11-23 devnull int perm(Fid*, int);
69 7763a61a 2003-11-23 devnull int permf(VacFile*, char*, int);
70 7763a61a 2003-11-23 devnull ulong getl(void *p);
71 7763a61a 2003-11-23 devnull void init(char*, char*, long, int);
72 7763a61a 2003-11-23 devnull DirBuf *dirBufAlloc(VacFile*);
73 7763a61a 2003-11-23 devnull VacDir *dirBufGet(DirBuf*);
74 7763a61a 2003-11-23 devnull int dirBufUnget(DirBuf*);
75 7763a61a 2003-11-23 devnull void dirBufFree(DirBuf*);
76 7763a61a 2003-11-23 devnull int vacdirread(Fid *f, char *p, long off, long cnt);
77 7763a61a 2003-11-23 devnull int vdStat(VacDir *vd, uchar *p, int np);
78 7763a61a 2003-11-23 devnull
79 7763a61a 2003-11-23 devnull char *rflush(Fid*), *rversion(Fid*),
80 7763a61a 2003-11-23 devnull *rauth(Fid*), *rattach(Fid*), *rwalk(Fid*),
81 7763a61a 2003-11-23 devnull *ropen(Fid*), *rcreate(Fid*),
82 7763a61a 2003-11-23 devnull *rread(Fid*), *rwrite(Fid*), *rclunk(Fid*),
83 7763a61a 2003-11-23 devnull *rremove(Fid*), *rstat(Fid*), *rwstat(Fid*);
84 7763a61a 2003-11-23 devnull
85 7763a61a 2003-11-23 devnull char *(*fcalls[])(Fid*) = {
86 7763a61a 2003-11-23 devnull [Tflush] rflush,
87 7763a61a 2003-11-23 devnull [Tversion] rversion,
88 7763a61a 2003-11-23 devnull [Tattach] rattach,
89 7763a61a 2003-11-23 devnull [Tauth] rauth,
90 7763a61a 2003-11-23 devnull [Twalk] rwalk,
91 7763a61a 2003-11-23 devnull [Topen] ropen,
92 7763a61a 2003-11-23 devnull [Tcreate] rcreate,
93 7763a61a 2003-11-23 devnull [Tread] rread,
94 7763a61a 2003-11-23 devnull [Twrite] rwrite,
95 7763a61a 2003-11-23 devnull [Tclunk] rclunk,
96 7763a61a 2003-11-23 devnull [Tremove] rremove,
97 7763a61a 2003-11-23 devnull [Tstat] rstat,
98 7763a61a 2003-11-23 devnull [Twstat] rwstat,
99 7763a61a 2003-11-23 devnull };
100 7763a61a 2003-11-23 devnull
101 7763a61a 2003-11-23 devnull char Eperm[] = "permission denied";
102 7763a61a 2003-11-23 devnull char Enotdir[] = "not a directory";
103 7763a61a 2003-11-23 devnull char Enotexist[] = "file does not exist";
104 7763a61a 2003-11-23 devnull char Einuse[] = "file in use";
105 7763a61a 2003-11-23 devnull char Eexist[] = "file exists";
106 7763a61a 2003-11-23 devnull char Enotowner[] = "not owner";
107 7763a61a 2003-11-23 devnull char Eisopen[] = "file already open for I/O";
108 7763a61a 2003-11-23 devnull char Excl[] = "exclusive use file already open";
109 7763a61a 2003-11-23 devnull char Ename[] = "illegal name";
110 7763a61a 2003-11-23 devnull char Erdonly[] = "read only file system";
111 7763a61a 2003-11-23 devnull char Eio[] = "i/o error";
112 7763a61a 2003-11-23 devnull char Eempty[] = "directory is not empty";
113 7763a61a 2003-11-23 devnull char Emode[] = "illegal mode";
114 7763a61a 2003-11-23 devnull
115 7763a61a 2003-11-23 devnull int dflag;
116 7763a61a 2003-11-23 devnull
117 7763a61a 2003-11-23 devnull void
118 7763a61a 2003-11-23 devnull notifyf(void *a, char *s)
119 7763a61a 2003-11-23 devnull {
120 7763a61a 2003-11-23 devnull USED(a);
121 7763a61a 2003-11-23 devnull if(strncmp(s, "interrupt", 9) == 0)
122 7763a61a 2003-11-23 devnull noted(NCONT);
123 7763a61a 2003-11-23 devnull noted(NDFLT);
124 7763a61a 2003-11-23 devnull }
125 7763a61a 2003-11-23 devnull
126 7763a61a 2003-11-23 devnull void
127 7763a61a 2003-11-23 devnull main(int argc, char *argv[])
128 7763a61a 2003-11-23 devnull {
129 7763a61a 2003-11-23 devnull char *defmnt;
130 7763a61a 2003-11-23 devnull int p[2];
131 7763a61a 2003-11-23 devnull char buf[12];
132 7763a61a 2003-11-23 devnull int fd;
133 7763a61a 2003-11-23 devnull int stdio = 0;
134 7763a61a 2003-11-23 devnull char *host = nil;
135 7763a61a 2003-11-23 devnull long ncache = 1000;
136 7763a61a 2003-11-23 devnull int readOnly = 1;
137 7763a61a 2003-11-23 devnull
138 7763a61a 2003-11-23 devnull defmnt = "/n/vac";
139 7763a61a 2003-11-23 devnull ARGBEGIN{
140 7763a61a 2003-11-23 devnull case 'd':
141 7763a61a 2003-11-23 devnull fmtinstall('F', fcallfmt);
142 7763a61a 2003-11-23 devnull dflag = 1;
143 7763a61a 2003-11-23 devnull break;
144 7763a61a 2003-11-23 devnull case 'c':
145 7763a61a 2003-11-23 devnull ncache = atoi(ARGF());
146 7763a61a 2003-11-23 devnull break;
147 7763a61a 2003-11-23 devnull case 'i':
148 7763a61a 2003-11-23 devnull defmnt = 0;
149 7763a61a 2003-11-23 devnull stdio = 1;
150 7763a61a 2003-11-23 devnull mfd[0] = 0;
151 7763a61a 2003-11-23 devnull mfd[1] = 1;
152 7763a61a 2003-11-23 devnull break;
153 7763a61a 2003-11-23 devnull case 'h':
154 7763a61a 2003-11-23 devnull host = ARGF();
155 7763a61a 2003-11-23 devnull break;
156 7763a61a 2003-11-23 devnull case 's':
157 7763a61a 2003-11-23 devnull defmnt = 0;
158 7763a61a 2003-11-23 devnull break;
159 7763a61a 2003-11-23 devnull case 'p':
160 7763a61a 2003-11-23 devnull noperm = 1;
161 7763a61a 2003-11-23 devnull break;
162 7763a61a 2003-11-23 devnull case 'm':
163 7763a61a 2003-11-23 devnull defmnt = ARGF();
164 7763a61a 2003-11-23 devnull break;
165 7763a61a 2003-11-23 devnull default:
166 7763a61a 2003-11-23 devnull usage();
167 7763a61a 2003-11-23 devnull }ARGEND
168 7763a61a 2003-11-23 devnull
169 7763a61a 2003-11-23 devnull if(argc != 1)
170 7763a61a 2003-11-23 devnull usage();
171 7763a61a 2003-11-23 devnull
172 7763a61a 2003-11-23 devnull vtAttach();
173 7763a61a 2003-11-23 devnull
174 7763a61a 2003-11-23 devnull init(argv[0], host, ncache, readOnly);
175 7763a61a 2003-11-23 devnull
176 7763a61a 2003-11-23 devnull if(pipe(p) < 0)
177 7763a61a 2003-11-23 devnull sysfatal("pipe failed: %r");
178 7763a61a 2003-11-23 devnull if(!stdio){
179 7763a61a 2003-11-23 devnull mfd[0] = p[0];
180 7763a61a 2003-11-23 devnull mfd[1] = p[0];
181 7763a61a 2003-11-23 devnull if(defmnt == 0){
182 7763a61a 2003-11-23 devnull fd = create("#s/vacfs", OWRITE, 0666);
183 7763a61a 2003-11-23 devnull if(fd < 0)
184 7763a61a 2003-11-23 devnull sysfatal("create of /srv/vacfs failed: %r");
185 7763a61a 2003-11-23 devnull sprint(buf, "%d", p[1]);
186 7763a61a 2003-11-23 devnull if(write(fd, buf, strlen(buf)) < 0)
187 7763a61a 2003-11-23 devnull sysfatal("writing /srv/vacfs: %r");
188 7763a61a 2003-11-23 devnull }
189 7763a61a 2003-11-23 devnull }
190 7763a61a 2003-11-23 devnull
191 7763a61a 2003-11-23 devnull switch(rfork(RFFDG|RFPROC|RFNAMEG|RFNOTEG)){
192 7763a61a 2003-11-23 devnull case -1:
193 7763a61a 2003-11-23 devnull sysfatal("fork: %r");
194 7763a61a 2003-11-23 devnull case 0:
195 7763a61a 2003-11-23 devnull vtAttach();
196 7763a61a 2003-11-23 devnull close(p[1]);
197 7763a61a 2003-11-23 devnull io();
198 7763a61a 2003-11-23 devnull shutdown();
199 7763a61a 2003-11-23 devnull break;
200 7763a61a 2003-11-23 devnull default:
201 7763a61a 2003-11-23 devnull close(p[0]); /* don't deadlock if child fails */
202 7763a61a 2003-11-23 devnull if(defmnt && mount(p[1], -1, defmnt, MREPL|MCREATE, "") < 0)
203 7763a61a 2003-11-23 devnull sysfatal("mount failed: %r");
204 7763a61a 2003-11-23 devnull }
205 7763a61a 2003-11-23 devnull vtDetach();
206 7763a61a 2003-11-23 devnull exits(0);
207 7763a61a 2003-11-23 devnull }
208 7763a61a 2003-11-23 devnull
209 7763a61a 2003-11-23 devnull void
210 7763a61a 2003-11-23 devnull usage(void)
211 7763a61a 2003-11-23 devnull {
212 7763a61a 2003-11-23 devnull fprint(2, "usage: %s [-sd] [-h host] [-c ncache] [-m mountpoint] vacfile\n", argv0);
213 7763a61a 2003-11-23 devnull exits("usage");
214 7763a61a 2003-11-23 devnull }
215 7763a61a 2003-11-23 devnull
216 7763a61a 2003-11-23 devnull char*
217 7763a61a 2003-11-23 devnull rversion(Fid *unused)
218 7763a61a 2003-11-23 devnull {
219 7763a61a 2003-11-23 devnull Fid *f;
220 7763a61a 2003-11-23 devnull
221 7763a61a 2003-11-23 devnull USED(unused);
222 7763a61a 2003-11-23 devnull
223 7763a61a 2003-11-23 devnull for(f = fids; f; f = f->next)
224 7763a61a 2003-11-23 devnull if(f->busy)
225 7763a61a 2003-11-23 devnull rclunk(f);
226 7763a61a 2003-11-23 devnull
227 7763a61a 2003-11-23 devnull if(rhdr.msize < 256)
228 7763a61a 2003-11-23 devnull return "version: message size too small";
229 7763a61a 2003-11-23 devnull messagesize = rhdr.msize;
230 7763a61a 2003-11-23 devnull if(messagesize > sizeof mdata)
231 7763a61a 2003-11-23 devnull messagesize = sizeof mdata;
232 7763a61a 2003-11-23 devnull thdr.msize = messagesize;
233 7763a61a 2003-11-23 devnull if(strncmp(rhdr.version, "9P2000", 6) != 0)
234 7763a61a 2003-11-23 devnull return "unrecognized 9P version";
235 7763a61a 2003-11-23 devnull thdr.version = "9P2000";
236 7763a61a 2003-11-23 devnull return nil;
237 7763a61a 2003-11-23 devnull }
238 7763a61a 2003-11-23 devnull
239 7763a61a 2003-11-23 devnull char*
240 7763a61a 2003-11-23 devnull rflush(Fid *f)
241 7763a61a 2003-11-23 devnull {
242 7763a61a 2003-11-23 devnull USED(f);
243 7763a61a 2003-11-23 devnull return 0;
244 7763a61a 2003-11-23 devnull }
245 7763a61a 2003-11-23 devnull
246 7763a61a 2003-11-23 devnull char*
247 7763a61a 2003-11-23 devnull rauth(Fid *f)
248 7763a61a 2003-11-23 devnull {
249 7763a61a 2003-11-23 devnull USED(f);
250 7763a61a 2003-11-23 devnull return "vacfs: authentication not required";
251 7763a61a 2003-11-23 devnull }
252 7763a61a 2003-11-23 devnull
253 7763a61a 2003-11-23 devnull char*
254 7763a61a 2003-11-23 devnull rattach(Fid *f)
255 7763a61a 2003-11-23 devnull {
256 7763a61a 2003-11-23 devnull /* no authentication for the momment */
257 7763a61a 2003-11-23 devnull VacFile *file;
258 7763a61a 2003-11-23 devnull
259 7763a61a 2003-11-23 devnull file = vfsGetRoot(fs);
260 7763a61a 2003-11-23 devnull if(file == nil)
261 7763a61a 2003-11-23 devnull return vtGetError();
262 7763a61a 2003-11-23 devnull f->busy = 1;
263 7763a61a 2003-11-23 devnull f->file = file;
264 7763a61a 2003-11-23 devnull f->qid = (Qid){vfGetId(f->file), 0, QTDIR};
265 7763a61a 2003-11-23 devnull thdr.qid = f->qid;
266 7763a61a 2003-11-23 devnull if(rhdr.uname[0])
267 7763a61a 2003-11-23 devnull f->user = vtStrDup(rhdr.uname);
268 7763a61a 2003-11-23 devnull else
269 7763a61a 2003-11-23 devnull f->user = "none";
270 7763a61a 2003-11-23 devnull return 0;
271 7763a61a 2003-11-23 devnull }
272 7763a61a 2003-11-23 devnull
273 7763a61a 2003-11-23 devnull VacFile*
274 7763a61a 2003-11-23 devnull _vfWalk(VacFile *file, char *name)
275 7763a61a 2003-11-23 devnull {
276 7763a61a 2003-11-23 devnull VacFile *n;
277 7763a61a 2003-11-23 devnull
278 7763a61a 2003-11-23 devnull n = vfWalk(file, name);
279 7763a61a 2003-11-23 devnull if(n)
280 7763a61a 2003-11-23 devnull return n;
281 7763a61a 2003-11-23 devnull if(strcmp(name, "SLASH") == 0)
282 7763a61a 2003-11-23 devnull return vfWalk(file, "/");
283 7763a61a 2003-11-23 devnull return nil;
284 7763a61a 2003-11-23 devnull }
285 7763a61a 2003-11-23 devnull
286 7763a61a 2003-11-23 devnull char*
287 7763a61a 2003-11-23 devnull rwalk(Fid *f)
288 7763a61a 2003-11-23 devnull {
289 7763a61a 2003-11-23 devnull VacFile *file, *nfile;
290 7763a61a 2003-11-23 devnull Fid *nf;
291 7763a61a 2003-11-23 devnull int nqid, nwname;
292 7763a61a 2003-11-23 devnull Qid qid;
293 7763a61a 2003-11-23 devnull
294 7763a61a 2003-11-23 devnull if(f->busy == 0)
295 7763a61a 2003-11-23 devnull return Enotexist;
296 7763a61a 2003-11-23 devnull nf = nil;
297 7763a61a 2003-11-23 devnull if(rhdr.fid != rhdr.newfid){
298 7763a61a 2003-11-23 devnull if(f->open)
299 7763a61a 2003-11-23 devnull return Eisopen;
300 7763a61a 2003-11-23 devnull if(f->busy == 0)
301 7763a61a 2003-11-23 devnull return Enotexist;
302 7763a61a 2003-11-23 devnull nf = newfid(rhdr.newfid);
303 7763a61a 2003-11-23 devnull if(nf->busy)
304 7763a61a 2003-11-23 devnull return Eisopen;
305 7763a61a 2003-11-23 devnull nf->busy = 1;
306 7763a61a 2003-11-23 devnull nf->open = 0;
307 7763a61a 2003-11-23 devnull nf->qid = f->qid;
308 7763a61a 2003-11-23 devnull nf->file = vfIncRef(f->file);
309 7763a61a 2003-11-23 devnull nf->user = vtStrDup(f->user);
310 7763a61a 2003-11-23 devnull f = nf;
311 7763a61a 2003-11-23 devnull }
312 7763a61a 2003-11-23 devnull
313 7763a61a 2003-11-23 devnull nwname = rhdr.nwname;
314 7763a61a 2003-11-23 devnull
315 7763a61a 2003-11-23 devnull /* easy case */
316 7763a61a 2003-11-23 devnull if(nwname == 0) {
317 7763a61a 2003-11-23 devnull thdr.nwqid = 0;
318 7763a61a 2003-11-23 devnull return 0;
319 7763a61a 2003-11-23 devnull }
320 7763a61a 2003-11-23 devnull
321 7763a61a 2003-11-23 devnull file = f->file;
322 7763a61a 2003-11-23 devnull vfIncRef(file);
323 7763a61a 2003-11-23 devnull qid = f->qid;
324 7763a61a 2003-11-23 devnull
325 7763a61a 2003-11-23 devnull for(nqid = 0; nqid < nwname; nqid++){
326 7763a61a 2003-11-23 devnull if((qid.type & QTDIR) == 0){
327 7763a61a 2003-11-23 devnull vtSetError(Enotdir);
328 7763a61a 2003-11-23 devnull break;
329 7763a61a 2003-11-23 devnull }
330 7763a61a 2003-11-23 devnull if(!permf(file, f->user, Pexec)) {
331 7763a61a 2003-11-23 devnull vtSetError(Eperm);
332 7763a61a 2003-11-23 devnull break;
333 7763a61a 2003-11-23 devnull }
334 7763a61a 2003-11-23 devnull nfile = _vfWalk(file, rhdr.wname[nqid]);
335 7763a61a 2003-11-23 devnull if(nfile == nil)
336 7763a61a 2003-11-23 devnull break;
337 7763a61a 2003-11-23 devnull vfDecRef(file);
338 7763a61a 2003-11-23 devnull file = nfile;
339 7763a61a 2003-11-23 devnull qid.type = QTFILE;
340 7763a61a 2003-11-23 devnull if(vfIsDir(file))
341 7763a61a 2003-11-23 devnull qid.type = QTDIR;
342 7763a61a 2003-11-23 devnull qid.vers = vfGetMcount(file);
343 7763a61a 2003-11-23 devnull qid.path = vfGetId(file);
344 7763a61a 2003-11-23 devnull thdr.wqid[nqid] = qid;
345 7763a61a 2003-11-23 devnull }
346 7763a61a 2003-11-23 devnull
347 7763a61a 2003-11-23 devnull thdr.nwqid = nqid;
348 7763a61a 2003-11-23 devnull
349 7763a61a 2003-11-23 devnull if(nqid == nwname){
350 7763a61a 2003-11-23 devnull /* success */
351 7763a61a 2003-11-23 devnull f->qid = thdr.wqid[nqid-1];
352 7763a61a 2003-11-23 devnull vfDecRef(f->file);
353 7763a61a 2003-11-23 devnull f->file = file;
354 7763a61a 2003-11-23 devnull return 0;
355 7763a61a 2003-11-23 devnull }
356 7763a61a 2003-11-23 devnull
357 7763a61a 2003-11-23 devnull vfDecRef(file);
358 7763a61a 2003-11-23 devnull if(nf != nil)
359 7763a61a 2003-11-23 devnull rclunk(nf);
360 7763a61a 2003-11-23 devnull
361 7763a61a 2003-11-23 devnull /* only error on the first element */
362 7763a61a 2003-11-23 devnull if(nqid == 0)
363 7763a61a 2003-11-23 devnull return vtGetError();
364 7763a61a 2003-11-23 devnull
365 7763a61a 2003-11-23 devnull return 0;
366 7763a61a 2003-11-23 devnull }
367 7763a61a 2003-11-23 devnull
368 7763a61a 2003-11-23 devnull char *
369 7763a61a 2003-11-23 devnull ropen(Fid *f)
370 7763a61a 2003-11-23 devnull {
371 7763a61a 2003-11-23 devnull int mode, trunc;
372 7763a61a 2003-11-23 devnull
373 7763a61a 2003-11-23 devnull if(f->open)
374 7763a61a 2003-11-23 devnull return Eisopen;
375 7763a61a 2003-11-23 devnull if(!f->busy)
376 7763a61a 2003-11-23 devnull return Enotexist;
377 7763a61a 2003-11-23 devnull mode = rhdr.mode;
378 7763a61a 2003-11-23 devnull thdr.iounit = messagesize - IOHDRSZ;
379 7763a61a 2003-11-23 devnull if(f->qid.type & QTDIR){
380 7763a61a 2003-11-23 devnull if(mode != OREAD)
381 7763a61a 2003-11-23 devnull return Eperm;
382 7763a61a 2003-11-23 devnull if(!perm(f, Pread))
383 7763a61a 2003-11-23 devnull return Eperm;
384 7763a61a 2003-11-23 devnull thdr.qid = f->qid;
385 7763a61a 2003-11-23 devnull f->db = nil;
386 7763a61a 2003-11-23 devnull f->open = 1;
387 7763a61a 2003-11-23 devnull return 0;
388 7763a61a 2003-11-23 devnull }
389 7763a61a 2003-11-23 devnull if(mode & ORCLOSE)
390 7763a61a 2003-11-23 devnull return Erdonly;
391 7763a61a 2003-11-23 devnull trunc = mode & OTRUNC;
392 7763a61a 2003-11-23 devnull mode &= OPERM;
393 7763a61a 2003-11-23 devnull if(mode==OWRITE || mode==ORDWR || trunc)
394 7763a61a 2003-11-23 devnull if(!perm(f, Pwrite))
395 7763a61a 2003-11-23 devnull return Eperm;
396 7763a61a 2003-11-23 devnull if(mode==OREAD || mode==ORDWR)
397 7763a61a 2003-11-23 devnull if(!perm(f, Pread))
398 7763a61a 2003-11-23 devnull return Eperm;
399 7763a61a 2003-11-23 devnull if(mode==OEXEC)
400 7763a61a 2003-11-23 devnull if(!perm(f, Pexec))
401 7763a61a 2003-11-23 devnull return Eperm;
402 7763a61a 2003-11-23 devnull thdr.qid = f->qid;
403 7763a61a 2003-11-23 devnull thdr.iounit = messagesize - IOHDRSZ;
404 7763a61a 2003-11-23 devnull f->open = 1;
405 7763a61a 2003-11-23 devnull return 0;
406 7763a61a 2003-11-23 devnull }
407 7763a61a 2003-11-23 devnull
408 7763a61a 2003-11-23 devnull char*
409 7763a61a 2003-11-23 devnull rcreate(Fid* fid)
410 7763a61a 2003-11-23 devnull {
411 7763a61a 2003-11-23 devnull VacFile *vf;
412 7763a61a 2003-11-23 devnull ulong mode;
413 7763a61a 2003-11-23 devnull
414 7763a61a 2003-11-23 devnull if(fid->open)
415 7763a61a 2003-11-23 devnull return Eisopen;
416 7763a61a 2003-11-23 devnull if(!fid->busy)
417 7763a61a 2003-11-23 devnull return Enotexist;
418 7763a61a 2003-11-23 devnull if(vfsIsReadOnly(fs))
419 7763a61a 2003-11-23 devnull return Erdonly;
420 7763a61a 2003-11-23 devnull vf = fid->file;
421 7763a61a 2003-11-23 devnull if(!vfIsDir(vf))
422 7763a61a 2003-11-23 devnull return Enotdir;
423 7763a61a 2003-11-23 devnull if(!permf(vf, fid->user, Pwrite))
424 7763a61a 2003-11-23 devnull return Eperm;
425 7763a61a 2003-11-23 devnull
426 7763a61a 2003-11-23 devnull mode = rhdr.perm & 0777;
427 7763a61a 2003-11-23 devnull
428 7763a61a 2003-11-23 devnull if(rhdr.perm & DMDIR){
429 7763a61a 2003-11-23 devnull if((rhdr.mode & OTRUNC) || (rhdr.perm & DMAPPEND))
430 7763a61a 2003-11-23 devnull return Emode;
431 7763a61a 2003-11-23 devnull switch(rhdr.mode & OPERM){
432 7763a61a 2003-11-23 devnull default:
433 7763a61a 2003-11-23 devnull return Emode;
434 7763a61a 2003-11-23 devnull case OEXEC:
435 7763a61a 2003-11-23 devnull case OREAD:
436 7763a61a 2003-11-23 devnull break;
437 7763a61a 2003-11-23 devnull case OWRITE:
438 7763a61a 2003-11-23 devnull case ORDWR:
439 7763a61a 2003-11-23 devnull return Eperm;
440 7763a61a 2003-11-23 devnull }
441 7763a61a 2003-11-23 devnull mode |= ModeDir;
442 7763a61a 2003-11-23 devnull }
443 7763a61a 2003-11-23 devnull vf = vfCreate(vf, rhdr.name, mode, "none");
444 7763a61a 2003-11-23 devnull if(vf == nil)
445 7763a61a 2003-11-23 devnull return vtGetError();
446 7763a61a 2003-11-23 devnull vfDecRef(fid->file);
447 7763a61a 2003-11-23 devnull
448 7763a61a 2003-11-23 devnull fid->file = vf;
449 7763a61a 2003-11-23 devnull fid->qid.type = QTFILE;
450 7763a61a 2003-11-23 devnull if(vfIsDir(vf))
451 7763a61a 2003-11-23 devnull fid->qid.type = QTDIR;
452 7763a61a 2003-11-23 devnull fid->qid.vers = vfGetMcount(vf);
453 7763a61a 2003-11-23 devnull fid->qid.path = vfGetId(vf);
454 7763a61a 2003-11-23 devnull
455 7763a61a 2003-11-23 devnull thdr.qid = fid->qid;
456 7763a61a 2003-11-23 devnull thdr.iounit = messagesize - IOHDRSZ;
457 7763a61a 2003-11-23 devnull
458 7763a61a 2003-11-23 devnull return 0;
459 7763a61a 2003-11-23 devnull }
460 7763a61a 2003-11-23 devnull
461 7763a61a 2003-11-23 devnull char*
462 7763a61a 2003-11-23 devnull rread(Fid *f)
463 7763a61a 2003-11-23 devnull {
464 7763a61a 2003-11-23 devnull char *buf;
465 7763a61a 2003-11-23 devnull vlong off;
466 7763a61a 2003-11-23 devnull int cnt;
467 7763a61a 2003-11-23 devnull VacFile *vf;
468 7763a61a 2003-11-23 devnull char *err;
469 7763a61a 2003-11-23 devnull int n;
470 7763a61a 2003-11-23 devnull
471 7763a61a 2003-11-23 devnull if(!f->busy)
472 7763a61a 2003-11-23 devnull return Enotexist;
473 7763a61a 2003-11-23 devnull vf = f->file;
474 7763a61a 2003-11-23 devnull thdr.count = 0;
475 7763a61a 2003-11-23 devnull off = rhdr.offset;
476 7763a61a 2003-11-23 devnull buf = thdr.data;
477 7763a61a 2003-11-23 devnull cnt = rhdr.count;
478 7763a61a 2003-11-23 devnull if(f->qid.type & QTDIR)
479 7763a61a 2003-11-23 devnull n = vacdirread(f, buf, off, cnt);
480 7763a61a 2003-11-23 devnull else
481 7763a61a 2003-11-23 devnull n = vfRead(vf, buf, cnt, off);
482 7763a61a 2003-11-23 devnull if(n < 0) {
483 7763a61a 2003-11-23 devnull err = vtGetError();
484 7763a61a 2003-11-23 devnull if(err == nil)
485 7763a61a 2003-11-23 devnull err = "unknown error!";
486 7763a61a 2003-11-23 devnull return err;
487 7763a61a 2003-11-23 devnull }
488 7763a61a 2003-11-23 devnull thdr.count = n;
489 7763a61a 2003-11-23 devnull return 0;
490 7763a61a 2003-11-23 devnull }
491 7763a61a 2003-11-23 devnull
492 7763a61a 2003-11-23 devnull char*
493 7763a61a 2003-11-23 devnull rwrite(Fid *f)
494 7763a61a 2003-11-23 devnull {
495 7763a61a 2003-11-23 devnull char *buf;
496 7763a61a 2003-11-23 devnull vlong off;
497 7763a61a 2003-11-23 devnull int cnt;
498 7763a61a 2003-11-23 devnull VacFile *vf;
499 7763a61a 2003-11-23 devnull
500 7763a61a 2003-11-23 devnull if(!f->busy)
501 7763a61a 2003-11-23 devnull return Enotexist;
502 7763a61a 2003-11-23 devnull vf = f->file;
503 7763a61a 2003-11-23 devnull thdr.count = 0;
504 7763a61a 2003-11-23 devnull off = rhdr.offset;
505 7763a61a 2003-11-23 devnull buf = rhdr.data;
506 7763a61a 2003-11-23 devnull cnt = rhdr.count;
507 7763a61a 2003-11-23 devnull if(f->qid.type & QTDIR)
508 7763a61a 2003-11-23 devnull return "file is a directory";
509 7763a61a 2003-11-23 devnull thdr.count = vfWrite(vf, buf, cnt, off, "none");
510 7763a61a 2003-11-23 devnull if(thdr.count < 0) {
511 7763a61a 2003-11-23 devnull fprint(2, "write failed: %s\n", vtGetError());
512 7763a61a 2003-11-23 devnull return vtGetError();
513 7763a61a 2003-11-23 devnull }
514 7763a61a 2003-11-23 devnull return 0;
515 7763a61a 2003-11-23 devnull }
516 7763a61a 2003-11-23 devnull
517 7763a61a 2003-11-23 devnull char *
518 7763a61a 2003-11-23 devnull rclunk(Fid *f)
519 7763a61a 2003-11-23 devnull {
520 7763a61a 2003-11-23 devnull f->busy = 0;
521 7763a61a 2003-11-23 devnull f->open = 0;
522 7763a61a 2003-11-23 devnull vtMemFree(f->user);
523 7763a61a 2003-11-23 devnull f->user = nil;
524 7763a61a 2003-11-23 devnull vfDecRef(f->file);
525 7763a61a 2003-11-23 devnull f->file = nil;
526 7763a61a 2003-11-23 devnull dirBufFree(f->db);
527 7763a61a 2003-11-23 devnull f->db = nil;
528 7763a61a 2003-11-23 devnull return 0;
529 7763a61a 2003-11-23 devnull }
530 7763a61a 2003-11-23 devnull
531 7763a61a 2003-11-23 devnull char *
532 7763a61a 2003-11-23 devnull rremove(Fid *f)
533 7763a61a 2003-11-23 devnull {
534 7763a61a 2003-11-23 devnull VacFile *vf, *vfp;
535 7763a61a 2003-11-23 devnull char *err = nil;
536 7763a61a 2003-11-23 devnull
537 7763a61a 2003-11-23 devnull if(!f->busy)
538 7763a61a 2003-11-23 devnull return Enotexist;
539 7763a61a 2003-11-23 devnull vf = f->file;
540 7763a61a 2003-11-23 devnull vfp = vfGetParent(vf);
541 7763a61a 2003-11-23 devnull
542 7763a61a 2003-11-23 devnull if(!permf(vfp, f->user, Pwrite)) {
543 7763a61a 2003-11-23 devnull err = Eperm;
544 7763a61a 2003-11-23 devnull goto Exit;
545 7763a61a 2003-11-23 devnull }
546 7763a61a 2003-11-23 devnull
547 7763a61a 2003-11-23 devnull if(!vfRemove(vf, "none")) {
548 7763a61a 2003-11-23 devnull print("vfRemove failed\n");
549 7763a61a 2003-11-23 devnull err = vtGetError();
550 7763a61a 2003-11-23 devnull }
551 7763a61a 2003-11-23 devnull
552 7763a61a 2003-11-23 devnull Exit:
553 7763a61a 2003-11-23 devnull vfDecRef(vfp);
554 7763a61a 2003-11-23 devnull rclunk(f);
555 7763a61a 2003-11-23 devnull return err;
556 7763a61a 2003-11-23 devnull }
557 7763a61a 2003-11-23 devnull
558 7763a61a 2003-11-23 devnull char *
559 7763a61a 2003-11-23 devnull rstat(Fid *f)
560 7763a61a 2003-11-23 devnull {
561 7763a61a 2003-11-23 devnull VacDir dir;
562 7763a61a 2003-11-23 devnull static uchar statbuf[1024];
563 7763a61a 2003-11-23 devnull
564 7763a61a 2003-11-23 devnull if(!f->busy)
565 7763a61a 2003-11-23 devnull return Enotexist;
566 7763a61a 2003-11-23 devnull vfGetDir(f->file, &dir);
567 7763a61a 2003-11-23 devnull thdr.stat = statbuf;
568 7763a61a 2003-11-23 devnull thdr.nstat = vdStat(&dir, thdr.stat, sizeof statbuf);
569 7763a61a 2003-11-23 devnull vdCleanup(&dir);
570 7763a61a 2003-11-23 devnull return 0;
571 7763a61a 2003-11-23 devnull }
572 7763a61a 2003-11-23 devnull
573 7763a61a 2003-11-23 devnull char *
574 7763a61a 2003-11-23 devnull rwstat(Fid *f)
575 7763a61a 2003-11-23 devnull {
576 7763a61a 2003-11-23 devnull if(!f->busy)
577 7763a61a 2003-11-23 devnull return Enotexist;
578 7763a61a 2003-11-23 devnull return Erdonly;
579 7763a61a 2003-11-23 devnull }
580 7763a61a 2003-11-23 devnull
581 7763a61a 2003-11-23 devnull int
582 7763a61a 2003-11-23 devnull vdStat(VacDir *vd, uchar *p, int np)
583 7763a61a 2003-11-23 devnull {
584 7763a61a 2003-11-23 devnull Dir dir;
585 7763a61a 2003-11-23 devnull
586 7763a61a 2003-11-23 devnull memset(&dir, 0, sizeof(dir));
587 7763a61a 2003-11-23 devnull
588 7763a61a 2003-11-23 devnull /*
589 7763a61a 2003-11-23 devnull * Where do path and version come from
590 7763a61a 2003-11-23 devnull */
591 7763a61a 2003-11-23 devnull dir.qid.path = vd->qid;
592 7763a61a 2003-11-23 devnull dir.qid.vers = vd->mcount;
593 7763a61a 2003-11-23 devnull dir.mode = vd->mode & 0777;
594 7763a61a 2003-11-23 devnull if(vd->mode & ModeAppend){
595 7763a61a 2003-11-23 devnull dir.qid.type |= QTAPPEND;
596 7763a61a 2003-11-23 devnull dir.mode |= DMAPPEND;
597 7763a61a 2003-11-23 devnull }
598 7763a61a 2003-11-23 devnull if(vd->mode & ModeExclusive){
599 7763a61a 2003-11-23 devnull dir.qid.type |= QTEXCL;
600 7763a61a 2003-11-23 devnull dir.mode |= DMEXCL;
601 7763a61a 2003-11-23 devnull }
602 7763a61a 2003-11-23 devnull if(vd->mode & ModeDir){
603 7763a61a 2003-11-23 devnull dir.qid.type |= QTDIR;
604 7763a61a 2003-11-23 devnull dir.mode |= DMDIR;
605 7763a61a 2003-11-23 devnull }
606 7763a61a 2003-11-23 devnull
607 7763a61a 2003-11-23 devnull dir.atime = vd->atime;
608 7763a61a 2003-11-23 devnull dir.mtime = vd->mtime;
609 7763a61a 2003-11-23 devnull dir.length = vd->size;
610 7763a61a 2003-11-23 devnull
611 7763a61a 2003-11-23 devnull dir.name = vd->elem;
612 7763a61a 2003-11-23 devnull dir.uid = vd->uid;
613 7763a61a 2003-11-23 devnull dir.gid = vd->gid;
614 7763a61a 2003-11-23 devnull dir.muid = vd->mid;
615 7763a61a 2003-11-23 devnull
616 7763a61a 2003-11-23 devnull return convD2M(&dir, p, np);
617 7763a61a 2003-11-23 devnull }
618 7763a61a 2003-11-23 devnull
619 7763a61a 2003-11-23 devnull DirBuf*
620 7763a61a 2003-11-23 devnull dirBufAlloc(VacFile *vf)
621 7763a61a 2003-11-23 devnull {
622 7763a61a 2003-11-23 devnull DirBuf *db;
623 7763a61a 2003-11-23 devnull
624 7763a61a 2003-11-23 devnull db = vtMemAllocZ(sizeof(DirBuf));
625 7763a61a 2003-11-23 devnull db->vde = vfDirEnum(vf);
626 7763a61a 2003-11-23 devnull return db;
627 7763a61a 2003-11-23 devnull }
628 7763a61a 2003-11-23 devnull
629 7763a61a 2003-11-23 devnull VacDir *
630 7763a61a 2003-11-23 devnull dirBufGet(DirBuf *db)
631 7763a61a 2003-11-23 devnull {
632 7763a61a 2003-11-23 devnull VacDir *vd;
633 7763a61a 2003-11-23 devnull int n;
634 7763a61a 2003-11-23 devnull
635 7763a61a 2003-11-23 devnull if(db->eof)
636 7763a61a 2003-11-23 devnull return nil;
637 7763a61a 2003-11-23 devnull
638 7763a61a 2003-11-23 devnull if(db->i >= db->n) {
639 7763a61a 2003-11-23 devnull n = vdeRead(db->vde, db->buf, DirBufSize);
640 7763a61a 2003-11-23 devnull if(n < 0)
641 7763a61a 2003-11-23 devnull return nil;
642 7763a61a 2003-11-23 devnull db->i = 0;
643 7763a61a 2003-11-23 devnull db->n = n;
644 7763a61a 2003-11-23 devnull if(n == 0) {
645 7763a61a 2003-11-23 devnull db->eof = 1;
646 7763a61a 2003-11-23 devnull return nil;
647 7763a61a 2003-11-23 devnull }
648 7763a61a 2003-11-23 devnull }
649 7763a61a 2003-11-23 devnull
650 7763a61a 2003-11-23 devnull vd = db->buf + db->i;
651 7763a61a 2003-11-23 devnull db->i++;
652 7763a61a 2003-11-23 devnull
653 7763a61a 2003-11-23 devnull return vd;
654 7763a61a 2003-11-23 devnull }
655 7763a61a 2003-11-23 devnull
656 7763a61a 2003-11-23 devnull int
657 7763a61a 2003-11-23 devnull dirBufUnget(DirBuf *db)
658 7763a61a 2003-11-23 devnull {
659 7763a61a 2003-11-23 devnull assert(db->i > 0);
660 7763a61a 2003-11-23 devnull db->i--;
661 7763a61a 2003-11-23 devnull return 1;
662 7763a61a 2003-11-23 devnull }
663 7763a61a 2003-11-23 devnull
664 7763a61a 2003-11-23 devnull void
665 7763a61a 2003-11-23 devnull dirBufFree(DirBuf *db)
666 7763a61a 2003-11-23 devnull {
667 7763a61a 2003-11-23 devnull int i;
668 7763a61a 2003-11-23 devnull
669 7763a61a 2003-11-23 devnull if(db == nil)
670 7763a61a 2003-11-23 devnull return;
671 7763a61a 2003-11-23 devnull
672 7763a61a 2003-11-23 devnull for(i=db->i; i<db->n; i++)
673 7763a61a 2003-11-23 devnull vdCleanup(db->buf + i);
674 7763a61a 2003-11-23 devnull vdeFree(db->vde);
675 7763a61a 2003-11-23 devnull vtMemFree(db);
676 7763a61a 2003-11-23 devnull }
677 7763a61a 2003-11-23 devnull
678 7763a61a 2003-11-23 devnull int
679 7763a61a 2003-11-23 devnull vacdirread(Fid *f, char *p, long off, long cnt)
680 7763a61a 2003-11-23 devnull {
681 7763a61a 2003-11-23 devnull int n, nb;
682 7763a61a 2003-11-23 devnull VacDir *vd;
683 7763a61a 2003-11-23 devnull
684 7763a61a 2003-11-23 devnull /*
685 7763a61a 2003-11-23 devnull * special case of rewinding a directory
686 7763a61a 2003-11-23 devnull * otherwise ignore the offset
687 7763a61a 2003-11-23 devnull */
688 7763a61a 2003-11-23 devnull if(off == 0 && f->db) {
689 7763a61a 2003-11-23 devnull dirBufFree(f->db);
690 7763a61a 2003-11-23 devnull f->db = nil;
691 7763a61a 2003-11-23 devnull }
692 7763a61a 2003-11-23 devnull
693 7763a61a 2003-11-23 devnull if(f->db == nil)
694 7763a61a 2003-11-23 devnull f->db = dirBufAlloc(f->file);
695 7763a61a 2003-11-23 devnull
696 7763a61a 2003-11-23 devnull for(nb = 0; nb < cnt; nb += n) {
697 7763a61a 2003-11-23 devnull vd = dirBufGet(f->db);
698 7763a61a 2003-11-23 devnull if(vd == nil) {
699 7763a61a 2003-11-23 devnull if(!f->db->eof)
700 7763a61a 2003-11-23 devnull return -1;
701 7763a61a 2003-11-23 devnull break;
702 7763a61a 2003-11-23 devnull }
703 7763a61a 2003-11-23 devnull n = vdStat(vd, (uchar*)p, cnt-nb);
704 7763a61a 2003-11-23 devnull if(n <= BIT16SZ) {
705 7763a61a 2003-11-23 devnull dirBufUnget(f->db);
706 7763a61a 2003-11-23 devnull break;
707 7763a61a 2003-11-23 devnull }
708 7763a61a 2003-11-23 devnull vdCleanup(vd);
709 7763a61a 2003-11-23 devnull p += n;
710 7763a61a 2003-11-23 devnull }
711 7763a61a 2003-11-23 devnull return nb;
712 7763a61a 2003-11-23 devnull }
713 7763a61a 2003-11-23 devnull
714 7763a61a 2003-11-23 devnull Fid *
715 7763a61a 2003-11-23 devnull newfid(int fid)
716 7763a61a 2003-11-23 devnull {
717 7763a61a 2003-11-23 devnull Fid *f, *ff;
718 7763a61a 2003-11-23 devnull
719 7763a61a 2003-11-23 devnull ff = 0;
720 7763a61a 2003-11-23 devnull for(f = fids; f; f = f->next)
721 7763a61a 2003-11-23 devnull if(f->fid == fid)
722 7763a61a 2003-11-23 devnull return f;
723 7763a61a 2003-11-23 devnull else if(!ff && !f->busy)
724 7763a61a 2003-11-23 devnull ff = f;
725 7763a61a 2003-11-23 devnull if(ff){
726 7763a61a 2003-11-23 devnull ff->fid = fid;
727 7763a61a 2003-11-23 devnull return ff;
728 7763a61a 2003-11-23 devnull }
729 7763a61a 2003-11-23 devnull f = vtMemAllocZ(sizeof *f);
730 7763a61a 2003-11-23 devnull f->fid = fid;
731 7763a61a 2003-11-23 devnull f->next = fids;
732 7763a61a 2003-11-23 devnull fids = f;
733 7763a61a 2003-11-23 devnull return f;
734 7763a61a 2003-11-23 devnull }
735 7763a61a 2003-11-23 devnull
736 7763a61a 2003-11-23 devnull void
737 7763a61a 2003-11-23 devnull io(void)
738 7763a61a 2003-11-23 devnull {
739 7763a61a 2003-11-23 devnull char *err;
740 7763a61a 2003-11-23 devnull int n;
741 7763a61a 2003-11-23 devnull
742 7763a61a 2003-11-23 devnull for(;;){
743 7763a61a 2003-11-23 devnull /*
744 7763a61a 2003-11-23 devnull * reading from a pipe or a network device
745 7763a61a 2003-11-23 devnull * will give an error after a few eof reads
746 7763a61a 2003-11-23 devnull * however, we cannot tell the difference
747 7763a61a 2003-11-23 devnull * between a zero-length read and an interrupt
748 7763a61a 2003-11-23 devnull * on the processes writing to us,
749 7763a61a 2003-11-23 devnull * so we wait for the error
750 7763a61a 2003-11-23 devnull */
751 7763a61a 2003-11-23 devnull n = read9pmsg(mfd[0], mdata, sizeof mdata);
752 7763a61a 2003-11-23 devnull if(n == 0)
753 7763a61a 2003-11-23 devnull continue;
754 7763a61a 2003-11-23 devnull if(n < 0)
755 7763a61a 2003-11-23 devnull break;
756 7763a61a 2003-11-23 devnull if(convM2S(mdata, n, &rhdr) != n)
757 7763a61a 2003-11-23 devnull sysfatal("convM2S conversion error");
758 7763a61a 2003-11-23 devnull
759 7763a61a 2003-11-23 devnull if(dflag)
760 7763a61a 2003-11-23 devnull fprint(2, "vacfs:<-%F\n", &rhdr);
761 7763a61a 2003-11-23 devnull
762 7763a61a 2003-11-23 devnull thdr.data = (char*)mdata + IOHDRSZ;
763 7763a61a 2003-11-23 devnull if(!fcalls[rhdr.type])
764 7763a61a 2003-11-23 devnull err = "bad fcall type";
765 7763a61a 2003-11-23 devnull else
766 7763a61a 2003-11-23 devnull err = (*fcalls[rhdr.type])(newfid(rhdr.fid));
767 7763a61a 2003-11-23 devnull if(err){
768 7763a61a 2003-11-23 devnull thdr.type = Rerror;
769 7763a61a 2003-11-23 devnull thdr.ename = err;
770 7763a61a 2003-11-23 devnull }else{
771 7763a61a 2003-11-23 devnull thdr.type = rhdr.type + 1;
772 7763a61a 2003-11-23 devnull thdr.fid = rhdr.fid;
773 7763a61a 2003-11-23 devnull }
774 7763a61a 2003-11-23 devnull thdr.tag = rhdr.tag;
775 7763a61a 2003-11-23 devnull if(dflag)
776 7763a61a 2003-11-23 devnull fprint(2, "vacfs:->%F\n", &thdr);
777 7763a61a 2003-11-23 devnull n = convS2M(&thdr, mdata, messagesize);
778 7763a61a 2003-11-23 devnull if(write(mfd[1], mdata, n) != n)
779 7763a61a 2003-11-23 devnull sysfatal("mount write: %r");
780 7763a61a 2003-11-23 devnull }
781 7763a61a 2003-11-23 devnull }
782 7763a61a 2003-11-23 devnull
783 7763a61a 2003-11-23 devnull int
784 7763a61a 2003-11-23 devnull permf(VacFile *vf, char *user, int p)
785 7763a61a 2003-11-23 devnull {
786 7763a61a 2003-11-23 devnull VacDir dir;
787 7763a61a 2003-11-23 devnull ulong perm;
788 7763a61a 2003-11-23 devnull
789 7763a61a 2003-11-23 devnull if(!vfGetDir(vf, &dir))
790 7763a61a 2003-11-23 devnull return 0;
791 7763a61a 2003-11-23 devnull perm = dir.mode & 0777;
792 7763a61a 2003-11-23 devnull if(noperm)
793 7763a61a 2003-11-23 devnull goto Good;
794 7763a61a 2003-11-23 devnull if((p*Pother) & perm)
795 7763a61a 2003-11-23 devnull goto Good;
796 7763a61a 2003-11-23 devnull if(strcmp(user, dir.gid)==0 && ((p*Pgroup) & perm))
797 7763a61a 2003-11-23 devnull goto Good;
798 7763a61a 2003-11-23 devnull if(strcmp(user, dir.uid)==0 && ((p*Powner) & perm))
799 7763a61a 2003-11-23 devnull goto Good;
800 7763a61a 2003-11-23 devnull vdCleanup(&dir);
801 7763a61a 2003-11-23 devnull return 0;
802 7763a61a 2003-11-23 devnull Good:
803 7763a61a 2003-11-23 devnull vdCleanup(&dir);
804 7763a61a 2003-11-23 devnull return 1;
805 7763a61a 2003-11-23 devnull }
806 7763a61a 2003-11-23 devnull
807 7763a61a 2003-11-23 devnull int
808 7763a61a 2003-11-23 devnull perm(Fid *f, int p)
809 7763a61a 2003-11-23 devnull {
810 7763a61a 2003-11-23 devnull return permf(f->file, f->user, p);
811 7763a61a 2003-11-23 devnull }
812 7763a61a 2003-11-23 devnull
813 7763a61a 2003-11-23 devnull void
814 7763a61a 2003-11-23 devnull init(char *file, char *host, long ncache, int readOnly)
815 7763a61a 2003-11-23 devnull {
816 7763a61a 2003-11-23 devnull notify(notifyf);
817 7763a61a 2003-11-23 devnull user = getuser();
818 7763a61a 2003-11-23 devnull
819 7763a61a 2003-11-23 devnull fmtinstall('V', vtScoreFmt);
820 7763a61a 2003-11-23 devnull fmtinstall('R', vtErrFmt);
821 7763a61a 2003-11-23 devnull
822 7763a61a 2003-11-23 devnull session = vtDial(host, 0);
823 7763a61a 2003-11-23 devnull if(session == nil)
824 7763a61a 2003-11-23 devnull vtFatal("could not connect to server: %s", vtGetError());
825 7763a61a 2003-11-23 devnull
826 7763a61a 2003-11-23 devnull if(!vtConnect(session, 0))
827 7763a61a 2003-11-23 devnull vtFatal("vtConnect: %s", vtGetError());
828 7763a61a 2003-11-23 devnull
829 7763a61a 2003-11-23 devnull fs = vfsOpen(session, file, readOnly, ncache);
830 7763a61a 2003-11-23 devnull if(fs == nil)
831 7763a61a 2003-11-23 devnull vtFatal("vfsOpen: %s", vtGetError());
832 7763a61a 2003-11-23 devnull }
833 7763a61a 2003-11-23 devnull
834 7763a61a 2003-11-23 devnull void
835 7763a61a 2003-11-23 devnull shutdown(void)
836 7763a61a 2003-11-23 devnull {
837 7763a61a 2003-11-23 devnull Fid *f;
838 7763a61a 2003-11-23 devnull
839 7763a61a 2003-11-23 devnull for(f = fids; f; f = f->next) {
840 7763a61a 2003-11-23 devnull if(!f->busy)
841 7763a61a 2003-11-23 devnull continue;
842 7763a61a 2003-11-23 devnull fprint(2, "open fid: %d\n", f->fid);
843 7763a61a 2003-11-23 devnull rclunk(f);
844 7763a61a 2003-11-23 devnull }
845 7763a61a 2003-11-23 devnull
846 7763a61a 2003-11-23 devnull vfsClose(fs);
847 7763a61a 2003-11-23 devnull vtClose(session);
848 7763a61a 2003-11-23 devnull }
849 7763a61a 2003-11-23 devnull