{"id":463,"date":"2013-10-23T12:45:17","date_gmt":"2013-10-23T10:45:17","guid":{"rendered":"http:\/\/valentijn.sessink.nl\/?p=463"},"modified":"2020-01-24T11:50:37","modified_gmt":"2020-01-24T09:50:37","slug":"ip-addresses-for-your-hetzner-machine","status":"publish","type":"post","link":"https:\/\/valentijn.sessink.nl\/?p=463","title":{"rendered":"IP addresses for your Hetzner machine"},"content":{"rendered":"<p>We lease a couple of machines at Hetzner.de and recently, I looked to improve my initial <a href=\"http:\/\/wiki.hetzner.de\/index.php\/KVM_mit_Nutzung_aller_IPs_-_the_easy_way\/en\" target=\"_blank\" rel=\"noopener noreferrer\">Easy Setup manual<\/a>, so I could also use the IPv4 &#8220;main&#8221; address for a virtual machine. This leaves the main server (the &#8220;host&#8221;) without an IPv4 address. Please read below how to proceed.<!--more--><\/p>\n<p>Hetzner has a rather ingenious network setup, where the switch (or router) does not send ARP requests. Instead, all your traffic is directed to the MAC address of your primary NIC. This poses a few difficulties, but I found a way around them back in January, 2011. But now it&#8217;s 2013 and we don&#8217;t want the primary IP address to live in the host machine &#8211; just for nothing. We&#8217;d like to use that in a guest machine, too.<\/p>\n<p><strong>Here&#8217;s how to proceed.<\/strong><br \/>\nThe first thing to note is, that I <strong>am<\/strong> going to use an IP address for the host machine. Without an IP address, I would need a different way to resolve MAC addresses &#8211; most likely, a list of VM&#8217;s with their IP address and accompanying network card address. This is what ARP was invented for, so we want to use ARP.<\/p>\n<p>On the host machine, this is what my \/etc\/network\/interfaces file looks like:<\/p>\n<p><code>### Hetzner Online AG - installimage<br \/>\n# Loopback device:<br \/>\nauto lo<br \/>\niface lo inet loopback<\/code><\/p>\n<p><code><br \/>\n<\/code><\/p>\n<p><code>auto br0<br \/>\niface br0 inet6 static<br \/>\naddress 2a01:xxxx:xxx:xx::x<br \/>\nnetmask 64<br \/>\ngateway fe80::1<br \/>\nbridge_ports eth0<br \/>\nbridge_maxwait 0<br \/>\niface br0 inet static<br \/>\naddress 10.9.8.7<br \/>\nnetmask 255.255.255.255<br \/>\npointopoint $Hetzner-gateway-IP<br \/>\n<\/code><br \/>\nAs you&#8217;ll notice, I have a single bridge that connects the outside world (eth0) with the virtual machines inside the bridge. This has the rather odd side effect of seeing every packet twice: once when Hetzner sends it to your ethernet card (source MAC address from Hetzner, destination MAC is your card), then again when your host concludes that this packet is to be routed to one of your virtual machines (source MAC is your card, destination is your virtual network card). I have pondered the possibility of having a proper routed net, giving eth0 something like 10.9.8.7 and br0 something like 10.10.11.12. This would have the advantage of isolating the virtual network traffic (&#8220;arp who-has 10.10.11.12&#8221; from the virtual machines) from the outside. The disadvantage, however, is, that we would need to route our IPv6 network. Hetzner, as far as I can see, <em>does<\/em> use proper neighbour discovery for IPv6 &#8211; so it actually uses the virtual MAC addresses for IPv6 traffic.<\/p>\n<p>So I will use a single bridge. Hetzner will receive the virtual machine&#8217;s &#8220;who has 10.9.8.7&#8221; but it ignores them anyway.<\/p>\n<p>Our setup is almost ready. There&#8217;s a few things that won&#8217;t go quite right now. If the host sends an &#8220;arp who-has&#8221;, it will do so with the source address of 10.9.8.7. And Hetzner does not answer such a request, because it doesn&#8217;t recognize the source address. We need &#8220;arptables&#8221; for this, with a &#8220;post-up&#8221; command:<\/p>\n<p><code>  post-up  arptables -A OUTPUT -s 10.9.8.7 -d $Hetzner-gateway-IP -j mangle --mangle-ip-s $Your-main-IP-address<\/code><\/p>\n<p>Another issue is, that the host won&#8217;t know which IP addresses are link local &#8211; i.e. belong to a virtual machine. It will send all traffic to Hetzner &#8211; which, in turn, will send it back &#8211; unless you tell it otherwise. In order to send &#8220;arp who has&#8221; to br0, you&#8217;ll need to add routes. I&#8217;ll add another bunch of &#8220;post-up&#8221; commands to our br0-device in \/etc\/network\/interfaces:<\/p>\n<p><code><br \/>\niface br0 inet6 static<br \/>\n[...]<br \/>\npost-up  arptables -A OUTPUT -s 10.9.8.7 -d $Hetzner-gateway-IP -j mangle --mangle-ip-s $Your-main-IP-address<br \/>\npost-up ip ro a $your-extra-ip-address1\/32 dev br0<br \/>\npost-up ip ro a $your-extra-ip-address2\/32 dev br0<br \/>\npost-up ip ro a $your-extra-ip-address2\/32 dev br0<br \/>\n<\/code><\/p>\n<p>&#8230; a &#8220;ip ro a&#8221; command for every IP address that you lease. Please note, that you cannot use &#8220;$your-ip-subnet\/29&#8221;, because that would render the first and last IP addresses in the subnet useless.<\/p>\n<p>Now you only need to setup your guest machine&#8217;s network interfaces. That&#8217;s fairly easy, once they&#8217;re installed:<\/p>\n<p><code><br \/>\nauto eth0<br \/>\niface eth0 inet static<br \/>\naddress $your-hetzner-address<br \/>\nnetmask 255.255.255.255<br \/>\npointopoint 10.9.8.7<br \/>\ngateway 10.9.8.7<br \/>\niface eth0 inet6 static<br \/>\naddress 2a01:xxxx:xxxx:xxxx::xxxx<br \/>\nnetmask 64<br \/>\ngateway fe80::1<br \/>\n<\/code><\/p>\n<p>A final note: if you are going to install an Ubuntu or Debian machine, the installer won&#8217;t be able to setup the network properly. Proceed as follows.<br \/>\nRun the installer. After trying to configure the network, choose &#8220;do not configure the network at this time&#8221;. Your next question is the &#8220;hostname&#8221;. Switch to a virtual terminal, by pressing &#8220;alt&#8221;-&#8220;right arrow&#8221; or &#8220;alt-F2&#8221;. Activate the console and enter the following commands (please note: 8.8.8.8 is the public Google-DNS, feel free to use another DNS-server):<\/p>\n<p><code><br \/>\nip address add $your-ip-address\/32 dev eth0<br \/>\nip route add 10.9.8.7 dev eth0<br \/>\nip route add default via 10.9.8.7<br \/>\necho 'nameserver 8.8.8.8' &gt; \/etc\/resolv.conf<br \/>\nping www.openoffice.nl<br \/>\n<\/code><\/p>\n<p>If everything went well, your ping command should say &#8220;www.openoffice.nl is alive!&#8221; You can shorten the &#8220;ip&#8221; commands: &#8220;ip address add&#8221; can be abbreviated by &#8220;ip a a&#8221;, and &#8220;ip route add&#8221; may be shortened to &#8220;ip ro add&#8221;.<\/p>\n<p>Now return to the installer by pressing &#8220;Alt-F1&#8221; or &#8220;Alt&#8221;-&#8220;left-arrow&#8221;, and continue the installation. After the installation has finished, you need to enter the correct information in \/etc\/network\/interfaces &#8211; see above.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>We lease a couple of machines at Hetzner.de and recently, I looked to improve my initial Easy Setup manual, so I could also use the IPv4 &#8220;main&#8221; address for a virtual machine. This leaves the main server (the &#8220;host&#8221;) without an IPv4 address. Please read below how to proceed.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[49],"tags":[],"class_list":["post-463","post","type-post","status-publish","format-standard","hentry","category-ipv6-2"],"_links":{"self":[{"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=\/wp\/v2\/posts\/463","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=463"}],"version-history":[{"count":19,"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=\/wp\/v2\/posts\/463\/revisions"}],"predecessor-version":[{"id":732,"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=\/wp\/v2\/posts\/463\/revisions\/732"}],"wp:attachment":[{"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=463"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=463"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/valentijn.sessink.nl\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=463"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}