Can't tell my truth from my lies
For a long time now, my blog has consisted of handcrafted XHTML marked up with hAtom, and using XSLTs to generate HTML versions and my Atom feed. While this worked out reasonably well in terms of giving me control over every last detail of my content, it was pretty much a pain in the ass when it came to churning out light-weight comment. Sure, some days I'm doing something important enough to worry about the details; other days I just want to type some stuff into a textbox and click "post". The ultimate solution will probably be to write my own blog software, but there are already half a million projects on my todo list that would be above that one, so it's not going to happen any time soon.
However, today I suddenly realised that I don't have to choose a single place to blog; I can keep blogs at two (or more) different sites, and just aggregate them all into a single feed for people who want to follow my blatherings. Sure, it means someone manually navigating my content is going to have a harder time finding it all, but that's what Google is for anyway. So here's my new shiny Vox blog, where I'll probably be writing a heck of a lot more than I ever did on my old blog. If you're reading this before I've hooked it up to my main feed, congratulations!
08-04-04
Hi from Vox mobile
Nu Metro website defaced
tags:
It seems the Nu Metro website has been defaced by a Turkish group; a little research suggests that this is at least the second time this year.
In case the site has already been restored by the time you read this, I’ve uploaded a screencap of the defacement for posterity.
URL switchoroo
tags:
So, I finally made the switch; please change any links pointing at http://mithrandi.za.net/… to point at http://mithrandi.net/… — note that my e-mail address has *not* changed. Still haven’t gotten around to switching up the latter, although I probably will do it at some point. The old URLs will continue to work, with an HTTP 301 permanent redirect pointing at the new domain, but it would obviously be better if everything pointed directly at the right location. If you’re reading this through a feed aggregator, with any luck it will be smart enough to acknowledge the HTTP 301 and automatically update my feed URL, but if not, please change it yourself for the best experience.
Also, I guess I have to claim my blog again for my Technorati Profile…
DNS evils: glueless delegations
tags:
One of the most serious design flaws in DNS today, is the decision to use hostnames in NS records, instead of IP addresses. Why? Because it has the potential to massively complexify the chain of DNS queries a recursive resolver has to follow in order to resolve a particular name.
Let’s say you type http://www.google.com/
into your web browser. Your web browser hands the address www.google.com
to the resolver library; it will generally end up making a recursive query to your ISP’s caching resolver. This is where all the hard work happens. The resolver starts by sending a query for A www.google.com
to one of the root nameservers; it will then respond with the list of NS records corresponding to the servers hosting the .com
TLD. The resolver will then repeat the query to one of these servers, and so on until it arrives at a server that is authoritative for www.google.com
, which it has determined by following the chain of delegations in the form of NS records, and by getting an authoritative response from a server it queries.
So, that may seem simple enough; however there’s one snag here: NS records contain hostnames, and not IP addresses, so when the resolver receives an NS record containing a particular hostname, it then needs to perform a separate lookup, starting the process all over again. This second lookup could, in turn, require a third lookup to be performed for hostnames encountered during the second query, and so on. If this were the whole story, it would actually never be possible to resolve these NS records, because there would be no way to locate the server containing the A records for those servers in the first place.
Enter delegations with “glue”; a DNS query response has multiple sections, one of which is particularly important here: the “additional” section. This section contains records that, while not directly part of the records requested, may be helpful in using the records returned in the other sections of the response. This allows for returning A records for the hostnames specified in the NS records returned, thus providing a way for the resolver to avoid making a secondary lookup. Unfortunately, this is only possible under certain circumstances: if your DNS server is authoritative for google.com
(by way of an NS record served up by the .com servers), you can return records relating to google.com, and any domain “below” it, such as quux.google.com
. Resolvers recognize that your server is authoritative for these names, because they have followed the chain of NS records starting at the root. So, if you return a record like ns1.google.com 172800 A 216.239.32.10
in the additional section, resolvers will accept (and cache) this, and be able to avoid a secondary lookup of ns1.google.com
. However, if your NS records point at some other address, such as ns1.yendor.net
, even if you return records providing an address for ns1.yendor.net
, resolvers *must* ignore these records, as your server is not authoritative for yendor.net
, or anything above it. Thus, there is no way to avoid the secondary lookup; these cases are referred to as “glueless” delegations.
So, to summarize: delegations with glue are almost as good as having IP addresses in NS records, as they avoid a secondary lookup for the hostname specified in the NS record. Glueless delegations, however, do require a secondary lookup, leading to situations where a convoluted chain of delegations must be followed and many queries made in order to look up a name. This leads to increased vulnerability to attack: compromising any server along the chain gives you the ability to influence the final result, by directing the resolver to servers under your control. In addition, the increased number of queries can lead to timeouts due to the length of time it takes to get all of the responses. To see an example of how bad this situation can become, I’ve prepared transcripts simulating what a resolver has to do in order to look up a particular domain name: dns insanity and dns sanity. Also, the level of indirection along the chain may change at any time, as presumably the other names along the chain are not directly under your control (otherwise you wouldn’t have used a glueless delegation in the first place); an additional level of gluelessness might be added, causing longer delays and possibly failures, without you realising until users start complaining.
There are a few reasons you might want to use glueless delegations; probably the most common is the case where a third party is providing all of your DNS servers, or at least providing backup servers. In this case, they probably already have a hostname for their servers, and you may wish to simply use this, rather than copying their IP address into your record data. The simplest way around this is to do just that; copy their address into your data. DNS server addresses should usually be quite stable, so you shouldn’t have to worry too much about the address changing; just make sure the third-party provider notifies you of any such changes when they are to occur. Another way would be to have an automated process (either built into your DNS server, or as a separate service) that caches the address, looks it up again (using a normal simple recursive query), and updates the DNS server data if the address changes. This is effectively what resolvers have to do anyway with a glueless delegation, but this way it is only your server doing it, rather than hundreds, thousands, or millions of resolvers around the internet. Both of these solutions require a little more work on the DNS admin’s end, but improve the efficiency and reliability of your DNS data publication.
So please, think of the childr… err… dns resolvers, and use glueless delegations.
Cooperative __init__ in Python
tags:
So, super()
and __init__
in Python kinda sucks. Actually, the linked example involves a method other than __init__
, but this is probably the most common situation in which this problem arises.
There is a pattern I sometimes use in this situation, which provides cooperative handling of kwargs, with the caveat that the argument namespace is shared across the whole inheritance hierarchy. The usage looks something like this:
class Base(object): def __init__(self, foo): self.foo = foo class A(Base): def __init__(self, bar=5, **kw): # consume bar parameter super(A, self).__init__(**kw) self.bar = bar # sample instantiations A(foo=10) A(foo=5, bar=10) class B(Base): def __init__(self, baz, **kw): # consume baz parameter super(B, self).__init__(**kw) self.baz = baz # sample instantiations B(foo=7, baz=9) class C(A, B): def __init__(self, foo, baz=10, quux, **kw): # munge foo, and make baz default to 10 # also consume quux super(B, self).__init__(foo=foo + 5, baz=baz, **kw) self.quux = quux # sample instantiations C(foo=2, bar=10, baz=7) C(foo=8)
I’m not going to debate the larger issues here; I’m just presenting this as something that hopefully be a useful tool for handling this kind of situation. In the cases where I’ve used it, it has worked quite well, although you will probably run into trouble when many parts of the inheritance tree are under different people’s control, due to the shared argument namespace.
Quote of the Day
tags:
No substantial famine has ever occurred in any independent and democratic country with a relatively free press.
— Amartya Sen, by way of JP
Fusion production deployment
tags:
I just finished deploying Fusion 1.0 to our production server. If you don’t know what that is, suffice it to say that it’s the new system I’ve been working on for the last 6 months or so, replacing the existing legacy system. If you’re wondering why I’m excited, not terrified, here is a snippet of code from the legacy system:
printf([<input type="submit" value="Next Page" onClick="if (checkMatrix('MAINFORM', 'qmtx')] + ;
[ && checkMPStuff('MAINFORM', 'toolkitnum', 'qmp')] + ;
; //’ && checkReasons(%s)’ + ;
[ && confirm('Proceed with inception of selected products? This is irrevocable!')) changeAction('MAINFORM', 'MAKEPAGE.EXE'); else return false;" /></div>],;
{jsDict(getOptDatabases())})]]
In case you’re interested, Fusion is deployed on top of the Divmod Mantissa stack (which includes Axiom, Nevow, Twisted). Without these awesome Free Software projects, this would have been a much longer ride, and the resulting product would no doubt have been of far inferior quality; thanks to all the contributors that make these projects a reality!
Anyhow, that’s all for now. Coming up next… a series on JavaScript “features” that are likely to stab you in the face. Maybe even over the internet.