uudecode: fix to base64 decode by Jorgen Cederlof
No binary (build failed)
—
(log yok)
| @@ -70,7 +70,7 @@ static void read_base64(FILE *src_stream, FILE *dst_stream) | |
| { | |
| static const char base64_table[] = | |
| "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=\n"; | |
| - | int term_count = 0; |
| + | int term_count = 1; |
| while (1) { | |
| char translated[4]; | |
| @@ -86,19 +86,19 @@ static void read_base64(FILE *src_stream, FILE *dst_stream) | |
| if (ch == EOF) { | |
| bb_error_msg_and_die("short file"); | |
| } | |
| - | } while ((table_ptr = strchr(base64_table, ch)) == NULL); |
| + | table_ptr = strchr(base64_table, ch); |
| + | } while (table_ptr == NULL); |
| /* Convert encoded charcter to decimal */ | |
| ch = table_ptr - base64_table; | |
| if (*table_ptr == '=') { | |
| if (term_count == 0) { | |
| - | translated[count] = 0; |
| + | translated[count] = '\0'; |
| break; | |
| } | |
| term_count++; | |
| - | } |
| - | else if (*table_ptr == '\n') { |
| + | } else if (*table_ptr == '\n') { |
| /* Check for terminating line */ | |
| if (term_count == 5) { | |
| return; | |
| @@ -113,7 +113,9 @@ static void read_base64(FILE *src_stream, FILE *dst_stream) | |
| } | |
| /* Merge 6 bit chars to 8 bit */ | |
| - | fputc(translated[0] << 2 | translated[1] >> 4, dst_stream); |
| + | if (count > 1) { |
| + | fputc(translated[0] << 2 | translated[1] >> 4, dst_stream); |
| + | } |
| if (count > 2) { | |
| fputc(translated[1] << 4 | translated[2] >> 2, dst_stream); | |
| } | |
| @@ -126,19 +128,16 @@ static void read_base64(FILE *src_stream, FILE *dst_stream) | |
| int uudecode_main(int argc, char **argv); | |
| int uudecode_main(int argc, char **argv) | |
| { | |
| - | FILE *src_stream; |
| + | FILE *src_stream = stdin; |
| char *outname = NULL; | |
| char *line; | |
| + | opt_complementary = "?1"; /* 1 argument max */ |
| getopt32(argc, argv, "o:", &outname); | |
| + | argv += optind; |
| - | if (optind == argc) { |
| - | src_stream = stdin; |
| - | } else if (optind + 1 == argc) { |
| - | src_stream = xfopen(argv[optind], "r"); |
| - | } else { |
| - | bb_show_usage(); |
| - | } |
| + | if (argv[0]) |
| + | src_stream = xfopen(argv[0], "r"); |
| /* Search for the start of the encoding */ | |
| while ((line = xmalloc_getline(src_stream)) != NULL) { | |
| @@ -158,6 +157,7 @@ int uudecode_main(int argc, char **argv) | |
| continue; | |
| } | |
| + | /* begin line found. decode and exit */ |
| mode = strtoul(line_ptr, NULL, 8); | |
| if (outname == NULL) { | |
| outname = strchr(line_ptr, ' '); | |
| @@ -166,16 +166,48 @@ int uudecode_main(int argc, char **argv) | |
| } | |
| outname++; | |
| } | |
| - | if (LONE_DASH(outname)) { |
| - | dst_stream = stdout; |
| - | } else { |
| + | dst_stream = stdout; |
| + | if (NOT_LONE_DASH(outname)) { |
| dst_stream = xfopen(outname, "w"); | |
| chmod(outname, mode & (S_IRWXU | S_IRWXG | S_IRWXO)); | |
| } | |
| free(line); | |
| decode_fn_ptr(src_stream, dst_stream); | |
| - | fclose_if_not_stdin(src_stream); |
| + | /* fclose_if_not_stdin(src_stream); - redundant */ |
| return EXIT_SUCCESS; | |
| } | |
| bb_error_msg_and_die("no 'begin' line"); | |
| } | |
| + | |
| + | /* Test script. |
| + | Put this into an empty dir with busybox binary, an run. |
| + | |
| + | #!/bin/sh |
| + | test -x busybox || { echo "No ./busybox?"; exit; } |
| + | ln -sf busybox uudecode |
| + | ln -sf busybox uuencode |
| + | >A_null |
| + | echo -n A >A |
| + | echo -n AB >AB |
| + | echo -n ABC >ABC |
| + | echo -n ABCD >ABCD |
| + | echo -n ABCDE >ABCDE |
| + | echo -n ABCDEF >ABCDEF |
| + | cat busybox >A_bbox |
| + | for f in A*; do |
| + | echo uuencode $f |
| + | ./uuencode $f <$f >u_$f |
| + | ./uuencode -m $f <$f >m_$f |
| + | done |
| + | mkdir unpk_u unpk_m 2>/dev/null |
| + | for f in u_*; do |
| + | ./uudecode <$f -o unpk_u/${f:2} |
| + | diff -a ${f:2} unpk_u/${f:2} >/dev/null 2>&1 |
| + | echo uudecode $f: $? |
| + | done |
| + | for f in m_*; do |
| + | ./uudecode <$f -o unpk_m/${f:2} |
| + | diff -a ${f:2} unpk_m/${f:2} >/dev/null 2>&1 |
| + | echo uudecode $f: $? |
| + | done |
| + | */ |
| @@ -28,7 +28,7 @@ int uuencode_main(int argc, char **argv) | |
| RESERVE_CONFIG_BUFFER(dst_buf, DST_BUF_SIZE + 1); | |
| tbl = bb_uuenc_tbl_std; | |
| - | if (getopt32(argc, argv, "m") & 1) { |
| + | if (getopt32(argc, argv, "m")) { |
| tbl = bb_uuenc_tbl_base64; | |
| } | |
| @@ -37,9 +37,6 @@ int uuencode_main(int argc, char **argv) | |
| src_stream = xfopen(argv[optind], "r"); | |
| xstat(argv[optind], &stat_buf); | |
| mode = stat_buf.st_mode & (S_IRWXU | S_IRWXG | S_IRWXO); | |
| - | if (src_stream == stdout) { |
| - | puts("NULL"); |
| - | } |
| break; | |
| case 1: | |
| mode = 0666 & ~umask(0666); | |
| @@ -3664,20 +3664,19 @@ USE_FEATURE_RUN_PARTS_FANCY("\n -l Prints names of all matching files even when | |
| "[pauses for 1 second]\n" | |
| #define uudecode_trivial_usage \ | |
| - | "[FILE]..." |
| + | "[-o outfile] [infile]" |
| #define uudecode_full_usage \ | |
| - | "Uudecode a file" \ |
| - | "\n\nOptions:\n" \ |
| - | " -o FILE Direct output to FILE" |
| + | "Uudecode a file\n" \ |
| + | "NB: finds outfile name in uuencoded source unless -o is given" |
| #define uudecode_example_usage \ | |
| "$ uudecode -o busybox busybox.uu\n" \ | |
| "$ ls -l busybox\n" \ | |
| "-rwxr-xr-x 1 ams ams 245264 Jun 7 21:35 busybox\n" | |
| #define uuencode_trivial_usage \ | |
| - | "[OPTION] [INFILE] REMOTEFILE" |
| + | "[-m] [infile] stored_filename" |
| #define uuencode_full_usage \ | |
| - | "Uuencode a file" \ |
| + | "Uuencode a file to stdout" \ |
| "\n\nOptions:\n" \ | |
| " -m Use base64 encoding per RFC1521" | |
| #define uuencode_example_usage \ | |