Blame


1 7763a61a 2003-11-23 devnull #include "stdinc.h"
2 7763a61a 2003-11-23 devnull #include "vac.h"
3 7763a61a 2003-11-23 devnull #include "dat.h"
4 7763a61a 2003-11-23 devnull #include "fns.h"
5 7763a61a 2003-11-23 devnull #include "error.h"
6 7763a61a 2003-11-23 devnull
7 7763a61a 2003-11-23 devnull /*
8 7763a61a 2003-11-23 devnull * locking order is upwards. A thread can hold the lock for a VacFile
9 7763a61a 2003-11-23 devnull * and then acquire the lock of its parent
10 7763a61a 2003-11-23 devnull */
11 3d77c87e 2004-03-15 devnull struct VacFile
12 3d77c87e 2004-03-15 devnull {
13 3d77c87e 2004-03-15 devnull VacFs *fs; /* immutable */
14 7763a61a 2003-11-23 devnull
15 7763a61a 2003-11-23 devnull /* meta data for file: protected by the lk in the parent */
16 3d77c87e 2004-03-15 devnull int ref; /* holds this data structure up */
17 7763a61a 2003-11-23 devnull
18 3d77c87e 2004-03-15 devnull int partial; /* file was never really open */
19 3d77c87e 2004-03-15 devnull int removed; /* file has been removed */
20 3d77c87e 2004-03-15 devnull int dirty; /* dir is dirty with respect to meta data in block */
21 3d77c87e 2004-03-15 devnull u32int boff; /* block offset within msource for this file's metadata */
22 3d77c87e 2004-03-15 devnull VacDir dir; /* metadata for this file */
23 3d77c87e 2004-03-15 devnull VacFile *up; /* parent file */
24 3d77c87e 2004-03-15 devnull VacFile *next; /* sibling */
25 7763a61a 2003-11-23 devnull
26 3d77c87e 2004-03-15 devnull RWLock lk; /* lock for the following */
27 3d77c87e 2004-03-15 devnull VtFile *source; /* actual data */
28 3d77c87e 2004-03-15 devnull VtFile *msource; /* metadata for children in a directory */
29 3d77c87e 2004-03-15 devnull VacFile *down; /* children */
30 3d77c87e 2004-03-15 devnull int mode;
31 7763a61a 2003-11-23 devnull };
32 7763a61a 2003-11-23 devnull
33 3d77c87e 2004-03-15 devnull static int filelock(VacFile*);
34 3d77c87e 2004-03-15 devnull static u32int filemetaalloc(VacFile*, VacDir*, u32int);
35 3d77c87e 2004-03-15 devnull static int filemetaflush2(VacFile*, char*);
36 3d77c87e 2004-03-15 devnull static void filemetalock(VacFile*);
37 3d77c87e 2004-03-15 devnull static void filemetaunlock(VacFile*);
38 3d77c87e 2004-03-15 devnull static void fileraccess(VacFile*);
39 3d77c87e 2004-03-15 devnull static int filerlock(VacFile*);
40 3d77c87e 2004-03-15 devnull static void filerunlock(VacFile*);
41 3d77c87e 2004-03-15 devnull static void fileunlock(VacFile*);
42 3d77c87e 2004-03-15 devnull static void filewaccess(VacFile*, char*);
43 7763a61a 2003-11-23 devnull
44 3d77c87e 2004-03-15 devnull void mbinit(MetaBlock*, u8int*, uint, uint);
45 3d77c87e 2004-03-15 devnull int mbsearch(MetaBlock*, char*, int*, MetaEntry*);
46 3d77c87e 2004-03-15 devnull int mbresize(MetaBlock*, MetaEntry*, int);
47 3d77c87e 2004-03-15 devnull VacFile *vdlookup(VacFile*, char*);
48 7763a61a 2003-11-23 devnull
49 3d77c87e 2004-03-15 devnull static VacFile*
50 3d77c87e 2004-03-15 devnull filealloc(VacFs *fs)
51 7763a61a 2003-11-23 devnull {
52 3d77c87e 2004-03-15 devnull VacFile *f;
53 7763a61a 2003-11-23 devnull
54 3d77c87e 2004-03-15 devnull f = vtmallocz(sizeof(VacFile));
55 3d77c87e 2004-03-15 devnull f->ref = 1;
56 3d77c87e 2004-03-15 devnull f->fs = fs;
57 3d77c87e 2004-03-15 devnull f->boff = NilBlock;
58 3d77c87e 2004-03-15 devnull f->mode = fs->mode;
59 3d77c87e 2004-03-15 devnull return f;
60 7763a61a 2003-11-23 devnull }
61 7763a61a 2003-11-23 devnull
62 7763a61a 2003-11-23 devnull static void
63 3d77c87e 2004-03-15 devnull filefree(VacFile *f)
64 7763a61a 2003-11-23 devnull {
65 3d77c87e 2004-03-15 devnull vtfileclose(f->source);
66 3d77c87e 2004-03-15 devnull vtfileclose(f->msource);
67 3d77c87e 2004-03-15 devnull vdcleanup(&f->dir);
68 3d77c87e 2004-03-15 devnull memset(f, ~0, sizeof *f); /* paranoia */
69 3d77c87e 2004-03-15 devnull vtfree(f);
70 7763a61a 2003-11-23 devnull }
71 7763a61a 2003-11-23 devnull
72 3d77c87e 2004-03-15 devnull /*
73 3d77c87e 2004-03-15 devnull * the file is locked already
74 3d77c87e 2004-03-15 devnull * f->msource is unlocked
75 3d77c87e 2004-03-15 devnull */
76 3d77c87e 2004-03-15 devnull static VacFile*
77 3d77c87e 2004-03-15 devnull dirlookup(VacFile *f, char *elem)
78 7763a61a 2003-11-23 devnull {
79 7763a61a 2003-11-23 devnull int i;
80 7763a61a 2003-11-23 devnull MetaBlock mb;
81 3d77c87e 2004-03-15 devnull MetaEntry me;
82 3d77c87e 2004-03-15 devnull VtBlock *b;
83 3d77c87e 2004-03-15 devnull VtFile *meta;
84 3d77c87e 2004-03-15 devnull VacFile *ff;
85 3d77c87e 2004-03-15 devnull u32int bo, nb;
86 7763a61a 2003-11-23 devnull
87 3d77c87e 2004-03-15 devnull meta = f->msource;
88 3d77c87e 2004-03-15 devnull b = nil;
89 3d77c87e 2004-03-15 devnull if(vtfilelock(meta, -1) < 0)
90 3d77c87e 2004-03-15 devnull return nil;
91 3d77c87e 2004-03-15 devnull nb = (vtfilegetsize(meta)+meta->dsize-1)/meta->dsize;
92 3d77c87e 2004-03-15 devnull for(bo=0; bo<nb; bo++){
93 3d77c87e 2004-03-15 devnull b = vtfileblock(meta, bo, VtOREAD);
94 3d77c87e 2004-03-15 devnull if(b == nil)
95 3d77c87e 2004-03-15 devnull goto Err;
96 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, meta->dsize) < 0)
97 3d77c87e 2004-03-15 devnull goto Err;
98 a20a1468 2005-01-16 devnull if(mbsearch(&mb, elem, &i, &me) >= 0){
99 3d77c87e 2004-03-15 devnull ff = filealloc(f->fs);
100 3d77c87e 2004-03-15 devnull if(vdunpack(&ff->dir, &me) < 0){
101 3d77c87e 2004-03-15 devnull filefree(ff);
102 3d77c87e 2004-03-15 devnull goto Err;
103 3d77c87e 2004-03-15 devnull }
104 3d77c87e 2004-03-15 devnull vtfileunlock(meta);
105 3d77c87e 2004-03-15 devnull vtblockput(b);
106 3d77c87e 2004-03-15 devnull ff->boff = bo;
107 3d77c87e 2004-03-15 devnull ff->mode = f->mode;
108 3d77c87e 2004-03-15 devnull return ff;
109 7763a61a 2003-11-23 devnull }
110 7763a61a 2003-11-23 devnull
111 3d77c87e 2004-03-15 devnull vtblockput(b);
112 3d77c87e 2004-03-15 devnull b = nil;
113 7763a61a 2003-11-23 devnull }
114 3d77c87e 2004-03-15 devnull werrstr(ENoFile);
115 7763a61a 2003-11-23 devnull /* fall through */
116 7763a61a 2003-11-23 devnull Err:
117 3d77c87e 2004-03-15 devnull vtfileunlock(meta);
118 3d77c87e 2004-03-15 devnull vtblockput(b);
119 7763a61a 2003-11-23 devnull return nil;
120 7763a61a 2003-11-23 devnull }
121 7763a61a 2003-11-23 devnull
122 3d77c87e 2004-03-15 devnull VacFile*
123 3d77c87e 2004-03-15 devnull _vacfileroot(VacFs *fs, VtFile *r)
124 7763a61a 2003-11-23 devnull {
125 3d77c87e 2004-03-15 devnull VtBlock *b;
126 3d77c87e 2004-03-15 devnull VtFile *r0, *r1, *r2;
127 7763a61a 2003-11-23 devnull MetaBlock mb;
128 7763a61a 2003-11-23 devnull MetaEntry me;
129 7763a61a 2003-11-23 devnull VacFile *root, *mr;
130 7763a61a 2003-11-23 devnull
131 3d77c87e 2004-03-15 devnull b = nil;
132 7763a61a 2003-11-23 devnull root = nil;
133 7763a61a 2003-11-23 devnull mr = nil;
134 7763a61a 2003-11-23 devnull r1 = nil;
135 7763a61a 2003-11-23 devnull r2 = nil;
136 7763a61a 2003-11-23 devnull
137 3d77c87e 2004-03-15 devnull if(vtfilelock(r, -1) < 0)
138 3d77c87e 2004-03-15 devnull return nil;
139 3d77c87e 2004-03-15 devnull r0 = vtfileopen(r, 0, fs->mode);
140 3d77c87e 2004-03-15 devnull if(r0 == nil)
141 7763a61a 2003-11-23 devnull goto Err;
142 3d77c87e 2004-03-15 devnull r1 = vtfileopen(r, 1, fs->mode);
143 3d77c87e 2004-03-15 devnull if(r1 == nil)
144 7763a61a 2003-11-23 devnull goto Err;
145 3d77c87e 2004-03-15 devnull r2 = vtfileopen(r, 2, fs->mode);
146 3d77c87e 2004-03-15 devnull if(r2 == nil)
147 3d77c87e 2004-03-15 devnull goto Err;
148 7763a61a 2003-11-23 devnull
149 3d77c87e 2004-03-15 devnull mr = filealloc(fs);
150 7763a61a 2003-11-23 devnull mr->msource = r2;
151 7763a61a 2003-11-23 devnull r2 = nil;
152 7763a61a 2003-11-23 devnull
153 3d77c87e 2004-03-15 devnull root = filealloc(fs);
154 3d77c87e 2004-03-15 devnull root->boff = 0;
155 7763a61a 2003-11-23 devnull root->up = mr;
156 7763a61a 2003-11-23 devnull root->source = r0;
157 7763a61a 2003-11-23 devnull r0 = nil;
158 7763a61a 2003-11-23 devnull root->msource = r1;
159 7763a61a 2003-11-23 devnull r1 = nil;
160 7763a61a 2003-11-23 devnull
161 7763a61a 2003-11-23 devnull mr->down = root;
162 7763a61a 2003-11-23 devnull
163 3d77c87e 2004-03-15 devnull if(vtfilelock(mr->msource, -1) < 0)
164 7763a61a 2003-11-23 devnull goto Err;
165 3d77c87e 2004-03-15 devnull b = vtfileblock(mr->msource, 0, VtOREAD);
166 3d77c87e 2004-03-15 devnull vtfileunlock(mr->msource);
167 3d77c87e 2004-03-15 devnull if(b == nil)
168 3d77c87e 2004-03-15 devnull goto Err;
169 7763a61a 2003-11-23 devnull
170 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, mr->msource->dsize) < 0)
171 7763a61a 2003-11-23 devnull goto Err;
172 3d77c87e 2004-03-15 devnull
173 3d77c87e 2004-03-15 devnull meunpack(&me, &mb, 0);
174 3d77c87e 2004-03-15 devnull if(vdunpack(&root->dir, &me) < 0)
175 7763a61a 2003-11-23 devnull goto Err;
176 3d77c87e 2004-03-15 devnull vtblockput(b);
177 3d77c87e 2004-03-15 devnull vtfileunlock(r);
178 3d77c87e 2004-03-15 devnull fileraccess(root);
179 7763a61a 2003-11-23 devnull
180 7763a61a 2003-11-23 devnull return root;
181 7763a61a 2003-11-23 devnull Err:
182 3d77c87e 2004-03-15 devnull vtblockput(b);
183 7763a61a 2003-11-23 devnull if(r0)
184 3d77c87e 2004-03-15 devnull vtfileclose(r0);
185 7763a61a 2003-11-23 devnull if(r1)
186 3d77c87e 2004-03-15 devnull vtfileclose(r1);
187 7763a61a 2003-11-23 devnull if(r2)
188 3d77c87e 2004-03-15 devnull vtfileclose(r2);
189 7763a61a 2003-11-23 devnull if(mr)
190 3d77c87e 2004-03-15 devnull filefree(mr);
191 7763a61a 2003-11-23 devnull if(root)
192 3d77c87e 2004-03-15 devnull filefree(root);
193 3d77c87e 2004-03-15 devnull vtfileunlock(r);
194 7763a61a 2003-11-23 devnull
195 7763a61a 2003-11-23 devnull return nil;
196 7763a61a 2003-11-23 devnull }
197 7763a61a 2003-11-23 devnull
198 3d77c87e 2004-03-15 devnull static VtFile *
199 3d77c87e 2004-03-15 devnull fileopensource(VacFile *f, u32int offset, u32int gen, int dir, uint mode)
200 7763a61a 2003-11-23 devnull {
201 3d77c87e 2004-03-15 devnull VtFile *r;
202 7763a61a 2003-11-23 devnull
203 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, mode) < 0)
204 3d77c87e 2004-03-15 devnull return nil;
205 3d77c87e 2004-03-15 devnull r = vtfileopen(f->source, offset, mode);
206 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
207 3d77c87e 2004-03-15 devnull if(r == nil)
208 3d77c87e 2004-03-15 devnull return nil;
209 3d77c87e 2004-03-15 devnull if(r->gen != gen){
210 3d77c87e 2004-03-15 devnull werrstr(ERemoved);
211 3d77c87e 2004-03-15 devnull goto Err;
212 3d77c87e 2004-03-15 devnull }
213 3d77c87e 2004-03-15 devnull if(r->dir != dir && r->mode != -1){
214 3d77c87e 2004-03-15 devnull fprint(2, "fileopensource: dir mismatch %d %d\n", r->dir, dir);
215 3d77c87e 2004-03-15 devnull werrstr(EBadMeta);
216 3d77c87e 2004-03-15 devnull goto Err;
217 3d77c87e 2004-03-15 devnull }
218 3d77c87e 2004-03-15 devnull return r;
219 3d77c87e 2004-03-15 devnull Err:
220 3d77c87e 2004-03-15 devnull vtfileclose(r);
221 3d77c87e 2004-03-15 devnull return nil;
222 3d77c87e 2004-03-15 devnull }
223 7763a61a 2003-11-23 devnull
224 3d77c87e 2004-03-15 devnull VacFile*
225 3d77c87e 2004-03-15 devnull _filewalk(VacFile *f, char *elem, int partial)
226 3d77c87e 2004-03-15 devnull {
227 3d77c87e 2004-03-15 devnull VacFile *ff;
228 3d77c87e 2004-03-15 devnull
229 3d77c87e 2004-03-15 devnull fileraccess(f);
230 3d77c87e 2004-03-15 devnull
231 3d77c87e 2004-03-15 devnull if(elem[0] == 0){
232 3d77c87e 2004-03-15 devnull werrstr(EBadPath);
233 7763a61a 2003-11-23 devnull return nil;
234 7763a61a 2003-11-23 devnull }
235 3d77c87e 2004-03-15 devnull
236 3d77c87e 2004-03-15 devnull if(!vacfileisdir(f)){
237 3d77c87e 2004-03-15 devnull werrstr(ENotDir);
238 7763a61a 2003-11-23 devnull return nil;
239 7763a61a 2003-11-23 devnull }
240 7763a61a 2003-11-23 devnull
241 3d77c87e 2004-03-15 devnull if(strcmp(elem, ".") == 0){
242 3d77c87e 2004-03-15 devnull return vacfileincref(f);
243 7763a61a 2003-11-23 devnull }
244 7763a61a 2003-11-23 devnull
245 3d77c87e 2004-03-15 devnull if(strcmp(elem, "..") == 0){
246 3d77c87e 2004-03-15 devnull if(vacfileisroot(f))
247 3d77c87e 2004-03-15 devnull return vacfileincref(f);
248 3d77c87e 2004-03-15 devnull return vacfileincref(f->up);
249 7763a61a 2003-11-23 devnull }
250 7763a61a 2003-11-23 devnull
251 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
252 7763a61a 2003-11-23 devnull return nil;
253 7763a61a 2003-11-23 devnull
254 3d77c87e 2004-03-15 devnull for(ff = f->down; ff; ff=ff->next){
255 3d77c87e 2004-03-15 devnull if(strcmp(elem, ff->dir.elem) == 0 && !ff->removed){
256 3d77c87e 2004-03-15 devnull ff->ref++;
257 7763a61a 2003-11-23 devnull goto Exit;
258 7763a61a 2003-11-23 devnull }
259 7763a61a 2003-11-23 devnull }
260 7763a61a 2003-11-23 devnull
261 3d77c87e 2004-03-15 devnull ff = dirlookup(f, elem);
262 3d77c87e 2004-03-15 devnull if(ff == nil)
263 7763a61a 2003-11-23 devnull goto Err;
264 3d77c87e 2004-03-15 devnull
265 3d77c87e 2004-03-15 devnull if(ff->dir.mode & ModeSnapshot)
266 3d77c87e 2004-03-15 devnull ff->mode = VtOREAD;
267 3d77c87e 2004-03-15 devnull
268 3d77c87e 2004-03-15 devnull if(partial){
269 3d77c87e 2004-03-15 devnull /*
270 3d77c87e 2004-03-15 devnull * Do nothing. We're opening this file only so we can clri it.
271 3d77c87e 2004-03-15 devnull * Usually the sources can't be opened, hence we won't even bother.
272 3d77c87e 2004-03-15 devnull * Be VERY careful with the returned file. If you hand it to a routine
273 3d77c87e 2004-03-15 devnull * expecting ff->source and/or ff->msource to be non-nil, we're
274 3d77c87e 2004-03-15 devnull * likely to dereference nil. FileClri should be the only routine
275 3d77c87e 2004-03-15 devnull * setting partial.
276 3d77c87e 2004-03-15 devnull */
277 3d77c87e 2004-03-15 devnull ff->partial = 1;
278 3d77c87e 2004-03-15 devnull }else if(ff->dir.mode & ModeDir){
279 3d77c87e 2004-03-15 devnull ff->source = fileopensource(f, ff->dir.entry, ff->dir.gen, 1, ff->mode);
280 3d77c87e 2004-03-15 devnull ff->msource = fileopensource(f, ff->dir.mentry, ff->dir.mgen, 0, ff->mode);
281 3d77c87e 2004-03-15 devnull if(ff->source == nil || ff->msource == nil)
282 7763a61a 2003-11-23 devnull goto Err;
283 3d77c87e 2004-03-15 devnull }else{
284 3d77c87e 2004-03-15 devnull ff->source = fileopensource(f, ff->dir.entry, ff->dir.gen, 0, ff->mode);
285 3d77c87e 2004-03-15 devnull if(ff->source == nil)
286 3d77c87e 2004-03-15 devnull goto Err;
287 7763a61a 2003-11-23 devnull }
288 7763a61a 2003-11-23 devnull
289 7763a61a 2003-11-23 devnull /* link in and up parent ref count */
290 3d77c87e 2004-03-15 devnull ff->next = f->down;
291 3d77c87e 2004-03-15 devnull f->down = ff;
292 3d77c87e 2004-03-15 devnull ff->up = f;
293 3d77c87e 2004-03-15 devnull vacfileincref(f);
294 7763a61a 2003-11-23 devnull Exit:
295 3d77c87e 2004-03-15 devnull fileunlock(f);
296 3d77c87e 2004-03-15 devnull return ff;
297 7763a61a 2003-11-23 devnull Err:
298 3d77c87e 2004-03-15 devnull fileunlock(f);
299 3d77c87e 2004-03-15 devnull if(ff != nil)
300 3d77c87e 2004-03-15 devnull vacfiledecref(ff);
301 7763a61a 2003-11-23 devnull return nil;
302 7763a61a 2003-11-23 devnull }
303 7763a61a 2003-11-23 devnull
304 3d77c87e 2004-03-15 devnull VacFile*
305 3d77c87e 2004-03-15 devnull vacfilewalk(VacFile *f, char *elem)
306 7763a61a 2003-11-23 devnull {
307 3d77c87e 2004-03-15 devnull return _filewalk(f, elem, 0);
308 3d77c87e 2004-03-15 devnull }
309 3d77c87e 2004-03-15 devnull
310 3d77c87e 2004-03-15 devnull VacFile*
311 3d77c87e 2004-03-15 devnull _fileopen(VacFs *fs, char *path, int partial)
312 3d77c87e 2004-03-15 devnull {
313 3d77c87e 2004-03-15 devnull VacFile *f, *ff;
314 3d77c87e 2004-03-15 devnull char *p, elem[VtMaxStringSize], *opath;
315 7763a61a 2003-11-23 devnull int n;
316 7763a61a 2003-11-23 devnull
317 3d77c87e 2004-03-15 devnull f = fs->root;
318 3d77c87e 2004-03-15 devnull vacfileincref(f);
319 3d77c87e 2004-03-15 devnull opath = path;
320 3d77c87e 2004-03-15 devnull while(*path != 0){
321 7763a61a 2003-11-23 devnull for(p = path; *p && *p != '/'; p++)
322 7763a61a 2003-11-23 devnull ;
323 7763a61a 2003-11-23 devnull n = p - path;
324 3d77c87e 2004-03-15 devnull if(n > 0){
325 3d77c87e 2004-03-15 devnull if(n > VtMaxStringSize){
326 3d77c87e 2004-03-15 devnull werrstr("%s: element too long", EBadPath);
327 7763a61a 2003-11-23 devnull goto Err;
328 7763a61a 2003-11-23 devnull }
329 7763a61a 2003-11-23 devnull memmove(elem, path, n);
330 7763a61a 2003-11-23 devnull elem[n] = 0;
331 3d77c87e 2004-03-15 devnull ff = _filewalk(f, elem, partial && *p=='\0');
332 3d77c87e 2004-03-15 devnull if(ff == nil){
333 3d77c87e 2004-03-15 devnull werrstr("%.*s: %R", utfnlen(opath, p-opath), opath);
334 7763a61a 2003-11-23 devnull goto Err;
335 3d77c87e 2004-03-15 devnull }
336 3d77c87e 2004-03-15 devnull vacfiledecref(f);
337 3d77c87e 2004-03-15 devnull f = ff;
338 7763a61a 2003-11-23 devnull }
339 7763a61a 2003-11-23 devnull if(*p == '/')
340 7763a61a 2003-11-23 devnull p++;
341 7763a61a 2003-11-23 devnull path = p;
342 7763a61a 2003-11-23 devnull }
343 3d77c87e 2004-03-15 devnull return f;
344 7763a61a 2003-11-23 devnull Err:
345 3d77c87e 2004-03-15 devnull vacfiledecref(f);
346 7763a61a 2003-11-23 devnull return nil;
347 7763a61a 2003-11-23 devnull }
348 7763a61a 2003-11-23 devnull
349 3d77c87e 2004-03-15 devnull VacFile*
350 3d77c87e 2004-03-15 devnull vacfileopen(VacFs *fs, char *path)
351 7763a61a 2003-11-23 devnull {
352 3d77c87e 2004-03-15 devnull return _fileopen(fs, path, 0);
353 3d77c87e 2004-03-15 devnull }
354 3d77c87e 2004-03-15 devnull
355 3d77c87e 2004-03-15 devnull #if 0
356 3d77c87e 2004-03-15 devnull static void
357 3d77c87e 2004-03-15 devnull filesettmp(VacFile *f, int istmp)
358 3d77c87e 2004-03-15 devnull {
359 3d77c87e 2004-03-15 devnull int i;
360 3d77c87e 2004-03-15 devnull VtEntry e;
361 3d77c87e 2004-03-15 devnull VtFile *r;
362 3d77c87e 2004-03-15 devnull
363 3d77c87e 2004-03-15 devnull for(i=0; i<2; i++){
364 3d77c87e 2004-03-15 devnull if(i==0)
365 3d77c87e 2004-03-15 devnull r = f->source;
366 3d77c87e 2004-03-15 devnull else
367 3d77c87e 2004-03-15 devnull r = f->msource;
368 3d77c87e 2004-03-15 devnull if(r == nil)
369 3d77c87e 2004-03-15 devnull continue;
370 3d77c87e 2004-03-15 devnull if(vtfilegetentry(r, &e) < 0){
371 3d77c87e 2004-03-15 devnull fprint(2, "vtfilegetentry failed (cannot happen): %r\n");
372 3d77c87e 2004-03-15 devnull continue;
373 3d77c87e 2004-03-15 devnull }
374 3d77c87e 2004-03-15 devnull if(istmp)
375 3d77c87e 2004-03-15 devnull e.flags |= VtEntryNoArchive;
376 3d77c87e 2004-03-15 devnull else
377 3d77c87e 2004-03-15 devnull e.flags &= ~VtEntryNoArchive;
378 3d77c87e 2004-03-15 devnull if(vtfilesetentry(r, &e) < 0){
379 3d77c87e 2004-03-15 devnull fprint(2, "vtfilesetentry failed (cannot happen): %r\n");
380 3d77c87e 2004-03-15 devnull continue;
381 3d77c87e 2004-03-15 devnull }
382 3d77c87e 2004-03-15 devnull }
383 3d77c87e 2004-03-15 devnull }
384 3d77c87e 2004-03-15 devnull #endif
385 3d77c87e 2004-03-15 devnull
386 3d77c87e 2004-03-15 devnull VacFile*
387 3d77c87e 2004-03-15 devnull vacfilecreate(VacFile *f, char *elem, ulong mode, char *uid)
388 3d77c87e 2004-03-15 devnull {
389 3d77c87e 2004-03-15 devnull VacFile *ff;
390 7763a61a 2003-11-23 devnull VacDir *dir;
391 3d77c87e 2004-03-15 devnull VtFile *pr, *r, *mr;
392 7763a61a 2003-11-23 devnull int isdir;
393 7763a61a 2003-11-23 devnull
394 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
395 7763a61a 2003-11-23 devnull return nil;
396 7763a61a 2003-11-23 devnull
397 7763a61a 2003-11-23 devnull r = nil;
398 7763a61a 2003-11-23 devnull mr = nil;
399 3d77c87e 2004-03-15 devnull for(ff = f->down; ff; ff=ff->next){
400 3d77c87e 2004-03-15 devnull if(strcmp(elem, ff->dir.elem) == 0 && !ff->removed){
401 3d77c87e 2004-03-15 devnull ff = nil;
402 3d77c87e 2004-03-15 devnull werrstr(EExists);
403 3d77c87e 2004-03-15 devnull goto Err1;
404 7763a61a 2003-11-23 devnull }
405 7763a61a 2003-11-23 devnull }
406 7763a61a 2003-11-23 devnull
407 3d77c87e 2004-03-15 devnull ff = dirlookup(f, elem);
408 3d77c87e 2004-03-15 devnull if(ff != nil){
409 3d77c87e 2004-03-15 devnull werrstr(EExists);
410 3d77c87e 2004-03-15 devnull goto Err1;
411 7763a61a 2003-11-23 devnull }
412 7763a61a 2003-11-23 devnull
413 3d77c87e 2004-03-15 devnull pr = f->source;
414 3d77c87e 2004-03-15 devnull if(pr->mode != VtORDWR){
415 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
416 3d77c87e 2004-03-15 devnull goto Err1;
417 3d77c87e 2004-03-15 devnull }
418 3d77c87e 2004-03-15 devnull
419 3d77c87e 2004-03-15 devnull if(vtfilelock2(f->source, f->msource, -1) < 0)
420 3d77c87e 2004-03-15 devnull goto Err1;
421 3d77c87e 2004-03-15 devnull
422 3d77c87e 2004-03-15 devnull ff = filealloc(f->fs);
423 7763a61a 2003-11-23 devnull isdir = mode & ModeDir;
424 7763a61a 2003-11-23 devnull
425 3d77c87e 2004-03-15 devnull r = vtfilecreate(pr, pr->dsize, isdir, 0);
426 7763a61a 2003-11-23 devnull if(r == nil)
427 7763a61a 2003-11-23 devnull goto Err;
428 3d77c87e 2004-03-15 devnull if(isdir){
429 3d77c87e 2004-03-15 devnull mr = vtfilecreate(pr, pr->dsize, 0, r->offset);
430 7763a61a 2003-11-23 devnull if(mr == nil)
431 7763a61a 2003-11-23 devnull goto Err;
432 7763a61a 2003-11-23 devnull }
433 3d77c87e 2004-03-15 devnull
434 3d77c87e 2004-03-15 devnull dir = &ff->dir;
435 3d77c87e 2004-03-15 devnull dir->elem = vtstrdup(elem);
436 3d77c87e 2004-03-15 devnull dir->entry = r->offset;
437 7763a61a 2003-11-23 devnull dir->gen = r->gen;
438 3d77c87e 2004-03-15 devnull if(isdir){
439 3d77c87e 2004-03-15 devnull dir->mentry = mr->offset;
440 7763a61a 2003-11-23 devnull dir->mgen = mr->gen;
441 7763a61a 2003-11-23 devnull }
442 7763a61a 2003-11-23 devnull dir->size = 0;
443 3d77c87e 2004-03-15 devnull if(_vacfsnextqid(f->fs, &dir->qid) < 0)
444 3d77c87e 2004-03-15 devnull goto Err;
445 3d77c87e 2004-03-15 devnull dir->uid = vtstrdup(uid);
446 3d77c87e 2004-03-15 devnull dir->gid = vtstrdup(f->dir.gid);
447 3d77c87e 2004-03-15 devnull dir->mid = vtstrdup(uid);
448 7763a61a 2003-11-23 devnull dir->mtime = time(0L);
449 7763a61a 2003-11-23 devnull dir->mcount = 0;
450 7763a61a 2003-11-23 devnull dir->ctime = dir->mtime;
451 7763a61a 2003-11-23 devnull dir->atime = dir->mtime;
452 7763a61a 2003-11-23 devnull dir->mode = mode;
453 7763a61a 2003-11-23 devnull
454 3d77c87e 2004-03-15 devnull ff->boff = filemetaalloc(f, dir, 0);
455 3d77c87e 2004-03-15 devnull if(ff->boff == NilBlock)
456 7763a61a 2003-11-23 devnull goto Err;
457 7763a61a 2003-11-23 devnull
458 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
459 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
460 7763a61a 2003-11-23 devnull
461 3d77c87e 2004-03-15 devnull ff->source = r;
462 3d77c87e 2004-03-15 devnull ff->msource = mr;
463 7763a61a 2003-11-23 devnull
464 3d77c87e 2004-03-15 devnull #if 0
465 3d77c87e 2004-03-15 devnull if(mode&ModeTemporary){
466 3d77c87e 2004-03-15 devnull if(vtfilelock2(r, mr, -1) < 0)
467 3d77c87e 2004-03-15 devnull goto Err1;
468 3d77c87e 2004-03-15 devnull filesettmp(ff, 1);
469 3d77c87e 2004-03-15 devnull vtfileunlock(r);
470 3d77c87e 2004-03-15 devnull if(mr)
471 3d77c87e 2004-03-15 devnull vtfileunlock(mr);
472 3d77c87e 2004-03-15 devnull }
473 3d77c87e 2004-03-15 devnull #endif
474 3d77c87e 2004-03-15 devnull
475 3d77c87e 2004-03-15 devnull /* committed */
476 3d77c87e 2004-03-15 devnull
477 7763a61a 2003-11-23 devnull /* link in and up parent ref count */
478 3d77c87e 2004-03-15 devnull ff->next = f->down;
479 3d77c87e 2004-03-15 devnull f->down = ff;
480 3d77c87e 2004-03-15 devnull ff->up = f;
481 3d77c87e 2004-03-15 devnull vacfileincref(f);
482 7763a61a 2003-11-23 devnull
483 3d77c87e 2004-03-15 devnull filewaccess(f, uid);
484 7763a61a 2003-11-23 devnull
485 3d77c87e 2004-03-15 devnull fileunlock(f);
486 3d77c87e 2004-03-15 devnull return ff;
487 7763a61a 2003-11-23 devnull
488 7763a61a 2003-11-23 devnull Err:
489 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
490 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
491 3d77c87e 2004-03-15 devnull Err1:
492 3d77c87e 2004-03-15 devnull if(r){
493 3d77c87e 2004-03-15 devnull vtfilelock(r, -1);
494 3d77c87e 2004-03-15 devnull vtfileremove(r);
495 3d77c87e 2004-03-15 devnull }
496 3d77c87e 2004-03-15 devnull if(mr){
497 3d77c87e 2004-03-15 devnull vtfilelock(mr, -1);
498 3d77c87e 2004-03-15 devnull vtfileremove(mr);
499 3d77c87e 2004-03-15 devnull }
500 3d77c87e 2004-03-15 devnull if(ff)
501 3d77c87e 2004-03-15 devnull vacfiledecref(ff);
502 3d77c87e 2004-03-15 devnull fileunlock(f);
503 3d77c87e 2004-03-15 devnull return nil;
504 7763a61a 2003-11-23 devnull }
505 7763a61a 2003-11-23 devnull
506 7763a61a 2003-11-23 devnull int
507 3d77c87e 2004-03-15 devnull vacfileblockscore(VacFile *f, u32int bn, u8int *score)
508 7763a61a 2003-11-23 devnull {
509 3d77c87e 2004-03-15 devnull VtFile *s;
510 7763a61a 2003-11-23 devnull uvlong size;
511 3d77c87e 2004-03-15 devnull int dsize, ret;
512 3d77c87e 2004-03-15 devnull
513 3d77c87e 2004-03-15 devnull ret = -1;
514 3d77c87e 2004-03-15 devnull if(filerlock(f) < 0)
515 3d77c87e 2004-03-15 devnull return -1;
516 3d77c87e 2004-03-15 devnull fileraccess(f);
517 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, VtOREAD) < 0)
518 3d77c87e 2004-03-15 devnull goto out;
519 3d77c87e 2004-03-15 devnull
520 3d77c87e 2004-03-15 devnull s = f->source;
521 3d77c87e 2004-03-15 devnull dsize = s->dsize;
522 3d77c87e 2004-03-15 devnull size = vtfilegetsize(s);
523 3d77c87e 2004-03-15 devnull if((uvlong)bn*dsize >= size)
524 3d77c87e 2004-03-15 devnull goto out;
525 3d77c87e 2004-03-15 devnull ret = vtfileblockscore(f->source, bn, score);
526 3d77c87e 2004-03-15 devnull
527 3d77c87e 2004-03-15 devnull out:
528 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
529 3d77c87e 2004-03-15 devnull filerunlock(f);
530 3d77c87e 2004-03-15 devnull return ret;
531 3d77c87e 2004-03-15 devnull }
532 3d77c87e 2004-03-15 devnull
533 3d77c87e 2004-03-15 devnull int
534 3d77c87e 2004-03-15 devnull vacfileread(VacFile *f, void *buf, int cnt, vlong offset)
535 3d77c87e 2004-03-15 devnull {
536 3d77c87e 2004-03-15 devnull VtFile *s;
537 3d77c87e 2004-03-15 devnull uvlong size;
538 3d77c87e 2004-03-15 devnull u32int bn;
539 7763a61a 2003-11-23 devnull int off, dsize, n, nn;
540 3d77c87e 2004-03-15 devnull VtBlock *b;
541 3d77c87e 2004-03-15 devnull uchar *p;
542 7763a61a 2003-11-23 devnull
543 3d77c87e 2004-03-15 devnull if(0)fprint(2, "fileRead: %s %d, %lld\n", f->dir.elem, cnt, offset);
544 7763a61a 2003-11-23 devnull
545 3d77c87e 2004-03-15 devnull if(filerlock(f) < 0)
546 7763a61a 2003-11-23 devnull return -1;
547 7763a61a 2003-11-23 devnull
548 3d77c87e 2004-03-15 devnull if(offset < 0){
549 3d77c87e 2004-03-15 devnull werrstr(EBadOffset);
550 3d77c87e 2004-03-15 devnull goto Err1;
551 3d77c87e 2004-03-15 devnull }
552 7763a61a 2003-11-23 devnull
553 3d77c87e 2004-03-15 devnull fileraccess(f);
554 7763a61a 2003-11-23 devnull
555 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, VtOREAD) < 0)
556 3d77c87e 2004-03-15 devnull goto Err1;
557 7763a61a 2003-11-23 devnull
558 3d77c87e 2004-03-15 devnull s = f->source;
559 3d77c87e 2004-03-15 devnull dsize = s->dsize;
560 3d77c87e 2004-03-15 devnull size = vtfilegetsize(s);
561 7763a61a 2003-11-23 devnull
562 7763a61a 2003-11-23 devnull if(offset >= size)
563 7763a61a 2003-11-23 devnull offset = size;
564 7763a61a 2003-11-23 devnull
565 7763a61a 2003-11-23 devnull if(cnt > size-offset)
566 7763a61a 2003-11-23 devnull cnt = size-offset;
567 7763a61a 2003-11-23 devnull bn = offset/dsize;
568 7763a61a 2003-11-23 devnull off = offset%dsize;
569 3d77c87e 2004-03-15 devnull p = buf;
570 3d77c87e 2004-03-15 devnull while(cnt > 0){
571 3d77c87e 2004-03-15 devnull b = vtfileblock(s, bn, OREAD);
572 3d77c87e 2004-03-15 devnull if(b == nil)
573 7763a61a 2003-11-23 devnull goto Err;
574 7763a61a 2003-11-23 devnull n = cnt;
575 7763a61a 2003-11-23 devnull if(n > dsize-off)
576 7763a61a 2003-11-23 devnull n = dsize-off;
577 3d77c87e 2004-03-15 devnull nn = dsize-off;
578 7763a61a 2003-11-23 devnull if(nn > n)
579 7763a61a 2003-11-23 devnull nn = n;
580 3d77c87e 2004-03-15 devnull memmove(p, b->data+off, nn);
581 3d77c87e 2004-03-15 devnull memset(p+nn, 0, nn-n);
582 7763a61a 2003-11-23 devnull off = 0;
583 7763a61a 2003-11-23 devnull bn++;
584 7763a61a 2003-11-23 devnull cnt -= n;
585 3d77c87e 2004-03-15 devnull p += n;
586 3d77c87e 2004-03-15 devnull vtblockput(b);
587 7763a61a 2003-11-23 devnull }
588 3d77c87e 2004-03-15 devnull vtfileunlock(s);
589 3d77c87e 2004-03-15 devnull filerunlock(f);
590 3d77c87e 2004-03-15 devnull return p-(uchar*)buf;
591 3d77c87e 2004-03-15 devnull
592 7763a61a 2003-11-23 devnull Err:
593 3d77c87e 2004-03-15 devnull vtfileunlock(s);
594 3d77c87e 2004-03-15 devnull Err1:
595 3d77c87e 2004-03-15 devnull filerunlock(f);
596 7763a61a 2003-11-23 devnull return -1;
597 7763a61a 2003-11-23 devnull }
598 7763a61a 2003-11-23 devnull
599 3d77c87e 2004-03-15 devnull #if 0
600 3d77c87e 2004-03-15 devnull /*
601 3d77c87e 2004-03-15 devnull * Changes the file block bn to be the given block score.
602 3d77c87e 2004-03-15 devnull * Very sneaky. Only used by flfmt.
603 3d77c87e 2004-03-15 devnull */
604 7763a61a 2003-11-23 devnull int
605 3d77c87e 2004-03-15 devnull filemapblock(VacFile *f, ulong bn, uchar score[VtScoreSize], ulong tag)
606 7763a61a 2003-11-23 devnull {
607 3d77c87e 2004-03-15 devnull VtBlock *b;
608 3d77c87e 2004-03-15 devnull VtEntry e;
609 3d77c87e 2004-03-15 devnull VtFile *s;
610 7763a61a 2003-11-23 devnull
611 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
612 7763a61a 2003-11-23 devnull return -1;
613 7763a61a 2003-11-23 devnull
614 3d77c87e 2004-03-15 devnull s = nil;
615 3d77c87e 2004-03-15 devnull if(f->dir.mode & ModeDir){
616 3d77c87e 2004-03-15 devnull werrstr(ENotFile);
617 7763a61a 2003-11-23 devnull goto Err;
618 7763a61a 2003-11-23 devnull }
619 7763a61a 2003-11-23 devnull
620 3d77c87e 2004-03-15 devnull if(f->source->mode != VtORDWR){
621 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
622 7763a61a 2003-11-23 devnull goto Err;
623 7763a61a 2003-11-23 devnull }
624 7763a61a 2003-11-23 devnull
625 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, -1) < 0)
626 3d77c87e 2004-03-15 devnull goto Err;
627 7763a61a 2003-11-23 devnull
628 3d77c87e 2004-03-15 devnull s = f->source;
629 3d77c87e 2004-03-15 devnull b = _vtfileblock(s, bn, VtORDWR, 1, tag);
630 3d77c87e 2004-03-15 devnull if(b == nil)
631 7763a61a 2003-11-23 devnull goto Err;
632 7763a61a 2003-11-23 devnull
633 3d77c87e 2004-03-15 devnull if(vtfilegetentry(s, &e) < 0)
634 3d77c87e 2004-03-15 devnull goto Err;
635 3d77c87e 2004-03-15 devnull if(b->l.type == BtDir){
636 3d77c87e 2004-03-15 devnull memmove(e.score, score, VtScoreSize);
637 3d77c87e 2004-03-15 devnull assert(e.tag == tag || e.tag == 0);
638 3d77c87e 2004-03-15 devnull e.tag = tag;
639 3d77c87e 2004-03-15 devnull e.flags |= VtEntryLocal;
640 3d77c87e 2004-03-15 devnull vtentrypack(&e, b->data, f->source->offset % f->source->epb);
641 3d77c87e 2004-03-15 devnull }else
642 3d77c87e 2004-03-15 devnull memmove(b->data + (bn%(e.psize/VtScoreSize))*VtScoreSize, score, VtScoreSize);
643 3d77c87e 2004-03-15 devnull vtblockdirty(b);
644 3d77c87e 2004-03-15 devnull vtblockput(b);
645 3d77c87e 2004-03-15 devnull vtfileunlock(s);
646 3d77c87e 2004-03-15 devnull fileunlock(f);
647 3d77c87e 2004-03-15 devnull return 0;
648 7763a61a 2003-11-23 devnull
649 7763a61a 2003-11-23 devnull Err:
650 3d77c87e 2004-03-15 devnull if(s)
651 3d77c87e 2004-03-15 devnull vtfileunlock(s);
652 3d77c87e 2004-03-15 devnull fileunlock(f);
653 7763a61a 2003-11-23 devnull return -1;
654 7763a61a 2003-11-23 devnull }
655 3d77c87e 2004-03-15 devnull #endif
656 7763a61a 2003-11-23 devnull
657 7763a61a 2003-11-23 devnull int
658 3d77c87e 2004-03-15 devnull vacfilesetsize(VacFile *f, uvlong size)
659 7763a61a 2003-11-23 devnull {
660 3d77c87e 2004-03-15 devnull int r;
661 7763a61a 2003-11-23 devnull
662 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
663 3d77c87e 2004-03-15 devnull return -1;
664 3d77c87e 2004-03-15 devnull r = 0;
665 3d77c87e 2004-03-15 devnull if(f->dir.mode & ModeDir){
666 3d77c87e 2004-03-15 devnull werrstr(ENotFile);
667 3d77c87e 2004-03-15 devnull goto Err;
668 3d77c87e 2004-03-15 devnull }
669 3d77c87e 2004-03-15 devnull if(f->source->mode != VtORDWR){
670 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
671 3d77c87e 2004-03-15 devnull goto Err;
672 3d77c87e 2004-03-15 devnull }
673 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, -1) < 0)
674 3d77c87e 2004-03-15 devnull goto Err;
675 3d77c87e 2004-03-15 devnull r = vtfilesetsize(f->source, size);
676 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
677 3d77c87e 2004-03-15 devnull Err:
678 3d77c87e 2004-03-15 devnull fileunlock(f);
679 3d77c87e 2004-03-15 devnull return r;
680 7763a61a 2003-11-23 devnull }
681 7763a61a 2003-11-23 devnull
682 3d77c87e 2004-03-15 devnull int
683 3d77c87e 2004-03-15 devnull filewrite(VacFile *f, void *buf, int cnt, vlong offset, char *uid)
684 7763a61a 2003-11-23 devnull {
685 3d77c87e 2004-03-15 devnull VtFile *s;
686 3d77c87e 2004-03-15 devnull ulong bn;
687 3d77c87e 2004-03-15 devnull int off, dsize, n;
688 3d77c87e 2004-03-15 devnull VtBlock *b;
689 3d77c87e 2004-03-15 devnull uchar *p;
690 3d77c87e 2004-03-15 devnull vlong eof;
691 7763a61a 2003-11-23 devnull
692 3d77c87e 2004-03-15 devnull if(0)fprint(2, "fileWrite: %s %d, %lld\n", f->dir.elem, cnt, offset);
693 7763a61a 2003-11-23 devnull
694 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
695 3d77c87e 2004-03-15 devnull return -1;
696 3d77c87e 2004-03-15 devnull
697 3d77c87e 2004-03-15 devnull s = nil;
698 3d77c87e 2004-03-15 devnull if(f->dir.mode & ModeDir){
699 3d77c87e 2004-03-15 devnull werrstr(ENotFile);
700 3d77c87e 2004-03-15 devnull goto Err;
701 3d77c87e 2004-03-15 devnull }
702 3d77c87e 2004-03-15 devnull
703 3d77c87e 2004-03-15 devnull if(f->source->mode != VtORDWR){
704 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
705 3d77c87e 2004-03-15 devnull goto Err;
706 3d77c87e 2004-03-15 devnull }
707 3d77c87e 2004-03-15 devnull if(offset < 0){
708 3d77c87e 2004-03-15 devnull werrstr(EBadOffset);
709 3d77c87e 2004-03-15 devnull goto Err;
710 3d77c87e 2004-03-15 devnull }
711 3d77c87e 2004-03-15 devnull
712 3d77c87e 2004-03-15 devnull filewaccess(f, uid);
713 3d77c87e 2004-03-15 devnull
714 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, -1) < 0)
715 3d77c87e 2004-03-15 devnull goto Err;
716 3d77c87e 2004-03-15 devnull s = f->source;
717 3d77c87e 2004-03-15 devnull dsize = s->dsize;
718 3d77c87e 2004-03-15 devnull
719 3d77c87e 2004-03-15 devnull eof = vtfilegetsize(s);
720 3d77c87e 2004-03-15 devnull if(f->dir.mode & ModeAppend)
721 3d77c87e 2004-03-15 devnull offset = eof;
722 3d77c87e 2004-03-15 devnull bn = offset/dsize;
723 3d77c87e 2004-03-15 devnull off = offset%dsize;
724 3d77c87e 2004-03-15 devnull p = buf;
725 3d77c87e 2004-03-15 devnull while(cnt > 0){
726 3d77c87e 2004-03-15 devnull n = cnt;
727 3d77c87e 2004-03-15 devnull if(n > dsize-off)
728 3d77c87e 2004-03-15 devnull n = dsize-off;
729 3d77c87e 2004-03-15 devnull b = vtfileblock(s, bn, n<dsize?VtORDWR:VtOWRITE);
730 3d77c87e 2004-03-15 devnull if(b == nil){
731 3d77c87e 2004-03-15 devnull if(offset > eof)
732 3d77c87e 2004-03-15 devnull vtfilesetsize(s, offset);
733 3d77c87e 2004-03-15 devnull goto Err;
734 3d77c87e 2004-03-15 devnull }
735 3d77c87e 2004-03-15 devnull memmove(b->data+off, p, n);
736 3d77c87e 2004-03-15 devnull off = 0;
737 3d77c87e 2004-03-15 devnull cnt -= n;
738 3d77c87e 2004-03-15 devnull p += n;
739 3d77c87e 2004-03-15 devnull offset += n;
740 3d77c87e 2004-03-15 devnull bn++;
741 3d77c87e 2004-03-15 devnull vtblockdirty(b);
742 3d77c87e 2004-03-15 devnull vtblockput(b);
743 3d77c87e 2004-03-15 devnull }
744 3d77c87e 2004-03-15 devnull if(offset > eof && vtfilesetsize(s, offset) < 0)
745 3d77c87e 2004-03-15 devnull goto Err;
746 3d77c87e 2004-03-15 devnull vtfileunlock(s);
747 3d77c87e 2004-03-15 devnull fileunlock(f);
748 3d77c87e 2004-03-15 devnull return p-(uchar*)buf;
749 3d77c87e 2004-03-15 devnull Err:
750 3d77c87e 2004-03-15 devnull if(s)
751 3d77c87e 2004-03-15 devnull vtfileunlock(s);
752 3d77c87e 2004-03-15 devnull fileunlock(f);
753 3d77c87e 2004-03-15 devnull return -1;
754 7763a61a 2003-11-23 devnull }
755 7763a61a 2003-11-23 devnull
756 7763a61a 2003-11-23 devnull int
757 3d77c87e 2004-03-15 devnull vacfilegetdir(VacFile *f, VacDir *dir)
758 7763a61a 2003-11-23 devnull {
759 3d77c87e 2004-03-15 devnull if(filerlock(f) < 0)
760 3d77c87e 2004-03-15 devnull return -1;
761 3d77c87e 2004-03-15 devnull
762 3d77c87e 2004-03-15 devnull filemetalock(f);
763 3d77c87e 2004-03-15 devnull vdcopy(dir, &f->dir);
764 3d77c87e 2004-03-15 devnull filemetaunlock(f);
765 3d77c87e 2004-03-15 devnull
766 3d77c87e 2004-03-15 devnull if(vacfileisdir(f) < 0){
767 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, VtOREAD) < 0){
768 3d77c87e 2004-03-15 devnull filerunlock(f);
769 3d77c87e 2004-03-15 devnull return -1;
770 3d77c87e 2004-03-15 devnull }
771 3d77c87e 2004-03-15 devnull dir->size = vtfilegetsize(f->source);
772 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
773 3d77c87e 2004-03-15 devnull }
774 3d77c87e 2004-03-15 devnull filerunlock(f);
775 3d77c87e 2004-03-15 devnull
776 3d77c87e 2004-03-15 devnull return 0;
777 7763a61a 2003-11-23 devnull }
778 7763a61a 2003-11-23 devnull
779 7763a61a 2003-11-23 devnull int
780 3d77c87e 2004-03-15 devnull vacfiletruncate(VacFile *f, char *uid)
781 7763a61a 2003-11-23 devnull {
782 3d77c87e 2004-03-15 devnull if(vacfileisdir(f)){
783 3d77c87e 2004-03-15 devnull werrstr(ENotFile);
784 3d77c87e 2004-03-15 devnull return -1;
785 3d77c87e 2004-03-15 devnull }
786 7763a61a 2003-11-23 devnull
787 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
788 3d77c87e 2004-03-15 devnull return -1;
789 3d77c87e 2004-03-15 devnull
790 3d77c87e 2004-03-15 devnull if(f->source->mode != VtORDWR){
791 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
792 3d77c87e 2004-03-15 devnull fileunlock(f);
793 3d77c87e 2004-03-15 devnull return -1;
794 3d77c87e 2004-03-15 devnull }
795 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, -1) < 0){
796 3d77c87e 2004-03-15 devnull fileunlock(f);
797 3d77c87e 2004-03-15 devnull return -1;
798 3d77c87e 2004-03-15 devnull }
799 3d77c87e 2004-03-15 devnull if(vtfiletruncate(f->source) < 0){
800 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
801 3d77c87e 2004-03-15 devnull fileunlock(f);
802 3d77c87e 2004-03-15 devnull return -1;
803 3d77c87e 2004-03-15 devnull }
804 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
805 3d77c87e 2004-03-15 devnull fileunlock(f);
806 3d77c87e 2004-03-15 devnull
807 3d77c87e 2004-03-15 devnull filewaccess(f, uid);
808 3d77c87e 2004-03-15 devnull
809 3d77c87e 2004-03-15 devnull return 0;
810 7763a61a 2003-11-23 devnull }
811 7763a61a 2003-11-23 devnull
812 3d77c87e 2004-03-15 devnull int
813 3d77c87e 2004-03-15 devnull vacfilesetdir(VacFile *f, VacDir *dir, char *uid)
814 7763a61a 2003-11-23 devnull {
815 3d77c87e 2004-03-15 devnull VacFile *ff;
816 3d77c87e 2004-03-15 devnull char *oelem;
817 3d77c87e 2004-03-15 devnull u32int mask;
818 3d77c87e 2004-03-15 devnull u64int size;
819 7763a61a 2003-11-23 devnull
820 3d77c87e 2004-03-15 devnull /* can not set permissions for the root */
821 3d77c87e 2004-03-15 devnull if(vacfileisroot(f)){
822 3d77c87e 2004-03-15 devnull werrstr(ERoot);
823 3d77c87e 2004-03-15 devnull return -1;
824 3d77c87e 2004-03-15 devnull }
825 7763a61a 2003-11-23 devnull
826 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
827 3d77c87e 2004-03-15 devnull return -1;
828 7763a61a 2003-11-23 devnull
829 3d77c87e 2004-03-15 devnull if(f->source->mode != VtORDWR){
830 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
831 3d77c87e 2004-03-15 devnull fileunlock(f);
832 3d77c87e 2004-03-15 devnull return -1;
833 3d77c87e 2004-03-15 devnull }
834 7763a61a 2003-11-23 devnull
835 3d77c87e 2004-03-15 devnull filemetalock(f);
836 7763a61a 2003-11-23 devnull
837 3d77c87e 2004-03-15 devnull /* check new name does not already exist */
838 3d77c87e 2004-03-15 devnull if(strcmp(f->dir.elem, dir->elem) != 0){
839 3d77c87e 2004-03-15 devnull for(ff = f->up->down; ff; ff=ff->next){
840 3d77c87e 2004-03-15 devnull if(strcmp(dir->elem, ff->dir.elem) == 0 && !ff->removed){
841 3d77c87e 2004-03-15 devnull werrstr(EExists);
842 3d77c87e 2004-03-15 devnull goto Err;
843 3d77c87e 2004-03-15 devnull }
844 3d77c87e 2004-03-15 devnull }
845 3d77c87e 2004-03-15 devnull
846 3d77c87e 2004-03-15 devnull ff = dirlookup(f->up, dir->elem);
847 3d77c87e 2004-03-15 devnull if(ff != nil){
848 3d77c87e 2004-03-15 devnull vacfiledecref(ff);
849 3d77c87e 2004-03-15 devnull werrstr(EExists);
850 3d77c87e 2004-03-15 devnull goto Err;
851 3d77c87e 2004-03-15 devnull }
852 3d77c87e 2004-03-15 devnull }
853 3d77c87e 2004-03-15 devnull
854 3d77c87e 2004-03-15 devnull if(vtfilelock2(f->source, f->msource, -1) < 0)
855 7763a61a 2003-11-23 devnull goto Err;
856 3d77c87e 2004-03-15 devnull if(!vacfileisdir(f)){
857 3d77c87e 2004-03-15 devnull size = vtfilegetsize(f->source);
858 3d77c87e 2004-03-15 devnull if(size != dir->size){
859 3d77c87e 2004-03-15 devnull if(vtfilesetsize(f->source, dir->size) < 0){
860 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
861 3d77c87e 2004-03-15 devnull if(f->msource)
862 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
863 3d77c87e 2004-03-15 devnull goto Err;
864 3d77c87e 2004-03-15 devnull }
865 3d77c87e 2004-03-15 devnull /* commited to changing it now */
866 3d77c87e 2004-03-15 devnull }
867 3d77c87e 2004-03-15 devnull }
868 3d77c87e 2004-03-15 devnull /* commited to changing it now */
869 3d77c87e 2004-03-15 devnull #if 0
870 3d77c87e 2004-03-15 devnull if((f->dir.mode&ModeTemporary) != (dir->mode&ModeTemporary))
871 3d77c87e 2004-03-15 devnull filesettmp(f, dir->mode&ModeTemporary);
872 3d77c87e 2004-03-15 devnull #endif
873 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
874 3d77c87e 2004-03-15 devnull if(f->msource)
875 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
876 7763a61a 2003-11-23 devnull
877 3d77c87e 2004-03-15 devnull oelem = nil;
878 3d77c87e 2004-03-15 devnull if(strcmp(f->dir.elem, dir->elem) != 0){
879 3d77c87e 2004-03-15 devnull oelem = f->dir.elem;
880 3d77c87e 2004-03-15 devnull f->dir.elem = vtstrdup(dir->elem);
881 3d77c87e 2004-03-15 devnull }
882 7763a61a 2003-11-23 devnull
883 3d77c87e 2004-03-15 devnull if(strcmp(f->dir.uid, dir->uid) != 0){
884 3d77c87e 2004-03-15 devnull vtfree(f->dir.uid);
885 3d77c87e 2004-03-15 devnull f->dir.uid = vtstrdup(dir->uid);
886 3d77c87e 2004-03-15 devnull }
887 3d77c87e 2004-03-15 devnull
888 3d77c87e 2004-03-15 devnull if(strcmp(f->dir.gid, dir->gid) != 0){
889 3d77c87e 2004-03-15 devnull vtfree(f->dir.gid);
890 3d77c87e 2004-03-15 devnull f->dir.gid = vtstrdup(dir->gid);
891 3d77c87e 2004-03-15 devnull }
892 3d77c87e 2004-03-15 devnull
893 3d77c87e 2004-03-15 devnull f->dir.mtime = dir->mtime;
894 3d77c87e 2004-03-15 devnull f->dir.atime = dir->atime;
895 3d77c87e 2004-03-15 devnull
896 3d77c87e 2004-03-15 devnull //fprint(2, "mode %x %x ", f->dir.mode, dir->mode);
897 3d77c87e 2004-03-15 devnull mask = ~(ModeDir|ModeSnapshot);
898 3d77c87e 2004-03-15 devnull f->dir.mode &= ~mask;
899 3d77c87e 2004-03-15 devnull f->dir.mode |= mask & dir->mode;
900 3d77c87e 2004-03-15 devnull f->dirty = 1;
901 3d77c87e 2004-03-15 devnull //fprint(2, "->%x\n", f->dir.mode);
902 3d77c87e 2004-03-15 devnull
903 3d77c87e 2004-03-15 devnull filemetaflush2(f, oelem);
904 3d77c87e 2004-03-15 devnull vtfree(oelem);
905 3d77c87e 2004-03-15 devnull
906 3d77c87e 2004-03-15 devnull filemetaunlock(f);
907 3d77c87e 2004-03-15 devnull fileunlock(f);
908 3d77c87e 2004-03-15 devnull
909 3d77c87e 2004-03-15 devnull filewaccess(f->up, uid);
910 3d77c87e 2004-03-15 devnull
911 7763a61a 2003-11-23 devnull return 0;
912 3d77c87e 2004-03-15 devnull Err:
913 3d77c87e 2004-03-15 devnull filemetaunlock(f);
914 3d77c87e 2004-03-15 devnull fileunlock(f);
915 3d77c87e 2004-03-15 devnull return -1;
916 7763a61a 2003-11-23 devnull }
917 7763a61a 2003-11-23 devnull
918 3d77c87e 2004-03-15 devnull int
919 3d77c87e 2004-03-15 devnull vacfilesetqidspace(VacFile *f, u64int offset, u64int max)
920 3d77c87e 2004-03-15 devnull {
921 3d77c87e 2004-03-15 devnull int ret;
922 7763a61a 2003-11-23 devnull
923 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
924 3d77c87e 2004-03-15 devnull return -1;
925 3d77c87e 2004-03-15 devnull filemetalock(f);
926 3d77c87e 2004-03-15 devnull f->dir.qidspace = 1;
927 3d77c87e 2004-03-15 devnull f->dir.qidoffset = offset;
928 3d77c87e 2004-03-15 devnull f->dir.qidmax = max;
929 3d77c87e 2004-03-15 devnull ret = filemetaflush2(f, nil);
930 3d77c87e 2004-03-15 devnull filemetaunlock(f);
931 3d77c87e 2004-03-15 devnull fileunlock(f);
932 3d77c87e 2004-03-15 devnull return ret;
933 3d77c87e 2004-03-15 devnull }
934 3d77c87e 2004-03-15 devnull
935 3d77c87e 2004-03-15 devnull uvlong
936 3d77c87e 2004-03-15 devnull vacfilegetid(VacFile *f)
937 7763a61a 2003-11-23 devnull {
938 3d77c87e 2004-03-15 devnull /* immutable */
939 3d77c87e 2004-03-15 devnull return f->dir.qid;
940 3d77c87e 2004-03-15 devnull }
941 7763a61a 2003-11-23 devnull
942 3d77c87e 2004-03-15 devnull ulong
943 3d77c87e 2004-03-15 devnull vacfilegetmcount(VacFile *f)
944 3d77c87e 2004-03-15 devnull {
945 3d77c87e 2004-03-15 devnull ulong mcount;
946 3d77c87e 2004-03-15 devnull
947 3d77c87e 2004-03-15 devnull filemetalock(f);
948 3d77c87e 2004-03-15 devnull mcount = f->dir.mcount;
949 3d77c87e 2004-03-15 devnull filemetaunlock(f);
950 3d77c87e 2004-03-15 devnull return mcount;
951 3d77c87e 2004-03-15 devnull }
952 3d77c87e 2004-03-15 devnull
953 3d77c87e 2004-03-15 devnull ulong
954 3d77c87e 2004-03-15 devnull vacfilegetmode(VacFile *f)
955 3d77c87e 2004-03-15 devnull {
956 3d77c87e 2004-03-15 devnull ulong mode;
957 3d77c87e 2004-03-15 devnull
958 3d77c87e 2004-03-15 devnull filemetalock(f);
959 3d77c87e 2004-03-15 devnull mode = f->dir.mode;
960 3d77c87e 2004-03-15 devnull filemetaunlock(f);
961 3d77c87e 2004-03-15 devnull return mode;
962 3d77c87e 2004-03-15 devnull }
963 3d77c87e 2004-03-15 devnull
964 3d77c87e 2004-03-15 devnull int
965 3d77c87e 2004-03-15 devnull vacfileisdir(VacFile *f)
966 3d77c87e 2004-03-15 devnull {
967 3d77c87e 2004-03-15 devnull /* immutable */
968 3d77c87e 2004-03-15 devnull return (f->dir.mode & ModeDir) != 0;
969 3d77c87e 2004-03-15 devnull }
970 3d77c87e 2004-03-15 devnull
971 3d77c87e 2004-03-15 devnull int
972 3d77c87e 2004-03-15 devnull vacfileisroot(VacFile *f)
973 3d77c87e 2004-03-15 devnull {
974 3d77c87e 2004-03-15 devnull return f == f->fs->root;
975 3d77c87e 2004-03-15 devnull }
976 3d77c87e 2004-03-15 devnull
977 3d77c87e 2004-03-15 devnull int
978 3d77c87e 2004-03-15 devnull vacfilegetsize(VacFile *f, uvlong *size)
979 3d77c87e 2004-03-15 devnull {
980 3d77c87e 2004-03-15 devnull if(filerlock(f) < 0)
981 3d77c87e 2004-03-15 devnull return 0;
982 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, VtOREAD) < 0){
983 3d77c87e 2004-03-15 devnull filerunlock(f);
984 3d77c87e 2004-03-15 devnull return -1;
985 7763a61a 2003-11-23 devnull }
986 3d77c87e 2004-03-15 devnull *size = vtfilegetsize(f->source);
987 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
988 3d77c87e 2004-03-15 devnull filerunlock(f);
989 3d77c87e 2004-03-15 devnull
990 7763a61a 2003-11-23 devnull return 0;
991 7763a61a 2003-11-23 devnull }
992 7763a61a 2003-11-23 devnull
993 7763a61a 2003-11-23 devnull int
994 3d77c87e 2004-03-15 devnull vacfilegetvtentry(VacFile *f, VtEntry *e)
995 3d77c87e 2004-03-15 devnull {
996 3d77c87e 2004-03-15 devnull if(filerlock(f) < 0)
997 7763a61a 2003-11-23 devnull return 0;
998 3d77c87e 2004-03-15 devnull if(vtfilelock(f->source, VtOREAD) < 0){
999 3d77c87e 2004-03-15 devnull filerunlock(f);
1000 3d77c87e 2004-03-15 devnull return -1;
1001 7763a61a 2003-11-23 devnull }
1002 3d77c87e 2004-03-15 devnull vtfilegetentry(f->source, e);
1003 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
1004 3d77c87e 2004-03-15 devnull filerunlock(f);
1005 7763a61a 2003-11-23 devnull
1006 3d77c87e 2004-03-15 devnull return 0;
1007 3d77c87e 2004-03-15 devnull }
1008 3d77c87e 2004-03-15 devnull
1009 3d77c87e 2004-03-15 devnull void
1010 3d77c87e 2004-03-15 devnull vacfilemetaflush(VacFile *f, int rec)
1011 3d77c87e 2004-03-15 devnull {
1012 3d77c87e 2004-03-15 devnull VacFile **kids, *p;
1013 3d77c87e 2004-03-15 devnull int nkids;
1014 3d77c87e 2004-03-15 devnull int i;
1015 3d77c87e 2004-03-15 devnull
1016 3d77c87e 2004-03-15 devnull filemetalock(f);
1017 3d77c87e 2004-03-15 devnull filemetaflush2(f, nil);
1018 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1019 3d77c87e 2004-03-15 devnull
1020 3d77c87e 2004-03-15 devnull if(!rec || !vacfileisdir(f))
1021 3d77c87e 2004-03-15 devnull return;
1022 3d77c87e 2004-03-15 devnull
1023 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
1024 3d77c87e 2004-03-15 devnull return;
1025 3d77c87e 2004-03-15 devnull nkids = 0;
1026 3d77c87e 2004-03-15 devnull for(p=f->down; p; p=p->next)
1027 3d77c87e 2004-03-15 devnull nkids++;
1028 3d77c87e 2004-03-15 devnull kids = vtmalloc(nkids*sizeof(VacFile*));
1029 3d77c87e 2004-03-15 devnull i = 0;
1030 3d77c87e 2004-03-15 devnull for(p=f->down; p; p=p->next){
1031 3d77c87e 2004-03-15 devnull kids[i++] = p;
1032 3d77c87e 2004-03-15 devnull p->ref++;
1033 3d77c87e 2004-03-15 devnull }
1034 3d77c87e 2004-03-15 devnull fileunlock(f);
1035 3d77c87e 2004-03-15 devnull
1036 3d77c87e 2004-03-15 devnull for(i=0; i<nkids; i++){
1037 3d77c87e 2004-03-15 devnull vacfilemetaflush(kids[i], 1);
1038 3d77c87e 2004-03-15 devnull vacfiledecref(kids[i]);
1039 3d77c87e 2004-03-15 devnull }
1040 3d77c87e 2004-03-15 devnull vtfree(kids);
1041 3d77c87e 2004-03-15 devnull }
1042 3d77c87e 2004-03-15 devnull
1043 3d77c87e 2004-03-15 devnull /* assumes metaLock is held */
1044 3d77c87e 2004-03-15 devnull static int
1045 3d77c87e 2004-03-15 devnull filemetaflush2(VacFile *f, char *oelem)
1046 3d77c87e 2004-03-15 devnull {
1047 3d77c87e 2004-03-15 devnull VacFile *fp;
1048 3d77c87e 2004-03-15 devnull VtBlock *b, *bb;
1049 3d77c87e 2004-03-15 devnull MetaBlock mb;
1050 3d77c87e 2004-03-15 devnull MetaEntry me, me2;
1051 3d77c87e 2004-03-15 devnull int i, n;
1052 3d77c87e 2004-03-15 devnull u32int boff;
1053 3d77c87e 2004-03-15 devnull
1054 3d77c87e 2004-03-15 devnull if(!f->dirty)
1055 7763a61a 2003-11-23 devnull return 0;
1056 7763a61a 2003-11-23 devnull
1057 3d77c87e 2004-03-15 devnull if(oelem == nil)
1058 3d77c87e 2004-03-15 devnull oelem = f->dir.elem;
1059 3d77c87e 2004-03-15 devnull
1060 3d77c87e 2004-03-15 devnull fp = f->up;
1061 3d77c87e 2004-03-15 devnull
1062 3d77c87e 2004-03-15 devnull if(vtfilelock(fp->msource, -1) < 0)
1063 3d77c87e 2004-03-15 devnull return 0;
1064 3d77c87e 2004-03-15 devnull /* can happen if source is clri'ed out from under us */
1065 3d77c87e 2004-03-15 devnull if(f->boff == NilBlock)
1066 3d77c87e 2004-03-15 devnull goto Err1;
1067 3d77c87e 2004-03-15 devnull b = vtfileblock(fp->msource, f->boff, VtORDWR);
1068 3d77c87e 2004-03-15 devnull if(b == nil)
1069 3d77c87e 2004-03-15 devnull goto Err1;
1070 3d77c87e 2004-03-15 devnull
1071 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, fp->msource->dsize) < 0)
1072 7763a61a 2003-11-23 devnull goto Err;
1073 3d77c87e 2004-03-15 devnull if(mbsearch(&mb, oelem, &i, &me) < 0)
1074 3d77c87e 2004-03-15 devnull goto Err;
1075 7763a61a 2003-11-23 devnull
1076 3d77c87e 2004-03-15 devnull n = vdsize(&f->dir);
1077 3d77c87e 2004-03-15 devnull if(0)fprint(2, "old size %d new size %d\n", me.size, n);
1078 3d77c87e 2004-03-15 devnull
1079 3d77c87e 2004-03-15 devnull if(mbresize(&mb, &me, n) >= 0){
1080 3d77c87e 2004-03-15 devnull /* fits in the block */
1081 3d77c87e 2004-03-15 devnull mbdelete(&mb, i, &me);
1082 3d77c87e 2004-03-15 devnull if(strcmp(f->dir.elem, oelem) != 0)
1083 3d77c87e 2004-03-15 devnull mbsearch(&mb, f->dir.elem, &i, &me2);
1084 3d77c87e 2004-03-15 devnull vdpack(&f->dir, &me);
1085 3d77c87e 2004-03-15 devnull mbinsert(&mb, i, &me);
1086 3d77c87e 2004-03-15 devnull mbpack(&mb);
1087 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1088 3d77c87e 2004-03-15 devnull vtblockput(b);
1089 3d77c87e 2004-03-15 devnull vtfileunlock(fp->msource);
1090 3d77c87e 2004-03-15 devnull f->dirty = 0;
1091 3d77c87e 2004-03-15 devnull return -1;
1092 7763a61a 2003-11-23 devnull }
1093 3d77c87e 2004-03-15 devnull
1094 3d77c87e 2004-03-15 devnull /*
1095 3d77c87e 2004-03-15 devnull * moving entry to another block
1096 3d77c87e 2004-03-15 devnull * it is feasible for the fs to crash leaving two copies
1097 3d77c87e 2004-03-15 devnull * of the directory entry. This is just too much work to
1098 3d77c87e 2004-03-15 devnull * fix. Given that entries are only allocated in a block that
1099 3d77c87e 2004-03-15 devnull * is less than PercentageFull, most modifications of meta data
1100 3d77c87e 2004-03-15 devnull * will fit within the block. i.e. this code should almost
1101 3d77c87e 2004-03-15 devnull * never be executed.
1102 3d77c87e 2004-03-15 devnull */
1103 3d77c87e 2004-03-15 devnull boff = filemetaalloc(fp, &f->dir, f->boff+1);
1104 3d77c87e 2004-03-15 devnull if(boff == NilBlock){
1105 3d77c87e 2004-03-15 devnull /* mbResize might have modified block */
1106 3d77c87e 2004-03-15 devnull mbpack(&mb);
1107 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1108 3d77c87e 2004-03-15 devnull goto Err;
1109 3d77c87e 2004-03-15 devnull }
1110 3d77c87e 2004-03-15 devnull fprint(2, "fileMetaFlush moving entry from %ud -> %ud\n", f->boff, boff);
1111 3d77c87e 2004-03-15 devnull f->boff = boff;
1112 3d77c87e 2004-03-15 devnull
1113 3d77c87e 2004-03-15 devnull /* make sure deletion goes to disk after new entry */
1114 3d77c87e 2004-03-15 devnull bb = vtfileblock(fp->msource, f->boff, VtORDWR);
1115 3d77c87e 2004-03-15 devnull mbdelete(&mb, i, &me);
1116 3d77c87e 2004-03-15 devnull mbpack(&mb);
1117 3d77c87e 2004-03-15 devnull // blockDependency(b, bb, -1, nil, nil);
1118 3d77c87e 2004-03-15 devnull vtblockput(bb);
1119 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1120 3d77c87e 2004-03-15 devnull vtblockput(b);
1121 3d77c87e 2004-03-15 devnull vtfileunlock(fp->msource);
1122 3d77c87e 2004-03-15 devnull
1123 3d77c87e 2004-03-15 devnull f->dirty = 0;
1124 3d77c87e 2004-03-15 devnull
1125 3d77c87e 2004-03-15 devnull return 0;
1126 3d77c87e 2004-03-15 devnull
1127 7763a61a 2003-11-23 devnull Err:
1128 3d77c87e 2004-03-15 devnull vtblockput(b);
1129 3d77c87e 2004-03-15 devnull Err1:
1130 3d77c87e 2004-03-15 devnull vtfileunlock(fp->msource);
1131 3d77c87e 2004-03-15 devnull return -1;
1132 3d77c87e 2004-03-15 devnull }
1133 3d77c87e 2004-03-15 devnull
1134 3d77c87e 2004-03-15 devnull static int
1135 3d77c87e 2004-03-15 devnull filemetaremove(VacFile *f, char *uid)
1136 3d77c87e 2004-03-15 devnull {
1137 3d77c87e 2004-03-15 devnull VtBlock *b;
1138 3d77c87e 2004-03-15 devnull MetaBlock mb;
1139 3d77c87e 2004-03-15 devnull MetaEntry me;
1140 3d77c87e 2004-03-15 devnull int i;
1141 3d77c87e 2004-03-15 devnull VacFile *up;
1142 3d77c87e 2004-03-15 devnull
1143 3d77c87e 2004-03-15 devnull b = nil;
1144 3d77c87e 2004-03-15 devnull up = f->up;
1145 3d77c87e 2004-03-15 devnull filewaccess(up, uid);
1146 3d77c87e 2004-03-15 devnull filemetalock(f);
1147 3d77c87e 2004-03-15 devnull
1148 3d77c87e 2004-03-15 devnull if(vtfilelock(up->msource, VtORDWR) < 0)
1149 3d77c87e 2004-03-15 devnull goto Err;
1150 3d77c87e 2004-03-15 devnull b = vtfileblock(up->msource, f->boff, VtORDWR);
1151 3d77c87e 2004-03-15 devnull if(b == nil)
1152 3d77c87e 2004-03-15 devnull goto Err;
1153 3d77c87e 2004-03-15 devnull
1154 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, up->msource->dsize) < 0)
1155 3d77c87e 2004-03-15 devnull goto Err;
1156 3d77c87e 2004-03-15 devnull if(mbsearch(&mb, f->dir.elem, &i, &me) < 0)
1157 3d77c87e 2004-03-15 devnull goto Err;
1158 3d77c87e 2004-03-15 devnull mbdelete(&mb, i, &me);
1159 3d77c87e 2004-03-15 devnull mbpack(&mb);
1160 3d77c87e 2004-03-15 devnull vtfileunlock(up->msource);
1161 3d77c87e 2004-03-15 devnull
1162 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1163 3d77c87e 2004-03-15 devnull vtblockput(b);
1164 3d77c87e 2004-03-15 devnull
1165 3d77c87e 2004-03-15 devnull f->removed = 1;
1166 3d77c87e 2004-03-15 devnull f->boff = NilBlock;
1167 3d77c87e 2004-03-15 devnull f->dirty = 0;
1168 3d77c87e 2004-03-15 devnull
1169 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1170 7763a61a 2003-11-23 devnull return 0;
1171 3d77c87e 2004-03-15 devnull
1172 3d77c87e 2004-03-15 devnull Err:
1173 3d77c87e 2004-03-15 devnull vtfileunlock(up->msource);
1174 3d77c87e 2004-03-15 devnull vtblockput(b);
1175 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1176 3d77c87e 2004-03-15 devnull return -1;
1177 7763a61a 2003-11-23 devnull }
1178 7763a61a 2003-11-23 devnull
1179 3d77c87e 2004-03-15 devnull /* assume file is locked, assume f->msource is locked */
1180 3d77c87e 2004-03-15 devnull static int
1181 3d77c87e 2004-03-15 devnull filecheckempty(VacFile *f)
1182 7763a61a 2003-11-23 devnull {
1183 3d77c87e 2004-03-15 devnull u32int i, n;
1184 3d77c87e 2004-03-15 devnull VtBlock *b;
1185 3d77c87e 2004-03-15 devnull MetaBlock mb;
1186 3d77c87e 2004-03-15 devnull VtFile *r;
1187 3d77c87e 2004-03-15 devnull
1188 3d77c87e 2004-03-15 devnull r = f->msource;
1189 3d77c87e 2004-03-15 devnull n = (vtfilegetsize(r)+r->dsize-1)/r->dsize;
1190 3d77c87e 2004-03-15 devnull for(i=0; i<n; i++){
1191 3d77c87e 2004-03-15 devnull b = vtfileblock(r, i, VtORDWR);
1192 3d77c87e 2004-03-15 devnull if(b == nil)
1193 3d77c87e 2004-03-15 devnull goto Err;
1194 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, r->dsize) < 0)
1195 3d77c87e 2004-03-15 devnull goto Err;
1196 3d77c87e 2004-03-15 devnull if(mb.nindex > 0){
1197 3d77c87e 2004-03-15 devnull werrstr(ENotEmpty);
1198 3d77c87e 2004-03-15 devnull goto Err;
1199 3d77c87e 2004-03-15 devnull }
1200 3d77c87e 2004-03-15 devnull vtblockput(b);
1201 3d77c87e 2004-03-15 devnull }
1202 3d77c87e 2004-03-15 devnull return 0;
1203 3d77c87e 2004-03-15 devnull Err:
1204 3d77c87e 2004-03-15 devnull vtblockput(b);
1205 3d77c87e 2004-03-15 devnull return -1;
1206 7763a61a 2003-11-23 devnull }
1207 7763a61a 2003-11-23 devnull
1208 3d77c87e 2004-03-15 devnull int
1209 3d77c87e 2004-03-15 devnull vacfileremove(VacFile *f, char *muid)
1210 7763a61a 2003-11-23 devnull {
1211 3d77c87e 2004-03-15 devnull VacFile *ff;
1212 7763a61a 2003-11-23 devnull
1213 3d77c87e 2004-03-15 devnull /* can not remove the root */
1214 3d77c87e 2004-03-15 devnull if(vacfileisroot(f)){
1215 3d77c87e 2004-03-15 devnull werrstr(ERoot);
1216 3d77c87e 2004-03-15 devnull return -1;
1217 7763a61a 2003-11-23 devnull }
1218 7763a61a 2003-11-23 devnull
1219 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
1220 3d77c87e 2004-03-15 devnull return -1;
1221 3d77c87e 2004-03-15 devnull
1222 3d77c87e 2004-03-15 devnull if(f->source->mode != VtORDWR){
1223 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
1224 3d77c87e 2004-03-15 devnull goto Err1;
1225 7763a61a 2003-11-23 devnull }
1226 3d77c87e 2004-03-15 devnull if(vtfilelock2(f->source, f->msource, -1) < 0)
1227 3d77c87e 2004-03-15 devnull goto Err1;
1228 3d77c87e 2004-03-15 devnull if(vacfileisdir(f) && filecheckempty(f)<0)
1229 3d77c87e 2004-03-15 devnull goto Err;
1230 7763a61a 2003-11-23 devnull
1231 3d77c87e 2004-03-15 devnull for(ff=f->down; ff; ff=ff->next)
1232 3d77c87e 2004-03-15 devnull assert(ff->removed);
1233 7763a61a 2003-11-23 devnull
1234 3d77c87e 2004-03-15 devnull vtfileremove(f->source);
1235 3d77c87e 2004-03-15 devnull f->source = nil;
1236 3d77c87e 2004-03-15 devnull if(f->msource){
1237 3d77c87e 2004-03-15 devnull vtfileremove(f->msource);
1238 3d77c87e 2004-03-15 devnull f->msource = nil;
1239 3d77c87e 2004-03-15 devnull }
1240 7763a61a 2003-11-23 devnull
1241 3d77c87e 2004-03-15 devnull fileunlock(f);
1242 3d77c87e 2004-03-15 devnull
1243 3d77c87e 2004-03-15 devnull if(filemetaremove(f, muid) < 0)
1244 3d77c87e 2004-03-15 devnull return -1;
1245 3d77c87e 2004-03-15 devnull
1246 3d77c87e 2004-03-15 devnull return 0;
1247 3d77c87e 2004-03-15 devnull
1248 3d77c87e 2004-03-15 devnull Err:
1249 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
1250 3d77c87e 2004-03-15 devnull if(f->msource)
1251 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
1252 3d77c87e 2004-03-15 devnull Err1:
1253 3d77c87e 2004-03-15 devnull fileunlock(f);
1254 3d77c87e 2004-03-15 devnull return -1;
1255 7763a61a 2003-11-23 devnull }
1256 7763a61a 2003-11-23 devnull
1257 3d77c87e 2004-03-15 devnull static int
1258 3d77c87e 2004-03-15 devnull clri(VacFile *f, char *uid)
1259 3d77c87e 2004-03-15 devnull {
1260 3d77c87e 2004-03-15 devnull int r;
1261 3d77c87e 2004-03-15 devnull
1262 3d77c87e 2004-03-15 devnull if(f == nil)
1263 3d77c87e 2004-03-15 devnull return -1;
1264 3d77c87e 2004-03-15 devnull if(f->up->source->mode != VtORDWR){
1265 3d77c87e 2004-03-15 devnull werrstr(EReadOnly);
1266 3d77c87e 2004-03-15 devnull vacfiledecref(f);
1267 3d77c87e 2004-03-15 devnull return -1;
1268 3d77c87e 2004-03-15 devnull }
1269 3d77c87e 2004-03-15 devnull r = filemetaremove(f, uid);
1270 3d77c87e 2004-03-15 devnull vacfiledecref(f);
1271 3d77c87e 2004-03-15 devnull return r;
1272 3d77c87e 2004-03-15 devnull }
1273 3d77c87e 2004-03-15 devnull
1274 7763a61a 2003-11-23 devnull int
1275 3d77c87e 2004-03-15 devnull vacfileclripath(VacFs *fs, char *path, char *uid)
1276 7763a61a 2003-11-23 devnull {
1277 3d77c87e 2004-03-15 devnull return clri(_fileopen(fs, path, 1), uid);
1278 3d77c87e 2004-03-15 devnull }
1279 7763a61a 2003-11-23 devnull
1280 3d77c87e 2004-03-15 devnull int
1281 3d77c87e 2004-03-15 devnull vacfileclri(VacFile *dir, char *elem, char *uid)
1282 3d77c87e 2004-03-15 devnull {
1283 3d77c87e 2004-03-15 devnull return clri(_filewalk(dir, elem, 1), uid);
1284 7763a61a 2003-11-23 devnull }
1285 7763a61a 2003-11-23 devnull
1286 3d77c87e 2004-03-15 devnull VacFile*
1287 3d77c87e 2004-03-15 devnull vacfileincref(VacFile *vf)
1288 3d77c87e 2004-03-15 devnull {
1289 3d77c87e 2004-03-15 devnull filemetalock(vf);
1290 3d77c87e 2004-03-15 devnull assert(vf->ref > 0);
1291 3d77c87e 2004-03-15 devnull vf->ref++;
1292 3d77c87e 2004-03-15 devnull filemetaunlock(vf);
1293 3d77c87e 2004-03-15 devnull return vf;
1294 3d77c87e 2004-03-15 devnull }
1295 3d77c87e 2004-03-15 devnull
1296 7763a61a 2003-11-23 devnull int
1297 3d77c87e 2004-03-15 devnull vacfiledecref(VacFile *f)
1298 7763a61a 2003-11-23 devnull {
1299 3d77c87e 2004-03-15 devnull VacFile *p, *q, **qq;
1300 7763a61a 2003-11-23 devnull
1301 3d77c87e 2004-03-15 devnull if(f->up == nil){
1302 3d77c87e 2004-03-15 devnull /* never linked in */
1303 3d77c87e 2004-03-15 devnull assert(f->ref == 1);
1304 3d77c87e 2004-03-15 devnull filefree(f);
1305 7763a61a 2003-11-23 devnull return 0;
1306 3d77c87e 2004-03-15 devnull }
1307 7763a61a 2003-11-23 devnull
1308 3d77c87e 2004-03-15 devnull filemetalock(f);
1309 3d77c87e 2004-03-15 devnull f->ref--;
1310 3d77c87e 2004-03-15 devnull if(f->ref > 0){
1311 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1312 3d77c87e 2004-03-15 devnull return -1;
1313 7763a61a 2003-11-23 devnull }
1314 3d77c87e 2004-03-15 devnull assert(f->ref == 0);
1315 3d77c87e 2004-03-15 devnull assert(f->down == nil);
1316 7763a61a 2003-11-23 devnull
1317 3d77c87e 2004-03-15 devnull filemetaflush2(f, nil);
1318 7763a61a 2003-11-23 devnull
1319 3d77c87e 2004-03-15 devnull p = f->up;
1320 3d77c87e 2004-03-15 devnull qq = &p->down;
1321 3d77c87e 2004-03-15 devnull for(q = *qq; q; q = *qq){
1322 3d77c87e 2004-03-15 devnull if(q == f)
1323 3d77c87e 2004-03-15 devnull break;
1324 3d77c87e 2004-03-15 devnull qq = &q->next;
1325 3d77c87e 2004-03-15 devnull }
1326 3d77c87e 2004-03-15 devnull assert(q != nil);
1327 3d77c87e 2004-03-15 devnull *qq = f->next;
1328 3d77c87e 2004-03-15 devnull
1329 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1330 3d77c87e 2004-03-15 devnull filefree(f);
1331 3d77c87e 2004-03-15 devnull vacfiledecref(p);
1332 3d77c87e 2004-03-15 devnull return 0;
1333 7763a61a 2003-11-23 devnull }
1334 7763a61a 2003-11-23 devnull
1335 3d77c87e 2004-03-15 devnull VacFile*
1336 a20a1468 2005-01-16 devnull vacfilegetparent(VacFile *f)
1337 7763a61a 2003-11-23 devnull {
1338 3d77c87e 2004-03-15 devnull if(vacfileisroot(f))
1339 3d77c87e 2004-03-15 devnull return vacfileincref(f);
1340 3d77c87e 2004-03-15 devnull return vacfileincref(f->up);
1341 7763a61a 2003-11-23 devnull }
1342 7763a61a 2003-11-23 devnull
1343 a20a1468 2005-01-16 devnull int
1344 a20a1468 2005-01-16 devnull vacfilewrite(VacFile *file, void *buf, int n, vlong offset, char *muid)
1345 a20a1468 2005-01-16 devnull {
1346 a20a1468 2005-01-16 devnull werrstr("read only file system");
1347 a20a1468 2005-01-16 devnull return -1;
1348 a20a1468 2005-01-16 devnull }
1349 a20a1468 2005-01-16 devnull
1350 3d77c87e 2004-03-15 devnull VacDirEnum*
1351 3d77c87e 2004-03-15 devnull vdeopen(VacFile *f)
1352 7763a61a 2003-11-23 devnull {
1353 3d77c87e 2004-03-15 devnull VacDirEnum *vde;
1354 3d77c87e 2004-03-15 devnull VacFile *p;
1355 7763a61a 2003-11-23 devnull
1356 3d77c87e 2004-03-15 devnull if(!vacfileisdir(f)){
1357 3d77c87e 2004-03-15 devnull werrstr(ENotDir);
1358 7763a61a 2003-11-23 devnull return nil;
1359 7763a61a 2003-11-23 devnull }
1360 7763a61a 2003-11-23 devnull
1361 3d77c87e 2004-03-15 devnull /* flush out meta data */
1362 3d77c87e 2004-03-15 devnull if(filelock(f) < 0)
1363 7763a61a 2003-11-23 devnull return nil;
1364 3d77c87e 2004-03-15 devnull for(p=f->down; p; p=p->next)
1365 3d77c87e 2004-03-15 devnull filemetaflush2(p, nil);
1366 3d77c87e 2004-03-15 devnull fileunlock(f);
1367 7763a61a 2003-11-23 devnull
1368 3d77c87e 2004-03-15 devnull vde = vtmallocz(sizeof(VacDirEnum));
1369 3d77c87e 2004-03-15 devnull vde->file = vacfileincref(f);
1370 7763a61a 2003-11-23 devnull
1371 3d77c87e 2004-03-15 devnull return vde;
1372 7763a61a 2003-11-23 devnull }
1373 7763a61a 2003-11-23 devnull
1374 7763a61a 2003-11-23 devnull static int
1375 3d77c87e 2004-03-15 devnull direntrysize(VtFile *s, ulong elem, ulong gen, uvlong *size)
1376 7763a61a 2003-11-23 devnull {
1377 3d77c87e 2004-03-15 devnull VtBlock *b;
1378 7763a61a 2003-11-23 devnull ulong bn;
1379 7763a61a 2003-11-23 devnull VtEntry e;
1380 3d77c87e 2004-03-15 devnull int epb;
1381 7763a61a 2003-11-23 devnull
1382 3d77c87e 2004-03-15 devnull epb = s->dsize/VtEntrySize;
1383 3d77c87e 2004-03-15 devnull bn = elem/epb;
1384 3d77c87e 2004-03-15 devnull elem -= bn*epb;
1385 7763a61a 2003-11-23 devnull
1386 3d77c87e 2004-03-15 devnull b = vtfileblock(s, bn, VtOREAD);
1387 3d77c87e 2004-03-15 devnull if(b == nil)
1388 7763a61a 2003-11-23 devnull goto Err;
1389 3d77c87e 2004-03-15 devnull if(vtentryunpack(&e, b->data, elem) < 0)
1390 7763a61a 2003-11-23 devnull goto Err;
1391 7763a61a 2003-11-23 devnull
1392 3d77c87e 2004-03-15 devnull /* hanging entries are returned as zero size */
1393 3d77c87e 2004-03-15 devnull if(!(e.flags & VtEntryActive) || e.gen != gen)
1394 3d77c87e 2004-03-15 devnull *size = 0;
1395 3d77c87e 2004-03-15 devnull else
1396 3d77c87e 2004-03-15 devnull *size = e.size;
1397 3d77c87e 2004-03-15 devnull vtblockput(b);
1398 3d77c87e 2004-03-15 devnull return 0;
1399 7763a61a 2003-11-23 devnull
1400 7763a61a 2003-11-23 devnull Err:
1401 3d77c87e 2004-03-15 devnull vtblockput(b);
1402 3d77c87e 2004-03-15 devnull return -1;
1403 7763a61a 2003-11-23 devnull }
1404 7763a61a 2003-11-23 devnull
1405 3d77c87e 2004-03-15 devnull static int
1406 3d77c87e 2004-03-15 devnull vdefill(VacDirEnum *vde)
1407 7763a61a 2003-11-23 devnull {
1408 3d77c87e 2004-03-15 devnull int i, n;
1409 3d77c87e 2004-03-15 devnull VtFile *meta, *source;
1410 7763a61a 2003-11-23 devnull MetaBlock mb;
1411 7763a61a 2003-11-23 devnull MetaEntry me;
1412 3d77c87e 2004-03-15 devnull VacFile *f;
1413 3d77c87e 2004-03-15 devnull VtBlock *b;
1414 3d77c87e 2004-03-15 devnull VacDir *de;
1415 7763a61a 2003-11-23 devnull
1416 3d77c87e 2004-03-15 devnull /* clean up first */
1417 3d77c87e 2004-03-15 devnull for(i=vde->i; i<vde->n; i++)
1418 3d77c87e 2004-03-15 devnull vdcleanup(vde->buf+i);
1419 3d77c87e 2004-03-15 devnull vtfree(vde->buf);
1420 3d77c87e 2004-03-15 devnull vde->buf = nil;
1421 3d77c87e 2004-03-15 devnull vde->i = 0;
1422 3d77c87e 2004-03-15 devnull vde->n = 0;
1423 7763a61a 2003-11-23 devnull
1424 3d77c87e 2004-03-15 devnull f = vde->file;
1425 7763a61a 2003-11-23 devnull
1426 3d77c87e 2004-03-15 devnull source = f->source;
1427 3d77c87e 2004-03-15 devnull meta = f->msource;
1428 7763a61a 2003-11-23 devnull
1429 3d77c87e 2004-03-15 devnull b = vtfileblock(meta, vde->boff, VtOREAD);
1430 3d77c87e 2004-03-15 devnull if(b == nil)
1431 7763a61a 2003-11-23 devnull goto Err;
1432 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, meta->dsize) < 0)
1433 7763a61a 2003-11-23 devnull goto Err;
1434 7763a61a 2003-11-23 devnull
1435 3d77c87e 2004-03-15 devnull n = mb.nindex;
1436 3d77c87e 2004-03-15 devnull vde->buf = vtmalloc(n * sizeof(VacDir));
1437 3d77c87e 2004-03-15 devnull
1438 3d77c87e 2004-03-15 devnull for(i=0; i<n; i++){
1439 3d77c87e 2004-03-15 devnull de = vde->buf + i;
1440 3d77c87e 2004-03-15 devnull meunpack(&me, &mb, i);
1441 3d77c87e 2004-03-15 devnull if(vdunpack(de, &me) < 0)
1442 7763a61a 2003-11-23 devnull goto Err;
1443 3d77c87e 2004-03-15 devnull vde->n++;
1444 3d77c87e 2004-03-15 devnull if(!(de->mode & ModeDir))
1445 3d77c87e 2004-03-15 devnull if(direntrysize(source, de->entry, de->gen, &de->size) < 0)
1446 3d77c87e 2004-03-15 devnull goto Err;
1447 7763a61a 2003-11-23 devnull }
1448 3d77c87e 2004-03-15 devnull vde->boff++;
1449 3d77c87e 2004-03-15 devnull vtblockput(b);
1450 3d77c87e 2004-03-15 devnull return 0;
1451 7763a61a 2003-11-23 devnull Err:
1452 3d77c87e 2004-03-15 devnull vtblockput(b);
1453 7763a61a 2003-11-23 devnull return -1;
1454 7763a61a 2003-11-23 devnull }
1455 7763a61a 2003-11-23 devnull
1456 3d77c87e 2004-03-15 devnull int
1457 3d77c87e 2004-03-15 devnull vderead(VacDirEnum *vde, VacDir *de)
1458 3d77c87e 2004-03-15 devnull {
1459 3d77c87e 2004-03-15 devnull int ret, didread;
1460 3d77c87e 2004-03-15 devnull VacFile *f;
1461 3d77c87e 2004-03-15 devnull u32int nb;
1462 3d77c87e 2004-03-15 devnull
1463 3d77c87e 2004-03-15 devnull f = vde->file;
1464 3d77c87e 2004-03-15 devnull if(filerlock(f) < 0)
1465 3d77c87e 2004-03-15 devnull return -1;
1466 3d77c87e 2004-03-15 devnull
1467 3d77c87e 2004-03-15 devnull if(vtfilelock2(f->source, f->msource, VtOREAD) < 0){
1468 3d77c87e 2004-03-15 devnull filerunlock(f);
1469 3d77c87e 2004-03-15 devnull return -1;
1470 3d77c87e 2004-03-15 devnull }
1471 3d77c87e 2004-03-15 devnull
1472 3d77c87e 2004-03-15 devnull nb = (vtfilegetsize(f->msource)+f->msource->dsize-1)/f->msource->dsize;
1473 3d77c87e 2004-03-15 devnull
1474 3d77c87e 2004-03-15 devnull didread = 0;
1475 3d77c87e 2004-03-15 devnull while(vde->i >= vde->n){
1476 3d77c87e 2004-03-15 devnull if(vde->boff >= nb){
1477 3d77c87e 2004-03-15 devnull ret = 0;
1478 3d77c87e 2004-03-15 devnull goto Return;
1479 3d77c87e 2004-03-15 devnull }
1480 3d77c87e 2004-03-15 devnull didread = 1;
1481 3d77c87e 2004-03-15 devnull if(vdefill(vde) < 0){
1482 3d77c87e 2004-03-15 devnull ret = -1;
1483 3d77c87e 2004-03-15 devnull goto Return;
1484 3d77c87e 2004-03-15 devnull }
1485 3d77c87e 2004-03-15 devnull }
1486 3d77c87e 2004-03-15 devnull
1487 3d77c87e 2004-03-15 devnull memmove(de, vde->buf + vde->i, sizeof(VacDir));
1488 3d77c87e 2004-03-15 devnull vde->i++;
1489 3d77c87e 2004-03-15 devnull ret = 1;
1490 3d77c87e 2004-03-15 devnull
1491 3d77c87e 2004-03-15 devnull Return:
1492 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
1493 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
1494 3d77c87e 2004-03-15 devnull filerunlock(f);
1495 3d77c87e 2004-03-15 devnull
1496 3d77c87e 2004-03-15 devnull if(didread)
1497 3d77c87e 2004-03-15 devnull fileraccess(f);
1498 3d77c87e 2004-03-15 devnull return ret;
1499 3d77c87e 2004-03-15 devnull }
1500 3d77c87e 2004-03-15 devnull
1501 7763a61a 2003-11-23 devnull void
1502 3d77c87e 2004-03-15 devnull vdeclose(VacDirEnum *vde)
1503 7763a61a 2003-11-23 devnull {
1504 3d77c87e 2004-03-15 devnull int i;
1505 3d77c87e 2004-03-15 devnull if(vde == nil)
1506 7763a61a 2003-11-23 devnull return;
1507 3d77c87e 2004-03-15 devnull for(i=vde->i; i<vde->n; i++)
1508 3d77c87e 2004-03-15 devnull vdcleanup(vde->buf+i);
1509 3d77c87e 2004-03-15 devnull vtfree(vde->buf);
1510 3d77c87e 2004-03-15 devnull vacfiledecref(vde->file);
1511 3d77c87e 2004-03-15 devnull vtfree(vde);
1512 7763a61a 2003-11-23 devnull }
1513 7763a61a 2003-11-23 devnull
1514 3d77c87e 2004-03-15 devnull /*
1515 3d77c87e 2004-03-15 devnull * caller must lock f->source and f->msource
1516 3d77c87e 2004-03-15 devnull * caller must NOT lock the source and msource
1517 3d77c87e 2004-03-15 devnull * referenced by dir.
1518 3d77c87e 2004-03-15 devnull */
1519 3d77c87e 2004-03-15 devnull static u32int
1520 3d77c87e 2004-03-15 devnull filemetaalloc(VacFile *f, VacDir *dir, u32int start)
1521 7763a61a 2003-11-23 devnull {
1522 3d77c87e 2004-03-15 devnull u32int nb, bo;
1523 a6662a36 2005-01-04 devnull VtBlock *b;
1524 7763a61a 2003-11-23 devnull MetaBlock mb;
1525 3d77c87e 2004-03-15 devnull int nn;
1526 3d77c87e 2004-03-15 devnull uchar *p;
1527 a6662a36 2005-01-04 devnull int i, n;
1528 3d77c87e 2004-03-15 devnull MetaEntry me;
1529 3d77c87e 2004-03-15 devnull VtFile *s, *ms;
1530 7763a61a 2003-11-23 devnull
1531 3d77c87e 2004-03-15 devnull s = f->source;
1532 3d77c87e 2004-03-15 devnull ms = f->msource;
1533 3d77c87e 2004-03-15 devnull
1534 3d77c87e 2004-03-15 devnull n = vdsize(dir);
1535 3d77c87e 2004-03-15 devnull nb = (vtfilegetsize(ms)+ms->dsize-1)/ms->dsize;
1536 3d77c87e 2004-03-15 devnull b = nil;
1537 7763a61a 2003-11-23 devnull if(start > nb)
1538 7763a61a 2003-11-23 devnull start = nb;
1539 3d77c87e 2004-03-15 devnull for(bo=start; bo<nb; bo++){
1540 3d77c87e 2004-03-15 devnull b = vtfileblock(ms, bo, VtORDWR);
1541 3d77c87e 2004-03-15 devnull if(b == nil)
1542 7763a61a 2003-11-23 devnull goto Err;
1543 3d77c87e 2004-03-15 devnull if(mbunpack(&mb, b->data, ms->dsize) < 0)
1544 7763a61a 2003-11-23 devnull goto Err;
1545 3d77c87e 2004-03-15 devnull nn = (mb.maxsize*FullPercentage/100) - mb.size + mb.free;
1546 3d77c87e 2004-03-15 devnull if(n <= nn && mb.nindex < mb.maxindex)
1547 7763a61a 2003-11-23 devnull break;
1548 3d77c87e 2004-03-15 devnull vtblockput(b);
1549 3d77c87e 2004-03-15 devnull b = nil;
1550 7763a61a 2003-11-23 devnull }
1551 3d77c87e 2004-03-15 devnull
1552 7763a61a 2003-11-23 devnull /* add block to meta file */
1553 3d77c87e 2004-03-15 devnull if(b == nil){
1554 3d77c87e 2004-03-15 devnull b = vtfileblock(ms, bo, VtORDWR);
1555 3d77c87e 2004-03-15 devnull if(b == nil)
1556 7763a61a 2003-11-23 devnull goto Err;
1557 3d77c87e 2004-03-15 devnull vtfilesetsize(ms, (nb+1)*ms->dsize);
1558 3d77c87e 2004-03-15 devnull mbinit(&mb, b->data, ms->dsize, ms->dsize/BytesPerEntry);
1559 7763a61a 2003-11-23 devnull }
1560 3d77c87e 2004-03-15 devnull
1561 3d77c87e 2004-03-15 devnull p = mballoc(&mb, n);
1562 3d77c87e 2004-03-15 devnull if(p == nil){
1563 3d77c87e 2004-03-15 devnull /* mbAlloc might have changed block */
1564 3d77c87e 2004-03-15 devnull mbpack(&mb);
1565 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1566 3d77c87e 2004-03-15 devnull werrstr(EBadMeta);
1567 3d77c87e 2004-03-15 devnull goto Err;
1568 3d77c87e 2004-03-15 devnull }
1569 3d77c87e 2004-03-15 devnull
1570 3d77c87e 2004-03-15 devnull mbsearch(&mb, dir->elem, &i, &me);
1571 3d77c87e 2004-03-15 devnull assert(me.p == nil);
1572 3d77c87e 2004-03-15 devnull me.p = p;
1573 3d77c87e 2004-03-15 devnull me.size = n;
1574 3d77c87e 2004-03-15 devnull vdpack(dir, &me);
1575 3d77c87e 2004-03-15 devnull mbinsert(&mb, i, &me);
1576 3d77c87e 2004-03-15 devnull mbpack(&mb);
1577 3d77c87e 2004-03-15 devnull
1578 3d77c87e 2004-03-15 devnull #ifdef notdef /* XXX */
1579 3d77c87e 2004-03-15 devnull /* meta block depends on super block for qid ... */
1580 3d77c87e 2004-03-15 devnull bb = cacheLocal(b->c, PartSuper, 0, VtOREAD);
1581 3d77c87e 2004-03-15 devnull blockDependency(b, bb, -1, nil, nil);
1582 3d77c87e 2004-03-15 devnull vtblockput(bb);
1583 3d77c87e 2004-03-15 devnull
1584 3d77c87e 2004-03-15 devnull /* ... and one or two dir entries */
1585 3d77c87e 2004-03-15 devnull epb = s->dsize/VtEntrySize;
1586 3d77c87e 2004-03-15 devnull bb = vtfileblock(s, dir->entry/epb, VtOREAD);
1587 3d77c87e 2004-03-15 devnull blockDependency(b, bb, -1, nil, nil);
1588 3d77c87e 2004-03-15 devnull vtblockput(bb);
1589 3d77c87e 2004-03-15 devnull if(dir->mode & ModeDir){
1590 3d77c87e 2004-03-15 devnull bb = sourceBlock(s, dir->mentry/epb, VtOREAD);
1591 3d77c87e 2004-03-15 devnull blockDependency(b, bb, -1, nil, nil);
1592 3d77c87e 2004-03-15 devnull vtblockput(bb);
1593 3d77c87e 2004-03-15 devnull }
1594 3d77c87e 2004-03-15 devnull #endif
1595 3d77c87e 2004-03-15 devnull
1596 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1597 3d77c87e 2004-03-15 devnull vtblockput(b);
1598 3d77c87e 2004-03-15 devnull return bo;
1599 7763a61a 2003-11-23 devnull Err:
1600 3d77c87e 2004-03-15 devnull vtblockput(b);
1601 7763a61a 2003-11-23 devnull return NilBlock;
1602 7763a61a 2003-11-23 devnull }
1603 7763a61a 2003-11-23 devnull
1604 3d77c87e 2004-03-15 devnull static int
1605 3d77c87e 2004-03-15 devnull chksource(VacFile *f)
1606 3d77c87e 2004-03-15 devnull {
1607 3d77c87e 2004-03-15 devnull if(f->partial)
1608 3d77c87e 2004-03-15 devnull return 0;
1609 3d77c87e 2004-03-15 devnull
1610 3d77c87e 2004-03-15 devnull if(f->source == nil || (f->dir.mode & ModeDir) && f->msource == nil){
1611 3d77c87e 2004-03-15 devnull werrstr(ERemoved);
1612 3d77c87e 2004-03-15 devnull return -1;
1613 3d77c87e 2004-03-15 devnull }
1614 3d77c87e 2004-03-15 devnull return 0;
1615 3d77c87e 2004-03-15 devnull }
1616 3d77c87e 2004-03-15 devnull
1617 3d77c87e 2004-03-15 devnull static int
1618 3d77c87e 2004-03-15 devnull filerlock(VacFile *f)
1619 3d77c87e 2004-03-15 devnull {
1620 3d77c87e 2004-03-15 devnull // assert(!canwlock(&f->fs->elk));
1621 3d77c87e 2004-03-15 devnull rlock(&f->lk);
1622 3d77c87e 2004-03-15 devnull if(chksource(f) < 0){
1623 3d77c87e 2004-03-15 devnull runlock(&f->lk);
1624 3d77c87e 2004-03-15 devnull return -1;
1625 3d77c87e 2004-03-15 devnull }
1626 3d77c87e 2004-03-15 devnull return 0;
1627 3d77c87e 2004-03-15 devnull }
1628 3d77c87e 2004-03-15 devnull
1629 3d77c87e 2004-03-15 devnull static void
1630 3d77c87e 2004-03-15 devnull filerunlock(VacFile *f)
1631 3d77c87e 2004-03-15 devnull {
1632 3d77c87e 2004-03-15 devnull runlock(&f->lk);
1633 3d77c87e 2004-03-15 devnull }
1634 3d77c87e 2004-03-15 devnull
1635 3d77c87e 2004-03-15 devnull static int
1636 3d77c87e 2004-03-15 devnull filelock(VacFile *f)
1637 3d77c87e 2004-03-15 devnull {
1638 3d77c87e 2004-03-15 devnull // assert(!canwlock(&f->fs->elk));
1639 3d77c87e 2004-03-15 devnull wlock(&f->lk);
1640 3d77c87e 2004-03-15 devnull if(chksource(f) < 0){
1641 3d77c87e 2004-03-15 devnull wunlock(&f->lk);
1642 3d77c87e 2004-03-15 devnull return -1;
1643 3d77c87e 2004-03-15 devnull }
1644 3d77c87e 2004-03-15 devnull return 0;
1645 3d77c87e 2004-03-15 devnull }
1646 3d77c87e 2004-03-15 devnull
1647 3d77c87e 2004-03-15 devnull static void
1648 3d77c87e 2004-03-15 devnull fileunlock(VacFile *f)
1649 3d77c87e 2004-03-15 devnull {
1650 3d77c87e 2004-03-15 devnull wunlock(&f->lk);
1651 3d77c87e 2004-03-15 devnull }
1652 3d77c87e 2004-03-15 devnull
1653 3d77c87e 2004-03-15 devnull /*
1654 3d77c87e 2004-03-15 devnull * f->source and f->msource must NOT be locked.
1655 3d77c87e 2004-03-15 devnull * fileMetaFlush locks the fileMeta and then the source (in fileMetaFlush2).
1656 3d77c87e 2004-03-15 devnull * We have to respect that ordering.
1657 3d77c87e 2004-03-15 devnull */
1658 3d77c87e 2004-03-15 devnull static void
1659 3d77c87e 2004-03-15 devnull filemetalock(VacFile *f)
1660 3d77c87e 2004-03-15 devnull {
1661 3d77c87e 2004-03-15 devnull assert(f->up != nil);
1662 3d77c87e 2004-03-15 devnull // assert(!canwlock(&f->fs->elk));
1663 3d77c87e 2004-03-15 devnull wlock(&f->up->lk);
1664 3d77c87e 2004-03-15 devnull }
1665 3d77c87e 2004-03-15 devnull
1666 3d77c87e 2004-03-15 devnull static void
1667 3d77c87e 2004-03-15 devnull filemetaunlock(VacFile *f)
1668 3d77c87e 2004-03-15 devnull {
1669 3d77c87e 2004-03-15 devnull wunlock(&f->up->lk);
1670 3d77c87e 2004-03-15 devnull }
1671 3d77c87e 2004-03-15 devnull
1672 3d77c87e 2004-03-15 devnull /*
1673 3d77c87e 2004-03-15 devnull * f->source and f->msource must NOT be locked.
1674 3d77c87e 2004-03-15 devnull * see filemetalock.
1675 3d77c87e 2004-03-15 devnull */
1676 3d77c87e 2004-03-15 devnull static void
1677 3d77c87e 2004-03-15 devnull fileraccess(VacFile* f)
1678 3d77c87e 2004-03-15 devnull {
1679 3d77c87e 2004-03-15 devnull if(f->mode == VtOREAD)
1680 3d77c87e 2004-03-15 devnull return;
1681 3d77c87e 2004-03-15 devnull
1682 3d77c87e 2004-03-15 devnull filemetalock(f);
1683 3d77c87e 2004-03-15 devnull f->dir.atime = time(0L);
1684 3d77c87e 2004-03-15 devnull f->dirty = 1;
1685 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1686 3d77c87e 2004-03-15 devnull }
1687 3d77c87e 2004-03-15 devnull
1688 3d77c87e 2004-03-15 devnull /*
1689 3d77c87e 2004-03-15 devnull * f->source and f->msource must NOT be locked.
1690 3d77c87e 2004-03-15 devnull * see filemetalock.
1691 3d77c87e 2004-03-15 devnull */
1692 3d77c87e 2004-03-15 devnull static void
1693 3d77c87e 2004-03-15 devnull filewaccess(VacFile* f, char *mid)
1694 3d77c87e 2004-03-15 devnull {
1695 3d77c87e 2004-03-15 devnull if(f->mode == VtOREAD)
1696 3d77c87e 2004-03-15 devnull return;
1697 3d77c87e 2004-03-15 devnull
1698 3d77c87e 2004-03-15 devnull filemetalock(f);
1699 3d77c87e 2004-03-15 devnull f->dir.atime = f->dir.mtime = time(0L);
1700 3d77c87e 2004-03-15 devnull if(strcmp(f->dir.mid, mid) != 0){
1701 3d77c87e 2004-03-15 devnull vtfree(f->dir.mid);
1702 3d77c87e 2004-03-15 devnull f->dir.mid = vtstrdup(mid);
1703 3d77c87e 2004-03-15 devnull }
1704 3d77c87e 2004-03-15 devnull f->dir.mcount++;
1705 3d77c87e 2004-03-15 devnull f->dirty = 1;
1706 3d77c87e 2004-03-15 devnull filemetaunlock(f);
1707 3d77c87e 2004-03-15 devnull
1708 3d77c87e 2004-03-15 devnull /*RSC: let's try this */
1709 3d77c87e 2004-03-15 devnull /*presotto - lets not
1710 3d77c87e 2004-03-15 devnull if(f->up)
1711 3d77c87e 2004-03-15 devnull filewaccess(f->up, mid);
1712 3d77c87e 2004-03-15 devnull */
1713 3d77c87e 2004-03-15 devnull }
1714 3d77c87e 2004-03-15 devnull
1715 3d77c87e 2004-03-15 devnull #if 0
1716 3d77c87e 2004-03-15 devnull static void
1717 3d77c87e 2004-03-15 devnull markCopied(Block *b)
1718 3d77c87e 2004-03-15 devnull {
1719 3d77c87e 2004-03-15 devnull VtBlock *lb;
1720 3d77c87e 2004-03-15 devnull Label l;
1721 3d77c87e 2004-03-15 devnull
1722 3d77c87e 2004-03-15 devnull if(globalToLocal(b->score) == NilBlock)
1723 3d77c87e 2004-03-15 devnull return;
1724 3d77c87e 2004-03-15 devnull
1725 3d77c87e 2004-03-15 devnull if(!(b->l.state & BsCopied)){
1726 3d77c87e 2004-03-15 devnull /*
1727 3d77c87e 2004-03-15 devnull * We need to record that there are now pointers in
1728 3d77c87e 2004-03-15 devnull * b that are not unique to b. We do this by marking
1729 3d77c87e 2004-03-15 devnull * b as copied. Since we don't return the label block,
1730 3d77c87e 2004-03-15 devnull * the caller can't get the dependencies right. So we have
1731 3d77c87e 2004-03-15 devnull * to flush the block ourselves. This is a rare occurrence.
1732 3d77c87e 2004-03-15 devnull */
1733 3d77c87e 2004-03-15 devnull l = b->l;
1734 3d77c87e 2004-03-15 devnull l.state |= BsCopied;
1735 3d77c87e 2004-03-15 devnull lb = _blockSetLabel(b, &l);
1736 3d77c87e 2004-03-15 devnull WriteAgain:
1737 3d77c87e 2004-03-15 devnull while(!blockWrite(lb)){
1738 3d77c87e 2004-03-15 devnull fprint(2, "getEntry: could not write label block\n");
1739 3d77c87e 2004-03-15 devnull sleep(10*1000);
1740 3d77c87e 2004-03-15 devnull }
1741 3d77c87e 2004-03-15 devnull while(lb->iostate != BioClean && lb->iostate != BioDirty){
1742 3d77c87e 2004-03-15 devnull assert(lb->iostate == BioWriting);
1743 3d77c87e 2004-03-15 devnull vtSleep(lb->ioready);
1744 3d77c87e 2004-03-15 devnull }
1745 3d77c87e 2004-03-15 devnull if(lb->iostate == BioDirty)
1746 3d77c87e 2004-03-15 devnull goto WriteAgain;
1747 3d77c87e 2004-03-15 devnull vtblockput(lb);
1748 3d77c87e 2004-03-15 devnull }
1749 3d77c87e 2004-03-15 devnull }
1750 3d77c87e 2004-03-15 devnull
1751 3d77c87e 2004-03-15 devnull static int
1752 3d77c87e 2004-03-15 devnull getEntry(VtFile *r, Entry *e, int mark)
1753 3d77c87e 2004-03-15 devnull {
1754 3d77c87e 2004-03-15 devnull Block *b;
1755 3d77c87e 2004-03-15 devnull
1756 3d77c87e 2004-03-15 devnull if(r == nil){
1757 3d77c87e 2004-03-15 devnull memset(&e, 0, sizeof e);
1758 3d77c87e 2004-03-15 devnull return 1;
1759 3d77c87e 2004-03-15 devnull }
1760 3d77c87e 2004-03-15 devnull
1761 3d77c87e 2004-03-15 devnull b = cacheGlobal(r->fs->cache, r->score, BtDir, r->tag, VtOREAD);
1762 3d77c87e 2004-03-15 devnull if(b == nil)
1763 3d77c87e 2004-03-15 devnull return 0;
1764 3d77c87e 2004-03-15 devnull if(!entryUnpack(e, b->data, r->offset % r->epb)){
1765 3d77c87e 2004-03-15 devnull vtblockput(b);
1766 3d77c87e 2004-03-15 devnull return 0;
1767 3d77c87e 2004-03-15 devnull }
1768 3d77c87e 2004-03-15 devnull
1769 3d77c87e 2004-03-15 devnull if(mark)
1770 3d77c87e 2004-03-15 devnull markCopied(b);
1771 3d77c87e 2004-03-15 devnull vtblockput(b);
1772 3d77c87e 2004-03-15 devnull return 1;
1773 3d77c87e 2004-03-15 devnull }
1774 3d77c87e 2004-03-15 devnull
1775 3d77c87e 2004-03-15 devnull static int
1776 3d77c87e 2004-03-15 devnull setEntry(Source *r, Entry *e)
1777 3d77c87e 2004-03-15 devnull {
1778 3d77c87e 2004-03-15 devnull Block *b;
1779 3d77c87e 2004-03-15 devnull Entry oe;
1780 3d77c87e 2004-03-15 devnull
1781 3d77c87e 2004-03-15 devnull b = cacheGlobal(r->fs->cache, r->score, BtDir, r->tag, VtORDWR);
1782 3d77c87e 2004-03-15 devnull if(0) fprint(2, "setEntry: b %#ux %d score=%V\n", b->addr, r->offset % r->epb, e->score);
1783 3d77c87e 2004-03-15 devnull if(b == nil)
1784 3d77c87e 2004-03-15 devnull return 0;
1785 3d77c87e 2004-03-15 devnull if(!entryUnpack(&oe, b->data, r->offset % r->epb)){
1786 3d77c87e 2004-03-15 devnull vtblockput(b);
1787 3d77c87e 2004-03-15 devnull return 0;
1788 3d77c87e 2004-03-15 devnull }
1789 3d77c87e 2004-03-15 devnull e->gen = oe.gen;
1790 3d77c87e 2004-03-15 devnull entryPack(e, b->data, r->offset % r->epb);
1791 3d77c87e 2004-03-15 devnull
1792 3d77c87e 2004-03-15 devnull /* BUG b should depend on the entry pointer */
1793 3d77c87e 2004-03-15 devnull
1794 3d77c87e 2004-03-15 devnull markCopied(b);
1795 3d77c87e 2004-03-15 devnull vtblockdirty(b);
1796 3d77c87e 2004-03-15 devnull vtblockput(b);
1797 3d77c87e 2004-03-15 devnull return 1;
1798 3d77c87e 2004-03-15 devnull }
1799 3d77c87e 2004-03-15 devnull
1800 3d77c87e 2004-03-15 devnull /* assumes hold elk */
1801 3d77c87e 2004-03-15 devnull int
1802 3d77c87e 2004-03-15 devnull fileSnapshot(VacFile *dst, VacFile *src, u32int epoch, int doarchive)
1803 3d77c87e 2004-03-15 devnull {
1804 3d77c87e 2004-03-15 devnull Entry e, ee;
1805 3d77c87e 2004-03-15 devnull
1806 3d77c87e 2004-03-15 devnull /* add link to snapshot */
1807 3d77c87e 2004-03-15 devnull if(!getEntry(src->source, &e, 1) || !getEntry(src->msource, &ee, 1))
1808 3d77c87e 2004-03-15 devnull return 0;
1809 3d77c87e 2004-03-15 devnull
1810 3d77c87e 2004-03-15 devnull e.snap = epoch;
1811 3d77c87e 2004-03-15 devnull e.archive = doarchive;
1812 3d77c87e 2004-03-15 devnull ee.snap = epoch;
1813 3d77c87e 2004-03-15 devnull ee.archive = doarchive;
1814 3d77c87e 2004-03-15 devnull
1815 3d77c87e 2004-03-15 devnull if(!setEntry(dst->source, &e) || !setEntry(dst->msource, &ee))
1816 3d77c87e 2004-03-15 devnull return 0;
1817 3d77c87e 2004-03-15 devnull return 1;
1818 3d77c87e 2004-03-15 devnull }
1819 3d77c87e 2004-03-15 devnull
1820 3d77c87e 2004-03-15 devnull int
1821 3d77c87e 2004-03-15 devnull fileGetSources(VacFile *f, Entry *e, Entry *ee, int mark)
1822 3d77c87e 2004-03-15 devnull {
1823 3d77c87e 2004-03-15 devnull if(!getEntry(f->source, e, mark)
1824 3d77c87e 2004-03-15 devnull || !getEntry(f->msource, ee, mark))
1825 3d77c87e 2004-03-15 devnull return 0;
1826 3d77c87e 2004-03-15 devnull return 1;
1827 3d77c87e 2004-03-15 devnull }
1828 3d77c87e 2004-03-15 devnull
1829 3d77c87e 2004-03-15 devnull int
1830 3d77c87e 2004-03-15 devnull fileWalkSources(VacFile *f)
1831 3d77c87e 2004-03-15 devnull {
1832 3d77c87e 2004-03-15 devnull if(f->mode == VtOREAD)
1833 3d77c87e 2004-03-15 devnull return 1;
1834 3d77c87e 2004-03-15 devnull if(!sourceLock2(f->source, f->msource, VtORDWR))
1835 3d77c87e 2004-03-15 devnull return 0;
1836 3d77c87e 2004-03-15 devnull vtfileunlock(f->source);
1837 3d77c87e 2004-03-15 devnull vtfileunlock(f->msource);
1838 3d77c87e 2004-03-15 devnull return 1;
1839 3d77c87e 2004-03-15 devnull }
1840 3d77c87e 2004-03-15 devnull
1841 3d77c87e 2004-03-15 devnull #endif