29#define WHO "qmail-dkverify"
53void out(
char *s) {
if (buffer_puts(&
bo,s) == -1)
_exit(111); }
59 out(
"ZOut of memory. (#4.3.0)\n");
64 out(
"ZUnable to switch to target directory. (#4.3.0)\n");
69 out(
"ZUnable to create DKIM stage file. (#4.3.0)\n");
74 out(
"ZUnable to unlink DKIM stage file. (#4.3.0)\n");
79 out(
"ZUnable to read message. (#4.3.0)\n");
84 out(
"ZUnable to crate socket pair. (#4.3.0)\n");
89 out(
"ZUnable to read control files. (#4.3.0)\n");
93static stralloc
me = {0};
95static stralloc dkheader = {0};
96static stralloc
fndkin = {0};
98static stralloc result = {0};
125 r = buffer_get(&
bi,&ch,1);
130 if (ch !=
'\r') buffer_put(&
bo,&ch,1);
131 r = buffer_get(&
bi,&ch,1);
135 buffer_put(&
bo,
"\r\n",2);
138 if (buffer_flush(&
bo) == -1)
die(51);
164 if (case_starts(
line.s,
"DKIM-Signature: ")) r = 1;
166 if (case_starts(
line.s,
"From: ")) {
167 at = str_chr(
line.s,
'@');
169 end = str_chr(
line.s,
'\n');
170 ket = str_chr(
line.s,
'>');
171 len = (ket < end) ? ket : end;
180 for (i = 0; i <
line.len; ++i) {
181 if (*(
line.s + i) ==
'=' && *(
line.s + i - 1) ==
'd') {
183 while (*(
line.s + i) !=
';') {
191 if (r >= 2 || !
match)
break;
207 args[0] =
"qmail-dkim";
214 if (!(child = fork())) {
216 if (errno)
_exit(111);
220 wait_pid(&wstat,child);
221 if (wait_crashed(wstat))
return 1;
223 switch (r = wait_exitcode(wstat)) {
239 if ((
fd = open_read(
fndkout.s)) == -1)
return 0;
245 if (result.len > 2) {
246 if (case_starts(result.s,
"pass")) r = 0;
247 if (case_starts(result.s,
"fail")) r = 35;
253 if (!stralloc_cats(&dkheader,
"; dkim="))
temp_nomem();
255 for (
j = 0;
j < result.len;
j++) {
257 if (ch ==
'\r' || ch ==
'\n' || ch ==
'\0')
continue;
258 if (
j <= max)
if (!stralloc_catb(&dkheader,&ch,1))
temp_nomem();
259 if (ch ==
' ' && (
j > max)) {
260 if (!stralloc_cats(&dkheader,
"\n "))
temp_nomem();
265 if (!stralloc_cats(&dkheader,
"; "))
temp_nomem();
284 args[0] =
"qmail-queue";
287 switch (child = vfork()) {
289 close(pi[0]); close(pi[1]);
296 if (errno)
_exit(111);
303 if (dkheader.len > 2) {
312 while ((r = read(
fd,&ch,1)) > 0)
319 wait_pid(&wstat,child);
320 if (wait_crashed(wstat))
return 1;
322 switch (r = wait_exitcode(wstat)) {
332 if (unlink(
fndkin.s) == -1)
358 mode = env_get(
"DKIM");
359 if (!mode || *mode !=
'+') r = 0;
int control_readline(stralloc *sa, char *fn)
int stralloc_copys(stralloc *, char const *)
unsigned int fmtqfn(char *s, char *dirslash, unsigned long id, int flagsplit)
void fnmake_dkim(unsigned long id)
int dkim_result(const char *me)