xref: /freebsd/usr.sbin/bsdconfig/networking/share/hostname.subr (revision ab2043b81eaba0d7d7769b4a58b2b6d17bc464a3)
1*ab2043b8SDevin Teskeif [ ! "$_NETWORKING_HOSTNAME_SUBR" ]; then _NETWORKING_HOSTNAME_SUBR=1
2*ab2043b8SDevin Teske#
3*ab2043b8SDevin Teske# Copyright (c) 2006-2012 Devin Teske
4*ab2043b8SDevin Teske# All Rights Reserved.
5*ab2043b8SDevin Teske#
6*ab2043b8SDevin Teske# Redistribution and use in source and binary forms, with or without
7*ab2043b8SDevin Teske# modification, are permitted provided that the following conditions
8*ab2043b8SDevin Teske# are met:
9*ab2043b8SDevin Teske# 1. Redistributions of source code must retain the above copyright
10*ab2043b8SDevin Teske#    notice, this list of conditions and the following disclaimer.
11*ab2043b8SDevin Teske# 2. Redistributions in binary form must reproduce the above copyright
12*ab2043b8SDevin Teske#    notice, this list of conditions and the following disclaimer in the
13*ab2043b8SDevin Teske#    documentation and/or other materials provided with the distribution.
14*ab2043b8SDevin Teske#
15*ab2043b8SDevin Teske# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16*ab2043b8SDevin Teske# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, THE
17*ab2043b8SDevin Teske# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18*ab2043b8SDevin Teske# ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19*ab2043b8SDevin Teske# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20*ab2043b8SDevin Teske# DAMAGES (INLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21*ab2043b8SDevin Teske# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22*ab2043b8SDevin Teske# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23*ab2043b8SDevin Teske# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24*ab2043b8SDevin Teske# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25*ab2043b8SDevin Teske# SUCH DAMAGE.
26*ab2043b8SDevin Teske#
27*ab2043b8SDevin Teske# $FreeBSD$
28*ab2043b8SDevin Teske#
29*ab2043b8SDevin Teske############################################################ INCLUDES
30*ab2043b8SDevin Teske
31*ab2043b8SDevin TeskeBSDCFG_SHARE="/usr/share/bsdconfig"
32*ab2043b8SDevin Teske. $BSDCFG_SHARE/common.subr || exit 1
33*ab2043b8SDevin Teskef_include $BSDCFG_SHARE/sysrc.subr
34*ab2043b8SDevin Teskef_include $BSDCFG_SHARE/dialog.subr
35*ab2043b8SDevin Teskef_include $BSDCFG_SHARE/networking/common.subr
36*ab2043b8SDevin Teskef_include $BSDCFG_SHARE/networking/resolv.subr
37*ab2043b8SDevin Teske
38*ab2043b8SDevin TeskeBSDCFG_LIBE="/usr/libexec/bsdconfig" APP_DIR="120.networking"
39*ab2043b8SDevin Teskef_include_lang $BSDCFG_LIBE/$APP_DIR/include/messages.subr
40*ab2043b8SDevin Teske
41*ab2043b8SDevin Teske############################################################ FUNCTIONS
42*ab2043b8SDevin Teske
43*ab2043b8SDevin Teske# f_dialog_validate_hostname $hostname
44*ab2043b8SDevin Teske#
45*ab2043b8SDevin Teske# Returns zero if the given argument (a fully-qualified hostname) is compliant
46*ab2043b8SDevin Teske# with standards set-forth in RFC's 952 and 1123 of the Network Working Group:
47*ab2043b8SDevin Teske#
48*ab2043b8SDevin Teske# RFC 952 - DoD Internet host table specification
49*ab2043b8SDevin Teske# http://tools.ietf.org/html/rfc952
50*ab2043b8SDevin Teske#
51*ab2043b8SDevin Teske# RFC 1123 - Requirements for Internet Hosts - Application and Support
52*ab2043b8SDevin Teske# http://tools.ietf.org/html/rfc1123
53*ab2043b8SDevin Teske#
54*ab2043b8SDevin Teske# See http://en.wikipedia.org/wiki/Hostname for a brief overview.
55*ab2043b8SDevin Teske#
56*ab2043b8SDevin Teske# The return status for invalid hostnames is one of:
57*ab2043b8SDevin Teske# 	255	Entire hostname exceeds the maximum length of 255 characters.
58*ab2043b8SDevin Teske# 	 63	One or more individual labels within the hostname (separated by
59*ab2043b8SDevin Teske# 	   	dots) exceeds the maximum of 63 characters.
60*ab2043b8SDevin Teske# 	  1	One or more individual labels within the hostname contains one
61*ab2043b8SDevin Teske# 	   	or more invalid characters.
62*ab2043b8SDevin Teske# 	  2	One or more individual labels within the hostname starts or
63*ab2043b8SDevin Teske# 	   	ends with a hyphen (hyphens are allowed, but a label cannot
64*ab2043b8SDevin Teske# 	   	begin or end with a hyphen).
65*ab2043b8SDevin Teske# 	  3	One or more individual labels within the hostname are null.
66*ab2043b8SDevin Teske#
67*ab2043b8SDevin Teske# If the hostname is determined to be invalid, the appropriate error will be
68*ab2043b8SDevin Teske# displayed using the f_dialog_msgbox function.
69*ab2043b8SDevin Teske#
70*ab2043b8SDevin Teskef_dialog_validate_hostname()
71*ab2043b8SDevin Teske{
72*ab2043b8SDevin Teske	local fqhn="$1"
73*ab2043b8SDevin Teske
74*ab2043b8SDevin Teske	( # Operate within a sub-shell to protect the parent environment
75*ab2043b8SDevin Teske
76*ab2043b8SDevin Teske		# Return error if the hostname exceeds 255 characters
77*ab2043b8SDevin Teske		[ ${#fqhn} -gt 255 ] && exit 255
78*ab2043b8SDevin Teske
79*ab2043b8SDevin Teske		IFS="." # Split on `dot'
80*ab2043b8SDevin Teske		for label in $fqhn; do
81*ab2043b8SDevin Teske
82*ab2043b8SDevin Teske			# Return error if the label exceeds 63 characters
83*ab2043b8SDevin Teske			[ ${#label} -gt 63 ] && exit 63
84*ab2043b8SDevin Teske
85*ab2043b8SDevin Teske			# Return error if the label is null
86*ab2043b8SDevin Teske			[ "$label" ] || exit 3
87*ab2043b8SDevin Teske
88*ab2043b8SDevin Teske			# Return error if label begins/ends with dash
89*ab2043b8SDevin Teske			case "$label" in
90*ab2043b8SDevin Teske			-*|*-) exit 2
91*ab2043b8SDevin Teske			esac
92*ab2043b8SDevin Teske
93*ab2043b8SDevin Teske			# Return error if the label contains any invalid chars
94*ab2043b8SDevin Teske			echo "$label" | grep -q '^[[:alnum:]-]*$' || exit 1
95*ab2043b8SDevin Teske
96*ab2043b8SDevin Teske		done
97*ab2043b8SDevin Teske	)
98*ab2043b8SDevin Teske
99*ab2043b8SDevin Teske	#
100*ab2043b8SDevin Teske	# Produce an appropriate error message if necessary.
101*ab2043b8SDevin Teske	#
102*ab2043b8SDevin Teske	local retval=$?
103*ab2043b8SDevin Teske	case $retval in
104*ab2043b8SDevin Teske	1) f_dialog_msgbox "$( printf \
105*ab2043b8SDevin Teske		"$msg_hostname_label_contains_invalid_chars" "$fqhn" )";;
106*ab2043b8SDevin Teske	2) f_dialog_msgbox "$( printf \
107*ab2043b8SDevin Teske		"$msg_hostname_label_starts_or_ends_with_hyphen" "$fqhn" )";;
108*ab2043b8SDevin Teske	3) f_dialog_msgbox "$( printf \
109*ab2043b8SDevin Teske		"$msg_hostname_label_is_null" "$fqhn" )";;
110*ab2043b8SDevin Teske	63) f_dialog_msgbox "$( printf \
111*ab2043b8SDevin Teske		"$msg_hostname_label_exceeds_max_length" "$fqhn" )";;
112*ab2043b8SDevin Teske	255) f_dialog_msgbox "$( printf \
113*ab2043b8SDevin Teske		"$msg_hostname_exceeds_max_length" "$fqhn" )";;
114*ab2043b8SDevin Teske	esac
115*ab2043b8SDevin Teske
116*ab2043b8SDevin Teske	return $retval
117*ab2043b8SDevin Teske}
118*ab2043b8SDevin Teske
119*ab2043b8SDevin Teske# f_dialog_input_hostname
120*ab2043b8SDevin Teske#
121*ab2043b8SDevin Teske# Edits the current hostname.
122*ab2043b8SDevin Teske#
123*ab2043b8SDevin Teskef_dialog_input_hostname()
124*ab2043b8SDevin Teske{
125*ab2043b8SDevin Teske	local hostname="$( f_sysrc_get 'hostname:-$(hostname)' )"
126*ab2043b8SDevin Teske	local hostname_orig="$hostname" # for change-tracking
127*ab2043b8SDevin Teske
128*ab2043b8SDevin Teske	local msg
129*ab2043b8SDevin Teske	if [ "$USE_XDIALOG" ]; then
130*ab2043b8SDevin Teske		msg="$xmsg_please_enter_fqhn"
131*ab2043b8SDevin Teske	else
132*ab2043b8SDevin Teske		msg="$msg_please_enter_fqhn"
133*ab2043b8SDevin Teske	fi
134*ab2043b8SDevin Teske
135*ab2043b8SDevin Teske	local hline="$hline_alnum_punc_tab_enter"
136*ab2043b8SDevin Teske
137*ab2043b8SDevin Teske	#
138*ab2043b8SDevin Teske	# Loop until the user provides taint-free input.
139*ab2043b8SDevin Teske	#
140*ab2043b8SDevin Teske	local size height width
141*ab2043b8SDevin Teske	while :; do
142*ab2043b8SDevin Teske
143*ab2043b8SDevin Teske		size=$( f_dialog_inputbox_size \
144*ab2043b8SDevin Teske		         	"$DIALOG_TITLE"     \
145*ab2043b8SDevin Teske		         	"$DIALOG_BACKTITLE" \
146*ab2043b8SDevin Teske		         	"$msg"              \
147*ab2043b8SDevin Teske		         	"$hostname"         \
148*ab2043b8SDevin Teske		         	"$hline"            )
149*ab2043b8SDevin Teske		eval $DIALOG \
150*ab2043b8SDevin Teske			--title \"\$DIALOG_TITLE\"         \
151*ab2043b8SDevin Teske			--backtitle \"\$DIALOG_BACKTITLE\" \
152*ab2043b8SDevin Teske			--hline \"\$hline\"                \
153*ab2043b8SDevin Teske			--ok-label \"\$msg_ok\"            \
154*ab2043b8SDevin Teske			--cancel-label \"\$msg_cancel\"    \
155*ab2043b8SDevin Teske			--inputbox \"\$msg\" $size         \
156*ab2043b8SDevin Teske			\"\$hostname\"                     \
157*ab2043b8SDevin Teske			2> "$DIALOG_TMPDIR/dialog.inputbox.$$"
158*ab2043b8SDevin Teske
159*ab2043b8SDevin Teske		local retval=$?
160*ab2043b8SDevin Teske		hostname=$( f_dialog_inputstr )
161*ab2043b8SDevin Teske
162*ab2043b8SDevin Teske		[ $retval -eq $SUCCESS ] || return $retval
163*ab2043b8SDevin Teske
164*ab2043b8SDevin Teske		# Taint-check the user's input
165*ab2043b8SDevin Teske		f_dialog_validate_hostname "$hostname" && break
166*ab2043b8SDevin Teske
167*ab2043b8SDevin Teske	done
168*ab2043b8SDevin Teske
169*ab2043b8SDevin Teske	#
170*ab2043b8SDevin Teske	# Save hostname only if the user changed the hostname.
171*ab2043b8SDevin Teske	#
172*ab2043b8SDevin Teske	if [ "$hostname" != "$hostname_orig" ]; then
173*ab2043b8SDevin Teske		f_dialog_info "$msg_saving_hostname"
174*ab2043b8SDevin Teske		f_sysrc_set hostname "$hostname"
175*ab2043b8SDevin Teske	fi
176*ab2043b8SDevin Teske
177*ab2043b8SDevin Teske	#
178*ab2043b8SDevin Teske	# Update resolv.conf(5) search/domain directives
179*ab2043b8SDevin Teske	#
180*ab2043b8SDevin Teske	f_dialog_resolv_conf_update "$hostname"
181*ab2043b8SDevin Teske
182*ab2043b8SDevin Teske	#
183*ab2043b8SDevin Teske	# Only ask to apply setting if the current hostname is different than
184*ab2043b8SDevin Teske	# the stored configuration (in rc.conf(5)).
185*ab2043b8SDevin Teske	#
186*ab2043b8SDevin Teske	if [ "$( hostname )" != "$( f_sysrc_get hostname )" ]; then
187*ab2043b8SDevin Teske		[ ! "$USE_XDIALOG" ] && dialog_clear
188*ab2043b8SDevin Teske
189*ab2043b8SDevin Teske		#
190*ab2043b8SDevin Teske		# If connected via ssh(1) and performing X11-Forwarding, don't
191*ab2043b8SDevin Teske		# allow the hostname to be changed to prevent the fatal error
192*ab2043b8SDevin Teske		# "X11 connection rejected because of wrong authentication."
193*ab2043b8SDevin Teske		#
194*ab2043b8SDevin Teske		if [ "$USE_XDIALOG" -a "$SSH_CONNECTION" ]; then
195*ab2043b8SDevin Teske			f_dialog_msgbox "$(
196*ab2043b8SDevin Teske				printf "$msg_activate_hostname_x11warning" \
197*ab2043b8SDevin Teske				       "$( hostname )" "$hostname"
198*ab2043b8SDevin Teske			)"
199*ab2043b8SDevin Teske		else
200*ab2043b8SDevin Teske			f_dialog_yesno "$(
201*ab2043b8SDevin Teske				printf "$msg_activate_hostname" \
202*ab2043b8SDevin Teske				       "$( hostname )" "$hostname" \
203*ab2043b8SDevin Teske			)" \
204*ab2043b8SDevin Teske			&& hostname "$hostname"
205*ab2043b8SDevin Teske		fi
206*ab2043b8SDevin Teske	fi
207*ab2043b8SDevin Teske
208*ab2043b8SDevin Teske	return $SUCCESS
209*ab2043b8SDevin Teske}
210*ab2043b8SDevin Teske
211*ab2043b8SDevin Teskefi # ! $_NETWORKING_HOSTNAME_SUBR
212