git://git.exim.org
/
exim.git
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
DKIM: use string-allocate facilities for DNS lookup
[exim.git]
/
src
/
src
/
pdkim
/
pdkim.c
diff --git
a/src/src/pdkim/pdkim.c
b/src/src/pdkim/pdkim.c
index 1420b1a795d32944f624bfecd2277f0a24033bc1..679607dbd46d4abcf174023227ff8153bd4dd3a7 100644
(file)
--- a/
src/src/pdkim/pdkim.c
+++ b/
src/src/pdkim/pdkim.c
@@
-224,13
+224,13
@@
static void
pdkim_strtrim(gstring * str)
{
uschar * p = str->s;
pdkim_strtrim(gstring * str)
{
uschar * p = str->s;
-uschar * q
= p + str->ptr
;
+uschar * q;
while (*p == '\t' || *p == ' ') /* dump the leading whitespace */
{ str->size--; str->ptr--; str->s++; }
while ( str->ptr > 0
while (*p == '\t' || *p == ' ') /* dump the leading whitespace */
{ str->size--; str->ptr--; str->s++; }
while ( str->ptr > 0
- && (
q = str->s + str->ptr - 1), *q == '\t' || *q == ' '
+ && (
(q = str->s + str->ptr - 1), (*q == '\t' || *q == ' '))
)
str->ptr--; /* dump trailing whitespace */
)
str->ptr--; /* dump trailing whitespace */
@@
-250,16
+250,19
@@
pdkim_free_ctx(pdkim_ctx *ctx)
/* -------------------------------------------------------------------------- */
/* Matches the name of the passed raw "header" against
the passed colon-separated "tick", and invalidates
/* -------------------------------------------------------------------------- */
/* Matches the name of the passed raw "header" against
the passed colon-separated "tick", and invalidates
- the entry in tick. Returns OK or fail-code */
-/*XXX might be safer done using a pdkim_stringlist for "tick" */
+ the entry in tick. Entries can be prefixed for multi- or over-signing,
+ in which case do not invalidate.
+
+ Returns OK for a match, or fail-code
+*/
static int
header_name_match(const uschar * header, uschar * tick)
{
static int
header_name_match(const uschar * header, uschar * tick)
{
-
uschar * hname
;
-
uschar * lcopy
;
-
uschar * p
;
-uschar *
q
;
+
const uschar * ticklist = tick
;
+
int sep = ':'
;
+
BOOL multisign
;
+uschar *
hname, * p, * ele
;
uschar * hcolon = Ustrchr(header, ':'); /* Get header name */
if (!hcolon)
uschar * hcolon = Ustrchr(header, ':'); /* Get header name */
if (!hcolon)
@@
-268,27
+271,22
@@
if (!hcolon)
/* if we had strncmpic() we wouldn't need this copy */
hname = string_copyn(header, hcolon-header);
/* if we had strncmpic() we wouldn't need this copy */
hname = string_copyn(header, hcolon-header);
-/* Copy tick-off list locally, so we can punch zeroes into it */
-p = lcopy = string_copy(tick);
-
-for (q = Ustrchr(p, ':'); q; q = Ustrchr(p, ':'))
+while (p = US ticklist, ele = string_nextinlist(&ticklist, &sep, NULL, 0))
{
{
- *q = '\0';
- if (strcmpic(p, hname) == 0)
- goto found;
-
- p = q+1;
+ switch (*ele)
+ {
+ case '=': case '+': multisign = TRUE; ele++; break;
+ default: multisign = FALSE; break;
}
}
-if (strcmpic(p, hname) == 0)
- goto found;
-
+ if (strcmpic(ele, hname) == 0)
+ {
+ if (!multisign)
+ *p = '_'; /* Invalidate this header name instance in tick-off list */
+ return PDKIM_OK;
+ }
+ }
return PDKIM_FAIL;
return PDKIM_FAIL;
-
-found:
- /* Invalidate header name instance in tick-off list */
- tick[p-lcopy] = '_';
- return PDKIM_OK;
}
}
@@
-492,7
+490,12
@@
for (p = raw_hdr; ; p++)
if (c == ';' || c == '\0')
{
if (c == ';' || c == '\0')
{
- if (cur_tag && cur_val)
+ /* We must have both tag and value, and tags must be one char except
+ for the possibility of "bh". */
+
+ if ( cur_tag && cur_val
+ && (cur_tag->ptr == 1 || *cur_tag->s == 'b')
+ )
{
(void) string_from_gstring(cur_val);
pdkim_strtrim(cur_val);
{
(void) string_from_gstring(cur_val);
pdkim_strtrim(cur_val);
@@
-502,8
+505,14
@@
for (p = raw_hdr; ; p++)
switch (*cur_tag->s)
{
case 'b':
switch (*cur_tag->s)
{
case 'b':
- pdkim_decode_base64(cur_val->s,
- cur_tag->s[1] == 'h' ? &sig->bodyhash : &sig->sighash);
+ switch (cur_tag->s[1])
+ {
+ case '\0': pdkim_decode_base64(cur_val->s, &sig->sighash); break;
+ case 'h': if (cur_tag->ptr == 2)
+ pdkim_decode_base64(cur_val->s, &sig->bodyhash);
+ break;
+ default: break;
+ }
break;
case 'v':
/* We only support version 1, and that is currently the
break;
case 'v':
/* We only support version 1, and that is currently the
@@
-645,7
+654,8
@@
while ((ele = string_nextinlist(&raw_record, &sep, NULL, 0)))
}
/* Set fallback defaults */
}
/* Set fallback defaults */
-if (!pub->version ) pub->version = string_copy(PDKIM_PUB_RECORD_VERSION);
+if (!pub->version)
+ pub->version = string_copy(PDKIM_PUB_RECORD_VERSION);
else if (Ustrcmp(pub->version, PDKIM_PUB_RECORD_VERSION) != 0)
{
DEBUG(D_acl) debug_printf(" Bad v= field\n");
else if (Ustrcmp(pub->version, PDKIM_PUB_RECORD_VERSION) != 0)
{
DEBUG(D_acl) debug_printf(" Bad v= field\n");
@@
-1296,10
+1306,7
@@
pdkim_pubkey * p;
dns_txt_name = string_sprintf("%s._domainkey.%s.", sig->selector, sig->domain);
dns_txt_name = string_sprintf("%s._domainkey.%s.", sig->selector, sig->domain);
-dns_txt_reply = store_get(PDKIM_DNS_TXT_MAX_RECLEN);
-memset(dns_txt_reply, 0, PDKIM_DNS_TXT_MAX_RECLEN);
-
-if ( ctx->dns_txt_callback(CS dns_txt_name, CS dns_txt_reply) != PDKIM_OK
+if ( !(dns_txt_reply = ctx->dns_txt_callback(CS dns_txt_name))
|| dns_txt_reply[0] == '\0'
)
{
|| dns_txt_reply[0] == '\0'
)
{
@@
-1445,11
+1452,17
@@
for (sig = ctx->sig; sig; sig = sig->next)
}
}
}
}
- /* Any headers we wanted to sign but were not present must also be listed */
+ /* Any headers we wanted to sign but were not present must also be listed.
+ Ignore elements that have been ticked-off or are marked as never-oversign. */
+
l = sig->sign_headers;
while((s = string_nextinlist(&l, &sep, NULL, 0)))
l = sig->sign_headers;
while((s = string_nextinlist(&l, &sep, NULL, 0)))
- if (*s != '_')
+ {
+ if (*s == '+') /* skip oversigning marker */
+ s++;
+ if (*s != '_' && *s != '=')
g = string_append_listele(g, ':', s);
g = string_append_listele(g, ':', s);
+ }
sig->headernames = string_from_gstring(g);
/* Create signature header with b= omitted */
sig->headernames = string_from_gstring(g);
/* Create signature header with b= omitted */
@@
-1697,7
+1710,7
@@
return PDKIM_OK;
/* -------------------------------------------------------------------------- */
DLLEXPORT pdkim_ctx *
/* -------------------------------------------------------------------------- */
DLLEXPORT pdkim_ctx *
-pdkim_init_verify(
int(*dns_txt_callback)(char *,
char *), BOOL dot_stuffing)
+pdkim_init_verify(
uschar * (*dns_txt_callback)(
char *), BOOL dot_stuffing)
{
pdkim_ctx * ctx;
{
pdkim_ctx * ctx;
@@
-1801,7
+1814,7
@@
return;
void
pdkim_init_context(pdkim_ctx * ctx, BOOL dot_stuffed,
void
pdkim_init_context(pdkim_ctx * ctx, BOOL dot_stuffed,
-
int(*dns_txt_callback)(char *,
char *))
+
uschar * (*dns_txt_callback)(
char *))
{
memset(ctx, 0, sizeof(pdkim_ctx));
ctx->flags = dot_stuffed ? PDKIM_MODE_SIGN | PDKIM_DOT_TERM : PDKIM_MODE_SIGN;
{
memset(ctx, 0, sizeof(pdkim_ctx));
ctx->flags = dot_stuffed ? PDKIM_MODE_SIGN | PDKIM_DOT_TERM : PDKIM_MODE_SIGN;