Last active
August 29, 2015 14:24
-
-
Save simonster/f2cc51584ae5f8709e70 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
if (platform == "win") { | |
libc = ctypes.open("Ws2_32.dll"); | |
var dnsapi = ctypes.open("Dnsapi.dll"); | |
var DNS_RECORD = new ctypes.StructType("DNS_RECORD"); | |
DNS_RECORD.define([{"pNext":DNS_RECORD.ptr}, {"pName":ctypes.char.ptr}, {"wType":ctypes.unsigned_short}, | |
{"wDataLength":ctypes.unsigned_short}, {"DW":ctypes.unsigned_long}, {"dwTtl":ctypes.unsigned_long}, | |
{"dwReserved":ctypes.unsigned_long}, {"pNameHost":ctypes.char.ptr}]); | |
var DnsQuery = dnsapi.declare("DnsQuery_A", ctypes.winapi_abi, ctypes.int, ctypes.char.ptr, ctypes.unsigned_short, | |
ctypes.unsigned_long, ctypes.voidptr_t, DNS_RECORD.ptr, ctypes.voidptr_t); | |
var DnsRecordListFree = dnsapi.declare("DnsRecordListFree", ctypes.winapi_abi, ctypes.void_t, DNS_RECORD.ptr, | |
ctypes.int); | |
var record = new DNS_RECORD(); | |
var getIPForLookup = function(ip) { | |
if (ip.indexOf(".") != -1) { | |
// IPv4 | |
x = ip.split(".").reverse().join(".")+".in-addr.arpa"; | |
} else { | |
if (ip.indexOf("%") != -1) ip = ip.substr(0, ip.indexOf("%")); | |
// IPv6 | |
var parts = ip.split(":"); | |
x = "ip6.arpa" | |
for (var i = 0; i < parts.length; i++) { | |
var part = parts[i]; | |
for (var j = 0; j < (part.length == 0 ? 4*(9-parts.length) : 4-part.length); j++) x = "0." + x; | |
for (var j = 0; j < part.length; j++) x = part[j] + "." + x; | |
} | |
} | |
return x; | |
} | |
var reverseLookup = function(ip) { | |
var status = DnsQuery(getIPForLookup(ip), 12 /*DNS_TYPE_PTR*/, 32 /*DNS_QUERY_NO_LOCAL_NAME*/, null, record.address(), null); | |
if (status != 0 || record.pNext.isNull()) return null; | |
var retval = record.pNext.contents.pNameHost.readString(); | |
DnsRecordListFree(record.pNext, 1); | |
return retval; | |
}; | |
} else if (platform == "mac") { | |
libc = ctypes.open("libc.dylib"); | |
} else { | |
var possibleLibcs = [ | |
"libc.so.6", | |
"libc.so.6.1", | |
"libc.so" | |
]; | |
for(var i = 0; i < possibleLibcs.length; i++) { | |
try { | |
libc = ctypes.open(possibleLibcs[i]); | |
break; | |
} catch(e) {} | |
} | |
} | |
var sockaddr = new ctypes.StructType("sockaddr"); | |
var addrinfo = new ctypes.StructType("arrinfo"); | |
addrinfo.define([{"ai_flags":ctypes.int}, {"ai_family":ctypes.int}, {"ai_socktype":ctypes.int}, | |
{"ai_protocol":ctypes.int}, {"ai_addrlen":ctypes.int}, {"ai_canonname":ctypes.char.ptr}, | |
{"ai_addr":sockaddr.ptr}, {"ai_next":addrinfo.ptr}]); | |
var gethostname = libc.declare("gethostname", ctypes.default_abi, ctypes.int, ctypes.char.ptr, ctypes.size_t); | |
var getaddrinfo = libc.declare("getaddrinfo", ctypes.default_abi, ctypes.int, ctypes.char.ptr, ctypes.char.ptr, | |
addrinfo.ptr, addrinfo.ptr.ptr); | |
var freeaddrinfo = libc.declare("freeaddrinfo", ctypes.default_abi, ctypes.void_t, addrinfo.ptr); | |
var getnameinfo = libc.declare("getnameinfo", ctypes.default_abi, ctypes.int, sockaddr.ptr, ctypes.int, | |
ctypes.char.ptr, ctypes.int, ctypes.char.ptr, ctypes.int, ctypes.int); | |
var buf = new new ctypes.ArrayType(ctypes.char, 1025); | |
var status = gethostname(buf, 1025); | |
if (status != 0) throw new Error("could not get hostname: "+status); | |
var hosts = []; | |
var hints = new addrinfo(); | |
if (platform != "win") hints.ai_flags = 2; | |
var out = new addrinfo.ptr(); | |
status = getaddrinfo(buf, null, hints.address(), out.address()); | |
if (status != 0) throw new Error("could not get addrinfo: "+status); | |
var rec = out; | |
try { | |
if (platform == "win") { | |
while (!rec.isNull()) { | |
status = getnameinfo(rec.contents.ai_addr, rec.contents.ai_addrlen, buf, 1025, null, 0, 2); | |
if (status != 0) throw new Error("could not get IP address: "+status); | |
var host = reverseLookup(buf.readString()); | |
if (host) hosts.push(host); | |
rec = rec.contents.ai_next; | |
} | |
} else { | |
// Not perfect, but need to figure out the right API to do a | |
// proper query | |
while (!rec.isNull()) { | |
if (!rec.contents.ai_canonname.isNull()) hosts.push(rec.contents.ai_canonname.readString()); | |
rec = rec.contents.ai_next; | |
} | |
} | |
} finally { | |
freeaddrinfo(out); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment