X-Git-Url: https://git.librecmc.org/?a=blobdiff_plain;f=coreutils%2Fdos2unix.c;h=0c419aca79a30d6051fe6a6defcf54345e9756d1;hb=843c5ef0f95e0a6f61f4e27d0355aca5e09ee6b1;hp=b2dcfd9c21d71419904930dffd738c5940fb0fbb;hpb=50b787cac5e83deaeea1f0c3b73b3289321f8e80;p=oweals%2Fbusybox.git diff --git a/coreutils/dos2unix.c b/coreutils/dos2unix.c index b2dcfd9c2..0c419aca7 100644 --- a/coreutils/dos2unix.c +++ b/coreutils/dos2unix.c @@ -27,27 +27,151 @@ * See the COPYING file for license information. */ -#include +#include +#include +#include +#include +#include #include "busybox.h" -int dos2unix_main(int argc, char *argv[]) { - int ConvType = CT_AUTO; - int o; +#define CT_UNIX2DOS 1 +#define CT_DOS2UNIX 2 - // process parameters - while ((o = getopt(argc, argv, "du")) != EOF) { - switch (o) { - case 'd': - ConvType = CT_UNIX2DOS; - break; - case 'u': - ConvType = CT_DOS2UNIX; +/* We are making a lame pseudo-random string generator here. in + * convert(), each pass through the while loop will add more and more + * stuff into value, which is _supposed_ to wrap. We don't care about + * it being accurate. We care about it being messy, since we use it + * to pick a random letter to add to out temporary file. */ +typedef unsigned long int bb_uint64_t; + +/* if fn is NULL then input is stdin and output is stdout */ +static int convert(char *fn, int ConvType) +{ + int c, fd; + struct timeval tv; + RESERVE_CONFIG_BUFFER(tempFn, BUFSIZ); + static bb_uint64_t value=0; + FILE *in, *out; + + if (fn != NULL) { + in = bb_xfopen(fn, "rw"); + safe_strncpy(tempFn, fn, sizeof(tempFn)); + c = strlen(tempFn); + tempFn[c] = '.'; + while(1) { + /* tempFn is BUFSIZ so the last addressable spot it BUFSIZ-1. + * The loop increments by 2. So this must check for BUFSIZ-3. */ + if (c >=BUFSIZ-3) + bb_error_msg_and_die("unique name not found"); + /* Get some semi random stuff to try and make a + * random filename based (and in the same dir as) + * the input file... */ + gettimeofday (&tv, NULL); + value += ((bb_uint64_t) tv.tv_usec << 16) ^ tv.tv_sec ^ getpid (); + tempFn[++c] = ((value%62) < 26)?(value%62)+97: + ((value%62) < 52)?(value%62)+39: + (value%62)-4; + tempFn[c+1] = '\0'; + value /= 62; + + if ((fd = open(tempFn, O_RDWR | O_CREAT | O_EXCL, 0600)) < 0 ) { + continue; + } + out = fdopen(fd, "w+"); + if (!out) { + close(fd); + remove(tempFn); + continue; + } + break; + } + } else { + in = stdin; + out = stdout; + } + + while ((c = fgetc(in)) != EOF) { + if (c == '\r') { + if ((ConvType == CT_UNIX2DOS) && (fn != NULL)) { + /* file is already in DOS format so it is + * not necessary to touch it. */ + remove(tempFn); + if (fclose(in) < 0 || fclose(out) < 0) { + bb_perror_nomsg(); + return -2; + } + return 0; + } break; - default: - show_usage(); } + if (c == '\n') { + if ((ConvType == CT_DOS2UNIX) && (fn != NULL)) { + /* file is already in DOS format so it is + * not necessary to touch it. */ + remove(tempFn); + if ((fclose(in) < 0) || (fclose(out) < 0)) { + bb_perror_nomsg(); + return -2; + } + return 0; + } + if (ConvType == CT_UNIX2DOS) { + fputc('\r', out); + } + } + fputc(c, out); + } + while (c != EOF && (c = fgetc(in)) != EOF) { + if (c == '\r') + continue; + if (c == '\n') { + if (ConvType == CT_UNIX2DOS) + fputc('\r', out); + fputc('\n', out); + continue; + } + fputc(c, out); } + if (fn != NULL) { + if (fclose(in) < 0 || fclose(out) < 0) { + bb_perror_nomsg(); + remove(tempFn); + return -2; + } + + /* Assume they are both on the same filesystem (which + * should be true since we put them into the same directory + * so we _should_ be ok, but you never know... */ + if (rename(tempFn, fn) < 0) { + bb_perror_msg("unable to rename '%s' as '%s'", tempFn, fn); + return -1; + } + } + + return 0; +} + +int dos2unix_main(int argc, char *argv[]) +{ + int ConvType; + int o; + + /* See if we are supposed to be doing dos2unix or unix2dos */ + if (argv[0][0]=='d') { + ConvType = CT_DOS2UNIX; + } else { + ConvType = CT_UNIX2DOS; + } + + /* process parameters */ + o = bb_getopt_ulflags(argc, argv, "ud"); + + /* Do the conversion requested by an argument else do the default + * conversion depending on our name. */ + if (o) + ConvType = o; + if (optind < argc) { while(optind < argc) if ((o = convert(argv[optind++], ConvType)) < 0)