From 9f1239d71bb9fff1a290351aaf42f6fac5753922 Mon Sep 17 00:00:00 2001 From: Ilya Bakulin Date: Wed, 29 Oct 2014 15:17:03 +0100 Subject: net: Support for IPv6, correctly validate IP addresses Since socket.gethostbyname_ex() doesn't support IPv6, switch to using socket.getaddrinfo() Additionally validate IP addresses using inet_pton() instead of simply counting dots in the string. Counting dots fails if the domain name contains 3 dots (www6.mail.bakulin.de) and doesn't work with IPv6. Unfortunately we cannot use ipaddress module because it's available only in Python 3. --- plugins/net.py | 21 +++++++++++---------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/plugins/net.py b/plugins/net.py index 4012e1d..b82c2da 100644 --- a/plugins/net.py +++ b/plugins/net.py @@ -49,22 +49,23 @@ def get_tld(type, jid, nick, text): else: msg = L('What do you want to find?','%s/%s'%(jid,nick)) send_msg(type, jid, nick, msg) +def is_valid_ip(ipstr): + try: socket.inet_pton(socket.AF_INET, ipstr) + except: + try: socket.inet_pton(socket.AF_INET6, ipstr) + except: return False + return True + def get_dns(type, jid, nick, text): - is_ip = None - if text.count('.') == 3: - is_ip = True - for ii in text: - if not nmbrs.count(ii): - is_ip = None - break - if is_ip: + if is_valid_ip(text): try: msg = socket.gethostbyaddr(text)[0] except: msg = L('I can\'t resolve it','%s/%s'%(jid,nick)) else: try: - ans = socket.gethostbyname_ex(text.encode('idna'))[2] + ans = socket.getaddrinfo(text.encode('idna'), None, 0, 0, socket.IPPROTO_TCP) msg = text+' - ' - for an in ans: msg += an + ' | ' + for an in ans: + msg += an[4][0] + ' | ' msg = msg[:-2] except: msg = L('I can\'t resolve it','%s/%s'%(jid,nick)) send_msg(type, jid, nick, msg) -- cgit v1.2.3