diff --git a/man/systemd.network.xml b/man/systemd.network.xml index 9bad97b07b8..dfae8119e73 100644 --- a/man/systemd.network.xml +++ b/man/systemd.network.xml @@ -267,15 +267,8 @@ when determining whether the system is online (including when running systemd-networkd-wait-online). When no, the network is ignored when determining the online state. When a minimum operational state and an optional - maximum operational state are set, yes is implied, and this controls the - minimum and maximum operational state required for the network interface to be considered - online. - - When yes is specified for a CAN device, - systemd-networkd-wait-online deems that the interface is online when its - operational state becomes carrier. For an interface with other type, e.g. - ether, the interface is deened online when its online state is - degraded or routable. + maximum operational state are set, systemd-networkd-wait-online deems that the + interface is online when the operational state is in the specified range. Defaults to yes when ActivationPolicy= is not set, or set to up, always-up, or @@ -290,6 +283,44 @@ skipped automatically by systemd-networkd-wait-online if RequiredForOnline=no. + The boolean value yes is translated as follows; + + + + + carrier, + + + + + + + degraded-carrier with RequiredFamilyForOnline=any, + + + + + + + enslaved, + + + + + + + degraded. + + + + + + + This setting can be overridden by the command line option for + systemd-networkd-wait-online. See + systemd-networkd-wait-online.service8 + for more details. + diff --git a/src/network/networkd-link.c b/src/network/networkd-link.c index 194d31eafe8..621f8592061 100644 --- a/src/network/networkd-link.c +++ b/src/network/networkd-link.c @@ -76,16 +76,48 @@ void link_required_operstate_for_online(Link *link, LinkOperationalStateRange *r assert(ret); if (link->network && operational_state_range_is_valid(&link->network->required_operstate_for_online)) + /* If explicitly specified, use it as is. */ *ret = link->network->required_operstate_for_online; else if (link->iftype == ARPHRD_CAN) + /* CAN devices do not support addressing, hence defaults to 'carrier'. */ *ret = (const LinkOperationalStateRange) { .min = LINK_OPERSTATE_CARRIER, .max = LINK_OPERSTATE_CARRIER, }; + else if (link->network && link->network->bond) + /* Bonding slaves do not support addressing. */ + *ret = (const LinkOperationalStateRange) { + .min = LINK_OPERSTATE_ENSLAVED, + .max = LINK_OPERSTATE_ENSLAVED, + }; + else if (STRPTR_IN_SET(link->kind, "batadv", "bond", "bridge", "vrf")) + /* Some of slave interfaces may be offline. */ + *ret = (const LinkOperationalStateRange) { + .min = LINK_OPERSTATE_DEGRADED_CARRIER, + .max = LINK_OPERSTATE_ROUTABLE, + }; else *ret = LINK_OPERSTATE_RANGE_DEFAULT; } +AddressFamily link_required_family_for_online(Link *link) { + assert(link); + + if (link->network && link->network->required_family_for_online >= 0) + return link->network->required_family_for_online; + + if (link->network && operational_state_range_is_valid(&link->network->required_operstate_for_online)) + /* If RequiredForOnline= is explicitly specified, defaults to no. */ + return ADDRESS_FAMILY_NO; + + if (STRPTR_IN_SET(link->kind, "batadv", "bond", "bridge", "vrf")) + /* As the minimum required operstate for master interfaces is 'degraded-carrier', + * we should request an address assigned to the link for backward compatibility. */ + return ADDRESS_FAMILY_YES; + + return ADDRESS_FAMILY_NO; +} + bool link_ipv6_enabled(Link *link) { assert(link); @@ -1877,7 +1909,7 @@ void link_update_operstate(Link *link, bool also_update_master) { online_state = LINK_ONLINE_STATE_OFFLINE; else { - AddressFamily required_family = link->network->required_family_for_online; + AddressFamily required_family = link_required_family_for_online(link); bool needs_ipv4 = required_family & ADDRESS_FAMILY_IPV4; bool needs_ipv6 = required_family & ADDRESS_FAMILY_IPV6; diff --git a/src/network/networkd-link.h b/src/network/networkd-link.h index 985670fcd2f..d81b45bd643 100644 --- a/src/network/networkd-link.h +++ b/src/network/networkd-link.h @@ -260,3 +260,4 @@ int link_flags_to_string_alloc(uint32_t flags, char **ret); const char *kernel_operstate_to_string(int t) _const_; void link_required_operstate_for_online(Link *link, LinkOperationalStateRange *ret); +AddressFamily link_required_family_for_online(Link *link); diff --git a/src/network/networkd-state-file.c b/src/network/networkd-state-file.c index 5b2e8a2de4f..859a28aa59f 100644 --- a/src/network/networkd-state-file.c +++ b/src/network/networkd-state-file.c @@ -637,7 +637,7 @@ static int link_save(Link *link) { link_operstate_to_string(st.min), link_operstate_to_string(st.max)); fprintf(f, "REQUIRED_FAMILY_FOR_ONLINE=%s\n", - link_required_address_family_to_string(link->network->required_family_for_online)); + link_required_address_family_to_string(link_required_family_for_online(link))); fprintf(f, "ACTIVATION_POLICY=%s\n", activation_policy_to_string(link->network->activation_policy));