]>
Commit | Line | Data |
---|---|---|
164f7660 | 1 | |
0c05d982 | 2 | #include "config.h" |
3 | ||
4 | #if HAVE_STDIO_H | |
5 | #include <stdio.h> | |
6 | #endif | |
7 | #if HAVE_STDLIB_H | |
8 | #include <stdlib.h> | |
9 | #endif | |
10 | ||
f5b8bbc4 | 11 | static void base64_init(void); |
0673c0ba | 12 | |
0c05d982 | 13 | static int base64_initialized = 0; |
14 | int base64_value[256]; | |
d5aa0e3b | 15 | const char base64_code[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; |
0c05d982 | 16 | |
f86a22c5 | 17 | |
b8d8561b | 18 | static void |
0673c0ba | 19 | base64_init(void) |
0c05d982 | 20 | { |
21 | int i; | |
22 | ||
23 | for (i = 0; i < 256; i++) | |
24 | base64_value[i] = -1; | |
25 | ||
26 | for (i = 0; i < 64; i++) | |
27 | base64_value[(int) base64_code[i]] = i; | |
28 | base64_value['='] = 0; | |
29 | ||
30 | base64_initialized = 1; | |
31 | } | |
32 | ||
b8d8561b | 33 | char * |
0ee4272b | 34 | base64_decode(const char *p) |
0c05d982 | 35 | { |
36 | static char result[8192]; | |
37 | int c; | |
38 | long val; | |
39 | int i; | |
40 | char *d; | |
41 | ||
42 | if (!p) | |
0ee4272b | 43 | return NULL; |
0c05d982 | 44 | |
45 | if (!base64_initialized) | |
46 | base64_init(); | |
47 | ||
48 | val = c = 0; | |
49 | d = result; | |
50 | while (*p) { | |
51 | i = base64_value[(int) *p++]; | |
52 | if (i >= 0) { | |
53 | val = val * 64 + i; | |
54 | c++; | |
55 | } | |
56 | if (c == 4) { /* One quantum of four encoding characters/24 bit */ | |
57 | *d++ = val >> 16; /* High 8 bits */ | |
58 | *d++ = (val >> 8) & 0xff; /* Mid 8 bits */ | |
59 | *d++ = val & 0xff; /* Low 8 bits */ | |
60 | val = c = 0; | |
61 | } | |
62 | } | |
becf2977 | 63 | *d = 0; |
0c05d982 | 64 | return *result ? result : NULL; |
65 | } | |
f86a22c5 | 66 | |
67 | /* adopted from http://ftp.sunet.se/pub2/gnu/vm/base64-encode.c with adjustments */ | |
68 | const char * | |
69 | base64_encode(const char *decoded_str) | |
70 | { | |
71 | static char result[8192]; | |
72 | int bits = 0; | |
73 | int char_count = 0; | |
74 | int out_cnt = 0; | |
75 | int c; | |
76 | ||
77 | if (!decoded_str) | |
78 | return decoded_str; | |
79 | ||
80 | if (!base64_initialized) | |
81 | base64_init(); | |
82 | ||
f6aaeace | 83 | while ((c = *decoded_str++) && out_cnt < sizeof(result) - 1) { |
84 | bits += c; | |
85 | char_count++; | |
86 | if (char_count == 3) { | |
87 | result[out_cnt++] = base64_code[bits >> 18]; | |
88 | result[out_cnt++] = base64_code[(bits >> 12) & 0x3f]; | |
89 | result[out_cnt++] = base64_code[(bits >> 6) & 0x3f]; | |
90 | result[out_cnt++] = base64_code[bits & 0x3f]; | |
91 | bits = 0; | |
92 | char_count = 0; | |
f86a22c5 | 93 | } else { |
f6aaeace | 94 | bits <<= 8; |
f86a22c5 | 95 | } |
96 | } | |
97 | if (char_count != 0) { | |
f6aaeace | 98 | bits <<= 16 - (8 * char_count); |
99 | result[out_cnt++] = base64_code[bits >> 18]; | |
100 | result[out_cnt++] = base64_code[(bits >> 12) & 0x3f]; | |
101 | if (char_count == 1) { | |
102 | result[out_cnt++] = '='; | |
103 | result[out_cnt++] = '='; | |
f86a22c5 | 104 | } else { |
f6aaeace | 105 | result[out_cnt++] = base64_code[(bits >> 6) & 0x3f]; |
106 | result[out_cnt++] = '='; | |
f86a22c5 | 107 | } |
108 | } | |
f6aaeace | 109 | result[out_cnt] = '\0'; /* terminate */ |
f86a22c5 | 110 | return result; |
111 | } |