net.adns: Flush buffer after sending DNS request
[prosody.git] / net / adns.lua
1 local server = require "net.server";
2 local dns = require "net.dns";
3
4 local log = require "util.logger".init("adns");
5
6 local coroutine, tostring, pcall = coroutine, tostring, pcall;
7
8 module "adns"
9
10 function lookup(handler, qname, qtype, qclass)
11         return dns.peek(qname, qtype, qclass) or
12                 coroutine.wrap(function ()
13                                 log("debug", "Records for "..qname.." not in cache, sending query (%s)...", tostring(coroutine.running()));
14                                 dns.query(qname, qtype, qclass);
15                                 coroutine.yield(nil); -- Wait for reply
16                                 log("debug", "Reply for "..qname.." (%s)", tostring(coroutine.running()));
17                                 local ok, err = pcall(handler, dns.peek(qname, qtype, qclass));
18                                 if not ok then
19                                         log("debug", "Error in DNS response handler: %s", tostring(err));
20                                 end
21                         end)();
22 end
23
24 function new_async_socket(sock)
25         local newconn = {};
26         local listener = {};
27         function listener.incoming(conn, data)
28                 dns.feed(sock, data);
29         end
30         function listener.disconnect()
31         end
32         newconn.handler, newconn._socket = server.wrapclient(sock, "dns", 53, listener);
33         newconn.handler.settimeout = function () end
34         newconn.handler.setsockname = function (_, ...) return sock:setsockname(...); end
35         newconn.handler.setpeername = function (_, ...) local ret = sock:setpeername(...); _.setsend(sock.send); return ret; end
36         newconn.handler.connect = function (_, ...) return sock:connect(...) end        
37         newconn.handler.send = function (_, data) _.write(data); return _.sendbuffer(); end     
38         return newconn.handler;
39 end
40
41 dns:socket_wrapper_set(new_async_socket);
42
43 return _M;