blind-decompress.c (1318B)
1 /* See LICENSE file for copyright and license details. */ 2 #include "common.h" 3 4 USAGE("") 5 6 int 7 main(int argc, char *argv[]) 8 { 9 struct stream stream; 10 char *buf; 11 size_t m, fptr, sptr, same = 0, diff = 0; 12 13 UNOFLAGS(argc); 14 15 eopen_stream(&stream, NULL); 16 echeck_dimensions(&stream, WIDTH | HEIGHT, NULL); 17 fprint_stream_head(stdout, &stream); 18 efflush(stdout, "<stdout>"); 19 20 buf = ecalloc(1, stream.frame_size); 21 22 fptr = 0; 23 do { 24 sptr = 0; 25 again: 26 while (same) { 27 m = MIN(same, stream.frame_size - fptr); 28 ewriteall(STDOUT_FILENO, buf + fptr, m, "<stdout>"); 29 fptr = (fptr + m) % stream.frame_size; 30 same -= m; 31 } 32 33 while (diff && sptr < stream.ptr) { 34 m = MIN(diff, stream.frame_size - fptr); 35 m = MIN(m, stream.ptr - sptr); 36 memcpy(buf + fptr, stream.buf + sptr, m); 37 ewriteall(STDOUT_FILENO, buf + fptr, m, "<stdout>"); 38 fptr = (fptr + m) % stream.frame_size; 39 diff -= m; 40 sptr += m; 41 } 42 43 if (diff || sptr + 2 * sizeof(size_t) > stream.ptr) { 44 memmove(stream.buf, stream.buf + sptr, stream.ptr -= sptr); 45 } else { 46 same = ((size_t *)(stream.buf + sptr))[0]; 47 diff = ((size_t *)(stream.buf + sptr))[1]; 48 sptr += 2 * sizeof(size_t); 49 goto again; 50 } 51 } while (eread_stream(&stream, SIZE_MAX)); 52 53 free(buf); 54 if (same || diff) 55 eprintf("<stdin>: corrupt input\n"); 56 return 0; 57 }