• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* base64.c - Encode and decode base64
2  *
3  * Copyright 2014 Rob Landley <rob@landley.net>
4  *
5  * No standard
6 
7 USE_BASE64(NEWTOY(base64, "diw#<0=76[!dw]", TOYFLAG_USR|TOYFLAG_BIN))
8 
9 config BASE64
10   bool "base64"
11   default y
12   help
13     usage: base64 [-di] [-w COLUMNS] [FILE...]
14 
15     Encode or decode in base64.
16 
17     -d	Decode
18     -i	Ignore non-alphabetic characters
19     -w	Wrap output at COLUMNS (default 76 or 0 for no wrap)
20 */
21 
22 #define FOR_base64
23 #include "toys.h"
24 
GLOBALS(long w;unsigned total;)25 GLOBALS(
26   long w;
27 
28   unsigned total;
29 )
30 
31 static void wraputchar(int c, int *x)
32 {
33   putchar(c);
34   TT.total++;
35   if (TT.w && ++*x == TT.w) {
36     *x = 0;
37     xputc('\n');
38   };
39 }
40 
do_base64(int fd,char * name)41 static void do_base64(int fd, char *name)
42 {
43   int out = 0, bits = 0, x = 0, i, len;
44   char *buf = toybuf+128;
45 
46   TT.total = 0;
47 
48   for (;;) {
49     // If no more data, flush buffer
50     if (!(len = xread(fd, buf, sizeof(toybuf)-128))) {
51       if (!(toys.optflags & FLAG_d)) {
52         if (bits) wraputchar(toybuf[out<<(6-bits)], &x);
53         while (TT.total&3) wraputchar('=', &x);
54         if (x) xputc('\n');
55       }
56 
57       return;
58     }
59 
60     for (i=0; i<len; i++) {
61       if (toys.optflags & FLAG_d) {
62         if (buf[i] == '=') return;
63 
64         if ((x = stridx(toybuf, buf[i])) != -1) {
65           out = (out<<6) + x;
66           bits += 6;
67           if (bits >= 8) {
68             putchar(out >> (bits -= 8));
69             out &= (1<<bits)-1;
70             if (ferror(stdout)) perror_exit(0);
71           }
72 
73           continue;
74         }
75         if (buf[i] == '\n' || (toys.optflags & FLAG_i)) continue;
76 
77         break;
78       } else {
79         out = (out<<8) + buf[i];
80         bits += 8;
81         while (bits >= 6) {
82           wraputchar(toybuf[out >> (bits -= 6)], &x);
83           out &= (1<<bits)-1;
84         }
85       }
86     }
87   }
88 }
89 
base64_main(void)90 void base64_main(void)
91 {
92   base64_init(toybuf);
93   loopfiles(toys.optargs, do_base64);
94 }
95