Bug 1157856

Summary: Request to change hostname logic handling for "static"/"none" interface configuration
Product: Red Hat Enterprise Linux 6 Reporter: Bryan Totty <btotty>
Component: initscriptsAssignee: David Kaspar [Dee'Kej] <deekej>
Status: CLOSED ERRATA QA Contact: Jan Ščotka <jscotka>
Severity: medium Docs Contact: Clayton Spicer <cspicer>
Priority: medium    
Version: 6.7CC: ckozler, cww, deekej, jpopelka, jscotka, psklenar
Target Milestone: rcKeywords: Patch
Target Release: ---   
Hardware: All   
OS: Linux   
Whiteboard:
Fixed In Version: initscripts-9.03.55-1 Doc Type: Enhancement
Doc Text:
The `NO_DHCP_HOSTNAME` option has been added The `NO_DHCP_HOSTNAME` option can now be specified in the `/etc/sysconfig/network` configuration file. Previously, in certain situations it was not possible to prevent initialization scripts from obtaining the host name through DHCP, even when using a static configuration. With this update, if the `NO_DHCP_HOSTNAME` option is set to `yes`, `true`, or `1` in the `/etc/sysconfig/network` file, initialization scripts are prevented from obtaining the host name through DHCP.
Story Points: ---
Clone Of:
: 1398672 (view as bug list) Environment:
Last Closed: 2017-03-21 11:51:52 UTC Type: Bug
Regression: --- Mount Type: ---
Documentation: --- CRM:
Verified Versions: Category: ---
oVirt Team: --- RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: --- Target Upstream Version:
Bug Depends On:    
Bug Blocks: 1172231, 1269194, 1356047, 1398672    

Description Bryan Totty 2014-10-27 21:15:48 UTC
Version-Release number of selected component (if applicable):
initscripts 9.0.46-1.el6 / RHEL 6.6

How reproducible:
Always


Current logic, this is a summary and should the double checked for accuracy:

-------------------------------------------------------------------------------
For details, here is the hostname setting logic when the system boots up:
* In rc.sysinit: If hostname is not set yet[1], and HOSTNAME is defined in /etc/sysconfig/network, then use the HOSTNAME in /etc/sysconfig/network.

    /etc/rc.d/rc.sysinit:
      8 HOSTNAME=`/bin/hostname`
    ...
    14 if [ -f /etc/sysconfig/network ]; then
    15     . /etc/sysconfig/network
    16 fi
    17 if [ -z "$HOSTNAME" -o "$HOSTNAME" = "(none)" ]; then
    18     HOSTNAME=localhost
    19 fi
    ...
    397 # Set the hostname.
    398 update_boot_stage RChostname
    399 action $"Setting hostname ${HOSTNAME}: " hostname ${HOSTNAME}

The hostname setting code in rc.sysinit will usually not effective in this stage because network service is not started yet [1] so the system usually doesn't have ip address to get the hostname by the following code:

    581         if [ "$HOSTNAME" = "localhost" -o "$HOSTNAME" = "localhost.localdoma    in" ]; then
    582                 ipaddr=$(ip addr show to 0/0 scope global | awk '/[[:space:]    ]inet / { print gensub("/.*","","g",$2) }')
    583                 if [ -n "$ipaddr" ]; then
    584                         eval $(ipcalc -h $ipaddr 2>/dev/null)
    585                         hostname ${HOSTNAME}
    586                 fi
    587         fi

2. Then in "service network start" when system boot up[2], there are 2 places that can set the hostname for each interface:

2.1. In ifup-eth, if the network device get IP by dhcp, it will use dhclient to get the IP and other network information from DHCP server. Then in /sbin/dhclient-script, If hostname is still (none)/localhost/localhost.localdomin, AND "host-name" exists in dhcp lease, it will set the hostname to that.

    /sbin/dhclient-script:
    345         if [ -n "$new_host_name" ] && need_hostname; then
    346             hostname $new_host_name
    347         fi

need_hostname is defined in /etc/sysconfig/network-scripts/network-functions:

    252 need_hostname ()
    253 {
    254     CHECK_HOSTNAME=`hostname`
    255     if [ "$CHECK_HOSTNAME" = "(none)" -o "$CHECK_HOSTNAME" = "localhost" -o \
    256         "$CHECK_HOSTNAME" = "localhost.localdomain" ]; then
    257         return 0
    258     else
    259         return 1
    260     fi
    261 }

2.2. After that, in ifup-post, if the hostname is still (none)/localhost/localhost.localdomin, it will use ipcalc to get the hostname by ip address. ipcalc use gethostbyaddr function (in glibc) to query for the hostname, so you can refer to /etc/nsswitch.conf for the order, which is usually files (/etc/hosts) first and then from DNS.

    /etc/sysconfig/network-scripts/ifup-post:
    82 # don't set hostname on ppp/slip connections
    83 if [ "$2" = "boot" -a \
    84      "${DEVICE}" != lo -a \
    85      "${DEVICETYPE}" != "ppp" -a \
    86      "${DEVICETYPE}" != "slip" ]; then
    87     if need_hostname; then
    88         IPADDR=LANG= LC_ALL= ifconfig ${DEVICE} | grep 'inet addr' |
    89&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; awk -F: '{ print $2 } ' | awk '{ print $1 }'
    90         eval `/bin/ipcalc --silent --hostname ${IPADDR}`
    91         if [ "$?" = "0" ]; then
    92             set_hostname $HOSTNAME
    93         fi
    94     fi
    95 fi

Because step 2.1 and 2.2 would use need_hostname to check if hostname is set, if hostname is set by one interface, it will not be overwritten by others afterwards.

3. Because sysctl would be run in a late stage of /etc/init.d/network script, if kernel.hostname is specified in /etc/sysctl.conf, it will overwrite the hostname set before.

    172         # Run this again to catch any interface-specific actions
    173         sysctl -e -p /etc/sysctl.conf >/dev/null 2>&1
----------------------------------------------------------------------------------



This functionality can cause problems downstream. 

For instance:

- Person A requests DNS team add DNS of server1.domain.com with IP 10.1.89.22
- Person B adds DNS entry
- Person A discards their VM because they dont need it anymore and shuts it down
- Person C sees that the IP 10.1.89.22 is available and uses it. System comes up with name server1

This can lead to confusion on Person C's side and could also cause automated processes to break.

We are aware that the best practice is to configure the server side DHCP reservation infomation correctly so that it does not draw the incorrect hostname, but there are some instances where administrators want explicit control over their client system. IE: They don't want their client system to be a slave to receiving a incorrect hostname per the initscript logic.

We can add the 'kernel.hostname = localhost.localdomain' to the end of sysctl.conf but we'd rather not have another config file to manage post-install and would rather have a static on/off switch for this type of functionality that ifup is assuming.

Example:

if [ $HOSTNAME == "localhost" ] || [ $HOSTNAME == "localhost.localdomain" ]  && [ $BOOT_PROTO != "static" ] && [ $BOOT_PROTO != "none" ]; then
        echo "+ Setting hostname from DNS"
else
        if [ $BOOT_PROTO == "static" ]; then
                echo "+ Not setting hostname from DNS. BOOT_PROTO=static"
        fi
        if [ $BOOT_PROTO == "none" ]; then
                echo "+ Not setting hostname from DNS. BOOT_PROTO=none"
        fi
fi


This may not be exactly what you're looking for but you see what I'm saying. Overall you're skipping the logic handling of checking if we are using a static or none for BOOT_PROTO from /etc/sysconfig/network and assuming we want to set our local hostname from DNS. I know that static is deprecated but this is the general idea.

It should be setup so that if you are using DHCP or similar for network handling *then* you want to have the system set the hostname to what is defined by DNS. While I don't approve of that either, I feel like this would be better suited than assuming we (the admin) *always* want the hostname set automatically.

Using DHCP assumes we want automatic features such as IP, hostname, gateway, and the likes...static or no boot proto means we want to do it ourselves - to not have the system decide what to do regardless of what we say.

Comment 2 Lukáš Nykrýn 2014-10-29 12:22:07 UTC
Hmmm, I don't think that changing default behavior would be a good idea. Someone else could be using that and having regressions is much worse.

I am still not sure what is not enough just to set HOSTNAME in sysconfig/network.

But otherwise I would be open to some new option for sysconfig/network like DHCPHOSTNAME.

Comment 3 Bryan Totty 2014-10-30 14:28:26 UTC
I believe that any option that gives control back to the administrator of the system will be acceptable. We just don't want the hostname being taken control of when using a static configuration.

Comment 4 Charles Kozler 2014-11-04 13:27:34 UTC
Hi Lukáš Nykrýn - Bryan is exactly right. I am the original requestor and ultimately having a system assume dynamic behavior when not configured in such a manner is undesired. This can break upstream processes such as bootstrapping or other automated processes which can break if the system makes assumptions. An option such that DHCPHOSTNAME=yes/no or something of the similar that tells the system to set the local hostname would be ideal in that we could then set this flag in our template vs alternative routes of trying to manage it through sysctl.conf (eg: once deployment is complete then unset manual setting in sysctl). 

Thanks

Comment 5 Lukáš Nykrýn 2015-02-27 14:29:36 UTC
Hmm this needs a patch i dhclient and unfortunately we will not make it in 6.7, so lets postpone it to 6.8

Comment 6 Charles Kozler 2015-02-27 14:33:35 UTC
What is the patch required in dhclient?

Comment 7 Lukáš Nykrýn 2015-02-28 19:32:25 UTC
we should not modify need_hostname function, because its behavior should be stable. So if we want to add some additional variable it should be also read directly by dhclient-script

Comment 8 Lukáš Nykrýn 2015-04-24 10:19:31 UTC
Adding maintainer of dhclient to CC.

Comment 10 David Kaspar [Dee'Kej] 2016-11-10 16:18:09 UTC
Hello Bryan and Charles,

we were discussing possible options and we decided to introduce a new option 'NO_DHCP_HOSTNAME' for you that you could set in /etc/sysconfig/network file:

https://github.com/fedora-sysv/initscripts/pull/39

We're open to discussion in case you see this not sufficent to fix your issues.

Best regards,

David

Comment 21 errata-xmlrpc 2017-03-21 11:51:52 UTC
Since the problem described in this bug report should be
resolved in a recent advisory, it has been closed with a
resolution of ERRATA.

For information on the advisory, and where to find the updated
files, follow the link below.

If the solution does not work for you, open a new bug report.

https://rhn.redhat.com/errata/RHBA-2017-0786.html