iconv.c (1801B)
1 #include <u.h> 2 #include <libc.h> 3 #include <draw.h> 4 #include <memdraw.h> 5 6 void 7 usage(void) 8 { 9 fprint(2, "usage: iconv [-u] [-c chanstr] [file]\n"); 10 exits("usage"); 11 } 12 13 void 14 writeuncompressed(int fd, Memimage *m) 15 { 16 char chanstr[32]; 17 int bpl, y, j; 18 uchar *buf; 19 20 if(chantostr(chanstr, m->chan) == nil) 21 sysfatal("can't convert channel descriptor: %r"); 22 fprint(fd, "%11s %11d %11d %11d %11d ", 23 chanstr, m->r.min.x, m->r.min.y, m->r.max.x, m->r.max.y); 24 25 bpl = bytesperline(m->r, m->depth); 26 buf = malloc(bpl); 27 if(buf == nil) 28 sysfatal("malloc failed: %r"); 29 for(y=m->r.min.y; y<m->r.max.y; y++){ 30 j = unloadmemimage(m, Rect(m->r.min.x, y, m->r.max.x, y+1), buf, bpl); 31 if(j != bpl) 32 sysfatal("image unload failed: %r"); 33 if(write(fd, buf, bpl) != bpl) 34 sysfatal("write failed: %r"); 35 } 36 free(buf); 37 } 38 39 void 40 main(int argc, char *argv[]) 41 { 42 char *tostr, *file; 43 int fd, uncompressed; 44 ulong tochan; 45 Memimage *m, *n; 46 47 tostr = nil; 48 uncompressed = 0; 49 ARGBEGIN{ 50 case 'c': 51 tostr = EARGF(usage()); 52 break; 53 case 'u': 54 uncompressed = 1; 55 break; 56 default: 57 usage(); 58 }ARGEND 59 60 memimageinit(); 61 62 file = "<stdin>"; 63 m = nil; 64 65 switch(argc){ 66 case 0: 67 m = readmemimage(0); 68 break; 69 case 1: 70 file = argv[0]; 71 fd = open(file, OREAD); 72 if(fd < 0) 73 sysfatal("can't open %s: %r", file); 74 m = readmemimage(fd); 75 close(fd); 76 break; 77 default: 78 usage(); 79 } 80 81 if(m == nil) 82 sysfatal("can't read %s: %r", file); 83 84 if(tostr == nil) 85 tochan = m->chan; 86 else{ 87 tochan = strtochan(tostr); 88 if(tochan == 0) 89 sysfatal("bad channel descriptor '%s'", tostr); 90 } 91 92 n = allocmemimage(m->r, tochan); 93 if(n == nil) 94 sysfatal("can't allocate new image: %r"); 95 96 memimagedraw(n, n->r, m, m->r.min, nil, ZP, S); 97 if(uncompressed) 98 writeuncompressed(1, n); 99 else 100 writememimage(1, n); 101 exits(nil); 102 }