1*6490Smckusick static char *sccsid = "@(#)icheck.c 2.1 (Berkeley) 04/08/82"; 24410Smckusic 34240Smckusick /* 44240Smckusick * icheck 54240Smckusick */ 64240Smckusick #define NB 500 74240Smckusick #define MAXFN 500 85349Smckusic #define MAXNINDIR (MAXBSIZE / sizeof (daddr_t)) 94240Smckusick 104240Smckusick #ifndef STANDALONE 114240Smckusick #include <stdio.h> 124240Smckusick #endif 13*6490Smckusick #ifndef SIMFS 14*6490Smckusick #include <sys/param.h> 15*6490Smckusick #include <sys/inode.h> 16*6490Smckusick #include <sys/fs.h> 17*6490Smckusick #else 184240Smckusick #include "../h/param.h" 194240Smckusick #include "../h/inode.h" 204240Smckusick #include "../h/fs.h" 21*6490Smckusick #endif 224240Smckusick 234240Smckusick union { 244240Smckusick struct fs sb; 255326Smckusic char pad[MAXBSIZE]; 264240Smckusick } sbun; 274240Smckusick #define sblock sbun.sb 284240Smckusick 294240Smckusick union { 304240Smckusick struct cg cg; 315326Smckusic char pad[MAXBSIZE]; 324240Smckusick } cgun; 334240Smckusick #define cgrp cgun.cg 344240Smckusick 354240Smckusick struct dinode itab[MAXIPG]; 364240Smckusick daddr_t blist[NB]; 374240Smckusick char *bmap; 384240Smckusick 394240Smckusick int mflg; 405098Smckusic int sflg; 414240Smckusick int dflg; 424240Smckusick int fi; 434240Smckusick ino_t ino; 444240Smckusick int cginit; 454240Smckusick 464240Smckusick ino_t nrfile; 474240Smckusick ino_t ndfile; 484240Smckusick ino_t nbfile; 494240Smckusick ino_t ncfile; 506286Smckusick ino_t nlfile; 514240Smckusick 524240Smckusick daddr_t nblock; 534240Smckusick daddr_t nfrag; 544240Smckusick daddr_t nindir; 554240Smckusick daddr_t niindir; 564240Smckusick 574240Smckusick daddr_t nffree; 584240Smckusick daddr_t nbfree; 594240Smckusick 604240Smckusick daddr_t ndup; 614240Smckusick 624240Smckusick int nerror; 634240Smckusick 645098Smckusic extern int inside[], around[]; 655326Smckusic extern unsigned char *fragtbl[]; 665098Smckusic 674240Smckusick long atol(); 684240Smckusick #ifndef STANDALONE 694240Smckusick char *malloc(); 705098Smckusic char *calloc(); 714240Smckusick #endif 724240Smckusick 734240Smckusick main(argc, argv) 745098Smckusic int argc; 755098Smckusic char *argv[]; 764240Smckusick { 774240Smckusick register i; 784240Smckusick long n; 794240Smckusick 804240Smckusick blist[0] = -1; 814240Smckusick #ifndef STANDALONE 824240Smckusick while (--argc) { 834240Smckusick argv++; 844240Smckusick if (**argv=='-') 854240Smckusick switch ((*argv)[1]) { 864240Smckusick case 'd': 874240Smckusick dflg++; 884240Smckusick continue; 894240Smckusick 904240Smckusick case 'm': 914240Smckusick mflg++; 924240Smckusick continue; 934240Smckusick 945098Smckusic case 's': 955098Smckusic sflg++; 965098Smckusic continue; 975098Smckusic 984240Smckusick case 'b': 994240Smckusick for(i=0; i<NB; i++) { 1004240Smckusick n = atol(argv[1]); 1014240Smckusick if(n == 0) 1024240Smckusick break; 1034240Smckusick blist[i] = n; 1044240Smckusick argv++; 1054240Smckusick argc--; 1064240Smckusick } 1074240Smckusick blist[i] = -1; 1084240Smckusick continue; 1094240Smckusick 1104240Smckusick default: 1114240Smckusick printf("Bad flag\n"); 1124240Smckusick } 1134240Smckusick check(*argv); 1144240Smckusick } 1154240Smckusick #else 1164240Smckusick { 1174240Smckusick static char fname[128]; 1184240Smckusick 1194240Smckusick printf("File: "); 1204240Smckusick gets(fname); 1214240Smckusick check(fname); 1224240Smckusick } 1234240Smckusick #endif 1244240Smckusick return(nerror); 1254240Smckusick } 1264240Smckusick 1274240Smckusick check(file) 1285098Smckusic char *file; 1294240Smckusick { 1304240Smckusick register i, j, c; 1314240Smckusick daddr_t d, cgd, cbase, b; 1324240Smckusick long n; 1334240Smckusick 1345098Smckusic fi = open(file, sflg ? 2 : 0); 1354240Smckusick if (fi < 0) { 1365098Smckusic perror(file); 1374240Smckusick nerror |= 04; 1384240Smckusick return; 1394240Smckusick } 1404240Smckusick printf("%s:\n", file); 1414240Smckusick nrfile = 0; 1424240Smckusick ndfile = 0; 1434240Smckusick ncfile = 0; 1444240Smckusick nbfile = 0; 1456286Smckusick nlfile = 0; 1464240Smckusick 1474240Smckusick nblock = 0; 1484240Smckusick nfrag = 0; 1494240Smckusick nindir = 0; 1504240Smckusick niindir = 0; 1514240Smckusick 1524240Smckusick ndup = 0; 1534240Smckusick #ifndef STANDALONE 1544240Smckusick sync(); 1554240Smckusick #endif 1565326Smckusic getsb(&sblock, file); 1575326Smckusic if (nerror) 1584240Smckusick return; 1594240Smckusick ino = 0; 1605098Smckusic n = roundup(howmany(sblock.fs_size, NBBY), sizeof(short)); 1614240Smckusick #ifdef STANDALONE 1624240Smckusick bmap = NULL; 1634240Smckusick #else 1644240Smckusick bmap = malloc((unsigned)n); 1654240Smckusick #endif 1664240Smckusick if (bmap==NULL) { 1674240Smckusick printf("Not enough core; duplicates unchecked\n"); 1684240Smckusick dflg++; 1695098Smckusic if (sflg) { 1705098Smckusic printf("No Updates\n"); 1715098Smckusic sflg = 0; 1725098Smckusic } 1734240Smckusick } 1744240Smckusick ino = 0; 1754240Smckusick cginit = 1; 1764240Smckusick if(!dflg) { 1774240Smckusick for (i=0; i<(unsigned)n; i++) 1784240Smckusick bmap[i] = 0; 1794240Smckusick for (c=0; c < sblock.fs_ncg; c++) { 1805382Smckusic cgd = cgtod(&sblock, c); 1815382Smckusic for (d = cgbase(&sblock, c); d < cgd; d += sblock.fs_frag) 1825326Smckusic chk(d, "badcg", sblock.fs_bsize); 1835382Smckusic d = cgimin(&sblock, c); 1844240Smckusick while (cgd < d) { 1855326Smckusic chk(cgd, "cg", sblock.fs_bsize); 1865326Smckusic cgd += sblock.fs_frag; 1874240Smckusick } 1885382Smckusic d = cgdmin(&sblock, c); 1895326Smckusic for (; cgd < d; cgd += sblock.fs_frag) 1905326Smckusic chk(cgd, "inode", sblock.fs_bsize); 1914240Smckusick if (c == 0) { 1925326Smckusic d += howmany(sblock.fs_cssize, sblock.fs_bsize) 1935326Smckusic * sblock.fs_frag; 1945326Smckusic for (; cgd < d; cgd += sblock.fs_frag) 1955326Smckusic chk(cgd, "csum", sblock.fs_bsize); 1964240Smckusick } 1974240Smckusick } 1984240Smckusick } 1994240Smckusick cginit = 0; 2004240Smckusick for (c = 0; c < sblock.fs_ncg; c++) { 2015382Smckusic bread(fsbtodb(&sblock, cgimin(&sblock, c)), (char *)itab, 2024240Smckusick sblock.fs_ipg * sizeof (struct dinode)); 2034240Smckusick for (j=0; j < sblock.fs_ipg; j++) { 2044240Smckusick pass1(&itab[j]); 2054240Smckusick ino++; 2064240Smckusick } 2074240Smckusick } 2084240Smckusick ino = 0; 2094240Smckusick #ifndef STANDALONE 2104240Smckusick sync(); 2114240Smckusick #endif 2125098Smckusic if (sflg) { 2135098Smckusic makecg(); 2145098Smckusic close(fi); 2155098Smckusic #ifndef STANDALONE 2165098Smckusic if (bmap) 2175098Smckusic free(bmap); 2185098Smckusic #endif 2195098Smckusic return; 2205098Smckusic } 2214240Smckusick nffree = 0; 2224240Smckusick nbfree = 0; 2234240Smckusick for (c = 0; c < sblock.fs_ncg; c++) { 2245382Smckusic cbase = cgbase(&sblock, c); 2255382Smckusic bread(fsbtodb(&sblock, cgtod(&sblock, c)), (char *)&cgrp, 2265326Smckusic sblock.fs_cgsize); 2275326Smckusic for (b = 0; b < sblock.fs_fpg; b += sblock.fs_frag) { 2285326Smckusic if (isblock(&sblock, cgrp.cg_free, 2295326Smckusic b / sblock.fs_frag)) { 2304240Smckusick nbfree++; 2315326Smckusic chk(cbase+b, "block", sblock.fs_bsize); 2324240Smckusick } else { 2335326Smckusic for (d = 0; d < sblock.fs_frag; d++) 2344240Smckusick if (isset(cgrp.cg_free, b+d)) { 2355326Smckusic chk(cbase+b+d, "frag", sblock.fs_fsize); 2364240Smckusick nffree++; 2374240Smckusick } 2384240Smckusick } 2394240Smckusick } 2404240Smckusick } 2414240Smckusick close(fi); 2424240Smckusick #ifndef STANDALONE 2434240Smckusick if (bmap) 2444240Smckusick free(bmap); 2454240Smckusick #endif 2464240Smckusick 2476286Smckusick i = nrfile + ndfile + ncfile + nbfile + nlfile; 2484240Smckusick #ifndef STANDALONE 2496286Smckusick printf("files %6u (r=%u,d=%u,b=%u,c=%u,sl=%u)\n", 2506286Smckusick i, nrfile, ndfile, nbfile, ncfile, nlfile); 2514240Smckusick #else 2526286Smckusick printf("files %u (r=%u,d=%u,b=%u,c=%u,sl=%u)\n", 2536286Smckusick i, nrfile, ndfile, nbfile, ncfile, nlfile); 2544240Smckusick #endif 2555326Smckusic n = (nblock + nindir + niindir) * sblock.fs_frag + nfrag; 2564240Smckusick #ifdef STANDALONE 2574240Smckusick printf("used %ld (i=%ld,ii=%ld,b=%ld,f=%ld)\n", 2584240Smckusick n, nindir, niindir, nblock, nfrag); 2595326Smckusic printf("free %ld (b=%ld,f=%ld)\n", nffree + sblock.fs_frag * nbfree, 2604240Smckusick nbfree, nffree); 2614240Smckusick #else 2624240Smckusick printf("used %7ld (i=%ld,ii=%ld,b=%ld,f=%ld)\n", 2634240Smckusick n, nindir, niindir, nblock, nfrag); 2645326Smckusic printf("free %7ld (b=%ld,f=%ld)\n", nffree + sblock.fs_frag * nbfree, 2654240Smckusick nbfree, nffree); 2664240Smckusick #endif 2674240Smckusick if(!dflg) { 2684240Smckusick n = 0; 2694410Smckusic for (d = 0; d < sblock.fs_size; d++) 2705326Smckusic if(!duped(d, sblock.fs_fsize)) { 2714240Smckusick if(mflg) 2724240Smckusick printf("%ld missing\n", d); 2734240Smckusick n++; 2744240Smckusick } 2754240Smckusick printf("missing%5ld\n", n); 2764240Smckusick } 2774240Smckusick } 2784240Smckusick 2794240Smckusick pass1(ip) 2804410Smckusic register struct dinode *ip; 2814240Smckusick { 2825326Smckusic daddr_t ind1[MAXNINDIR]; 2835326Smckusic daddr_t ind2[MAXNINDIR]; 2844429Smckusic daddr_t db, ib; 2854429Smckusic register int i, j, k, siz; 2864240Smckusick 2874240Smckusick i = ip->di_mode & IFMT; 2884790Smckusic if(i == 0) 2894240Smckusick return; 2904240Smckusick switch (i) { 2914240Smckusick case IFCHR: 2924240Smckusick ncfile++; 2934240Smckusick return; 2944240Smckusick case IFBLK: 2954240Smckusick nbfile++; 2964240Smckusick return; 2974240Smckusick case IFDIR: 2984240Smckusick ndfile++; 2994240Smckusick break; 3004240Smckusick case IFREG: 3014240Smckusick nrfile++; 3024240Smckusick break; 3036286Smckusick case IFLNK: 3046286Smckusick nlfile++; 3056286Smckusick break; 3064240Smckusick default: 3074240Smckusick printf("bad mode %u\n", ino); 3084240Smckusick return; 3094240Smckusick } 3104410Smckusic for (i = 0; i < NDADDR; i++) { 3114410Smckusic db = ip->di_db[i]; 3124410Smckusic if (db == 0) 3134240Smckusick continue; 3145326Smckusic siz = dblksize(&sblock, ip, i); 3154429Smckusic chk(db, "data (block)", siz); 3165326Smckusic if (siz == sblock.fs_bsize) 3174429Smckusic nblock++; 3184429Smckusic else 3195326Smckusic nfrag += howmany(siz, sblock.fs_fsize); 3204240Smckusick } 3214410Smckusic for(i = 0; i < NIADDR; i++) { 3224410Smckusic ib = ip->di_ib[i]; 3234410Smckusic if(ib == 0) 3244240Smckusick continue; 3255326Smckusic if (chk(ib, "1st indirect", sblock.fs_bsize)) 3264410Smckusic continue; 3275326Smckusic bread(fsbtodb(&sblock, ib), (char *)ind1, sblock.fs_bsize); 3284240Smckusick nindir++; 3295326Smckusic for (j = 0; j < NINDIR(&sblock); j++) { 3304410Smckusic ib = ind1[j]; 3314410Smckusic if (ib == 0) 3324240Smckusick continue; 3334410Smckusic if (i == 0) { 3345326Smckusic siz = dblksize(&sblock, ip, NDADDR + j); 3354429Smckusic chk(ib, "data (large)", siz); 3365326Smckusic if (siz == sblock.fs_bsize) 3374429Smckusic nblock++; 3384429Smckusic else 3395326Smckusic nfrag += howmany(siz, sblock.fs_fsize); 3404240Smckusick continue; 3414240Smckusick } 3425326Smckusic if (chk(ib, "2nd indirect", sblock.fs_bsize)) 3434410Smckusic continue; 3445326Smckusic bread(fsbtodb(&sblock, ib), (char *)ind2, 3455326Smckusic sblock.fs_bsize); 3464240Smckusick niindir++; 3475326Smckusic for (k = 0; k < NINDIR(&sblock); k++) { 3484410Smckusic ib = ind2[k]; 3494410Smckusic if (ib == 0) 3504240Smckusick continue; 3515326Smckusic siz = dblksize(&sblock, ip, 3525326Smckusic NDADDR + NINDIR(&sblock) * (i + j) + k); 3534429Smckusic chk(ib, "data (huge)", siz); 3545326Smckusic if (siz == sblock.fs_bsize) 3554429Smckusic nblock++; 3564429Smckusic else 3575326Smckusic nfrag += howmany(siz, sblock.fs_fsize); 3584240Smckusick } 3594240Smckusick } 3604240Smckusick } 3614240Smckusick } 3624240Smckusick 3634429Smckusic chk(bno, s, size) 3644410Smckusic daddr_t bno; 3654410Smckusic char *s; 3664429Smckusic int size; 3674240Smckusick { 3684240Smckusick register n, cg; 3695957Smckusic int frags; 3704240Smckusick 3715382Smckusic cg = dtog(&sblock, bno); 3724429Smckusic if (cginit==0 && 3735382Smckusic bno<cgdmin(&sblock, cg) || bno >= sblock.fs_frag * sblock.fs_size) { 3744240Smckusick printf("%ld bad; inode=%u, class=%s\n", bno, ino, s); 3754240Smckusick return(1); 3764240Smckusick } 3775326Smckusic if (size == sblock.fs_bsize) { 3784429Smckusic if (duped(bno, size)) { 3794429Smckusic printf("%ld dup block; inode=%u, class=%s\n", 3804429Smckusic bno, ino, s); 3815326Smckusic ndup += sblock.fs_frag; 3824429Smckusic } 3834429Smckusic } else { 3845957Smckusic frags = numfrags(&sblock, size); 3855957Smckusic for (n = 0; n < frags; n++) { 3865326Smckusic if (duped(bno + n, sblock.fs_fsize)) { 3874429Smckusic printf("%ld dup frag; inode=%u, class=%s\n", 3884429Smckusic bno, ino, s); 3894429Smckusic ndup++; 3904429Smckusic } 3914429Smckusic } 3924240Smckusick } 3934240Smckusick for (n=0; blist[n] != -1; n++) 3944240Smckusick if (bno == blist[n]) 3954240Smckusick printf("%ld arg; inode=%u, class=%s\n", bno, ino, s); 3964240Smckusick return(0); 3974240Smckusick } 3984240Smckusick 3994429Smckusic duped(bno, size) 4004410Smckusic daddr_t bno; 4014429Smckusic int size; 4024240Smckusick { 4034240Smckusick if(dflg) 4044240Smckusick return(0); 4055326Smckusic if (size != sblock.fs_fsize && size != sblock.fs_bsize) 4064429Smckusic printf("bad size %d to duped\n", size); 4075326Smckusic if (size == sblock.fs_fsize) { 4084410Smckusic if (isset(bmap, bno)) 4094410Smckusic return(1); 4104410Smckusic setbit(bmap, bno); 4114410Smckusic return (0); 4124410Smckusic } 4135326Smckusic if (bno % sblock.fs_frag != 0) 4144410Smckusic printf("bad bno %d to duped\n", bno); 4155326Smckusic if (isblock(&sblock, bmap, bno/sblock.fs_frag)) 4164410Smckusic return (1); 4175326Smckusic setblock(&sblock, bmap, bno/sblock.fs_frag); 4184240Smckusick return(0); 4194240Smckusick } 4204240Smckusick 4215098Smckusic makecg() 4225098Smckusic { 4235098Smckusic int c, blk; 4245098Smckusic daddr_t dbase, d, dmin, dmax; 4255098Smckusic long i, j, s; 4265098Smckusic register struct csum *cs; 4275098Smckusic register struct dinode *dp; 4285098Smckusic 4295098Smckusic sblock.fs_cstotal.cs_nbfree = 0; 4305098Smckusic sblock.fs_cstotal.cs_nffree = 0; 4315098Smckusic sblock.fs_cstotal.cs_nifree = 0; 4325098Smckusic sblock.fs_cstotal.cs_ndir = 0; 4335098Smckusic for (c = 0; c < sblock.fs_ncg; c++) { 4345382Smckusic dbase = cgbase(&sblock, c); 4355098Smckusic dmax = dbase + sblock.fs_fpg; 4365410Smckusic if (dmax > sblock.fs_size) { 4375410Smckusic for ( ; dmax >= sblock.fs_size; dmax--) 4385400Smckusic clrbit(cgrp.cg_free, dmax - dbase); 4395410Smckusic dmax++; 4405410Smckusic } 4415400Smckusic dmin = sblock.fs_dblkno; 4425326Smckusic cs = &sblock.fs_cs(&sblock, c); 4435098Smckusic cgrp.cg_time = time(0); 4445098Smckusic cgrp.cg_magic = CG_MAGIC; 4455098Smckusic cgrp.cg_cgx = c; 4465098Smckusic cgrp.cg_ncyl = sblock.fs_cpg; 4475098Smckusic cgrp.cg_niblk = sblock.fs_ipg; 4485098Smckusic cgrp.cg_ndblk = dmax - dbase; 4495098Smckusic cgrp.cg_cs.cs_ndir = 0; 4505098Smckusic cgrp.cg_cs.cs_nffree = 0; 4515098Smckusic cgrp.cg_cs.cs_nbfree = 0; 4525098Smckusic cgrp.cg_cs.cs_nifree = 0; 4535098Smckusic cgrp.cg_rotor = dmin; 4545098Smckusic cgrp.cg_frotor = dmin; 4555098Smckusic cgrp.cg_irotor = 0; 4565326Smckusic for (i = 0; i < sblock.fs_frag; i++) 4575098Smckusic cgrp.cg_frsum[i] = 0; 4585382Smckusic bread(fsbtodb(&sblock, cgimin(&sblock, c)), (char *)itab, 4595098Smckusic sblock.fs_ipg * sizeof(struct dinode)); 4605098Smckusic for (i = 0; i < sblock.fs_ipg; i++) { 4615945Smckusic cgrp.cg_cs.cs_nifree++; 4625945Smckusic clrbit(cgrp.cg_iused, i); 4635098Smckusic dp = &itab[i]; 4645098Smckusic if ((dp->di_mode & IFMT) != 0) { 4655098Smckusic if ((dp->di_mode & IFMT) == IFDIR) 4665098Smckusic cgrp.cg_cs.cs_ndir++; 4675945Smckusic cgrp.cg_cs.cs_nifree--; 4685098Smckusic setbit(cgrp.cg_iused, i); 4695098Smckusic continue; 4705098Smckusic } 4715098Smckusic } 4725098Smckusic while (i < MAXIPG) { 4735098Smckusic clrbit(cgrp.cg_iused, i); 4745098Smckusic i++; 4755098Smckusic } 4765338Smckusic if (c == 0) 4775338Smckusic for (i = 0; i < ROOTINO; i++) { 4785338Smckusic setbit(cgrp.cg_iused, i); 4795338Smckusic cgrp.cg_cs.cs_nifree--; 4805338Smckusic } 4815372Smckusic for (s = 0; s < MAXCPG; s++) { 4825372Smckusic cgrp.cg_btot[s] = 0; 4835098Smckusic for (i = 0; i < NRPOS; i++) 4845098Smckusic cgrp.cg_b[s][i] = 0; 4855372Smckusic } 4865098Smckusic if (c == 0) { 4875326Smckusic dmin += howmany(sblock.fs_cssize, sblock.fs_bsize) * 4885326Smckusic sblock.fs_frag; 4895098Smckusic } 4905098Smckusic for (d = 0; d < dmin; d++) 4915098Smckusic clrbit(cgrp.cg_free, d); 4925326Smckusic for (; (d + sblock.fs_frag) <= dmax - dbase; d += sblock.fs_frag) { 4935098Smckusic j = 0; 4945326Smckusic for (i = 0; i < sblock.fs_frag; i++) { 4955098Smckusic if (!isset(bmap, dbase+d+i)) { 4965098Smckusic setbit(cgrp.cg_free, d+i); 4975098Smckusic j++; 4985098Smckusic } else 4995098Smckusic clrbit(cgrp.cg_free, d+i); 5005098Smckusic } 5015326Smckusic if (j == sblock.fs_frag) { 5025098Smckusic cgrp.cg_cs.cs_nbfree++; 5035372Smckusic cgrp.cg_btot[cbtocylno(&sblock, d)]++; 5045364Smckusic cgrp.cg_b[cbtocylno(&sblock, d)] 5055364Smckusic [cbtorpos(&sblock, d)]++; 5065098Smckusic } else if (j > 0) { 5075098Smckusic cgrp.cg_cs.cs_nffree += j; 5085098Smckusic blk = ((cgrp.cg_free[d / NBBY] >> (d % NBBY)) & 5095326Smckusic (0xff >> (NBBY - sblock.fs_frag))); 5105326Smckusic fragacct(&sblock, blk, cgrp.cg_frsum, 1); 5115098Smckusic } 5125098Smckusic } 5135098Smckusic for (j = d; d < dmax - dbase; d++) { 5145098Smckusic if (!isset(bmap, dbase+d)) { 5155098Smckusic setbit(cgrp.cg_free, d); 5165098Smckusic cgrp.cg_cs.cs_nffree++; 5175098Smckusic } else 5185098Smckusic clrbit(cgrp.cg_free, d); 5195098Smckusic } 5205098Smckusic if (j != d) { 5215098Smckusic blk = ((cgrp.cg_free[j / NBBY] >> (j % NBBY)) & 5225326Smckusic (0xff >> (NBBY - sblock.fs_frag))); 5235326Smckusic fragacct(&sblock, blk, cgrp.cg_frsum, 1); 5245098Smckusic } 5255326Smckusic for (; d < MAXBPG(&sblock); d++) 5265098Smckusic clrbit(cgrp.cg_free, d); 5275098Smckusic sblock.fs_cstotal.cs_nffree += cgrp.cg_cs.cs_nffree; 5285098Smckusic sblock.fs_cstotal.cs_nbfree += cgrp.cg_cs.cs_nbfree; 5295098Smckusic sblock.fs_cstotal.cs_nifree += cgrp.cg_cs.cs_nifree; 5305098Smckusic sblock.fs_cstotal.cs_ndir += cgrp.cg_cs.cs_ndir; 5315098Smckusic *cs = cgrp.cg_cs; 5325382Smckusic bwrite(fsbtodb(&sblock, cgtod(&sblock, c)), &cgrp, 5335326Smckusic sblock.fs_cgsize); 5345098Smckusic } 5355326Smckusic for (i = 0; i < howmany(sblock.fs_cssize, sblock.fs_bsize); i++) { 5365326Smckusic bwrite(fsbtodb(&sblock, 5375326Smckusic sblock.fs_csaddr + (i * sblock.fs_frag)), 5385326Smckusic (char *)sblock.fs_csp[i], sblock.fs_bsize); 5395098Smckusic } 5405098Smckusic sblock.fs_ronly = 0; 5415098Smckusic sblock.fs_fmod = 0; 5425349Smckusic bwrite(SBLOCK, (char *)&sblock, SBSIZE); 5435098Smckusic } 5445098Smckusic 5455098Smckusic /* 5465098Smckusic * update the frsum fields to reflect addition or deletion 5475098Smckusic * of some frags 5485098Smckusic */ 5495326Smckusic fragacct(fs, fragmap, fraglist, cnt) 5505326Smckusic struct fs *fs; 5515098Smckusic int fragmap; 5525098Smckusic long fraglist[]; 5535098Smckusic int cnt; 5545098Smckusic { 5555098Smckusic int inblk; 5565098Smckusic register int field, subfield; 5575098Smckusic register int siz, pos; 5585098Smckusic 5595326Smckusic inblk = (int)(fragtbl[fs->fs_frag][fragmap] << 1); 5605098Smckusic fragmap <<= 1; 5615326Smckusic for (siz = 1; siz < fs->fs_frag; siz++) { 5626291Smckusick if ((inblk & (1 << (siz + (fs->fs_frag % NBBY)))) == 0) 5635098Smckusic continue; 5645098Smckusic field = around[siz]; 5655098Smckusic subfield = inside[siz]; 5665326Smckusic for (pos = siz; pos <= fs->fs_frag; pos++) { 5675098Smckusic if ((fragmap & field) == subfield) { 5685098Smckusic fraglist[siz] += cnt; 5695098Smckusic pos += siz; 5705098Smckusic field <<= siz; 5715098Smckusic subfield <<= siz; 5725098Smckusic } 5735098Smckusic field <<= 1; 5745098Smckusic subfield <<= 1; 5755098Smckusic } 5765098Smckusic } 5775098Smckusic } 5785098Smckusic 5795326Smckusic getsb(fs, file) 5805326Smckusic register struct fs *fs; 5815326Smckusic char *file; 5825326Smckusic { 5835326Smckusic int i; 5845326Smckusic 5855349Smckusic if (bread(SBLOCK, fs, SBSIZE)) { 5865326Smckusic printf("bad super block"); 5875326Smckusic perror(file); 5885326Smckusic nerror |= 04; 5895326Smckusic return; 5905326Smckusic } 5915326Smckusic if (fs->fs_magic != FS_MAGIC) { 5925326Smckusic printf("%s: bad magic number\n", file); 5935326Smckusic nerror |= 04; 5945326Smckusic return; 5955326Smckusic } 5965326Smckusic for (i = 0; i < howmany(fs->fs_cssize, fs->fs_bsize); i++) { 5975326Smckusic fs->fs_csp[i] = (struct csum *)calloc(1, fs->fs_bsize); 5985326Smckusic bread(fsbtodb(fs, fs->fs_csaddr + (i * fs->fs_frag)), 5995326Smckusic (char *)fs->fs_csp[i], fs->fs_bsize); 6005326Smckusic } 6015326Smckusic } 6025326Smckusic 6035098Smckusic bwrite(blk, buf, size) 6045098Smckusic char *buf; 6055098Smckusic daddr_t blk; 6065098Smckusic register size; 6075098Smckusic { 6085326Smckusic if (lseek(fi, blk * DEV_BSIZE, 0) < 0) { 6095098Smckusic perror("FS SEEK"); 6105098Smckusic return(1); 6115098Smckusic } 6125098Smckusic if (write(fi, buf, size) != size) { 6135098Smckusic perror("FS WRITE"); 6145098Smckusic return(1); 6155098Smckusic } 6165326Smckusic return (0); 6175098Smckusic } 6185098Smckusic 6194240Smckusick bread(bno, buf, cnt) 6204410Smckusic daddr_t bno; 6214410Smckusic char *buf; 6224240Smckusick { 6234240Smckusick register i; 6244240Smckusick 6255326Smckusic lseek(fi, bno * DEV_BSIZE, 0); 6264240Smckusick if ((i = read(fi, buf, cnt)) != cnt) { 6275098Smckusic if (sflg) { 6285098Smckusic printf("No Update\n"); 6295098Smckusic sflg = 0; 6305098Smckusic } 6315326Smckusic for(i=0; i<sblock.fs_bsize; i++) 6324240Smckusick buf[i] = 0; 6335326Smckusic return (1); 6344240Smckusick } 6355326Smckusic return (0); 6364240Smckusick } 6375326Smckusic 6385326Smckusic /* 6395326Smckusic * block operations 6405326Smckusic */ 6415326Smckusic 6425326Smckusic isblock(fs, cp, h) 6435326Smckusic struct fs *fs; 6445326Smckusic unsigned char *cp; 6455326Smckusic int h; 6465326Smckusic { 6475326Smckusic unsigned char mask; 6485326Smckusic 6495326Smckusic switch (fs->fs_frag) { 6505326Smckusic case 8: 6515326Smckusic return (cp[h] == 0xff); 6525326Smckusic case 4: 6535326Smckusic mask = 0x0f << ((h & 0x1) << 2); 6545326Smckusic return ((cp[h >> 1] & mask) == mask); 6555326Smckusic case 2: 6565326Smckusic mask = 0x03 << ((h & 0x3) << 1); 6575326Smckusic return ((cp[h >> 2] & mask) == mask); 6585326Smckusic case 1: 6595326Smckusic mask = 0x01 << (h & 0x7); 6605326Smckusic return ((cp[h >> 3] & mask) == mask); 6615326Smckusic default: 6625326Smckusic fprintf(stderr, "isblock bad fs_frag %d\n", fs->fs_frag); 6635326Smckusic return; 6645326Smckusic } 6655326Smckusic } 6665326Smckusic 6675326Smckusic setblock(fs, cp, h) 6685326Smckusic struct fs *fs; 6695326Smckusic unsigned char *cp; 6705326Smckusic int h; 6715326Smckusic { 6725326Smckusic switch (fs->fs_frag) { 6735326Smckusic case 8: 6745326Smckusic cp[h] = 0xff; 6755326Smckusic return; 6765326Smckusic case 4: 6775326Smckusic cp[h >> 1] |= (0x0f << ((h & 0x1) << 2)); 6785326Smckusic return; 6795326Smckusic case 2: 6805326Smckusic cp[h >> 2] |= (0x03 << ((h & 0x3) << 1)); 6815326Smckusic return; 6825326Smckusic case 1: 6835326Smckusic cp[h >> 3] |= (0x01 << (h & 0x7)); 6845326Smckusic return; 6855326Smckusic default: 6865326Smckusic fprintf(stderr, "setblock bad fs_frag %d\n", fs->fs_frag); 6875326Smckusic return; 6885326Smckusic } 6895326Smckusic } 690*6490Smckusick 691*6490Smckusick /* tables.c 4.1 82/03/25 */ 692*6490Smckusick 693*6490Smckusick /* merged into kernel: tables.c 2.1 3/25/82 */ 694*6490Smckusick 695*6490Smckusick /* last monet version: partab.c 4.2 81/03/08 */ 696*6490Smckusick 697*6490Smckusick /* 698*6490Smckusick * bit patterns for identifying fragments in the block map 699*6490Smckusick * used as ((map & around) == inside) 700*6490Smckusick */ 701*6490Smckusick int around[9] = { 702*6490Smckusick 0x3, 0x7, 0xf, 0x1f, 0x3f, 0x7f, 0xff, 0x1ff, 0x3ff 703*6490Smckusick }; 704*6490Smckusick int inside[9] = { 705*6490Smckusick 0x0, 0x2, 0x6, 0xe, 0x1e, 0x3e, 0x7e, 0xfe, 0x1fe 706*6490Smckusick }; 707*6490Smckusick 708*6490Smckusick /* 709*6490Smckusick * given a block map bit pattern, the frag tables tell whether a 710*6490Smckusick * particular size fragment is available. 711*6490Smckusick * 712*6490Smckusick * used as: 713*6490Smckusick * if ((1 << (size - 1)) & fragtbl[fs->fs_frag][map] { 714*6490Smckusick * at least one fragment of the indicated size is available 715*6490Smckusick * } 716*6490Smckusick * 717*6490Smckusick * These tables are used by the scanc instruction on the VAX to 718*6490Smckusick * quickly find an appropriate fragment. 719*6490Smckusick */ 720*6490Smckusick 721*6490Smckusick unsigned char fragtbl124[256] = { 722*6490Smckusick 0x00, 0x16, 0x16, 0x2a, 0x16, 0x16, 0x26, 0x4e, 723*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x2a, 0x3e, 0x4e, 0x8a, 724*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 725*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 726*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 727*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 728*6490Smckusick 0x2a, 0x3e, 0x3e, 0x2a, 0x3e, 0x3e, 0x2e, 0x6e, 729*6490Smckusick 0x3e, 0x3e, 0x3e, 0x3e, 0x2a, 0x3e, 0x6e, 0xaa, 730*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 731*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 732*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 733*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 734*6490Smckusick 0x26, 0x36, 0x36, 0x2e, 0x36, 0x36, 0x26, 0x6e, 735*6490Smckusick 0x36, 0x36, 0x36, 0x3e, 0x2e, 0x3e, 0x6e, 0xae, 736*6490Smckusick 0x4e, 0x5e, 0x5e, 0x6e, 0x5e, 0x5e, 0x6e, 0x4e, 737*6490Smckusick 0x5e, 0x5e, 0x5e, 0x7e, 0x6e, 0x7e, 0x4e, 0xce, 738*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 739*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 740*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 741*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 742*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x16, 0x16, 0x36, 0x5e, 743*6490Smckusick 0x16, 0x16, 0x16, 0x3e, 0x3e, 0x3e, 0x5e, 0x9e, 744*6490Smckusick 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x7e, 745*6490Smckusick 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x7e, 0xbe, 746*6490Smckusick 0x2a, 0x3e, 0x3e, 0x2a, 0x3e, 0x3e, 0x2e, 0x6e, 747*6490Smckusick 0x3e, 0x3e, 0x3e, 0x3e, 0x2a, 0x3e, 0x6e, 0xaa, 748*6490Smckusick 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x7e, 749*6490Smckusick 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x3e, 0x7e, 0xbe, 750*6490Smckusick 0x4e, 0x5e, 0x5e, 0x6e, 0x5e, 0x5e, 0x6e, 0x4e, 751*6490Smckusick 0x5e, 0x5e, 0x5e, 0x7e, 0x6e, 0x7e, 0x4e, 0xce, 752*6490Smckusick 0x8a, 0x9e, 0x9e, 0xaa, 0x9e, 0x9e, 0xae, 0xce, 753*6490Smckusick 0x9e, 0x9e, 0x9e, 0xbe, 0xaa, 0xbe, 0xce, 0x8a, 754*6490Smckusick }; 755*6490Smckusick 756*6490Smckusick unsigned char fragtbl8[256] = { 757*6490Smckusick 0x00, 0x01, 0x01, 0x02, 0x01, 0x01, 0x02, 0x04, 758*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x02, 0x03, 0x04, 0x08, 759*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 760*6490Smckusick 0x02, 0x03, 0x03, 0x02, 0x04, 0x05, 0x08, 0x10, 761*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 762*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x03, 0x03, 0x05, 0x09, 763*6490Smckusick 0x02, 0x03, 0x03, 0x02, 0x03, 0x03, 0x02, 0x06, 764*6490Smckusick 0x04, 0x05, 0x05, 0x06, 0x08, 0x09, 0x10, 0x20, 765*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 766*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x03, 0x03, 0x05, 0x09, 767*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 768*6490Smckusick 0x03, 0x03, 0x03, 0x03, 0x05, 0x05, 0x09, 0x11, 769*6490Smckusick 0x02, 0x03, 0x03, 0x02, 0x03, 0x03, 0x02, 0x06, 770*6490Smckusick 0x03, 0x03, 0x03, 0x03, 0x02, 0x03, 0x06, 0x0a, 771*6490Smckusick 0x04, 0x05, 0x05, 0x06, 0x05, 0x05, 0x06, 0x04, 772*6490Smckusick 0x08, 0x09, 0x09, 0x0a, 0x10, 0x11, 0x20, 0x40, 773*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 774*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x03, 0x03, 0x05, 0x09, 775*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 776*6490Smckusick 0x03, 0x03, 0x03, 0x03, 0x05, 0x05, 0x09, 0x11, 777*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x01, 0x01, 0x03, 0x05, 778*6490Smckusick 0x01, 0x01, 0x01, 0x03, 0x03, 0x03, 0x05, 0x09, 779*6490Smckusick 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x07, 780*6490Smckusick 0x05, 0x05, 0x05, 0x07, 0x09, 0x09, 0x11, 0x21, 781*6490Smckusick 0x02, 0x03, 0x03, 0x02, 0x03, 0x03, 0x02, 0x06, 782*6490Smckusick 0x03, 0x03, 0x03, 0x03, 0x02, 0x03, 0x06, 0x0a, 783*6490Smckusick 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x03, 0x07, 784*6490Smckusick 0x02, 0x03, 0x03, 0x02, 0x06, 0x07, 0x0a, 0x12, 785*6490Smckusick 0x04, 0x05, 0x05, 0x06, 0x05, 0x05, 0x06, 0x04, 786*6490Smckusick 0x05, 0x05, 0x05, 0x07, 0x06, 0x07, 0x04, 0x0c, 787*6490Smckusick 0x08, 0x09, 0x09, 0x0a, 0x09, 0x09, 0x0a, 0x0c, 788*6490Smckusick 0x10, 0x11, 0x11, 0x12, 0x20, 0x21, 0x40, 0x80, 789*6490Smckusick }; 790*6490Smckusick 791*6490Smckusick /* 792*6490Smckusick * the actual fragtbl array 793*6490Smckusick */ 794*6490Smckusick unsigned char *fragtbl[MAXFRAG + 1] = { 795*6490Smckusick 0, fragtbl124, fragtbl124, 0, fragtbl124, 0, 0, 0, fragtbl8, 796*6490Smckusick }; 797