human

convert bytes to human readable formats
git clone git://git.2f30.org/human.git
Log | Files | Refs | README | LICENSE

commit 875338685d3d412069ae68583114a97e2b7d4c52
parent e4cf962033ae7483d8db97e14c07e41b78a65110
Author: z3bra <willyatmailoodotorg>
Date:   Fri, 23 Oct 2015 12:56:06 +0200

Add two-way conversion and -b flag

The utility can now convert down to bytes, and understand number
suffixes as B, K, M, G and T, to convert number from these factorization
levels. For example:

    human -b 123M
    128974848

Diffstat:
README | 7+++++--
human.1 | 12+++++++++---
human.c | 46+++++++++++++++++++++++++++++++---------------
3 files changed, 45 insertions(+), 20 deletions(-)

diff --git a/README b/README @@ -8,8 +8,7 @@ Human is a small program which translate numbers into a human readable format. By default, it tries to detect the best factorisation, but you can force its output. -You can adjust the number of decimals by tweaking the environment variable -$SCALE. +You can adjust the number of decimals by with the `SCALE` environment variable. # convert 123456 to the best human factorisation human 123456 @@ -22,4 +21,8 @@ $SCALE. SCALE=3 human -m 123456 0.118M + # convert from a different factorization level + SCALE=6 human -g 123M + 0.120117G + Well, that's it (and that's enough !) diff --git a/human.1 b/human.1 @@ -3,7 +3,7 @@ human \- output a number in human-readable format .SH SYNOPSIS .B human -.RI [ \-hkmgt ] <number> +.RI [ \-hbkmgt ] <number> .SH DESCRIPTION .PP .B human @@ -12,8 +12,8 @@ takes the number given as an argument, and output it in a human readable format. .B \-h Displays a help text .TP -.B \-k, -m, -g, -t -Force output in, respectively, KiB, MiB, GiB or TiB. +.B \-b, -k, -m, -g, -t +Force output in, respectively, Bytes, KiB, MiB, GiB or TiB. .SH ENVIRONMENT .B SCALE The special variable SCALE will allow you to choose how many numbers you want after the decimal point. @@ -36,6 +36,12 @@ The special variable SCALE will allow you to choose how many numbers you want af \fBhuman \fR-m 1234567890 1177M .EE +.TP +\(buConvert a number from Mib to bytes +.EX +\fBhuman \fR-b 128M +134217728 +.EE .SH REPORTING BUGS If you encounter any bugs, feel free to report them at \fIwilly@mailoo.org\fR .SH AUTHORS / CONTRIBUTORS diff --git a/human.c b/human.c @@ -20,6 +20,7 @@ #include <stdlib.h> #include <getopt.h> #include <limits.h> +#include <string.h> #define TERA 1099511627776 #define GIGA 1073741824 @@ -28,11 +29,16 @@ #define DEFAULT_SCALE 0 -/* dumb user is dumb.. */ +/* + * Help, I need somebody + * Help, not just anybody + * Help, you know I need someone + * Help! + * + */ void usage (char *progname) { - printf("usage: %s [-hkmgt] <number>\n", progname); - return; /* void */ + printf("usage: %s [-hbkmgt] <number>\n", progname); } /* @@ -42,7 +48,7 @@ void usage (char *progname) */ long power (long number, int pow) { - return pow > 0 ? number * power(number, pow - 1) : number; + return pow > 0 ? number * power(number, pow - 1) : 1; } /* @@ -83,12 +89,12 @@ double humanize (double number, char factor) { int pow = 0; - /* cascading switch. note a lack of "break" statements */ + /* cascading switch. note the lack of "break" statements */ switch (factor) { case 'T' : pow++; case 'G' : pow++; case 'M' : pow++; - case 'K' : break; + case 'K' : pow++; break; default : return number; } @@ -98,32 +104,42 @@ double humanize (double number, char factor) int main (int argc, char **argv) { - char ch, fac = 0; + char ch, pow = 0, fac = 0; double number = 0; /* only switches are use to force factorization */ - while ((ch = getopt(argc, argv, "hkmgt")) != -1) { + while ((ch = getopt(argc, argv, "hbkmgt")) != -1) { switch (ch) { case 'h': usage(argv[0]); exit(0); break; - case 't': fac ='T'; break; - case 'g': fac ='G'; break; - case 'm': fac ='M'; break; - case 'k': fac ='K'; break; + case 't': fac = 'T'; break; + case 'g': fac = 'G'; break; + case 'm': fac = 'M'; break; + case 'k': fac = 'K'; break; + case 'b': fac = 'B'; break; } } - /* get the number. if there is not, strtold will return 0 */ + switch (argv[argc - 1][strnlen(argv[argc - 1],32) - 1]) { + case 'T': pow++; + case 'G': pow++; + case 'M': pow++; + case 'K': pow++; + case 'B': argv[argc - 1][strnlen(argv[argc - 1],32) - 1] = 0; + } + + /* get the number and convert it to bytes. If there is none, strtold will return 0 */ number = strtold(argv[argc - 1], NULL); + number *= power(1024, pow); if (number <= 0) { - errx(EXIT_FAILURE, "I ain't gonna do it. Deal with it."); + errx(EXIT_FAILURE, "I ain't gonna do that. Deal with it."); } /* use explicit factorization. otherwise, guess the best one */ fac = fac > 0 ? fac : factorize(number); /* actually print the result, isn't that what we're here for after all ? */ - printf("%.*f%c\n", getscale(), humanize(number, fac), fac); + printf("%.*f%c\n", getscale(), humanize(number, fac), fac == 'B' ? 0 : fac); return 0; }