We can disable/enable configuration snippets per NetworkManager
version. But we must compare it against the current version
that we build, not the current API version.
In a previous patch I added deactivate_async to make sure that NM
auto re-connect waits for the IWD state to changed from "disconnecting"
to "disconnected" before starting a new activation when the user wants
to switch from one profile to another. This doesn't account for when
IWD itself goes into "disconnecting" because of a connect failure.
When IWD goes into the "disconnecting" state we call
nm_device_state_changed (NM_DEVICE_STATE_FAILED,
NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT)
immediately to give feedback to user as soon as possible. We will
return FALSE from get_autoconnect_allowed for the period the
"disconnecting" state.
Deactivating the connection translates to a Device.Disconnect dbus call
to IWD. The dbus call normally returns immediately because the
corresponding nl80211 command returns immediately but we can't rely on
that. Make sure that NMDevice waits for the IWD method return before
continuing with the new activation request when switching wifi networks.
The handler would until now check if nm_device_is_activating() was true
or the NMDevice state was "activated" to decide whether to report to
NMDevice that we'd been unexpectedly disconnected (i.e. connection
failed). However NM's "prepare" and "need auth" states correspond to
IWD's "disconnected" state because they don't involve Wifi
authentication/association.
Additionally nm_device_is_activating() returns TRUE even when NMDevice
state is "disconnected" but an activation request is pending. As a
result when switching networks, NMDevice would first save the activation
request and go into the "disconnected" state, we'd then call the IWD's
Disconnect method and when we received the IWD state change notification
to "disconnected", we'd cause the pending activation request to be
considered a failure. The handler shouldn't report a failed
connection when the NMDevice state is "disconnected".
We already avoid committing the IP configuration for external devices
(see commit 60334a2893). However, we still start DHCP/IPv6-autoconf
and, especially, we change sysctl values of the device.
To be sure that no action is taken on the device, return early from
the IP configuration phase, as in the method=disabled/ignore case.
https://bugzilla.redhat.com/show_bug.cgi?id=1530288
Previouslly, the value of ieee80211w and key_mgmt field in
wpa_supplicant.conf was defined by the value of pmf.
NM_SETTING_WIRELESS_SECURITY_PMF_DISABLE
ieee80211w=0
key_mgmt=wpa-eap
NM_SETTING_WIRELESS_SECURITY_PMF_OPTIONAL
ieee80211w=1
key_mgmt=wpa-eap wpa-eap-sha256
NM_SETTING_WIRELESS_SECURITY_PMF_REQUIRED
ieee80211w=2
key_mgmt=wpa-eap-sha256
Though these works, these does not include whole combinations.
The key_mgmt could be set independent of ieee80211w value.
For example, management frame protection could be used with
wpa-eap.
ieee80211w=2
key_mgmt=wpa-eap
And wpa-eap-sha256 could be used without management frame
protection.
ieee80211w=0
key_mgmt=wpa-eap-sha256
So this patch uses always key_mgmt=wpa-psk wpa-psk-sha256 or
key_mgmt=wpa-eap wpa-eap-sha256. By this setting, when AP
supports both, stronger algorithm will be chosen (ex. when AP
supports both wpa-eap and wpa-eap-sha256, wpa-eap-sha256 will be
chosen).
Signed-off-by: Masashi Honma <masashi.honma@gmail.com>
Especially useful, because we don't link against libnl-genl-3.so
but re-implement generic netlink support. Such code should go there
so it can be used by various components.
netlink's API is stable, and strictly defined by the integer values that make
up commands and attributes. There is little reason do disable a netlink feature
based on compile time detection of the kernel headers.
Either kernel supports it, or it will fail with an appropriate response.
Also, support for NL80211_CMD_CRIT_PROTOCOL_START was merge to kernel
in 2013. Maybe, we should now just always assume support (in the kernel
headers is there). Anyway, don't do that yet, but instead avoid the
defines and use the numeric values directly.
Add a WifiDataClass struct, that is immutable and contains all the
function pointers that were previously embedded in WifiData directly.
They are not ever modified after creation, hence this allows to have
a "static const" allocated instance of the VTable.
Also rename wifi_data_deinit() to wifi_data_unref(). It does not only
deinitialize the instance, instead it also frees it. Hence, rename it
to "unref()".
Similarly to what systemd-resolved does, introduce the concept of
"routing" domain, which is a domain in the search list that is used
only to decide the interface over which a query must be forwarded, but
is not used to complete unqualified host names. Routing domains are
those starting with a tilde ('~') before the actual domain name.
Domains without the initial tilde are used both for completing
unqualified names and for the routing decision.
The "domain" key of the D-Bus configuration dictionary specifies the
domains a configuration applies to. In DNS code we consider domains
and searches as equivalent, so they should be exported via D-Bus using
the same logic used to populate resolv.conf and for plugins.
When NM knows of the ifindex/name of the new PPP interface (through
the SetIfindex() call), it renames it. This can race with the pppd
daemon, which issues ioctl() using the interface name cached in the
global 'ifname' variable:
...
NetworkManager[27213]: <debug> [1515427406.0036] ppp-manager: set-ifindex 71
pppd[27801]: sent [CCP ConfRej id=0x1 <deflate 15> <deflate(old#) 15> <bsd v1 15>]
NetworkManager[27213]: <debug> [1515427406.0036] platform: link: setting 'ppp5' (71) name dsl-ppp
pppd[27801]: sent [IPCP ConfAck id=0x2 <addr 3.1.1.1>]
pppd[27801]: ioctl(SIOCSIFADDR): No such device (line 2473)
pppd[27801]: Interface configuration failed
pppd[27801]: Couldn't get PPP statistics: No such device
...
Fortunately the variable is exposed to plugins and so we can turn the
SetIfindex() D-Bus call into a synchronous one and then update the
value of the 'ifname' global variable with the new interface name
assigned by NM.
If IPV6CP terminates before IPCP, pppd enters the RUNNING phase and we
start IP configuration without having an IP interface set, which
triggers assertions.
Instead, add a SetIfindex() D-Bus method that gets called by the
plugin when pppd becomes RUNNING. The method sets the IP ifindex of
the device and starts IP configuration.
https://bugzilla.redhat.com/show_bug.cgi?id=1515829
We also unconditionally use them with autotools.
Also, the detection for have_version_script does
not seem correct to me. At least, it didn't work
with clang.
The strings holding the names used for libraries have also been
moved to different variables. This way they would be less error
as these variables can be reused easily and any typing error
would be quickly detected.
Some targets are missing dependencies on some generated sources in
the meson port. These makes the build to fail due to missing source
files on a highly parallelized build.
These dependencies have been resolved by taking advantage of meson's
internal dependencies which can be used to pass source files,
include directories, libraries and compiler flags.
One of such internal dependencies called `core_dep` was already in
use. However, in order to avoid any confusion with another new
internal dependency called `nm_core_dep`, which is used to include
directories and source files from the `libnm-core` directory, the
`core_dep` dependency has been renamed to `nm_dep`.
These changes have allowed minimizing the build details which are
inherited by using those dependencies. The parallelized build has
also been improved.
In some cases we might want to load device plugins from multiple
directories. A special case that I have in mind is to load plugins from
build directory subdirectories in order to run NetworkManager from the
build directory.
[thaller@redhat.com: modify original patch]
The connection.mdns setting is a per-connection setting,
so one might expect that one activated device can only have
one MDNS setting at a time.
However, with certain VPN plugins (those that don't have their
own IP interface, like libreswan), the VPN configuration is merged
into the configuration of the device. So, in this case, there
might be multiple settings for one device that must be merged.
We already have a mechanism for that. It's NMIP4Config. Let NMIP4Config
track this piece of information. Although, stricitly speaking this
is not tied to IPv4, the alternative would be to introduce a new
object to track such data, which would be a tremendous effort
and more complicated then this.
Luckily, NMDnsManager and NMDnsPlugin are already equipped to
handle multiple NMIPConfig instances per device (IPv4 vs. IPv6,
and Device vs. VPN).
Also make "connection.mdns" configurable via global defaults in
NetworkManager.conf.
Don't track the per-device configuration in NMDnsManager by
the ifname, but by the ifindex. We should consistently treat
the ifindex as the ID of a link, like kernel does.
At the few places where we actually need the ifname, resolve
it by looking into the platform cache. That is not necessarily
the same as the ifname that is currently tracked by NMDevice,
because netdev interfaces can be renamed, and NMDevice updates
it's link properties delayed. However, the platform cache has
the most recent notion of the correct interface name for an
ifindex, so if we ever hit a race here, we do it now more
correctly.
This also temporarily drops support for mdns. Will be re-added next,
but differently.
We had two separate queues, one for "SetLinkDNS" and one for
"SetLinkDomains". Merge them into one, and track the operation
as part of the new RequestItem structure.
A visible change to before is that we now would make all requests
per-interface first. Prevously, we would first make all SetLinkDNS
requests (for all interfaces) and then all SetLinkDomains requests.
It feels more correct to order the requests this way, not by
type.
The reason to merge is, that we will next get another operation
and in the current scheme we would need 3 GQueue instances.
While at it, refactor the code to use CList. We now anyway would
need a new struct to track the operation, requiring to allocate
and free it. Previously, we would only track the GVariant argument
as data of the GQueue.
Use a GHashTable instead of a GArray to construct the list of
@interfaces. Also, use NMCListElem instead of GList. With this,
the runtime is O(n*log(n)) instead of O(n^2).
I belive, we should take care that all our code has a reasonable
runtime complexity, even in common use-cases the number of elements
is small. This is not about performace, because likely we expect few
entries anyway, and the direct GArray implementation is likely faster
in those cases. It's about using the data structure that best suits the
access pattern.
The log(n) part comes from sorting the keys. I also believe we should
always aim for a stable behavior. When sending the D-Bus request to
resolved, the order of elements should be in ~some~ defined order.