diff --git a/bin/digd.js b/bin/digd.js deleted file mode 100644 index bb67ffb..0000000 --- a/bin/digd.js +++ /dev/null @@ -1,379 +0,0 @@ -'use strict'; - -var cli = require('cli'); -var dig = require('../dns-request'); -var dgram = require('dgram'); -var dnsjs = require('dns-suite'); -var crypto = require('crypto'); -var common = require('../common'); -var defaultNameservers = require('dns').getServers(); -var hexdump; - -cli.parse({ -// 'b': [ false, 'set source IP address (defaults to 0.0.0.0)', 'string' ] - 'class': [ 'c', 'class (defaults to IN)', 'string', 'IN' ] -, 'debug': [ false, 'more verbose output', 'boolean', false ] -//, 'insecure': [ false, 'turn off RaNDOm cAPS required for securing queries'] -//, 'ipv4': [ '4', 'use ipv4 exclusively (defaults to false)', 'boolean', false ] -//, 'ipv6': [ '6', 'use ipv6 exclusively (defaults to false)', 'boolean', false ] -//, 'json': [ false, 'output results as json', 'string' ] -//, 'lint': [ false, 'attack (in the metaphorical sense) a nameserver with all sorts of queries to test for correct responses', 'string', false ] -, 'mdns': [ false, "Alias for setting defaults to -p 5353 @224.0.0.251 -t PTR -q _services._dns-sd._udp.local and waiting for multiple responses", 'boolean', false ] -, 'timeout': [ false, "How long, in milliseconds, to wait for a response. Alias of +time=", 'int', false ] -, 'output': [ 'o', 'output prefix to use for writing query and response(s) to disk', 'file' ] -, 'address': [ false, 'ip address(es) to listen on (defaults to 0.0.0.0,::0)', 'string' ] -, 'port': [ 'p', 'port (defaults to 53 for dns and 5353 for mdns)', 'int' ] -, 'nameserver': [ false, 'the nameserver(s) to use for recursive lookups (defaults to ' + defaultNameservers.join(',') + ')', 'string' ] -//, 'serve': [ 's', 'path to json file with array of responses to issue for given queries', 'string' ] -, 'type': [ 't', 'type (defaults to ANY for dns and PTR for mdns)', 'string' ] -, 'query': [ 'q', 'a superfluous explicit option to set the query as a command line flag' ] -}); - -cli.main(function (args, cli) { - args.forEach(function (arg) { - if (arg === '+norecurse') { - if (cli.norecurse) { - console.error("'+norecurse' was specified more than once"); - process.exit(1); - return; - } - cli.norecurse = true; - return; - } - }); - - if (cli.mdns) { - if (!cli.type) { - cli.type = cli.t = 'PTR'; - } - if (!cli.port) { - cli.port = cli.p = 5353; - } - if (!cli.nameserver) { - cli.nameserver = '224.0.0.251'; - } - if (!cli.query) { - cli.query = '_services._dns-sd._udp.local'; - } - if (!('timeout' in cli)) { - cli.timeout = 3000; - } - } else { - if (!cli.port) { - cli.port = cli.p = 53; - } - } - - var handlers = {}; - var server = dgram.createSocket({ - type: cli.udp6 ? 'udp6' : 'udp4' - //, reuseAddr: true - }); - server.bind({ - port: cli.port - , address: cli.address - }); - - handlers.onError = function (err) { - console.error("error:", err.stack); - server.close(); - }; - - handlers.onMessage = function (nb, rinfo) { - var queryAb = nb.buffer.slice(nb.byteOffset, nb.byteOffset + nb.byteLength); - var query; - var count; - - try { - query = dnsjs.DNSPacket.parse(queryAb); - } catch(e) { - // TODO log bad queries (?) - console.error("Could not parse DNS query, ignoring."); - try { - hexdump = require('hexdump.js').hexdump; - console.error(hexdump(queryAb)); - console.error(''); - } catch(e) { - // ignore - } - return; - } - - if (cli.debug) { - console.log(''); - console.log('DNS Question:'); - console.log(''); - console.log(query); - console.log(''); - try { - hexdump = require('hexdump.js').hexdump; - console.log(hexdump(queryAb)); - console.log(''); - } catch(e) { - // ignore - } - } - - dig.logQuestion(query); - /* - console.log(';; Got question:'); - console.log(';; ->>HEADER<<-'); - console.log(JSON.stringify(query.header)); - console.log(''); - console.log(';; QUESTION SECTION:'); - query.question.forEach(function (q) { - console.log(';' + q.name + '.', ' ', q.className, q.typeName); - }); - */ - - function print(q) { - var printer = common.printers[q.typeName] || common.printers.ANY; - printer(q); - } - if (query.answer.length) { - console.error('[ERROR] Query contains an answer section:'); - console.log(';; ANSWER SECTION:'); - query.answer.forEach(print); - } - if (query.authority.length) { - console.log(''); - console.error('[ERROR] Query contains an authority section:'); - console.log(';; AUTHORITY SECTION:'); - query.authority.forEach(print); - } - if (query.additional.length) { - console.log(''); - console.error('[ERROR] Query contains an additional section:'); - console.log(';; ADDITIONAL SECTION:'); - query.additional.forEach(print); - } - console.log(''); - console.log(';; MSG SIZE rcvd: ' + nb.byteLength); - console.log(''); - - if (cli.output) { - console.log(''); - common.writeQuery(cli, query, queryAb); - //common.writeResponse(opts, query, nb, packet); - } - - function sendEmptyResponse(query, nx) { - var newAb; - var emptyResp = { - header: { - id: query.header.id // require('crypto').randomBytes(2).readUInt16BE(0) - , qr: 1 - , opcode: 0 - , aa: 0 // TODO it may be authoritative - , tc: 0 - , rd: query.header.rd - , ra: cli.norecurse ? 0 : 1 // TODO is this bit dependent on the rd bit? - , rcode: nx ? 3 : 0 // no error - } - , question: [] - , answer: [] - , authority: [] - , additional: [] - }; - query.question.forEach(function (q) { - emptyResp.question.push({ - name: q.name - , type: q.type - , typeName: q.typeName - , class: q.class - , className: q.className - }); - }); - - try { - newAb = dnsjs.DNSPacket.write(emptyResp); - } catch(e) { - console.error("Could not write DNS response"); - console.error(emptyResp); - return; - } - - server.send(newAb, rinfo.port, rinfo.address, function () { - console.log('[DEV] response sent (empty)'); - }); - } - - function sendResponse(newPacket) { - var newAb; - - try { - newAb = dnsjs.DNSPacket.write(newPacket); - } catch(e) { - console.error("Could not write DNS response"); - console.error(newPacket); - return; - } - - server.send(newAb, rinfo.port, rinfo.address, function () { - console.log('[DEV] response sent (local query)'); - }); - } - - function recurse() { - if (!query.header.rd) { - console.log("[Could not answer. Sent empty response.]"); - sendEmptyResponse(query, true); - return; - } - - if (cli.norecurse) { - console.log("[Could not answer. Sent empty response.]"); - sendEmptyResponse(query, true); - return; - } - - // TODO newQuery - - var newResponse = { - header: { - id: query.header.id // require('crypto').randomBytes(2).readUInt16BE(0) - , qr: 0 - , opcode: 0 - , aa: query.header.aa ? 1 : 0 // NA? not sure what this would do - , tc: 0 // NA - , rd: 1 - , ra: 0 // NA - , rcode: 0 // NA - } - , question: [] - , answer: [] - , authority: [] - , additional: [] - }; - query.question.forEach(function (q) { - newResponse.question.push({ - name: q.name - , type: q.type - , typeName: q.typeName - , class: q.class - , className: q.className - }); - - function updateCount() { - var newAb; - count -= 1; - - if (!count) { - try { - newAb = dnsjs.DNSPacket.write(newResponse); - } catch(e) { - console.error("Could not write DNS response"); - console.error(newResponse); - return; - } - - server.send(newAb, rinfo.port, rinfo.address, function () { - console.log('[DEV] response sent'); - }); - } - } - - var opts = { - onError: function () { - updateCount(); - } - , onMessage: function (packet) { - - (packet.answer||[]).forEach(function (a) { - // TODO copy each relevant property - console.log('ans', JSON.stringify(a, null, 2)); - newResponse.answer.push(a); - }); - (packet.authority||[]).forEach(function (a) { - // TODO copy each relevant property - console.log('auth', JSON.stringify(a, null, 2)); - newResponse.authority.push(a); - }); - (packet.additional||[]).forEach(function (a) { - // TODO copy each relevant property - console.log('add', JSON.stringify(a, null, 2)); - newResponse.additional.push(a); - }); - - updateCount(); - - } - , onListening: function () {} - , onSent: function (/*res*/) { - /* - if (cli.debug) { - console.log(''); - console.log('request sent to', res.nameserver); - } - */ - console.log('[DEV] response sent (recurse)'); - } - , onTimeout: function (res) { - console.log(";; [" + q.name + "] connection timed out; no servers could be reached"); - console.log(";; [timed out after " + res.timeout + "ms and 1 tries]"); - } - , onClose: function () { - console.log(''); - } - , mdns: cli.mdns - , nameserver: cli.nameserver - , port: cli.port - , timeout: cli.timeout - }; - - //dig.resolve(queryAb, opts); - dig.resolveJson(query, opts); - - console.log(';' + q.name + '.', ' ', q.className, q.typeName); - }); - } - - count = query.question.length; - if (!count) { - sendEmptyResponse(query); - return; - } - - // TODO get local answer first, if available - require('../dns-store').query(query, function (err, resp) { - if (err) { recurse(); return; } - - sendResponse(resp); - }); - - }; - - handlers.onListening = function () { - /*jshint validthis:true*/ - var server = this; - var nameserver = cli.nameserver; - var index; - - if (!nameserver) { - index = crypto.randomBytes(2).readUInt16BE(0) % defaultNameservers.length; - nameserver = defaultNameservers[index]; - if (cli.debug) { - console.log(index, defaultNameservers); - } - } - - if (cli.mdns || '224.0.0.251' === cli.nameserver) { - server.setBroadcast(true); - server.addMembership(cli.nameserver); - } - - console.log(''); - console.log('Bound and Listening:'); - console.log(server.address().address + '#' + server.address().port); - }; - - console.log(''); - if (!cli.nocmd) { - console.log('; <<>> digd.js ' + 'v0.0.0' + ' <<>> ' + process.argv.slice(2)); - console.log(';; global options: +cmd'); - } - - server.on('error', handlers.onError); - server.on('message', handlers.onMessage); - server.on('listening', handlers.onListening); -}); diff --git a/dns-store.js b/dns-store.js deleted file mode 100644 index 1387edd..0000000 --- a/dns-store.js +++ /dev/null @@ -1,10 +0,0 @@ -(function () { -'use strict'; - -module.exports.query = function (query, cb) { - process.nextTick(function () { - cb(new Error('No local lookup method for DNS records defined.')); - }); -}; - -}()); diff --git a/package.json b/package.json index a9e2bd8..670f930 100644 --- a/package.json +++ b/package.json @@ -4,8 +4,7 @@ "description": "Create and capture DNS and mDNS query and response packets to disk as binary and/or JSON. Options are similar to the Unix `dig` command.", "main": "index.js", "bin": { - "dig.js": "./bin/dig.js", - "digd.js": "./bin/digd.js" + "dig.js": "./bin/dig.js" }, "scripts": { "test": "echo \"Error: no test specified\" && exit 1"