comparison f-demime/header.c @ 0:7e0d08176f32

f-demime starting code
author Mychaela Falconia <falcon@freecalypso.org>
date Sat, 06 May 2023 06:14:03 +0000
parents
children 612c4d0df768
comparison
equal deleted inserted replaced
-1:000000000000 0:7e0d08176f32
1 /*
2 * This module implements initial processing (pass-through and collection)
3 * of message and body part headers.
4 */
5
6 #include <ctype.h>
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <string.h>
10 #include <strings.h>
11 #include "defs.h"
12
13 extern enum msg_hdr_state hdr_state;
14 extern char cont_type_buf[HDR_BUF_SIZE], cont_te_buf[HDR_BUF_SIZE];
15 extern int got_cont_type, got_cont_te;
16
17 static void
18 error(line, msg)
19 char *line, *msg;
20 {
21 if (got_cont_type) {
22 fputs(cont_type_buf, stdout);
23 got_cont_type = 0;
24 }
25 if (got_cont_te) {
26 fputs(cont_te_buf, stdout);
27 got_cont_te = 0;
28 }
29 printf("X-Fdemime-Error: %s\n", msg);
30 puts(line);
31 hdr_state = HDR_STATE_ERROR;
32 }
33
34 static void
35 error_ct_cont(hdr_name)
36 char *hdr_name;
37 {
38 printf("X-Fdemime-Error: %s header is too long\n", hdr_name);
39 }
40
41 static void
42 cont_line(line)
43 char *line;
44 {
45 unsigned prev_len;
46
47 switch (hdr_state) {
48 case HDR_STATE_BEGIN:
49 error(line, "continuation line at the beginning of header");
50 return;
51 case HDR_STATE_GOTSOME:
52 puts(line);
53 return;
54 case HDR_STATE_CONT_TYPE:
55 prev_len = strlen(cont_type_buf);
56 if (prev_len + strlen(line) + 2 > HDR_BUF_SIZE) {
57 error_ct_cont("Content-Type");
58 fputs(cont_type_buf, stdout);
59 puts(line);
60 hdr_state = HDR_STATE_ERROR;
61 got_cont_type = 0;
62 return;
63 }
64 sprintf(cont_type_buf + prev_len, "%s\n", line);
65 return;
66 case HDR_STATE_CONT_TE:
67 prev_len = strlen(cont_te_buf);
68 if (prev_len + strlen(line) + 2 > HDR_BUF_SIZE) {
69 error_ct_cont("Content-Transfer-Encoding");
70 fputs(cont_te_buf, stdout);
71 puts(line);
72 hdr_state = HDR_STATE_ERROR;
73 got_cont_te = 0;
74 return;
75 }
76 sprintf(cont_te_buf + prev_len, "%s\n", line);
77 return;
78 default:
79 fprintf(stderr,
80 "f-demime internal error: bad state in cont_line()\n");
81 abort();
82 }
83 }
84
85 void
86 header_input_line(line)
87 char *line;
88 {
89 char *cp, savech;
90 enum msg_hdr_state newhdr;
91
92 if (!line[0]) {
93 process_header_end();
94 return;
95 }
96 if (hdr_state == HDR_STATE_ERROR) {
97 puts(line);
98 return;
99 }
100 if (line[0] == ' ' || line[0] == '\t') {
101 cont_line(line);
102 return;
103 }
104 cp = index(line, ':');
105 if (!cp) {
106 error(line, "header line has no colon");
107 return;
108 }
109 if (cp == line) {
110 error(line, "null header field name");
111 return;
112 }
113 while (cp[-1] == ' ' || cp[-1] == '\t')
114 cp--;
115 savech = *cp;
116 *cp = '\0';
117 if (!strcasecmp(line, "Content-Type"))
118 newhdr = HDR_STATE_CONT_TYPE;
119 else if (!strcasecmp(line, "Content-Transfer-Encoding"))
120 newhdr = HDR_STATE_CONT_TE;
121 else
122 newhdr = HDR_STATE_GOTSOME;
123 *cp = savech;
124 switch (newhdr) {
125 case HDR_STATE_CONT_TYPE:
126 if (got_cont_type) {
127 error(line, "duplicate Content-Type");
128 return;
129 }
130 sprintf(cont_type_buf, "%s\n", line);
131 got_cont_type = 1;
132 break;
133 case HDR_STATE_CONT_TE:
134 if (got_cont_te) {
135 error(line, "duplicate Content-Transfer-Encoding");
136 return;
137 }
138 sprintf(cont_te_buf, "%s\n", line);
139 got_cont_te = 1;
140 break;
141 default:
142 puts(line);
143 }
144 hdr_state = newhdr;
145 }