Software /
code /
prosody
Comparison
plugins/mod_s2s/s2sout.lib.lua @ 6682:63f5870f9afe
mod_s2s/s2sout: Use the local address assigned to UDP sockets instead of util.net to enumerate possible source addresses
author | Kim Alvefur <zash@zash.se> |
---|---|
date | Wed, 13 May 2015 21:47:39 +0200 |
parent | 6680:ae34b12c4335 |
child | 6685:3f05b255937f |
child | 7092:bee63de49663 |
comparison
equal
deleted
inserted
replaced
6681:0217a04722c7 | 6682:63f5870f9afe |
---|---|
16 local rfc6724_dest = require "util.rfc6724".destination; | 16 local rfc6724_dest = require "util.rfc6724".destination; |
17 local socket = require "socket"; | 17 local socket = require "socket"; |
18 local adns = require "net.adns"; | 18 local adns = require "net.adns"; |
19 local dns = require "net.dns"; | 19 local dns = require "net.dns"; |
20 local t_insert, t_sort, ipairs = table.insert, table.sort, ipairs; | 20 local t_insert, t_sort, ipairs = table.insert, table.sort, ipairs; |
21 local local_addresses = require "util.net".local_addresses; | |
22 | 21 |
23 local s2s_destroy_session = require "core.s2smanager".destroy_session; | 22 local s2s_destroy_session = require "core.s2smanager".destroy_session; |
24 | 23 |
25 local log = module._log; | 24 local log = module._log; |
26 | 25 |
27 local sources = {}; | 26 local anysource = { IPv4 = "0.0.0.0", IPv6 = "::" }; |
27 local function get_sources(addrs) | |
28 local sources = {}; | |
29 for _, IP in ipairs(addrs) do | |
30 local sock; | |
31 if IP.proto == "IPv4" then | |
32 sock = socket.udp(); | |
33 elseif IP.proto == "IPv6" then | |
34 sock = socket.udp6(); | |
35 end | |
36 sock:setpeername(IP.addr, 9); | |
37 local localaddr = sock:getsockname() or anysource[IP.proto]; | |
38 sock:close(); | |
39 if not sources[localaddr] then | |
40 sources[localaddr] = true; | |
41 t_insert(sources, new_ip(localaddr, IP.proto)); | |
42 end | |
43 end | |
44 return sources; | |
45 end | |
28 local has_ipv4, has_ipv6; | 46 local has_ipv4, has_ipv6; |
29 | 47 |
30 local dns_timeout = module:get_option_number("dns_timeout", 15); | 48 local dns_timeout = module:get_option_number("dns_timeout", 15); |
31 dns.settimeout(dns_timeout); | 49 dns.settimeout(dns_timeout); |
32 | 50 |
175 end | 193 end |
176 end | 194 end |
177 | 195 |
178 if have_other_result then | 196 if have_other_result then |
179 if #IPs > 0 then | 197 if #IPs > 0 then |
180 rfc6724_dest(host_session.ip_hosts, sources); | 198 rfc6724_dest(host_session.ip_hosts, get_sources(host_session.ip_hosts)); |
181 for i = 1, #IPs do | 199 for i = 1, #IPs do |
182 IPs[i] = {ip = IPs[i], port = connect_port}; | 200 IPs[i] = {ip = IPs[i], port = connect_port}; |
183 end | 201 end |
184 host_session.ip_choice = 0; | 202 host_session.ip_choice = 0; |
185 s2sout.try_next_ip(host_session); | 203 s2sout.try_next_ip(host_session); |
211 end | 229 end |
212 end | 230 end |
213 | 231 |
214 if have_other_result then | 232 if have_other_result then |
215 if #IPs > 0 then | 233 if #IPs > 0 then |
216 rfc6724_dest(host_session.ip_hosts, sources); | 234 rfc6724_dest(host_session.ip_hosts, get_sources(host_session.ip_hosts)); |
217 for i = 1, #IPs do | 235 for i = 1, #IPs do |
218 IPs[i] = {ip = IPs[i], port = connect_port}; | 236 IPs[i] = {ip = IPs[i], port = connect_port}; |
219 end | 237 end |
220 host_session.ip_choice = 0; | 238 host_session.ip_choice = 0; |
221 s2sout.try_next_ip(host_session); | 239 s2sout.try_next_ip(host_session); |
313 if not s2s_sources then | 331 if not s2s_sources then |
314 module:log("warn", "s2s not listening on any ports, outgoing connections may fail"); | 332 module:log("warn", "s2s not listening on any ports, outgoing connections may fail"); |
315 return; | 333 return; |
316 end | 334 end |
317 for source, _ in pairs(s2s_sources) do | 335 for source, _ in pairs(s2s_sources) do |
318 if source == "*" or source == "0.0.0.0" then | 336 if source:find(":") then |
319 for _, addr in ipairs(local_addresses("ipv4", true)) do | 337 has_ipv6 = true; |
320 sources[#sources + 1] = new_ip(addr, "IPv4"); | |
321 end | |
322 elseif source == "::" then | |
323 for _, addr in ipairs(local_addresses("ipv6", true)) do | |
324 sources[#sources + 1] = new_ip(addr, "IPv6"); | |
325 end | |
326 else | 338 else |
327 sources[#sources + 1] = new_ip(source, (source:find(":") and "IPv6") or "IPv4"); | |
328 end | |
329 end | |
330 for i = 1,#sources do | |
331 if sources[i].proto == "IPv6" then | |
332 has_ipv6 = true; | |
333 elseif sources[i].proto == "IPv4" then | |
334 has_ipv4 = true; | 339 has_ipv4 = true; |
335 end | 340 end |
336 end | 341 end |
337 if not (has_ipv4 or has_ipv6) then | |
338 module:log("warn", "No local IPv4 or IPv6 addresses detected, outgoing connections may fail"); | |
339 end | |
340 end); | 342 end); |
341 | 343 |
342 return s2sout; | 344 return s2sout; |