#include #include #define MAX_INLINE 200 #define MAX_OUT_FN 100 int debug = 0, trace = 0, info = 0; int readline(FILE *f, char *ln) { char ch; int i = 0; while ((ch = (char)fgetc(f)) != '\n') if (feof(f)) break; else if (i < MAX_INLINE) ln[i++] = ch; ln[i] = '\0'; return !feof(f) || ln[0] != '\0'; } int begin_line(char *line, char *fn) { int i, j; fn[0] = '\0'; if (strncmp(line, "begin ", 6)) return 0; for (i = 7; line[i] >= '0' && line[i] <= '9'; i++); if (i == 7 || line[i] != ' ') return 0; while (line[i] == ' ') i++; for (j = 0; line[i] != ' ' && line[i] != '\0'; i++) if (j < MAX_OUT_FN) fn[j++] = line[i]; fn[j] = '\0'; return line[i] == '\0'; } int end_line(char *line) { return !strcmp(line, "end"); } int decode_ch(char ch) { return (ch == '`' ? ' ' : ch) - 32; } int correct_line(char *line) { int l, i, sl = strlen(line); if (line[0] < ' ' || line[0] > '`') { if (debug) printf("first `%c'\n", line[0]); return 0; } l = decode_ch(line[0]); if ((sl - 1)/4 != (l + 2)/ 3) { if (debug) printf("%d %d %d %d\n", strlen(line), l, (strlen(line) - 1)/4, (l + 2)/3); return 0; } for (i = 1; i < sl; i++) if (line[i] < ' ' || line[i] > '`') { if (debug) printf("line[%d] = `%c'", i, line[i]); return 0; } return 1; } void decode_line(char *line, FILE *f) { int l = decode_ch(line[0]), sl = strlen(line), i, j; for (j = 0, i = 1; i < sl;) { int c1, c2, c3, c4, b1, b2, b3; c1 = decode_ch(line[i++]); c2 = decode_ch(line[i++]); c3 = decode_ch(line[i++]); c4 = decode_ch(line[i++]); b1 = (c1 << 2) | (c2 >> 4); b2 = (c2 << 4) | (c3 >> 2); b3 = (c3 << 6) | c4; if (j++ < l) fputc(b1, f); if (j++ < l) fputc(b2, f); if (j++ < l) fputc(b3, f); } } void uudecode_file(char *fn) { FILE *fin = fopen(fn, "r"); char line[MAX_INLINE + 1]; char out_fn[MAX_OUT_FN + 1]; printf("uudecode file: %s\n", fn); if (fin == NULL) { printf("Error: cannot open `%s'\n", fn); return; } while (readline(fin, line)) { while (!begin_line(line, out_fn)) { if (info) printf("Skipping: %s\n", line); if (!readline(fin, line)) break; } if (out_fn[0] != '\0') { FILE *fout = fopen(out_fn, "w"); printf("Outfile: %s\n", out_fn); if (fout == NULL) printf("Error: cannot open file %s\n", out_fn); while (readline(fin, line) && !end_line(line)) { if (correct_line(line)) { if (fout != NULL) decode_line(line, fout); } else if (trace) printf("Ignoring: %s\n", line); } if (fout != NULL) fclose(fout); } } fclose(fin); } void main(int argc, char *argv[]) { int i; for (i = 1; i < argc; i++) { char *arg = argv[i]; if (!strcmp(arg, "+d")) debug = 1; else if (!strcmp(arg, "-d")) debug = 0; else if (!strcmp(arg, "+t")) trace = 1; else if (!strcmp(arg, "-t")) trace = 0; else if (!strcmp(arg, "+i")) info = 1; else if (!strcmp(arg, "-i")) info = 0; else uudecode_file(argv[i]); } }