Index: usr.bin/uuencode/Makefile =================================================================== --- usr.bin/uuencode/Makefile +++ usr.bin/uuencode/Makefile @@ -10,6 +10,7 @@ LINKS+= ${BINDIR}/bin2text2bin ${BINDIR}/b64encode LINKS+= ${BINDIR}/bin2text2bin ${BINDIR}/uudecode LINKS+= ${BINDIR}/bin2text2bin ${BINDIR}/b64decode +LINKS+= ${BINDIR}/bin2text2bin ${BINDIR}/base64 MLINKS= uuencode.1 uudecode.1 \ uuencode.format.5 uuencode.5 \ uuencode.1 b64encode.1 \ Index: usr.bin/uuencode/bin2text2bin.c =================================================================== --- usr.bin/uuencode/bin2text2bin.c +++ usr.bin/uuencode/bin2text2bin.c @@ -26,7 +26,9 @@ */ #include +#include #include +#include #include #include #include @@ -37,7 +39,16 @@ static int search(const char *const); enum coders { - uuencode, uudecode, b64encode, b64decode + uuencode, uudecode, b64encode, b64decode, base64 +}; + +static const struct option long_options[] = +{ + {"decode", no_argument, NULL, 'd'}, + {"wrap", required_argument, NULL, 'w'}, + {"ignore-garbage", no_argument, NULL, 'i'}, + {"help", no_argument, NULL, 0}, + {NULL, no_argument, NULL, 0} }; int @@ -60,11 +71,50 @@ case b64decode: main_decode(argc, argv); break; + case base64: { + int ch; + int nargc; + char *nargv[8] = {NULL}; + bool decode = false; + + nargc = 0; + nargv[nargc++] = (char []){"base64"}; + nargv[nargc++] = (char []){"-r"}; + nargv[nargc++] = (char []){"-m"}; + while ((ch = getopt_long(argc, argv, "diw:", + long_options, NULL)) != -1) { + if (ch == 'd') + decode = true; + else if (ch == 'i') + /* ignore */; + else if (ch == 'w') { + nargv[nargc++] = (char []){"-w"}; + nargv[nargc++] = optarg; + } + else { + (void)fprintf(stderr, + "usage: base64 [-w col | --wrap=col] [-d | --decode] [FILE]\n"); + exit(EXIT_FAILURE); + } + } + if (argv[optind] != NULL) + nargv[nargc++] = argv[optind]; + else + nargv[nargc++] = (char []){"/dev/stdin"}; + optreset = optind = 1; + if (decode) + main_decode(nargc, nargv); + else { + nargv[nargc++] = (char []){"/dev/stdout"}; + main_encode(nargc, nargv); + } + } default: (void)fprintf(stderr, - "usage: %s ...\n" - " %s ...\n", - progname, progname); + "usage: %1$s ...\n" + " %1$s ...\n" + " %1$s ...\n", + progname); exit(EXIT_FAILURE); } } @@ -77,7 +127,8 @@ DESIGNATE(uuencode), DESIGNATE(uudecode), DESIGNATE(b64encode), - DESIGNATE(b64decode) + DESIGNATE(b64decode), + DESIGNATE(base64) }; for (size_t i = 0; i < nitems(known); i++) Index: usr.bin/uuencode/uuencode.1 =================================================================== --- usr.bin/uuencode/uuencode.1 +++ usr.bin/uuencode/uuencode.1 @@ -28,7 +28,7 @@ .\" @(#)uuencode.1 8.1 (Berkeley) 6/6/93 .\" $FreeBSD$ .\" -.Dd January 27, 2002 +.Dd November 11, 2021 .Dt UUENCODE 1 .Os .Sh NAME @@ -63,6 +63,10 @@ .Op Fl i .Fl o Ar output_file .Op Ar file +.Nm base64 +.Op Fl d +.Op Fl w Ar column +.Op Ar file .Sh DESCRIPTION The .Nm @@ -88,6 +92,33 @@ flag specified. .Pp The +.Nm base64 +utility acts as a base64 decoder when passed the +.Fl -decode +.Po or +.Fl d +.Pc +flag and as a base64 encoder otherwise. +As a decoder it only accepts raw base64 input +and as an encoder it does not produce the framing lines. +.Nm base64 +reads standard input or +.Ar file +if it is provided and writes to standard output. +Options +.Fl -wrap +.Po or +.Fl w +.Pc +and +.Fl -ignore-garbage +.Po or +.Fl i +.Pc +are accepted for compatibility with GNU base64, +but the latter is unimplemented and silently ignored. +.Pp +The .Nm utility reads .Ar file