tidying: coverity issues
[exim.git] / src / src / pdkim / pdkim.c
1 /*
2  *  PDKIM - a RFC4871 (DKIM) implementation
3  *
4  *  Copyright (C) 2009 - 2016  Tom Kistner <tom@duncanthrax.net>
5  *  Copyright (C) 2016  Jeremy Harris <jgh@exim.org>
6  *
7  *  http://duncanthrax.net/pdkim/
8  *
9  *  This program is free software; you can redistribute it and/or modify
10  *  it under the terms of the GNU General Public License as published by
11  *  the Free Software Foundation; either version 2 of the License, or
12  *  (at your option) any later version.
13  *
14  *  This program is distributed in the hope that it will be useful,
15  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  *  GNU General Public License for more details.
18  *
19  *  You should have received a copy of the GNU General Public License along
20  *  with this program; if not, write to the Free Software Foundation, Inc.,
21  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
22  */
23
24 #include "../exim.h"
25
26
27 #ifndef DISABLE_DKIM    /* entire file */
28
29 #ifndef SUPPORT_TLS
30 # error Need SUPPORT_TLS for DKIM
31 #endif
32
33 #include "crypt_ver.h"
34
35 #ifdef RSA_OPENSSL
36 # include <openssl/rsa.h>
37 # include <openssl/ssl.h>
38 # include <openssl/err.h>
39 #elif defined(RSA_GNUTLS)
40 # include <gnutls/gnutls.h>
41 # include <gnutls/x509.h>
42 #endif
43
44 #include "pdkim.h"
45 #include "rsa.h"
46
47 #define PDKIM_SIGNATURE_VERSION     "1"
48 #define PDKIM_PUB_RECORD_VERSION    "DKIM1"
49
50 #define PDKIM_MAX_HEADER_LEN        65536
51 #define PDKIM_MAX_HEADERS           512
52 #define PDKIM_MAX_BODY_LINE_LEN     16384
53 #define PDKIM_DNS_TXT_MAX_NAMELEN   1024
54 #define PDKIM_DEFAULT_SIGN_HEADERS "From:Sender:Reply-To:Subject:Date:"\
55                              "Message-ID:To:Cc:MIME-Version:Content-Type:"\
56                              "Content-Transfer-Encoding:Content-ID:"\
57                              "Content-Description:Resent-Date:Resent-From:"\
58                              "Resent-Sender:Resent-To:Resent-Cc:"\
59                              "Resent-Message-ID:In-Reply-To:References:"\
60                              "List-Id:List-Help:List-Unsubscribe:"\
61                              "List-Subscribe:List-Post:List-Owner:List-Archive"
62
63 /* -------------------------------------------------------------------------- */
64 struct pdkim_stringlist {
65   char *value;
66   int  tag;
67   void *next;
68 };
69
70 #define PDKIM_STR_ALLOC_FRAG 256
71 struct pdkim_str {
72   char         *str;
73   unsigned int  len;
74   unsigned int  allocated;
75 };
76
77 /* -------------------------------------------------------------------------- */
78 /* A bunch of list constants */
79 const char *pdkim_querymethods[] = {
80   "dns/txt",
81   NULL
82 };
83 const char *pdkim_algos[] = {
84   "rsa-sha256",
85   "rsa-sha1",
86   NULL
87 };
88 const char *pdkim_canons[] = {
89   "simple",
90   "relaxed",
91   NULL
92 };
93 const char *pdkim_hashes[] = {
94   "sha256",
95   "sha1",
96   NULL
97 };
98 const char *pdkim_keytypes[] = {
99   "rsa",
100   NULL
101 };
102
103 typedef struct pdkim_combined_canon_entry {
104   const char *str;
105   int canon_headers;
106   int canon_body;
107 } pdkim_combined_canon_entry;
108
109 pdkim_combined_canon_entry pdkim_combined_canons[] = {
110   { "simple/simple",    PDKIM_CANON_SIMPLE,   PDKIM_CANON_SIMPLE },
111   { "simple/relaxed",   PDKIM_CANON_SIMPLE,   PDKIM_CANON_RELAXED },
112   { "relaxed/simple",   PDKIM_CANON_RELAXED,  PDKIM_CANON_SIMPLE },
113   { "relaxed/relaxed",  PDKIM_CANON_RELAXED,  PDKIM_CANON_RELAXED },
114   { "simple",           PDKIM_CANON_SIMPLE,   PDKIM_CANON_SIMPLE },
115   { "relaxed",          PDKIM_CANON_RELAXED,  PDKIM_CANON_SIMPLE },
116   { NULL,               0,                    0 }
117 };
118
119
120 /* -------------------------------------------------------------------------- */
121
122 const char *
123 pdkim_verify_status_str(int status)
124 {
125   switch(status) {
126     case PDKIM_VERIFY_NONE:    return "PDKIM_VERIFY_NONE";
127     case PDKIM_VERIFY_INVALID: return "PDKIM_VERIFY_INVALID";
128     case PDKIM_VERIFY_FAIL:    return "PDKIM_VERIFY_FAIL";
129     case PDKIM_VERIFY_PASS:    return "PDKIM_VERIFY_PASS";
130     default:                   return "PDKIM_VERIFY_UNKNOWN";
131   }
132 }
133
134 const char *
135 pdkim_verify_ext_status_str(int ext_status)
136 {
137   switch(ext_status) {
138     case PDKIM_VERIFY_FAIL_BODY: return "PDKIM_VERIFY_FAIL_BODY";
139     case PDKIM_VERIFY_FAIL_MESSAGE: return "PDKIM_VERIFY_FAIL_MESSAGE";
140     case PDKIM_VERIFY_INVALID_PUBKEY_UNAVAILABLE: return "PDKIM_VERIFY_INVALID_PUBKEY_UNAVAILABLE";
141     case PDKIM_VERIFY_INVALID_BUFFER_SIZE: return "PDKIM_VERIFY_INVALID_BUFFER_SIZE";
142     case PDKIM_VERIFY_INVALID_PUBKEY_DNSRECORD: return "PDKIM_VERIFY_INVALID_PUBKEY_DNSRECORD";
143     case PDKIM_VERIFY_INVALID_PUBKEY_IMPORT: return "PDKIM_VERIFY_INVALID_PUBKEY_IMPORT";
144     default: return "PDKIM_VERIFY_UNKNOWN";
145   }
146 }
147
148
149 /* -------------------------------------------------------------------------- */
150 /* Print debugging functions */
151 static void
152 pdkim_quoteprint(const uschar *data, int len)
153 {
154 int i;
155 for (i = 0; i < len; i++)
156   {
157   const int c = data[i];
158   switch (c)
159     {
160     case ' ' : debug_printf("{SP}"); break;
161     case '\t': debug_printf("{TB}"); break;
162     case '\r': debug_printf("{CR}"); break;
163     case '\n': debug_printf("{LF}"); break;
164     case '{' : debug_printf("{BO}"); break;
165     case '}' : debug_printf("{BC}"); break;
166     default:
167       if ( (c < 32) || (c > 127) )
168         debug_printf("{%02x}", c);
169       else
170         debug_printf("%c", c);
171       break;
172     }
173   }
174 debug_printf("\n");
175 }
176
177 static void
178 pdkim_hexprint(const uschar *data, int len)
179 {
180 int i;
181 for (i = 0 ; i < len; i++) debug_printf("%02x", data[i]);
182 debug_printf("\n");
183 }
184
185
186
187 /* SSS probably want to keep the "stringlist" notion */
188
189 static pdkim_stringlist *
190 pdkim_prepend_stringlist(pdkim_stringlist *base, char *str)
191 {
192 pdkim_stringlist *new_entry = malloc(sizeof(pdkim_stringlist));
193
194 if (!new_entry) return NULL;
195 memset(new_entry, 0, sizeof(pdkim_stringlist));
196 if (!(new_entry->value = strdup(str))) return NULL;
197 if (base) new_entry->next = base;
198 return new_entry;
199 }
200
201
202 /* -------------------------------------------------------------------------- */
203 /* A small "growing string" implementation to escape malloc/realloc hell */
204 /* String package: should be replaced by Exim standard ones */
205 /* SSS Ustrcpy */
206
207 static pdkim_str *
208 pdkim_strnew (const char *cstr)
209 {
210 unsigned int len = cstr ? strlen(cstr) : 0;
211 pdkim_str *p = malloc(sizeof(pdkim_str));
212
213 if (!p) return NULL;
214 memset(p, 0, sizeof(pdkim_str));
215 if (!(p->str = malloc(len+1)))
216   {
217   free(p);
218   return NULL;
219   }
220 p->allocated = len+1;
221 p->len = len;
222 if (cstr)
223   strcpy(p->str, cstr);
224 else
225   p->str[p->len] = '\0';
226 return p;
227 }
228
229
230 /*SSS Ustrncat */
231
232 static char *
233 pdkim_strncat(pdkim_str *str, const char *data, int len)
234 {
235 if ((str->allocated - str->len) < (len+1))
236   {
237   /* Extend the buffer */
238   int num_frags = ((len+1)/PDKIM_STR_ALLOC_FRAG)+1;
239   char *n = realloc(str->str,
240                     (str->allocated+(num_frags*PDKIM_STR_ALLOC_FRAG)));
241   if (n == NULL) return NULL;
242   str->str = n;
243   str->allocated += (num_frags*PDKIM_STR_ALLOC_FRAG);
244   }
245 strncpy(&(str->str[str->len]), data, len);
246 str->len += len;
247 str->str[str->len] = '\0';
248 return str->str;
249 }
250
251
252 /* SSS Ustrcat */
253
254 static char *
255 pdkim_strcat(pdkim_str *str, const char *cstr)
256 {
257 return pdkim_strncat(str, cstr, strlen(cstr));
258 }
259
260
261
262 /* Trim whitespace fore & aft */
263
264 static char *
265 pdkim_strtrim(pdkim_str *str)
266 {
267 char *p = str->str;
268 char *q = str->str;
269 while (*p == '\t' || *p == ' ') p++;            /* skip whitespace */
270 while (*p) {*q = *p; q++; p++;}                 /* dump the leading whitespace */
271 *q = '\0';
272 while (q != str->str && ( (*q == '\0') || (*q == '\t') || (*q == ' ') ) )
273   {                                             /* dump trailing whitespace */
274   *q = '\0';
275   q--;
276   }
277 str->len = strlen(str->str);
278 return str->str;
279 }
280
281
282
283 static char *
284 pdkim_strclear(pdkim_str *str)
285 {
286 str->str[0] = '\0';
287 str->len = 0;
288 return str->str;
289 }
290
291
292
293 static void
294 pdkim_strfree(pdkim_str *str)
295 {
296 if (!str) return;
297 if (str->str) free(str->str);
298 free(str);
299 }
300
301
302 static void
303 pdkim_stringlist_free(pdkim_stringlist * e)
304 {
305 while(e)
306   {
307   pdkim_stringlist * c = e;
308   if (e->value) free(e->value);
309   e = e->next;
310   free(c);
311   }
312 }
313
314
315
316 /* -------------------------------------------------------------------------- */
317
318 static void
319 pdkim_free_pubkey(pdkim_pubkey *pub)
320 {
321 if (pub)
322   {
323   if (pub->version    ) free(pub->version);
324   if (pub->granularity) free(pub->granularity);
325   if (pub->hashes     ) free(pub->hashes);
326   if (pub->keytype    ) free(pub->keytype);
327   if (pub->srvtype    ) free(pub->srvtype);
328   if (pub->notes      ) free(pub->notes);
329   free(pub);
330   }
331 }
332
333
334 /* -------------------------------------------------------------------------- */
335
336 static void
337 pdkim_free_sig(pdkim_signature *sig)
338 {
339 if (sig)
340   {
341   pdkim_signature *next = (pdkim_signature *)sig->next;
342
343   pdkim_stringlist_free(sig->headers);
344   if (sig->selector        ) free(sig->selector);
345   if (sig->domain          ) free(sig->domain);
346   if (sig->identity        ) free(sig->identity);
347   if (sig->copiedheaders   ) free(sig->copiedheaders);
348   if (sig->rsa_privkey     ) free(sig->rsa_privkey);
349   if (sig->sign_headers    ) free(sig->sign_headers);
350   if (sig->signature_header) free(sig->signature_header);
351
352   if (sig->pubkey) pdkim_free_pubkey(sig->pubkey);
353
354   free(sig);
355   if (next) pdkim_free_sig(next);
356   }
357 }
358
359
360 /* -------------------------------------------------------------------------- */
361
362 DLLEXPORT void
363 pdkim_free_ctx(pdkim_ctx *ctx)
364 {
365 if (ctx)
366   {
367   pdkim_stringlist_free(ctx->headers);
368   pdkim_free_sig(ctx->sig);
369   pdkim_strfree(ctx->cur_header);
370   free(ctx);
371   }
372 }
373
374
375 /* -------------------------------------------------------------------------- */
376 /* Matches the name of the passed raw "header" against
377    the passed colon-separated "tick", and invalidates
378    the entry in tick. Returns OK or fail-code */
379 /*XXX might be safer done using a pdkim_stringlist for "tick" */
380
381 static int
382 header_name_match(const char * header, char * tick)
383 {
384 char *hname;
385 char *lcopy;
386 char *p;
387 char *q;
388 int rc = PDKIM_FAIL;
389
390 /* Get header name */
391 char *hcolon = strchr(header, ':');
392
393 if (!hcolon) return rc; /* This isn't a header */
394
395 if (!(hname = malloc((hcolon-header)+1)))
396   return PDKIM_ERR_OOM;
397 memset(hname, 0, (hcolon-header)+1);
398 strncpy(hname, header, (hcolon-header));
399
400 /* Copy tick-off list locally, so we can punch zeroes into it */
401 if (!(lcopy = strdup(tick)))
402   {
403   free(hname);
404   return PDKIM_ERR_OOM;
405   }
406 p = lcopy;
407 q = strchr(p, ':');
408 while (q)
409   {
410   *q = '\0';
411
412   if (strcasecmp(p, hname) == 0)
413     {
414     rc = PDKIM_OK;
415     /* Invalidate header name instance in tick-off list */
416     tick[p-lcopy] = '_';
417     goto BAIL;
418     }
419
420   p = q+1;
421   q = strchr(p, ':');
422   }
423
424 if (strcasecmp(p, hname) == 0)
425   {
426   rc = PDKIM_OK;
427   /* Invalidate header name instance in tick-off list */
428   tick[p-lcopy] = '_';
429   }
430
431 BAIL:
432 free(hname);
433 free(lcopy);
434 return rc;
435 }
436
437
438 /* -------------------------------------------------------------------------- */
439 /* Performs "relaxed" canonicalization of a header. The returned pointer needs
440    to be free()d. */
441
442 static char *
443 pdkim_relax_header (char *header, int crlf)
444 {
445 BOOL past_field_name = FALSE;
446 BOOL seen_wsp = FALSE;
447 char *p;
448 char *q;
449 char *relaxed = malloc(strlen(header)+3);
450
451 if (!relaxed) return NULL;
452
453 q = relaxed;
454 for (p = header; *p != '\0'; p++)
455   {
456   int c = *p;
457   /* Ignore CR & LF */
458   if (c == '\r' || c == '\n')
459     continue;
460   if (c == '\t' || c == ' ')
461     {
462     if (seen_wsp)
463       continue;
464     c = ' ';                    /* Turns WSP into SP */
465     seen_wsp = TRUE;
466     }
467   else
468     if (!past_field_name && c == ':')
469       {
470       if (seen_wsp) q--;        /* This removes WSP before the colon */
471       seen_wsp = TRUE;          /* This removes WSP after the colon */
472       past_field_name = TRUE;
473       }
474     else
475       seen_wsp = FALSE;
476
477   /* Lowercase header name */
478   if (!past_field_name) c = tolower(c);
479   *q++ = c;
480   }
481
482 if (q > relaxed && q[-1] == ' ') q--; /* Squash eventual trailing SP */
483 *q = '\0';
484
485 if (crlf) strcat(relaxed, "\r\n");
486 return relaxed;
487 }
488
489
490 /* -------------------------------------------------------------------------- */
491 #define PDKIM_QP_ERROR_DECODE -1
492
493 static char *
494 pdkim_decode_qp_char(char *qp_p, int *c)
495 {
496 char *initial_pos = qp_p;
497
498 /* Advance one char */
499 qp_p++;
500
501 /* Check for two hex digits and decode them */
502 if (isxdigit(*qp_p) && isxdigit(qp_p[1]))
503   {
504   /* Do hex conversion */
505   *c = (isdigit(*qp_p) ? *qp_p - '0' : toupper(*qp_p) - 'A' + 10) << 4;
506   *c |= isdigit(qp_p[1]) ? qp_p[1] - '0' : toupper(qp_p[1]) - 'A' + 10;
507   return qp_p + 2;
508   }
509
510 /* Illegal char here */
511 *c = PDKIM_QP_ERROR_DECODE;
512 return initial_pos;
513 }
514
515
516 /* -------------------------------------------------------------------------- */
517
518 static char *
519 pdkim_decode_qp(char *str)
520 {
521 int nchar = 0;
522 char *q;
523 char *p = str;
524 char *n = malloc(strlen(p)+1);
525
526 if (!n) return NULL;
527
528 *n = '\0';
529 q = n;
530 while (*p != '\0')
531   {
532   if (*p == '=')
533     {
534     p = pdkim_decode_qp_char(p, &nchar);
535     if (nchar >= 0)
536       {
537       *q++ = nchar;
538       continue;
539       }
540     }
541   else
542     *q++ = *p;
543   p++;
544   }
545 *q = '\0';
546 return n;
547 }
548
549
550 /* -------------------------------------------------------------------------- */
551
552 static void
553 pdkim_decode_base64(uschar *str, blob * b)
554 {
555 int dlen;
556 dlen = b64decode(str, &b->data);
557 if (dlen < 0) b->data = NULL;
558 b->len = dlen;
559 }
560
561 /* -------------------------------------------------------------------------- */
562
563 static char *
564 pdkim_encode_base64(blob * b)
565 {
566 char * ret;
567 int old_pool = store_pool;
568
569 store_pool = POOL_PERM;
570 ret = CS b64encode(b->data, b->len);
571 store_pool = old_pool;
572 return ret;
573 }
574
575
576 /* -------------------------------------------------------------------------- */
577 #define PDKIM_HDR_LIMBO 0
578 #define PDKIM_HDR_TAG   1
579 #define PDKIM_HDR_VALUE 2
580
581 static pdkim_signature *
582 pdkim_parse_sig_header(pdkim_ctx *ctx, char *raw_hdr)
583 {
584 pdkim_signature *sig ;
585 char *p, *q;
586 pdkim_str *cur_tag = NULL;
587 pdkim_str *cur_val = NULL;
588 BOOL past_hname = FALSE;
589 BOOL in_b_val = FALSE;
590 int where = PDKIM_HDR_LIMBO;
591 int i;
592 int old_pool = store_pool;
593
594 /* There is a store-reset between header & body reception
595 so cannot use the main pool. Any allocs done by Exim
596 memory-handling must use the perm pool. */
597
598 store_pool = POOL_PERM;
599
600 if (!(sig = malloc(sizeof(pdkim_signature)))) return NULL;
601 memset(sig, 0, sizeof(pdkim_signature));
602 sig->bodylength = -1;
603
604 if (!(sig->rawsig_no_b_val = malloc(strlen(raw_hdr)+1)))
605   {
606   free(sig);
607   return NULL;
608   }
609
610 q = sig->rawsig_no_b_val;
611
612 for (p = raw_hdr; ; p++)
613   {
614   char c = *p;
615
616   /* Ignore FWS */
617   if (c == '\r' || c == '\n')
618     goto NEXT_CHAR;
619
620   /* Fast-forward through header name */
621   if (!past_hname)
622     {
623     if (c == ':') past_hname = TRUE;
624     goto NEXT_CHAR;
625     }
626
627   if (where == PDKIM_HDR_LIMBO)
628     {
629     /* In limbo, just wait for a tag-char to appear */
630     if (!(c >= 'a' && c <= 'z'))
631       goto NEXT_CHAR;
632
633     where = PDKIM_HDR_TAG;
634     }
635
636   if (where == PDKIM_HDR_TAG)
637     {
638     if (!cur_tag)
639       cur_tag = pdkim_strnew(NULL);
640
641     if (c >= 'a' && c <= 'z')
642       pdkim_strncat(cur_tag, p, 1);
643
644     if (c == '=')
645       {
646       if (strcmp(cur_tag->str, "b") == 0)
647         {
648         *q = '='; q++;
649         in_b_val = TRUE;
650         }
651       where = PDKIM_HDR_VALUE;
652       goto NEXT_CHAR;
653       }
654     }
655
656   if (where == PDKIM_HDR_VALUE)
657     {
658     if (!cur_val)
659       cur_val = pdkim_strnew(NULL);
660
661     if (c == '\r' || c == '\n' || c == ' ' || c == '\t')
662       goto NEXT_CHAR;
663
664     if (c == ';' || c == '\0')
665       {
666       if (cur_tag->len > 0)
667         {
668         pdkim_strtrim(cur_val);
669
670         DEBUG(D_acl) debug_printf(" %s=%s\n", cur_tag->str, cur_val->str);
671
672         switch (cur_tag->str[0])
673           {
674           case 'b':
675             if (cur_tag->str[1] == 'h')
676               pdkim_decode_base64(US cur_val->str, &sig->bodyhash);
677             else
678               pdkim_decode_base64(US cur_val->str, &sig->sigdata);
679             break;
680           case 'v':
681               /* We only support version 1, and that is currently the
682                  only version there is. */
683             if (strcmp(cur_val->str, PDKIM_SIGNATURE_VERSION) == 0)
684               sig->version = 1;
685             break;
686           case 'a':
687             for (i = 0; pdkim_algos[i]; i++)
688               if (strcmp(cur_val->str, pdkim_algos[i]) == 0)
689                 {
690                 sig->algo = i;
691                 break;
692                 }
693             break;
694           case 'c':
695             for (i = 0; pdkim_combined_canons[i].str; i++)
696               if (strcmp(cur_val->str, pdkim_combined_canons[i].str) == 0)
697                 {
698                 sig->canon_headers = pdkim_combined_canons[i].canon_headers;
699                 sig->canon_body    = pdkim_combined_canons[i].canon_body;
700                 break;
701                 }
702             break;
703           case 'q':
704             for (i = 0; pdkim_querymethods[i]; i++)
705               if (strcmp(cur_val->str, pdkim_querymethods[i]) == 0)
706                 {
707                 sig->querymethod = i;
708                 break;
709                 }
710             break;
711           case 's':
712             sig->selector = strdup(cur_val->str); break;
713           case 'd':
714             sig->domain = strdup(cur_val->str); break;
715           case 'i':
716             sig->identity = pdkim_decode_qp(cur_val->str); break;
717           case 't':
718             sig->created = strtoul(cur_val->str, NULL, 10); break;
719           case 'x':
720             sig->expires = strtoul(cur_val->str, NULL, 10); break;
721           case 'l':
722             sig->bodylength = strtol(cur_val->str, NULL, 10); break;
723           case 'h':
724             sig->headernames = string_copy(US cur_val->str); break;
725           case 'z':
726             sig->copiedheaders = pdkim_decode_qp(cur_val->str); break;
727           default:
728             DEBUG(D_acl) debug_printf(" Unknown tag encountered\n");
729             break;
730           }
731         }
732       pdkim_strclear(cur_tag);
733       pdkim_strclear(cur_val);
734       in_b_val = FALSE;
735       where = PDKIM_HDR_LIMBO;
736       }
737     else
738       pdkim_strncat(cur_val, p, 1);
739     }
740
741 NEXT_CHAR:
742   if (c == '\0')
743     break;
744
745   if (!in_b_val)
746     *q++ = c;
747   }
748
749 store_pool = old_pool;
750
751 /* Make sure the most important bits are there. */
752 if (!(sig->domain      && (*(sig->domain)      != '\0') &&
753       sig->selector    && (*(sig->selector)    != '\0') &&
754       sig->headernames && (*(sig->headernames) != '\0') &&
755       sig->version))
756   {
757   pdkim_free_sig(sig);
758   return NULL;
759   }
760
761 *q = '\0';
762 /* Chomp raw header. The final newline must not be added to the signature. */
763 while (--q > sig->rawsig_no_b_val  && (*q == '\r' || *q == '\n'))
764   *q = '\0';
765
766 DEBUG(D_acl)
767   {
768   debug_printf(
769           "PDKIM >> Raw signature w/o b= tag value >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n");
770   pdkim_quoteprint(US sig->rawsig_no_b_val, strlen(sig->rawsig_no_b_val));
771   debug_printf(
772           "PDKIM >> Sig size: %4u bits\n", (unsigned) sig->sigdata.len*8);
773   debug_printf(
774           "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
775   }
776
777 exim_sha_init(&sig->body_hash, sig->algo == PDKIM_ALGO_RSA_SHA1);
778 return sig;
779 }
780
781
782 /* -------------------------------------------------------------------------- */
783
784 static pdkim_pubkey *
785 pdkim_parse_pubkey_record(pdkim_ctx *ctx, char *raw_record)
786 {
787 pdkim_pubkey *pub;
788 char *p;
789 pdkim_str *cur_tag = NULL;
790 pdkim_str *cur_val = NULL;
791 int where = PDKIM_HDR_LIMBO;
792
793 if (!(pub = malloc(sizeof(pdkim_pubkey)))) return NULL;
794 memset(pub, 0, sizeof(pdkim_pubkey));
795
796 for (p = raw_record; ; p++)
797   {
798   char c = *p;
799
800   /* Ignore FWS */
801   if (c == '\r' || c == '\n')
802     goto NEXT_CHAR;
803
804   if (where == PDKIM_HDR_LIMBO)
805     {
806     /* In limbo, just wait for a tag-char to appear */
807     if (!(c >= 'a' && c <= 'z'))
808       goto NEXT_CHAR;
809
810     where = PDKIM_HDR_TAG;
811     }
812
813   if (where == PDKIM_HDR_TAG)
814     {
815     if (!cur_tag)
816       cur_tag = pdkim_strnew(NULL);
817
818     if (c >= 'a' && c <= 'z')
819       pdkim_strncat(cur_tag, p, 1);
820
821     if (c == '=')
822       {
823       where = PDKIM_HDR_VALUE;
824       goto NEXT_CHAR;
825       }
826     }
827
828   if (where == PDKIM_HDR_VALUE)
829     {
830     if (!cur_val)
831       cur_val = pdkim_strnew(NULL);
832
833     if (c == ';' || c == '\0')
834       {
835       if (cur_tag->len > 0)
836         {
837         pdkim_strtrim(cur_val);
838         DEBUG(D_acl) debug_printf(" %s=%s\n", cur_tag->str, cur_val->str);
839
840         switch (cur_tag->str[0])
841           {
842           case 'v':
843             /* This tag isn't evaluated because:
844                - We only support version DKIM1.
845                - Which is the default for this value (set below)
846                - Other versions are currently not specified.      */
847             break;
848           case 'h':
849             pub->hashes = strdup(cur_val->str); break;
850           case 'g':
851             pub->granularity = strdup(cur_val->str); break;
852           case 'n':
853             pub->notes = pdkim_decode_qp(cur_val->str); break;
854           case 'p':
855             pdkim_decode_base64(US cur_val->str, &pub->key);
856             break;
857           case 'k':
858             pub->hashes = strdup(cur_val->str); break;
859           case 's':
860             pub->srvtype = strdup(cur_val->str); break;
861           case 't':
862             if (strchr(cur_val->str, 'y') != NULL) pub->testing = 1;
863             if (strchr(cur_val->str, 's') != NULL) pub->no_subdomaining = 1;
864             break;
865           default:
866             DEBUG(D_acl) debug_printf(" Unknown tag encountered\n");
867             break;
868           }
869         }
870       pdkim_strclear(cur_tag);
871       pdkim_strclear(cur_val);
872       where = PDKIM_HDR_LIMBO;
873       }
874     else
875       pdkim_strncat(cur_val, p, 1);
876     }
877
878 NEXT_CHAR:
879   if (c == '\0') break;
880   }
881
882 /* Set fallback defaults */
883 if (!pub->version    ) pub->version     = strdup(PDKIM_PUB_RECORD_VERSION);
884 if (!pub->granularity) pub->granularity = strdup("*");
885 if (!pub->keytype    ) pub->keytype     = strdup("rsa");
886 if (!pub->srvtype    ) pub->srvtype     = strdup("*");
887
888 /* p= is required */
889 if (pub->key.data)
890   return pub;
891
892 pdkim_free_pubkey(pub);
893 return NULL;
894 }
895
896
897 /* -------------------------------------------------------------------------- */
898
899 static int
900 pdkim_update_bodyhash(pdkim_ctx *ctx, const char *data, int len)
901 {
902 pdkim_signature *sig = ctx->sig;
903 /* Cache relaxed version of data */
904 uschar *relaxed_data = NULL;
905 int     relaxed_len  = 0;
906
907 /* Traverse all signatures, updating their hashes. */
908 while (sig)
909   {
910   /* Defaults to simple canon (no further treatment necessary) */
911   const uschar *canon_data = CUS data;
912   int           canon_len = len;
913
914   if (sig->canon_body == PDKIM_CANON_RELAXED)
915     {
916     /* Relax the line if not done already */
917     if (!relaxed_data)
918       {
919       BOOL seen_wsp = FALSE;
920       const char *p;
921       int q = 0;
922
923       if (!(relaxed_data = malloc(len+1)))
924         return PDKIM_ERR_OOM;
925
926       for (p = data; *p; p++)
927         {
928         char c = *p;
929         if (c == '\r')
930           {
931           if (q > 0 && relaxed_data[q-1] == ' ')
932             q--;
933           }
934         else if (c == '\t' || c == ' ')
935           {
936           c = ' '; /* Turns WSP into SP */
937           if (seen_wsp)
938             continue;
939           seen_wsp = TRUE;
940           }
941         else
942           seen_wsp = FALSE;
943         relaxed_data[q++] = c;
944         }
945       relaxed_data[q] = '\0';
946       relaxed_len = q;
947       }
948     canon_data = relaxed_data;
949     canon_len  = relaxed_len;
950     }
951
952   /* Make sure we don't exceed the to-be-signed body length */
953   if (  sig->bodylength >= 0
954      && sig->signed_body_bytes + (unsigned long)canon_len > sig->bodylength
955      )
956     canon_len = sig->bodylength - sig->signed_body_bytes;
957
958   if (canon_len > 0)
959     {
960     exim_sha_update(&sig->body_hash, CCS canon_data, canon_len);
961     sig->signed_body_bytes += canon_len;
962     DEBUG(D_acl) pdkim_quoteprint(canon_data, canon_len);
963     }
964
965   sig = sig->next;
966   }
967
968 if (relaxed_data) free(relaxed_data);
969 return PDKIM_OK;
970 }
971
972
973 /* -------------------------------------------------------------------------- */
974
975 static int
976 pdkim_finish_bodyhash(pdkim_ctx *ctx)
977 {
978 pdkim_signature *sig;
979
980 /* Traverse all signatures */
981 for (sig = ctx->sig; sig; sig = sig->next)
982   {                                     /* Finish hashes */
983   blob bh;
984
985   exim_sha_finish(&sig->body_hash, &bh);
986
987   DEBUG(D_acl)
988     {
989     debug_printf("PDKIM [%s] Body bytes hashed: %lu\n"
990                  "PDKIM [%s] bh  computed: ",
991                 sig->domain, sig->signed_body_bytes, sig->domain);
992     pdkim_hexprint(CUS bh.data, bh.len);
993     }
994
995   /* SIGNING -------------------------------------------------------------- */
996   if (ctx->mode == PDKIM_MODE_SIGN)
997     {
998     sig->bodyhash = bh;
999
1000     /* If bodylength limit is set, and we have received less bytes
1001        than the requested amount, effectively remove the limit tag. */
1002     if (sig->signed_body_bytes < sig->bodylength)
1003       sig->bodylength = -1;
1004     }
1005
1006   /* VERIFICATION --------------------------------------------------------- */
1007   else
1008     {
1009     /* Compare bodyhash */
1010     if (memcmp(bh.data, sig->bodyhash.data, bh.len) == 0)
1011       {
1012       DEBUG(D_acl) debug_printf("PDKIM [%s] Body hash verified OK\n", sig->domain);
1013       }
1014     else
1015       {
1016       DEBUG(D_acl)
1017         {
1018         debug_printf("PDKIM [%s] bh signature: ", sig->domain);
1019         pdkim_hexprint(sig->bodyhash.data,
1020                          exim_sha_hashlen(&sig->body_hash));
1021         debug_printf("PDKIM [%s] Body hash did NOT verify\n", sig->domain);
1022         }
1023       sig->verify_status     = PDKIM_VERIFY_FAIL;
1024       sig->verify_ext_status = PDKIM_VERIFY_FAIL_BODY;
1025       }
1026     }
1027   }
1028
1029 return PDKIM_OK;
1030 }
1031
1032
1033
1034 /* -------------------------------------------------------------------------- */
1035 /* Callback from pdkim_feed below for processing complete body lines */
1036
1037 static int
1038 pdkim_bodyline_complete(pdkim_ctx *ctx)
1039 {
1040 char *p = ctx->linebuf;
1041 int   n = ctx->linebuf_offset;
1042 pdkim_signature *sig = ctx->sig;        /*XXX assumes only one sig */
1043
1044 /* Ignore extra data if we've seen the end-of-data marker */
1045 if (ctx->seen_eod) goto BAIL;
1046
1047 /* We've always got one extra byte to stuff a zero ... */
1048 ctx->linebuf[ctx->linebuf_offset] = '\0';
1049
1050 /* Terminate on EOD marker */
1051 if (memcmp(p, ".\r\n", 3) == 0)
1052   {
1053   /* In simple body mode, if any empty lines were buffered,
1054   replace with one. rfc 4871 3.4.3 */
1055   /*XXX checking the signed-body-bytes is a gross hack; I think
1056   it indicates that all linebreaks should be buffered, including
1057   the one terminating a text line */
1058   if (  sig && sig->canon_body == PDKIM_CANON_SIMPLE
1059      && sig->signed_body_bytes == 0
1060      && ctx->num_buffered_crlf > 0
1061      )
1062     pdkim_update_bodyhash(ctx, "\r\n", 2);
1063
1064   ctx->seen_eod = TRUE;
1065   goto BAIL;
1066   }
1067 /* Unstuff dots */
1068 if (memcmp(p, "..", 2) == 0)
1069   {
1070   p++;
1071   n--;
1072   }
1073
1074 /* Empty lines need to be buffered until we find a non-empty line */
1075 if (memcmp(p, "\r\n", 2) == 0)
1076   {
1077   ctx->num_buffered_crlf++;
1078   goto BAIL;
1079   }
1080
1081 if (sig && sig->canon_body == PDKIM_CANON_RELAXED)
1082   {
1083   /* Lines with just spaces need to be buffered too */
1084   char *check = p;
1085   while (memcmp(check, "\r\n", 2) != 0)
1086     {
1087     char c = *check;
1088
1089     if (c != '\t' && c != ' ')
1090       goto PROCESS;
1091     check++;
1092     }
1093
1094   ctx->num_buffered_crlf++;
1095   goto BAIL;
1096 }
1097
1098 PROCESS:
1099 /* At this point, we have a non-empty line, so release the buffered ones. */
1100 while (ctx->num_buffered_crlf)
1101   {
1102   pdkim_update_bodyhash(ctx, "\r\n", 2);
1103   ctx->num_buffered_crlf--;
1104   }
1105
1106 pdkim_update_bodyhash(ctx, p, n);
1107
1108 BAIL:
1109 ctx->linebuf_offset = 0;
1110 return PDKIM_OK;
1111 }
1112
1113
1114 /* -------------------------------------------------------------------------- */
1115 /* Callback from pdkim_feed below for processing complete headers */
1116 #define DKIM_SIGNATURE_HEADERNAME "DKIM-Signature:"
1117
1118 static int
1119 pdkim_header_complete(pdkim_ctx *ctx)
1120 {
1121 /* Special case: The last header can have an extra \r appended */
1122 if ( (ctx->cur_header->len > 1) &&
1123      (ctx->cur_header->str[(ctx->cur_header->len)-1] == '\r') )
1124   {
1125   ctx->cur_header->str[(ctx->cur_header->len)-1] = '\0';
1126   ctx->cur_header->len--;
1127   }
1128
1129 ctx->num_headers++;
1130 if (ctx->num_headers > PDKIM_MAX_HEADERS) goto BAIL;
1131
1132 /* SIGNING -------------------------------------------------------------- */
1133 if (ctx->mode == PDKIM_MODE_SIGN)
1134   {
1135   pdkim_signature *sig;
1136
1137   for (sig = ctx->sig; sig; sig = sig->next)                    /* Traverse all signatures */
1138     {
1139     pdkim_stringlist *list;
1140
1141     /* Add header to the signed headers list (in reverse order) */
1142     if (!(list = pdkim_prepend_stringlist(sig->headers,
1143                                   ctx->cur_header->str)))
1144       return PDKIM_ERR_OOM;
1145     sig->headers = list;
1146     }
1147   }
1148
1149 /* VERIFICATION ----------------------------------------------------------- */
1150 /* DKIM-Signature: headers are added to the verification list */
1151 if (ctx->mode == PDKIM_MODE_VERIFY)
1152   {
1153   if (strncasecmp(ctx->cur_header->str,
1154                   DKIM_SIGNATURE_HEADERNAME,
1155                   strlen(DKIM_SIGNATURE_HEADERNAME)) == 0)
1156     {
1157     pdkim_signature *new_sig;
1158
1159     /* Create and chain new signature block */
1160     DEBUG(D_acl) debug_printf(
1161         "PDKIM >> Found sig, trying to parse >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n");
1162
1163     if ((new_sig = pdkim_parse_sig_header(ctx, ctx->cur_header->str)))
1164       {
1165       pdkim_signature *last_sig = ctx->sig;
1166       if (!last_sig)
1167         ctx->sig = new_sig;
1168       else
1169         {
1170         while (last_sig->next) last_sig = last_sig->next;
1171         last_sig->next = new_sig;
1172         }
1173       }
1174     else
1175       DEBUG(D_acl) debug_printf(
1176           "Error while parsing signature header\n"
1177           "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
1178     }
1179
1180   /* every other header is stored for signature verification */
1181   else
1182     {
1183     pdkim_stringlist *list;
1184
1185     if (!(list = pdkim_prepend_stringlist(ctx->headers, ctx->cur_header->str)))
1186       return PDKIM_ERR_OOM;
1187     ctx->headers = list;
1188     }
1189   }
1190
1191 BAIL:
1192 pdkim_strclear(ctx->cur_header); /* Re-use existing pdkim_str */
1193 return PDKIM_OK;
1194 }
1195
1196
1197
1198 /* -------------------------------------------------------------------------- */
1199 #define HEADER_BUFFER_FRAG_SIZE 256
1200
1201 DLLEXPORT int
1202 pdkim_feed (pdkim_ctx *ctx, char *data, int len)
1203 {
1204 int p;
1205
1206 for (p = 0; p<len; p++)
1207   {
1208   char c = data[p];
1209
1210   if (ctx->past_headers)
1211     {
1212     /* Processing body byte */
1213     ctx->linebuf[ctx->linebuf_offset++] = c;
1214     if (c == '\n')
1215       {
1216       int rc = pdkim_bodyline_complete(ctx); /* End of line */
1217       if (rc != PDKIM_OK) return rc;
1218       }
1219     if (ctx->linebuf_offset == (PDKIM_MAX_BODY_LINE_LEN-1))
1220       return PDKIM_ERR_LONG_LINE;
1221     }
1222   else
1223     {
1224     /* Processing header byte */
1225     if (c != '\r')
1226       {
1227       if (c == '\n')
1228         {
1229         if (ctx->seen_lf)
1230           {
1231           int rc = pdkim_header_complete(ctx); /* Seen last header line */
1232           if (rc != PDKIM_OK) return rc;
1233
1234           ctx->past_headers = TRUE;
1235           ctx->seen_lf = 0;
1236           DEBUG(D_acl) debug_printf(
1237               "PDKIM >> Body data for hash, canonicalized >>>>>>>>>>>>>>>>>>>>>>\n");
1238           continue;
1239           }
1240         else
1241           ctx->seen_lf = TRUE;
1242         }
1243       else if (ctx->seen_lf)
1244         {
1245         if (!(c == '\t' || c == ' '))
1246           {
1247           int rc = pdkim_header_complete(ctx); /* End of header */
1248           if (rc != PDKIM_OK) return rc;
1249           }
1250         ctx->seen_lf = FALSE;
1251         }
1252       }
1253
1254     if (!ctx->cur_header)
1255       if (!(ctx->cur_header = pdkim_strnew(NULL)))
1256         return PDKIM_ERR_OOM;
1257
1258     if (ctx->cur_header->len < PDKIM_MAX_HEADER_LEN)
1259       if (!pdkim_strncat(ctx->cur_header, &data[p], 1))
1260         return PDKIM_ERR_OOM;
1261     }
1262   }
1263 return PDKIM_OK;
1264 }
1265
1266 /*
1267  * RFC 5322 specifies that header line length SHOULD be no more than 78
1268  * lets make it so!
1269  *  pdkim_headcat
1270  * returns char*
1271  *
1272  * col: this int holds and receives column number (octets since last '\n')
1273  * str: partial string to append to
1274  * pad: padding, split line or space after before or after eg: ";"
1275  * intro: - must join to payload eg "h=", usually the tag name
1276  * payload: eg base64 data - long data can be split arbitrarily.
1277  *
1278  * this code doesn't fold the header in some of the places that RFC4871
1279  * allows: As per RFC5322(2.2.3) it only folds before or after tag-value
1280  * pairs and inside long values. it also always spaces or breaks after the
1281  * "pad"
1282  *
1283  * no guarantees are made for output given out-of range input. like tag
1284  * names longer than 78, or bogus col. Input is assumed to be free of line breaks.
1285  */
1286
1287 static char *
1288 pdkim_headcat(int *col, pdkim_str *str, const char * pad,
1289   const char *intro, const char *payload)
1290 {
1291 size_t l;
1292
1293 if (pad)
1294   {
1295   l = strlen(pad);
1296   if (*col + l > 78)
1297     {
1298     pdkim_strcat(str, "\r\n\t");
1299     *col = 1;
1300     }
1301   pdkim_strncat(str, pad, l);
1302   *col += l;
1303   }
1304
1305 l = (pad?1:0) + (intro?strlen(intro):0);
1306
1307 if (*col + l > 78)
1308   { /*can't fit intro - start a new line to make room.*/
1309   pdkim_strcat(str, "\r\n\t");
1310   *col = 1;
1311   l = intro?strlen(intro):0;
1312   }
1313
1314 l += payload ? strlen(payload):0 ;
1315
1316 while (l>77)
1317   { /* this fragment will not fit on a single line */
1318   if (pad)
1319     {
1320     pdkim_strcat(str, " ");
1321     *col += 1;
1322     pad = NULL; /* only want this once */
1323     l--;
1324     }
1325
1326   if (intro)
1327     {
1328     size_t sl = strlen(intro);
1329
1330     pdkim_strncat(str, intro, sl);
1331     *col += sl;
1332     l -= sl;
1333     intro = NULL; /* only want this once */
1334     }
1335
1336   if (payload)
1337     {
1338     size_t sl = strlen(payload);
1339     size_t chomp = *col+sl < 77 ? sl : 78-*col;
1340
1341     pdkim_strncat(str, payload, chomp);
1342     *col += chomp;
1343     payload += chomp;
1344     l -= chomp-1;
1345     }
1346
1347   /* the while precondition tells us it didn't fit. */
1348   pdkim_strcat(str, "\r\n\t");
1349   *col = 1;
1350   }
1351
1352 if (*col + l > 78)
1353   {
1354   pdkim_strcat(str, "\r\n\t");
1355   *col = 1;
1356   pad = NULL;
1357   }
1358
1359 if (pad)
1360   {
1361   pdkim_strcat(str, " ");
1362   *col += 1;
1363   pad = NULL;
1364   }
1365
1366 if (intro)
1367   {
1368   size_t sl = strlen(intro);
1369
1370   pdkim_strncat(str, intro, sl);
1371   *col += sl;
1372   l -= sl;
1373   intro = NULL;
1374   }
1375
1376 if (payload)
1377   {
1378   size_t sl = strlen(payload);
1379
1380   pdkim_strncat(str, payload, sl);
1381   *col += sl;
1382   }
1383
1384 return str->str;
1385 }
1386
1387
1388 /* -------------------------------------------------------------------------- */
1389
1390 static char *
1391 pdkim_create_header(pdkim_signature *sig, BOOL final)
1392 {
1393 char *rc = NULL;
1394 char *base64_bh = NULL;
1395 char *base64_b  = NULL;
1396 int col = 0;
1397 pdkim_str *hdr;
1398 pdkim_str *canon_all;
1399
1400 if (!(hdr = pdkim_strnew("DKIM-Signature: v="PDKIM_SIGNATURE_VERSION)))
1401   return NULL;
1402
1403 if (!(canon_all = pdkim_strnew(pdkim_canons[sig->canon_headers])))
1404   goto BAIL;
1405
1406 if (!(base64_bh = pdkim_encode_base64(&sig->bodyhash)))
1407   goto BAIL;
1408
1409 col = strlen(hdr->str);
1410
1411 /* Required and static bits */
1412 if (  pdkim_headcat(&col, hdr, ";", "a=", pdkim_algos[sig->algo])
1413    && pdkim_headcat(&col, hdr, ";", "q=", pdkim_querymethods[sig->querymethod])
1414    && pdkim_strcat(canon_all, "/")
1415    && pdkim_strcat(canon_all, pdkim_canons[sig->canon_body])
1416    && pdkim_headcat(&col, hdr, ";", "c=", canon_all->str)
1417    && pdkim_headcat(&col, hdr, ";", "d=", sig->domain)
1418    && pdkim_headcat(&col, hdr, ";", "s=", sig->selector)
1419    )
1420   {
1421   /* list of header names can be split between items. */
1422     {
1423     char *n = CS string_copy(sig->headernames);
1424     char *i = "h=";
1425     char *s = ";";
1426
1427     if (!n) goto BAIL;
1428     while (*n)
1429       {
1430       char *c = strchr(n, ':');
1431
1432       if (c) *c ='\0';
1433
1434       if (!i)
1435         if (!pdkim_headcat(&col, hdr, NULL, NULL, ":"))
1436           {
1437           goto BAIL;
1438           }
1439
1440       if (!pdkim_headcat(&col, hdr, s, i, n))
1441         {
1442         goto BAIL;
1443         }
1444
1445       if (!c)
1446         break;
1447
1448       n = c+1;
1449       s = NULL;
1450       i = NULL;
1451       }
1452     }
1453
1454   if(!pdkim_headcat(&col, hdr, ";", "bh=", base64_bh))
1455     goto BAIL;
1456
1457   /* Optional bits */
1458   if (sig->identity)
1459     if(!pdkim_headcat(&col, hdr, ";", "i=", sig->identity))
1460       goto BAIL;
1461
1462   if (sig->created > 0)
1463     {
1464     char minibuf[20];
1465
1466     snprintf(minibuf, 20, "%lu", sig->created);
1467     if(!pdkim_headcat(&col, hdr, ";", "t=", minibuf))
1468       goto BAIL;
1469   }
1470
1471   if (sig->expires > 0)
1472     {
1473     char minibuf[20];
1474
1475     snprintf(minibuf, 20, "%lu", sig->expires);
1476     if(!pdkim_headcat(&col, hdr, ";", "x=", minibuf))
1477       goto BAIL;
1478     }
1479
1480   if (sig->bodylength >= 0)
1481     {
1482     char minibuf[20];
1483
1484     snprintf(minibuf, 20, "%lu", sig->bodylength);
1485     if(!pdkim_headcat(&col, hdr, ";", "l=", minibuf))
1486       goto BAIL;
1487     }
1488
1489   /* Preliminary or final version? */
1490   if (final)
1491     {
1492     if (!(base64_b = pdkim_encode_base64(&sig->sigdata)))
1493       goto BAIL;
1494     if (!pdkim_headcat(&col, hdr, ";", "b=", base64_b))
1495       goto BAIL;
1496   }
1497   else 
1498     if(!pdkim_headcat(&col, hdr, ";", "b=", ""))
1499       goto BAIL;
1500
1501   /* add trailing semicolon: I'm not sure if this is actually needed */
1502   if (!pdkim_headcat(&col, hdr, NULL, ";", ""))
1503     goto BAIL;
1504   }
1505
1506 rc = strdup(hdr->str);
1507
1508 BAIL:
1509 pdkim_strfree(hdr);
1510 if (canon_all) pdkim_strfree(canon_all);
1511 return rc;
1512 }
1513
1514
1515 /* -------------------------------------------------------------------------- */
1516
1517 DLLEXPORT int
1518 pdkim_feed_finish(pdkim_ctx *ctx, pdkim_signature **return_signatures)
1519 {
1520 pdkim_signature *sig = ctx->sig;
1521 pdkim_str *headernames = NULL;             /* Collected signed header names */
1522
1523 /* Check if we must still flush a (partial) header. If that is the
1524    case, the message has no body, and we must compute a body hash
1525    out of '<CR><LF>' */
1526 if (ctx->cur_header && ctx->cur_header->len)
1527   {
1528   int rc = pdkim_header_complete(ctx);
1529   if (rc != PDKIM_OK) return rc;
1530   pdkim_update_bodyhash(ctx, "\r\n", 2);
1531   }
1532 else
1533   DEBUG(D_acl) debug_printf(
1534       "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
1535
1536 /* Build (and/or evaluate) body hash */
1537 if (pdkim_finish_bodyhash(ctx) != PDKIM_OK)
1538   return PDKIM_ERR_OOM;
1539
1540 /* SIGNING -------------------------------------------------------------- */
1541 if (ctx->mode == PDKIM_MODE_SIGN)
1542   if (!(headernames = pdkim_strnew(NULL)))
1543     return PDKIM_ERR_OOM;
1544 /* ---------------------------------------------------------------------- */
1545
1546 while (sig)
1547   {
1548   BOOL is_sha1 = sig->algo == PDKIM_ALGO_RSA_SHA1;
1549   hctx hhash_ctx;
1550   char * sig_hdr;
1551   blob hhash;
1552   blob hdata;
1553   int hdata_alloc = 0;
1554
1555   hdata.data = NULL;
1556   hdata.len = 0;
1557
1558   exim_sha_init(&hhash_ctx, is_sha1);
1559
1560   DEBUG(D_acl) debug_printf(
1561       "PDKIM >> Hashed header data, canonicalized, in sequence >>>>>>>>>>>>>>\n");
1562
1563   /* SIGNING ---------------------------------------------------------------- */
1564   /* When signing, walk through our header list and add them to the hash. As we
1565      go, construct a list of the header's names to use for the h= parameter.
1566      Then append to that list any remaining header names for which there was no
1567      header to sign. */
1568
1569   if (ctx->mode == PDKIM_MODE_SIGN)
1570     {
1571     pdkim_stringlist *p;
1572     const uschar * l;
1573     uschar * s;
1574     int sep = 0;
1575
1576     for (p = sig->headers; p; p = p->next)
1577       if (header_name_match(p->value, sig->sign_headers) == PDKIM_OK)
1578         {
1579         uschar * rh;
1580         /* Collect header names (Note: colon presence is guaranteed here) */
1581         uschar * q = Ustrchr(p->value, ':');
1582
1583         if (!(pdkim_strncat(headernames, p->value,
1584                           (q - US p->value) + (p->next ? 1 : 0))))
1585           return PDKIM_ERR_OOM;
1586
1587         rh = sig->canon_headers == PDKIM_CANON_RELAXED
1588           ? US pdkim_relax_header(p->value, 1) /* cook header for relaxed canon */
1589           : string_copy(CUS p->value);         /* just copy it for simple canon */
1590         if (!rh)
1591           return PDKIM_ERR_OOM;
1592
1593         /* Feed header to the hash algorithm */
1594         exim_sha_update(&hhash_ctx, CCS rh, Ustrlen(rh));
1595
1596         /* Remember headers block for signing (when the library cannot do incremental)  */
1597         (void) exim_rsa_data_append(&hdata, &hdata_alloc, rh);
1598
1599         DEBUG(D_acl) pdkim_quoteprint(rh, Ustrlen(rh));
1600         }
1601
1602     l = US sig->sign_headers;
1603     while((s = string_nextinlist(&l, &sep, NULL, 0)))
1604       if (*s != '_')
1605         {                       /*SSS string_append_listele() */
1606         if (headernames->len > 0 && headernames->str[headernames->len-1] != ':')
1607           if (!(pdkim_strncat(headernames, ":", 1)))
1608             return PDKIM_ERR_OOM;
1609         if (!(pdkim_strncat(headernames, CS s, Ustrlen(s))))
1610           return PDKIM_ERR_OOM;
1611         }
1612     }
1613
1614   /* VERIFICATION ----------------------------------------------------------- */
1615   /* When verifying, walk through the header name list in the h= parameter and
1616      add the headers to the hash in that order. */
1617   else
1618     {
1619     uschar * b = string_copy(sig->headernames);
1620     uschar * p = b;
1621     uschar * q;
1622     pdkim_stringlist * hdrs;
1623
1624     if (!b) return PDKIM_ERR_OOM;
1625
1626     /* clear tags */
1627     for (hdrs = ctx->headers; hdrs; hdrs = hdrs->next)
1628       hdrs->tag = 0;
1629
1630     while(1)
1631       {
1632       if ((q = Ustrchr(p, ':')))
1633         *q = '\0';
1634
1635 /*XXX walk the list of headers in same order as received. */
1636       for (hdrs = ctx->headers; hdrs; hdrs = hdrs->next)
1637         if (  hdrs->tag == 0
1638            && strncasecmp(hdrs->value, CS p, Ustrlen(p)) == 0
1639            && (hdrs->value)[Ustrlen(p)] == ':'
1640            )
1641           {
1642           uschar * rh = sig->canon_headers == PDKIM_CANON_RELAXED
1643             ? US pdkim_relax_header(hdrs->value, 1) /* cook header for relaxed canon */
1644             : string_copy(CUS hdrs->value);         /* just copy it for simple canon */
1645           if (!rh)
1646             return PDKIM_ERR_OOM;
1647
1648           /* Feed header to the hash algorithm */
1649           exim_sha_update(&hhash_ctx, CCS rh, Ustrlen(rh));
1650
1651           DEBUG(D_acl) pdkim_quoteprint(rh, Ustrlen(rh));
1652           hdrs->tag = 1;
1653           break;
1654           }
1655
1656       if (!q) break;
1657       p = q+1;
1658       }
1659     }
1660
1661   DEBUG(D_acl) debug_printf(
1662             "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
1663
1664   /* SIGNING ---------------------------------------------------------------- */
1665   if (ctx->mode == PDKIM_MODE_SIGN)
1666     {
1667     /* Copy headernames to signature struct */
1668     sig->headernames = string_copy(US headernames->str);
1669     pdkim_strfree(headernames);
1670
1671     /* Create signature header with b= omitted */
1672     sig_hdr = pdkim_create_header(sig, FALSE);
1673     }
1674
1675   /* VERIFICATION ----------------------------------------------------------- */
1676   else
1677     sig_hdr = strdup(sig->rawsig_no_b_val);
1678   /* ------------------------------------------------------------------------ */
1679
1680   if (!sig_hdr)
1681     return PDKIM_ERR_OOM;
1682
1683   /* Relax header if necessary */
1684   if (sig->canon_headers == PDKIM_CANON_RELAXED)
1685     {
1686     char *relaxed_hdr = pdkim_relax_header(sig_hdr, 0);
1687
1688     free(sig_hdr);
1689     if (!relaxed_hdr)
1690       return PDKIM_ERR_OOM;
1691     sig_hdr = relaxed_hdr;
1692     }
1693
1694   DEBUG(D_acl)
1695     {
1696     debug_printf(
1697             "PDKIM >> Signed DKIM-Signature header, canonicalized >>>>>>>>>>>>>>>>>\n");
1698     pdkim_quoteprint(CUS sig_hdr, strlen(sig_hdr));
1699     debug_printf(
1700             "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
1701     }
1702
1703   /* Finalize header hash */
1704   exim_sha_update(&hhash_ctx, sig_hdr, strlen(sig_hdr));
1705   exim_sha_finish(&hhash_ctx, &hhash);
1706
1707   DEBUG(D_acl)
1708     {
1709     debug_printf("PDKIM [%s] hh computed: ", sig->domain);
1710     pdkim_hexprint(hhash.data, hhash.len);
1711     }
1712
1713   /* Remember headers block for signing (when the library cannot do incremental)  */
1714   if (ctx->mode == PDKIM_MODE_SIGN)
1715     (void) exim_rsa_data_append(&hdata, &hdata_alloc, US sig_hdr);
1716
1717   free(sig_hdr);
1718
1719   /* SIGNING ---------------------------------------------------------------- */
1720   if (ctx->mode == PDKIM_MODE_SIGN)
1721     {
1722     es_ctx sctx;
1723     const uschar * errstr;
1724
1725     /* Import private key */
1726     if ((errstr = exim_rsa_signing_init(US sig->rsa_privkey, &sctx)))
1727       {
1728       DEBUG(D_acl) debug_printf("signing_init: %s\n", errstr);
1729       return PDKIM_ERR_RSA_PRIVKEY;
1730       }
1731
1732     /* Do signing.  With OpenSSL we are signing the hash of headers just
1733     calculated, with GnuTLS we have to sign an entire block of headers
1734     (due to available interfaces) and it recalculates the hash internally. */
1735
1736 #if defined(RSA_OPENSSL) || defined(RSA_GCRYPT)
1737     hdata = hhash;
1738 #endif
1739
1740     if ((errstr = exim_rsa_sign(&sctx, is_sha1, &hdata, &sig->sigdata)))
1741       {
1742       DEBUG(D_acl) debug_printf("signing: %s\n", errstr);
1743       return PDKIM_ERR_RSA_SIGNING;
1744       }
1745
1746     DEBUG(D_acl)
1747       {
1748       debug_printf( "PDKIM [%s] b computed: ", sig->domain);
1749       pdkim_hexprint(sig->sigdata.data, sig->sigdata.len);
1750       }
1751
1752     if (!(sig->signature_header = pdkim_create_header(sig, TRUE)))
1753       return PDKIM_ERR_OOM;
1754
1755     /* We only ever sign with one sig, and we free'd "headernames"
1756     above.  So to keep static-analysers happy, exit the loop explicitly.
1757     Perhaps the code would be more clear if signing and verification
1758     loops were separated? */
1759
1760     break;
1761     }
1762
1763   /* VERIFICATION ----------------------------------------------------------- */
1764   else
1765     {
1766     ev_ctx vctx;
1767     const uschar * errstr;
1768
1769     char *dns_txt_name, *dns_txt_reply;
1770
1771     /* Fetch public key for signing domain, from DNS */
1772
1773     if (!(dns_txt_name  = malloc(PDKIM_DNS_TXT_MAX_NAMELEN)))
1774       return PDKIM_ERR_OOM;
1775
1776     if (!(dns_txt_reply = malloc(PDKIM_DNS_TXT_MAX_RECLEN)))
1777       {
1778       free(dns_txt_name);
1779       return PDKIM_ERR_OOM;
1780       }
1781
1782     memset(dns_txt_reply, 0, PDKIM_DNS_TXT_MAX_RECLEN);
1783     memset(dns_txt_name , 0, PDKIM_DNS_TXT_MAX_NAMELEN);
1784
1785     if (snprintf(dns_txt_name, PDKIM_DNS_TXT_MAX_NAMELEN,
1786                  "%s._domainkey.%s.",
1787                  sig->selector, sig->domain) >= PDKIM_DNS_TXT_MAX_NAMELEN)
1788       {
1789       sig->verify_status =      PDKIM_VERIFY_INVALID;
1790       sig->verify_ext_status =  PDKIM_VERIFY_INVALID_BUFFER_SIZE;
1791       goto NEXT_VERIFY;
1792       }
1793
1794     if (  ctx->dns_txt_callback(dns_txt_name, dns_txt_reply) != PDKIM_OK 
1795        || dns_txt_reply[0] == '\0')
1796       {
1797       sig->verify_status =      PDKIM_VERIFY_INVALID;
1798       sig->verify_ext_status =  PDKIM_VERIFY_INVALID_PUBKEY_UNAVAILABLE;
1799       goto NEXT_VERIFY;
1800       }
1801
1802     DEBUG(D_acl)
1803       {
1804       debug_printf(
1805           "PDKIM >> Parsing public key record >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n"
1806           " Raw record: ");
1807       pdkim_quoteprint(CUS dns_txt_reply, strlen(dns_txt_reply));
1808       }
1809
1810     if (!(sig->pubkey = pdkim_parse_pubkey_record(ctx, dns_txt_reply)))
1811       {
1812       sig->verify_status =      PDKIM_VERIFY_INVALID;
1813       sig->verify_ext_status =  PDKIM_VERIFY_INVALID_PUBKEY_DNSRECORD;
1814
1815       DEBUG(D_acl) debug_printf(
1816           " Error while parsing public key record\n"
1817           "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
1818       goto NEXT_VERIFY;
1819       }
1820
1821     DEBUG(D_acl) debug_printf(
1822           "PDKIM <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
1823
1824     /* Import public key */
1825     if ((errstr = exim_rsa_verify_init(&sig->pubkey->key, &vctx)))
1826       {
1827       DEBUG(D_acl) debug_printf("verify_init: %s\n", errstr);
1828       sig->verify_status =      PDKIM_VERIFY_INVALID;
1829       sig->verify_ext_status =  PDKIM_VERIFY_INVALID_PUBKEY_IMPORT;
1830       goto NEXT_VERIFY;
1831       }
1832
1833     /* Check the signature */
1834     if ((errstr = exim_rsa_verify(&vctx, is_sha1, &hhash, &sig->sigdata)))
1835       {
1836       DEBUG(D_acl) debug_printf("headers verify: %s\n", errstr);
1837       sig->verify_status =      PDKIM_VERIFY_FAIL;
1838       sig->verify_ext_status =  PDKIM_VERIFY_FAIL_MESSAGE;
1839       goto NEXT_VERIFY;
1840       }
1841
1842
1843     /* We have a winner! (if bodydhash was correct earlier) */
1844     if (sig->verify_status == PDKIM_VERIFY_NONE)
1845       sig->verify_status = PDKIM_VERIFY_PASS;
1846
1847 NEXT_VERIFY:
1848
1849     DEBUG(D_acl)
1850       {
1851       debug_printf("PDKIM [%s] signature status: %s",
1852               sig->domain, pdkim_verify_status_str(sig->verify_status));
1853       if (sig->verify_ext_status > 0)
1854         debug_printf(" (%s)\n",
1855                 pdkim_verify_ext_status_str(sig->verify_ext_status));
1856       else
1857         debug_printf("\n");
1858       }
1859
1860     free(dns_txt_name);
1861     free(dns_txt_reply);
1862     }
1863
1864   sig = sig->next;
1865   }
1866
1867 /* If requested, set return pointer to signature(s) */
1868 if (return_signatures)
1869   *return_signatures = ctx->sig;
1870
1871 return PDKIM_OK;
1872 }
1873
1874
1875 /* -------------------------------------------------------------------------- */
1876
1877 DLLEXPORT pdkim_ctx *
1878 pdkim_init_verify(int(*dns_txt_callback)(char *, char *))
1879 {
1880 pdkim_ctx *ctx = malloc(sizeof(pdkim_ctx));
1881
1882 if (!ctx)
1883   return NULL;
1884 memset(ctx, 0, sizeof(pdkim_ctx));
1885
1886 if (!(ctx->linebuf = malloc(PDKIM_MAX_BODY_LINE_LEN)))
1887   {
1888   free(ctx);
1889   return NULL;
1890   }
1891
1892 ctx->mode = PDKIM_MODE_VERIFY;
1893 ctx->dns_txt_callback = dns_txt_callback;
1894
1895 return ctx;
1896 }
1897
1898
1899 /* -------------------------------------------------------------------------- */
1900
1901 DLLEXPORT pdkim_ctx *
1902 pdkim_init_sign(char *domain, char *selector, char *rsa_privkey, int algo)
1903 {
1904 pdkim_ctx *ctx;
1905 pdkim_signature *sig;
1906
1907 if (!domain || !selector || !rsa_privkey)
1908   return NULL;
1909
1910 if (!(ctx = malloc(sizeof(pdkim_ctx))))
1911   return NULL;
1912 memset(ctx, 0, sizeof(pdkim_ctx));
1913
1914 if (!(ctx->linebuf = malloc(PDKIM_MAX_BODY_LINE_LEN)))
1915   {
1916   free(ctx);
1917   return NULL;
1918   }
1919
1920 if (!(sig = malloc(sizeof(pdkim_signature))))
1921   {
1922   free(ctx->linebuf);
1923   free(ctx);
1924   return NULL;
1925   }
1926 memset(sig, 0, sizeof(pdkim_signature));
1927
1928 sig->bodylength = -1;
1929
1930 ctx->mode = PDKIM_MODE_SIGN;
1931 ctx->sig = sig;
1932
1933 sig->domain = strdup(domain);
1934 sig->selector = strdup(selector);
1935 sig->rsa_privkey = strdup(rsa_privkey);
1936 sig->algo = algo;
1937
1938 if (!sig->domain || !sig->selector || !sig->rsa_privkey)
1939   goto BAIL;
1940
1941 exim_sha_init(&sig->body_hash, algo == PDKIM_ALGO_RSA_SHA1);
1942 return ctx;
1943
1944 BAIL:
1945   pdkim_free_ctx(ctx);
1946   return NULL;
1947 }
1948
1949
1950 /* -------------------------------------------------------------------------- */
1951
1952 DLLEXPORT int
1953 pdkim_set_optional(pdkim_ctx *ctx,
1954                        char *sign_headers,
1955                        char *identity,
1956                        int canon_headers,
1957                        int canon_body,
1958                        long bodylength,
1959                        unsigned long created,
1960                        unsigned long expires)
1961 {
1962 pdkim_signature * sig = ctx->sig;
1963
1964 if (identity)
1965   if (!(sig->identity = strdup(identity)))
1966     return PDKIM_ERR_OOM;
1967
1968 if (!(sig->sign_headers = strdup(sign_headers
1969         ? sign_headers : PDKIM_DEFAULT_SIGN_HEADERS)))
1970   return PDKIM_ERR_OOM;
1971
1972 sig->canon_headers = canon_headers;
1973 sig->canon_body = canon_body;
1974 sig->bodylength = bodylength;
1975 sig->created = created;
1976 sig->expires = expires;
1977
1978 return PDKIM_OK;
1979 }
1980
1981
1982 void
1983 pdkim_init(void)
1984 {
1985 exim_rsa_init();
1986 }
1987
1988
1989
1990 #endif  /*DISABLE_DKIM*/