Move libexpat, unbound into core and introduce hnsd
[librecmc/librecmc.git] / package / network / services / unbound / files / unbound.sh
1 #!/bin/sh
2 ##############################################################################
3 #
4 # This program is free software; you can redistribute it and/or modify
5 # it under the terms of the GNU General Public License version 2 as
6 # published by the Free Software Foundation.
7 #
8 # This program is distributed in the hope that it will be useful,
9 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 # GNU General Public License for more details.
12 #
13 # Copyright (C) 2016 Eric Luehrsen
14 #
15 ##############################################################################
16 #
17 # Unbound is a full featured recursive server with many options. The UCI
18 # provided tries to simplify and bundle options. This should make Unbound
19 # easier to deploy. Even light duty routers may resolve recursively instead of
20 # depending on a stub with the ISP. The UCI also attempts to replicate dnsmasq
21 # features as used in base LEDE/OpenWrt. If there is a desire for more
22 # detailed tuning, then manual conf file overrides are also made available.
23 #
24 ##############################################################################
25
26 UB_B_SLAAC6_MAC=0
27 UB_B_DNSSEC=0
28 UB_B_DNS64=0
29 UB_B_EXT_STATS=0
30 UB_B_GATE_NAME=0
31 UB_B_HIDE_BIND=1
32 UB_B_LOCL_BLCK=0
33 UB_B_LOCL_SERV=1
34 UB_B_MAN_CONF=0
35 UB_B_NTP_BOOT=1
36 UB_B_QUERY_MIN=0
37 UB_B_QRY_MINST=0
38 UB_B_AUTH_ROOT=0
39
40 UB_D_CONTROL=0
41 UB_D_DOMAIN_TYPE=static
42 UB_D_DHCP_LINK=none
43 UB_D_EXTRA_DNS=0
44 UB_D_LAN_FQDN=0
45 UB_D_PRIV_BLCK=1
46 UB_D_PROTOCOL=mixed
47 UB_D_RESOURCE=small
48 UB_D_RECURSION=passive
49 UB_D_VERBOSE=1
50 UB_D_WAN_FQDN=0
51
52 UB_IP_DNS64="64:ff9b::/96"
53
54 UB_N_EDNS_SIZE=1280
55 UB_N_RX_PORT=53
56 UB_N_ROOT_AGE=9
57
58 UB_TTL_MIN=120
59 UB_TXT_DOMAIN=lan
60 UB_TXT_HOSTNAME=thisrouter
61
62 ##############################################################################
63
64 # reset as a combo with UB_B_NTP_BOOT and some time stamp files
65 UB_B_READY=1
66
67 # keep track of assignments during inserted resource records
68 UB_LIST_NETW_ALL=""
69 UB_LIST_NETW_LAN=""
70 UB_LIST_NETW_WAN=""
71 UB_LIST_INSECURE=""
72 UB_LIST_ZONE_SERVERS=""
73 UB_LIST_ZONE_NAMES=""
74
75 ##############################################################################
76
77 . /lib/functions.sh
78 . /lib/functions/network.sh
79
80 . /usr/lib/unbound/defaults.sh
81 . /usr/lib/unbound/dnsmasq.sh
82 . /usr/lib/unbound/iptools.sh
83
84 ##############################################################################
85
86 bundle_all_networks() {
87   local cfg="$1"
88   local ifname ifdashname validip
89   local subnet subnets subnets4 subnets6
90
91   network_get_subnets  subnets4 "$cfg"
92   network_get_subnets6 subnets6 "$cfg"
93   network_get_device   ifname   "$cfg"
94
95   ifdashname="${ifname//./-}"
96   subnets="$subnets4 $subnets6"
97
98
99   if [ -n "$subnets" ] ; then
100     for subnet in $subnets ; do
101       validip=$( valid_subnet_any $subnet )
102
103
104       if [ "$validip" = "ok" ] ; then
105         UB_LIST_NETW_ALL="$UB_LIST_NETW_ALL $ifdashname@$subnet"
106       fi
107     done
108   fi
109 }
110
111 ##############################################################################
112
113 bundle_lan_networks() {
114   local cfg="$1"
115   local ifsubnet ifname ifdashname ignore
116
117   config_get_bool    ignore "$cfg" ignore 0
118   network_get_device ifname "$cfg"
119   ifdashname="${ifname//./-}"
120
121
122   if [ "$ignore" -eq 0 -a -n "$ifdashname" -a -n "$UB_LIST_NETW_ALL" ] ; then
123     for ifsubnet in $UB_LIST_NETW_ALL ; do
124       case $ifsubnet in
125         "${ifdashname}"@*)
126           # Special GLA protection for local block; ULA protected as a catagory
127           UB_LIST_NETW_LAN="$UB_LIST_NETW_LAN $ifsubnet"
128           ;;
129       esac
130     done
131   fi
132 }
133
134 ##############################################################################
135
136 bundle_wan_networks() {
137   local ifsubnet
138
139
140   if [ -n "$UB_LIST_NETW_ALL" ] ; then
141     for ifsubnet in $UB_LIST_NETW_ALL ; do
142       case $UB_LIST_NETW_LAN in
143         *"${ifsubnet}"*)
144           # If LAN, then not WAN ...
145           ;;
146
147         *)
148           UB_LIST_NETW_WAN="$UB_LIST_NETW_WAN $ifsubnet"
149           ;;
150       esac
151     done
152   fi
153 }
154
155 ##############################################################################
156
157 bundle_resolv_conf_servers() {
158   local resolvers=$( awk '/nameserver/ { print $2 }' /tmp/resolv.conf.auto )
159   UB_LIST_ZONE_SERVERS="$UB_LIST_ZONE_SERVERS $resolvers"
160 }
161
162 ##############################################################################
163
164 bundle_zone_names() {
165   UB_LIST_ZONE_NAMES="$UB_LIST_ZONE_NAMES $1"
166 }
167
168 ##############################################################################
169
170 bundle_zone_servers() {
171   UB_LIST_ZONE_SERVERS="$UB_LIST_ZONE_SERVERS $1"
172 }
173
174 ##############################################################################
175
176 bundle_domain_insecure() {
177   UB_LIST_INSECURE="$UB_LIST_INSECURE $1"
178 }
179
180 ##############################################################################
181
182 unbound_mkdir() {
183   local filestuff
184
185
186   if [ "$UB_D_DHCP_LINK" = "odhcpd" ] ; then
187     local dhcp_origin=$( uci_get dhcp.@odhcpd[0].leasefile )
188     local dhcp_dir=$( dirname $dhcp_origin )
189
190
191     if [ ! -d "$dhcp_dir" ] ; then
192       # make sure odhcpd has a directory to write (not done itself, yet)
193       mkdir -p "$dhcp_dir"
194     fi
195   fi
196
197
198   if [ -f $UB_RKEY_FILE ] ; then
199     filestuff=$( cat $UB_RKEY_FILE )
200
201
202     case "$filestuff" in
203       *"state=2 [  VALID  ]"*)
204         # Lets not lose RFC 5011 tracking if we don't have to
205         cp -p $UB_RKEY_FILE $UB_RKEY_FILE.keep
206         ;;
207     esac
208   fi
209
210
211   # Blind copy /etc/unbound to /var/lib/unbound
212   mkdir -p $UB_VARDIR
213   rm -f $UB_VARDIR/dhcp_*
214   touch $UB_TOTAL_CONF
215   cp -p /etc/unbound/* $UB_VARDIR/
216
217
218   if [ ! -f $UB_RHINT_FILE ] ; then
219     if [ -f /usr/share/dns/root.hints ] ; then
220       # Debian-like package dns-root-data
221       cp -p /usr/share/dns/root.hints $UB_RHINT_FILE
222
223     elif [ "$UB_B_READY" -eq 0 ] ; then
224       logger -t unbound -s "default root hints (built in root-servers.net)"
225     fi
226   fi
227
228
229   if [ ! -f $UB_RKEY_FILE ] ; then
230     if [ -f /usr/share/dns/root.key ] ; then
231       # Debian-like package dns-root-data
232       cp -p /usr/share/dns/root.key $UB_RKEY_FILE
233
234     elif [ -x $UB_ANCHOR ] ; then
235       $UB_ANCHOR -a $UB_RKEY_FILE
236
237     elif [ "$UB_B_READY" -eq 0 ] ; then
238       logger -t unbound -s "default trust anchor (built in root DS record)"
239     fi
240   fi
241
242
243   if [ -f $UB_RKEY_FILE.keep ] ; then
244     # root.key.keep is reused if newest
245     cp -u $UB_RKEY_FILE.keep $UB_RKEY_FILE
246     rm -f $UB_RKEY_FILE.keep
247   fi
248
249
250   if [ -f $UB_TLS_ETC_FILE ] ; then
251     # copy the cert bundle into jail
252     cp -p $UB_TLS_ETC_FILE $UB_TLS_FWD_FILE
253   fi
254
255
256   # Ensure access and prepare to jail
257   chown -R unbound:unbound $UB_VARDIR
258   chmod 755 $UB_VARDIR
259   chmod 644 $UB_VARDIR/*
260
261
262   if [ -f $UB_CTLKEY_FILE -o -f $UB_CTLPEM_FILE \
263     -o -f $UB_SRVKEY_FILE -o -f $UB_SRVPEM_FILE ] ; then
264     # Keys (some) exist already; do not create new ones
265     chmod 640 $UB_CTLKEY_FILE $UB_CTLPEM_FILE \
266               $UB_SRVKEY_FILE $UB_SRVPEM_FILE
267
268   elif [ -x /usr/sbin/unbound-control-setup ] ; then
269     case "$UB_D_CONTROL" in
270       [2-3])
271         # unbound-control-setup for encrypt opt. 2 and 3, but not 4 "static"
272         /usr/sbin/unbound-control-setup -d $UB_VARDIR
273
274         chown -R unbound:unbound  $UB_CTLKEY_FILE $UB_CTLPEM_FILE \
275                                   $UB_SRVKEY_FILE $UB_SRVPEM_FILE
276
277         chmod 640 $UB_CTLKEY_FILE $UB_CTLPEM_FILE \
278                   $UB_SRVKEY_FILE $UB_SRVPEM_FILE
279
280         cp -p $UB_CTLKEY_FILE /etc/unbound/unbound_control.key
281         cp -p $UB_CTLPEM_FILE /etc/unbound/unbound_control.pem
282         cp -p $UB_SRVKEY_FILE /etc/unbound/unbound_server.key
283         cp -p $UB_SRVPEM_FILE /etc/unbound/unbound_server.pem
284         ;;
285     esac
286   fi
287
288
289   if [ -f "$UB_TIME_FILE" ] ; then
290     # NTP is done so its like you actually had an RTC
291     UB_B_READY=1
292     UB_B_NTP_BOOT=0
293
294   elif [ "$UB_B_NTP_BOOT" -eq 0 ] ; then
295     # time is considered okay on this device (ignore /etc/hotplug/ntpd/unbound)
296     date -Is > $UB_TIME_FILE
297     UB_B_READY=0
298     UB_B_NTP_BOOT=0
299
300   else
301     # DNSSEC-TIME will not reconcile
302     UB_B_READY=0
303     UB_B_NTP_BOOT=1
304   fi
305 }
306
307 ##############################################################################
308
309 unbound_control() {
310   echo "# $UB_CTRL_CONF generated by UCI $( date -Is )" > $UB_CTRL_CONF
311
312
313   if [ "$UB_D_CONTROL" -gt 1 ] ; then
314     if [ ! -f $UB_CTLKEY_FILE -o ! -f $UB_CTLPEM_FILE \
315       -o ! -f $UB_SRVKEY_FILE -o ! -f $UB_SRVPEM_FILE ] ; then
316       # Key files need to be present; if unbound-control-setup was found, then
317       # they might have been made during unbound_makedir() above.
318       UB_D_CONTROL=0
319     fi
320   fi
321
322
323   case "$UB_D_CONTROL" in
324     1)
325       {
326         # Local Host Only Unencrypted Remote Control
327         echo "remote-control:"
328         echo "  control-enable: yes"
329         echo "  control-use-cert: no"
330         echo "  control-interface: 127.0.0.1"
331         echo "  control-interface: ::1"
332         echo
333       } >> $UB_CTRL_CONF
334       ;;
335
336     2)
337       {
338         # Local Host Only Encrypted Remote Control
339         echo "remote-control:"
340         echo "  control-enable: yes"
341         echo "  control-use-cert: yes"
342         echo "  control-interface: 127.0.0.1"
343         echo "  control-interface: ::1"
344         echo "  server-key-file: $UB_SRVKEY_FILE"
345         echo "  server-cert-file: $UB_SRVPEM_FILE"
346         echo "  control-key-file: $UB_CTLKEY_FILE"
347         echo "  control-cert-file: $UB_CTLPEM_FILE"
348         echo
349       } >> $UB_CTRL_CONF
350       ;;
351
352     [3-4])
353       {
354         # Network Encrypted Remote Control
355         # (3) may auto setup and (4) must have static key/pem files
356         # TODO: add UCI list for interfaces to bind
357         echo "remote-control:"
358         echo "  control-enable: yes"
359         echo "  control-use-cert: yes"
360         echo "  control-interface: 0.0.0.0"
361         echo "  control-interface: ::0"
362         echo "  server-key-file: $UB_SRVKEY_FILE"
363         echo "  server-cert-file: $UB_SRVPEM_FILE"
364         echo "  control-key-file: $UB_CTLKEY_FILE"
365         echo "  control-cert-file: $UB_CTLPEM_FILE"
366         echo
367       } >> $UB_CTRL_CONF
368       ;;
369   esac
370 }
371
372 ##############################################################################
373
374 unbound_zone() {
375   local cfg=$1
376   local servers_ip=""
377   local servers_host=""
378   local zone_sym zone_name zone_type zone_enabled zone_file
379   local tls_upstream fallback
380   local server port tls_port tls_index tls_suffix url_dir
381
382   if [ ! -f "$UB_ZONE_CONF" ] ; then
383     echo "# $UB_ZONE_CONF generated by UCI $( date -Is )" > $UB_ZONE_CONF
384   fi
385
386
387   config_get_bool zone_enabled  "$cfg" enabled 0
388
389
390   if [ "$zone_enabled" -eq 1 ] ; then
391     # these lists are built for each zone; empty to start
392     UB_LIST_ZONE_NAMES=""
393     UB_LIST_ZONE_SERVERS=""
394
395     config_get  zone_type "$cfg" zone_type ""
396     config_get  port      "$cfg" port ""
397     config_get  tls_index "$cfg" tls_index ""
398     config_get  tls_port  "$cfg" tls_port 853
399     config_get  url_dir   "$cfg" url_dir ""
400
401     config_get_bool resolv_conf   "$cfg" resolv_conf 0
402     config_get_bool fallback      "$cfg" fallback 1
403     config_get_bool tls_upstream  "$cfg" tls_upstream 0
404
405     config_list_foreach "$cfg" zone_name  bundle_zone_names
406     config_list_foreach "$cfg" server     bundle_zone_servers
407
408     # string formating for Unbound syntax
409     tls_suffix="${tls_port:+@${tls_port}${tls_index:+#${tls_index}}}"
410     [ "$fallback" -eq 0 ]     && fallback=no     || fallback=yes
411     [ "$tls_upstream" -eq 0 ] && tls_upstream=no || tls_upstream=yes
412
413
414     if [ $resolv_conf -eq 1 ] ; then
415       bundle_resolv_conf_servers
416     fi
417
418   else
419     zone_type=skip
420   fi
421
422
423   case $zone_type in
424     auth_zone)
425       if [ -n "$UB_LIST_ZONE_NAMES" \
426            -a \( -n "$url_dir" -o -n "$UB_LIST_ZONE_SERVERS" \) ] ; then
427         for zone_name in $UB_LIST_ZONE_NAMES ; do
428           if [ "$zone_name" = "." ] ; then
429             zone_sym=.
430             zone_name=root
431             zone_file=root.zone
432           else
433             zone_sym=$zone_name
434             zone_file=$zone_name.zone
435             zone_file=${zone_file//../.}
436           fi
437
438
439           {
440             # generate an auth-zone: with switches for prefetch cache
441             echo "auth-zone:"
442             echo "  name: $zone_sym"
443             for server in $UB_LIST_ZONE_SERVERS ; do
444               echo "  master: $server${port:+@${port}}"
445             done
446             if [ -n "$url_dir" ] ; then
447               echo "  url: $url_dir$zone_file"
448             fi
449             echo "  fallback-enabled: $fallback"
450             echo "  for-downstream: no"
451             echo "  for-upstream: yes"
452             echo "  zonefile: $zone_file"
453             echo
454           } >> $UB_ZONE_CONF
455         done
456       fi
457       ;;
458
459     forward_zone)
460       if [ ! -f $UB_TLS_FWD_FILE -a "$tls_upstream" = "yes" ] ; then
461         logger -p 4 -t unbound -s \
462           "Forward-zone TLS benefits from authentication in package 'ca-bundle'"
463       fi
464
465
466       if [ -n "$UB_LIST_ZONE_NAMES" -a -n "$UB_LIST_ZONE_SERVERS" ] ; then
467         for server in $UB_LIST_ZONE_SERVERS ; do
468           if [ "$( valid_subnet_any $server )" = "not" ] ; then
469             case $server in
470               *@[0-9]*)
471                 # unique Unbound option for server host name
472                 servers_host="$servers_host $server"
473                 ;;
474
475               *)
476                 if [ "$tls_upstream" = "yes" ] ; then
477                   servers_host="$servers_host $server${tls_port:+@${tls_port}}"
478                 else
479                   servers_host="$servers_host $server${port:+@${port}}"
480                 fi
481             esac
482
483           else
484             case $server in
485               *[0-9]@[0-9]*)
486                 # unique Unbound option for server address
487                 servers_ip="$servers_ip $server"
488                 ;;
489
490               *)
491                 if [ "$tls_upstream" = "yes" ] ; then
492                   servers_ip="$servers_ip $server$tls_suffix"
493                 else
494                   servers_ip="$servers_ip $server${port:+@${port}}"
495                 fi
496             esac
497           fi
498         done
499
500
501         for zonename in $UB_LIST_ZONE_NAMES ; do
502           {
503             # generate a forward-zone with or without tls
504             echo "forward-zone:"
505             echo "  name: $zonename"
506             for server in $servers_host ; do
507               echo "  forward-host: $server"
508             done
509             for server in $servers_ip ; do
510               echo "  forward-addr: $server"
511             done
512             echo "  forward-first: $fallback"
513             echo "  forward-tls-upstream: $tls_upstream"
514             echo
515           } >> $UB_ZONE_CONF
516         done
517       fi
518       ;;
519
520     stub_zone)
521       if [ -n "$UB_LIST_ZONE_NAMES" -a -n "$UB_LIST_ZONE_SERVERS" ] ; then
522         for zonename in $UB_LIST_ZONE_NAMES ; do
523           {
524             # generate a stub-zone: or ensure short cut to authority NS
525             echo "stub-zone:"
526             echo "  name: $zonename"
527             for server in $UB_LIST_ZONE_SERVERS ; do
528               echo "  stub-addr: $server${port:+@${port}}"
529             done
530             echo "  stub-first: $fallback"
531             echo
532           } >> $UB_ZONE_CONF
533         done
534       fi
535       ;;
536   esac
537 }
538
539 ##############################################################################
540
541 unbound_conf() {
542   local rt_mem rt_conn rt_buff modulestring domain ifsubnet nsubnet
543
544   {
545     # server: for this whole function
546     echo "# $UB_CORE_CONF generated by UCI $( date -Is )"
547     echo "server:"
548     echo "  username: unbound"
549     echo "  chroot: $UB_VARDIR"
550     echo "  directory: $UB_VARDIR"
551     echo "  pidfile: $UB_PIDFILE"
552   } > $UB_CORE_CONF
553
554
555   if [ -f "$UB_TLS_FWD_FILE" ] ; then
556     # TLS cert bundle for upstream forwarder and https zone files
557     # This is loaded before drop to root, so pull from /etc/ssl
558     echo "  tls-cert-bundle: $UB_TLS_FWD_FILE" >> $UB_CORE_CONF
559   fi
560
561
562   if [ -f "$UB_RHINT_FILE" ] ; then
563     # Optional hints if found
564     echo "  root-hints: $UB_RHINT_FILE" >> $UB_CORE_CONF
565   fi
566
567
568   if [ "$UB_B_DNSSEC" -gt 0 -a -f "$UB_RKEY_FILE" ] ; then
569     {
570       echo "  auto-trust-anchor-file: $UB_RKEY_FILE"
571       echo
572     } >> $UB_CORE_CONF
573
574   else
575     echo >> $UB_CORE_CONF
576   fi
577
578
579   {
580     # No threading
581     echo "  num-threads: 1"
582     echo "  msg-cache-slabs: 1"
583     echo "  rrset-cache-slabs: 1"
584     echo "  infra-cache-slabs: 1"
585     echo "  key-cache-slabs: 1"
586     echo
587     # Logging
588     echo "  use-syslog: yes"
589     echo "  statistics-interval: 0"
590     echo "  statistics-cumulative: no"
591   } >> $UB_CORE_CONF
592
593
594   if [ "$UB_D_VERBOSE" -ge 0 -a "$UB_D_VERBOSE" -le 5 ] ; then
595     echo "  verbosity: $UB_D_VERBOSE" >> $UB_CORE_CONF
596   fi
597
598
599   if [ "$UB_B_EXT_STATS" -gt 0 ] ; then
600     {
601       # Log More
602       echo "  extended-statistics: yes"
603       echo
604     } >> $UB_CORE_CONF
605
606   else
607     {
608       # Log Less
609       echo "  extended-statistics: no"
610       echo
611     } >> $UB_CORE_CONF
612   fi
613
614
615   case "$UB_D_PROTOCOL" in
616     ip4_only)
617       {
618         echo "  edns-buffer-size: $UB_N_EDNS_SIZE"
619         echo "  port: $UB_N_RX_PORT"
620         echo "  outgoing-port-permit: 10240-65535"
621         echo "  interface: 0.0.0.0"
622         echo "  interface: ::0"
623         echo "  outgoing-interface: 0.0.0.0"
624         echo "  do-ip4: yes"
625         echo "  do-ip6: no"
626         echo
627       } >> $UB_CORE_CONF
628       ;;
629
630     ip6_only)
631       {
632         echo "  edns-buffer-size: $UB_N_EDNS_SIZE"
633         echo "  port: $UB_N_RX_PORT"
634         echo "  outgoing-port-permit: 10240-65535"
635         echo "  interface: 0.0.0.0"
636         echo "  interface: ::0"
637         echo "  outgoing-interface: ::0"
638         echo "  do-ip4: no"
639         echo "  do-ip6: yes"
640         echo
641       } >> $UB_CORE_CONF
642       ;;
643
644     ip6_prefer)
645       {
646         echo "  edns-buffer-size: $UB_N_EDNS_SIZE"
647         echo "  port: $UB_N_RX_PORT"
648         echo "  outgoing-port-permit: 10240-65535"
649         echo "  interface: 0.0.0.0"
650         echo "  interface: ::0"
651         echo "  outgoing-interface: 0.0.0.0"
652         echo "  outgoing-interface: ::0"
653         echo "  do-ip4: yes"
654         echo "  do-ip6: yes"
655         echo "  prefer-ip6: yes"
656         echo
657       } >> $UB_CORE_CONF
658       ;;
659
660     mixed)
661       {
662         # Interface Wildcard (access contol handled by "option local_service")
663         echo "  edns-buffer-size: $UB_N_EDNS_SIZE"
664         echo "  port: $UB_N_RX_PORT"
665         echo "  outgoing-port-permit: 10240-65535"
666         echo "  interface: 0.0.0.0"
667         echo "  interface: ::0"
668         echo "  outgoing-interface: 0.0.0.0"
669         echo "  outgoing-interface: ::0"
670         echo "  do-ip4: yes"
671         echo "  do-ip6: yes"
672         echo
673       } >> $UB_CORE_CONF
674       ;;
675
676     *)
677       if [ "$UB_B_READY" -eq 0 ] ; then
678         logger -t unbound -s "default protocol configuration"
679       fi
680
681
682       {
683         # outgoing-interface has useful defaults; incoming is localhost though
684         echo "  edns-buffer-size: $UB_N_EDNS_SIZE"
685         echo "  port: $UB_N_RX_PORT"
686         echo "  outgoing-port-permit: 10240-65535"
687         echo "  interface: 0.0.0.0"
688         echo "  interface: ::0"
689         echo
690       } >> $UB_CORE_CONF
691       ;;
692   esac
693
694
695   {
696     # Other harding and options for an embedded router
697     echo "  harden-short-bufsize: yes"
698     echo "  harden-large-queries: yes"
699     echo "  harden-glue: yes"
700     echo "  harden-below-nxdomain: no"
701     echo "  harden-referral-path: no"
702     echo "  use-caps-for-id: no"
703     echo
704   } >> $UB_CORE_CONF
705
706
707   case "$UB_D_RESOURCE" in
708     # Tiny - Unbound's recommended cheap hardware config
709     tiny)   rt_mem=1  ; rt_conn=2  ; rt_buff=1 ;;
710     # Small - Half RRCACHE and open ports
711     small)  rt_mem=8  ; rt_conn=10 ; rt_buff=2 ;;
712     # Medium - Nearly default but with some added balancintg
713     medium) rt_mem=16 ; rt_conn=20 ; rt_buff=4 ;;
714     # Large - Double medium
715     large)  rt_mem=32 ; rt_conn=40 ; rt_buff=4 ;;
716     # Whatever unbound does
717     *) rt_mem=0 ; rt_conn=0 ;;
718   esac
719
720
721   if [ "$rt_mem" -gt 0 ] ; then
722     {
723       # Set memory sizing parameters
724       echo "  msg-buffer-size: $(($rt_buff*8192))"
725       echo "  outgoing-range: $(($rt_conn*64))"
726       echo "  num-queries-per-thread: $(($rt_conn*32))"
727       echo "  outgoing-num-tcp: $(($rt_conn))"
728       echo "  incoming-num-tcp: $(($rt_conn))"
729       echo "  rrset-cache-size: $(($rt_mem*256))k"
730       echo "  msg-cache-size: $(($rt_mem*128))k"
731       echo "  key-cache-size: $(($rt_mem*128))k"
732       echo "  neg-cache-size: $(($rt_mem*64))k"
733       echo "  infra-cache-numhosts: $(($rt_mem*256))"
734       echo
735     } >> $UB_CORE_CONF
736
737   elif [ "$UB_B_READY" -eq 0 ] ; then
738     logger -t unbound -s "default memory configuration"
739   fi
740
741
742   # Assembly of module-config: options is tricky; order matters
743   modulestring="iterator"
744
745
746   if [ "$UB_B_DNSSEC" -gt 0 ] ; then
747     if [ "$UB_B_NTP_BOOT" -gt 0 ] ; then
748       # DNSSEC chicken and egg with getting NTP time
749       echo "  val-override-date: -1" >> $UB_CORE_CONF
750     fi
751
752
753     {
754       echo "  harden-dnssec-stripped: yes"
755       echo "  val-clean-additional: yes"
756       echo "  ignore-cd-flag: yes"
757     } >> $UB_CORE_CONF
758
759
760     modulestring="validator $modulestring"
761   fi
762
763
764   if [ "$UB_B_DNS64" -gt 0 ] ; then
765     echo "  dns64-prefix: $UB_IP_DNS64" >> $UB_CORE_CONF
766
767     modulestring="dns64 $modulestring"
768   fi
769
770
771   {
772     # Print final module string
773     echo "  module-config: \"$modulestring\""
774     echo
775   }  >> $UB_CORE_CONF
776
777
778   case "$UB_D_RECURSION" in
779     passive)
780       {
781         # Some query privacy but "strict" will break some servers
782         if [ "$UB_B_QRY_MINST" -gt 0 \
783           -a "$UB_B_QUERY_MIN" -gt 0 ] ; then
784           echo "  qname-minimisation: yes"
785           echo "  qname-minimisation-strict: yes"
786         elif [ "$UB_B_QUERY_MIN" -gt 0 ] ; then
787           echo "  qname-minimisation: yes"
788         else
789           echo "  qname-minimisation: no"
790         fi
791         # Use DNSSEC to quickly understand NXDOMAIN ranges
792         if [ "$UB_B_DNSSEC" -gt 0 ] ; then
793           echo "  aggressive-nsec: yes"
794           echo "  prefetch-key: no"
795         fi
796         # On demand fetching
797         echo "  prefetch: no"
798         echo "  target-fetch-policy: \"0 0 0 0 0\""
799         echo
800       } >> $UB_CORE_CONF
801       ;;
802
803     aggressive)
804       {
805         # Some query privacy but "strict" will break some servers
806         if [ "$UB_B_QRY_MINST" -gt 0 \
807           -a "$UB_B_QUERY_MIN" -gt 0 ] ; then
808           echo "  qname-minimisation: yes"
809           echo "  qname-minimisation-strict: yes"
810         elif [ "$UB_B_QUERY_MIN" -gt 0 ] ; then
811           echo "  qname-minimisation: yes"
812         else
813           echo "  qname-minimisation: no"
814         fi
815         # Use DNSSEC to quickly understand NXDOMAIN ranges
816         if [ "$UB_B_DNSSEC" -gt 0 ] ; then
817           echo "  aggressive-nsec: yes"
818           echo "  prefetch-key: yes"
819         fi
820         # Prefetch what can be
821         echo "  prefetch: yes"
822         echo "  target-fetch-policy: \"3 2 1 0 0\""
823         echo
824       } >> $UB_CORE_CONF
825       ;;
826
827     *)
828       if [ "$UB_B_READY" -eq 0 ] ; then
829         logger -t unbound -s "default recursion configuration"
830       fi
831       ;;
832   esac
833
834
835   {
836     # Reload records more than 20 hours old
837     # DNSSEC 5 minute bogus cool down before retry
838     # Adaptive infrastructure info kept for 15 minutes
839     echo "  cache-min-ttl: $UB_TTL_MIN"
840     echo "  cache-max-ttl: 72000"
841     echo "  val-bogus-ttl: 300"
842     echo "  infra-host-ttl: 900"
843     echo
844   } >> $UB_CORE_CONF
845
846
847   if [ "$UB_B_HIDE_BIND" -gt 0 ] ; then
848     {
849       # Block server id and version DNS TXT records
850       echo "  hide-identity: yes"
851       echo "  hide-version: yes"
852       echo
853     } >> $UB_CORE_CONF
854   fi
855
856
857   if [ "$UB_D_PRIV_BLCK" -gt 0 ] ; then
858     {
859       # Remove _upstream_ or global reponses with private addresses.
860       # Unbounds own "local zone" and "forward zone" may still use these.
861       # RFC1918, RFC3927, RFC4291, RFC6598, RFC6890
862       echo "  private-address: 10.0.0.0/8"
863       echo "  private-address: 100.64.0.0/10"
864       echo "  private-address: 169.254.0.0/16"
865       echo "  private-address: 172.16.0.0/12"
866       echo "  private-address: 192.168.0.0/16"
867       echo "  private-address: fc00::/7"
868       echo "  private-address: fe80::/10"
869       echo
870     } >> $UB_CORE_CONF
871   fi
872
873
874   if [ -n "$UB_LIST_NETW_LAN" -a "$UB_D_PRIV_BLCK" -gt 1 ] ; then
875     {
876       for ifsubnet in $UB_LIST_NETW_LAN ; do
877         case $ifsubnet in
878           *@[1-9][0-9a-f][0-9a-f][0-9a-f]:*:[0-9a-f]*)
879             # Remove global DNS responses with your local network IP6 GLA
880             echo "  private-address: ${ifsubnet#*@}"
881             ;;
882         esac
883       done
884       echo
885     } >> $UB_CORE_CONF
886   fi
887
888
889   if [ "$UB_B_LOCL_BLCK" -gt 0 ] ; then
890     {
891       # Remove DNS reponses from upstream with loopback IP
892       # Black hole DNS method for ad blocking, so consider...
893       echo "  private-address: 127.0.0.0/8"
894       echo "  private-address: ::1/128"
895       echo
896     } >> $UB_CORE_CONF
897   fi
898
899
900   if  [ -n "$UB_LIST_INSECURE" ] ; then
901     {
902       for domain in $UB_LIST_INSECURE ; do
903         # Except and accept domains without (DNSSEC); work around broken domains
904         echo "  domain-insecure: $domain"
905       done
906       echo
907     } >> $UB_CORE_CONF
908   fi
909
910
911   if [ "$UB_B_LOCL_SERV" -gt 0 -a -n "$UB_LIST_NETW_ALL" ] ; then
912     {
913       for ifsubnet in $UB_LIST_NETW_ALL ; do
914         # Only respond to queries from subnets which have an interface.
915         # Prevent DNS amplification attacks by not responding to the universe.
916         echo "  access-control: ${ifsubnet#*@} allow"
917       done
918       echo "  access-control: 127.0.0.0/8 allow"
919       echo "  access-control: ::1/128 allow"
920       echo "  access-control: fe80::/10 allow"
921       echo
922     } >> $UB_CORE_CONF
923
924   else
925     {
926       echo "  access-control: 0.0.0.0/0 allow"
927       echo "  access-control: ::0/0 allow"
928       echo
929     } >> $UB_CORE_CONF
930   fi
931 }
932
933 ##############################################################################
934
935 unbound_hostname() {
936   local ifsubnet ifarpa ifaddr ifname iffqdn
937   local ulaprefix hostfqdn name names namerec ptrrec
938   local zonetype=0
939
940   echo "# $UB_HOST_CONF generated by UCI $( date -Is )" > $UB_HOST_CONF
941
942
943   if [ "$UB_D_DHCP_LINK" = "dnsmasq" ] ; then
944     {
945       echo "# Local zone is handled by dnsmasq"
946       echo
947     } >> $UB_HOST_CONF
948
949   elif [ -n "$UB_TXT_DOMAIN" \
950          -a \( "$UB_D_WAN_FQDN" -gt 0 -o "$UB_D_LAN_FQDN" -gt 0 \) ] ; then
951     case "$UB_D_DOMAIN_TYPE" in
952       deny|inform_deny|refuse|static)
953         {
954           # type static means only this router has your domain
955           echo "  domain-insecure: $UB_TXT_DOMAIN"
956           echo "  private-domain: $UB_TXT_DOMAIN"
957           echo "  local-zone: $UB_TXT_DOMAIN $UB_D_DOMAIN_TYPE"
958           echo "  local-data: \"$UB_TXT_DOMAIN. $UB_XSOA\""
959           echo "  local-data: \"$UB_TXT_DOMAIN. $UB_XNS\""
960           echo "  local-data: '$UB_TXT_DOMAIN. $UB_XTXT'"
961           echo
962           # avoid upstream involvement in RFC6762
963           echo "  domain-insecure: local"
964           echo "  private-domain: local"
965           echo "  local-zone: local $UB_D_DOMAIN_TYPE"
966           echo "  local-data: \"local. $UB_XSOA\""
967           echo "  local-data: \"local. $UB_XNS\""
968           echo "  local-data: 'local. $UB_LTXT'"
969           echo
970         } >> $UB_HOST_CONF
971         zonetype=2
972         ;;
973
974       transparent|typetransparent)
975         {
976           # transparent will permit forward-zone: or stub-zone: clauses
977           echo "  private-domain: $UB_TXT_DOMAIN"
978           echo "  local-zone: $UB_TXT_DOMAIN $UB_D_DOMAIN_TYPE"
979           echo
980         } >> $UB_HOST_CONF
981         zonetype=1
982         ;;
983     esac
984
985
986     {
987       # Hostname as TLD works, but not transparent through recursion (singular)
988       echo "  domain-insecure: $UB_TXT_HOSTNAME"
989       echo "  private-domain: $UB_TXT_HOSTNAME"
990       echo "  local-zone: $UB_TXT_HOSTNAME static"
991       echo "  local-data: \"$UB_TXT_HOSTNAME. $UB_XSOA\""
992       echo "  local-data: \"$UB_TXT_HOSTNAME. $UB_XNS\""
993       echo "  local-data: '$UB_TXT_HOSTNAME. $UB_XTXT'"
994       echo
995     } >> $UB_HOST_CONF
996
997
998     if [ -n "$UB_LIST_NETW_WAN" ] ; then
999       for ifsubnet in $UB_LIST_NETW_WAN ; do
1000         ifaddr=${ifsubnet#*@}
1001         ifaddr=${ifaddr%/*}
1002         ifarpa=$( host_ptr_any "$ifaddr" )
1003
1004
1005         if [ -n "$ifarpa" ] ; then
1006           if [ "$UB_D_WAN_FQDN" -gt 0 ] ; then
1007             {
1008               # Create a static zone for WAN host record only (singular)
1009               echo "  domain-insecure: $ifarpa"
1010               echo "  private-address: $ifaddr"
1011               echo "  local-zone: $ifarpa static"
1012               echo "  local-data: \"$ifarpa. $UB_XSOA\""
1013               echo "  local-data: \"$ifarpa. $UB_XNS\""
1014               echo "  local-data: '$ifarpa. $UB_MTXT'"
1015               echo
1016             } >> $UB_HOST_CONF
1017
1018           elif [ "$zonetype" -gt 0 ] ; then
1019             {
1020               echo "  local-zone: $ifarpa transparent"
1021               echo
1022             } >> $UB_HOST_CONF
1023           fi
1024         fi
1025       done
1026     fi
1027
1028
1029     if  [ -n "$UB_LIST_NETW_LAN" ] ; then
1030       for ifsubnet in $UB_LIST_NETW_LAN ; do
1031         ifarpa=$( domain_ptr_any "${ifsubnet#*@}" )
1032
1033
1034         if [ -n "$ifarpa" ] ; then
1035           if [ "$zonetype" -eq 2 ] ; then
1036             {
1037               # Do NOT forward queries with your ip6.arpa or in-addr.arpa
1038               echo "  domain-insecure: $ifarpa"
1039               echo "  local-zone: $ifarpa static"
1040               echo "  local-data: \"$ifarpa. $UB_XSOA\""
1041               echo "  local-data: \"$ifarpa. $UB_XNS\""
1042               echo "  local-data: '$ifarpa. $UB_XTXT'"
1043               echo
1044             } >> $UB_HOST_CONF
1045
1046           elif [ "$zonetype" -eq 1 -a "$UB_D_PRIV_BLCK" -eq 0 ] ; then
1047             {
1048               echo "  local-zone: $ifarpa transparent"
1049               echo
1050             } >> $UB_HOST_CONF
1051           fi
1052         fi
1053       done
1054     fi
1055
1056
1057     ulaprefix=$( uci_get network.@globals[0].ula_prefix )
1058     ulaprefix=${ulaprefix%%:/*}
1059     hostfqdn="$UB_TXT_HOSTNAME.$UB_TXT_DOMAIN"
1060
1061
1062     if [ -z "$ulaprefix" ] ; then
1063       # Nonsense so this option isn't globbed below
1064       ulaprefix="fdno:such:addr::"
1065     fi
1066
1067
1068     if [ "$UB_LIST_NETW_LAN" -a "$UB_D_LAN_FQDN" -gt 0 ] ; then
1069       for ifsubnet in $UB_LIST_NETW_LAN ; do
1070         ifaddr=${ifsubnet#*@}
1071         ifaddr=${ifaddr%/*}
1072         ifname=${ifsubnet%@*}
1073         iffqdn="$ifname.$hostfqdn"
1074
1075
1076         if [ "$UB_D_LAN_FQDN" -eq 4 ] ; then
1077           names="$iffqdn $hostfqdn $UB_TXT_HOSTNAME"
1078           ptrrec="  local-data-ptr: \"$ifaddr 300 $iffqdn\""
1079           echo "$ptrrec" >> $UB_HOST_CONF
1080
1081         elif [ "$UB_D_LAN_FQDN" -eq 3 ] ; then
1082           names="$hostfqdn $UB_TXT_HOSTNAME"
1083           ptrrec="  local-data-ptr: \"$ifaddr 300 $hostfqdn\""
1084           echo "$ptrrec" >> $UB_HOST_CONF
1085
1086         else
1087           names="$UB_TXT_HOSTNAME"
1088           ptrrec="  local-data-ptr: \"$ifaddr 300 $UB_TXT_HOSTNAME\""
1089           echo "$ptrrec" >> $UB_HOST_CONF
1090         fi
1091
1092
1093         for name in $names ; do
1094           case $ifaddr in
1095             "${ulaprefix}"*)
1096               # IP6 ULA only is assigned for OPTION 1
1097               namerec="  local-data: \"$name. 300 IN AAAA $ifaddr\""
1098               echo "$namerec" >> $UB_HOST_CONF
1099               ;;
1100
1101             [1-9]*.*[0-9])
1102               namerec="  local-data: \"$name. 300 IN A $ifaddr\""
1103               echo "$namerec" >> $UB_HOST_CONF
1104               ;;
1105
1106             *)
1107               if [ "$UB_D_LAN_FQDN" -gt 1 ] ; then
1108                 # IP6 GLA is assigned for higher options
1109                 namerec="  local-data: \"$name. 300 IN AAAA $ifaddr\""
1110                 echo "$namerec" >> $UB_HOST_CONF
1111               fi
1112               ;;
1113           esac
1114         done
1115         echo >> $UB_HOST_CONF
1116       done
1117     fi
1118
1119
1120     if [ -n "$UB_LIST_NETW_WAN" -a "$UB_D_WAN_FQDN" -gt 0 ] ; then
1121       for ifsubnet in $UB_LIST_NETW_WAN ; do
1122         ifaddr=${ifsubnet#*@}
1123         ifaddr=${ifaddr%/*}
1124         ifname=${ifsubnet%@*}
1125         iffqdn="$ifname.$hostfqdn"
1126
1127
1128         if [ "$UB_D_WAN_FQDN" -eq 4 ] ; then
1129           names="$iffqdn $hostfqdn $UB_TXT_HOSTNAME"
1130           ptrrec="  local-data-ptr: \"$ifaddr 300 $iffqdn\""
1131           echo "$ptrrec" >> $UB_HOST_CONF
1132
1133         elif [ "$UB_D_WAN_FQDN" -eq 3 ] ; then
1134           names="$hostfqdn $UB_TXT_HOSTNAME"
1135           ptrrec="  local-data-ptr: \"$ifaddr 300 $hostfqdn\""
1136           echo "$ptrrec" >> $UB_HOST_CONF
1137
1138         else
1139           names="$UB_TXT_HOSTNAME"
1140           ptrrec="  local-data-ptr: \"$ifaddr 300 $UB_TXT_HOSTNAME\""
1141           echo "$ptrrec" >> $UB_HOST_CONF
1142         fi
1143
1144
1145         for name in $names ; do
1146           case $ifaddr in
1147             "${ulaprefix}"*)
1148               # IP6 ULA only is assigned for OPTION 1
1149               namerec="  local-data: \"$name. 300 IN AAAA $ifaddr\""
1150               echo "$namerec" >> $UB_HOST_CONF
1151               ;;
1152
1153             [1-9]*.*[0-9])
1154               namerec="  local-data: \"$name. 300 IN A $ifaddr\""
1155               echo "$namerec" >> $UB_HOST_CONF
1156               ;;
1157
1158             *)
1159               if [ "$UB_D_WAN_FQDN" -gt 1 ] ; then
1160                 # IP6 GLA is assigned for higher options
1161                 namerec="  local-data: \"$name. 300 IN AAAA $ifaddr\""
1162                 echo "$namerec" >> $UB_HOST_CONF
1163               fi
1164             ;;
1165           esac
1166         done
1167         echo >> $UB_HOST_CONF
1168       done
1169     fi
1170   fi # end if uci valid
1171 }
1172
1173 ##############################################################################
1174
1175 unbound_uci() {
1176   local cfg="$1"
1177   local dnsmasqpath hostnm
1178
1179   hostnm=$( uci_get system.@system[0].hostname | awk '{print tolower($0)}' )
1180   UB_TXT_HOSTNAME=${hostnm:-thisrouter}
1181
1182   config_get_bool UB_B_SLAAC6_MAC "$cfg" dhcp4_slaac6 0
1183   config_get_bool UB_B_DNS64      "$cfg" dns64 0
1184   config_get_bool UB_B_EXT_STATS  "$cfg" extended_stats 0
1185   config_get_bool UB_B_HIDE_BIND  "$cfg" hide_binddata 1
1186   config_get_bool UB_B_LOCL_SERV  "$cfg" localservice 1
1187   config_get_bool UB_B_MAN_CONF   "$cfg" manual_conf 0
1188   config_get_bool UB_B_QUERY_MIN  "$cfg" query_minimize 0
1189   config_get_bool UB_B_QRY_MINST  "$cfg" query_min_strict 0
1190   config_get_bool UB_B_AUTH_ROOT  "$cfg" prefetch_root 0
1191   config_get_bool UB_B_LOCL_BLCK  "$cfg" rebind_localhost 0
1192   config_get_bool UB_B_DNSSEC     "$cfg" validator 0
1193   config_get_bool UB_B_NTP_BOOT   "$cfg" validator_ntp 1
1194
1195   config_get UB_IP_DNS64    "$cfg" dns64_prefix "64:ff9b::/96"
1196
1197   config_get UB_N_EDNS_SIZE "$cfg" edns_size 1280
1198   config_get UB_N_RX_PORT   "$cfg" listen_port 53
1199   config_get UB_N_ROOT_AGE  "$cfg" root_age 9
1200
1201   config_get UB_D_CONTROL     "$cfg" unbound_control 0
1202   config_get UB_D_DOMAIN_TYPE "$cfg" domain_type static
1203   config_get UB_D_DHCP_LINK   "$cfg" dhcp_link none
1204   config_get UB_D_EXTRA_DNS   "$cfg" add_extra_dns 0
1205   config_get UB_D_LAN_FQDN    "$cfg" add_local_fqdn 0
1206   config_get UB_D_PRIV_BLCK   "$cfg" rebind_protection 1
1207   config_get UB_D_PROTOCOL    "$cfg" protocol mixed
1208   config_get UB_D_RECURSION   "$cfg" recursion passive
1209   config_get UB_D_RESOURCE    "$cfg" resource small
1210   config_get UB_D_VERBOSE     "$cfg" verbosity 1
1211   config_get UB_D_WAN_FQDN    "$cfg" add_wan_fqdn 0
1212
1213   config_get UB_TTL_MIN     "$cfg" ttl_min 120
1214   config_get UB_TXT_DOMAIN  "$cfg" domain lan
1215
1216   config_list_foreach "$cfg" domain_insecure  bundle_domain_insecure
1217
1218
1219   if [ "$UB_D_DHCP_LINK" = "none" ] ; then
1220     config_get_bool UB_B_DNSMASQ   "$cfg" dnsmasq_link_dns 0
1221
1222
1223     if [ "$UB_B_DNSMASQ" -gt 0 ] ; then
1224       UB_D_DHCP_LINK=dnsmasq
1225
1226
1227       if [ "$UB_B_READY" -eq 0 ] ; then
1228         logger -t unbound -s "Please use 'dhcp_link' selector instead"
1229       fi
1230     fi
1231   fi
1232
1233
1234   if [ "$UB_D_DHCP_LINK" = "dnsmasq" ] ; then
1235     if [ ! -x /usr/sbin/dnsmasq -o ! -x /etc/init.d/dnsmasq ] ; then
1236       UB_D_DHCP_LINK=none
1237     else
1238       /etc/init.d/dnsmasq enabled || UB_D_DHCP_LINK=none
1239     fi
1240
1241
1242     if [ "$UB_B_READY" -eq 0 -a "$UB_D_DHCP_LINK" = "none" ] ; then
1243       logger -t unbound -s "cannot forward to dnsmasq"
1244     fi
1245   fi
1246
1247
1248   if [ "$UB_D_DHCP_LINK" = "odhcpd" ] ; then
1249     if [ ! -x /usr/sbin/odhcpd -o ! -x /etc/init.d/odhcpd ] ; then
1250       UB_D_DHCP_LINK=none
1251     else
1252       /etc/init.d/odhcpd enabled || UB_D_DHCP_LINK=none
1253     fi
1254
1255
1256     if [ "$UB_B_READY" -eq 0 -a "$UB_D_DHCP_LINK" = "none" ] ; then
1257       logger -t unbound -s "cannot receive records from odhcpd"
1258     fi
1259   fi
1260
1261
1262   if [ "$UB_N_EDNS_SIZE" -lt 512 \
1263     -o 4096 -lt "$UB_N_EDNS_SIZE" ] ; then
1264     logger -t unbound -s "edns_size exceeds range, using default"
1265     UB_N_EDNS_SIZE=1280
1266   fi
1267
1268
1269   if [ "$UB_N_RX_PORT" -ne 53 \
1270       -a \( "$UB_N_RX_PORT" -lt 1024 -o 10240 -lt "$UB_N_RX_PORT" \) ] ; then
1271     logger -t unbound -s "privileged port or in 5 digits, using default"
1272     UB_N_RX_PORT=53
1273   fi
1274
1275
1276   if [ "$UB_TTL_MIN" -gt 1800 ] ; then
1277     logger -t unbound -s "ttl_min could have had awful side effects, using 300"
1278     UB_TTL_MIN=300
1279   fi
1280 }
1281
1282 ##############################################################################
1283
1284 unbound_include() {
1285   local adb_enabled
1286   local adb_files=$( ls $UB_VARDIR/adb_list.* 2>/dev/null )
1287
1288   echo "# $UB_TOTAL_CONF generated by UCI $( date -Is )" > $UB_TOTAL_CONF
1289
1290
1291   if [ -f "$UB_CORE_CONF" ] ; then
1292     # Yes this all looks busy, but it is in TMPFS. Working on separate files
1293     # and piecing together is easier. UCI order is less constrained.
1294     cat $UB_CORE_CONF >> $UB_TOTAL_CONF
1295     rm  $UB_CORE_CONF
1296   fi
1297
1298
1299   if [ -f "$UB_HOST_CONF" ] ; then
1300     # UCI definitions of local host or local subnet
1301     cat $UB_HOST_CONF >> $UB_TOTAL_CONF
1302     rm  $UB_HOST_CONF
1303   fi
1304
1305
1306   if [ -f $UB_SRVMASQ_CONF ] ; then
1307     # UCI found link to dnsmasq
1308     cat $UB_SRVMASQ_CONF >> $UB_TOTAL_CONF
1309     rm  $UB_SRVMASQ_CONF
1310   fi
1311
1312
1313   if [ -f "$UB_DHCP_CONF" ] ; then
1314     {
1315       # Seed DHCP records because dhcp scripts trigger externally
1316       # Incremental Unbound restarts may drop unbound-control records
1317       echo "include: $UB_DHCP_CONF"
1318       echo
1319     }>> $UB_TOTAL_CONF
1320   fi
1321
1322
1323   if [ -z "$adb_files" \
1324        -o  ! -x /usr/bin/adblock.sh -o ! -x /etc/init.d/adblock ] ; then
1325     adb_enabled=0
1326
1327   elif /etc/init.d/adblock enabled ; then
1328     adb_enabled=1
1329     {
1330       # Pull in your selected openwrt/pacakges/net/adblock generated lists
1331       echo "include: $UB_VARDIR/adb_list.*"
1332       echo
1333     } >> $UB_TOTAL_CONF
1334
1335   else
1336     adb_enabled=0
1337   fi
1338
1339
1340   if [ -f $UB_SRV_CONF ] ; then
1341     {
1342       # Pull your own "server:" options here
1343       echo "include: $UB_SRV_CONF"
1344       echo
1345     }>> $UB_TOTAL_CONF
1346   fi
1347
1348
1349   if [ -f "$UB_ZONE_CONF" ] ; then
1350     # UCI defined forward, stub, and auth zones
1351     cat $UB_ZONE_CONF >> $UB_TOTAL_CONF
1352     rm  $UB_ZONE_CONF
1353   fi
1354
1355
1356   if [ -f "$UB_CTRL_CONF" ] ; then
1357     # UCI defined control application connection
1358     cat $UB_CTRL_CONF >> $UB_TOTAL_CONF
1359     rm  $UB_CTRL_CONF
1360   fi
1361
1362
1363   if [ -f "$UB_EXTMASQ_CONF" ] ; then
1364     # UCI found link to dnsmasq
1365     cat $UB_EXTMASQ_CONF >> $UB_TOTAL_CONF
1366     rm  $UB_EXTMASQ_CONF
1367   fi
1368
1369
1370   if [ -f "$UB_EXT_CONF" ] ; then
1371     {
1372       # Pull your own extend feature clauses here
1373       echo "include: $UB_EXT_CONF"
1374       echo
1375     } >> $UB_TOTAL_CONF
1376   fi
1377 }
1378
1379 ##############################################################################
1380
1381 resolv_setup() {
1382   if [ "$UB_N_RX_PORT" != "53" ] ; then
1383     return
1384
1385   elif [ -x /etc/init.d/dnsmasq ] \
1386     && /etc/init.d/dnsmasq enabled \
1387     && nslookup localhost 127.0.0.1#53 >/dev/null 2>&1 ; then
1388     # unbound is configured for port 53, but dnsmasq is enabled and a resolver
1389     #   listens on localhost:53, lets assume dnsmasq manages the resolver file.
1390     # TODO:
1391     #   really check if dnsmasq runs a local (main) resolver in stead of using
1392     #   nslookup that times out when no resolver listens on localhost:53.
1393     return
1394   fi
1395
1396
1397   # unbound is designated to listen on 127.0.0.1#53,
1398   #   set resolver file to local.
1399   rm -f /tmp/resolv.conf
1400
1401   {
1402     echo "# /tmp/resolv.conf generated by Unbound UCI $( date -Is )"
1403     echo "nameserver 127.0.0.1"
1404     echo "nameserver ::1"
1405     echo "search $UB_TXT_DOMAIN."
1406   } > /tmp/resolv.conf
1407 }
1408
1409 ##############################################################################
1410
1411 unbound_start() {
1412   config_load unbound
1413   config_foreach unbound_uci unbound
1414   unbound_mkdir
1415
1416
1417   if [ "$UB_B_MAN_CONF" -eq 0 ] ; then
1418     # iterate zones before we load other UCI
1419     # forward-zone: auth-zone: and stub-zone:
1420     config_foreach unbound_zone zone
1421     # associate potential DNS RR with interfaces
1422     config_load network
1423     config_foreach bundle_all_networks interface
1424     config_load dhcp
1425     config_foreach bundle_lan_networks dhcp
1426     bundle_wan_networks
1427     # server:
1428     unbound_conf
1429     unbound_hostname
1430     # control:
1431     unbound_control
1432     # dnsmasq
1433     dnsmasq_link
1434     # merge
1435     unbound_include
1436   fi
1437
1438
1439   resolv_setup
1440 }
1441
1442 ##############################################################################
1443