{"id":1163,"date":"2012-02-18T15:27:06","date_gmt":"2012-02-18T14:27:06","guid":{"rendered":"http:\/\/blog.benny-baumann.de\/?p=1163"},"modified":"2012-02-18T15:27:06","modified_gmt":"2012-02-18T14:27:06","slug":"lautstarkenbegrenzung-fur-dns-queries","status":"publish","type":"post","link":"https:\/\/blog.benny-baumann.de\/?p=1163","title":{"rendered":"Lautst\u00e4rkenbegrenzung f\u00fcr DNS-Queries"},"content":{"rendered":"<p>Nachdem seit einiger Zeit versucht wurde, meinen Server mittels gef\u00e4lschter DNS-Queries als Teil eines <a href=\"http:\/\/isc.sans.edu\/diary.html?storyid=5713\">DNS-Amplification-DDoS<\/a> zu missbrauchen, gab es bereits vor einigen Wochen ein paar kleine \u00c4nderungen in meiner Firewall, um die Bandbreite, die mit solchen Angriffen erreicht werden kann, stark zu reduzieren. Und w\u00e4hrend wie man <a href=\"http:\/\/benny-baumann.de\/cgi-bin\/bindgraph.cgi\">im DNS-Graphen sehen kann<\/a>, auch bereits gut wirkte, so war dennoch dieses unn\u00f6tige Grundrauschen da. Um auch dieses zu entfernen, gab es eine weitere Erg\u00e4nzung in der Firewall.<!--more--><\/p>\n<p>Als Firewall kommt bei mir iptables zum Einsatz, was an sich keine gro\u00dfe Sache darstellt. Es filtert halt die Sachen, die es soll und l\u00e4sst den Rest in Ruhe. Nun bietet iptables aber eine ganze Menge mehr, als einfach nur stupide nach Source- oder Destination-IPs zu filtern. W\u00e4hrend also die ersten Ans\u00e4tze noch wirklich rein stupide<\/p>\n<pre lang=\"bash\">iptables -A INPUT -s \"angebliche Quell-IP\" -j DROP<\/pre>\n<p>waren, war der zweite Ansatz <a href=\"http:\/\/www.netfilter.org\/documentation\/HOWTO\/netfilter-extensions-HOWTO-3.html\">mittels Rate Limitting<\/a> bereits etwas gezielter und dennoch wesentlich flexibler:<\/p>\n<pre lang=\"bash\">iptables -I INPUT -p udp --dport 53 -i eth0 -m state --state NEW -m recent --set\r\niptables -I INPUT -p udp --dport 53 -i eth0 -m state --state NEW -m recent --update --seconds 15 --hitcount 30 -j DROP<\/pre>\n<p>W\u00e4hrend die erste Regel also Pakete z\u00e4hlt und den Timer resettet, sorgt die zweite Regel daf\u00fcr, dass \u00fcbersch\u00fcssige Pakete gedroppt werden. So kommen die im Graphen sichtbaren Kanten bei etwa 3-5 Queries\/Sekunde zustande.<\/p>\n<p>Doch so richtig zufriedenstellend war das noch nicht. Also heute dann noch ein weiterer Schritt, der <a href=\"http:\/\/forum.slicehost.com\/comments.php?DiscussionID=2970\">mittels String-Matching<\/a> die problematischen Pakete vor dem DNS gezielt eliminiert:<\/p>\n<pre lang=\"bash\">iptables -t raw -I PREROUTING -p udp --destination-port 53 -m string --algo kmp --from 30 --hex-string \"|010000010000000000000000020001|\" -j DROP\r\niptables -t raw -I PREROUTING -p udp --destination-port 53 -m string --algo kmp --from 30 --hex-string \"|0100000100000000000103697363036f72670000ff00010000291000000080000000|\" -j DROP<\/pre>\n<p>Die erste der beiden Zeilen filtert hierbei Anfragen nach den Nameservern f\u00fcr . (Die Root-Domain), w\u00e4hrend die zweite Regel f\u00fcr Ruhe sorgt, was spezifische Quelldomains (in meinem Fall wurde st\u00e4ndig nach isc.org gefragt) angeht. Um den korrekten Matching-String zu finden, gibt es mit sowohl Wireshark als auch tcpdump zwei sehr leistingsf\u00e4hige Programme. So kann man mit tcpdump recht einfach nach DNS-Paketen suchen, wenn man<\/p>\n<pre lang=\"bash\">tcpdump -nvvxxi eth0 port 53<\/pre>\n<p>eingibt und sich die einzelnen ankommenden Pakete anschaut. Interessant sind die Daten ab Offset 0x2C, was bei mir etwa wie folgt aussah:<\/p>\n<pre>15:01:52.966446 IP (tos 0x0, ttl 179, id 14613, offset 0, flags [none], proto UDP (17), length 64)\r\n    184.154.66.179.16996 > 176.9.26.150.53: [no cksum] 7490+ [1au] ANY? isc.org. ar: . OPT UDPsize=4096 OK (36)\r\n        0x0000:  6c62 6dbc bb87 28c0 da46 34a4 0800 4500\r\n        0x0010:  0040 3915 0000 b311 08ab b89a 42b3 b009\r\n        0x0020:  1a96 4264 0035 002c 0000 1d42 <strong>0100 0001\r\n        0x0030:  0000 0000 0001 <em>0369 7363 036f 7267<\/em> 0000\r\n        0x0040:  ff00 0100 0029 1000 0000 8000 0000<\/strong><\/pre>\n<p>Daraus die Leerzeichen entfernt, in zwei Pipes eingefasst und man hat den passenden Filter-String. Die eigentliche Domain findet sich ab Offset 0x36 und ist in diesem Fall isc.org.<\/p>\n<p>Trotz der Regel sieht man zwar noch den einkommenden Traffic; aber zumindest gibt es keine Antworten mehr an die (gef\u00e4lschten) Absenderadressen; man spart also durchaus einiges an Outbound-Traffic.<\/p>\n<p class=\"wp-flattr-button\"><a href=\"https:\/\/blog.benny-baumann.de\/?flattrss_redirect&amp;id=1163&amp;md5=43a259ae37274f640eb0d8522b457abc\" title=\"Flattr\" target=\"_blank\"><img src=\"http:\/\/blog.benny-baumann.de\/wp-content\/plugins\/flattr\/img\/flattr-badge-large.png\" srcset=\"http:\/\/blog.benny-baumann.de\/wp-content\/plugins\/flattr\/img\/flattr-badge-large.png\" alt=\"Flattr this!\"\/><\/a><\/p>","protected":false},"excerpt":{"rendered":"<p>Nachdem seit einiger Zeit versucht wurde, meinen Server mittels gef\u00e4lschter DNS-Queries als Teil eines DNS-Amplification-DDoS zu missbrauchen, gab es bereits vor einigen Wochen ein paar kleine \u00c4nderungen in meiner Firewall, um die Bandbreite, die mit solchen Angriffen erreicht werden kann, stark zu reduzieren. Und w\u00e4hrend wie man im DNS-Graphen sehen kann, auch bereits gut wirkte, [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"ngg_post_thumbnail":0,"footnotes":""},"categories":[4],"tags":[10,48,69,346],"class_list":["post-1163","post","type-post","status-publish","format-standard","hentry","category-server","tag-debian","tag-dns","tag-internet","tag-server"],"_links":{"self":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts\/1163","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=1163"}],"version-history":[{"count":1,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts\/1163\/revisions"}],"predecessor-version":[{"id":1164,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts\/1163\/revisions\/1164"}],"wp:attachment":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=1163"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=1163"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=1163"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}