Commit graph

17889 commits

Author SHA1 Message Date
Jan Vaclav
733cd99400 wip 2025-12-18 14:51:51 +01:00
Beniamino Galvani
427a7cf257 nmcli: start the agent only after updating the connection
When connecting to a wifi network and providing the password on the
command line, nmcli first looks if there is a compatible connection to
reuse. If there is not, it creates and activates a new one via a
single call to AddAndActivate().

If there is a compatible connection, nmcli first calls Update() on it
to set the new password and then Activate() to bring it up. Before
that, it registers a secret agent that can prompt for a new password
in case of authentication failure.

However, as soon as nmcli registers a secret agent, NM tries to
activate again the connection if it was blocked due to a previous
authentication failure. This connection attempt is going to fail
because it still uses the old password, as new one hasn't been set via
Update().

Change the order of operations to register the agent after Update()
and before Activate().

Reproducer:

 nmcli device wifi connect SSID password BAD_PASSWORD
 nmcli device wifi connect SSID password GOOD_PASSWORD

Fixes: c8ff1b30fb ('nmcli/dev: use secret agent for nmcli d [wifi] connect')
2025-12-17 10:55:51 +01:00
Beniamino Galvani
3a4e18e302 nmcli: fix "device wifi connect" command with existing connection
Executing this command twice, or when a connection profile already
exists for the SSID:

  nmcli device wifi connect $SSID password $PASSWORD

returns error:

  Error: 802-11-wireless-security.key-mgmt: property is missing.

When setting the password nmcli was wiping the existing wireless
security setting.

Fixes: c8ff1b30fb ('nmcli/dev: use secret agent for nmcli d [wifi] connect')

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1688
2025-12-17 10:55:50 +01:00
Íñigo Huguet
599cc1ed1d std-aux: use _nm_strerror_r
The function strerror_r returns an int per POSIX spec, but GNU version
returns char *. Using it fails the compilation in Alpine, so use
_nm_strerror_r instead that handles both cases.

Fixes: 41e28b900f ('daemon-helper: add read-file-as-user')
2025-12-12 15:07:53 +01:00
Beniamino Galvani
1a52bbe7c9 libnm: add function to copy a certificate or key as user
Add a new public function nm_utils_copy_cert_as_user() to libnm. It
reads a certificate or key file on behalf of the given user and writes
it to a directory in /run/NetworkManager. It is useful for VPN plugins
that run as root and need to verify that the user owning the
connection (the one listed in the connection.permissions property) can
access the file.
2025-12-12 12:43:15 +01:00
Beniamino Galvani
57eb4a5bc6 vpn: check that plugin supports private connections
Only allow private VPN connections if the VPN plugin declares the
supports-safe-private-file-access capability. Also check that the
private connection doesn't have more than one owner.
2025-12-12 12:42:01 +01:00
Beniamino Galvani
10db4baeb6 vpn: add nm_vpn_plugin_info_supports_safe_private_file_access()
The new API indicates that the VPN plugin supports reading files
(certificates, keys) of private connections in a safe way
(i.e. checking user permissions), or that it doesn't need to read any
file from disk.
2025-12-12 12:41:28 +01:00
Beniamino Galvani
8d8edda3f4 core,libnm-core: introduce property flag for certificate and keys
If we add a new property in the future and it references a certificate
or key stored on disk, we need to also implement the logic to verify
the access to the file for private connections.

Add a new property flag NM_SETTING_PARAM_CERT_KEY_FILE to existing
certificate and key properties, so that it's easier to see that they
need special treatment. Also add some assertions to verify that the
properties with the flag are handled properly.

While at it, move the enumeration of private-files to the settings.
2025-12-12 12:38:50 +01:00
Beniamino Galvani
e85cc46d0b core: pass certificates as blobs to supplicant for private connections
In case of private connections, the device has already read the
certificates and keys content from disk, validating that the owner of
the connection has access to them. Pass those files as blobs to the
supplicant so that it doesn't have to read them again from the
filesystem, creating the opportunity for TOCTOU bugs.
2025-12-12 12:38:50 +01:00
Beniamino Galvani
a1928b4459 device: read private files in stage2
During stage2 (prepare) of an activation, check if the connection is
private and if it contains any certificate/key path. If so, start
reading the files and delay stage2. Once done, store the files'
content into priv->private_files.table and continue the activation.
2025-12-12 12:38:49 +01:00
Beniamino Galvani
9703305122 core: add functions to read private files of connections
Add function nm_utils_read_private_files(). It can be used to read a
list of paths as the given user. It spawns the daemon-helper to read
each path and returns asynchronously a hash table containing the files
content.

Also add nm_utils_get_connection_private_files_paths() to return a
list of file paths referenced in a connection. The function currently
returns only 802.1x file paths for certificates and keys.
2025-12-12 12:38:49 +01:00
Beniamino Galvani
932b85f7e7 supplicant: rename variables
Rename uid to to blob_id, and con_uid to con_uuid.
2025-12-12 12:38:49 +01:00
Beniamino Galvani
4e26403c4a core: support returning binary output from the daemon helper
The full output of the daemon helper is added to a NMStrBuf, without
interpreting it as a string (that is, without stopping at the first
NUL character).

However, when we retrieve the content from the NMStrBuf we assume it's
a string. This is fine for certain commands that expect a string
output, but it's not for other commands as the read-file-as-user one.

Add a new argument to nm_utils_spawn_helper() to specify whether the
output is binary or not. Also have different finish functions
depending on the return type.
2025-12-12 12:38:49 +01:00
Beniamino Galvani
bd2484d1a9 supplicant: remove blobs before adding new ones
When connecting, we add the blobs to the Interface object of the
supplicant. Those blobs are not removed on disconnect and so when we
try to add blobs with the same id, the supplicant returns an error.

Make sure we start from a clean slate on each connection attempt, by
deleting all existing blobs. Probably we should also delete the added
blobs on disconnect, but that's left for a future improvement.
2025-12-12 12:38:48 +01:00
Beniamino Galvani
41e28b900f daemon-helper: add read-file-as-user
Add a new command to read the content of a file after switching to the
given user. This command can be used to enforce Unix filesystem
permissions when accessing a file on behalf of a user.
2025-12-12 12:38:48 +01:00
Beniamino Galvani
6c1e04fc61 helpers: move helper programs to the same directory
Create a new 'nm-helpers' directory for all the helper programs, to
avoid having too many subdirs in the src directory.
2025-12-12 12:38:48 +01:00
Beniamino Galvani
2739850b78 libnm-core, core: add permission helpers
Add utility functions to get the number of users and the first user
from the connection.permissions property of a connection.
2025-12-12 12:38:48 +01:00
Íñigo Huguet
13bfa44ceb nm-version: set API_VERSION with MICRO+1 (temporary)
In the past, stable branches used odd micro numbers as development micro
version. Because of that, NM_API_VERSION was defined with MICRO+1 so we
don't get warnings during development.

As we stopped using odd micro=devel it is wrong to set MICRO+1 on odd
releases. Final users of 1.52.3 has NM_API_VERSION 1.52.4.

However, during development we need to have MICRO+1. For example, if we
are working on top of 1.52.3 towards the next 1.52.4, we define new
symbols with NM_AVAILABLE_IN_1_52_4. Because of that, we get compilation
failures until we finally bump to 1.52.4, just before the release. The
CI remains red until then, potentially missing many bugs.

For now, just set MICRO+1 all the time. It is wrong, but it was wrong
half of the time anyway, and at least we'll have a green CI until we
implement a definitive solution.
2025-12-12 12:17:58 +01:00
Beniamino Galvani
dad4da06b1 libnm-core: fix the documentation of the gateway IP property
The D-Bus API documentation of the IPv4 and IPv6 settings say:

* addresses
 	Deprecated in favor of the 'address-data' and 'gateway'
 	properties, but this can be used for backward-compatibility
 	with older daemons. Note that if you send this property the
 	daemon will ignore 'address-data' and 'gateway'.

* gateway
       The gateway associated with this configuration. This is only
       meaningful if "addresses" is also set.

This documentation wrongly suggests that at D-Bus level "gateway"
requires "addresses", while it actually requires "address-data". The
reason for the inconsistency is that the gateway documentation is
common between nmcli and D-Bus and it refers to the "address" GObject
property, not to the D-Bus property.

Fix this inconsistency by not explicitly mentioning the property name.

Fixes: 36156b70dc ('libnm: Override parts of nm-setting-docs.xml')

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2319
2025-12-04 16:40:07 +01:00
Jan Vaclav
d40e88fd02 test-link: test bond with use_carrier=1
`use_carrier` is removed from kernel since 6.18 [1], and returns
the following error if set to 0:
> option obsolete, use_carrier cannot be disabled

This causes a failure of test-link-linux, so let's set it to 1.

[1] https://lore.kernel.org/all/2029487.1756512517@famine/
2025-12-04 11:51:28 +00:00
Jan Vaclav
8e72e6b4fb aux-intern: add explicit cast for strchr()
`addr` is always reallocated in this branch, so it
is safe to cast the result of strchr to char* here
to silence the const-qualifier warning.
2025-12-04 11:51:28 +00:00
Jan Vaclav
9e70f31c8c initrd: remove const qualifier from temporary variable
`argument` is not const, but `tmp` is. We use `tmp`
for reading arguments one by one, but we cannot add
a null byte to separate the key and value if it is const.

Make it non-const, so that `val[0] = '\0';` does not fail.
2025-12-04 11:51:28 +00:00
Jan Vaclav
ac427b25fb core, impl: drop const qualifier from split outputs
We write into the buffer returned by nm_strsplit_set_full(), even
though it is returned as `const char**`. The function description
claims this is fine:

> *   It is however safe and allowed to modify the individual strings in-place,
> *   like "g_strstrip((char *) iter[0])".

Remove the const qualifier via cast so that it does not raise errors.
2025-12-04 11:51:28 +00:00
Jan Vaclav
754b87e1c4 supplicant: separate input and local value
We reallocate this value in the function, which is necessary
because we write into it, and the input is const.

Move the allocation into a local variable instead of overwriting
the input pointer, because we are also pointing to it via
`char* s`, which is not const.
2025-12-04 11:51:28 +00:00
Jan Vaclav
5f6beb0e57 nm-udev-utils: constify strstr-output variable
`subsystem_full` is const, so `s` needs to be const too.
Reorder the NULL-byte write so that we are not writing
into a const char* (the underlying memory is the same).
2025-12-04 11:51:28 +00:00
Jan Vaclav
487ca30256 all: const-ify str(r)chr output variables where possible 2025-12-04 11:51:28 +00:00
Jan Vaclav
a07961cfbe systemd: selectively backport "Fix constness issues with newer glibc"
NetworkManager is failing to build on Rawhide with the following errors:
../src/libnm-systemd-shared/src/basic/string-util.h:33:16: error: return discards ‘const’ qualifier from pointer target type [-Werror=discarded-qualifiers]
   33 |         return strstr(haystack, needle);
      |                ^~~~~~
In file included from ../src/libnm-systemd-shared/src/basic/fd-util.c:30:
../src/libnm-systemd-shared/src/basic/sort-util.h: In function ‘bsearch_safe’:
../src/libnm-systemd-shared/src/basic/sort-util.h:34:16: error: return discards ‘const’ qualifier from pointer target type [-Werror=discarded-qualifiers]
   34 |         return bsearch(key, base, nmemb, size, compar);
      |                ^~~~~~~

This is fixed in systemd by commit 0bac1ed2422f15308414dd1e9d09812a966b0348:
> Latest glibc uses _Generic to have strstr() and other functions return
> const char* or char* based on whether the input is a const char* or a
> char*. This causes build failures as we previously always expected a char*.
>
> Let's fix the compilation failures and add our own macros similar to glibc's
> to have string functions that return a mutable or const pointer depending on
> the input.

Selectively backport the changes we need to fix building.
2025-12-04 11:51:28 +00:00
Mitchell Augustin
bcb96a1b19 core: add handlers for SaePasswordMismatch signal
Trigger a new auth request to the user when the SaePasswordMismatch
signal is received from wpa_supplicant.

Closes #904
2025-12-02 14:25:12 +00:00
Popax21
a9f2c15663 connectivity: add per-device check-connectivity setting
Adds a new `check-connectivity` setting to the `device` section which can be
used to disable the connectivity check for a particular device.
2025-12-02 10:04:20 +01:00
Beniamino Galvani
8a9b17071b version: add 1.58 macros 2025-11-28 19:05:59 +01:00
Antonio Alvarez Feijoo
636fb5ef24 systemd: install initrd services using a generator
Since both `NetworkManager.service` and `NetworkManager-initrd.service` are
allocated for the same bus name (`org.freedesktop.NetworkManager`) and this is
not allowed, the best option is to use a systemd generator to install them only
in the initrd, instead of setting fixed Install sections.

Fixes #1814
2025-11-20 13:26:15 +00:00
Popax21
6e2de1d2b3 core: restrict connectivity check lookups to per-link DNS if available
Restrict connectivity check DNS lookups to just the relevant link if the link
has a per-link DNS resolver configured. This change was previously discussed as
part of issue
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1836, and
brings NM's behavior back in line with the behavior documented in the man page.

The connectivity check checks for a per-link DNS resolver by querying
systemd-resolved's `ScopeMask` for the link; this involves a small D-Bus
roundtrip, but is ultimately the more flexible solution since it is also capable
of dealing with per-link DNS configuration stemming from other sources.

Fixes: e6dac4f0b6 ('core: don't restrict DNS interface when performing connectivity check')
2025-11-19 14:54:40 +00:00
Matthieu Baerts (NGI0)
8caa781270 mptcp: set the laminar flag by default
By default, the MPTCP limits have 'add_addr_accepted' set to 0. It means
that when the other peer announces an additional address it can be
reached from, the receiver will not try to establish any new subflows to
this address. If this limit is increased, and without the new 'laminar'
flag, the MPTCP in-kernel path-manager will select the source address by
looking at the routing tables to establish this new subflow.

This is not ideal: very likely, the source address will be the one
linked to the default route and a new subflow from the same interface as
the initial one will be created instead of using another path.

This is especially problematic when the other peer has set the 'C-flag'
in the MPTCP connection request (MP_CAPABLE). This flag can be set to
tell the other side that the peer will not accept extra subflows
requests sent to its initial IP address and port: typically set by a
server using an anycast address, behind a legacy Layer 4 load balancer.

It sounds better to add the 'laminar' flag by default to pick the source
address from well-defined MPTCP endpoints, rather than relying on
routing rules which will likely not pick the most interesting solution.

Note that older kernels will accept unsupported flags, and ignore them.
So it is fine to have the new flag added by default even if it is not
supported.

Signed-off-by: Matthieu Baerts (NGI0) <matttbe@kernel.org>
2025-11-19 12:54:09 +00:00
Matthieu Baerts (NGI0)
2b03057de0 mptcp: add 'laminar' endpoint support
This new endpoint type has been recently added to the kernel in v6.18
[1]. It will be used to create new subflows from the associated address
to additional addresses announced by the other peer. This will be done
if allowed by the MPTCP limits, and if the associated address is not
already being used by another subflow from the same MPTCP connection.

Note that the fullmesh flag takes precedence over the laminar one.
Without any of these two flags, the path-manager will create new
subflows to additional addresses announced by the other peer by
selecting the source address from the routing tables, which is harder to
configure if the announced address is not known in advance.

The support of the new flag is easy: simply by declaring a new flag for
NM, and adding it in the related helpers and existing checks looking at
the different MPTCP endpoint. The documentation now references the new
endpoint type.

Note that only the new 'define' has been added in the Linux header file:
this file has changed a bit since the last sync, now split in two files.
Only this new line is needed, so the minimum has been modified here.

Link: https://git.kernel.org/torvalds/c/539f6b9de39e [1]
Signed-off-by: Matthieu Baerts (NGI0) <matttbe@kernel.org>
2025-11-19 12:54:09 +00:00
Beniamino Galvani
3b10b88290 core: fix rate-limit test failures
It's possible that the first timeout gets delayed; therefore the
interval between the first and the second callback can be less than
one second, and the budget doesn't refill completely.

Schedule the second timeout from the first callback to guarantee that
at least one second passes between the callbacks.

Fixes: ff0c4346fc ('core: add rate-limiting helper')
2025-11-18 15:02:05 +01:00
Íñigo Huguet
d687768c61 libnm: move hsr symbols to the right version
These symbols has been added to the 1.54.2 stable branch, so they are
actually available since then.
2025-11-18 10:39:49 +01:00
Beniamino Galvani
22631d557a ndisc: rate limit messages about invalid RAs
Sending and receiving RA is repeated periodically. Don't spam logs
with the same message again and again. Rate limit the message to 6
every 12 hours per type and per ndisc instance.
2025-11-12 14:05:30 +01:00
Beniamino Galvani
ff0c4346fc core: add rate-limiting helper
It can be used to perform an action like logging a message with
simple rate limiting.
2025-11-12 11:48:59 +01:00
Robin Ebert
306f9c490b vpn: Use nm_device_create_l3_config_data_from_connection if possible
Using nm_device_create_l3_config_data_from_connection in favor of
nm_l3_config_data_new_from_connection allows the connection
properties: connection.mdns, connection.llmnr,
connection.dns-over-tls, connection.dnssec, connection.mptcp-flags,
and ipv6.ip6-privacy to be read from the vpn's connection settings
allowing them to be applied to vpn connections.
2025-10-27 10:31:16 +01:00
Robin Ebert
441e77a44c core: Make nm_device_create_l3_config_data_from_connection behave as expected
Currently nm_device_create_l3_config_data_from_connection uses the
connection applied to the given device for some properties.  Altough
this currently works since all users of
nm_device_create_l3_config_data_from_connection provide the applied
connection as parameter, it behaves unexpectedly when another
connection is given.
2025-10-27 09:58:07 +01:00
Íñigo Huguet
e06aaba1ca core: mark as managed-type=removed when unrealize
This is needed to ensure that the right CleanupType is chosen when
calling to nm_device_state_changed() a bit later. With this change
CLEANUP_TYPE_REMOVED will be used instead of CLEANUP_TYPE_DECONFIGURE,
which is wrong because the device has already disappeared.
2025-10-24 05:27:18 +00:00
Íñigo Huguet
32cbf4c629 ip: shared: stop using the global forwarding
As we introduced the ipv4.forwarding property in a8a2e6d727 ('ip-config:
Support configuring per-device IPv4 sysctl forwarding option'), we must
not enable or disable the global forwarding setting in the kernel, as it
affects to all the devices, maybe forcing them to behave in a way
different to what the user requested in ipv4.forwarding.

Instead, we need to selectively enable or disable the per-device forwarding
settings. Specifically, only devices activated with ipv4.forwarding=auto
must have their forwarding enabled or disabled depending on shared
connections. Devices with yes/no must not be affected by shared connections.

Also, devices with ipv4.forwarding=auto must get the proper forwarding value
on activation, but also change it when shared connections appear or
disappear dynamically. Use the new sharing-ipv4-change signal from
nm_manager to achieve it.

Fixes: a8a2e6d727 ('ip-config: Support configuring per-device IPv4 sysctl forwarding option')
2025-10-24 05:27:18 +00:00
Íñigo Huguet
8faa33b9d4 manager: add sharing-ipv4-changed signal
This signal notifies about the "sharing state", that's it, when there
is at least one shared connection active or not. Each device informs
to nm_manager when a shared connection is activated or deactivated
and nm_manager emits this signal when the first shared connection is
activated or the last one is deactivated.

For now we're only interested in IPv4 forwarding as it's the only one
that we need to track from nm_device (in following commits).

Fixes: a8a2e6d727 ('ip-config: Support configuring per-device IPv4 sysctl forwarding option')
2025-10-24 05:27:18 +00:00
Íñigo Huguet
d58d0a793e ip: restore IP forwarding on device deconfiguration
With the ipv4.forwarding property we may modify the forwarding sysctl of
the device on activation. In next commits, we will also modify it if the
connection is shared, instead of modifying the global forwarding.

Restore the forwarding value to the default one when the device is
deconfigured for any reason.

Fixes: a8a2e6d727 ('ip-config: Support configuring per-device IPv4 sysctl forwarding option')
2025-10-24 05:27:18 +00:00
Íñigo Huguet
f2a2e49d07 Revert "policy: refresh IPv4 forwarding after connection activation and disconnection"
This reverts commit 2ad5fbf025.

It is actually a partial revert. The changes to documentation don't need
to be reverted.

Fixes: 2ad5fbf025 ('policy: refresh IPv4 forwarding after connection activation and disconnection')
2025-10-24 05:27:18 +00:00
Mitchell Augustin
6dd07a80e5 core: add handlers for PskMismatch signal
Trigger a new PSK request to the user when the PskMismatch
signal is received from wpa_supplicant.

Closes #904
2025-10-23 14:36:54 +00:00
Jan Vaclav
b1614ffb90 l3cfg: add info about n-acd eBPF state to log messages 2025-10-22 21:49:56 +02:00
Jan Vaclav
8d33aaa5b6 build: drop "ebpf" configuration for n-acd compilation
Since we now check whether the user's machine supports
eBPF at runtime, we can drop all of this build machinery.
2025-10-22 21:48:39 +02:00
Jan Vaclav
191ebb439a n-dhcp4: re-import git-subtree for 'src/n-dhcp4'
git subtree pull --prefix src/n-dhcp4 git@github.com:nettools/n-dhcp4.git master --squash
2025-10-22 20:09:41 +02:00
Jan Vaclav
2f35c94628 Squashed 'src/n-dhcp4/' changes from 2707213e3e..0d4dcc9bb4
0d4dcc9bb4 n-dhcp4: introduce n_dhcp4_c_connection_clear_client_ip() helper
433c57ab2e n-dhcp4: Do not set ciaddr in DISCOVER state.
feacc2cccd n-dhcp4: change the default DSCP value to 0
b64e2c62e8 n-dhcp4: support setting the DSCP value
6cfa9d84d0 n-dhcp4: set xid of the DHCP header for RELEASE and DECLINE message

git-subtree-dir: src/n-dhcp4
git-subtree-split: 0d4dcc9bb45d5a63d53a787289ad79823343e624
2025-10-22 20:09:23 +02:00