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 static int sizeToDepth(uvlong s, int psize, int dsize);
8 7763a61a 2003-11-23 devnull
9 7763a61a 2003-11-23 devnull static int
10 7763a61a 2003-11-23 devnull sizeToDepth(uvlong s, int psize, int dsize)
11 7763a61a 2003-11-23 devnull {
12 7763a61a 2003-11-23 devnull int np;
13 7763a61a 2003-11-23 devnull int d;
14 7763a61a 2003-11-23 devnull
15 7763a61a 2003-11-23 devnull /* determine pointer depth */
16 7763a61a 2003-11-23 devnull np = psize/VtScoreSize;
17 7763a61a 2003-11-23 devnull s = (s + dsize - 1)/dsize;
18 7763a61a 2003-11-23 devnull for(d = 0; s > 1; d++)
19 7763a61a 2003-11-23 devnull s = (s + np - 1)/np;
20 7763a61a 2003-11-23 devnull return d;
21 7763a61a 2003-11-23 devnull }
22 7763a61a 2003-11-23 devnull
23 7763a61a 2003-11-23 devnull /* assumes u is lock? */
24 7763a61a 2003-11-23 devnull Source *
25 7763a61a 2003-11-23 devnull sourceAlloc(Cache *c, Lump *u, ulong block, int entry, int readOnly)
26 7763a61a 2003-11-23 devnull {
27 7763a61a 2003-11-23 devnull Source *r;
28 7763a61a 2003-11-23 devnull VtEntry d;
29 7763a61a 2003-11-23 devnull
30 7763a61a 2003-11-23 devnull if(u->asize < (entry+1)*VtEntrySize) {
31 7763a61a 2003-11-23 devnull vtSetError(ENoDir);
32 7763a61a 2003-11-23 devnull return nil;
33 7763a61a 2003-11-23 devnull }
34 7763a61a 2003-11-23 devnull
35 7763a61a 2003-11-23 devnull if(!vtEntryUnpack(&d, u->data, entry))
36 7763a61a 2003-11-23 devnull return nil;
37 7763a61a 2003-11-23 devnull
38 7763a61a 2003-11-23 devnull if(!(d.flags & VtEntryActive)) {
39 7763a61a 2003-11-23 devnull fprint(2, "bad flags %#ux %V\n", d.flags, d.score);
40 7763a61a 2003-11-23 devnull vtSetError(ENoDir);
41 7763a61a 2003-11-23 devnull return nil;
42 7763a61a 2003-11-23 devnull }
43 7763a61a 2003-11-23 devnull
44 7763a61a 2003-11-23 devnull /* HACK for backwards compatiblity - should go away at some point */
45 7763a61a 2003-11-23 devnull if(d.depth == 0) {
46 7763a61a 2003-11-23 devnull if(d.size > d.dsize) fprint(2, "depth == 0! size = %ulld\n", d.size);
47 7763a61a 2003-11-23 devnull d.depth = sizeToDepth(d.size, d.psize, d.dsize);
48 7763a61a 2003-11-23 devnull }
49 7763a61a 2003-11-23 devnull
50 7763a61a 2003-11-23 devnull if(d.depth < sizeToDepth(d.size, d.psize, d.dsize)) {
51 7763a61a 2003-11-23 devnull vtSetError(EBadDir);
52 7763a61a 2003-11-23 devnull return nil;
53 7763a61a 2003-11-23 devnull }
54 7763a61a 2003-11-23 devnull
55 7763a61a 2003-11-23 devnull r = vtMemAllocZ(sizeof(Source));
56 7763a61a 2003-11-23 devnull r->lk = vtLockAlloc();
57 7763a61a 2003-11-23 devnull r->cache = c;
58 7763a61a 2003-11-23 devnull r->readOnly = readOnly;
59 7763a61a 2003-11-23 devnull r->lump = lumpIncRef(u);
60 7763a61a 2003-11-23 devnull r->block = block;
61 7763a61a 2003-11-23 devnull r->entry = entry;
62 7763a61a 2003-11-23 devnull r->gen = d.gen;
63 7763a61a 2003-11-23 devnull r->dir = (d.flags & VtEntryDir) != 0;
64 7763a61a 2003-11-23 devnull r->depth = d.depth;
65 7763a61a 2003-11-23 devnull r->psize = d.psize;
66 7763a61a 2003-11-23 devnull r->dsize = d.dsize;
67 7763a61a 2003-11-23 devnull r->size = d.size;
68 7763a61a 2003-11-23 devnull
69 7763a61a 2003-11-23 devnull r->epb = r->dsize/VtEntrySize;
70 7763a61a 2003-11-23 devnull
71 7763a61a 2003-11-23 devnull return r;
72 7763a61a 2003-11-23 devnull }
73 7763a61a 2003-11-23 devnull
74 7763a61a 2003-11-23 devnull Source *
75 7763a61a 2003-11-23 devnull sourceOpen(Source *r, ulong entry, int readOnly)
76 7763a61a 2003-11-23 devnull {
77 7763a61a 2003-11-23 devnull ulong bn;
78 7763a61a 2003-11-23 devnull Lump *u;
79 7763a61a 2003-11-23 devnull
80 7763a61a 2003-11-23 devnull if(0)fprint(2, "sourceOpen: %V:%d: %lud\n", r->lump->score, r->entry, entry);
81 7763a61a 2003-11-23 devnull if(r->readOnly && !readOnly) {
82 7763a61a 2003-11-23 devnull vtSetError(EReadOnly);
83 7763a61a 2003-11-23 devnull return nil;
84 7763a61a 2003-11-23 devnull }
85 7763a61a 2003-11-23 devnull
86 7763a61a 2003-11-23 devnull bn = entry/r->epb;
87 7763a61a 2003-11-23 devnull
88 7763a61a 2003-11-23 devnull u = sourceGetLump(r, bn, readOnly, 1);
89 7763a61a 2003-11-23 devnull if(u == nil)
90 7763a61a 2003-11-23 devnull return nil;
91 7763a61a 2003-11-23 devnull
92 7763a61a 2003-11-23 devnull r = sourceAlloc(r->cache, u, bn, entry%r->epb, readOnly);
93 7763a61a 2003-11-23 devnull lumpDecRef(u, 1);
94 7763a61a 2003-11-23 devnull return r;
95 7763a61a 2003-11-23 devnull }
96 7763a61a 2003-11-23 devnull
97 7763a61a 2003-11-23 devnull Source *
98 7763a61a 2003-11-23 devnull sourceCreate(Source *r, int psize, int dsize, int isdir, ulong entry)
99 7763a61a 2003-11-23 devnull {
100 7763a61a 2003-11-23 devnull Source *rr;
101 7763a61a 2003-11-23 devnull int i;
102 7763a61a 2003-11-23 devnull Lump *u;
103 7763a61a 2003-11-23 devnull ulong bn;
104 7763a61a 2003-11-23 devnull VtEntry dir;
105 7763a61a 2003-11-23 devnull
106 7763a61a 2003-11-23 devnull if(r->readOnly) {
107 7763a61a 2003-11-23 devnull vtSetError(EReadOnly);
108 7763a61a 2003-11-23 devnull return nil;
109 7763a61a 2003-11-23 devnull }
110 7763a61a 2003-11-23 devnull
111 7763a61a 2003-11-23 devnull if(entry == 0) {
112 7763a61a 2003-11-23 devnull /*
113 7763a61a 2003-11-23 devnull * look at a random block to see if we can find an empty entry
114 7763a61a 2003-11-23 devnull */
115 7763a61a 2003-11-23 devnull entry = sourceGetDirSize(r);
116 7763a61a 2003-11-23 devnull entry = r->epb*lnrand(entry/r->epb+1);
117 7763a61a 2003-11-23 devnull }
118 7763a61a 2003-11-23 devnull
119 7763a61a 2003-11-23 devnull /*
120 7763a61a 2003-11-23 devnull * need to loop since multiple threads could be trying to allocate
121 7763a61a 2003-11-23 devnull */
122 7763a61a 2003-11-23 devnull for(;;) {
123 7763a61a 2003-11-23 devnull bn = entry/r->epb;
124 7763a61a 2003-11-23 devnull sourceSetDepth(r, (uvlong)(bn+1)*r->dsize);
125 7763a61a 2003-11-23 devnull u = sourceGetLump(r, bn, 0, 1);
126 7763a61a 2003-11-23 devnull if(u == nil)
127 7763a61a 2003-11-23 devnull return nil;
128 7763a61a 2003-11-23 devnull for(i=entry%r->epb; i<r->epb; i++) {
129 7763a61a 2003-11-23 devnull vtEntryUnpack(&dir, u->data, i);
130 7763a61a 2003-11-23 devnull if((dir.flags&VtEntryActive) == 0 && dir.gen != ~0)
131 7763a61a 2003-11-23 devnull goto Found;
132 7763a61a 2003-11-23 devnull }
133 7763a61a 2003-11-23 devnull lumpDecRef(u, 1);
134 7763a61a 2003-11-23 devnull entry = sourceGetDirSize(r);
135 7763a61a 2003-11-23 devnull }
136 7763a61a 2003-11-23 devnull Found:
137 7763a61a 2003-11-23 devnull /* found an entry */
138 7763a61a 2003-11-23 devnull dir.psize = psize;
139 7763a61a 2003-11-23 devnull dir.dsize = dsize;
140 7763a61a 2003-11-23 devnull dir.flags = VtEntryActive;
141 7763a61a 2003-11-23 devnull if(isdir)
142 7763a61a 2003-11-23 devnull dir.flags |= VtEntryDir;
143 7763a61a 2003-11-23 devnull dir.depth = 0;
144 7763a61a 2003-11-23 devnull dir.size = 0;
145 7763a61a 2003-11-23 devnull memmove(dir.score, vtZeroScore, VtScoreSize);
146 7763a61a 2003-11-23 devnull vtEntryPack(&dir, u->data, i);
147 7763a61a 2003-11-23 devnull
148 7763a61a 2003-11-23 devnull sourceSetDirSize(r, bn*r->epb + i + 1);
149 7763a61a 2003-11-23 devnull rr = sourceAlloc(r->cache, u, bn, i, 0);
150 7763a61a 2003-11-23 devnull
151 7763a61a 2003-11-23 devnull lumpDecRef(u, 1);
152 7763a61a 2003-11-23 devnull return rr;
153 7763a61a 2003-11-23 devnull }
154 7763a61a 2003-11-23 devnull
155 7763a61a 2003-11-23 devnull void
156 7763a61a 2003-11-23 devnull sourceRemove(Source *r)
157 7763a61a 2003-11-23 devnull {
158 7763a61a 2003-11-23 devnull lumpFreeEntry(r->lump, r->entry);
159 7763a61a 2003-11-23 devnull sourceFree(r);
160 7763a61a 2003-11-23 devnull }
161 7763a61a 2003-11-23 devnull
162 7763a61a 2003-11-23 devnull int
163 7763a61a 2003-11-23 devnull sourceSetDepth(Source *r, uvlong size)
164 7763a61a 2003-11-23 devnull {
165 7763a61a 2003-11-23 devnull Lump *u, *v;
166 7763a61a 2003-11-23 devnull VtEntry dir;
167 7763a61a 2003-11-23 devnull int depth;
168 7763a61a 2003-11-23 devnull
169 7763a61a 2003-11-23 devnull if(r->readOnly){
170 7763a61a 2003-11-23 devnull vtSetError(EReadOnly);
171 7763a61a 2003-11-23 devnull return 0;
172 7763a61a 2003-11-23 devnull }
173 7763a61a 2003-11-23 devnull
174 7763a61a 2003-11-23 devnull depth = sizeToDepth(size, r->psize, r->dsize);
175 7763a61a 2003-11-23 devnull
176 7763a61a 2003-11-23 devnull assert(depth >= 0);
177 7763a61a 2003-11-23 devnull
178 7763a61a 2003-11-23 devnull if(depth > VtPointerDepth) {
179 7763a61a 2003-11-23 devnull vtSetError(ETooBig);
180 7763a61a 2003-11-23 devnull return 0;
181 7763a61a 2003-11-23 devnull }
182 7763a61a 2003-11-23 devnull
183 7763a61a 2003-11-23 devnull vtLock(r->lk);
184 7763a61a 2003-11-23 devnull
185 7763a61a 2003-11-23 devnull if(r->depth >= depth) {
186 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
187 7763a61a 2003-11-23 devnull return 1;
188 7763a61a 2003-11-23 devnull }
189 7763a61a 2003-11-23 devnull
190 7763a61a 2003-11-23 devnull u = r->lump;
191 7763a61a 2003-11-23 devnull vtLock(u->lk);
192 7763a61a 2003-11-23 devnull if(!vtEntryUnpack(&dir, u->data, r->entry)) {
193 7763a61a 2003-11-23 devnull vtUnlock(u->lk);
194 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
195 7763a61a 2003-11-23 devnull return 0;
196 7763a61a 2003-11-23 devnull }
197 7763a61a 2003-11-23 devnull while(dir.depth < depth) {
198 7763a61a 2003-11-23 devnull v = cacheAllocLump(r->cache, VtPointerType0+r->depth, r->psize, r->dir);
199 7763a61a 2003-11-23 devnull if(v == nil)
200 7763a61a 2003-11-23 devnull break;
201 7763a61a 2003-11-23 devnull memmove(v->data, dir.score, VtScoreSize);
202 7763a61a 2003-11-23 devnull memmove(dir.score, v->score, VtScoreSize);
203 7763a61a 2003-11-23 devnull dir.depth++;
204 7763a61a 2003-11-23 devnull vtUnlock(v->lk);
205 7763a61a 2003-11-23 devnull }
206 7763a61a 2003-11-23 devnull vtEntryPack(&dir, u->data, r->entry);
207 7763a61a 2003-11-23 devnull vtUnlock(u->lk);
208 7763a61a 2003-11-23 devnull
209 7763a61a 2003-11-23 devnull r->depth = dir.depth;
210 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
211 7763a61a 2003-11-23 devnull
212 7763a61a 2003-11-23 devnull return dir.depth == depth;
213 7763a61a 2003-11-23 devnull }
214 7763a61a 2003-11-23 devnull
215 7763a61a 2003-11-23 devnull int
216 7763a61a 2003-11-23 devnull sourceGetVtEntry(Source *r, VtEntry *dir)
217 7763a61a 2003-11-23 devnull {
218 7763a61a 2003-11-23 devnull Lump *u;
219 7763a61a 2003-11-23 devnull
220 7763a61a 2003-11-23 devnull u = r->lump;
221 7763a61a 2003-11-23 devnull vtLock(u->lk);
222 7763a61a 2003-11-23 devnull if(!vtEntryUnpack(dir, u->data, r->entry)) {
223 7763a61a 2003-11-23 devnull vtUnlock(u->lk);
224 7763a61a 2003-11-23 devnull return 0;
225 7763a61a 2003-11-23 devnull }
226 7763a61a 2003-11-23 devnull vtUnlock(u->lk);
227 7763a61a 2003-11-23 devnull return 1;
228 7763a61a 2003-11-23 devnull }
229 7763a61a 2003-11-23 devnull
230 7763a61a 2003-11-23 devnull uvlong
231 7763a61a 2003-11-23 devnull sourceGetSize(Source *r)
232 7763a61a 2003-11-23 devnull {
233 7763a61a 2003-11-23 devnull uvlong size;
234 7763a61a 2003-11-23 devnull
235 7763a61a 2003-11-23 devnull vtLock(r->lk);
236 7763a61a 2003-11-23 devnull size = r->size;
237 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
238 7763a61a 2003-11-23 devnull
239 7763a61a 2003-11-23 devnull return size;
240 7763a61a 2003-11-23 devnull }
241 7763a61a 2003-11-23 devnull
242 7763a61a 2003-11-23 devnull
243 7763a61a 2003-11-23 devnull int
244 7763a61a 2003-11-23 devnull sourceSetSize(Source *r, uvlong size)
245 7763a61a 2003-11-23 devnull {
246 7763a61a 2003-11-23 devnull Lump *u;
247 7763a61a 2003-11-23 devnull VtEntry dir;
248 7763a61a 2003-11-23 devnull int depth;
249 7763a61a 2003-11-23 devnull
250 7763a61a 2003-11-23 devnull if(r->readOnly) {
251 7763a61a 2003-11-23 devnull vtSetError(EReadOnly);
252 7763a61a 2003-11-23 devnull return 0;
253 7763a61a 2003-11-23 devnull }
254 7763a61a 2003-11-23 devnull
255 7763a61a 2003-11-23 devnull if(size > VtMaxFileSize || size > ((uvlong)MaxBlock)*r->dsize) {
256 7763a61a 2003-11-23 devnull vtSetError(ETooBig);
257 7763a61a 2003-11-23 devnull return 0;
258 7763a61a 2003-11-23 devnull }
259 7763a61a 2003-11-23 devnull
260 7763a61a 2003-11-23 devnull vtLock(r->lk);
261 7763a61a 2003-11-23 devnull depth = sizeToDepth(size, r->psize, r->dsize);
262 7763a61a 2003-11-23 devnull if(size < r->size) {
263 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
264 7763a61a 2003-11-23 devnull return 1;
265 7763a61a 2003-11-23 devnull }
266 7763a61a 2003-11-23 devnull if(depth > r->depth) {
267 7763a61a 2003-11-23 devnull vtSetError(EBadDir);
268 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
269 7763a61a 2003-11-23 devnull return 0;
270 7763a61a 2003-11-23 devnull }
271 7763a61a 2003-11-23 devnull
272 7763a61a 2003-11-23 devnull u = r->lump;
273 7763a61a 2003-11-23 devnull vtLock(u->lk);
274 7763a61a 2003-11-23 devnull vtEntryUnpack(&dir, u->data, r->entry);
275 7763a61a 2003-11-23 devnull dir.size = size;
276 7763a61a 2003-11-23 devnull vtEntryPack(&dir, u->data, r->entry);
277 7763a61a 2003-11-23 devnull vtUnlock(u->lk);
278 7763a61a 2003-11-23 devnull r->size = size;
279 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
280 7763a61a 2003-11-23 devnull return 1;
281 7763a61a 2003-11-23 devnull }
282 7763a61a 2003-11-23 devnull
283 7763a61a 2003-11-23 devnull int
284 7763a61a 2003-11-23 devnull sourceSetDirSize(Source *r, ulong ds)
285 7763a61a 2003-11-23 devnull {
286 7763a61a 2003-11-23 devnull uvlong size;
287 7763a61a 2003-11-23 devnull
288 7763a61a 2003-11-23 devnull size = (uvlong)r->dsize*(ds/r->epb);
289 7763a61a 2003-11-23 devnull size += VtEntrySize*(ds%r->epb);
290 7763a61a 2003-11-23 devnull return sourceSetSize(r, size);
291 7763a61a 2003-11-23 devnull }
292 7763a61a 2003-11-23 devnull
293 7763a61a 2003-11-23 devnull ulong
294 7763a61a 2003-11-23 devnull sourceGetDirSize(Source *r)
295 7763a61a 2003-11-23 devnull {
296 7763a61a 2003-11-23 devnull ulong ds;
297 7763a61a 2003-11-23 devnull uvlong size;
298 7763a61a 2003-11-23 devnull
299 7763a61a 2003-11-23 devnull size = sourceGetSize(r);
300 7763a61a 2003-11-23 devnull ds = r->epb*(size/r->dsize);
301 7763a61a 2003-11-23 devnull ds += (size%r->dsize)/VtEntrySize;
302 7763a61a 2003-11-23 devnull return ds;
303 7763a61a 2003-11-23 devnull }
304 7763a61a 2003-11-23 devnull
305 7763a61a 2003-11-23 devnull ulong
306 7763a61a 2003-11-23 devnull sourceGetNumBlocks(Source *r)
307 7763a61a 2003-11-23 devnull {
308 7763a61a 2003-11-23 devnull return (sourceGetSize(r)+r->dsize-1)/r->dsize;
309 7763a61a 2003-11-23 devnull }
310 7763a61a 2003-11-23 devnull
311 7763a61a 2003-11-23 devnull Lump *
312 7763a61a 2003-11-23 devnull sourceWalk(Source *r, ulong block, int readOnly, int *off)
313 7763a61a 2003-11-23 devnull {
314 7763a61a 2003-11-23 devnull int depth;
315 7763a61a 2003-11-23 devnull int i, np;
316 7763a61a 2003-11-23 devnull Lump *u, *v;
317 7763a61a 2003-11-23 devnull int elem[VtPointerDepth+1];
318 7763a61a 2003-11-23 devnull ulong b;
319 7763a61a 2003-11-23 devnull
320 7763a61a 2003-11-23 devnull if(r->readOnly && !readOnly) {
321 7763a61a 2003-11-23 devnull vtSetError(EReadOnly);
322 7763a61a 2003-11-23 devnull return nil;
323 7763a61a 2003-11-23 devnull }
324 7763a61a 2003-11-23 devnull
325 7763a61a 2003-11-23 devnull vtLock(r->lk);
326 7763a61a 2003-11-23 devnull np = r->psize/VtScoreSize;
327 7763a61a 2003-11-23 devnull b = block;
328 7763a61a 2003-11-23 devnull for(i=0; i<r->depth; i++) {
329 7763a61a 2003-11-23 devnull elem[i] = b % np;
330 7763a61a 2003-11-23 devnull b /= np;
331 7763a61a 2003-11-23 devnull }
332 7763a61a 2003-11-23 devnull if(b != 0) {
333 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
334 7763a61a 2003-11-23 devnull vtSetError(EBadOffset);
335 7763a61a 2003-11-23 devnull return nil;
336 7763a61a 2003-11-23 devnull }
337 7763a61a 2003-11-23 devnull elem[i] = r->entry;
338 7763a61a 2003-11-23 devnull u = lumpIncRef(r->lump);
339 7763a61a 2003-11-23 devnull depth = r->depth;
340 7763a61a 2003-11-23 devnull *off = elem[0];
341 7763a61a 2003-11-23 devnull vtUnlock(r->lk);
342 7763a61a 2003-11-23 devnull
343 7763a61a 2003-11-23 devnull for(i=depth; i>0; i--) {
344 7763a61a 2003-11-23 devnull v = lumpWalk(u, elem[i], VtPointerType0+i-1, r->psize, readOnly, 0);
345 7763a61a 2003-11-23 devnull lumpDecRef(u, 0);
346 7763a61a 2003-11-23 devnull if(v == nil)
347 7763a61a 2003-11-23 devnull return nil;
348 7763a61a 2003-11-23 devnull u = v;
349 7763a61a 2003-11-23 devnull }
350 7763a61a 2003-11-23 devnull
351 7763a61a 2003-11-23 devnull return u;
352 7763a61a 2003-11-23 devnull }
353 7763a61a 2003-11-23 devnull
354 7763a61a 2003-11-23 devnull Lump *
355 7763a61a 2003-11-23 devnull sourceGetLump(Source *r, ulong block, int readOnly, int lock)
356 7763a61a 2003-11-23 devnull {
357 7763a61a 2003-11-23 devnull int type, off;
358 7763a61a 2003-11-23 devnull Lump *u, *v;
359 7763a61a 2003-11-23 devnull
360 7763a61a 2003-11-23 devnull if(r->readOnly && !readOnly) {
361 7763a61a 2003-11-23 devnull vtSetError(EReadOnly);
362 7763a61a 2003-11-23 devnull return nil;
363 7763a61a 2003-11-23 devnull }
364 7763a61a 2003-11-23 devnull if(block == NilBlock) {
365 7763a61a 2003-11-23 devnull vtSetError(ENilBlock);
366 7763a61a 2003-11-23 devnull return nil;
367 7763a61a 2003-11-23 devnull }
368 7763a61a 2003-11-23 devnull if(0)fprint(2, "sourceGetLump: %V:%d %lud\n", r->lump->score, r->entry, block);
369 7763a61a 2003-11-23 devnull u = sourceWalk(r, block, readOnly, &off);
370 7763a61a 2003-11-23 devnull if(u == nil)
371 7763a61a 2003-11-23 devnull return nil;
372 7763a61a 2003-11-23 devnull if(r->dir)
373 7763a61a 2003-11-23 devnull type = VtDirType;
374 7763a61a 2003-11-23 devnull else
375 7763a61a 2003-11-23 devnull type = VtDataType;
376 7763a61a 2003-11-23 devnull v = lumpWalk(u, off, type, r->dsize, readOnly, lock);
377 7763a61a 2003-11-23 devnull lumpDecRef(u, 0);
378 7763a61a 2003-11-23 devnull return v;
379 7763a61a 2003-11-23 devnull }
380 7763a61a 2003-11-23 devnull
381 7763a61a 2003-11-23 devnull void
382 7763a61a 2003-11-23 devnull sourceFree(Source *k)
383 7763a61a 2003-11-23 devnull {
384 7763a61a 2003-11-23 devnull if(k == nil)
385 7763a61a 2003-11-23 devnull return;
386 7763a61a 2003-11-23 devnull lumpDecRef(k->lump, 0);
387 7763a61a 2003-11-23 devnull vtLockFree(k->lk);
388 7763a61a 2003-11-23 devnull memset(k, ~0, sizeof(*k));
389 7763a61a 2003-11-23 devnull vtMemFree(k);
390 7763a61a 2003-11-23 devnull }