annotate f-demime/base64.c @ 0:7e0d08176f32

f-demime starting code
author Mychaela Falconia <falcon@freecalypso.org>
date Sat, 06 May 2023 06:14:03 +0000
parents
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
1 /*
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
2 * This module implements base64 decoding.
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
3 */
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
4
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
5 #include <ctype.h>
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
6 #include <stdio.h>
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
7 #include <stdlib.h>
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
8 #include <string.h>
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
9 #include <strings.h>
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
10 #include "defs.h"
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
11
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
12 extern void (*dec_outf)();
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
13
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
14 static unsigned b64_accum, b64_eq_flag;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
15 static int b64_state, last_partial;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
16 int b64_err_flag, b64_nonempty;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
17
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
18 void
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
19 base64_dec_init()
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
20 {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
21 b64_accum = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
22 b64_eq_flag = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
23 b64_state = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
24 b64_err_flag = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
25 b64_nonempty = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
26 last_partial = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
27 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
28
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
29 static void
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
30 process_unit()
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
31 {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
32 if (last_partial)
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
33 b64_err_flag = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
34 switch (b64_eq_flag) {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
35 case 0:
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
36 dec_outf(b64_accum >> 16);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
37 dec_outf((b64_accum >> 8) & 0xFF);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
38 dec_outf(b64_accum & 0xFF);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
39 last_partial = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
40 break;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
41 case 1:
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
42 dec_outf(b64_accum >> 16);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
43 dec_outf((b64_accum >> 8) & 0xFF);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
44 last_partial = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
45 break;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
46 case 3:
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
47 dec_outf(b64_accum >> 16);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
48 last_partial = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
49 break;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
50 default:
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
51 b64_err_flag = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
52 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
53 b64_accum = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
54 b64_eq_flag = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
55 b64_state = 0;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
56 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
57
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
58 static void
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
59 base64_input_char(ch)
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
60 {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
61 int code;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
62
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
63 b64_nonempty = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
64 if (ch >= 'A' && ch <= 'Z')
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
65 code = ch - 'A';
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
66 else if (ch >= 'a' && ch <= 'z')
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
67 code = ch - 'a' + 26;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
68 else if (ch >= '0' && ch <= '9')
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
69 code = ch - '0' + 52;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
70 else switch (ch) {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
71 case '+':
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
72 code = 62;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
73 break;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
74 case '/':
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
75 code = 63;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
76 break;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
77 case '=':
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
78 code = 64;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
79 break;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
80 default:
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
81 b64_err_flag = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
82 return;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
83 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
84 b64_accum <<= 6;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
85 b64_accum |= (code & 63);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
86 b64_eq_flag <<= 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
87 b64_eq_flag |= (code >> 6);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
88 b64_state++;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
89 if (b64_state >= 4)
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
90 process_unit();
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
91 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
92
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
93 void
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
94 base64_input_line(line)
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
95 char *line;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
96 {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
97 char *cp;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
98 int c;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
99
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
100 for (cp = line; *cp; ) {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
101 c = *cp++;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
102 if (!isspace(c))
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
103 base64_input_char(c);
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
104 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
105 }
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
106
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
107 void
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
108 base64_dec_finish()
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
109 {
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
110 if (b64_state)
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
111 b64_err_flag = 1;
7e0d08176f32 f-demime starting code
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
112 }