summaryrefslogtreecommitdiff
path: root/contrib/tor-resolve.py
diff options
context:
space:
mode:
authorNick Mathewson <nickm@torproject.org>2006-09-22 00:43:55 +0000
committerNick Mathewson <nickm@torproject.org>2006-09-22 00:43:55 +0000
commit213658f117f88eaeb21ffd61451155f451f67604 (patch)
tree31f4c5d408f6372cc08d1be2731f4c2ab10eced9 /contrib/tor-resolve.py
parent9bc8d69dfc4ddda5a9c8478b1f1e04490845ded0 (diff)
downloadtor-213658f117f88eaeb21ffd61451155f451f67604.tar.gz
tor-213658f117f88eaeb21ffd61451155f451f67604.zip
r8894@Kushana: nickm | 2006-09-21 18:30:42 -0400
Specify and implement SOCKS5 interface for reverse hostname lookup. svn:r8451
Diffstat (limited to 'contrib/tor-resolve.py')
-rwxr-xr-xcontrib/tor-resolve.py65
1 files changed, 44 insertions, 21 deletions
diff --git a/contrib/tor-resolve.py b/contrib/tor-resolve.py
index dd44255bc1..3557c2aa96 100755
--- a/contrib/tor-resolve.py
+++ b/contrib/tor-resolve.py
@@ -32,15 +32,14 @@ def socks5Hello():
def socks5ParseHello(response):
if response != "\x05\x00":
raise ValueError("Bizarre socks5 response")
-def socks5ResolveRequest(hostname):
+def socks5ResolveRequest(hostname, atype=0x03, command=0xF0):
version = 5
- command = 0xF0
rsv = 0
port = 0
- atype = 0x03
reqheader = struct.pack("!BBBBB",version, command, rsv, atype, len(hostname))
portstr = struct.pack("!H",port)
return "%s%s%s"%(reqheader,hostname,portstr)
+
def socks5ParseResponse(r):
if len(r)<8:
return None
@@ -49,18 +48,27 @@ def socks5ParseResponse(r):
assert rsv==0
if reply != 0x00:
return "ERROR",reply
- assert atype in (0x01,0x04)
- expected_len = 4 + ({1:4,4:16}[atype]) + 2
- if len(r) < expected_len:
- return None
- elif len(r) > expected_len:
- raise ValueError("Overlong socks5 reply!")
- addr = r[4:-2]
- if atype == 0x01:
- return "%d.%d.%d.%d"%tuple(map(ord,addr))
+ assert atype in (0x01,0x03,0x04)
+ if atype != 0x03:
+ expected_len = 4 + ({1:4,4:16}[atype]) + 2
+ if len(r) < expected_len:
+ return None
+ elif len(r) > expected_len:
+ raise ValueError("Overlong socks5 reply!")
+ addr = r[4:-2]
+ if atype == 0x01:
+ return "%d.%d.%d.%d"%tuple(map(ord,addr))
+ else:
+ # not really the right way to format IPv6
+ return "IPv6: %s"%(":".join([hex(ord(c)) for c in addr]))
else:
- # not really the right way to format IPv6
- return "IPv6: %s"%(":".join([hex(ord(c)) for c in addr]))
+ nul = r.index('\0',4)
+ return r[4:nul]
+
+def socks5ResolvePTRRequest(hostname):
+ return socks5ResolveRequest(socket.inet_aton(hostname),
+ atype=1, command = 0xF1)
+
def parseHostAndPort(h):
host, port = "localhost", 9050
@@ -80,14 +88,18 @@ def parseHostAndPort(h):
return host, port
-def resolve(hostname, sockshost, socksport, socksver=4):
+def resolve(hostname, sockshost, socksport, socksver=4, reverse=0):
assert socksver in (4,5)
if socksver == 4:
fmt = socks4AResolveRequest
parse = socks4AParseResponse
- else:
+ elif not reverse:
fmt = socks5ResolveRequest
parse = socks5ParseResponse
+ else:
+ fmt = socks5ResolvePTRRequest
+ parse = socks5ParseResponse
+
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((sockshost,socksport))
if socksver == 5:
@@ -114,14 +126,25 @@ if __name__ == '__main__':
print "Syntax: resolve.py [-4|-5] hostname [sockshost:socksport]"
sys.exit(0)
socksver = 4
- if sys.argv[1] in ("-4", "-5"):
- socksver = int(sys.argv[1][1])
- del sys.argv[1]
- if len(sys.argv) == 4:
+ reverse = 0
+ while sys.argv[1] == '-':
+ if sys.argv[1] in ("-4", "-5"):
+ socksver = int(sys.argv[1][1])
+ del sys.argv[1]
+ elif sys.argv[1] == '-x':
+ reverse = 1
+ del sys.argv[1]
+ elif sys.argv[1] == '--':
+ break
+
+ if len(sys.argv) >= 4:
print "Syntax: resolve.py [-4|-5] hostname [sockshost:socksport]"
sys.exit(0)
if len(sys.argv) == 3:
sh,sp = parseHostAndPort(sys.argv[2])
else:
sh,sp = parseHostAndPort("")
- resolve(sys.argv[1], sh, sp, socksver)
+
+ if reverse and socksver == 4:
+ socksver = 5
+ resolve(sys.argv[1], sh, sp, socksver, reverse)