|
|
1.1 ! root 1: #include <libc.h> ! 2: #include <fio.h> ! 3: #include <sys/types.h> ! 4: #include <sys/stat.h> ! 5: #include <signal.h> ! 6: #include "worm.h" ! 7: ! 8: long minfree = 40000; ! 9: int verbose = 0; ! 10: ! 11: main(argc, argv) ! 12: char **argv; ! 13: { ! 14: Superblock in, out; ! 15: char *e; ! 16: char buf[4096]; ! 17: int n; ! 18: long lineno; ! 19: int c; ! 20: char *dev = "/dev/worm0"; ! 21: long tfiles, tbytes; ! 22: int eof; ! 23: char first[4096]; ! 24: extern char *optarg; ! 25: extern int optind; ! 26: ! 27: argout = argv[0]; ! 28: while((c = getopt(argc, argv, "vm:f:")) != -1) ! 29: switch(c) ! 30: { ! 31: case 'f': dev = optarg; break; ! 32: case 'm': minfree = atol(optarg); break; ! 33: case 'v': verbose = 1; break; ! 34: case '?': usage(); ! 35: } ! 36: ! 37: if(optind+3 != argc) ! 38: usage(); ! 39: e = mapdev(argv[optind+1]); ! 40: if((out.fd = open(e, 2)) < 0){ ! 41: perror(e); ! 42: exit(1); ! 43: } ! 44: if(e = openinode(&out, SPIN_DOWN)){ ! 45: fprint(2, "%s: %s\n", *argv, e); ! 46: exit(1); ! 47: } ! 48: if(strcmp(out.vol_id, argv[optind+2])){ ! 49: fprint(2, "vol_id mismatch: wanted %s, got %s\n", argv[optind+2], out.vol_id); ! 50: exit(1); ! 51: } ! 52: if(out.version != VLINK){ ! 53: fprint(2, "%s: can't write on a b-tree disk\n", out.vol_id); ! 54: exit(1); ! 55: } ! 56: dev = mapdev(dev); ! 57: if((in.fd = open(dev, 2)) < 0){ ! 58: perror(*argv); ! 59: exit(1); ! 60: } ! 61: if(e = openinode(&in, DO_INODE|SPIN_DOWN)){ ! 62: fprint(2, "%s: %s\n", *argv, e); ! 63: exit(1); ! 64: } ! 65: if(strcmp(in.vol_id, argv[optind])){ ! 66: fprint(2, "vol_id mismatch: wanted %s, got %s\n", argv[optind], in.vol_id); ! 67: exit(1); ! 68: } ! 69: for(n = 1; n <= NSIG; n++) ! 70: signal(n, SIG_IGN); ! 71: eof = 0; ! 72: tfiles = tbytes = 0; ! 73: lineno = 0; ! 74: while(!eof){ ! 75: /* flush seperater lines */ ! 76: while(e = Frdline(0)){ ! 77: lineno++; ! 78: if(*e) ! 79: break; ! 80: } ! 81: if(e == 0) ! 82: break; ! 83: ininit(); ! 84: proc(&out, e); ! 85: strncpy(first, e, sizeof first); ! 86: if(out.nfree < minfree){ ! 87: fprint(2, "wcopy: disk %s full before copying group '%s' line %d\n", ! 88: out.vol_id, first, lineno); ! 89: exit(1); ! 90: } ! 91: while(e = Frdline(0)){ ! 92: lineno++; ! 93: if(*e == 0) ! 94: break; ! 95: proc(&out, e); ! 96: } ! 97: if(e == 0) ! 98: eof = 1; ! 99: if(bad) ! 100: exit(1); ! 101: nfiles = nbytes = 0; ! 102: blkdone = 0; ! 103: inwrite(&out, &in); ! 104: if(bad) ! 105: exit(1); ! 106: if(verbose) ! 107: fprint(1, "%s group('%s' %d files, %.6fMB) done\n", ! 108: timenow(), first, nfiles, nbytes/1e6); ! 109: tfiles += nfiles; ! 110: tbytes += nbytes; ! 111: } ! 112: if(verbose) ! 113: fprint(1, "%s total: %d files, %.6fMB\n", timenow(), tfiles, tbytes/1e6); ! 114: exit(0); ! 115: } ! 116: ! 117: usage() ! 118: { ! 119: fprint(2, "Usage: worm copy [-v] [-m minfree] [-f src_dev] src_id dest_dev dest_id < files\n"); ! 120: exit(1); ! 121: } ! 122: ! 123: proc(s, file) ! 124: Superblock *s; ! 125: char *file; ! 126: { ! 127: struct stat sbuf; ! 128: unsigned short mode; ! 129: Inode i; ! 130: Inode *srci; ! 131: ! 132: if((srci = inodeof(file)) == 0){ ! 133: fprint(2, "can't find file '%s'\n", file); ! 134: return; ! 135: } ! 136: memset((char *)&i, 0, sizeof(i)); ! 137: i = *srci; ! 138: i.block = 0; ! 139: nbytes += i.nbytes; ! 140: if(inadd(s, &i)) ! 141: bad = 1; ! 142: } ! 143: ! 144: writeout(dest, i, blk, src) ! 145: Superblock *dest, *src; ! 146: Inode *i; ! 147: long *blk; ! 148: { ! 149: char b[BIGBLOCK]; ! 150: Inode *srci; ! 151: long n, len, blen; ! 152: char *name; ! 153: ! 154: n = (i->nbytes+dest->blocksize-1)/dest->blocksize; ! 155: *blk += n; ! 156: blkdone += n; ! 157: blen = sizeof b/dest->blocksize; ! 158: len = blen*dest->blocksize; ! 159: nbytes += i->nbytes; ! 160: nfiles++; ! 161: name = i->name.n; ! 162: srci = inodeof(name); ! 163: Seek(src, srci->block); ! 164: for(n = i->nbytes; n > len; n -= len){ ! 165: if(Read(src, b, blen)){ ! 166: out: ! 167: fprint(2, "read problem: seek=%d n=%d blen=%d len=%d; ", ! 168: srci->block, n, blen, len); ! 169: perror(name); ! 170: bad = 1; ! 171: return; ! 172: } ! 173: if(Write(dest, b, blen)){ ! 174: fprint(2, "nb=%d, n=%d len=%d blen=%d\n", i->nbytes, n, len, blen); ! 175: perror("data write"); ! 176: exit(1); ! 177: } ! 178: } ! 179: if(n){ ! 180: n += dest->blocksize-1; ! 181: n /= dest->blocksize; ! 182: if(Read(src, b, n)) ! 183: goto out; ! 184: if(Write(dest, b, n)){ ! 185: perror("data write"); ! 186: exit(1); ! 187: } ! 188: } ! 189: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.