Home | History | Annotate | Download | only in dhcpcd-hooks
      1 # Generate /etc/resolv.conf
      2 # Support resolvconf(8) if available
      3 # We can merge other dhcpcd resolv.conf files into one like resolvconf,
      4 # but resolvconf is preferred as other applications like VPN clients
      5 # can readily hook into it.
      6 # Also, resolvconf can configure local nameservers such as bind
      7 # or dnsmasq. This is important as the libc resolver isn't that powerful.
      8 
      9 resolv_conf_dir="$state_dir/resolv.conf"
     10 
     11 build_resolv_conf()
     12 {
     13 	local cf="$state_dir/resolv.conf.$interface"
     14 	local interfaces= header= search= srvs= servers= x=
     15 
     16 	# Build a list of interfaces
     17 	interfaces=$(list_interfaces "$resolv_conf_dir")
     18 
     19 	# Build the resolv.conf
     20 	if [ -n "$interfaces" ]; then
     21 		# Build the header
     22 		for x in ${interfaces}; do
     23 			header="$header${header:+, }$x"
     24 		done
     25 
     26 		# Build the search list
     27 		domain=$(cd "$resolv_conf_dir"; \
     28 			key_get_value "domain " ${interfaces})
     29 		search=$(cd "$resolv_conf_dir"; \
     30 			key_get_value "search " ${interfaces})
     31 		set -- ${domain}
     32 		unset domain
     33 		if [ -n "$2" ]; then
     34 			search="$search $@"
     35 		elif [ -n "$1" ]; then
     36 			domain="domain $1\n"
     37 		fi
     38 		[ -n "$search" ] && search="search $(uniqify $search)\n"
     39 
     40 		# Build the nameserver list
     41 		srvs=$(cd "$resolv_conf_dir"; \
     42 			key_get_value "nameserver " ${interfaces})
     43 		for x in $(uniqify ${srvs}); do
     44 			servers="${servers}nameserver $x\n"
     45 		done
     46 	fi
     47 	header="$signature_base${header:+ $from }$header"
     48 
     49 	# Assemble resolv.conf using our head and tail files
     50 	[ -f "$cf" ] && rm -f "$cf"
     51 	[ -d "$resolv_conf_dir" ] || mkdir -p "$resolv_conf_dir"
     52 	echo "$header" > "$cf"
     53 	if [ -f /etc/resolv.conf.head ]; then
     54 		cat /etc/resolv.conf.head >> "$cf"
     55 	else
     56 		echo "# /etc/resolv.conf.head can replace this line" >> "$cf"
     57 	fi
     58 	printf "$domain$search$servers" >> "$cf"
     59 	if [ -f /etc/resolv.conf.tail ]; then
     60 		cat /etc/resolv.conf.tail >> "$cf"
     61 	else
     62 		echo "# /etc/resolv.conf.tail can replace this line" >> "$cf"
     63 	fi
     64 	cat "$cf" > /etc/resolv.conf
     65 	chmod 644 /etc/resolv.conf
     66 	rm -f "$cf"
     67 }
     68 
     69 add_resolv_conf()
     70 {
     71 	local x= conf="$signature\n"
     72 
     73 	# If we don't have any configuration, remove it
     74 	if [ -z "$new_domain_name_servers" -a \
     75 		-z "$new_domain_name" -a \
     76 		-z "$new_domain_search" ]; then
     77 		remove_resolv_conf
     78 		return $?
     79 	fi
     80 
     81 	if [ -n "$new_domain_name" ]; then
     82 		set -- $new_domain_name
     83 		new_domain_name="$1"
     84 		conf="${conf}domain $new_domain_name\n"
     85 		# Support RFC violating search in domain
     86 		if [ -z "$new_domain_search" -a -n "$2" ]; then
     87 			new_domain_search="$@"
     88 		fi
     89 	fi
     90 	if [ -n "$new_domain_search" ]; then
     91 		conf="${conf}search $new_domain_search\n"
     92 	fi
     93 	for x in ${new_domain_name_servers}; do
     94 		conf="${conf}nameserver $x\n"
     95 	done
     96 	if type resolvconf >/dev/null 2>&1; then
     97 		[ -n "$metric" ] && export IF_METRIC="$metric"
     98 		printf "$conf" | resolvconf -a "$interface"
     99 		return $?
    100 	fi
    101 
    102 	if [ -e "$resolv_conf_dir/$interface" ]; then
    103 		rm -f "$resolv_conf_dir/$interface"
    104 	fi
    105 	[ -d "$resolv_conf_dir" ] || mkdir -p "$resolv_conf_dir"
    106 	printf "$conf" > "$resolv_conf_dir/$interface"
    107 	build_resolv_conf
    108 }
    109 
    110 remove_resolv_conf()
    111 {
    112 	if type resolvconf >/dev/null 2>&1; then
    113 		resolvconf -d "$interface" -f
    114 	else
    115 		if [ -e "$resolv_conf_dir/$interface" ]; then
    116 			rm -f "$resolv_conf_dir/$interface"
    117 		fi
    118 		build_resolv_conf
    119 	fi
    120 }
    121 
    122 if $if_up; then
    123 	add_resolv_conf
    124 elif $if_down; then
    125 	remove_resolv_conf
    126 fi
    127