Blame TODO

Packit 5756e2
So you're interested in hacking on NetworkManager?  Here's some cool
Packit 5756e2
stuff you could do...
Packit 5756e2
Packit 5756e2
* Use netlink API instead of ioctl based ethtool.
Packit 5756e2
Packit 5756e2
NetworkManager uses ethtool API to set/obtain certain settings of network
Packit 5756e2
devices. This is an ioctl based API and implmented in "src/platform/nm-platform-utils.c".
Packit 5756e2
Recently, kernel got a netlink API for the same functionality
Packit 5756e2
(https://www.kernel.org/doc/html/latest/networking/ethtool-netlink.html).
Packit 5756e2
NetworkManager should use this API if present, and fallback to the old API
Packit 5756e2
when running on older kernels. The benefit if this is that netlink provides
Packit 5756e2
notifications when settings change. The ethtool command line tool
Packit 5756e2
also implements this API, however it is under an incompatible license,
Packit 5756e2
so better don't look and make sure not to use the code.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* Add 802-1x capability to nmtui.
Packit 5756e2
Packit 5756e2
Add dialogs to nmtui for 802-1x. This will be useful for ethernet (with 802-1x
Packit 5756e2
port authentication), enterprise Wi-Fi and MACSec. From the GUI and dialog design,
Packit 5756e2
possibly get inspired by nm-connection-editor.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* Add Azure support to nm-cloud-setup.
Packit 5756e2
Packit 5756e2
Currently, nm-cloud-setup only works for EC2 (and only for IPv4). Add support for Azure
Packit 5756e2
cloud. See for example SUSE's cloud-netconfig which supports Azure
Packit 5756e2
(https://github.com/SUSE-Enceladus/cloud-netconfig,
Packit 5756e2
https://www.suse.com/c/multi-nic-cloud-netconfig-ec2-azure/). Note that cloud-netconfig
Packit 5756e2
is under an incompatible license, so be careful not to reuse any code. But that would
Packit 5756e2
anyway be almost impossible, because one is written in bash and the other in C.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* Improve our gitlab-ci integration.
Packit 5756e2
Packit 5756e2
Currently, our .gitlab-ci starts various base containers and first installs
Packit 5756e2
the necessary dependencies. That takes time and consumes bandwidth, we should
Packit 5756e2
instead use more suitable containers. We should instead use ci-templates from
Packit 5756e2
https://gitlab.freedesktop.org/freedesktop/ci-templates.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* Ethernet Network Auto-detection
Packit 5756e2
Packit 5756e2
There are various methods we can use to autodetect which wired network connection
Packit 5756e2
to use if the user connects to more than one wired network on a frequent basis.
Packit 5756e2
First, 802.1x enterprise switches broadcast frames which can be used to indicate
Packit 5756e2
that the switch supports 802.1x and thus allow NetworkManager to select an
Packit 5756e2
802.1x connection instead of blindly trying DHCP.  Second, NetworkManager could
Packit 5756e2
listen for traffic from a list of MAC addresses.  Third, NetworkManager could
Packit 5756e2
integrate 'arping' functionality to determine if a given IP address matches a
Packit 5756e2
given MAC address, and thus automatically select that connection.  All these
Packit 5756e2
methods can co-exist and be used in parallel.
Packit 5756e2
Packit 5756e2
One small caveat is that MAC addresses are trivial to spoof, so just because
Packit 5756e2
NetworkManager has discovered a certain MAC address does not mean the network
Packit 5756e2
is authenticated; only 802.1x security can assure that a network is the network
Packit 5756e2
the user expects it to be.
Packit 5756e2
Packit 5756e2
In any case, a new 'anchor-addresses' property of type string-array should be
Packit 5756e2
added to the NMSettingWired setting.  Each string element of this property
Packit 5756e2
should be of the format "<ip>/<mac>" or simply "<mac>".  The first format with
Packit 5756e2
an IP address would indicate that "arping"-type behavior should be used to
Packit 5756e2
actively detect the given MAC address; obviously if the given MAC address is
Packit 5756e2
used for passive discovery as well.  The second format simply lists a MAC
Packit 5756e2
address to passively listen for.
Packit 5756e2
Packit 5756e2
One drawback of listening or probing for known MAC addresses is an increase in
Packit 5756e2
latency during connections to ethernet networks.  The probing/listening delay
Packit 5756e2
should be a reasonable amount of time, like 4 - 5 seconds or so, and should
Packit 5756e2
only be used when a visible connection has anchor addresses.
Packit 5756e2
Packit 5756e2
Next a gboolean 'anchor-probing' variable should be added to the
Packit 5756e2
NMDeviceEthernetPrivate structure in src/nm-device-ethernet.c.  This variable
Packit 5756e2
should be set to TRUE whenever the device's carrier turns on *and* there are
Packit 5756e2
visible NMConnections with anchor addresses (ie, connections which are system-
Packit 5756e2
wide or where one of the allowed users of that connection is logged in).  Then
Packit 5756e2
probing and listening are started, which involves opening a low-level socket
Packit 5756e2
on the interface and starting the arping run or listening for MAC addresses.
Packit 5756e2
A timer is also started (don't forget to cache the timer's source ID in the
Packit 5756e2
NMDeviceEthernetPrivate data, and to cancel the timer whenever the device
Packit 5756e2
transitions to any state other than DISCONNECTED).
Packit 5756e2
Packit 5756e2
If a known MAC address is discovered as a result of probing or listening, the
Packit 5756e2
probe/listen socket, timeout, and data are cleaned up, and NetworkManager
Packit 5756e2
would begin activation of the NMConnection that specified the found MAC address
Packit 5756e2
in the 'anchor-addresses' property.  If two or more connections specify the
Packit 5756e2
same MAC address, the connection with the most recent timestamp should be
Packit 5756e2
preferred.
Packit 5756e2
Packit 5756e2
Similarly, if the probing/listening process detects 802.1x frames the device
Packit 5756e2
should be marked as requiring 802.1x authentication until the carrier drops.
Packit 5756e2
This would be accomplished by adding a new property to the NMDeviceEthernet
Packit 5756e2
object and exporting that property through the
Packit 5756e2
introspection/nm-device-ethernet.xml file.  This would allow clients like
Packit 5756e2
applets to ensure that users are aware that the device will not allow
Packit 5756e2
un-authenticated connections and that additional credentials are required to
Packit 5756e2
successfully connect to this network.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* VPN re-connect (bgo #349151)
Packit 5756e2
Packit 5756e2
NM should remember whether a VPN was connected if a connection disconnects
Packit 5756e2
(like Wi-Fi drops out or short carrier drop) or if the laptop goes to sleep.
Packit 5756e2
Upon reconnect, if the same Connection is again active, the previously
Packit 5756e2
connected VPN should be activated again as well.  Basically, don't just drop
Packit 5756e2
the VPN because Wi-Fi choked for 10 seconds, but reconnect the VPN if it was
Packit 5756e2
connected before the drop.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* VPN IP Methods
Packit 5756e2
Packit 5756e2
Some VPNs (openvpn with TAP for example) require that DHCP is run on a
Packit 5756e2
pseudo-ethernet device to obtain addressing information.  Currenty, this is not
Packit 5756e2
possible, but NM already has all the code for DHCP.  Thus, a new "method"
Packit 5756e2
key should be defined in include/NetworkManagerVPN.h to allow for DHCP to
Packit 5756e2
be performed if the VPN service daemon requests it in the IP4Config or IP6Config
Packit 5756e2
signals. In nm-vpn-connection.c, upon receipt of the D-Bus Ip4Config signal
Packit 5756e2
from the VPN plugin, NetworkManager would inspect the "method" property of the
Packit 5756e2
ip4 config dictionary.  If that property was present and set to "auto" then
Packit 5756e2
DHCP would be started using the network interface returned in the dict.  The
Packit 5756e2
nm_vpn_connection_ip4_config_get() function should be split up into two
Packit 5756e2
functions, one containing the existing code for static configuration, and a
Packit 5756e2
second for handling DHCP kickoff.  Minimal parsing of the response should be
Packit 5756e2
handled in the newly reduced nm_vpn_connection_ip4_config_get() function.
Packit 5756e2
Packit 5756e2
To handle DHCP, the NMVPNConnectionPrivate structure should have two members
Packit 5756e2
added:
Packit 5756e2
Packit 5756e2
    NMDHCPManager *dhcp_manager;
Packit 5756e2
    NMDHCPClient  *dhcp4_client;
Packit 5756e2
Packit 5756e2
which would be initialized in the new DHCP handler code split off from
Packit 5756e2
nm_vpn_connection_ip4_config_get().  These new members would be disposed of in
Packit 5756e2
both vpn_cleanup() and dispose(), though remember to stop any ongoing DHCP
Packit 5756e2
transaction when doing so (see dhcp4_cleanup() in nm-device.c for example code).
Packit 5756e2
For basic code to start the DHCP transaction, see dhcp4_start() in nm-device.c
Packit 5756e2
as well.  After calling nm_dhcp_manager_start_ip4() and connecting the signals
Packit 5756e2
to monitor success and failure, the VPN IP4 config handler would simply return
Packit 5756e2
without changing VPN state, unless a failure occurred.
Packit 5756e2
Packit 5756e2
Then, when the DHCP transaction succeeds, which we'd know by checking the
Packit 5756e2
DHCP client state changes in the "state-changed" signal handler we attached to
Packit 5756e2
the DHCP client object returned from nm_dhcp_manager_start_ip4(), the code
Packit 5756e2
would retrieve the completed NMIP4Config object from the DHCP client using the
Packit 5756e2
nm_dhcp_client_get_ip4_config() function, and then proceed to execute
Packit 5756e2
essentially the bottom-half of the existing nm_vpn_connection_ip4_config_get()
Packit 5756e2
function to merge that config with user overrides and apply it to the VPN
Packit 5756e2
tunnel interface.  Other state changes from the DHCP client might trigger a
Packit 5756e2
failure of the VPN connection, just like DHCP timeouts and lease-renewal
Packit 5756e2
failures do for other devices (see dhcp_state_changed() in nm-device.c).
Packit 5756e2
Packit 5756e2
Packit 5756e2
* VPN Service Daemon Secret Requests
Packit 5756e2
Packit 5756e2
In addition to NM asking the service daemons whether more secrets are required,
Packit 5756e2
VPN service daemons (like nm-vpnc-service, nm-openvpn-service, etc) should be
Packit 5756e2
able to ask NetworkManager to provide secrets during the connection attempt. To
Packit 5756e2
do this, the plugin should advertise its ability to handle out-of-band secrets
Packit 5756e2
in its .service file via the key 'async-secrets=true'.  NetworkManager would
Packit 5756e2
check that key and if present activate the VPN as normal, but skip the explicit
Packit 5756e2
NeedSecrets calls.
Packit 5756e2
Packit 5756e2
Instead, a new "SecretsRequired" signal would be added to
Packit 5756e2
introspection/nm-vpn-plugin.xml (and corresponding helper code added to
Packit 5756e2
libnm-glib/nm-vpn-plugin.c) that would be emitted when the plugin determined
Packit 5756e2
that secrets were required.  This signal would have D-Bus signature of "sas"
Packit 5756e2
for the arguments [ <s:uuid>, <as:secrets> ] with the <uuid> obviously being
Packit 5756e2
the connection UUID, and <secrets> being an array of strings of plugin-specific
Packit 5756e2
strings the plugin requires secrets for.  This array of strings would then be
Packit 5756e2
passed as the "hints" parameter in nm-vpn-connection.c when secrets are
Packit 5756e2
requested from agents in a subsequent nm_settings_connection_get_secrets() call.
Packit 5756e2
At this time the agent code only allows one hint per request, so we may need to
Packit 5756e2
extend that to allow more than one hint.
Packit 5756e2
Packit 5756e2
Thus when connecting if the plugin supported async secrets NetworkManager would
Packit 5756e2
still request existing secrets (without interactivity) and send them to the
Packit 5756e2
VPN service daemon in the Connect D-Bus method, then wait for the service daemon
Packit 5756e2
to either request secrets asynchronously via the SecretsRequired signal or to
Packit 5756e2
signal successful connection via the Ip4Config signal.
Packit 5756e2
Packit 5756e2
The vpnc plugin would need to be reworked to open a pipe to vpnc's stdout and
Packit 5756e2
stdin file descriptors to capture any authentication messages, and to match
Packit 5756e2
these messages to known secrets request strings.  When receiving one of these
Packit 5756e2
strings the plugin would determine which secret was being requested and then
Packit 5756e2
emit the SecretsRequired signal to NetworkManager.  This would also imply that
Packit 5756e2
nm-vpnc-service exectutes vpnc with the "--xauth-inter" argument to enable
Packit 5756e2
challenge-response and does not use the "--non-inter" flag which suppresses that
Packit 5756e2
behavior.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* WPS
Packit 5756e2
Packit 5756e2
wpa_supplicant has support for WPS (Wifi Protected Setup, basically Bluetooth-
Packit 5756e2
like PIN codes for setting up a wifi connection) and we should add support for
Packit 5756e2
this to NetworkManager too.  APs that support WPS will say so in their beacon
Packit 5756e2
IEs which are contained in the "WPA" and "RSN" properties of the BSS object
Packit 5756e2
exported by the supplicant, and can be processed in src/nm-wifi-ap.c's
Packit 5756e2
foreach_property_cb() function.  We should add some private fields to the
Packit 5756e2
NMAccessPoint object (defined in nm-wifi-ap.c) to remember whether a specific
Packit 5756e2
AP supports WPS and what WPS methods it supports, and expose that over D-Bus to
Packit 5756e2
GUI clients as well.
Packit 5756e2
Packit 5756e2
There are two common WPS setup methods: PIN and button.  For PIN, the router
Packit 5756e2
either displays a random PIN on an LCD or the router's web UI, or a static PIN
Packit 5756e2
is printed on the router itself.  The user enters that PIN instead of a PSK
Packit 5756e2
when connecting.  For the "button" method, the router has a physical button that
Packit 5756e2
when pushed, allows any client to connect for a short period of time.
Packit 5756e2
Packit 5756e2
We'll then need to add some properties to the NMSettingWirelessSecurity setting
Packit 5756e2
for the WPS PIN code so that when the user enters it through the GUI, it can
Packit 5756e2
be passed back to NM.  And we'll need to figure out some mechanism for passing
Packit 5756e2
back an indication that the user pushed the button on the router for the
Packit 5756e2
pushbutton method.
Packit 5756e2
Packit 5756e2
When connecting to a new access point that supports WPS, the GUI client would
Packit 5756e2
call the AddAndActivateConnection method and wait for NM to request secrets.
Packit 5756e2
NM would determine that the AP supports WPS, and request WPS secrets from the
Packit 5756e2
applet.  The applet would ask the user for a PIN, or to push the button on the
Packit 5756e2
AP, instead of asking for a passphrase or PSK.  When the user has entered the
Packit 5756e2
PIN or pushed the button, the applet returns this information to NM, which
Packit 5756e2
proceeds with the connection.
Packit 5756e2
Packit 5756e2
NM sends the correct wpa_supplicant config for WPS to the supplicant, and waits
Packit 5756e2
for the connection to occur.  WPS can only be used the *first* time, so after a
Packit 5756e2
first successful connection, NM must request the actual hexadecimal PSK from
Packit 5756e2
wpa_supplicant via D-Bus, and store that PSK in the connection, clear any WPS
Packit 5756e2
PIN code from the connection, and save the connection to backing storage.
Packit 5756e2
Packit 5756e2
Any applet GUI should also allow the user to enter the PSK instead of completing
Packit 5756e2
association using WPS, since quite a few routers out there are broken, or
Packit 5756e2
because the user has no physical access to the router itself, but has been given
Packit 5756e2
as passphrase/PSK instead.
Packit 5756e2
Packit 5756e2
Packit 5756e2
* Better Tablet/Mobile Behavior
Packit 5756e2
Packit 5756e2
There are a few components to this:
Packit 5756e2
Packit 5756e2
1) kernel driver and hardware capabilities: most mobile devices use periodic
Packit 5756e2
background scanning to quickly determine whether a known SSID is available and
Packit 5756e2
notify the connection manager to connect to it.  This typically requires special
Packit 5756e2
capabilities and good powersave/sleep support from the Wi-Fi kernel driver.
Packit 5756e2
There is a background scanning API in nl80211, but we need to determine how many
Packit 5756e2
SSIDs each driver allows for background scanning, and based on that number, give
Packit 5756e2
the driver the most recent N SSIDs.  We still need to periodically wake the
Packit 5756e2
device up and do a full scan just in case the user is near a known SSID that was
Packit 5756e2
not in the N top recently used networks.  This is also beneficial to normal
Packit 5756e2
desktop use-cases.
Packit 5756e2
Packit 5756e2
wpa_supplicant doesn't currently provide an explicit interface for sending SSIDs
Packit 5756e2
to the driver for background scanning, but could simply send a list using
Packit 5756e2
configured networks.  However, NM currently does not send *all* configured
Packit 5756e2
connections' SSIDs to the supplicant, so that's something we should do first
Packit 5756e2
to optimize connection times.  To do this, NM would need to order all networks
Packit 5756e2
using the NM timestamp and convert that into a supplicant priority number, which
Packit 5756e2
would need to be adjusted periodically when the timestamp was updated.  This
Packit 5756e2
would involve tracking each network (exposed by the supplicant as a D-Bus
Packit 5756e2
object) and making sure they were added, deleted, and updated when the backing
Packit 5756e2
NMConnection objects changed.  One complication is that the supplicant
Packit 5756e2
requires secrets for various network types when the network is added via D-Bus,
Packit 5756e2
and NetworkManager might not have those secrets yet.  We may need to modify
Packit 5756e2
the supplicant allow for *all* secrets (PSKs, WEP keys, etc) to be requested
Packit 5756e2
on-demand, not just EAP secrets like 802.1x passwords.  We then need to fix
Packit 5756e2
up the supplicant's D-Bus interface to actually send requests for secrets out
Packit 5756e2
over D-Bus (like wpa_supplicant_eap_param_needed() does for the socket-based
Packit 5756e2
control interface) and to handle the resulting reply from a D-Bus client like
Packit 5756e2
wpa_supplicant_ctrl_iface_ctrl_rsp() does.
Packit 5756e2
Packit 5756e2
With the secrets request stuff and priority handling in place, wpa_supplicant
Packit 5756e2
would control network selection and roaming (based on the priorities NM gave it
Packit 5756e2
of course) instead of NetworkManager itself, and hopefully lead to a faster WiFi
Packit 5756e2
connection process.
Packit 5756e2
Packit 5756e2
2) single-device-at-a-time with overlapping connections: this is also probably
Packit 5756e2
the best route to go for desktop use-cases as well.  Instead of bringing all
Packit 5756e2
available connections up, only bring up the "best" connection at any given
Packit 5756e2
time based on the current priority list (which is roughly Ethernet > Wi-Fi >
Packit 5756e2
3G/Bluetooth).  However, to ensure seamless connectivity, when one connection
Packit 5756e2
begins to degrade, the next-best connection should be started before the
Packit 5756e2
current one is terminated, such that there is a small amount of overlap.
Packit 5756e2
Consequently the same behavior should be used when a better connection becomes
Packit 5756e2
available.  This behavior should be suspended when special connections like
Packit 5756e2
Internet Connection Sharing ones are started, where clearly the priorities
Packit 5756e2
are different (ie, for Mobile Hotspot 3G > WiFi).