14 sys.stderr.write('backend (%s): %s\n' % (os.getpid(), msg))
23 _log('writing: %s' % a)
28 sys.stdout.write('\t')
31 sys.stdout.write('\n')
38 line = sys.stdin.readline()
40 _log('read line: %s' % line)
41 return line.strip().split('\t')
51 self.name_servers = {}
52 self.blacklisted_ips = []
55 fname = self._get_config_filename()
56 if not os.path.exists(fname):
57 _log('%s does not exist' % fname)
60 with open(fname) as fp:
61 config = ConfigParser.ConfigParser()
64 self.id = config.get('soa', 'id')
65 self.soa = '%s %s %s' % (config.get('soa', 'ns'), config.get('soa', 'hostmaster'), self.id)
66 self.domain = config.get('main', 'domain')
67 self.ip_address = config.get('main', 'ipaddress')
68 self.ttl = config.get('main', 'ttl')
70 for entry in config.items('nameservers'):
71 self.name_servers[entry[0]] = entry[1]
73 if config.has_section("blacklist"):
74 for entry in config.items("blacklist"):
75 self.blacklisted_ips.append(entry[1])
77 _log('Name servers: %s' % self.name_servers)
78 _log('ID: %s' % self.id)
79 _log('TTL %s' % self.ttl)
80 _log('SOA: %s' % self.soa)
81 _log('IP Address: %s' % self.ip_address)
82 _log('DOMAIN: %s' % self.domain)
83 _log("Blacklist: %s" % self.blacklisted_ips)
87 handshake = _get_next()
88 if handshake[1] != '1':
89 _log('Not version 1: %s' % handshake)
91 _write('OK', 'We are good')
92 _log('Done handshake')
104 _log('did not understand: %s' % cmd)
108 qname = cmd[1].lower()
111 if (qtype == 'A' or qtype == 'ANY') and qname.endswith(self.domain):
112 if qname == self.domain:
113 self.handle_self(self.domain)
114 elif qname in self.name_servers:
115 self.handle_nameservers(qname)
117 self.handle_subdomains(qname)
118 elif qtype == 'SOA' and qname.endswith(self.domain):
119 self.handle_soa(qname)
121 self.handle_unknown(qtype, qname)
123 def handle_self(self, name):
124 _write('DATA', name, 'IN', 'A', self.ttl, self.id, self.ip_address)
125 self.write_name_servers(name)
128 def handle_subdomains(self, qname):
129 subdomain = qname[0:qname.find(self.domain) - 1]
131 subparts = subdomain.split('.')
132 if len(subparts) < 4:
134 _log('subparts less than 4')
135 self.handle_self(qname)
138 ip_address_parts = subparts[-4:]
140 _log('ip: %s' % ip_address_parts)
141 for part in ip_address_parts:
142 if re.match('^\d{1,3}$', part) is None:
144 _log('%s is not a number' % part)
145 self.handle_self(qname)
148 if parti < 0 or parti > 255:
150 _log('%d is too big/small' % parti)
151 self.handle_self(qname)
154 ip_address = ".".join(ip_address_parts)
155 if ip_address in self.blacklisted_ips:
156 self.handle_blacklisted(ip_address)
159 _write('DATA', qname, 'IN', 'A', self.ttl, self.id, '%s.%s.%s.%s' % (ip_address_parts[0], ip_address_parts[1], ip_address_parts[2], ip_address_parts[3]))
160 self.write_name_servers(qname)
163 def handle_nameservers(self, qname):
164 ip = self.name_servers[qname]
165 _write('DATA', qname, 'IN', 'A', self.ttl, self.id, ip)
168 def write_name_servers(self, qname):
169 for nameServer in self.name_servers:
170 _write('DATA', qname, 'IN', 'NS', self.ttl, self.id, nameServer)
172 def handle_soa(self, qname):
173 _write('DATA', qname, 'IN', 'SOA', self.ttl, self.id, self.soa)
176 def handle_unknown(self, qtype, qname):
177 _write('LOG', 'Unknown type: %s, domain: %s' % (qtype, qname))
180 def handle_blacklisted(self, ip_address):
181 _write('LOG', 'Blacklisted: %s' % ip_address)
184 def _get_config_filename(self):
185 return os.path.join(os.path.dirname(os.path.realpath(__file__)), 'backend.conf')
188 if __name__ == '__main__':
189 backend = DynamicBackend()