coda_subr.c (116173) | coda_subr.c (119832) |
---|---|
1/* 2 * Coda: an Experimental Distributed File System 3 * Release 3.1 4 * 5 * Copyright (c) 1987-1998 Carnegie Mellon University 6 * All Rights Reserved 7 * 8 * Permission to use, copy, modify and distribute this software and its --- 38 unchanged lines hidden (view full) --- 47 * The vnode pager does this. 48 * 2. coda_unmounting marks all cnodes scanning coda_cache. 49 * 3. cfs_checkunmounting (under DEBUG) checks all cnodes by chasing the vnodes 50 * under the /coda mount point. 51 * 4. coda_cacheprint (under DEBUG) prints names with vnode/cnode address 52 */ 53 54#include <sys/cdefs.h> | 1/* 2 * Coda: an Experimental Distributed File System 3 * Release 3.1 4 * 5 * Copyright (c) 1987-1998 Carnegie Mellon University 6 * All Rights Reserved 7 * 8 * Permission to use, copy, modify and distribute this software and its --- 38 unchanged lines hidden (view full) --- 47 * The vnode pager does this. 48 * 2. coda_unmounting marks all cnodes scanning coda_cache. 49 * 3. cfs_checkunmounting (under DEBUG) checks all cnodes by chasing the vnodes 50 * under the /coda mount point. 51 * 4. coda_cacheprint (under DEBUG) prints names with vnode/cnode address 52 */ 53 54#include <sys/cdefs.h> |
55__FBSDID("$FreeBSD: head/sys/fs/coda/coda_subr.c 116173 2003-06-10 21:29:12Z obrien $"); | 55__FBSDID("$FreeBSD: head/sys/fs/coda/coda_subr.c 119832 2003-09-07 07:43:10Z tjr $"); |
56 57#include <vcoda.h> 58 59#include <sys/param.h> 60#include <sys/systm.h> 61#include <sys/lock.h> 62#include <sys/malloc.h> 63#include <sys/mount.h> --- 5 unchanged lines hidden (view full) --- 69 70int coda_active = 0; 71int coda_reuse = 0; 72int coda_new = 0; 73 74struct cnode *coda_freelist = NULL; 75struct cnode *coda_cache[CODA_CACHESIZE]; 76 | 56 57#include <vcoda.h> 58 59#include <sys/param.h> 60#include <sys/systm.h> 61#include <sys/lock.h> 62#include <sys/malloc.h> 63#include <sys/mount.h> --- 5 unchanged lines hidden (view full) --- 69 70int coda_active = 0; 71int coda_reuse = 0; 72int coda_new = 0; 73 74struct cnode *coda_freelist = NULL; 75struct cnode *coda_cache[CODA_CACHESIZE]; 76 |
77#define coda_hash(fid) (((fid)->Volume + (fid)->Vnode) & (CODA_CACHESIZE-1)) | |
78#define CNODE_NEXT(cp) ((cp)->c_next) | 77#define CNODE_NEXT(cp) ((cp)->c_next) |
79#define ODD(vnode) ((vnode) & 0x1) | |
80 | 78 |
79#ifdef CODA_COMPAT_5 80#define coda_hash(fid) \ 81 (((fid)->Volume + (fid)->Vnode) & (CODA_CACHESIZE-1)) 82#define IS_DIR(cnode) (cnode.Vnode & 0x1) 83#else 84#define coda_hash(fid) (coda_f2i(fid) & (CODA_CACHESIZE-1)) 85#define IS_DIR(cnode) (cnode.opaque[2] & 0x1) 86#endif 87 |
|
81/* 82 * Allocate a cnode. 83 */ 84struct cnode * 85coda_alloc(void) 86{ 87 struct cnode *cp; 88 --- 67 unchanged lines hidden (view full) --- 156} 157 158/* 159 * Lookup a cnode by fid. If the cnode is dying, it is bogus so skip it. 160 * NOTE: this allows multiple cnodes with same fid -- dcs 1/25/95 161 */ 162struct cnode * 163coda_find(fid) | 88/* 89 * Allocate a cnode. 90 */ 91struct cnode * 92coda_alloc(void) 93{ 94 struct cnode *cp; 95 --- 67 unchanged lines hidden (view full) --- 163} 164 165/* 166 * Lookup a cnode by fid. If the cnode is dying, it is bogus so skip it. 167 * NOTE: this allows multiple cnodes with same fid -- dcs 1/25/95 168 */ 169struct cnode * 170coda_find(fid) |
164 ViceFid *fid; | 171 CodaFid *fid; |
165{ 166 struct cnode *cp; 167 168 cp = coda_cache[coda_hash(fid)]; 169 while (cp) { | 172{ 173 struct cnode *cp; 174 175 cp = coda_cache[coda_hash(fid)]; 176 while (cp) { |
170 if ((cp->c_fid.Vnode == fid->Vnode) && 171 (cp->c_fid.Volume == fid->Volume) && 172 (cp->c_fid.Unique == fid->Unique) && | 177 if (coda_fid_eq(&(cp->c_fid), fid) && |
173 (!IS_UNMOUNTING(cp))) 174 { 175 coda_active++; 176 return(cp); 177 } 178 cp = CNODE_NEXT(cp); 179 } 180 return(NULL); --- 32 unchanged lines hidden (view full) --- 213 for (hash = 0; hash < CODA_CACHESIZE; hash++) { 214 for (cp = coda_cache[hash]; cp != NULL; cp = CNODE_NEXT(cp)) { 215 if (CTOV(cp)->v_mount == whoIam) { 216#ifdef DEBUG 217 printf("coda_kill: vp %p, cp %p\n", CTOV(cp), cp); 218#endif 219 count++; 220 CODADEBUG(CODA_FLUSH, | 178 (!IS_UNMOUNTING(cp))) 179 { 180 coda_active++; 181 return(cp); 182 } 183 cp = CNODE_NEXT(cp); 184 } 185 return(NULL); --- 32 unchanged lines hidden (view full) --- 218 for (hash = 0; hash < CODA_CACHESIZE; hash++) { 219 for (cp = coda_cache[hash]; cp != NULL; cp = CNODE_NEXT(cp)) { 220 if (CTOV(cp)->v_mount == whoIam) { 221#ifdef DEBUG 222 printf("coda_kill: vp %p, cp %p\n", CTOV(cp), cp); 223#endif 224 count++; 225 CODADEBUG(CODA_FLUSH, |
221 myprintf(("Live cnode fid %lx.%lx.%lx flags %d count %d\n", 222 (cp->c_fid).Volume, 223 (cp->c_fid).Vnode, 224 (cp->c_fid).Unique, 225 cp->c_flags, 226 vrefcnt(CTOV(cp)))); ); | 226 myprintf(("Live cnode fid %s flags %d count %d\n", 227 coda_f2s(&cp->c_fid), 228 cp->c_flags, 229 vrefcnt(CTOV(cp)))); ); |
227 } 228 } 229 } 230 return count; 231} 232 233/* 234 * There are two reasons why a cnode may be in use, it may be in the --- 8 unchanged lines hidden (view full) --- 243 244 coda_clstat.ncalls++; 245 coda_clstat.reqs[CODA_FLUSH]++; 246 247 coda_nc_flush(dcstat); /* flush files from the name cache */ 248 249 for (hash = 0; hash < CODA_CACHESIZE; hash++) { 250 for (cp = coda_cache[hash]; cp != NULL; cp = CNODE_NEXT(cp)) { | 230 } 231 } 232 } 233 return count; 234} 235 236/* 237 * There are two reasons why a cnode may be in use, it may be in the --- 8 unchanged lines hidden (view full) --- 246 247 coda_clstat.ncalls++; 248 coda_clstat.reqs[CODA_FLUSH]++; 249 250 coda_nc_flush(dcstat); /* flush files from the name cache */ 251 252 for (hash = 0; hash < CODA_CACHESIZE; hash++) { 253 for (cp = coda_cache[hash]; cp != NULL; cp = CNODE_NEXT(cp)) { |
251 if (!ODD(cp->c_fid.Vnode)) /* only files can be executed */ | 254 if (!IS_DIR(cp->c_fid)) /* only files can be executed */ |
252 coda_vmflush(cp); 253 } 254 } 255} 256 257/* 258 * As a debugging measure, print out any cnodes that lived through a 259 * name cache flush. 260 */ 261void 262coda_testflush(void) 263{ 264 int hash; 265 struct cnode *cp; 266 267 for (hash = 0; hash < CODA_CACHESIZE; hash++) { 268 for (cp = coda_cache[hash]; 269 cp != NULL; 270 cp = CNODE_NEXT(cp)) { | 255 coda_vmflush(cp); 256 } 257 } 258} 259 260/* 261 * As a debugging measure, print out any cnodes that lived through a 262 * name cache flush. 263 */ 264void 265coda_testflush(void) 266{ 267 int hash; 268 struct cnode *cp; 269 270 for (hash = 0; hash < CODA_CACHESIZE; hash++) { 271 for (cp = coda_cache[hash]; 272 cp != NULL; 273 cp = CNODE_NEXT(cp)) { |
271 myprintf(("Live cnode fid %lx.%lx.%lx count %d\n", 272 (cp->c_fid).Volume,(cp->c_fid).Vnode, 273 (cp->c_fid).Unique, vrefcnt(CTOV(cp)))); | 274 myprintf(("Live cnode fid %s count %d\n", 275 coda_f2s(&cp->c_fid), CTOV(cp)->v_usecount)); |
274 } 275 } 276} 277 278/* 279 * First, step through all cnodes and mark them unmounting. 280 * NetBSD kernels may try to fsync them now that venus 281 * is dead, which would be a bad thing. --- 86 unchanged lines hidden (view full) --- 368 * CODA_PURGEFID -- flush the attribute for the file 369 * If it is a dir (odd vnode), purge its 370 * children from the namecache 371 * remove the file from the namecache. 372 * 373 * The sixth allows Venus to replace local fids with global ones 374 * during reintegration. 375 * | 276 } 277 } 278} 279 280/* 281 * First, step through all cnodes and mark them unmounting. 282 * NetBSD kernels may try to fsync them now that venus 283 * is dead, which would be a bad thing. --- 86 unchanged lines hidden (view full) --- 370 * CODA_PURGEFID -- flush the attribute for the file 371 * If it is a dir (odd vnode), purge its 372 * children from the namecache 373 * remove the file from the namecache. 374 * 375 * The sixth allows Venus to replace local fids with global ones 376 * during reintegration. 377 * |
376 * CODA_REPLACE -- replace one ViceFid with another throughout the name cache | 378 * CODA_REPLACE -- replace one CodaFid with another throughout the name cache |
377 */ 378 379int handleDownCall(opcode, out) 380 int opcode; union outputArgs *out; 381{ 382 int error; 383 384 /* Handle invalidate requests. */ --- 6 unchanged lines hidden (view full) --- 391 return(0); 392 } 393 394 case CODA_PURGEUSER : { 395 coda_clstat.ncalls++; 396 coda_clstat.reqs[CODA_PURGEUSER]++; 397 398 /* XXX - need to prevent fsync's */ | 379 */ 380 381int handleDownCall(opcode, out) 382 int opcode; union outputArgs *out; 383{ 384 int error; 385 386 /* Handle invalidate requests. */ --- 6 unchanged lines hidden (view full) --- 393 return(0); 394 } 395 396 case CODA_PURGEUSER : { 397 coda_clstat.ncalls++; 398 coda_clstat.reqs[CODA_PURGEUSER]++; 399 400 /* XXX - need to prevent fsync's */ |
401#ifdef CODA_COMPAT_5 |
|
399 coda_nc_purge_user(out->coda_purgeuser.cred.cr_uid, IS_DOWNCALL); | 402 coda_nc_purge_user(out->coda_purgeuser.cred.cr_uid, IS_DOWNCALL); |
403#else 404 coda_nc_purge_user(out->coda_purgeuser.uid, IS_DOWNCALL); 405#endif |
|
400 return(0); 401 } 402 403 case CODA_ZAPFILE : { 404 struct cnode *cp; 405 406 error = 0; 407 coda_clstat.ncalls++; 408 coda_clstat.reqs[CODA_ZAPFILE]++; 409 | 406 return(0); 407 } 408 409 case CODA_ZAPFILE : { 410 struct cnode *cp; 411 412 error = 0; 413 coda_clstat.ncalls++; 414 coda_clstat.reqs[CODA_ZAPFILE]++; 415 |
410 cp = coda_find(&out->coda_zapfile.CodaFid); | 416 cp = coda_find(&out->coda_zapfile.Fid); |
411 if (cp != NULL) { 412 vref(CTOV(cp)); 413 414 cp->c_flags &= ~C_VATTR; 415 ASSERT_VOP_LOCKED(CTOV(cp), "coda HandleDownCall"); 416 if (CTOV(cp)->v_vflag & VV_TEXT) 417 error = coda_vmflush(cp); | 417 if (cp != NULL) { 418 vref(CTOV(cp)); 419 420 cp->c_flags &= ~C_VATTR; 421 ASSERT_VOP_LOCKED(CTOV(cp), "coda HandleDownCall"); 422 if (CTOV(cp)->v_vflag & VV_TEXT) 423 error = coda_vmflush(cp); |
418 CODADEBUG(CODA_ZAPFILE, myprintf(( 419"zapfile: fid = (%lx.%lx.%lx), refcnt = %d, error = %d\n", 420 cp->c_fid.Volume, cp->c_fid.Vnode, cp->c_fid.Unique, 421 vrefcnt(CTOV(cp)) - 1, error));); 422 if (vrefcnt(CTOV(cp)) == 1) { | 424 CODADEBUG(CODA_ZAPFILE, 425 myprintf(("zapfile: fid = %s, refcnt = %d, error = %d\n", 426 coda_f2s(&cp->c_fid), CTOV(cp)->v_usecount - 1, error));); 427 if (vrefcnt(CTOV(cp)) == 1) { |
423 cp->c_flags |= C_PURGING; 424 } 425 vrele(CTOV(cp)); 426 } 427 428 return(error); 429 } 430 431 case CODA_ZAPDIR : { 432 struct cnode *cp; 433 434 coda_clstat.ncalls++; 435 coda_clstat.reqs[CODA_ZAPDIR]++; 436 | 428 cp->c_flags |= C_PURGING; 429 } 430 vrele(CTOV(cp)); 431 } 432 433 return(error); 434 } 435 436 case CODA_ZAPDIR : { 437 struct cnode *cp; 438 439 coda_clstat.ncalls++; 440 coda_clstat.reqs[CODA_ZAPDIR]++; 441 |
437 cp = coda_find(&out->coda_zapdir.CodaFid); | 442 cp = coda_find(&out->coda_zapdir.Fid); |
438 if (cp != NULL) { 439 vref(CTOV(cp)); 440 441 cp->c_flags &= ~C_VATTR; | 443 if (cp != NULL) { 444 vref(CTOV(cp)); 445 446 cp->c_flags &= ~C_VATTR; |
442 coda_nc_zapParentfid(&out->coda_zapdir.CodaFid, IS_DOWNCALL); | 447 coda_nc_zapParentfid(&out->coda_zapdir.Fid, IS_DOWNCALL); |
443 444 CODADEBUG(CODA_ZAPDIR, myprintf(( | 448 449 CODADEBUG(CODA_ZAPDIR, myprintf(( |
445"zapdir: fid = (%lx.%lx.%lx), refcnt = %d\n", 446 cp->c_fid.Volume, cp->c_fid.Vnode, cp->c_fid.Unique, 447 vrefcnt(CTOV(cp)) - 1));); | 450 "zapdir: fid = %s, refcnt = %d\n", 451 coda_f2s(&cp->c_fid), CTOV(cp)->v_usecount - 1));); |
448 if (vrefcnt(CTOV(cp)) == 1) { 449 cp->c_flags |= C_PURGING; 450 } 451 vrele(CTOV(cp)); 452 } 453 454 return(0); 455 } 456 457 case CODA_PURGEFID : { 458 struct cnode *cp; 459 460 error = 0; 461 coda_clstat.ncalls++; 462 coda_clstat.reqs[CODA_PURGEFID]++; 463 | 452 if (vrefcnt(CTOV(cp)) == 1) { 453 cp->c_flags |= C_PURGING; 454 } 455 vrele(CTOV(cp)); 456 } 457 458 return(0); 459 } 460 461 case CODA_PURGEFID : { 462 struct cnode *cp; 463 464 error = 0; 465 coda_clstat.ncalls++; 466 coda_clstat.reqs[CODA_PURGEFID]++; 467 |
464 cp = coda_find(&out->coda_purgefid.CodaFid); | 468 cp = coda_find(&out->coda_purgefid.Fid); |
465 if (cp != NULL) { 466 vref(CTOV(cp)); | 469 if (cp != NULL) { 470 vref(CTOV(cp)); |
467 if (ODD(out->coda_purgefid.CodaFid.Vnode)) { /* Vnode is a directory */ 468 coda_nc_zapParentfid(&out->coda_purgefid.CodaFid, 469 IS_DOWNCALL); | 471 if (IS_DIR(out->coda_purgefid.Fid)) { /* Vnode is a directory */ 472 coda_nc_zapParentfid(&out->coda_purgefid.Fid,IS_DOWNCALL); |
470 } 471 cp->c_flags &= ~C_VATTR; | 473 } 474 cp->c_flags &= ~C_VATTR; |
472 coda_nc_zapfid(&out->coda_purgefid.CodaFid, IS_DOWNCALL); | 475 coda_nc_zapfid(&out->coda_purgefid.Fid, IS_DOWNCALL); |
473 ASSERT_VOP_LOCKED(CTOV(cp), "coda HandleDownCall"); | 476 ASSERT_VOP_LOCKED(CTOV(cp), "coda HandleDownCall"); |
474 if (!(ODD(out->coda_purgefid.CodaFid.Vnode)) | 477 if (!(IS_DIR(out->coda_purgefid.Fid)) |
475 && (CTOV(cp)->v_vflag & VV_TEXT)) { 476 477 error = coda_vmflush(cp); 478 } | 478 && (CTOV(cp)->v_vflag & VV_TEXT)) { 479 480 error = coda_vmflush(cp); 481 } |
479 CODADEBUG(CODA_PURGEFID, myprintf(("purgefid: fid = (%lx.%lx.%lx), refcnt = %d, error = %d\n", 480 cp->c_fid.Volume, cp->c_fid.Vnode, 481 cp->c_fid.Unique, 482 vrefcnt(CTOV(cp)) - 1, error));); | 482 CODADEBUG(CODA_PURGEFID, myprintf(( 483 "purgefid: fid = %s, refcnt = %d, error = %d\n", 484 coda_f2s(&cp->c_fid), CTOV(cp)->v_usecount - 1, error));); |
483 if (vrefcnt(CTOV(cp)) == 1) { 484 cp->c_flags |= C_PURGING; 485 } 486 vrele(CTOV(cp)); 487 } 488 return(error); 489 } 490 --- 6 unchanged lines hidden (view full) --- 497 cp = coda_find(&out->coda_replace.OldFid); 498 if (cp != NULL) { 499 /* remove the cnode from the hash table, replace the fid, and reinsert */ 500 vref(CTOV(cp)); 501 coda_unsave(cp); 502 cp->c_fid = out->coda_replace.NewFid; 503 coda_save(cp); 504 | 485 if (vrefcnt(CTOV(cp)) == 1) { 486 cp->c_flags |= C_PURGING; 487 } 488 vrele(CTOV(cp)); 489 } 490 return(error); 491 } 492 --- 6 unchanged lines hidden (view full) --- 499 cp = coda_find(&out->coda_replace.OldFid); 500 if (cp != NULL) { 501 /* remove the cnode from the hash table, replace the fid, and reinsert */ 502 vref(CTOV(cp)); 503 coda_unsave(cp); 504 cp->c_fid = out->coda_replace.NewFid; 505 coda_save(cp); 506 |
505 CODADEBUG(CODA_REPLACE, myprintf(("replace: oldfid = (%lx.%lx.%lx), newfid = (%lx.%lx.%lx), cp = %p\n", 506 out->coda_replace.OldFid.Volume, 507 out->coda_replace.OldFid.Vnode, 508 out->coda_replace.OldFid.Unique, 509 cp->c_fid.Volume, cp->c_fid.Vnode, 510 cp->c_fid.Unique, cp));) 511 vrele(CTOV(cp)); | 507 CODADEBUG(CODA_REPLACE, myprintf(( 508 "replace: oldfid = %s, newfid = %s, cp = %p\n", 509 coda_f2s(&out->coda_replace.OldFid), 510 coda_f2s(&cp->c_fid), cp));) vrele(CTOV(cp)); |
512 } 513 return (0); 514 } 515 default: 516 myprintf(("handleDownCall: unknown opcode %d\n", opcode)); 517 return (EINVAL); 518 } 519} --- 51 unchanged lines hidden --- | 511 } 512 return (0); 513 } 514 default: 515 myprintf(("handleDownCall: unknown opcode %d\n", opcode)); 516 return (EINVAL); 517 } 518} --- 51 unchanged lines hidden --- |