diff --git a/inventory/group_vars/all b/inventory/group_vars/all index 1c841da..94a0b71 100644 --- a/inventory/group_vars/all +++ b/inventory/group_vars/all @@ -38,6 +38,15 @@ meshes: iface_mtu: 1350 peers_mesh_repo: https://github.com/freifunk-mwu/peers-ffmz.git peers_intragate_repo: https://github.com/freifunk-mwu/ffmz-infrastructure-peers.git + dns: + master: fd37:b4dc:4b1e::a25:103 + forward_zones: + ffmz.org: + user.ffmz.org: + bb.ffmz.org: + nodes.ffmz.org: + ffbin: + master: fd37:b4dc:4b1e::a25:10c wi: site_number: 56 @@ -60,6 +69,13 @@ meshes: iface_mtu: 1350 peers_mesh_repo: https://github.com/freifunk-mwu/peers-ffwi.git peers_intragate_repo: https://github.com/freifunk-mwu/ffwi-infrastructure-peers.git + dns: + master: fd56:b4dc:4b1e::a38:103 + forward_zones: + ffwi.org: + user.ffwi.org: + bb.ffwi.org: + nodes.ffwi.org: icvpn: prefix: mwu diff --git a/playbooks/gateways.yml b/playbooks/gateways.yml index e8b18ea..d60c0c1 100755 --- a/playbooks/gateways.yml +++ b/playbooks/gateways.yml @@ -25,5 +25,6 @@ - service-bird - service-bird-icvpn - service-bird-ffrl + - service-bind-slave - service-rclocal - system-sysctl-gateway diff --git a/roles/service-bind-slave/README.md b/roles/service-bind-slave/README.md new file mode 100644 index 0000000..5062605 --- /dev/null +++ b/roles/service-bind-slave/README.md @@ -0,0 +1,39 @@ +# Ansible role service-bind-slave + +Diese Ansible role installiert und konfiguriert den DNS Server BIND auf einem Freifunk Gateway. +Die Gateways agieren lediglich als Slave-DNS Server. + +- installiert BIND Pakete +- schreibt named.conf + named.conf.options + named.conf.logging +- schreibt named.conf.icvpn nur wenn noch nicht vorhanden +- schreibt für jedes Mesh eine Konfigurationsdatei named.conf.$site_code + - Forward-Zones müssen im `meshes`-Dict angegeben werden + - Reverse DNS Zones werden automatisch aus den benutzten IP-Subnetzen erzeugt + +## Benötigte Variablen + +- Dictionary `meshes` +´´´ +meshes: + xx: +... + site_code: # string + ipv4_network: + ipv6: + ula: + - # ULA-Prefix + - ... + dns: + master: # IP-Adresse des DNS Masters + forward_zones: + $zone: # DNS-Domain + master: # optional: IP-Adresse des DNS Masters, wenn die vom übergeordneten abweicht. + +´´´ +- Variable `icvpn_ipv4_transfer_net` +- Variable `icvpn_ipv6_transfer_net` +- Host Variable `magic` + +## Benötigte roles + +- git-repos diff --git a/roles/service-bind-slave/handlers/main.yml b/roles/service-bind-slave/handlers/main.yml new file mode 100644 index 0000000..e1b2000 --- /dev/null +++ b/roles/service-bind-slave/handlers/main.yml @@ -0,0 +1,9 @@ +--- +- name: reload systemd + systemd: + daemon_reload: yes + +- name: restart bind9 + systemd: + name: bind9 + state: restarted diff --git a/roles/service-bind-slave/meta/main.yml b/roles/service-bind-slave/meta/main.yml new file mode 100644 index 0000000..9a46e8e --- /dev/null +++ b/roles/service-bind-slave/meta/main.yml @@ -0,0 +1,3 @@ +--- +dependencies: + - { role: git-repos } diff --git a/roles/service-bind-slave/tasks/main.yml b/roles/service-bind-slave/tasks/main.yml new file mode 100644 index 0000000..5327055 --- /dev/null +++ b/roles/service-bind-slave/tasks/main.yml @@ -0,0 +1,67 @@ +--- +- name: install dns server packages + apt: + name: "{{ item }}" + state: present + notify: reload systemd + with_items: + - bind9 + - bind9-doc + - bind9utils + +- name: enable systemd unit bind9 + systemd: + name: bind9 + enabled: yes + +- name: write named.conf + template: + src: named.conf.j2 + dest: /etc/bind/named.conf + owner: root + group: bind + mode: 0644 + notify: restart bind9 + +- name: write named.conf.options + template: + src: named.conf.options.j2 + dest: /etc/bind/named.conf.options + owner: root + group: bind + mode: 0644 + notify: restart bind9 + +- name: write named.conf.logging + template: + src: named.conf.logging.j2 + dest: /etc/bind/named.conf.logging + owner: root + group: bind + mode: 0644 + notify: restart bind9 + +- name: write named.conf for meshes + template: + src: named.conf.mesh.j2 + dest: /etc/bind/named.conf.{{ item.value.site_code }} + owner: root + group: bind + mode: 0644 + notify: restart bind9 + with_dict: "{{ meshes }}" + +- name: write initial icvpn bind config + shell: /usr/bin/python3 /home/admin/clones/icvpn-scripts/mkdns -f bind -x mwu -x bingen -s /home/admin/clones/icvpn-meta > /etc/bind/named.conf.icvpn + args: + chdir: /home/admin/clones/icvpn-scripts + creates: /etc/bind/named.conf.icvpn + notify: restart bind9 + +- name: set file attributes for icvpn config + file: + path: /etc/bind/ + mode: 0644 + owner: root + group: bird + notify: restart bind9 diff --git a/roles/service-bind-slave/templates/named.conf.j2 b/roles/service-bind-slave/templates/named.conf.j2 new file mode 100644 index 0000000..04a4465 --- /dev/null +++ b/roles/service-bind-slave/templates/named.conf.j2 @@ -0,0 +1,11 @@ +// +// {{ ansible_managed }} +// + +include "/etc/bind/named.conf.options"; +include "/etc/bind/named.conf.default-zones"; +include "/etc/bind/named.conf.logging"; +{% for mesh_id, mesh_value in meshes.iteritems() %} +include "/etc/bind/named.conf.{{ mesh_value.site_code }}"; +{% endfor %} +include "/etc/bind/named.conf.icvpn"; diff --git a/roles/service-bind-slave/templates/named.conf.logging.j2 b/roles/service-bind-slave/templates/named.conf.logging.j2 new file mode 100644 index 0000000..21908ef --- /dev/null +++ b/roles/service-bind-slave/templates/named.conf.logging.j2 @@ -0,0 +1,9 @@ +// +// {{ ansible_managed }} +// + +logging { + channel null { null; }; + category default { null; }; +}; + diff --git a/roles/service-bind-slave/templates/named.conf.mesh.j2 b/roles/service-bind-slave/templates/named.conf.mesh.j2 new file mode 100644 index 0000000..2daf882 --- /dev/null +++ b/roles/service-bind-slave/templates/named.conf.mesh.j2 @@ -0,0 +1,58 @@ +// +// {{ ansible_managed }} +// + +// ACLs +masters "ns-master-{{ item.value.site_code }}" { + {{ item.value.dns.master }}; +}; + +{% for zone_id, zone_value in item.value.dns.forward_zones.iteritems() %} +{% if zone_value.master is defined %} +masters "ns-master-{{ zone_id }}" { + {{ zone_value.master }}; +}; + +{% endif %} +{% endfor %} + +acl "intern-{{ item.value.site_code }}" { + {{ item.value.ipv4_network | ipaddr('net') | ipaddr('network/prefix') }}; +{% for prefix in item.value.ipv6.ula %} + {{ prefix | ipaddr('net') | ipaddr('network/prefix') }}; +{% endfor %} +}; + +// DNS forward zones for {{ item.value.site_code }} +{% for zone_id, zone_value in item.value.dns.forward_zones.iteritems() %} +zone "{{ zone_id }}." { + type slave; + file "{{ zone_id }}.db"; +{% if zone_value.master is defined %} + masters { ns-master-{{ zone_id }}; }; +{% else %} + masters { ns-master-{{ item.value.site_code }}; }; +{% endif %} +}; +{% if not loop.last %} + +{% endif %} +{% endfor %} + +// DNS reverse zones for {{ item.value.site_code }} +zone "{{ item.value.ipv4_network | ipaddr('net') | ipaddr('revdns') }}" { + type slave; + file "{{ item.value.ipv4_network | ipaddr('net') | ipaddr('revdns') }}"; + masters { ns-master-{{ item.value.site_code }}; }; +}; + +{% for prefix in item.value.ipv6.ula %} +zone "{{ prefix | ipaddr('net') | ipaddr('revdns') }}" { + type slave; + file "{{ prefix | ipaddr('net') | ipaddr('revdns') }}"; + masters { ns-master-{{ item.value.site_code }}; }; +}; +{% if not loop.last %} + +{% endif %} +{% endfor %} diff --git a/roles/service-bind-slave/templates/named.conf.options.j2 b/roles/service-bind-slave/templates/named.conf.options.j2 new file mode 100644 index 0000000..1fec575 --- /dev/null +++ b/roles/service-bind-slave/templates/named.conf.options.j2 @@ -0,0 +1,37 @@ +// +// {{ ansible_managed }} +// +options { + directory "/var/cache/bind"; + + dnssec-validation no; + auth-nxdomain no; + + allow-query { any; }; + allow-recursion { + 127.0.0.1; + ::1; +{% for mesh_id, mesh_value in meshes.iteritems() %} + intern-{{ mesh_value.site_code }}; +{% endfor %} + }; + allow-transfer { any; }; + + listen-on { + 127.0.0.1; +{% for mesh_id, mesh_value in meshes.iteritems() %} + {{ mesh_value.ipv4_network | ipaddr('net') | ipaddr(magic) | ipaddr('address') }}; +{% endfor %} + {{ icvpn_ipv4_transfer_net | ipaddr('net') | ipsubnet(24, 37) | ipaddr(magic) | ipaddr('address') }}; + }; + + listen-on-v6 { + ::1; +{% for mesh_id, mesh_value in meshes.iteritems() %} +{% for ip in mesh_value.ipv6.ula %} + {{ ip | ipaddr('net') | ipsubnet(64, 0) | ipaddr(magic) }}; +{% endfor %} +{% endfor %} + {{ icvpn_ipv6_transfer_net | ipaddr('net') | ipsubnet(112, 37) | ipaddr(magic) | ipaddr('address') }}; + }; +};