Annotate

util/x509.lua @ 9912:601f9781a605

mod_csi_simple: Count buffered items and flush when it reaches configured limit In this mode, stanzas have been serialized to strings in the internal net.server buffer, so it is difficult to count them after the fact.
author Kim Alvefur <zash@zash.se>
date Sun, 24 Mar 2019 18:33:38 +0100
parent 9907:54e36a8677bc
child 10255:8e8d3b3a55da
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;
9907
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
23 local idna_to_unicode = require "util.encodings".idna.to_unicode;
6152
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
24 local base64 = require "util.encodings".base64;
3735
40b54c46a14c util.x509: "certverification" -> "x509".
Waqas Hussain <waqas20@gmail.com>
parents: 3733
diff changeset
25 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
26 local s_format = string.format;
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
27
6777
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
28 local _ENV = nil;
8555
4f0f5b49bb03 vairious: Add annotation when an empty environment is set [luacheck]
Kim Alvefur <zash@zash.se>
parents: 6777
diff changeset
29 -- luacheck: std none
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
6777
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
152 local function verify_identity(host, service, cert)
6708
d2beb98ece29 util.x509: Tell LuaSec we want UTF-8 data
Kim Alvefur <zash@zash.se>
parents: 6153
diff changeset
153 if cert.setencode then
d2beb98ece29 util.x509: Tell LuaSec we want UTF-8 data
Kim Alvefur <zash@zash.se>
parents: 6153
diff changeset
154 cert:setencode("utf8");
d2beb98ece29 util.x509: Tell LuaSec we want UTF-8 data
Kim Alvefur <zash@zash.se>
parents: 6153
diff changeset
155 end
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
156 local ext = cert:extensions()
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
157 if ext[oid_subjectaltname] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
158 local sans = ext[oid_subjectaltname];
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
159
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
160 -- 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
161 -- reference identifier if the presented identifiers include a DNS-ID
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
162 -- SRV-ID, URI-ID, or any application-specific identifier types"
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
163 local had_supported_altnames = false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
164
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
165 if sans[oid_xmppaddr] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
166 had_supported_altnames = true
5845
c48f717c2fd6 util.x509: Only compare identity with oid-on-xmppAddr for XMPP services
Kim Alvefur <zash@zash.se>
parents: 4825
diff changeset
167 if service == "_xmpp-client" or service == "_xmpp-server" then
c48f717c2fd6 util.x509: Only compare identity with oid-on-xmppAddr for XMPP services
Kim Alvefur <zash@zash.se>
parents: 4825
diff changeset
168 if compare_xmppaddr(host, sans[oid_xmppaddr]) then return true end
c48f717c2fd6 util.x509: Only compare identity with oid-on-xmppAddr for XMPP services
Kim Alvefur <zash@zash.se>
parents: 4825
diff changeset
169 end
3651
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
170 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
171
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
172 if sans[oid_dnssrv] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
173 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
174 -- Only check srvNames if the caller specified a service
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
175 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
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 if sans["dNSName"] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
179 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
180 if compare_dnsname(host, sans["dNSName"]) then return true end
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 -- We don't need URIs, but [TLS-CERTS] is clear.
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
184 if sans["uniformResourceIdentifier"] then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
185 had_supported_altnames = true
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
186 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
187
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
188 if had_supported_altnames then return false end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
189 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
190
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
191 -- 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
192 -- a dNSName subjectAltName (wildcards may apply for, and receive,
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
193 -- cat treats)
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
194 --
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
195 -- 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
196 -- which has one and only one Common Name
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
197 local subject = cert:subject()
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
198 local cn = nil
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
199 for i=1,#subject do
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
200 local dn = subject[i]
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
201 if dn["oid"] == oid_commonname then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
202 if cn then
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
203 log("info", "Certificate has multiple common names")
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
204 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
205 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
206
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
207 cn = dn["value"];
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
208 end
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 cn then
4330
520fcb333cba util.x509: Update references to published RFCs
Paul Aurich <paul@darkrain42.org>
parents: 3735
diff changeset
212 -- 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
213 return compare_dnsname(host, { cn })
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
214 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
215
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
216 -- If all else fails, well, why should we be any different?
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
217 return false
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
218 end
337391d34b70 s2s: SASL EXTERNAL
Paul Aurich <paul@darkrain42.org>
parents:
diff changeset
219
9907
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
220 -- TODO Support other SANs
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
221 local function get_identities(cert) --> set of names
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
222 if cert.setencode then
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
223 cert:setencode("utf8");
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
224 end
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
225
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
226 local names = {};
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
227
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
228 local ext = cert:extensions();
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
229 local sans = ext[oid_subjectaltname];
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
230 if sans and sans["dNSName"] then
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
231 for i = 1, #sans["dNSName"] do
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
232 names[ idna_to_unicode(sans["dNSName"][i]) ] = true;
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
233 end
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
234 end
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
235
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
236 local subject = cert:subject();
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
237 for i = 1, #subject do
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
238 local dn = subject[i];
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
239 if dn.oid == oid_commonname and nameprep(dn.value) then
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
240 names[dn.value] = true;
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
241 end
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
242 end
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
243 return names;
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
244 end
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
245
6152
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
246 local pat = "%-%-%-%-%-BEGIN ([A-Z ]+)%-%-%-%-%-\r?\n"..
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
247 "([0-9A-Za-z+/=\r\n]*)\r?\n%-%-%-%-%-END %1%-%-%-%-%-";
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
248
6777
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
249 local function pem2der(pem)
6152
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
250 local typ, data = pem:match(pat);
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
251 if typ and data then
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
252 return base64.decode(data), typ;
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
253 end
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
254 end
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
255
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
256 local wrap = ('.'):rep(64);
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
257 local envelope = "-----BEGIN %s-----\n%s\n-----END %s-----\n"
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
258
6777
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
259 local function der2pem(data, typ)
6152
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
260 typ = typ and typ:upper() or "CERTIFICATE";
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
261 data = base64.encode(data);
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
262 return s_format(envelope, typ, data:gsub(wrap, '%0\n', (#data-1)/64), typ);
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
263 end
fbab74c28e31 util.x509: And functions for converting between DER and PEM
Kim Alvefur <zash@zash.se>
parents: 5845
diff changeset
264
6777
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
265 return {
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
266 verify_identity = verify_identity;
9907
54e36a8677bc util.x509: Add function that extracts usable names from a certificate
Kim Alvefur <zash@zash.se>
parents: 8555
diff changeset
267 get_identities = get_identities;
6777
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
268 pem2der = pem2der;
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
269 der2pem = der2pem;
5de6b93d0190 util.*: Remove use of module() function, make all module functions local and return them in a table at the end
Kim Alvefur <zash@zash.se>
parents: 6708
diff changeset
270 };