Commit b5707788 authored by Avery Pennarun's avatar Avery Pennarun

dns: trim DNS channel handlers after a response, or after a timeout.

This avoids memory/socket leaks.
parent 4c5185dc
import struct, socket, select, errno, re, signal
import struct, socket, select, errno, re, signal, time
import compat.ssubprocess as ssubprocess
import helpers, ssnet, ssh, ssyslog
from ssnet import SockWrapper, Handler, Proxy, Mux, MuxWrapper
......@@ -293,22 +293,27 @@ def _main(listener, fw, ssh_cmd, remotename, python, latency_control,
handlers.append(Proxy(SockWrapper(sock, sock), outwrap))
handlers.append(Handler([listener], onaccept))
dnspeers = {}
dnsreqs = {}
def dns_done(chan, data):
peer = dnspeers.get(chan)
debug1('dns_done: channel=%r peer=%r\n' % (chan, peer))
peer,timeout = dnsreqs.get(chan)
debug3('dns_done: channel=%r peer=%r\n' % (chan, peer))
if peer:
del dnspeers[chan]
debug1('doing sendto %r\n' % (peer,))
del dnsreqs[chan]
debug3('doing sendto %r\n' % (peer,))
dnslistener.sendto(data, peer)
def ondns():
pkt,peer = dnslistener.recvfrom(4096)
now = time.time()
if pkt:
debug1('Got DNS request from %r: %d bytes\n' % (peer, len(pkt)))
debug1('DNS request from %r: %d bytes\n' % (peer, len(pkt)))
chan = mux.next_channel()
dnspeers[chan] = peer
dnsreqs[chan] = peer,now+30
mux.send(chan, ssnet.CMD_DNS_REQ, pkt)
mux.channels[chan] = lambda cmd,data: dns_done(chan,data)
for chan,(peer,timeout) in dnsreqs.items():
if timeout < now:
del dnsreqs[chan]
debug3('Remaining DNS requests: %d\n' % len(dnsreqs))
if dnslistener:
handlers.append(Handler([dnslistener], ondns))
......
import re, struct, socket, select, traceback
import re, struct, socket, select, traceback, time
if not globals().get('skip_imports'):
import ssnet, helpers, hostwatch
import compat.ssubprocess as ssubprocess
......@@ -111,6 +111,7 @@ class DnsProxy(Handler):
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
Handler.__init__(self, [sock])
self.sock = sock
self.timeout = time.time()+30
self.mux = mux
self.chan = chan
self.sock.setsockopt(socket.SOL_IP, socket.IP_TTL, 42)
......@@ -119,8 +120,9 @@ class DnsProxy(Handler):
def callback(self):
data = self.sock.recv(4096)
debug2('dns response: %d bytes\n' % len(data))
debug2('DNS response: %d bytes\n' % len(data))
self.mux.send(self.chan, ssnet.CMD_DNS_RESPONSE, data)
self.ok = False
def main():
......@@ -184,7 +186,7 @@ def main():
dnshandlers = {}
def dns_req(channel, data):
debug1('got dns request!\n')
debug2('Incoming DNS request.\n')
h = DnsProxy(mux, channel, data)
handlers.append(h)
dnshandlers[channel] = h
......@@ -201,3 +203,10 @@ def main():
if latency_control:
mux.check_fullness()
mux.callback()
if dnshandlers:
now = time.time()
for channel,h in dnshandlers.items():
if h.timeout < now or not h.ok:
del dnshandlers[channel]
h.ok = False
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment