Annotate

util/x509.lua @ 5915:e6fed1d80116

Back out 1b0ac7950129, as SSLv3 appears to still be in moderate use on the network. Also, although obsolete, SSLv3 isn't documented to have any weaknesses that TLS 1.0 (the most common version used today) doesn't also have. Get your act together clients!
author Matthew Wild <mwild1@gmail.com>
date Tue, 12 Nov 2013 02:13:01 +0000
parent 4825:5fdc36bd866c
child 5845:c48f717c2fd6
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
1 -- Prosody IM
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
2 -- Copyright (C) 2010 Matthew Wild
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
3 -- Copyright (C) 2010 Paul Aurich
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
4 --
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
5 -- This project is MIT/X11 licensed. Please see the
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
6 -- COPYING file in the source package for more information.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
7 --
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
8
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
9 -- TODO: I feel a fair amount of this logic should be integrated into Luasec,
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
10 -- so that everyone isn't re-inventing the wheel. Dependencies on
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
11 -- IDN libraries complicate that.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
12
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
13
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
14 -- [TLS-CERTS] - http://tools.ietf.org/html/rfc6125
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
15 -- [XMPP-CORE] - http://tools.ietf.org/html/rfc6120
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
16 -- [SRV-ID] - http://tools.ietf.org/html/rfc4985
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
17 -- [IDNA] - http://tools.ietf.org/html/rfc5890
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
18 -- [LDAP] - http://tools.ietf.org/html/rfc4519
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
19 -- [PKIX] - http://tools.ietf.org/html/rfc5280
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
20
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
21 local nameprep = require "util.encodings".stringprep.nameprep;
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
22 local idna_to_ascii = require "util.encodings".idna.to_ascii;
3735
40b54c46a14c util.x509: "certverification" -> "x509".
Waqas Hussain <waqas20@gmail.com>
parents: 3733
diff changeset
23 local log = require "util.logger".init("x509");
4486
f04db5e7e90d user.x509: Add some utility functions for generating OpenSSL configs
Kim Alvefur <zash@zash.se>
parents: 4330
diff changeset
24 local pairs, ipairs = pairs, ipairs;
f04db5e7e90d user.x509: Add some utility functions for generating OpenSSL configs
Kim Alvefur <zash@zash.se>
parents: 4330
diff changeset
25 local s_format = string.format;
f04db5e7e90d user.x509: Add some utility functions for generating OpenSSL configs
Kim Alvefur <zash@zash.se>
parents: 4330
diff changeset
26 local t_insert = table.insert;
f04db5e7e90d user.x509: Add some utility functions for generating OpenSSL configs
Kim Alvefur <zash@zash.se>
parents: 4330
diff changeset
27 local t_concat = table.concat;
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
28
3735
40b54c46a14c util.x509: "certverification" -> "x509".
Waqas Hussain <waqas20@gmail.com>
parents: 3733
diff changeset
29 module "x509"
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
30
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
31 local oid_commonname = "2.5.4.3"; -- [LDAP] 2.3
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
32 local oid_subjectaltname = "2.5.29.17"; -- [PKIX] 4.2.1.6
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
33 local oid_xmppaddr = "1.3.6.1.5.5.7.8.5"; -- [XMPP-CORE]
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
34 local oid_dnssrv = "1.3.6.1.5.5.7.8.7"; -- [SRV-ID]
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
35
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
36 -- Compare a hostname (possibly international) with asserted names
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
37 -- extracted from a certificate.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
38 -- This function follows the rules laid out in
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
39 -- sections 6.4.1 and 6.4.2 of [TLS-CERTS]
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
40 --
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
41 -- A wildcard ("*") all by itself is allowed only as the left-most label
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
42 local function compare_dnsname(host, asserted_names)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
43 -- TODO: Sufficient normalization? Review relevant specs.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
44 local norm_host = idna_to_ascii(host)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
45 if norm_host == nil then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
46 log("info", "Host %s failed IDNA ToASCII operation", host)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
47 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
48 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
49
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
50 norm_host = norm_host:lower()
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
51
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
52 local host_chopped = norm_host:gsub("^[^.]+%.", "") -- everything after the first label
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
53
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
54 for i=1,#asserted_names do
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
55 local name = asserted_names[i]
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
56 if norm_host == name:lower() then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
57 log("debug", "Cert dNSName %s matched hostname", name);
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
58 return true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
59 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
60
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
61 -- Allow the left most label to be a "*"
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
62 if name:match("^%*%.") then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
63 local rest_name = name:gsub("^[^.]+%.", "")
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
64 if host_chopped == rest_name:lower() then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
65 log("debug", "Cert dNSName %s matched hostname", name);
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
66 return true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
67 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
68 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
69 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
70
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
71 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
72 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
73
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
74 -- Compare an XMPP domain name with the asserted id-on-xmppAddr
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
75 -- identities extracted from a certificate. Both are UTF8 strings.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
76 --
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
77 -- Per [XMPP-CORE], matches against asserted identities don't include
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
78 -- wildcards, so we just do a normalize on both and then a string comparison
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
79 --
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
80 -- TODO: Support for full JIDs?
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
81 local function compare_xmppaddr(host, asserted_names)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
82 local norm_host = nameprep(host)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
83
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
84 for i=1,#asserted_names do
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
85 local name = asserted_names[i]
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
86
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
87 -- We only want to match against bare domains right now, not
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
88 -- those crazy full-er JIDs.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
89 if name:match("[@/]") then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
90 log("debug", "Ignoring xmppAddr %s because it's not a bare domain", name)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
91 else
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
92 local norm_name = nameprep(name)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
93 if norm_name == nil then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
94 log("info", "Ignoring xmppAddr %s, failed nameprep!", name)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
95 else
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
96 if norm_host == norm_name then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
97 log("debug", "Cert xmppAddr %s matched hostname", name)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
98 return true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
99 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
100 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
101 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
102 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
103
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
104 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
105 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
106
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
107 -- Compare a host + service against the asserted id-on-dnsSRV (SRV-ID)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
108 -- identities extracted from a certificate.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
109 --
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
110 -- Per [SRV-ID], the asserted identities will be encoded in ASCII via ToASCII.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
111 -- Comparison is done case-insensitively, and a wildcard ("*") all by itself
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
112 -- is allowed only as the left-most non-service label.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
113 local function compare_srvname(host, service, asserted_names)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
114 local norm_host = idna_to_ascii(host)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
115 if norm_host == nil then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
116 log("info", "Host %s failed IDNA ToASCII operation", host);
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
117 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
118 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
119
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
120 -- Service names start with a "_"
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
121 if service:match("^_") == nil then service = "_"..service end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
122
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
123 norm_host = norm_host:lower();
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
124 local host_chopped = norm_host:gsub("^[^.]+%.", "") -- everything after the first label
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
125
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
126 for i=1,#asserted_names do
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
127 local asserted_service, name = asserted_names[i]:match("^(_[^.]+)%.(.*)");
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
128 if service == asserted_service then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
129 if norm_host == name:lower() then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
130 log("debug", "Cert SRVName %s matched hostname", name);
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
131 return true;
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
132 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
133
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
134 -- Allow the left most label to be a "*"
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
135 if name:match("^%*%.") then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
136 local rest_name = name:gsub("^[^.]+%.", "")
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
137 if host_chopped == rest_name:lower() then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
138 log("debug", "Cert SRVName %s matched hostname", name)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
139 return true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
140 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
141 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
142 if norm_host == name:lower() then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
143 log("debug", "Cert SRVName %s matched hostname", name);
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
144 return true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
145 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
146 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
147 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
148
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
149 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
150 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
151
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
152 function verify_identity(host, service, cert)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
153 local ext = cert:extensions()
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
154 if ext[oid_subjectaltname] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
155 local sans = ext[oid_subjectaltname];
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
156
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
157 -- Per [TLS-CERTS] 6.3, 6.4.4, "a client MUST NOT seek a match for a
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
158 -- reference identifier if the presented identifiers include a DNS-ID
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
159 -- SRV-ID, URI-ID, or any application-specific identifier types"
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
160 local had_supported_altnames = false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
161
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
162 if sans[oid_xmppaddr] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
163 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
164 if compare_xmppaddr(host, sans[oid_xmppaddr]) then return true end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
165 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
166
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
167 if sans[oid_dnssrv] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
168 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
169 -- Only check srvNames if the caller specified a service
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
170 if service and compare_srvname(host, service, sans[oid_dnssrv]) then return true end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
171 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
172
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
173 if sans["dNSName"] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
174 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
175 if compare_dnsname(host, sans["dNSName"]) then return true end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
176 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
177
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
178 -- We don't need URIs, but [TLS-CERTS] is clear.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
179 if sans["uniformResourceIdentifier"] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
180 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
181 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
182
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
183 if had_supported_altnames then return false end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
184 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
185
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
186 -- Extract a common name from the certificate, and check it as if it were
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
187 -- a dNSName subjectAltName (wildcards may apply for, and receive,
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
188 -- cat treats)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
189 --
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
190 -- Per [TLS-CERTS] 1.8, a CN-ID is the Common Name from a cert subject
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
191 -- which has one and only one Common Name
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
192 local subject = cert:subject()
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
193 local cn = nil
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
194 for i=1,#subject do
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
195 local dn = subject[i]
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
196 if dn["oid"] == oid_commonname then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
197 if cn then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
198 log("info", "Certificate has multiple common names")
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
199 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
200 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
201
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
202 cn = dn["value"];
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
203 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
204 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
205
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
206 if cn then
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
207 -- Per [TLS-CERTS] 6.4.4, follow the comparison rules for dNSName SANs.
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
208 return compare_dnsname(host, { cn })
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
209 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
210
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
211 -- If all else fails, well, why should we be any different?
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
212 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
213 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
214
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
215 return _M;