Compare commits

..

578 commits
1.54.2 ... main

Author SHA1 Message Date
Rahul Rajesh
19b065bc4a merge: branch 'rr/controller-dhcp-send-release'
device: send dhcp send release before device removed

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2400
2026-04-30 15:31:39 +00:00
Gris Ge
1747eb96d6 manager: Ensure DHCP interface delete first when daemon stop
Given linux bridge/bond holds DHCP config with
`ipv4.dhcp-send-release: ture` or `ipv6.dhcp-send-release: true`,
when stopping NetworkManager daemon, then NM daemon might
remove/deactivate physical interface first causing DHCP release packet
cannot be delivered.

To fix the issue, we sort the device deletion to let software device
that holds DHCP config to remove first.

Merge Request: https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2379

Co-authored-by: Rahul Rajesh <rajeshrah22@gmail.com>
2026-04-29 17:04:04 -04:00
Rahul Rajesh
09784fcce3 device: cleanup DHCP before devices removed
Add _dev_ipdhcpx_cleanup in __set_state_full in DEACTIVATING STATE
before STATE_CHANGED signal is emitted to ensure DHCP RELEASE
packet is sent.

Assisted-by: Cursor with Claude Opus 4.5
2026-04-29 17:03:57 -04:00
Jan Vaclav
9303996b44 merge: branch 'jv/coverity'
coverity: fix bugs found by static analysis

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2394
2026-04-15 08:33:32 +00:00
Jan Vaclav
ca326bd636 libnm/tests: fix dead code in WireGuard roundtrip test
The inner condition at line 4086 duplicated the outer check for
NM_CONNECTION_SERIALIZE_ALL, making the else-if branch for
NM_CONNECTION_SERIALIZE_WITH_NON_SECRET unreachable. This meant
the non-secret serialization path was never actually tested.

Restructure to make both branches reachable.

Found by Coverity (CID: DEADCODE).

Fixes: 395a78618b ('libnm/tests: add tests for creating wireguard connection profiles')

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:54:12 +02:00
Jan Vaclav
3d4ad7b4ba libnm: fix wrong variable in route attribute validation error message
The validation checks 'addr' (the extracted address portion before '/')
but the error message prints 'string' (the full input including the
prefix). For input like "192.168.1.999/24", the error would show the
full string instead of just the invalid address part.

Found by Coverity (CID: COPY_PASTE_ERROR).

Fixes: 539db43619 ('libnm: avoid heap allocation for checking valid routes in nm_ip_route_attribute_validate()')

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:54:12 +02:00
Jan Vaclav
33871478b7 initrd: fix use-after-free when multiple iBFT entries fail
The error variable is declared outside the loop but freed with
g_error_free() which does not reset the pointer to NULL. On the
next iteration, g_set_error() sees a non-NULL *err (dangling pointer)
and error->message dereferences freed memory.

Use g_clear_error() instead which also resets the pointer.

Found by Coverity (CID: USE_AFTER_FREE).

Fixes: ecc074b2f8 ('initrd: add command line parser')

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:54:12 +02:00
Jan Vaclav
00f9a3d862 nmtui/wireguard: fix peer leak when adding new peer
nm_wireguard_peer_new() returns a new peer with refcount 1.
nmt_wireguard_peer_editor_new() takes its own copy via
g_value_dup_boxed(), so the original peer was never unreffed.

Unref the peer after passing it to the editor.

Found by Coverity (CID: RESOURCE_LEAK).

Fixes: b0f5b1d97a ('tui: add WireGuard support to nmtui')
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:54:12 +02:00
Jan Vaclav
8685ac1845 dns: fix infinite loop in assertion checking search domains
The loop condition checked the same pointer twice instead of checking
the array element: `ip_data->domains.search && ip_data->domains.search`
should be `ip_data->domains.search && ip_data->domains.search[i]`.

As written, the loop would never terminate when `search` is non-NULL
(only in debug builds with NM_MORE_ASSERTS > 5).

Found by Coverity (CID: CONSTANT_EXPRESSION_RESULT).

Fixes: b8dab47705 ('dns: fix handling default routing domains with systemd-resolved')
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:54:12 +02:00
Jan Vaclav
56099c5e14 device: fix potential null dereference when releasing port
find_port_info() can return NULL if the port is not registered.
The code dereferenced `info->port_state` before the null check,
which would crash. Move the null check before the dereference.

Found by Coverity (CID: REVERSE_INULL).

Fixes: a8329587c8 ('device: fix bug when deactivating port connections asynchronously')
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:54:12 +02:00
Jan Vaclav
4565c9efe4 policy: fix integer overflow in IPv6 PD subnet calculation
The literal `1` is a 32-bit int. When prefix length is less than 33,
the shift `(64 - plen)` exceeds 31 bits, causing undefined behavior.
Cast to guint64 (same type as `num_subnets`) to perform the shift in
64-bit arithmetic.

Found by Coverity (CID: OVERFLOW_BEFORE_WIDEN).

Fixes: ec12fcf6bf ('policy: delegate IPv6 configuration to ipv6.method=shared connections')
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-14 12:53:43 +02:00
Íñigo Huguet
6b038ef4dc merge: branch 'issue1476'
bond: change default value of `arp_missed_max`

Closes #1476

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2288
2026-04-14 05:46:02 +00:00
Pradyumn Rahar
921fe6ec68 The valid range of arp_missed_max according to the kernel is 1-255,
while the default value of the same in NM is 0, which causes warnings to
arise, change this default value.

Allow the range in NM to stay 0-255 as 0 is used to indicate arp_missed_max
is unset (for modes that don't support the setting), however do not let it
be set beyond the kernel permissible range for the modes that support it, set
it to the kernel default of 2 instead.

Do not apply or reapply the arp_missed_max setting when it is not
supported.

Signed-off-by: Pradyumn Rahar <pradyumn.rahar@oracle.com>
2026-04-14 10:20:27 +05:30
Íñigo Huguet
95a329a927 merge: branch 'misc-fixes'
Miscellaneous fixes: veth, macvlan, spec

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2248
2026-04-09 13:39:21 +00:00
David Ward
09e2de8b68 spec: fix scriptlet dependencies
Adjust %postun to handle missing udev, in the same way %post does.
This permits installation inside a container without udev.

/usr/sbin/update-alternatives is needed for the initscripts-updown
subpackage only.
2026-04-09 13:33:32 +00:00
David Ward
372fb5792c veth: fix updating peer when link changed
When creating the first device in a veth pair, the peer ifindex is
valid, but the peer device does not exist yet. This should be set
when update_properties() is called for the second device, but fix
the conditional.
2026-04-09 13:33:32 +00:00
David Ward
631127d2e5 macvlan: fix D-Bus property name 2026-04-09 13:33:32 +00:00
Jan Vaclav
fe793cd783 merge: branch 'jv/tui-bond-other'
nmtui/bond: introduce "other options" list

Closes #1805

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2392
2026-04-09 09:54:25 +00:00
Jan Vaclav
0b3db7c6ee nmtui: rename NMTAddressList -> NmtList 2026-04-09 11:33:20 +02:00
Jan Vaclav
6a841072ec nmtui/bond: introduce "other options" list
Bond connections can have options that are not exposed by any widget
in the bond editor. The presence of certain mode-specific options makes
it impossible to change the mode, e.g. from 802.3ad to active-backup
when `lacp_rate` is set.

Introduce an "Other options" list that shows all bond options not
already configurable by a specific widget, and allow the user to edit
them as key=value entries.

Resolves #1805
Resolves: https://redhat.atlassian.net/browse/NMT-1888
2026-04-09 11:33:20 +02:00
Íñigo Huguet
e8f379abb8 merge: branch 'fix/pppd-gateway-empty-ipcp'
pppd-plugin: fix gateway for PPP connections without carrier-provided remote IP

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2383
2026-04-09 08:00:31 +00:00
Ben Hagen
bd0a6356eb pppd-plugin: fix gateway for PPP connections without carrier-provided remote IP
During the dbus-glib to GDBus port in 89228569f (2014), the last-resort
gateway in nm_ip_up() was accidentally changed from peer_opts.hisaddr to
peer_opts.ouraddr. peer_opts.ouraddr is typically 0 when IPCP does not
provide a peer address, causing gateway=0 and broken PPP connectivity
probing/routing behavior.

Restore the original behavior from 369299271 (2008).

Fixes: 89228569f8 ('ppp-manager: port nm-pppd-plugin from dbus-glib to gdbus')
2026-04-09 08:00:12 +00:00
Íñigo Huguet
5e02f13611 merge: branch 'main'
po: Update Serbian (sr) and Serbian Latin (sr@latin) translations

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2385
2026-04-08 13:06:28 +00:00
Марко М. Костић (Marko M. Kostić)
834ae00607 po: Update Serbian Latin translation 2026-04-08 13:05:36 +00:00
Марко М. Костић (Marko M. Kostić)
d9c143ee58 po: Update Serbian translation 2026-04-08 13:05:36 +00:00
Íñigo Huguet
230009b9e8 merge: branch 'ih/sl-po'
po: update Slovenian translations

Closes #1894

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2374
2026-04-08 10:53:34 +00:00
filmsi
253ce99d2c po: update Slovenian translations 2026-04-08 10:53:25 +00:00
Íñigo Huguet
c86ae51240 merge: branch 'fixtypo'
Fix typos

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2371
2026-04-08 10:19:36 +00:00
Hiroyuki Yasuhara
9ca09aa020 cloud-setup/man: fix typo in man nm-cloud-setup 2026-04-08 10:19:23 +00:00
Hiroyuki Yasuhara
a6e133d5f4 libnm/docs: fix typo in man nm-settings-nmcli 2026-04-08 10:19:23 +00:00
Hiroyuki Yasuhara
330cb6a20b docs/libnm: fix typo in libnm.svg 2026-04-08 10:19:23 +00:00
Íñigo Huguet
92bf0178a4 merge: branch 'typo-fixes-2026'
libnmc-setting: fix typos

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2377
2026-04-08 10:17:06 +00:00
Anders Jonsson
e50272de78 libnmc-setting: fix typos 2026-04-08 10:13:31 +00:00
Íñigo Huguet
72950e5d5b merge: branch 'fix/meson'
meson: fix cross-compilation issues

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2380
2026-04-08 10:11:27 +00:00
Andrej Kozemcak
e5d2c7cc6d meson: fix cross-compilation issues
Strip newline from GI_TYPELIB_PATH and LD_LIBRARY_PATH
run_command().stdout() returns the raw shell output including a trailing
newline. When the value is used to build a colon-separated path, the newline
gets embedded at the end of the last path component, making the directory
invalid and causing GObject Introspection to fail with:

  ImportError: Typelib file for namespace 'Gio', version '2.0' not found

Use .strip() to remove leading/trailing whitespace from both env variable
reads.

Fix jansson SONAME detection for cross-compilation
When cross-compiling, jansson's pkg-config 'libdir' variable returns a
path relative to the sysroot (e.g., /usr/lib) without the actual sysroot
prefix.  The host readelf binary cannot find the library at that path.

Fix this by using meson.get_external_property('sys_root', '') to obtain
the sysroot path set by the cross-compilation environment and prepend it
to the library path before calling readelf.

Signed-off-by: Andrej Kozemcak <andrej.kozemcak@siemens.com>
2026-04-08 10:11:13 +00:00
Íñigo Huguet
bb50e8f0f4 merge: branch 'rr/fix-avc-error-2'
core: use GDir to avoid libgvfs loading

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2384
2026-04-08 08:30:37 +00:00
Rahul Rajesh
2e1ee043a7 core: use GDir to avoid libgvfs loading
Replace GFile with GDir to avoid libgvfs and other DBus infra
initialization.

This was done mainly to avoid heavy initialization just for executing
NetworkManager --print-config command.

Resolves: https://redhat.atlassian.net/browse/RHEL-140113
2026-04-08 08:30:18 +00:00
Íñigo Huguet
58f4c81673 merge: branch 'ih/dhcp-client-unknown'
dhcp: improve log message for unknown DHCP plugin

Closes #1917

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2388
2026-04-08 07:50:51 +00:00
Íñigo Huguet
24c50803a7 dhcp: improve log message for unknown DHCP plugin
If a DHCP plugin is unknown, the logs says "DHCP client 'x' not
available". This is the same message that is shown if, for example, it
is a valid DHCP plugin name, but the program is not installed in the
system.

For example, after 'dhclient' was deprecated, now NM is built without
support for it. Then, people with old configs `dhcp=dhclient` get the
message "DHCP client 'dhclient' not available". That seems to mean that
dhclient is not installed.

Show a message "unknown DHCP client" instead.

Fixes https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/work_items/1917
2026-04-08 07:50:41 +00:00
Íñigo Huguet
7f4efc484c merge: branch 'ih/spec'
rpm spec: set polkit_noauth_group=wheel by default

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2391
2026-04-08 07:50:11 +00:00
Íñigo Huguet
1970d8a8cd spec: set polkit_noauth_group=wheel by default
In Fedora there were complains about needing sudo to do changes. We
decided to allow doing changes without additional authentication if
they're done from a local console and an admin account.
2026-04-08 07:49:52 +00:00
Gris Ge
de91bd8070 merge: branch 'jv/clat-macro'
l3cfg: wrap _clat_prefix_is_better() in HAVE_CLAT guard

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2390
2026-04-01 10:06:51 +00:00
Jan Vaclav
66ac355c52 l3cfg: wrap _clat_prefix_is_better() in HAVE_CLAT guard
Fixes the following warning when building without CLAT:
../src/core/nm-l3cfg.c:4157:1: warning: ‘_clat_prefix_is_better’ defined but not used [-Wunused-function]
 4157 | _clat_prefix_is_better(const NMPlatformIP6Address *best,
      | ^~~~~~~~~~~~~~~~~~~~~~

Fixes: a03a245819 ('l3cfg: fix selection of the CLAT IPv6 prefix')
2026-03-31 11:44:42 +02:00
Rahul Rajesh
fb1104d278 release: bump version to 1.57.4 (development) 2026-03-27 09:08:35 -04:00
Beniamino Galvani
5580b982ac merge: branch 'bg/clat-prefix-selection'
l3cfg: fix selection of the CLAT IPv6 prefix

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2378
2026-03-18 17:44:41 +00:00
Beniamino Galvani
a03a245819 l3cfg: fix selection of the CLAT IPv6 prefix
If the router advertises both ULA and GUA prefixes, the CLAT should
select the one that better matches the NAT64 prefix when generating
the additional IPv6 address, as recommended by Internet Draft
draft-ietf-v6ops-claton.

The current implementation just takes the first one, which can cause
problems. For example, if the network is using a public NAT64 server,
the NAT64 prefix is in the GUA range. Choosing a ULA as source address
would not work.

Fixes: f0e77a4354 ('Add support for CLAT to l3cfg')
2026-03-17 14:45:04 +01:00
Beniamino Galvani
7f2745f3b1 libnm-glib-aux: add nm_ip6_addr_rfc6724_label() 2026-03-17 14:45:04 +01:00
Beniamino Galvani
1589346de4 libnm-glib-aux: add nm_ip6_addr_common_prefix_len() 2026-03-17 14:45:03 +01:00
Beniamino Galvani
0b1c6f467e merge: branch 'nmtui-menu'
nmtui: remove "OK" button in main menu

Closes #1816

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2357
2026-03-13 09:55:45 +00:00
Vladislav Tsisyk
1b07f92fae nmtui: remove "OK" button in main menu
Remove the redundant OK button from the main menu, as menu items are activated with Enter.
This simplifies the UI and avoids unnecessary actions.

Closes #1816
2026-03-12 14:01:28 +00:00
Beniamino Galvani
31fcd35b24 merge: branch 'bg/clat-ci'
gitlab-ci: disable CLAT if required libraries are missing

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2362
2026-03-12 10:04:57 +00:00
Beniamino Galvani
7d19805905 build: require libbpf 1.3.0
Version 1.3.0 of the library is needed to support "tcx" program types.
2026-03-12 09:45:03 +00:00
Beniamino Galvani
4e3371964c gitlab-ci: disable CLAT if required libraries are missing
Old Alpine and Debian release don't have the required libraries,
disable CLAT on them.

Fixes: dd3758dd80 ('contrib: Add libbpf and libxdp to dependencies')
2026-03-12 09:45:03 +00:00
Beniamino Galvani
62997ac8c0 merge: branch 'bg/warn-unreachable-gateways'
Warn about directly unreachable gateways

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2360
2026-03-12 07:46:09 +00:00
Beniamino Galvani
589286df78 NEWS: mention the warnings for unreachable gateways 2026-03-11 15:12:15 +01:00
Beniamino Galvani
8b9a702e1d core: emit warning for unreachable gateways 2026-03-11 15:12:15 +01:00
Beniamino Galvani
907508f4bf nmtui: emit warning for unreachable gateways 2026-03-11 15:12:15 +01:00
Beniamino Galvani
ec5f98e7a8 nmcli: emit warning for unreachable gateways 2026-03-11 15:12:15 +01:00
Beniamino Galvani
2b4b8d7e7e libnm-core: add function to get a warning message for unreachable gateways
We are going to print the same warning message in different places
(the daemon, nmcli, nmtui). Add a function to return the message. Note
that the message needs to be translated in clients but not in the
daemon logs.
2026-03-11 15:12:15 +01:00
Beniamino Galvani
f42e422b69 libnm-core: add function to detect directly-unreachable gateways
nm_connection_get_unreachable_gateways() is a non-public function,
available in the daemon and clients, which detects gateways in the
static configuration that are not directly reachable.

Unreachable gateways are often the consequence of user mistakes; we
want to catch them early. In the following commits, warnings will be
emitted when a connection is created/modified/activated and has
unreachable gateways.
2026-03-11 15:12:15 +01:00
Rahul Rajesh
22f4e74942 merge: branch 'rr/fix-avc-error'
core: delay D-Bus type initialization for --print-config

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2376
2026-03-10 12:36:29 +00:00
Till Maas
57bc396c12 core: delay D-Bus type initialization for --print-config
The --print-config option should only read and print the configuration
without initializing any D-Bus infrastructure. However, g_type_ensure()
calls for D-Bus types were happening before the --print-config check,
causing GLib/GIO to set up D-Bus infrastructure and create cache
directories (~/.cache/bus or /root/.cache) unnecessarily.

Move the g_type_ensure() calls to after the --print-config (and
--version) early exits, so they only run when NetworkManager actually
needs to start normally and use D-Bus.

Resolves: https://issues.redhat.com/browse/RHEL-140113

Assisted-by: Claude Code claude-sonnet-4-5@20250929
Signed-off-by: Till Maas <opensource@till.name>
2026-03-06 14:30:23 -05:00
Íñigo Huguet
0e2b679afb merge: branch 'ih/perm_unmanaged'
add API to manage/unmanage devices in a persistent way

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2358
2026-03-06 10:23:58 +00:00
Íñigo Huguet
b6bd9cee87 NEWS: update 2026-03-06 11:21:58 +01:00
Íñigo Huguet
2fbaca1cbc checkpoint: rollback devices' "permanently managed" configuration
If a device's "managed" configuration is changed persistently (stored to
NM-intern), it needs to be undone in a rollback.
2026-03-06 11:21:57 +01:00
Íñigo Huguet
1252f8dc7e core: config: add unit tests for the new get/set_device_managed 2026-03-06 11:21:56 +01:00
Íñigo Huguet
7ee50b687a nmcli: wait for device set async operation to finish
We need to wait for it to finish so we can show error messages, if any.

Also, if we don't do it, sometimes the `d set eth0 managed ...`
operation fails with the following message in the daemon's log: "Unable
to determine UID of the request". This is because the client's process
is terminated before the daemon can check the permissions, as it needs
to check the uid and gid from the client's process.
2026-03-06 11:21:55 +01:00
Íñigo Huguet
d2f98a1669 nmcli: add managed --permanent yes/no/up/down/reset
Allow to manage or unmanage a device persisting across reboots.
If --permanent is not specified, only the runtime managed state is
changed, preserving the previous behavior. The --permanent-only
option allows to edit only the persistent value, without touching
the runtime value.

Also add the values up/down. Up means managed=yes and set device's
administrative state UP. Down means managed=no and admin state DOWN.

Add the value 'reset' too. It reverts managed runtime status to default
behaviour. When used with `--permanent` flag, the persisted managed
settings is cleared.

Co-authored-by: Rahul Rajesh <rajeshrah22@gmail.com>
2026-03-06 11:21:53 +01:00
Íñigo Huguet
7c8f343f2c core: device: autoselect device match criteria in SetManaged()
Devices like veth without a permanent MAC address cannot be matched by
MAC. If using the BY_MAC flag in SetManaged(), the changes are not
effective for such kind of devices.

Add a BY_NAME flag, in addition to the BY_MAC one. If the client sets
one of them, it means to force this mode of matching. If none is
selected, the daemon will choose how to match, preferring matching by
MAC when possible, and by ifname when not possible.
2026-03-06 11:21:52 +01:00
Íñigo Huguet
b9725dab73 core: device: allow to change the admin state of the device in SetManaged()
Control it with a new NM_DEVICE_MANAGED_SET_ADMIN_STATE flag.
This flag will make that, at the same time that the device is moved to
managed/unmanaged, it's admin state is set to up/down. Many users want
to have a way to have their devices in a DOWN admin state when they are
not using them. Because of the complex activation process, NM wants to
have its devices in UP state all the time. However, it is not a problem
to have it DOWN if we are not managing it.
2026-03-06 11:21:51 +01:00
Íñigo Huguet
f346fcf977 core: device: allow to reset the managed property
Previous commits added the capability to persist to disk the value of
'managed' received via the D-Bus API. Users might need to clear the
previous content, thus reseting it to its default.

Although this is specially useful for the PERMANENT flag, we need to be
consistent and reset the runtime state too.
2026-03-06 11:21:50 +01:00
Íñigo Huguet
ec1522fa8c core: device: implement storing to disk for Device.SetManaged()
If the NM_DEVICE_MANAGED_FLAGS_PERMANENT flag is used, the value will be
stored to disk, to the NetworkManager-intern.conf file, in a [device-*]
section.

To modify the runtime value, the NM_DEVICE_MANAGED_FLAGS_RUNTIME must be
passed. This allows to control independently whether to modify only one
or both.
2026-03-06 11:21:48 +01:00
Íñigo Huguet
0a1503f052 core: config: allow to store 'managed' configs to NM-intern
To support setting devices as managed or unmanaged via D-Bus API in a
permanent way, we need a way to store this configuration on disk. Before
this commit, only config files manually edited allowed it. Following
commits will make use of the new functions to store [device-*] sections
into NetworkManager-intern.conf depending on D-Bus method invocations.
2026-03-06 11:21:48 +01:00
Íñigo Huguet
47c1b04f9e core: config-data: don't ignore [.intern.device/connection] sections
Now it is possible to have [.intern.device-*] sections in
NetworkManager-intern.conf. Take them into account when parsing the
configuration keyfiles.
2026-03-06 11:21:47 +01:00
Íñigo Huguet
9ff530c322 dbus: device: add SetManaged method
The 'Managed' property only sets the managed state in runtime, but it is
not possible to persist it to disk. Add a SetManaged method that will be
able to persist it to disk. In this commit, it just modify the runtime
state, so it actually only does the same than setting the property.
Storing to disk will be added in next commits.
2026-03-06 11:21:47 +01:00
Íñigo Huguet
121034d655 merge: branch 'ih/nmcli_field_ports'
nmcli: add BRIDGE.PORTS, TEAM.PORTS and GENERAL.CONTROLLER-PATH fields. Replace SLAVE for PORT in `c show`

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2369
2026-03-05 07:08:54 +00:00
Íñigo Huguet
cdd38f7cdf nmcli: replace SLAVE for PORT, still accepting SLAVE as alias
With `nmcli -f SLAVE` the PORT column will be shown. In this case we
don't duplicate the field because it's typically shown in columns and
having duplicated columns is more annoying than a duplicated row.
2026-03-05 07:08:14 +00:00
Íñigo Huguet
c6b6c7164b libnmc: allow to define an alias to match fields to show 2026-03-05 07:08:14 +00:00
Íñigo Huguet
ff1d435096 nmcli: add BRIDGE.PORTS, TEAM.PORTS and GENERAL.CONTROLLER-PATH fields
They show the same than the old BRIDGE/TEAM.SLAVES and GENERAL.MASTER-PATH.
We missed this when we did the changes in favour of conscious language.
Instead of replacing them, we add a new field that will show the same
value with the new name. This way we avoid breaking users doing
`nmcli -f BRIDGE.SLAVES` or `nmcli ... | grep SLAVES`.
2026-03-05 07:08:14 +00:00
Beniamino Galvani
1a2fec62f0 merge: branch 'bg/drop-veth-peer-ioctl'
platform: drop ioctl fallback for finding veth's peer

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2354
2026-03-04 17:27:08 +00:00
Beniamino Galvani
fddda02825 platform: drop ioctl fallback for finding veth's peer
The peer ifindex of a veth interface is available via netlink since
kernel 4.1 released in 2015. Drop the code that falls back to ioctl.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1881
2026-03-04 16:51:57 +00:00
Beniamino Galvani
2d30b71dd4 merge: branch 'bg/dhcp-routes'
dhcp: ignore the Router option when there are Classless Static Routes

Closes #834

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2364
2026-03-04 16:51:33 +00:00
Beniamino Galvani
7651ef0386 dhcp: ignore the Router option when there are Classless Static Routes
RFC 3442 says:

   If the DHCP server returns both a Classless Static Routes option and
   a Router option, the DHCP client MUST ignore the Router option.

Currently the internal client is ignoring the Router option only if
the Classless Static Routes option doesn't include a default route,
which is different from what is recommended in the RFC. Fix the behavior.

Fixes: 6adade6f21 ('dhcp: add nettools dhcp4 client')

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/834
2026-03-04 15:26:11 +00:00
Íñigo Huguet
8236c1c16a merge: branch 'lr/mtu-clarity'
device: do not set MTU twice in stage3

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2231
2026-03-04 11:15:19 +00:00
Lubomir Rintel
818cf77cb5 device: do not set MTU twice in stage3
The pair of _commit_mtu() calls in activate_stage3_ip_config() are very
heavily commented, but it is still not clear why would there be two of
them.

Remove one, and try to clarify the situation in an updated comment.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2231
2026-03-04 11:15:01 +00:00
Jan Vaclav
98256be220 merge: branch 'jv/onlink'
platform: introduce per-nexthop onlink attribute

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2368
2026-03-03 10:10:49 +00:00
Jan Vaclav
d564a0c3f9 platform: track onlink flag per-nexthop for IPv4 routes
In kernel, the onlink flag (RTNH_F_ONLINK) is associated with each
nexthop (rtnh_flags) rather than the route as a whole. NM previously
stored it only per-route in NMPlatformIPRoute.r_rtm_flags, which meant
that two nexthops only differing with the onlink flag were combined
as one entry in the platform cache.

Fix this by tracking the onlink flag per-nexthop.

Resolves: https://issues.redhat.com/browse/NMT-1486
2026-03-02 10:57:56 +00:00
Beniamino Galvani
a924826e2c merge: branch 'rr/fix-create-and-realize'
device: fix vxlan create_and_realize

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2363
2026-02-27 16:33:42 +00:00
Rahul Rajesh
04f7ca5029 device: fix vxlan create_and_realize
Assert that remote and local will be valid in this function since it
will be verified in verify function in connection profile.
2026-02-27 16:26:16 +00:00
Beniamino Galvani
de6d9930b9 gitlab: improve the merge request template
Mention the commit subject format.
2026-02-27 11:59:16 +01:00
Beniamino Galvani
30ca65ab88 merge: branch 'kk-l10n-add'
Add Kazakh translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2359
2026-02-27 09:41:00 +00:00
Baurzhan Muftakhidinov
bf80a9019e Add Kazakh translation 2026-02-27 10:02:13 +01:00
Beniamino Galvani
6b37d612fd merge: branch 'nmtui-tilde'
nmtui: allow enter tilde in search domains

Closes #1862

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2356
2026-02-27 08:58:02 +00:00
Vladislav Tsisyk
dbeb7fa0f6 nmtui: accept tilde in search domains
Closes #1862
2026-02-27 08:57:20 +00:00
Beniamino Galvani
b7d9625ae1 merge: branch 'lr/systemd-unit-lockdown'
data/NetworkManager.service: restrict the unit some more

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2062
2026-02-27 08:46:04 +00:00
Lubomir Rintel
cb51c4475a data/NetworkManager.service: restrict the unit some more
This adds some low-hanging food to improve our score with "systemd-analyze
security" by one point:

Before:
  → Overall exposure level for NetworkManager.service: 7.8 EXPOSED 🙁

After:
  → Overall exposure level for NetworkManager.service: 6.8 MEDIUM 😐

Nothing particularly impactful here: we still got DAC_OVERRIDE, we still
can insert loadable modules (as opposed to relying on autoload) and
read user home directories. But there's a slight chance this may save
our butts one day, who knows.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2062
2026-02-27 08:44:10 +00:00
Beniamino Galvani
756e612858 merge: branch 'fix-vpn-search-domains'
vpn: set search domains

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2340
2026-02-26 17:00:08 +00:00
François HORTA
03a3a449f6 vpn: set search domains
dns-search parameters set on VPN connections should be merged with
domains received through the VPN (which may be empty if the connection
sets ignore-auto-dns).

This is currently not the case because domains received by the VPN
connection are only added through nm_l3_config_data_add_domain.

If dns-search is unset, this behaves correctly because the structure
built in _mgr_configs_data_construct in src/core/dns/nm-dns-manager.c
correctly uses the domains from nm_l3_config_data_get_domains.

However if dns-search is set, nm_l3_config_data_get_searches is no
longer empty and it takes precedence because of the "n_searches > 0"
condition.
2026-02-26 16:40:59 +00:00
Beniamino Galvani
926795f11a merge: branch 'bulgarian'
Updated bulgarian translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2350
2026-02-26 15:12:51 +00:00
twlvnn
e4ca177be2 Updated bulgarian translation 2026-02-26 15:01:49 +00:00
Beniamino Galvani
20f975abe3 merge: branch 'bg/secret-permissions'
Fix the handling of permissions for connection secrets

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2367
2026-02-25 08:24:10 +00:00
Beniamino Galvani
024360bffa settings: fix check on existing system secrets
The previous check was based only on the presence of a non-NULL
"existing_secrets" GVariant. That GVariant is created via:

  nm_connection_to_dbus(nm_settings_connection_get_connection(self),
                        NM_CONNECTION_SERIALIZE_WITH_SECRETS_SYSTEM_OWNED)

The function returns a GVariant containing a first-level dictionary
for each setting, even for those that doesn't contain any secrets. As
a result, the check was requiring the system.modify permission even if
there weren't any cached secrets to send to the agent.

Fix the check to actually check for the presence of any secrets in the
cached dictionary. Some connection types have a third-level
dictionary that can be empty, for example VPNs have vpn.secrets.
2026-02-25 09:05:04 +01:00
Beniamino Galvani
db0825a110 settings: accept not-saved secrets from agents without modify-system
The "modify.system" polkit permission allows a user to modify settings
for connection profiles that belong to all users.

For this reason, when an agent returns system secrets (i.e. secrets
that are going to be stored to disk), NetworkManager checks that the
agent has the modify.system permission.

If a secret has the AGENT_OWNED flag, it's stored in the agent
itself. If the secret has the NOT_SAVED flag, it will be asked to
users at the beginning of every connection attempt.

In both those cases the profile is not modified and there is no need
for the modify.system permission. Fix the check to also consider the
NOT_SAVED flag.
2026-02-24 08:46:32 +01:00
Beniamino Galvani
eff8330b57 libnm-core: add missing flags check in .to_dbus_function()
Properties that define a .to_dbus_function() as a D-Bus override, need
to return early if the flags only ask to serialize secrets.

Fixes: 7fb23b0a62 ('libnm: add NMIPRoutingRule API')
2026-02-24 08:46:32 +01:00
Beniamino Galvani
128b49fe21 merge: branch 'rr/geneve-support'
geneve: add support for GENEVE tunnels

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2352
2026-02-18 12:43:47 +00:00
Rahul Rajesh
2e2b4946ea NEWS: add support for GENEVE interface
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2352

Resolves: https://issues.redhat.com/browse/RHEL-122042
2026-02-17 16:02:45 -05:00
Rahul Rajesh
0bfb8fa89d geneve: added GENEVE device support
Support device type geneve in libnm and nmcli.
2026-02-17 15:21:03 -05:00
Rahul Rajesh
2aaf88375e geneve: add connection profile settings
Added support for the following properties in connection profile:
id (VNI), remote IPv4/IPv6, ttl, tos, df, destination port.

See IP-LINK(8) manual page with command `man 8 ip-link` for more details
on the properties. See also previous commit for nm supported attributes.

id and remote are mandatory attributes:
```
$ nmcli connection add type geneve save no
Error: 'id' argument is required.
$ nmcli connection add type geneve id 42 save no
Error: 'remote' argument is required.
```
2026-02-17 15:21:03 -05:00
Rahul Rajesh
29c8bbe21a platform: add support for GENEVE tunnels
GENEVE (Generic Network Virtualization Encapsulation) is a network
tunneling protocol that provides a flexible encapsulation format for
overlay networks. It uses UDP as the transport protocol and supports
variable-length metadata in the tunnel header.

This patch adds GENEVE tunnel to NM's platform layer:

- Add platform API functions (nm_platform_link_geneve_add,
  nm_platform_link_get_lnk_geneve)

- Netlink message parsing for the following attributes:
  * IFLA_GENEVE_ID - VNI (Virtual Network Identifier)
  IPv4 and IPv6 remote
  * IFLA_GENEVE_REMOTE
  * IFLA_GENEVE_REMOTE6
  TTL, TOS, and DF flags
  * IFLA_GENEVE_TTL
  * IFLA_GENEVE_TOS
  * IFLA_GENEVE_DF
  UDP destination port
  * IFLA_GENEVE_PORT

- Add test cases for GENEVE tunnel creation and detection with two test
  modes covering IPv4 and IPv6.

The implementation tries to follow the same patterns as other tunnel
types (GRE, VXLAN, etc.) and integrates with the existing platform
abstraction layer.
2026-02-17 15:21:03 -05:00
Rahul Rajesh
ad78bd8570 platform: expand nmp object type flags to guint64
To allow for more than 32 NMP_OBJECT_* types.
2026-02-17 15:21:03 -05:00
Beniamino Galvani
54a4b42c05 merge: branch 'docs/get_secrets_fix'
docs: GetSecrets doesn't accept empty string

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2355
2026-02-17 10:35:30 +00:00
Mattia Dal Ben
8c93d0bdff introspection: fix documentation for GetSecrets 2026-02-17 09:01:20 +00:00
Beniamino Galvani
4fcebeaec0 merge: branch 'man-nmcli-checkpoint'
man: fix sentence in nmcli manual page

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2351
2026-02-17 09:00:40 +00:00
Federico Ton
40f19ad674 man: fix sentence in nmcli manual page
A not very clear sentence in the description of the `nmcli device checkpoint` command has been changed.
2026-02-16 18:57:52 +01:00
Vladimír Beneš
f70b37357a release: bump version to 1.57.3 (development) 2026-02-13 13:30:02 +01:00
Vladimír Beneš
30a5416a54 tmp 2026-02-13 13:23:55 +01:00
Vladimír Beneš
56b51b98fb release: bump version to 1.56.0 2026-02-12 23:14:41 +01:00
Jan Vaclav
cf52d3f52b 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/

(cherry picked from commit d40e88fd02)
2026-02-12 20:27:20 +01:00
Beniamino Galvani
a0e03b1228 supplicant: fix center channel calculation
The formula is wrong for channels above 144 because the layout of the
80MHz channels is not regular. Use a lookup table.

Fixes: 7bb5961779 ('supplicant: honor the 'wifi.channel-width' property in AP mode')
(cherry picked from commit 5763b9b4de)
2026-02-12 11:53:55 +01:00
Beniamino Galvani
9188c9fa9b cloud-setup: fix format string
On a i686 machine the build fails with:

../src/nm-cloud-setup/main.c: In function ‘_oci_new_vlan_dev’:
../src/nm-cloud-setup/main.c:800:47: error: format ‘%ld’ expects argument of type ‘long int’, but argument 2 has type ‘gssize’ {aka ‘int’} [-Werror=format=]
  800 |     macvlan_name  = g_strdup_printf("macvlan%ld", config_data->iface_idx);
      |                                             ~~^   ~~~~~~~~~~~~~~~~~~~~~~
      |                                               |              |
      |                                               long int       gssize {aka int}
      |                                             %d
../src/nm-cloud-setup/main.c:801:42: error: format ‘%ld’ expects argument of type ‘long int’, but argument 3 has type ‘gssize’ {aka ‘int’} [-Werror=format=]
  801 |     connection_id = g_strdup_printf("%s%ld", connection_type, config_data->iface_idx);
      |                                        ~~^                    ~~~~~~~~~~~~~~~~~~~~~~
      |                                          |                               |
      |                                          long int                        gssize {aka int}
      |                                        %d

Fixes: 68d7e17737 ('Reapply "cloud-setup: create VLANs for multiple VNICs on OCI"')
(cherry picked from commit 748be9a3e7)
2026-02-12 11:53:49 +01:00
Vladimír Beneš
3981d392aa NEWS: remove pre-release bits as we do 1.56.0 now 2026-02-12 11:37:43 +01:00
Íñigo Huguet
1bdcbdfd4f nm-version: allow to define NM_VERSION_MAX_ALLOWED alone
Previously, if NM_VERSION_MIN_REQUIRED was not defined, it defaulted to
NM_VERSION. As a consequence, if NM_VERSION_MAX_ALLOWED was defined we
got a compilation error because MAX_ALLOWED < MIN_REQUIRED.

MAX_ALLOWED is used to get compilation warnings if you unintentionally
use a libnm's symbol introduced in a newer version. MIN_REQUIRED is used
to get rid of warnings about symbol deprecations.

Libnm users may want to use MAX_ALLOWED alone, because using a too new
symbol would fail to compile with older libnm. But they might want to
get deprecation warnings as soon as possible, so they want to leave
MIN_REQUIRED empty.

(cherry picked from commit f849163e82)
2026-02-12 11:25:55 +01:00
Íñigo Huguet
8f3b8e0200 nm-version.h: use the right value of NM_API_VERSION
After the changes in release.sh in previous commits, during development
the value of NM_VERSION will always be the next version, not the latest
released one. As a consequence, we don't need to set MICRO+1 in
NM_API_VERSION, which was a temporary workaround.

(cherry picked from commit 36275bc51c)
2026-02-12 11:25:55 +01:00
Íñigo Huguet
045f328512 release: (manually) bump version to 1.56-rc3
After the previous commits, release.sh bumps the version after tagging
the release, and not before. Therefore, it expects that the version is
already the next one when doing the release.

Manually bump the version this time so release.sh sees the right value
the next time it's executed after these changes.

(cherry picked from commit c0fe80ff87)
2026-02-12 11:25:38 +01:00
Íñigo Huguet
a39acb38e8 release.sh: fix a few small bugs and typos
Fix typo freedestkop -> freedesktop.

Removed unused argument of check_news (additionally, it was incorrectly
using @ instead of $).

Fixed incorrect use of `$? = 0` that was always successful.

(cherry picked from commit 9a3462af99)
2026-02-12 11:25:01 +01:00
Íñigo Huguet
0740459a5a release.sh: bump version after release
After tagging a release, create a commit bumping to the next version.
This effectively ends the change in the logic initiated in the previous
commit, from "bump version, then release" to "release, then bump
version".

The purpose of this is to have the right version set in nm_version.h and
nm_version_macros.h between two releases. Without this change, when we
introduced a new symbol, thus using the NM_AVAILABLE_IN_1_XX annotations,
we got compilation warnings until we did the next release (making the CI
to be red when configured the compilation to fail on warnings).

(cherry picked from commit 5666407f15)
2026-02-12 11:25:01 +01:00
Íñigo Huguet
d72562e365 release.sh: assume that the version is already the right one
Don't bump the version before tagging the release. Instead, assume that
it's already correctly set. This is in preparation for the next commit
where we will bump the version after the release, not before.

But don't assume that in the case of rc1 and major releases. For rc1 we
switch from devel releases to RC releases, and in major we switch from
RC releases to stable releases. For example, when we are going to
release 1.58-rc1, the current version will be 1.57.X-dev, so we need to
bump to 1.58-rc1. When we're going to release 1.58.0, the current
version will be 1.58-rcX, so we need to bump to 1.58.0.

(cherry picked from commit 3a3a8ea59d)
2026-02-12 11:25:01 +01:00
Íñigo Huguet
b3d1055520 release.sh: add comments
(cherry picked from commit d56cd26aea)
2026-02-12 11:25:01 +01:00
Beniamino Galvani
b5410bb24a merge: branch 'bg/clat-improvements'
CLAT improvements

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2353
2026-02-10 08:53:35 +00:00
Beniamino Galvani
a4e30ee849 clat: print translation statistics during deactivation
Print some statistics about the translation when the connection goes
down:

  clat: stats: egress (v4 to v6): tcp 1275, udp 191, icmp 9, other 0, dropped 2; ingress (v6 to v4): tcp 1669, udp 272, icmp 0, other 0, fragment 136, dropped 0

Those counters can be used to better understand what's going wrong in
case of problems; for example, if the packets are being dropped in the
ingress path or in the egress one.
2026-02-06 17:47:33 +01:00
Beniamino Galvani
112190d09a clat: support layer3 interfaces
When running the CLAT over an interface that doesn't use the Ethernet
header, like an IP tunnel, there are some changes needed. The BPF
program must compute offsets differently. Also, the DAD packet should
not include an Ethernet header.
2026-02-06 17:47:30 +01:00
Beniamino Galvani
d7edc806b6 core: clat: add the "nm" prefix to ebpf program names
The program names are displayed in the "bpftool prog" output. It is
easier to recognize NM programs if they have the "nm" prefix.
2026-02-06 10:38:07 +01:00
Beniamino Galvani
f9b2083394 l3cd: rename "clat" to "clat_config"
The member indicates if CLAT is enabled in the configuration. Use a
clearer name.
2026-02-06 10:38:06 +01:00
Beniamino Galvani
e2cdd5c4dc build: don't require libndp >= 1.9 if CLAT is disabled
libndp >= 1.9 is only required to parse the PREF64 option needed for
CLAT. When building NM in an enviroment with an older libndp, still
allow building without CLAT support.
2026-02-06 10:38:05 +01:00
Beniamino Galvani
c86d234516 nmcli: show the CLAT state
It is useful to show that the CLAT is enabled and which addresses and
prefix it is using. Add this information to the overview and to the
device/connection output. Example:

$ nmcli
  veth0: connected to clat
          "veth0"
          ethernet (veth), 4A:37:01:56:9D:AE, sw, mtu 1500
          ip4 default
          inet4 192.0.0.5/32
          route4 default metric 101
          inet6 2002:aaaa::64d4:2932:3585:7c89/64
          inet6 fe80::c060:8caf:f69b:e41a/64
          route6 fe80::/64 metric 1024
          route6 2002:aaaa::/64 metric 101
          route6 default via fe80::871:7ff:fe14:b7b9 metric 101
          clat inet4 192.0.0.5 inet6 2002:aaaa::2c0d:1e71:ef87:fac7 pref64 64:ff9b::/96

$ nmcli connection show clat
   ...
  IP4.ADDRESS[1]:                         192.0.0.5/32
  IP4.GATEWAY:                            0.0.0.0
  IP4.ROUTE[1]:                           dst = 0.0.0.0/0, nh = 0.0.0.0, mt = 101
  IP4.CLAT-ADDRESS:                       192.0.0.5
  IP6.ADDRESS[1]:                         2002:aaaa::64d4:2932:3585:7c89/64
  IP6.ADDRESS[2]:                         fe80::c060:8caf:f69b:e41a/64
  IP6.GATEWAY:                            fe80::871:7ff:fe14:b7b9
  IP6.ROUTE[1]:                           dst = fe80::/64, nh = ::, mt = 1024
  IP6.ROUTE[2]:                           dst = 2002:aaaa::/64, nh = ::, mt = 101
  IP6.ROUTE[3]:                           dst = ::/0, nh = fe80::871:7ff:fe14:b7b9, mt = 101
  IP6.CLAT-ADDRESS:                       2002:aaaa::2c0d:1e71:ef87:fac7
  IP6.CLAT-PREF64:                        64:ff9b::/96

Note how the IPv4 CLAT address is displayed both in IP4.ADDRESS and
IP4.CLAT-ADDRESS. That's because it is also configured in kernel. The
IPv6 CLAT address is not displayed in IP6.ADDRESS because it's not
configured in kernel.
2026-02-06 10:38:04 +01:00
Beniamino Galvani
d1598a10ec libnm: support the CLAT state
Make available the CLAT state in the NMIPConfig libnm objects.
2026-02-06 10:38:03 +01:00
Beniamino Galvani
f00030d79a core: export the CLAT state over D-Bus
Export over D-Bus the CLAT state: the IPv4 and IPv6 CLAT addresses and
the NAT64 prefix.
2026-02-06 10:38:02 +01:00
Beniamino Galvani
72cb5839fc core: l3cd: store the CLAT state
In the l3cd we already stored the CLAT administrative state (whether
we want to enable it or not) and the selected PREF64. Also store the
other current CLAT parameters, so that we can export them to clients
via D-Bus.
2026-02-06 10:38:00 +01:00
Beniamino Galvani
5c041cb891 l3cfg: send DAD solicitation for the IPv6 CLAT address
As per draft-ietf-v6ops-claton-14, hosts must perform duplicate
addresses detection (DAD) on the generated CLAT IPv6 address. This is
necessary not only to avoid address collisions but also because some
networks drop traffic from addresses that have not done DAD.

Since doing true DAD adds complexity, adopt the same approach as
Android: start DAD by sending a neighbor solicitation and don't wait
for any reply. This avoids the problem with dropped traffic; it
doesn't help with collisions, but collisions are anyway very unlikely
because the interface identifier is a random 64-bit value.

 5ae193ae36/clatd/main.c (363)
2026-02-06 10:37:59 +01:00
Beniamino Galvani
6d44237ed3 ndisc: track multiple PREF64 options
Previously the NMNDisc instance always used the last received NAT64
prefix. If a network advertises multiple NAT64 prefixes,
NetworkManager would constantly flip between them.  Change this and
keep a list of valid PREF64. Most importantly, stick with the same
PREF64 unless a new one appears from a router with higher priority, or
the current PREF64 expires.
2026-02-06 10:37:58 +01:00
Beniamino Galvani
fbfb5afec0 build: move the CLAT line in the meson summary
Move the CLAT line from the Miscellaneous section to the Features one.
2026-02-06 10:37:58 +01:00
Beniamino Galvani
aeeb52ab66 core: log message if CLAT is enabled but not supported
If CLAT is not supported (disabled at build time) and the
configuration enables it, log a message.
2026-02-06 10:37:57 +01:00
Beniamino Galvani
de42acd3fd core: print whether CLAT support is compiled in
At startup, print whether CLAT support is compiled in; it is useful
when debugging.
2026-02-06 10:37:57 +01:00
Beniamino Galvani
f2ced1e115 l3cfg: split updating CLAT config to a separate function
Split the CLAT code from _l3cfg_update_combined_config() so that the
function can be followed more easily.
2026-02-06 10:37:57 +01:00
Beniamino Galvani
cb09291635 nmcli: fix hiding default values
A property should be hidden when it has the default value and one of the
following conditions is met:

 - nmcli is called in "overview" mode (with flag -o)
 - the property has the HIDE flag

Previously, properties with the HIDE flag were always hidden. Fix
that.
2026-02-06 10:37:56 +01:00
Beniamino Galvani
0aab6ef1c0 merge: branch 'wifi-use-auth-retries'
wifi: respect connection.auth-retry for WPA connections

Closes #1316

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2308
2026-02-05 10:34:03 +00:00
Jan Fooken
a01000d811
NEWS: WPA connections now respect connection.auth-retry 2026-01-28 15:46:32 +01:00
Jan Fooken
b4fc8550f5
man: wifi: Document connection.auth-retry for WPA connections
Remove the mentioned limitation of limiting authentication retires to
802.1X connections and add information about the introduced secret
prompting behaviour.
2026-01-28 15:46:32 +01:00
Jan Fooken
746a5902ad
wifi: use authentication retry mechanism
While NetworkManager tries it's best to determine whether a new PSK is
needed, it can still run into edge cases.  One of these edge cases is that
a device can leave the range of an access point and therefore fail a 4-way
handshake.  Because these cases can't be confidently detected, a device
which was previously connected, should try to exhaust it's authentication
retries before requesting new secrets.  This leads to less user-facing
prompts while increasing the time from PSK change to prompt.
2026-01-28 15:46:26 +01:00
Jan Fooken
6dc51ddf01
device: add public method nm_device_auth_retries_has_next
Devices don't know whether they have authentication retries left,
so they can only make decisions ad-hoc after calling
nm_device_auth_retries_try_next.

Giving devices a way to determine whether the current attempt is their
last attempt, allows them to make decisions before failing a connection.
2026-01-28 15:42:20 +01:00
Jan Fooken
a3267aaf7b
device: add private getter for property auth-retries 2026-01-28 15:42:20 +01:00
Íñigo Huguet
871da67916 merge: branch 'ih/fix-api-version'
Bump version just after release, fix NM_API_VERSION on stable branches

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2337
2026-01-26 06:44:38 +00:00
Íñigo Huguet
f849163e82 nm-version: allow to define NM_VERSION_MAX_ALLOWED alone
Previously, if NM_VERSION_MIN_REQUIRED was not defined, it defaulted to
NM_VERSION. As a consequence, if NM_VERSION_MAX_ALLOWED was defined we
got a compilation error because MAX_ALLOWED < MIN_REQUIRED.

MAX_ALLOWED is used to get compilation warnings if you unintentionally
use a libnm's symbol introduced in a newer version. MIN_REQUIRED is used
to get rid of warnings about symbol deprecations.

Libnm users may want to use MAX_ALLOWED alone, because using a too new
symbol would fail to compile with older libnm. But they might want to
get deprecation warnings as soon as possible, so they want to leave
MIN_REQUIRED empty.
2026-01-26 06:44:00 +00:00
Íñigo Huguet
36275bc51c nm-version.h: use the right value of NM_API_VERSION
After the changes in release.sh in previous commits, during development
the value of NM_VERSION will always be the next version, not the latest
released one. As a consequence, we don't need to set MICRO+1 in
NM_API_VERSION, which was a temporary workaround.
2026-01-26 06:44:00 +00:00
Íñigo Huguet
c0fe80ff87 release: (manually) bump version to 1.57.2-dev
After the previous commits, release.sh bumps the version after tagging
the release, and not before. Therefore, it expects that the version is
already the next one when doing the release.

Manually bump the version this time so release.sh sees the right value
the next time it's executed after these changes.
2026-01-26 06:44:00 +00:00
Íñigo Huguet
9a3462af99 release.sh: fix a few small bugs and typos
Fix typo freedestkop -> freedesktop.

Removed unused argument of check_news (additionally, it was incorrectly
using @ instead of $).

Fixed incorrect use of `$? = 0` that was always successful.
2026-01-26 06:44:00 +00:00
Íñigo Huguet
5666407f15 release.sh: bump version after release
After tagging a release, create a commit bumping to the next version.
This effectively ends the change in the logic initiated in the previous
commit, from "bump version, then release" to "release, then bump
version".

The purpose of this is to have the right version set in nm_version.h and
nm_version_macros.h between two releases. Without this change, when we
introduced a new symbol, thus using the NM_AVAILABLE_IN_1_XX annotations,
we got compilation warnings until we did the next release (making the CI
to be red when configured the compilation to fail on warnings).
2026-01-26 06:44:00 +00:00
Íñigo Huguet
3a3a8ea59d release.sh: assume that the version is already the right one
Don't bump the version before tagging the release. Instead, assume that
it's already correctly set. This is in preparation for the next commit
where we will bump the version after the release, not before.

But don't assume that in the case of rc1 and major releases. For rc1 we
switch from devel releases to RC releases, and in major we switch from
RC releases to stable releases. For example, when we are going to
release 1.58-rc1, the current version will be 1.57.X-dev, so we need to
bump to 1.58-rc1. When we're going to release 1.58.0, the current
version will be 1.58-rcX, so we need to bump to 1.58.0.
2026-01-26 06:44:00 +00:00
Íñigo Huguet
d56cd26aea release.sh: add comments 2026-01-26 06:44:00 +00:00
Beniamino Galvani
e311df0c75 merge: branch 'feature/mstrodl/clat'
Add support for CLAT using a BPF program

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2107
2026-01-24 09:32:53 +00:00
Beniamino Galvani
c32f0fb71f l3cfg: fix the metric of the CLAT default route
Previously the metric of the CLAT default route was set to the IPv6
route metric plus 50. Instead:

 - If there is another non-CLAT default route on the device, use the
   same metric plus 1, so that native connectivity is always
   preferred.

 - Otherwise, use the metric from the "ipv4.route-metric" property of
   the connection profile.
2026-01-24 09:45:01 +01:00
Beniamino Galvani
2c896713b8 bpf: clat: add macros for header sizes
They make the code more compact and readable.
2026-01-24 09:44:59 +01:00
Beniamino Galvani
29eb48d7f9 bpf: clat: ensure data is pulled for direct packet access
There is no guarantee that the part of the packet we want to read or
write via direct packet access is linear. From the documentation of
bpf_skb_pull_data():

  For direct packet access, testing that offsets to access are within
  packet boundaries (test on skb->data_end) is susceptible to fail if
  offsets are invalid, or if the requested data is in non-linear parts
  of the skb. On failure the program can just bail out, or in the case
  of a non-linear buffer, use a helper to make the data available. The
  bpf_skb_load_bytes() helper is a first solution to access the
  data. Another one consists in using bpf_skb_pull_data to pull in
  once the non-linear parts, then retesting and eventually access the
  data.

See: https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2107#note_3288979

Reported-by: DasSkelett <dasskelett@dasskelett.dev>
2026-01-24 09:44:57 +01:00
Beniamino Galvani
0731d8f3e0 bpf: clat: drop clat_handler()
Avoid the additional function call and perform the needed checks
directly in clat_handle_v4() and clat_handle_v6(). It will make easier
to check that the packet is linear is the next commit.
2026-01-24 09:44:55 +01:00
Beniamino Galvani
2d41711033 bpf: clat: support the IPv6 fragment header
Convert IPv6 fragments into IPv4.

The PLAT fragments IPv4 packets larger than the IPv6 MTU size into
smaller IPv6 packets. The safest IPv6 MTU value to configure on a PLAT
is the minimum IPv6 MTU, 1280. Therefore, we can expect IPv6 fragments
to be quite common.
2026-01-24 09:44:53 +01:00
Beniamino Galvani
616e18e61b l3cfg: fix CLAT MTU handling
The current code takes the IPv6 MTU value from the IPv6 default
route. However, that value is always zero because NM doesn't set it
usually. Instead, it should use the IPv6 MTU sysctl value. The problem
is that at this point NM hasn't written the sysctl yet, and we need
some logic to find the actual value.

Reported-by: DasSkelett <dasskelett@dasskelett.dev>
2026-01-24 09:44:50 +01:00
Beniamino Galvani
5cbd79a9ba core: introduce separate ipv6 mtu values in l3cd
The current "ip6_mtu" field of a l3cd is the IPv6 MTU received via
RA. Rename it accordingly and introduce another "ip6_mtu_static" field
that contains the value set in the ipv6.mtu connection property. It's
not used yet, but it will be in a following commit.
2026-01-24 09:44:48 +01:00
Beniamino Galvani
3699558106 bpf: clat: use IPv4 dummy address for ICMPv6 messages with native source
When running a traceroute for an IPv4 address, the nodes before the
NAT64 gateway return ICMPv6 Time Exceeded messages with a source IPv6
address not belonging to the NAT64 prefix. Such messages would be
normally dropped by the CLAT because the source address can't be
translated. This behavior complicates troubleshooting.

Follow the recommendation of
draft-ietf-v6ops-icmpext-xlat-v6only-source-01 and translate the
source address to the dummy IPv4 192.0.0.8.
2026-01-24 09:44:46 +01:00
Beniamino Galvani
2888d4c800 bpf: clat: fix redirect for outgoing packets
bpf_redirect_neigh() looks up the next hop in the routing table and
then redirects the packet to the given ifindex. The problem is that
the routing table might contain a default route with lower metric on a
different device; in that case the FIB lookup returns a next hop on
the other device, and the packet can't be delivered.

Use bpf_redirect() instead; the IPv4 already has the right L2
destination because the IPv4 default route points to the IPv6 gateway.

Reported-by: DasSkelett <dasskelett@dasskelett.dev>
2026-01-24 09:44:44 +01:00
Beniamino Galvani
6ac6d4f14e rpm: disable CLAT on i686
There is no bpftool compiled for i686.
2026-01-24 09:44:43 +01:00
Beniamino Galvani
6ec321d21b l3cfg: use the tcx attachment for the clat program
The TCX attachment type was added in kernel 6.6 (October 2023) and it
replaces the Traffic Control (TC) BPF attachment, providing better
usability. Convert the l3cfg code to use it.
2026-01-24 09:44:41 +01:00
Beniamino Galvani
bd67cefaaa ipv4: improve logging for ipv4.dhcp-ipv6-only-preferred 2026-01-24 09:44:40 +01:00
Beniamino Galvani
13cf12dd6e ipv4: enable by default ipv4.dhcp-ipv6-only-preferred when CLAT is on
When CLAT is enabled, we want to also enable and honor by default DHCP
option 108 (IPv6-only preferred), so that the host can avoid
requesting an IPv4 address and go IPv6-only.
2026-01-24 09:44:38 +01:00
Beniamino Galvani
193e37b410 bpf: clat: improve debug messages 2026-01-24 09:44:37 +01:00
Beniamino Galvani
c93ce65467 bpf: clat: translate inner headers of incoming ICMPv6 errors
ICMPv6 error messages contain a copy of the original packet that
caused the error. In a 464XLAT deployment, this inner packet is an
IPv6 packet (as translated by the PLAT), while the local host expects
to see the original IPv4 packet it generated.

Without translation, the local host can't match the error to an active
socket. This breaks functionality like Path MTU Discovery (PMTUD),
traceroute, and error reporting for connected UDP sockets.

This commit implements the translation of the inner headers from IPv6
to IPv4 for incoming ICMPv6 errors.

Some implementation notes:

 - this only handles incoming ICMPv6; outgoing ICMPv4 is not yet
   implemented, but it seems less important.

 - the program uses different functions for rewriting the outer and
   inner header. I tried using recursion but the verifier didn't seem
   to like it.

 - after rewriting the inner headers, the ICMP checksum is
   incrementally updated based on difference of all the individual
   modifications done to the inner headers. This has the advantage
   that all the operations are fixed-size. But probably it would be
   easier and faster to just calculate the checksum from scratch.
2026-01-24 09:44:36 +01:00
Beniamino Galvani
6f29305575 clat: support all pref64 lengths
Support all the prefix lengths defined in RFC 6052.
2026-01-24 09:42:36 +01:00
Beniamino Galvani
8414afd9ae clat: pass the configuration as a BPF global variable
The program only needs to know the local IPv4 address, the local IPv6
address and the PREF64. There is no need to create multiple maps for
that, just pass a global configuration struct containing those 3
fields.
2026-01-24 09:42:35 +01:00
Beniamino Galvani
8c83367a49 bpf: clat: improve the code style and consistency
Improve the code style and consistency of some functions:

- declare only one variable per line
- add "const" keyword to read-only function arguments
- remove unneeded function arguments
- rename variables holding headers on the stack with the "_buf"
  suffix
2026-01-24 09:42:34 +01:00
Beniamino Galvani
183d68dcbe bpf: clat: rework to avoid pointer arithmetic
Avoid using pointer arithmetic in the BPF program, so that it requires
only CAP_BPF and not CAP_PERFMON. In this context "pointer arithmetic"
means adding a variable value to a packet pointer. This means that the
program no longer tries to parse variable-size headers (IPv4 options,
IPv6 extension headers). Those were already not supported before. It
also doesn't parse VLAN tags, but there should be no need for that. If
we use fixed offset, we can avoid using the parsing helpers from
libxdp.
2026-01-24 09:42:33 +01:00
Beniamino Galvani
173dc154a0 bpf: clat: remove commented code
The rewrite of IPv6 header inside a ICMP error needs to be
implemented. Remove the unused comments for now.
2026-01-24 09:42:32 +01:00
Beniamino Galvani
e99a6452be bpf: clat: fix error handling for IPv6 packets
There are 3 possible results from clat_translate_v6():

 1. the packet didn't match the CLAT IPv6 address and must be
   accepted;

 2. the packet matches but it is invalid and so it must be dropped;

 3. the packet matches and it is valid; clat_handle_v6() should
    translate the packet to IPv4;

Before, the function returned TC_ACT_SHOT for both 2 and 3. Therefore,
clat_handle_v6() tried to rewrite also invalid packets.

Fix that by returning TC_ACT_UNSPEC for valid packets, meaning that
there isn't a final verdict yet.
2026-01-24 09:42:31 +01:00
Beniamino Galvani
232da41572 bpf: clat: don't explicitly inline functions
BPF handles function calls fine these days. Only leave the inline
qualifier on very small functions like csum_fold_helper().
2026-01-24 09:42:31 +01:00
Beniamino Galvani
213e9e33da bpf: clat: use the right endian-conversion function
bpf_ntohl() is more correct because the field is in network byte
order; but there is no actual change in behavior.
2026-01-24 09:42:30 +01:00
Beniamino Galvani
3af6761655 bpf: clat: fix translation of ICMPv6 Parameter Problem
According to RFC 6145 5.2, the pointer should be set for code 0, not
1.
2026-01-24 09:42:29 +01:00
Beniamino Galvani
6273f0afba bpf: clat: add missing "break" statements 2026-01-24 09:42:28 +01:00
Beniamino Galvani
d1351f1219 bpf: clat: remove unused includes 2026-01-24 09:42:27 +01:00
Beniamino Galvani
ade4de22f3 bpf: clat: remove unused variables 2026-01-24 09:42:27 +01:00
Beniamino Galvani
f9cd6e20a5 bpf: clat: fix other verifier errors
When copying the IPv6 addresses via a direct assignement, the compiler
generates 32-bit operations that the verifier doesn't like:

>   237: (61) r3 = *(u32 *)(r8 +76)       ; frame1: R3_w=pkt(r=0) R8=ctx()
>   ; .saddr = ip6h->saddr, @ clat.bpf.c:124
>   238: (63) *(u32 *)(r10 -64) = r3
>   invalid size of register spill

Use explicit memcpy() for those.

Also, check the packet length before accessing the ICMPv6 header.
2026-01-24 09:42:26 +01:00
Beniamino Galvani
815a795203 bpf: clat: avoid 32-bit register spills when access skb->data
The verifier reports this error when accessing skb->data:

  ; void *data     = (void *)(unsigned long long)skb->data; @ clat.bpf.c:625
  (61) r2 = *(u32 *)(r1 +76)       ; frame1: R1=ctx() R2_w=pkt(r=0)
  (63) *(u32 *)(r10 -120) = r2
  invalid size of register spill

Apparently it's trying to spill only 32 bits from the register to the
stack, which is invalid. A similar problem was reported here:
https://github.com/cilium/cilium/pull/25336

Add some macros using inline asm to fix the problem. With this change
now the compiler properly generates 64-bit spills.

 ; src/core/bpf/clat.bpf.c:625
-;     void *data     = (void *)(unsigned long long)skb->data;
+;     void *data     = SKB_DATA(skb);
      137:      61 12 4c 00 00 00 00 00 w2 = *(u32 *)(r1 + 0x4c)
-     138:      63 2a 88 ff 00 00 00 00 *(u32 *)(r10 - 0x78) = w2
+     138:      7b 2a 88 ff 00 00 00 00 *(u64 *)(r10 - 0x78) = r2
2026-01-24 09:42:25 +01:00
Mary Strodl
b5f534d31d NEWS: Note CLAT support 2026-01-24 09:42:22 +01:00
Beniamino Galvani
75c423f4c8 core: honor the ipv4.clat property 2026-01-24 09:42:01 +01:00
Beniamino Galvani
f11fb6dafc libnm,nmcli: add a new ipv4.clat property 2026-01-24 09:41:58 +01:00
Beniamino Galvani
ee1c91bbc8 ndisc: add support for PREF64 option (fixes) 2026-01-24 09:40:50 +01:00
Mary Strodl
4409c3d99a ndisc: add support for PREF64 option 2026-01-24 09:40:49 +01:00
Beniamino Galvani
76c18081d6 Add support for CLAT to l3cfg (fixes) 2026-01-24 09:40:49 +01:00
Mary Strodl
f0e77a4354 Add support for CLAT to l3cfg 2026-01-24 09:40:48 +01:00
Beniamino Galvani
ebb86ed2dd Add CLAT BPF program and build machinery (fixes) 2026-01-24 09:40:48 +01:00
Mary Strodl
fa9c00b595 Add CLAT BPF program and build machinery 2026-01-24 09:40:47 +01:00
Mary Strodl
dd3758dd80 contrib: Add libbpf and libxdp to dependencies
Required for CLAT support
2026-01-24 09:40:47 +01:00
Mary Strodl
83317fed4e l3-config-data: make get_direct_route_for_host public 2026-01-24 09:40:47 +01:00
Mary Strodl
afae4ddaf4 clat: propagate network_id down to l3cfg 2026-01-24 09:40:47 +01:00
Beniamino Galvani
5150a666cd netns: add a CLAT IP reservation type
This will be used to obtain an IPv4 address to be used for the CLAT
(464XLAT).

Based on a patch by Mary Strodl <ipadlover8322@gmail.com>.
2026-01-24 09:40:47 +01:00
Beniamino Galvani
c228427ae2 netns: allow defining a ip reservation that wraps around
The current implementation returns IP addresses obtained by adding a
counter to a base address. For CLAT we want to return all the 8
addresses in the 192.0.0.0/29 range, but not starting from 192.0.0.0
because that looks more like a network address. Slightly tweak the
algorithm so that addresses can wrap around.
2026-01-24 09:40:46 +01:00
Íñigo Huguet
87ee398db3 merge: branch 'update_ignored_phrases_and_words_in_product_names'
Update ignored phrases and words in product names

Closes #1863

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2346
2026-01-23 09:06:17 +00:00
Robert Schlabbach
7944f80f04 Update ignored phrases and words in product names
Update the lists of ignored phrases and words which are to be stripped
from product names, to remove product capabilities, the bus the product
attached on and similar nonsense.

Add tests for the product names which these additions are intended for.
2026-01-23 09:05:58 +00:00
Íñigo Huguet
5b6776089d merge: branch 'patch-3'
Update sl.po (Slovenian)

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2341
2026-01-23 08:59:29 +00:00
filmsi
4567c8e40f Replace sl.po (Slovenian) 2026-01-23 08:58:26 +00:00
Íñigo Huguet
85ba4d7c53 merge: branch 'main'
wwan: Ensure we get existing objects on reset

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/1957
2026-01-23 08:55:10 +00:00
Cédric Bellegarde
8f9bc6af94 wwan: Remove GDBusObjectManagerClient workaround
Tested with no ModemManager in the bus.

NetworkManager is receiving object-added signal. So hack not needed
anymore.
2026-01-23 08:03:51 +00:00
Beniamino Galvani
63e9b804e9 merge: branch 'rr/select-device-entry'
nmtui: select device entry when adding/editing connection

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2345
2026-01-22 19:55:56 +00:00
Rahul Rajesh
e10fac49bb nmtui: use select button to select available devices
Since it is error prone to manually type in interface names to match existing
ones, we introduce a select button that allows a user to chose from a list of devices.

- Show "Select..." button for physical devices to choose from available
  devices in a popup dialog.
- devices are sorted in alphabetical order.
- Only for physical devices (ethernet, infiniband, wifi, etc)

Resolves: https://issues.redhat.com/browse/RHEL-129186
2026-01-22 09:50:21 -05:00
Jan Vaclav
4c5478744c vpn: wait for device to become available before creating l3cd
In some situations, we will have a defined interface index, but
no device, because the idle source was not processed yet.

Reschedule _check_complete() in an idle source, so that it runs
after the device is processed.

Fixes: 306f9c490b ('vpn: Use nm_device_create_l3_config_data_from_connection if possible')
Resolves: https://issues.redhat.com/browse/RHEL-125796

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2347
(cherry picked from commit 574411b8a5)
2026-01-22 15:04:46 +01:00
Jan Vaclav
574411b8a5 vpn: wait for device to become available before creating l3cd
In some situations, we will have a defined interface index, but
no device, because the idle source was not processed yet.

Reschedule _check_complete() in an idle source, so that it runs
after the device is processed.

Fixes: 306f9c490b ('vpn: Use nm_device_create_l3_config_data_from_connection if possible')
Resolves: https://issues.redhat.com/browse/RHEL-125796

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2347
2026-01-22 14:51:58 +01:00
Beniamino Galvani
54e3859126 merge: branch 'bg/safe-file-access-syms-1-56' into nm-1-56 2026-01-20 15:29:14 +01:00
Beniamino Galvani
e776f80197 merge: branch 'bg/safe-file-access-syms-main' 2026-01-20 15:17:21 +01:00
Beniamino Galvani
a550828f76 libnm: add safe file access backported symbols from 1.54.3
Add to main branch symbols for safe file access that were
backported to 1.54.3 to allow seamless upgrading from 1.54 to 1.58.
2026-01-20 15:07:11 +01:00
Beniamino Galvani
cd223e6696 libnm: add safe file access backported symbols from 1.52.2
Add to main branch symbols for safe file access that were
backported to 1.52.2 to allow seamless upgrading from 1.52 to 1.58
2026-01-20 15:06:42 +01:00
Beniamino Galvani
6dc64dfa0c libnm: add safe file access backported symbols from 1.54.3
Add to branch nm-1-56 symbols for safe file access that were
backported to 1.54.3 to allow seamless upgrading from 1.54 to 1.56.
2026-01-20 15:03:48 +01:00
Beniamino Galvani
1a7f424ac8 libnm: add safe file access backported symbols from 1.52.2
Add to branch nm-1-56 symbols for safe file access that were
backported to 1.52.2 to allow seamless upgrading from 1.52 to 1.56.
2026-01-20 15:03:44 +01:00
Beniamino Galvani
c254c4df21 nmtui: fix build error
Fix the following error:

  In function ‘_nm_auto_unref_ptrarray’,
      inlined from ‘nmt_connect_connection_list’ at ../src/nmtui/nmtui-connect.c:593:34,
      inlined from ‘nmtui_connect’ at ../src/nmtui/nmtui-connect.c:673:16:
  ../src/libnm-std-aux/nm-std-aux.h:1106:12: error: ‘all_active_wifi_devices’ may be used uninitialized [-Werror=maybe-uninitialized]
   1106 |         if (*v)                               \
        |            ^
  ../src/nmtui/nmtui-connect.c: In function ‘nmtui_connect’:
  ../src/nmtui/nmtui-connect.c:593:34: note: ‘all_active_wifi_devices’ was declared here
    593 |     gs_unref_ptrarray GPtrArray *all_active_wifi_devices;

Fixes: 221da3f8c0 ('nmtui: feature: wifi-rescan feature for the nmtui.')
2026-01-20 14:11:54 +01:00
Beniamino Galvani
748be9a3e7 cloud-setup: fix format string
On a i686 machine the build fails with:

../src/nm-cloud-setup/main.c: In function ‘_oci_new_vlan_dev’:
../src/nm-cloud-setup/main.c:800:47: error: format ‘%ld’ expects argument of type ‘long int’, but argument 2 has type ‘gssize’ {aka ‘int’} [-Werror=format=]
  800 |     macvlan_name  = g_strdup_printf("macvlan%ld", config_data->iface_idx);
      |                                             ~~^   ~~~~~~~~~~~~~~~~~~~~~~
      |                                               |              |
      |                                               long int       gssize {aka int}
      |                                             %d
../src/nm-cloud-setup/main.c:801:42: error: format ‘%ld’ expects argument of type ‘long int’, but argument 3 has type ‘gssize’ {aka ‘int’} [-Werror=format=]
  801 |     connection_id = g_strdup_printf("%s%ld", connection_type, config_data->iface_idx);
      |                                        ~~^                    ~~~~~~~~~~~~~~~~~~~~~~
      |                                          |                               |
      |                                          long int                        gssize {aka int}
      |                                        %d

Fixes: 68d7e17737 ('Reapply "cloud-setup: create VLANs for multiple VNICs on OCI"')
2026-01-15 17:46:56 +01:00
Beniamino Galvani
9199c56f50 merge: branch 'bg/wifi-6ghz'
wifi: add support for new "6GHz" band

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2318
2026-01-15 16:44:06 +00:00
Beniamino Galvani
42e9cd1856 NEWS: update 2026-01-15 17:39:03 +01:00
Beniamino Galvani
499427a84e wifi: update the list of 5GHz channels
Update the list of Wi-Fi channels in the 5GHz band:

 - remove channels 7–16, which were part of 802.11j but were revoked
   in 2017;

 - remove the entries that are not valid as primary 20MHz channels but
   only as the center of bonded channels, e.g. 38, 42, etc.

 - add channel 144, introduced in the 802.11ac standard

Also restrict list of default channels for a 5GHz hotspot to those
that are available everywhere and without DFS.
2026-01-15 17:38:42 +01:00
Beniamino Galvani
c39b967a47 nmcli: print the band of wifi access points
It's a valuable information for users, especially because the channel
number can be ambiguous.

Before:
$ nmcli device wifi
IN-USE  BSSID              SSID   MODE   CHAN  RATE         SIGNAL  BARS  SECURITY
        42:00:00:AA:DD:CC  test   Infra  44    1170 Mbit/s  85      ▂▄▆█  WPA2
        92:00:00:AB:DD:CC  guest  Infra  44    1170 Mbit/s  85      ▂▄▆█  WPA2

After:
$ nmcli device wifi
IN-USE  BSSID              SSID   MODE   BAND     CHAN  RATE         SIGNAL  BARS  SECURITY
        42:00:00:AA:DD:CC  test   Infra  5 GHz    44    1170 Mbit/s  85      ▂▄▆█  WPA2
        42:00:00:AB:DD:CC  guest  Infra  5 GHz    44    1170 Mbit/s  85      ▂▄▆█  WPA2
2026-01-15 17:38:41 +01:00
Beniamino Galvani
7879acea8f libnm: export nm_utils_wifi_freq_to_band()
Clients typically want to show the band of an AP. The information is
already available because we export the frequency, but it is necessary
to implement some conversion logic.

Export libnm symbol nm_utils_wifi_freq_to_band() to do
that. Previously the function was used internally to generate the
value of the "band" string property from the frequency. For a public
function it is clearer if we return a enum value.
2026-01-15 17:38:41 +01:00
Thomas Makin
bb0a26e906 wifi: add support for new "6GHz" band
Until now the Wi-Fi bands were named after the first 802.11 standard
that introduced them: "a" for 5GHz introduced in 802.11a and "bg" for
2.4GHz introduced in 802.11b/g. With new bands added, this naming
scheme doesn't sound very intuitive to remember for users. Furthermore
we have now 6GHz that is introduced by 802.11ax (Wi-Fi 6), but the
compatible devices can use all three the bands (2.4, 5, 6 GHz).

For the 6 GHz band, simply name it "6GHz".

Co-authored-by: Beniamino Galvani <bgalvani@redhat.com>
2026-01-15 17:38:40 +01:00
Beniamino Galvani
5763b9b4de supplicant: fix center channel calculation
The formula is wrong for channels above 144 because the layout of the
80MHz channels is not regular. Use a lookup table.

Fixes: 7bb5961779 ('supplicant: honor the 'wifi.channel-width' property in AP mode')
2026-01-15 17:38:40 +01:00
Íñigo Huguet
ccc5f78fc4 merge: branch 'iwd-powersave'
device: Apply powersave configuration with iwd

Closes #1750

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2335
2026-01-15 08:55:43 +00:00
Vicki Pfau
5838c38b84 device: Apply powersave configuration with iwd
The powersave setting was apparently not touched at all in the iwd device,
so this adds the configuration, analogous to how the wifi device does.

Fixes #1750
2026-01-15 08:54:18 +00:00
Íñigo Huguet
57b6c1c5b7 merge: branch 'nmtui-wifi-rescan'
nmtui: feature: wifi-rescan feature for the nmtui.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2281
2026-01-15 07:55:48 +00:00
Rishabh Garg
221da3f8c0 nmtui: feature: wifi-rescan feature for the nmtui. 2026-01-15 07:55:48 +00:00
Íñigo Huguet
9c5b56d42a spec: move the main info to the top
It's clearer this way, and it will allow to modify directly the
"Version:" and "Release:" fields to bump the version. It is more aligned
with the layout of other projects' spec files too.

(cherry picked from commit 6d952902b9)
2026-01-13 09:32:49 +01:00
Íñigo Huguet
7372e93044 spec: remove snapshot and git_sha macros
Snapshot is only used from nm-copr-build.sh script, so not very useful.
Git_sha is used from build.sh. Other than that, downstream is always
nil.

Remove them and modify build.sh to use --define "dist xxx" instead of
them. This change is motivated by Packit not being able to modify the
release number if it has the %{snap} suffix.

(cherry picked from commit 5445ad2287)
2026-01-13 09:32:49 +01:00
Íñigo Huguet
d41cc08e78 spec: fix nmplugindir
When dist_version is defined in meson, NM installs plugins to a
directory called `NetworkManager-${dist_version}`. If the dist version
contains a `~`, like `1.56~rc1`, defining nmplugindir with
`%{version_no_tilde}` makes it `NetworkManager-1.56-rc1`, causing
rpmbuild errors due to the mismatch.

Fix it by defining nmplugindir with `%{version}` instead.

Fixes: d975389bcd ('spec: use versioning scheme with ~dev and ~rc suffixes')
(cherry picked from commit 9ebc8aa480)
2026-01-13 09:32:49 +01:00
Íñigo Huguet
4cf6f0f9a8 merge: branch 'ih/spec_rm_snap'
spec: fix nmplugindir, remove snapshot and git_sha, move main info to the top

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2342
2026-01-13 07:14:16 +00:00
Íñigo Huguet
6d952902b9 spec: move the main info to the top
It's clearer this way, and it will allow to modify directly the
"Version:" and "Release:" fields to bump the version. It is more aligned
with the layout of other projects' spec files too.
2026-01-12 08:35:29 +01:00
Íñigo Huguet
5445ad2287 spec: remove snapshot and git_sha macros
Snapshot is only used from nm-copr-build.sh script, so not very useful.
Git_sha is used from build.sh. Other than that, downstream is always
nil.

Remove them and modify build.sh to use --define "dist xxx" instead of
them. This change is motivated by Packit not being able to modify the
release number if it has the %{snap} suffix.
2026-01-12 08:35:24 +01:00
Íñigo Huguet
9ebc8aa480 spec: fix nmplugindir
When dist_version is defined in meson, NM installs plugins to a
directory called `NetworkManager-${dist_version}`. If the dist version
contains a `~`, like `1.56~rc1`, defining nmplugindir with
`%{version_no_tilde}` makes it `NetworkManager-1.56-rc1`, causing
rpmbuild errors due to the mismatch.

Fix it by defining nmplugindir with `%{version}` instead.

Fixes: d975389bcd ('spec: use versioning scheme with ~dev and ~rc suffixes')
2026-01-09 08:44:37 +01:00
Beniamino Galvani
85c5ba18ee merge: branch 'bg/supplicant-blob-size'
supplicant: properly validate blobs

Closes #1850

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2334

(cherry picked from commit 7cae64ac02)
2026-01-08 10:20:28 +01:00
Beniamino Galvani
7575117ab5 supplicant: properly validate blobs
The purpose of the validation is to check that we pass to the
supplicant a configuration that it can understand. For certificates
and keys we enforce a maximum length of 64KiB; that means that the
value of the property we send (i.e. the file path or the blob id) can
be at most 64KiB. Instead we wrongly checked the size of the blob
data.

Fix the validation. Also, enforce a maximum blob size of 32MiB.

Fixes: e85cc46d0b ('core: pass certificates as blobs to supplicant for private connections')
(cherry picked from commit eb784c3f27)
2026-01-08 10:20:28 +01:00
Beniamino Galvani
258686968f core: limit the result from the helper to 32MiB
(cherry picked from commit c4b39914c4)
2026-01-08 10:20:28 +01:00
Beniamino Galvani
7cae64ac02 merge: branch 'bg/supplicant-blob-size'
supplicant: properly validate blobs

Closes #1850

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2334
2026-01-07 17:23:02 +00:00
Beniamino Galvani
eb784c3f27 supplicant: properly validate blobs
The purpose of the validation is to check that we pass to the
supplicant a configuration that it can understand. For certificates
and keys we enforce a maximum length of 64KiB; that means that the
value of the property we send (i.e. the file path or the blob id) can
be at most 64KiB. Instead we wrongly checked the size of the blob
data.

Fix the validation. Also, enforce a maximum blob size of 32MiB.

Fixes: e85cc46d0b ('core: pass certificates as blobs to supplicant for private connections')
2026-01-07 18:20:43 +01:00
Beniamino Galvani
c4b39914c4 core: limit the result from the helper to 32MiB 2026-01-07 18:20:43 +01:00
Íñigo Huguet
4de02945b5 NEWS: update
And fix previous changes that incorrectly assigned the latest change to
1.56.1, when actually not even .0 has been released yet (we're still in
RC).
2026-01-07 15:18:31 +01:00
Íñigo Huguet
f3ec3957ff release.sh: use versioning scheme with -dev and -rc suffixes
The previous commits has unified the versioning scheme to only use the
version names like 1.56-rc2, 1.56.2 and 1.57.1-dev, like the version
names that we use in the Git tags. The scheme with micro>=90 for RCs
will be used only internally, in the C headers. The tarballs will be
named with the new scheme.

Adapt the release.sh script to correctly understand this versioning
scheme and to create the tarballs with the right new name.

This will enable us to use Packit to automate rpm updates.

(cherry picked from commit 9f4261168d)
2026-01-07 13:02:25 +01:00
Íñigo Huguet
92a6af3be3 spec: use versioning scheme with ~dev and ~rc suffixes
In the previous commit meson.build was adapted to use versions with -dev
and -rc suffixes, as we create them in the Git tags, instead of versions
with micro>90 for RCs as we used to do. The tarball name will contain
the version with the new scheme, so adapt the spec file for it.

This will enable us to use Packit to do automatic updates.

(cherry picked from commit d975389bcd)
2026-01-07 13:02:25 +01:00
Íñigo Huguet
1b1612f064 meson: specify project version with the -dev and -rc suffixes
This will create the tarball with names NetworkManager-1.56-rc2.tar.xz
or NetworkManager-1.57.1-dev.tar.xz. This way they will match with the
name of the Git tag, making easier for users, and specially for tools
like Packit, to understand the versioning scheme.

The goal is to make that there is only one public versioning scheme, the
one with -rc and -dev suffixes. Version numbers with micro>=90 for RC
releases is kept only as an internal thing for the C headers. Users of
the API can still use it.

Bump meson version to 0.56 to use str.substring().

(cherry picked from commit e422b1c3d9)
2026-01-07 13:02:16 +01:00
Íñigo Huguet
99514da050 merge: branch 'ih/versions-packit'
versioning: use everywhere the versioning scheme from the Git tags

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2332
2026-01-07 10:26:10 +00:00
Íñigo Huguet
4ce317a261 NEWS: update 2026-01-07 10:25:56 +00:00
Íñigo Huguet
9f4261168d release.sh: use versioning scheme with -dev and -rc suffixes
The previous commits has unified the versioning scheme to only use the
version names like 1.56-rc2, 1.56.2 and 1.57.1-dev, like the version
names that we use in the Git tags. The scheme with micro>=90 for RCs
will be used only internally, in the C headers. The tarballs will be
named with the new scheme.

Adapt the release.sh script to correctly understand this versioning
scheme and to create the tarballs with the right new name.

This will enable us to use Packit to automate rpm updates.
2026-01-07 10:25:56 +00:00
Íñigo Huguet
d975389bcd spec: use versioning scheme with ~dev and ~rc suffixes
In the previous commit meson.build was adapted to use versions with -dev
and -rc suffixes, as we create them in the Git tags, instead of versions
with micro>90 for RCs as we used to do. The tarball name will contain
the version with the new scheme, so adapt the spec file for it.

This will enable us to use Packit to do automatic updates.
2026-01-07 10:25:56 +00:00
Íñigo Huguet
e422b1c3d9 meson: specify project version with the -dev and -rc suffixes
This will create the tarball with names NetworkManager-1.56-rc2.tar.xz
or NetworkManager-1.57.1-dev.tar.xz. This way they will match with the
name of the Git tag, making easier for users, and specially for tools
like Packit, to understand the versioning scheme.

The goal is to make that there is only one public versioning scheme, the
one with -rc and -dev suffixes. Version numbers with micro>=90 for RC
releases is kept only as an internal thing for the C headers. Users of
the API can still use it.

Bump meson version to 0.56 to use str.substring().
2026-01-07 10:25:56 +00:00
Beniamino Galvani
19ac54fbd6 merge: branch 'bg/builtin-ping'
Use an internal "ping" implementation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2328
2026-01-07 09:16:19 +00:00
Beniamino Galvani
6b062dfeb5 rpm: drop weak dependency on iputils 2026-01-07 09:49:36 +01:00
Beniamino Galvani
de8d74aa08 device: use the internal ping implementation
Currently NetworkManager depends on the external ping binary to
perform the reachability check on IP addresses. This means that the NM
daemon package must depend on another package. On Fedora the iputils
package is 800KiB.

Implement the same functionality natively so that we can drop such
dependency.
2026-01-07 09:49:32 +01:00
Beniamino Galvani
90ea2ddb90 core: introduce nm_utils_ping_host()
Introduce a function that pings a given host. It opens a "ping socket"
(IPPROTO_ICMP), binds it to the given ifindex, connects it to the
remote address, and keep sending ICMP echo-request packets until it
receives a reply or the optional timeout is reached. By using this
kind of socket, the kernel automatically sets the ICMP ID on outgoing
packets and matches incoming packets by the same ID.
2026-01-07 09:48:00 +01:00
Íñigo Huguet
b416156b10 merge: branch 'bulgarian'
Update Bulgarian translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2331
2025-12-24 15:10:40 +00:00
twlvnn
9febe04761 Update Bulgarian translation 2025-12-24 15:08:56 +00:00
Íñigo Huguet
71b9d83349 merge: branch 'main'
Update Turkish translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2336
2025-12-24 15:08:10 +00:00
Muhammet Kara
664ba417c7 Update Turkish translation
Signed-off-by: Muhammet Kara <muhammetk@gmail.com>
2025-12-22 02:00:43 +03:00
Beniamino Galvani
a31a644f8b merge: branch 'bg/deprecate-wext'
build: deprecate Wireless Extensions

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2309
2025-12-18 15:14:45 +00:00
Beniamino Galvani
a45163b131 rpm: disable wireless extensions on Fedora
The Fedora kernel is built without WEXT since many years:

https://fedoraproject.org/wiki/Changes/RemoveWirelessExtensions
2025-12-18 16:06:44 +01:00
Beniamino Galvani
de1fcdcc72 build: deprecate Wireless Extensions
Wireless Extensions is the legacy, ioctl-based kernel interface used
to configure Wi-Fi cards. It has been deprecated and replaced by the
cfg80211/nl80211 API since 2007, as it doesn't support modern Wi-Fi
encryption and technologies. Mark it as deprecated, so that we can get
rid of some unmaintained and untested code in a future release.
2025-12-18 16:06:42 +01:00
Beniamino Galvani
d399ffbaba 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')
(cherry picked from commit 427a7cf257)
2025-12-17 12:01:54 +01:00
Beniamino Galvani
50387acd4b 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
(cherry picked from commit 3a4e18e302)
2025-12-17 12:01:53 +01:00
Beniamino Galvani
102c763348 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
(cherry picked from commit dad4da06b1)
2025-12-17 12:01:37 +01:00
Beniamino Galvani
a2d147366c Merge branch 'bg/issue1688'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2323
2025-12-17 11:59:20 +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
c978963ee7 release: bump version to 1.55.91 (1.56-rc2) (development) 2025-12-12 16:23:41 +01:00
Íñigo Huguet
8e0825f9cd release: bump version to 1.57.1 (development) 2025-12-12 16:01:44 +01:00
Íñigo Huguet
ea759ccf3a 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')
(cherry picked from commit 599cc1ed1d)
2025-12-12 15:40:41 +01:00
Íñigo Huguet
df8288de7f merge: branch 'ih/strerror_r'
Fix two compilation issues

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2330
2025-12-12 14:36:58 +00:00
Íñigo Huguet
118475d571 ci: build with -D systemdsystemgeneratordir=no
Avoid build failures in some distros.
  ERROR: Assert failed: systemd required but not found, please provide a valid systemd user generator dir or disable it

Fixes: 636fb5ef24 ('systemd: install initrd services using a generator')
2025-12-12 15:24:09 +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
Íñigo Huguet
db473709db merge: branch 'nm-1-56-issue1809'
[nm-1-56] CVE-2025-9615: avoid that non-admin user using other users' certificates

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2325
2025-12-12 12:30:08 +00:00
Íñigo Huguet
1756ec54e3 merge: branch 'issue1809'
CVE-2025-9615: avoid that non-admin user using other users' certificates.

Closes #1809

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2324
2025-12-12 12:29:41 +00:00
Íñigo Huguet
a9d7154fe1 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.

(cherry picked from commit 13bfa44ceb)
2025-12-12 12:47:26 +01:00
Beniamino Galvani
3d85bace3d 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.

(cherry picked from commit 1a52bbe7c9)
2025-12-12 12:47:02 +01:00
Beniamino Galvani
8437e14758 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.

(cherry picked from commit 10db4baeb6)
2025-12-12 12:45:56 +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
d8f143f601 spec: enable polkit_noauth_group for Fedora <= 43 and RHEL <= 10
In Fedora 44 and RHEL 11, admin users will need to type their password
even on local consoles.
2025-12-12 12:38:48 +01:00
Íñigo Huguet
39143f8bdd polkit: add build option to allow admin users not to type their password
Add a build option to allow installing a Polkit rule that will grant
permissions for admin users without asking for their password if they're
in a local console.

This shouldn't be encouraged, though. It's common practice that admin
users has to introduce their password to make system-wide changes. The
standard polkit policy, without this rule, is auth_admin_keep. This
policy will ask for the password once and won't ask for it again for
~5 minutes, so it is not too unconvenient.

Different distros use different group names for users with admin rights,
typically 'sudo' or 'wheel'. The build option allows to define the
desired group, or to leave it empty to not install the rule.

However, until the previous commit it was allowed that local users (even
non-admin) could do system-wide changes without introducing a password.
This option allows to maintain the same behavior for admin users,
keeping backwards compatibility so we avoid breaking existing scripts,
for example. We cannot achieve the same for non-admin users because
allowing them to create system-wide connection causes security
vulnerabilities that cannot be fixed in any other way.
2025-12-12 12:38:48 +01:00
Íñigo Huguet
0b75d905e5 polkit: remove the modify_system build option
This build option allowed non-admin users to create system-wide
connections. Generally, this is not a good idea as system-wide changes
should be done by administrators.

However, the main reason for the change is that this can be used to
bypass filesystem permissions, among possibly other attacks. As the
daemon runs as root, a user can create a system-wide connection that
uses a certificate from a different user to authenticate in a WiFi
network protected with 802.1X or a VPN, because as root user the daemon
can access to the file.

This patch does not completely fix the issue, as users can still create
private connections specifying a path to another user's connection. This
will be addressed in other patch. However, this patch is needed too,
because in system-wide connections we don't store which user created the
connection, so there woudn't be any way to check his/her permissions.

This is part of the fix for CVE-2025-9615

See: https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1809
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
e3c27f2a22 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.

(cherry picked from commit acbfae5e05)
2025-12-10 09:46:24 +01:00
Beniamino Galvani
aac5b80fca 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.

(cherry picked from commit 36ea70c099)
2025-12-10 09:46:22 +01:00
Beniamino Galvani
a417df3484 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.

(cherry picked from commit 98e6dbdf21)
2025-12-10 09:45:15 +01:00
Beniamino Galvani
9432822f34 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.

(cherry picked from commit de4eb64253)
2025-12-10 09:45:15 +01:00
Beniamino Galvani
a17f51fe15 supplicant: rename variables
Rename uid to to blob_id, and con_uid to con_uuid.

(cherry picked from commit 586f7700b8)
2025-12-10 09:45:15 +01:00
Beniamino Galvani
59df5fc93f 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.

(cherry picked from commit 1d90d50fc6)
2025-12-10 09:45:14 +01:00
Beniamino Galvani
ce3ebf6d3e 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.

(cherry picked from commit 0093bbd950)
2025-12-10 09:45:14 +01:00
Beniamino Galvani
022b992846 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.

(cherry picked from commit 285457a5f8)
2025-12-10 09:45:14 +01:00
Beniamino Galvani
afa6fc951b 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.

(cherry picked from commit 3d76d12eee)
2025-12-10 09:45:14 +01:00
Beniamino Galvani
2fc662cc71 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.

(cherry picked from commit 59543620dc)
2025-12-10 09:45:14 +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
0b61924048 merge: branch 'jv/fix-rawhide-build'
all: fix NM compilation on rawhide

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2321
2025-12-04 12:01:18 +00: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
Jan Vaclav
4e7e159224 merge: branch 'jv/unifcfg-scripts'
build/configure_for_system: stop building with ifcfg_rh support

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2320
2025-12-04 11:50:02 +00:00
Jan Vaclav
ae134ca9f4 build/configure_for_system: stop building with ifcfg_rh support
It has been deprecated for a long time, so it would be probably
fine to stop building with it enabled. RHEL 9 is excluded since
it still supports the ifcfg-rh format.
2025-12-04 11:33:13 +00:00
Jan Vaclav
55f96057c6 build/configure_for_system: disable building with team on rhel10+ 2025-12-04 11:33:13 +00:00
Jan Vaclav
de0a37b248 build: fix rhel version detection in configure_for_system 2025-12-04 11:33:13 +00:00
Beniamino Galvani
7315e7e0ee merge: branch 'saemismatch-signal-handlers'
core: add handlers for SaePasswordMismatch signal

Closes #904

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2293
2025-12-03 16:08:41 +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
Beniamino Galvani
561fff3c8d merge: branch 'main'
connectivity: add per-device check-connectivity setting

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2316
2025-12-02 09:55:34 +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
Till Maas
c1519bd514 merge: branch 'update_pt_BR'
Update Brazilian translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2307
2025-11-26 22:16:53 +01:00
Rafael Fontenelle
8b5a61458b Update Brazilian Portuguese translation
Co-authored-by: Matheus Barbosa <mdpb.matheus@gmail.com>
Co-authored-by: Samuel Schlemper <samuelschlemper2006@gmail.com>
Co-authored-by: Juliano de Souza Camargo <julianosc@pm.me>
2025-11-26 22:16:25 +01:00
Beniamino Galvani
9e01443b14 man: describe the allowed boolean values in NetworkManager.conf
The NetworkManager.conf man page is describing some options as
"whether X is enabled", without explicitly saying that it's a
boolean. Also, the allowed values are not mentioned. Clarify those
aspects.
2025-11-26 09:03:11 +01:00
Beniamino Galvani
78519589b9 NEWS: update 2025-11-26 09:03:08 +01:00
Till Maas
771f86105e merge: branch 'patch-2'
Updated Slovenian translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2317
2025-11-24 21:31:56 +01:00
filmsi
b3f9f52505 Updated Slovenian translation 2025-11-24 21:31:55 +01:00
Beniamino Galvani
b41a5ec2d4 merge: branch 'initrd-services-dbus-fix'
systemd: install initrd services using a generator

Closes #1814

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2312
2025-11-20 17:41:45 +00: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
4610511bcd 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')
(cherry picked from commit 6e2de1d2b3)
2025-11-20 09:28:59 +01:00
Beniamino Galvani
d006d61aa1 merge: branch 'main'
core: restrict connectivity check lookups to per-link DNS if available

Closes #1836

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2313
2025-11-20 08:24:08 +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
Beniamino Galvani
686effaabe merge: branch 'mptcp-laminar'
mptcp: add `laminar` endpoint support and set it by default

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2314

(cherry picked from commit 4afa00874f)
2025-11-19 15:01:59 +01:00
Matthieu Baerts (NGI0)
380cd0d248 NEWS: new MPTCP 'laminar' endpoint & default
A summary linked to the last two commits.

Signed-off-by: Matthieu Baerts (NGI0) <matttbe@kernel.org>
(cherry picked from commit 3ce1da1fd2)
2025-11-19 15:01:58 +01:00
Matthieu Baerts (NGI0)
12a4696229 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>
(cherry picked from commit 8caa781270)
2025-11-19 15:01:58 +01:00
Matthieu Baerts (NGI0)
e3f20ecf95 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>
(cherry picked from commit 2b03057de0)
2025-11-19 15:01:58 +01:00
Beniamino Galvani
4afa00874f merge: branch 'mptcp-laminar'
mptcp: add `laminar` endpoint support and set it by default

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2314
2025-11-19 14:01:05 +00:00
Matthieu Baerts (NGI0)
3ce1da1fd2 NEWS: new MPTCP 'laminar' endpoint & default
A summary linked to the last two commits.

Signed-off-by: Matthieu Baerts (NGI0) <matttbe@kernel.org>
2025-11-19 12:54:09 +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
f0cdf16e1d 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')
(cherry picked from commit 3b10b88290)
2025-11-18 15:02:45 +01: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
e74cf8fcc4 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.

(cherry picked from commit d687768c61)
2025-11-18 10:51:56 +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
Íñigo Huguet
239b0fbbc9 release: bump version to 1.57.0 (development) 2025-11-17 16:42:05 +01:00
Íñigo Huguet
29d523391a release: bump version to 1.55.90 (1.56-rc1) 2025-11-17 16:35:34 +01:00
Beniamino Galvani
f4bf54ca93 merge: branch 'bg/ndisc-ratelimit-warns'
ndisc: rate limit messages about invalid RAs

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2294
2025-11-12 13:12:25 +00: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
Jan Vaclav
5f85b55f7f NEWS: update
Fixes: 04ddd72ce9 ('merge: branch 'jv/import-nacd'')
2025-10-30 12:34:16 +01:00
Beniamino Galvani
461c9edfb4 merge: branch 'main'
Correctly apply some connection properties to vpn connections

Closes #1109

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2279
2025-10-27 09:46:41 +00: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
caf156b2ac merge: branch 'ih/fix-ci-pages'
ci: fix pages job

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2303
2025-10-24 11:58:18 +00:00
Íñigo Huguet
ed43e4b602 ci: fix pages job
Fix the rule that triggers this job so it is run each time that a commit
is pushed/merged to main. The incorrect rule was doing that it only ran
when the *source* branch (or a MR) was called "main". Therefore, it was
(almost) never running.

Fixes: 69efb4660c ('CI: periodically clean image's registry')
2025-10-24 12:48:20 +02:00
Íñigo Huguet
384dd7d5f2 merge: branch 'ih/forwarding'
core: ip forwarding: improve performance setting IPv4 forwarding for method=shared and forwarding=auto

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2201
2025-10-24 05:27:36 +00: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
Beniamino Galvani
b4e8edbc8a merge: branch 'pskmismatch-signal-handlers'
core: add handlers for PskMismatch signal

Closes #904

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2287
2025-10-23 14:38:43 +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
04ddd72ce9 merge: branch 'jv/import-nacd'
n-acd: detect eBPF capability at runtime

Closes #1049

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2300
2025-10-23 13:33:30 +00:00
Íñigo Huguet
58f46a6d11 merge: branch 'localhost'
core: nm-dns-dnsmasq: listen on ipv6 localhost too

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/1504
2025-10-23 05:42:34 +00:00
Jan Vaclav
427137d6da service: add CAP_BPF capability to NetworkManager
Since we are now always building n-acd with eBPF, and
are able to detect eBPF support at runtime, we can
reflect this in the unit as well.

Add CAP_BPF to CapabilityBoundingSet, so that NM can
request to create a BPF map when setting up n-acd.
2025-10-22 21:49:56 +02: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
Jan Vaclav
3a769bca67 n-acd: re-import git-subtree for 'src/n-acd'
git subtree pull --prefix src/n-acd git@github.com:nettools/n-acd.git master --squash
2025-10-22 20:09:16 +02:00
Jan Vaclav
0530af60b3 Squashed 'src/n-acd/' changes from a600afc870..6ac6f7e105
6ac6f7e105 n-acd: runtime eBPF support detection

git-subtree-dir: src/n-acd
git-subtree-split: 6ac6f7e105c06e0c352b78b5a136f87fcb5c7432
2025-10-22 20:09:16 +02:00
Jiri Slaby (SUSE)
a0482a4e35 core: nm-dns-dnsmasq: listen on ipv6 localhost too
Trying to resolve hosts using localhost errors out for ipv6 attempts:
  $ host www.seznam.cz localhost
  ;; communications error to ::1#53: connection refused
  ;; communications error to ::1#53: connection refused
  Using domain server:
  Name: localhost
  Address: 127.0.0.1#53
  Aliases:

  www.seznam.cz has address 77.75.77.222
  www.seznam.cz has address 77.75.79.222
  ;; communications error to ::1#53: connection refused
  ;; communications error to ::1#53: connection refused
  www.seznam.cz has IPv6 address 2a02:598:a::79:222
  www.seznam.cz has IPv6 address 2a02:598:2::1222
  ;; communications error to ::1#53: connection refused
  ;; communications error to ::1#53: connection refused

It's because on some distros (like openSUSE), localhost is defined both
as 127.0.0.1 and ::1.

So listen on ::1 too. This makes ipv4-switchoff easier.
/etc/resolv.conf should likely be updated to contain ::1 eventually too
(see update_dns()).

Fixes https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1188
2025-10-22 15:42:57 +02:00
Beniamino Galvani
0e121f5658 merge: branch 'bg/dns-no-stub'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2298
2025-10-22 10:01:46 +02:00
Beniamino Galvani
2d438ebef8 dns: specify a temporary file name when writing no-stub-resolv.conf
Using g_file_set_contents() makes it impossible to write a proper
SELinux policy because the function creates a file with a random
suffix, and SELinux file transitions can't match on wildcards.

Use a fixed temporary file name. In this case it's fine because
/run/NetworkManager is only writable by root and NetworkManager is the
only process writing into it.
2025-10-22 09:56:39 +02:00
Beniamino Galvani
c312390932 libnm-glib-aux: add temp name argument to nm_utils_file_set_contents()
In some cases it's useful to specify the name of the temporary file to
be used.
2025-10-22 09:56:39 +02:00
Íñigo Huguet
d06fd85e57 merge: branch 'ih/ovsdb-update-log'
ovs: print clearer logs of the ovsdb "update" event

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2297
2025-10-22 06:07:32 +00:00
Íñigo Huguet
2a63c33712 ovs: print clearer logs of the ovsdb "update" event
These lines says things like "changed a bridge", what seems to mean that
NM is doing the change. Actually, these logs indicate changes that NM is
being notified of, and they may even be external changes.

- Add the "monitor:" prefix to show that it's something that NM is
  monitoring, not doing.
- Say "bridge changed" instead of "changed a bridge", which sounds an
  action that we're doing.
- Print the bridge/port/iface name first, instead of the uuid-like key which
  is not useful for a quick look by a human.
- Print `connection=conn-uuid` instead of just `conn-uuid`, as it's not
  obvious that the uuid refers to the connection.

Before:
  ovsdb: obj[bridge:8c975244-cb0a-4add-8901-c398dcbc27d6]: changed a bridge: br-int, b1ef934d...

After:
  ovsdb: monitor: br-int: bridge changed: obj[bridge:8c975244-cb0a-4add-8901-c398dcbc27d6], connection=b1ef934d...
2025-10-22 06:07:25 +00:00
Beniamino Galvani
ce26d85ad1 merge: branch 'bg/reject-unsupported-conns'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2299
2025-10-21 15:34:19 +02:00
Beniamino Galvani
1e81aaa153 settings: document some data structures 2025-10-21 15:31:58 +02:00
Beniamino Galvani
c1baf09bf9 settings: ignore unsupported connections when they are loaded
In addition to rejecting new connections added via D-Bus when they are
unsupported, also ignore the existing on-disk ones.
2025-10-21 15:31:58 +02:00
Beniamino Galvani
247000deed core: reject new connections if the feature is disabled or removed
If a feature like Wi-Fi, OVS, team, etc. is disabled or no longer
supported, it is better to report an error when the connection is
added via nmcli than accepting the connection and complaining later
about a "missing plugin"; there is no plugin and the connection will
never be able to activate.

Example errors now:
  # nmcli connection add type team
  Error: Failed to add 'team-nm-team' connection: team support is disabled in this build

  # nmcli connection add type gsm
  Error: Failed to add 'gsm' connection: WWAN support is disabled in this build

  # nmcli connection add type wimax nsp 00:99:88:77:66:55
  Error: Failed to add 'wimax' connection: WiMAX is no longer supported

Note that we don't touch libnm-core (the part defining the settings
and properties), as that defines the API of NetworkManager. The API
should not change according to compile flags.
2025-10-21 15:31:58 +02:00
Íñigo Huguet
e5ae988603 merge: branch 'fix-autoreconnection'
Fix: unblock autoreconnect when a previously failed connection is now successful

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2295
2025-10-21 09:43:05 +00:00
Antoine Lassagne
03791e8b2d Fix: unblock autoreconnect when a previously failed connection is now successful 2025-10-21 09:39:52 +00:00
Beniamino Galvani
965aa81027 device: set bridge in supplicant for 802.1X ethernet and macsec
When authenticating via 802.1X, the supplicant must be made aware of
the bridge the interface is attached to. This was already done for
wifi in commit ae31b4bf4e ('wifi: set the BridgeIfname supplicant
property when needed'). When setting the BridgeIfname property, the
supplicant opens an additional socket to listen on the bridge, to
ensure that all incoming EAPOL packets are received.

Without this patch, the initial authentication usually works because
it is started during stage2 (prepare), when the device is not yet
attached to the bridge, but then the re-authentication fails.

Note: I could reproduce the problem only when the bridge is configured
with bridge.group-forward-mask 8.

Resolves: https://issues.redhat.com/browse/RHEL-121153
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2301
2025-10-21 11:26:08 +02:00
Jan Vaclav
86b67233bf merge: branch 'jv/hsr-interlink'
libnm: introduce `hsr.interlink` property

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2285
2025-10-13 10:42:51 +00:00
Beniamino Galvani
a148232789 merge: branch 'dnssec'
Add support for systemd-resolved's DNSSEC option

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2278
2025-10-13 10:10:34 +00:00
Robin Ebert
2bc895c0e9
NEWS: add new connection.dnssec feature to NEWS 2025-10-13 11:58:11 +02:00
Robin Ebert
c6a6801b1e
ifcfg-rh: throw error if connection.dnssec is used 2025-10-13 11:57:54 +02:00
Robin Ebert
46306c1be0
cli: add support for connection.dnssec 2025-10-13 11:57:53 +02:00
Robin Ebert
1dcd63ab5d
core: add support for connection.dnssec 2025-10-13 11:57:53 +02:00
Robin Ebert
029f8be4c1
libnm-core: Add connection.dnssec property 2025-10-13 11:57:34 +02:00
Íñigo Huguet
e6a31264c1 merge: branch 'ih/ovs-external-ports'
ovs: don't remove unrelated external ports

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2296
2025-10-13 06:58:30 +00:00
Íñigo Huguet
86ea2c5963 man: ovs: document known limitation when removing ifaces and ports
Document a known limitation that we delete bridges and ports from ovsdb
when we remove their last NM-owned attached port or interface, even if
other externally added ports or interfaces exist.
2025-10-13 06:58:23 +00:00
Íñigo Huguet
93491d76ec ovs: don't remove unrelated external ports
The commit linked below introduced a bug that caused that OVS ports
added externally to NM are always deleted when we delete any OVS
interface. It affects to all externally added ports, including those
that are not related to the deleted interface and even those in
different OVS bridges.

Fix it by only modifying ports and bridges that are ascendants of the
deleted interface, leaving everything else untouched.

Note that bridges and ports still need to have at least one NM-managed
interface, otherwise they will also be purged. For example, an NM-owned
OVS bridge with 2 ports+iface, one NM-owned and one external: if we
delete the NM-owned iface, both ports and the bridge will be deleted.
For now, this is a known limitation that is not being fixed here.

Fixes: 476c89b6f2 ('ovs: only keep bridges and ports with NM interfaces attached')
2025-10-13 06:58:23 +00:00
Íñigo Huguet
b271e0a051 merge: branch 'filmsi/update-po'
Update Slovenian translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2292
2025-10-10 14:51:37 +00:00
filmsi
f0f4d0dba0 Update Slovenian translation 2025-10-10 14:51:16 +00:00
Íñigo Huguet
4e10b1e6ab merge: branch 'hotfix/mstrodl/no-operator-code-retry'
wwan: retry after no operator code

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2270
2025-10-10 12:21:23 +00:00
Mary Strodl
52d08008b7
wwan: retry after no operator code
We've had a few rare instances where a modem stopped retrying
to autoconnect because it briefly didn't have an operator code.

This isn't a permanent failure, so we shouldn't abort completely
for it.
2025-10-10 08:16:57 -04:00
Íñigo Huguet
92aeed1f5c merge: branch 'patch-1'
Fix the exit test condition on modem state when creating the connection properties

Closes #1741

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2247
2025-10-09 06:42:22 +00:00
Christian Müller
018c5722ee Fix the exit test condition on modem state when creating the connection properties 2025-10-09 06:42:22 +00:00
Jan Vaclav
bf8b38618a NEWS: update 2025-10-08 22:52:14 +02:00
Jan Vaclav
17efec8b06 platform: configure HSR interlink from property
Uses the `hsr.interlink` property defined in the previous
commit to configure the property in the kernel.
2025-10-08 22:52:03 +02:00
Jan Vaclav
69d0fb161e libnm: introduce hsr.interlink property
This property allows the user to optionally configure
an interlink name on a HSR interface, so that it could
serve as RedBox (Redundant Box) by connecting DAN (dual
attachment node) to SAN (single attachment node).
2025-10-08 22:52:03 +02:00
Jan Vaclav
59c65bc859 merge: branch 'sktranslation_update'
Update Slovak translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2286
2025-10-07 10:31:27 +02:00
Jan Vaclav
a46827f899 merge: branch 'jv/hsr-version'
libnm: introduce `hsr.protocol-version` property

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2283
2025-10-06 09:02:04 +00:00
Íñigo Huguet
6801ce4927 merge: branch 'catalan_fixes'
Fixes to Catalan translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2289
2025-10-03 11:21:26 +00:00
Jordi Mas
6e32a8e821 Fixes to Catalan translation 2025-10-03 11:21:15 +00:00
Íñigo Huguet
13d7469ba0 merge: branch 'wwan-device-name-restriction'
add gsm device-uid setting to restrict the devices the connection applies to

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2176
2025-10-03 11:03:13 +00:00
Michael Mokricky
820e56c5df add gsm device-uid setting to restrict the devices the connection applies to 2025-10-03 11:02:21 +00:00
Jan Vaclav
c27caec33d NEWS: update 2025-09-30 14:29:00 +02:00
Jan Vaclav
0b99629278 platform: configure HSR protocol version from property
Uses the `hsr.protocol-version` property defined in the previous
commit to configure the property in the kernel.
2025-09-30 14:28:49 +02:00
Jan Vaclav
9a2395c779 libnm: introduce hsr.protocol-version property
This property allows the user to set the protocol
version when using HSR. Currently, the property
supports two values - `2010` (referred to as HSRv0
in the kernel), and `2012` (HSRv1).
2025-09-30 14:28:48 +02:00
Jose Riha
ddb31034f9 Update Slovak translation 2025-09-26 17:34:34 +02:00
Íñigo Huguet
9e0551aefd core: document CleanupType
We must do different cleanups depending on the CleanupType. Document the
meaning of the different types as it was very confusing to work on new
code without having very clear what do they mean.
2025-09-24 11:30:59 +02:00
Íñigo Huguet
dbec15eb8d merge: branch 'ih/net-off-logging'
Improve logging of `networking off`

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2284
2025-09-24 05:21:21 +00:00
Íñigo Huguet
48fc40e1ca core: rename unmanaged flag SLEEPING->MANAGER_DISABLED
The flag is used for both sleeping and networking disabled conditions.
This is because internally they share logic, but it's not obvious for
users and it has caused confusion in the past when investigating why
devices didn't become managed. Make it explicit that it can be because
of either reason.

It would be better to create two separate flags, actually, and it
doesn't seem complex, but better not to risk introducing bugs for that
little benefit.

Logs before:
  device (enp4s0): state change: disconnected -> unmanaged (reason 'unmanaged-sleeping' ...

Logs before:
  device (enp4s0): state change: disconnected -> unmanaged (reason 'unmanaged-nm-disabled' ...
2025-09-23 09:17:07 +02:00
Íñigo Huguet
f6d6a7e2eb core, libnm: add the "networking off" reason
When we disable networking with `nmcli networking off` the reason that
is logged is "sleeping". Explain instead that networking is disabled.

Before:
  device (lo): state change: activated -> deactivating (reason 'sleeping' ...

After:
  device (lo): state change: activated -> deactivating (reason 'networking-off' ...
2025-09-23 09:17:07 +02:00
Íñigo Huguet
3355ba9380 core: rename NM_STATE_ASLEEP to NM_STATE_DISABLED
When we do `nmcli networking off` it's shown as state "sleeping". This
is confusing, and the only reason is that we share internally code to
handle both situations in a similar way.

Rename the state to the more generic name "disabled", situation that can
happen either because of sleeping or networking off.

Clients cannot differentiate the exact reason only with the NMState value,
but better that they show "network off" as this is the most common reason
that they will be able to display. If the system is suspending, there will
be only a short period of time that they can show the state, and showing
"network off" is not wrong because that's what NM has done as a response
to suspend.

In the logs, let's make explicit the exact reason why state is changing
to DISABLED: sleeping or networking off.

Logs before:
  manager: disable requested (sleeping: no  enabled: yes)
  manager: NetworkManager state is now ASLEEP

Logs after:
  manager: disable requested (sleeping: no  enabled: yes)
  manager: NetworkManager state is now DISABLED (NEWORKING OFF)

State before:
  $ nmcli general
  STATE  ...
  asleep ...

State after:
  $ nmcli general
  STATE       ...
  network off ...
2025-09-23 09:17:03 +02:00
Íñigo Huguet
c36e0bedeb NEWS: update 2025-09-12 15:11:56 +02:00
Íñigo Huguet
e570498fbf release: bump version to 1.55.4 (development) 2025-09-12 13:38:36 +02:00
Beniamino Galvani
40aa27690c initrd: support setting the DHCP client-id
In some cases it is necessary to set a custom DHCP client-id during
early boot. For example, the firmware of some InfiniBand NIC uses a
48-bit MAC derived from the InfiniBand 20-byte MAC when doing
PXE. NetworkManager doesn't have any knowledge of that 48-bit MAC and
uses the full MAC as client-id, therefore getting a different lease.

Introduce a new option 'rd.net.dhcp.client-id' to specify a custom
client-id.

Resolves: https://issues.redhat.com/browse/RHEL-108454

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2277
2025-09-11 17:33:46 +02:00
Íñigo Huguet
f472111e58 merge: branch 'ih/dbus-global-dns'
core: dns: fix the behavior of [global-dns]

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2261
2025-09-11 10:26:06 +00:00
Íñigo Huguet
4a46f454da core: keep empty groups from keyfile configs
When reading NetworkManager.conf and NetworkManager-intern.conf we might
need to know if a group is defined or not, even if it's empty. This is
the case, for example, for [global-dns]. If [global-dns] is defined in
NM.conf overwrites the config from NM-intern, and if it's defined in any
of them they overwrite the configs from connections.

Before this patch, defining it as an empty group was ignored:
```
[global-dns]
```

Instead, it was necessary to add at least one key-value to the group.
Otherwise the group was silently ignored.
```
[global-dns]
searches=
```

Keep empty groups so we can take better decissions about overwritting
configs from other sources.
2025-09-11 10:25:36 +00:00
Íñigo Huguet
7fb4724efa core: dns: show in D-Bus if [global-dns] is defined but empty
Clients like nmstate needs to know if the [global-dns] section is
defined or not, so they know if DNS configs from connections are
relevant or not. Expose it in D-Bus by always exposing "searches"
and "options" if it's defined, maybe as empty lists.
2025-09-11 10:25:36 +00:00
Íñigo Huguet
1cba0a3cca dns: make [global-dns] to overwrite configs from connections
According to the documentation, settings from [global-dns] (searches and
options) are always merged with those from connections. However this was
not happening if no [global-dns-domain-*] exists, in which case
connections were ignored. This happened because in the past both global
sections must de defined or undefined. When this was changed to allow
defining only [global-dns], allowing it in the function that generates
the resolv.conf file was forgotten. Fix that now.

Anyway, merging these configs doesn't make much sense. The searches and
options defined in connections probably make sense only for the nameservers
defined in that same connection.

Because of this, make the following change: if global nameservers are
defined, use searches and options from [global-dns] only, because those
defined in connections may not make sense for the global nameservers. If
[global-dns] is missing, assume an empty [global-dns] section.

Also, if no global nameservers are defined, but [global-dns] is, make
that it overwrites the searches and options defined in connections. This
is not ideal, but none of the alternatives is better and at least this
is easy to remember.

So, the resulting rules from above are:
- If [global-dns] is defined, it always overwrite searches and options
  from connections.
- If [global-dns-domain-*] is defined, it always overwrite nameservers
  from connections. It overwrites searches and options too.

Fixes: 1f0d1d78d2 ('dns-manager: always apply options from [global-dns]')
Fixes: f57a848da5 ('man: update documentation about global DNS configuration')
2025-09-11 10:25:36 +00:00
Íñigo Huguet
294131a2a4 core: dbus: accept global DNS configuration without a default domain
Since 1.44 we accept a global-dns section without any global-dns-domain
section, so users can define searches and options without defining any
global DNS servers.

When set from the D-Bus API it was still rejected. Fix it.

Fixes: 1f0d1d78d2 ('dns-manager: always apply options from [global-dns]')
2025-09-11 10:25:36 +00:00
Íñigo Huguet
05efc6e253 merge: branch 'issue1476'
Fix reapply error with lacp_active

Closes #1476

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2275
2025-09-11 09:55:45 +00:00
Pradyumn Rahar
9c48bae3b2 bond: remove lacp_active option from reapply subset
NM_SETTING_BOND_OPTION_LACP_ACTIVE is flagged as BOND_OPTFLAG_IFDOWN in
the kernel and hence should not be in OPTIONS_REAPPLY_SUBSET.

Authored-by: Mohith Kumar Thummaluru <mohith.k.kumar.thummaluru@oracle.com>
Signed-off-by: Mohith Kumar Thummaluru <mohith.k.kumar.thummaluru@oracle.com>
Signed-off-by: Pradyumn Rahar <pradyumn.rahar@oracle.com>
2025-09-11 09:54:52 +00:00
Íñigo Huguet
1789a5b338 merge: branch 'ih/ip-reservation-use-after-free'
core: fix potential use after free

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2280
2025-09-11 09:47:40 +00:00
Íñigo Huguet
0d3fef3bcd core: fix potential use after free
_LOGD uses 'self', so don't unref it until after the _LOGD. Discovered
by Coverity.
2025-09-11 09:47:17 +00:00
Íñigo Huguet
4d17064f2a ci: use Fedora 42 as tier 1 a bit more
Switching to Fedora 43 changes the formatting. As Fedora 43 is not
released yet, it might still update clang-format and make it to change
again, as it happened in the past with other versions of Fedora.

Keep F42 until F43 is more stable.
2025-09-11 10:33:22 +02:00
Beniamino Galvani
86c7f1ed14 libnm-core: honor secrets flags when serializing WireGuard peers to D-Bus
If "flags" indicate that only secrets should be serialized and a peer
doesn't contain any secrets, skip it. Otherwise the function would
return a non-empty result when the connection contains no secret,
which causes issues later in the agent manager.

Fixes: e148ec07d5 ('libnm: add NMWireGuardPeer and libnm support for peers')

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2244
2025-09-09 16:56:26 +02:00
Beniamino Galvani
d8971cceed merge: branch 'bg/ip-reservation'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2276
2025-09-09 08:41:13 +02:00
Beniamino Galvani
d3e4f3344e core: generalize IP reservation functions
Generalize the functions to reserve an IP address from the netns, so
that it becomes easy to define new IP ranges for different purposes.
2025-09-08 21:38:21 +02:00
Beniamino Galvani
1504d12714 core: add test for nm_netns_shared_ip_reserve() 2025-09-08 21:37:41 +02:00
Íñigo Huguet
5677114e7c merge: branch 'ih/update-distros'
ci: update distros

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2271
2025-09-08 13:50:14 +00:00
Íñigo Huguet
13d8cda04e ci: update distros 2025-09-08 12:58:27 +02:00
Íñigo Huguet
6e67c830fb merge: branch 'main'
Update Russian translation

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2274
2025-09-08 10:48:35 +00:00
jtux270
5aafede823 update Russian translation 2025-09-08 10:48:08 +00:00
Íñigo Huguet
57ea2cf612 merge: branch 'bg/test-client-quotation'
test-client: fix quotation in expected message

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2269
2025-09-08 10:47:37 +00:00
Beniamino Galvani
d559f61423 libnm-client: fix memory leak
The test calls g_main_context_ref() on client_context, which must then
be unreferenced.

Fixes: 88724ff169 ('libnm: add nm_client_wait_shutdown() function for cleaning up NMClient')
2025-09-08 10:47:10 +00:00
Beniamino Galvani
5ad712974e test-client: fix quotation in expected message
With the newer glib and libc in F42 and Ubuntu devel, the
"{left,right} double quotation mark" characters are printed in the
output message. The double quotation marks are multi-byte characters
and they can't be matched using a character class []. Update the
regexp accordingly.
2025-09-08 10:47:10 +00:00
Íñigo Huguet
0ac63a4197 merge: branch 'bg/die-autotools'
build: remove autotools leftovers

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2268
2025-09-08 10:46:54 +00:00
Beniamino Galvani
fcf9b60cc2 build: remove autotools leftovers 2025-09-08 10:46:44 +00:00
Íñigo Huguet
7c0510ba0b merge: branch 'patch-1'
Replace sl.po (translated another 400 strings).

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2267
2025-09-08 10:46:04 +00:00
filmsi
26ac482f1c Replace sl.po (translated another 400 strings). 2025-09-08 10:45:56 +00:00
Beniamino Galvani
6c84a19eb2 merge: branch 'use-dynsym-for-exports'
build: use .dynsym for selecting symbols to export

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2262
2025-09-03 12:15:00 +00:00
Mateusz Mikuła
e5884cfb18 build: use .dynsym for selecting symbols to export
Nm uses .symtab by default which is less reliable for this use case.

Previously this would fail if user enabled stripping or used linker
that doesn't add undefined symbols to .symtab, like here:
https://github.com/davidlattimore/wild/issues/819#issuecomment-3215079862
2025-09-03 07:14:53 +00:00
Beniamino Galvani
7242c478a1 manager: unrealize device again after failure
If the device was realized in _internal_activate_device() and the
activation failed to start, unrealize the device again so that it
doesn't stay around.

Fixes-test: @ovs_delete_connecting_interface

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2263
2025-09-02 10:16:58 +02:00
Íñigo Huguet
d39179bee4 merge: branch 'ih/fix-wifi-dispose'
wifi: don't recheck  auto-activate on disposal

Closes #1791

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2259
2025-08-27 06:37:48 +00:00
Íñigo Huguet
3904135150 wifi: don't recheck auto-activate on disposal
During disposal we're calling to remove_all_aps that in turns schedules
an auto-activate recheck. As the device is removed, this triggers an
assertion when trying to do the recheck.

Fix that by not scheduling the recheck.

Example of backtrace that this commits fix:
  0  __libc_do_syscall () at ../sysdeps/unix/sysv/linux/arm/libc-do-syscall.S:47
  1  0xf746e270 in __pthread_kill_implementation (threadid=<optimized out>, signo=6, no_tid=<optimized out>) at pthread_kill.c:43
  2  0xf743fbc6 in __GI_raise (sig=sig@entry=6) at ../sysdeps/posix/raise.c:26
  3  0xf7431614 in __GI_abort () at abort.c:79
  4  0xf775afea in g_assertion_message (domain=domain@entry=0x209a9f "nm", file=file@entry=0x1f7d59 "../NetworkManager-1.43.7/src/core/nm-policy.c", line=line@entry=1665,
     func=func@entry=0x1f94d9 <__func__.6> "nm_policy_device_recheck_auto_activate_schedule",
     message=message@entry=0x1d3e950 "assertion failed: (g_signal_handler_find(device, G_SIGNAL_MATCH_DATA, 0, 0, NULL, NULL, NM_POLICY_GET_PRIVATE(self)) != 0)")
     at ../glib-2.72.3/glib/gtestutils.c:3253
  5  0xf775b05e in g_assertion_message_expr (domain=0x209a9f "nm", file=0x1f7d59 "../NetworkManager-1.43.7/src/core/nm-policy.c", line=1665,
     func=0x1f94d9 <__func__.6> "nm_policy_device_recheck_auto_activate_schedule",
     expr=0x1f8afc "g_signal_handler_find(device, G_SIGNAL_MATCH_DATA, 0, 0, NULL, NULL, NM_POLICY_GET_PRIVATE(self)) != 0") at ../glib-2.72.3/glib/gtestutils.c:3279
  6  0x0005f27a in nm_policy_device_recheck_auto_activate_schedule (self=0x1d3e950, device=0x209a9f) at ../NetworkManager-1.43.7/src/core/nm-policy.c:1679
  7  0x000548ae in nm_manager_device_recheck_auto_activate_schedule (self=<optimized out>, device=<optimized out>) at ../NetworkManager-1.43.7/src/core/nm-manager.c:3113
  8  0x00070622 in nm_device_recheck_auto_activate_schedule (self=<optimized out>) at ../NetworkManager-1.43.7/src/core/devices/nm-device.c:9249
  9  0xf693aa8c in ap_add_remove (self=self@entry=0x1ceb0b0, is_adding=0, ap=<optimized out>, recheck_available_connections=0)
     at ../NetworkManager-1.43.7/src/core/devices/wifi/nm-device-wifi.c:846
  10 0xf693bcda in remove_all_aps (self=self@entry=0x1ceb0b0) at ../NetworkManager-1.43.7/src/core/devices/wifi/nm-device-wifi.c:863
  11 0xf693f83c in dispose (object=0x1ceb0b0) at ../NetworkManager-1.43.7/src/core/devices/wifi/nm-device-wifi.c:3809
  12 0xf7806e72 in g_object_unref (_object=<optimized out>) at ../glib-2.72.3/gobject/gobject.c:3636
  13 g_object_unref (_object=0x1ceb0b0) at ../glib-2.72.3/gobject/gobject.c:3553
  14 0x000f7fa4 in _nm_dbus_object_clear_and_unexport (location=location@entry=0xffa50644) at ../NetworkManager-1.43.7/src/core/nm-dbus-object.c:203
  15 0x000576e4 in remove_device (self=self@entry=0x1c9c900, device=<optimized out>, quitting=quitting@entry=1) at ../NetworkManager-1.43.7/src/core/nm-manager.c:2289
  16 0x0005a864 in nm_manager_stop (self=self@entry=0x1c9c900) at ../NetworkManager-1.43.7/src/core/nm-manager.c:7784
  17 0x00023438 in main (argc=<optimized out>, argv=<optimized out>) at ../NetworkManager-1.43.7/src/core/main.c:530

Fixes: 96f40dcdcd ('wifi/ap: explicitly unexport AP and refactor add/remove AP')
Fixes: https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1791
2025-08-27 06:37:33 +00:00
Beniamino Galvani
0b03614b68 device: ensure that sw devices are unrealized after connection deletion
When a software device becomes deactivated, we check whether it can
be unrealized (= deleted in kernel), by calling function
delete_on_deactivate_check_and_schedule().

The function returns without doing anything if there is a new
activation enqueued on the device (priv->queued_act_request), because
in that case the device will be reused for the next activation.

This commit fixes a problem seen in NMCI test
@ovs_delete_connecting_interface: sometimes the device is not
unrealized after deleting the connection. That happens because if the
queued activation fails, we never try again to unrealize the device.

Fix that by calling delete_on_deactivate_check_and_schedule() when
there is a failure starting the queued activation.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2258
2025-08-26 20:51:32 +02:00
Beniamino Galvani
8b26cb35ee device: explicitly handle unrealized devices in is_available()
Unrealized software devices are always available for activation,
hardware devices never.

In nm_manager_get_best_device_for_activation() we call
nm_device_is_available() on candidate devices. Without this fix, any
unrealized software device would be not considered ready for
activation, which is wrong.

A software device can override the default implementation of
is_available(). For example NMDeviceOvsInterface does that and only
checks the OVSDB is ready.

Fixes: ba86c208e0 ('Revert "core: prevent the activation of unavailable OVS interfaces only"')

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2253
2025-08-26 20:39:18 +02:00
Íñigo Huguet
96be0cf049 merge: branch 'ih/domain-search-sep'
dns: ensure that no wrong separators are used for DNS search domains

Closes #1740

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2196
2025-08-26 09:00:18 +00:00
Íñigo Huguet
b0b72dd2f1 dns: don't break existing configs with wrong separators in dns-search
The previous commit will raise an error if wrong list
separators are being used in an nmconnection file for dns-search to
avoid that they are all considered a single string.

However, existing users might have wrong values of dns-search that
currently are not preventing the connection of being activated. To avoid
that a NetworkManager update breaks existing configs, potentially even
cutting connectivity with remote machines, accept wrong separators in
keyfiles but emitting a warning.

Fixes: 919156552ede ('dns: ensure that no wrong separators are used for DNS search domains')
2025-08-26 08:59:37 +00:00
Íñigo Huguet
3266203bf1 dns: ensure that no wrong separators are used for DNS search domains
If wrong separators are used in they keyfile, like commas, the whole
line is considered as a single domain string, like "a.org,b.org".
Obviously this is invalid.

Ideally we should validate that the string is a valid domain, but this
gets quite complex if we want to support unicode characters, which are
valid for many top domains. For now, validate at least that no wrong
separators have been used.

Fixes https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1740
2025-08-26 08:59:37 +00:00
Beniamino Galvani
21bbe24fee merge: branch 'nbft-parser-2'
nm-initrd-generator: Add NBFT tests

Closes #1756

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2256
2025-08-26 08:01:09 +00:00
Tomas Bzatek
dce149352d nm-initrd-generator: add NBFT parser tests
This adds simple unit tests for most common NBFT deployments.
Sample data were mostly taken from the upstream libnvme repository.
2025-08-26 07:45:53 +00:00
Tomas Bzatek
592a4f077b nm-initrd-generator: fix a conn_name leak 2025-08-26 07:45:53 +00:00
Tomas Bzatek
6304d51440 nm-initrd-generator: rework NBFT HFI DHCP detection
There are several flags specified in the NVMe Boot Specification
that may indicate DHCP was used to acquire information during the
pre-OS phase. This commit considers these additional sources,
based on actual NBFT table contents from different systems.

Although we've seen slight variations in firmware implementations
regarding the HFI IP Origin values when DHCP was configured, the
new set of rules still align with expectations.
2025-08-26 07:45:53 +00:00
Beniamino Galvani
0c1fba5c95 wireguard: don't add peer routes if they duplicate prefix routes
With this configuration:

  [Interface]
  ...
  Address = 172.16.110.116/28,172.16.111.21/28

  [Peer]
  ...
  AllowedIPs = 172.16.110.112/28

  [Peer]
  ...
  AllowedIPs = 172.16.111.16/28

NetworkManager currently creates the following routes

  (1) 172.16.110.112/28 dev wg0 proto static scope link metric 50 <-- peer route
  (2) 172.16.110.112/28 dev wg0 proto kernel scope link src 172.16.110.116 metric 50 <-- prefix route
  (3) 172.16.111.16/28 dev wg0 proto static scope link metric 50 <-- peer route
  (4) 172.16.111.16/28 dev wg0 proto kernel scope link src 172.16.111.21 metric 50 <-- prefix route

If we try to reach a host in the second peer subnet, route (4)
matches. Route (4) doesn't specify a source IP and so the kernel will
use the first IP set on the interface (172.16.110.116), which is the
wrong one.

  # ip route get 172.16.111.17
  172.16.111.17 dev wg0 src 172.16.110.116 uid 0

To fix this problem, if the AllowedIP subnet is already reachable on
the interface via the prefix route of a static IP address, we should
skip adding the peer route.

wg-quick does something similar here:

  https://git.zx2c4.com/wireguard-tools/tree/src/wg-quick/linux.bash?h=v1.0.20250521#n177

The condition in wg-quick is a bit different because it checks that no
duplicate route exists on the interface. We can't do exactly the same
because in NMDeviceWireGuard we don't have visibility on all the
platform routes.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1790
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2254
2025-08-25 16:49:16 +02:00
Íñigo Huguet
933ddab90f merge: branch 'ih/close-parenthesis'
libnmc: fix typo of missing close parenthesis

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2249
2025-08-25 13:35:33 +00:00
Íñigo Huguet
f5c5bcc99d libnmc: fix typo of missing close parenthesis 2025-08-25 13:35:33 +00:00
Íñigo Huguet
7b4d0ef9f2 merge: branch 'ih/release-vpn-gnome'
doc: update the process to release a VPN plugin

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2252
2025-08-25 13:34:54 +00:00
Íñigo Huguet
79ffe55686 doc: update the process to release a VPN plugin 2025-08-25 13:34:54 +00:00
Beniamino Galvani
94d7dd9b11 rpm: change system_ca_path
/etc/pki/tls/cert.pem was a symlink to
/etc/pki/ca-trust/extracted/pem/tls-ca-bundle.pem since Fedora 19 and
it is being removed in Fedora 43.

See https://fedoraproject.org/wiki/Changes/droppingOfCertPemFile

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2257
https://bugzilla.redhat.com/show_bug.cgi?id=2380436
2025-08-25 15:19:47 +02:00
Jan Vaclav
29390b053d merge: branch 'jv/reapply-vfs'
device: add support for reapplying the `sriov.vfs` property

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2255
2025-08-21 08:32:57 +00:00
Jan Vaclav
bbe0e9d8c2 NEWS: update 2025-08-20 09:58:52 +02:00
Jan Vaclav
4ba3ffee67 device: add support for reapplying the sriov.vfs property
Adds support for reapplying the `sriov.vfs` property. Note this
does not include `num_vfs`, as the configuration needs to be reset
and reconfigured from scratch in that case.

Previously, if an existing VF is modified (e.g. if we change the `trust`
flag), we reset all VF configurations, and started from scratch. But in
some cases, this is unnecessarily disruptive.

Resolves: https://issues.redhat.com/browse/RHEL-95844
2025-08-20 09:58:52 +02:00
Jan Vaclav
588a69cd1b device: extract sriov platform vf generation to separate function 2025-08-20 09:58:52 +02:00
Beniamino Galvani
11da867072 merge: branch 'bg/dns-server-valid'
libnm: add nm_dns_server_validate()

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2251
2025-08-18 12:04:03 +00:00
Beniamino Galvani
9f76e11a75 libnm: add nm_dns_server_validate()
Add a new public symbol nm_dns_server_validate() that clients can use
to validate a single DNS server before adding it to the connection.
2025-08-14 11:22:41 +02:00
Beniamino Galvani
d62c25ef2f dns: return error from nm_dns_uri_parse()
Return a GError from nm_dns_uri_parse() to indicate why the URI could
not be parsed. This is useful for logging and user reporting.
2025-08-14 09:40:26 +02:00
Beniamino Galvani
e1a7d5ac06 device: don't generate an assumed connection for ports on wake
After resuming from suspend, devices with wake-on-lan enabled are
temporarily set as unmanaged, and then managed again. At the beginning
of this process, an active device goes from state ACTIVATED to
UNMANAGED and is deconfigured via
"nm_device_cleanup(cleanup_type=CLEANUP_TYPE_DECONFIGURE)".

If the device is attached to a controller, the cleanup doesn't detach
it. Later when the device is managed again, NetworkManager tries to
create an assumed connection. Normally, this would fail because we
detect that the device is not configured. However, if there is a
controller-port relationship, the assumed connection generation
succeeds and the persistent connection doesn't go up.

As this is wrong, prevent the generation of the assumed connection by
detaching the port during a cleanup.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1766
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2242
2025-08-13 13:43:24 +02:00
Íñigo Huguet
600c5452bf po: fix command that should not be translated
The message contains a literal command that should not be translated,
but it was. Fix it.

Fixes https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1799
2025-08-12 10:52:29 +02:00
Filip Pokryvka
7562b0e5f9 release: bump version to 1.55.3 (development) 2025-08-01 16:00:58 +02:00
Beniamino Galvani
93ed7a2c38 merge: branch 'bg/misc-fixes2'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2245
2025-07-23 11:13:14 +02:00
Beniamino Galvani
ec996135a9 device: fix comment in attach_port() 2025-07-23 11:12:00 +02:00
Beniamino Galvani
012f1cbfac device: fix signal emission on port detach/release
The "notify::controller" signal must be emitted on the port, not on
the controller.

Fixes: 1f05526ed7 ('core: drop NMDevice master and introduce controller')
2025-07-23 11:11:59 +02:00
Beniamino Galvani
394f6281ea platform: fix GError free function
Fixes: dd7810c473 ('platform: destroy VFs before changing the eswitch mode')
2025-07-23 11:11:59 +02:00
Beniamino Galvani
4938507de8 dhcp6: fix accessor macro for t2
sd_dhcp6_lease_get_t2() was returning t1, and so sometimes the client
was going directly to the rebind state skipping the lease renewal.

See the systemd PR: https://github.com/systemd/systemd/pull/38275

Fixes: a14a033efb ('systemd: update code from upstream (2024-02-12)')
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2246
2025-07-23 11:00:13 +02:00
Beniamino Galvani
3c8c0364a4 merge: branch 'bg/acd-timeout'
l3cfg: don't reset the ACD probe timestamp during timer events

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2241
2025-07-22 08:44:36 +00:00
Beniamino Galvani
eb0a41ce1f l3cfg: simplify the ACD timeouts
ACD_WAIT_PROBING_EXTRA_TIME_MSEC and ACD_WAIT_PROBING_EXTRA_TIME2_MSEC
now are always used together. Consolidate them into a single constant.
2025-07-22 10:24:27 +02:00
Beniamino Galvani
127f73a5c2 l3cfg: fix the interval of the ACD restart timer
After ACD_WAIT_PROBING_EXTRA_TIME_MSEC has elapsed,
_l3_acd_data_timeout_schedule_probing_restart() keeps rescheduling the
timer with a zero interval, resulting in 100% CPU usage. This
continues until the probe is destroyed after
ACD_WAIT_PROBING_EXTRA_TIME2_MSEC.

When computing the interval, we need to use
(ACD_WAIT_PROBING_EXTRA_TIME_MSEC + ACD_WAIT_PROBING_EXTRA_TIME2_MSEC)
as the expiry time.
2025-07-22 10:24:26 +02:00
Beniamino Galvani
407d753a5a l3cfg: don't reset the ACD probe timestamp during timer events
acd_data->probing_timestamp_msec indicates when the probing
started. It is used in different places to calculate the timeout for
certain operations. In particular, it is used to detect that the probe
creation took too long when handling the ACD_STATE_CHANGE_MODE_TIMEOUT
event.

If we reset this timestamp at every timer event, we'll never hit the
probe creation timeout. Therefore, the l3cfg will keep trying forever
to create the probe.
See: https://lists.freedesktop.org/archives/networkmanager/2025-July/000418.html

Fix this by not updating the timestamp during a timeout event.

Fixes: a09f9cc616 ('l3cfg: ensure the probing timeout is initialized on probe start')
2025-07-22 10:24:26 +02:00
Beniamino Galvani
b019883a9a core: accept hostnames longer than 64 characters from DNS lookup
When resolving the system hostname from DNS lookup, we use
nm_utils_validate_hostname() which checks that the result is a valid
hostname. A valid hostname is at most 64 characters on Linux. Anything
longer is discarded.

However, the reverse DNS lookup doesn't return a hostname, it returns
a DNS name. The DNS name can have multiple labels, each limited to 63
characters. The maximum length of the DNS name is 253 characters.

If the result is longer than 64 characters because it has multiple
labels, we should still accept it, provided that it is a valid DNS
name. Then when setting the hostname in the system, only the first
label will be kept.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2243

Resolves: https://issues.redhat.com/browse/RHEL-104357
2025-07-22 10:20:36 +02:00
Beniamino Galvani
b4a22ad2a9 platform: fix compilation without LTO
Fix the following error seen when running the build_clean.sh script
with LTO disabled:

  In file included from ../src/libnm-glib-aux/nm-default-glib.h:66,
                   from ../src/libnm-glib-aux/nm-default-glib-i18n-prog.h:13,
                   from ../src/core/nm-default-daemon.h:11,
                   from ../src/core/platform/tests/test-link.c:6:
  In function ‘_nm_auto_freev’,
      inlined from ‘test_link_get_bridge_fdb’ at ../src/core/platform/tests/test-link.c:2732:33:
  ../src/libnm-glib-aux/nm-macros-internal.h:166:8: error: ‘addrs’ may be used uninitialized [-Werror=maybe-uninitialized]
    166 |     if (*p) {
        |        ^
  ../src/core/platform/tests/test-link.c: In function ‘test_link_get_bridge_fdb’:
  ../src/core/platform/tests/test-link.c:2732:33: note: ‘addrs’ was declared here
   2732 |     nm_auto_freev NMEtherAddr **addrs;
        |                                 ^~~~~
  cc1: all warnings being treated as errors

Fixes: 16ef33d380 ('bond-slb: fix memory leak')
2025-07-17 10:30:18 +02:00
Beniamino Galvani
bd41951f1d merge: branch 'bg/bridge-port-fix-reapply'
bridge: fix reapplying port VLANs

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2240
2025-07-14 13:04:00 +00:00
Beniamino Galvani
261fa8db33 device: accept changes to the bond-port.vlans during reapply
Commit c5d1e35f99 ('device: support reapplying bridge-port VLANs')
didn't update can_reapply_change() to accept the "bridge-port.vlans"
property during a reapply. So, it was only possible to change the
bridge port VLANs by updating the "bridge.vlan-default-pvid" property
and doing a reapply. Fix that.

Fixes: c5d1e35f99 ('device: support reapplying bridge-port VLANs')
2025-07-14 15:03:06 +02:00
Beniamino Galvani
bf79fbd678 bridge: fix reapplying port VLANs
If the bridge default-pvid is zero, it means that the default PVID is
disabled. That is, the bridge PVID is not propagated to ports.

Currently NM tries to merge the existing bridge VLANs on the port with
the default PVID from the bridge, even when the PVID is zero. This
causes an error when setting the new VLAN list in the kernel, because
it rejects VLAN zero.

Skip the merge of the default PVID when zero.

Fixes: c5d1e35f99 ('device: support reapplying bridge-port VLANs')
2025-07-14 15:03:05 +02:00
Beniamino Galvani
f655cd1cba man: fix nmcli connection types list
Update the nmcli man page to accurately reflect the connection types
supported by NetworkManager:

- Remove ovs-dpdk and ovs-patch (not supported by nmcli)
- Add hsr, ipvlan, and loopback (missing from the documentation)

This ensures the man page matches the actual connection types returned by
'nmcli --complete-args connection add type'.

https://issues.redhat.com/browse/RHEL-100893
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2235
2025-07-14 14:59:00 +02:00
Filip Pokryvka
f584524197 release: bump version to 1.55.2 (development) 2025-07-11 08:33:22 +02:00
Beniamino Galvani
74cf2a2bd8 l3cfg: fix logging message
Fix spacing in:

 acd[192.168.122.42, probing]: probing currently  stillnot possible
                                                 ^^^^^^^^^

Fixes: b8f9d7b5dd
2025-07-10 10:04:36 +02:00
Beniamino Galvani
c983e3bbf5 merge: branch 'bg/misc-fixes'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2239
2025-07-10 09:14:00 +02:00
Beniamino Galvani
eb7917a387 ndisc: fix logic to limit the number of addresses
Fixes: c2c8c67d8c ('ndisc: rate limit number of accepted RA data to track')
2025-07-10 09:12:06 +02:00
Beniamino Galvani
b45d5f41dd platform: fix harmless typo
The function should modify the "ip6_address" member of the union. In
practice, it doesn't matter because the ifindex is the first member of
both "ip4_address" and "ip6_address".
2025-07-10 09:12:05 +02:00
Beniamino Galvani
fdb8f07c44 libnm-core: validate the ipvlan mode
The setting must reject unknown ipvlan modes.

Fixes: d238ff487b ('ipvlan: add support to IPVLAN interface')
2025-07-10 09:12:05 +02:00
Beniamino Galvani
104cafdd44 libnm-core: fix documentation for NMSettingMatch functions
Fixes: 3a8e46f2a5 ('settings: add match for proc cmdline')
2025-07-10 09:12:04 +02:00
Beniamino Galvani
f4f1ecc7ea libnm-core: fix p-key validation for Infiniband connections
verify() is setting an error without returning FALSE to make the
validation fail. When the parent is set, the device is a Infiniband
partition and it must have a p-key != -1.

Fixes: d595f7843e ('libnm: add libnm/libnm-core (part 1)')
2025-07-10 09:12:04 +02:00
Beniamino Galvani
fa80896ee7 core: fix Wi-Fi data rate tables
Fixes: f2b0092b5b ('wifi: parse BSS IEs for 80211n and 80211ac data rates')
2025-07-10 09:12:03 +02:00
Beniamino Galvani
b58a37acfe core: fix nm_utils_get_nm_gid()
Fixes: 31dbcb81fe ('core: make nm_utils_get_nm_[ug]id() thread safe')
2025-07-10 09:12:03 +02:00
Beniamino Galvani
16ef33d380 bond-slb: fix memory leak
If sendto() fails, the function returns and the remaining entries are
not deallocated. Use nm_auto_freev instead to free the array and the
pointer it contains.

Add a test to check that nm_auto_freev does the right thing on the
value returned by nm_linux_platform_get_bridge_fdb().

Fixes: 3f2f922dd9 ('bonding: send ARP announcement on bonding-slb link/carrier down')
2025-07-10 09:12:02 +02:00
Beniamino Galvani
7d23ed9f73 platform: rename nm_linux_platform_get_link_fdb_table()
Rename nm_linux_platform_get_link_fdb_table() to
nm_linux_platform_get_bridge_fdb(). The new name better indicates that
the function returns the bridge FDB entries.
2025-07-10 09:12:02 +02:00
Beniamino Galvani
d017dc67b4 dhcp: fix typo in tcp_keepalive_interval option name
Fixes: eed205bff3 ('dhcp/internal: move dhcp options management to shared dhcp codebase')
2025-07-10 09:12:02 +02:00
Beniamino Galvani
a9d7abbc50 dhcp: fix parsing of the search list option
The DHCP search list option (119) can use the "message compression"
algorithm specified in RFC 1035 section 4.1.4 to reduce the size of
the message in presence of subdomains that appear multiple times.

When using the compression a label starts with:

    +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+
    | 1  1|                OFFSET                   |
    +--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+--+

where the offset points to a previous domain.

Previously, the parsing code was taking the lower 6 bits of the first
byte, shifting them left 16 bits, and adding the next byte. Instead,
the shift should be of 8 bits.

The effect of this bug was that when the offset was greater than 255,
it was incorrectly parsed as a number larger than the message size,
and the parsing failed.

Note that while a single DHCP option can be at most 255 bytes, a DHCP
message can contain multiple instances of the same option. The
receiver must concatenate all the occurrences according to RFC 3396
and parse the resulting buffer.

Fixes: 6adade6f21 ('dhcp: add nettools dhcp4 client')
2025-07-10 09:12:02 +02:00
Beniamino Galvani
43f738473c core: remove duplicate include 2025-07-10 09:12:01 +02:00
Beniamino Galvani
50a400e16f supplicant: fix wrong check on "EAP" signal arguments
The check is inverted.

Fixes: b83f07916a ('supplicant: large rework of wpa_supplicant handling')
2025-07-10 09:12:01 +02:00
Beniamino Galvani
ce17284c3f lldp: fix memchr() argument order
The validation of embedded NUL character was skipped due to the wrong
order of arguments to memchr(). Fix it.

Fixes: 4043f82790 ('lldp: cleanup converting binary LLDP fields to string')
2025-07-10 09:12:01 +02:00
Beniamino Galvani
20a1d7e816 vrf: fix wrong logging domain
Fixes: 667568d1b2 ('core,libnm: add VRF support')
2025-07-10 09:12:01 +02:00
Beniamino Galvani
1229fe5abd bond: fix attribute assignment macro
Currently the bug is hidden because the macro is only called with
NM_SETTING_BOND_OPTION_ARP_IP_TARGET.

Fixes: 45c95e9314 ('device/bond: rework setting of arp_ip_target bond options')
2025-07-10 09:12:00 +02:00
Beniamino Galvani
404a3ec853 core: fix properties update for HSR devices
Fixes: 5426bdf4a1 ('HSR: add support to HSR/PRP interface')
2025-07-10 09:12:00 +02:00
Beniamino Galvani
62558d50be core: fix constant name for IPv4 method
Fix the name for consistency, even if this is harmless because the
IPv4 and IPv6 values are the same.
2025-07-10 09:12:00 +02:00
Beniamino Galvani
55765d2914 ovs: fix logging message
Fixes: a259303e1d ('ovs: add support for "other_config" settings')
2025-07-10 09:12:00 +02:00
Beniamino Galvani
253800238e libnm-core,core: accept uid/gid up to (2^32 - 2) for tun devices
Linux UIDs/GIDs are 32-bit unsigned integer, with 4294967295 reserved
as undefined.

Before:
  # useradd -u 4294967294 -M testuser
  useradd warning: testuser's uid -2 outside of the UID_MIN 1000 and UID_MAX 60000 range.
  # nmcli connection add type tun ifname tun1 owner 4294967294 ipv4.method disabled ipv6.method disabled
  Error: Failed to add 'tun-tun1' connection: tun.owner: '4294967294': invalid user ID

After:
  # useradd -u 4294967294 -M testuser
  useradd warning: testuser's uid -2 outside of the UID_MIN 1000 and UID_MAX 60000 range.
  # nmcli connection add type tun ifname tun1 owner 4294967294 ipv4.method disabled ipv6.method disabled
  Connection 'tun-tun1' (5da24d19-1723-45d5-8e04-c976f7a251d0) successfully added.
  # ip -d link show tun1
  2421: tun1: <NO-CARRIER,POINTOPOINT,MULTICAST,NOARP,UP> mtu 1500 qdisc fq_codel state DOWN mode DEFAULT group default qlen 500
      link/none  promiscuity 0 allmulti 0 minmtu 68 maxmtu 65535
      tun type tun pi off vnet_hdr off persist on user testuser ...
                                                 ^^^^^^^^^^^^^
Fixes: 1f30147a7a ('libnm-core: add NMSettingTun')
2025-07-10 09:12:00 +02:00
Beniamino Galvani
45ab9d96f1 platform: use g_strdup() instead of strdup() in ethtool code
The string is freed with g_free(), it needs to be allocated with
g_strdup(). In practice, the GLib allocator uses malloc() nowadays,
but it is better to be consistent.
2025-07-10 09:12:00 +02:00
Beniamino Galvani
326fb8f9cf initrd: make parsing of VLANs more robust
We are missing some validations when parsing VLANs: a unexpected
argument can cause a crash, an assertion, or the connection being
dropped without any warning. Make it more robust.
2025-07-10 09:12:00 +02:00
Beniamino Galvani
eff8471de4 nmcli: fix format
Fixes: a9b66e254c ('nmcli: fix compile error')
2025-07-09 15:08:15 +02:00
Beniamino Galvani
959ddec2a4 contrib/nm-vpn-plugin-utils: add nm_vpn_plugin_utils_get_cert_path()
Add a function to generate the path for imported certificates.

See https://gitlab.gnome.org/GNOME/NetworkManager-openvpn/-/merge_requests/95
2025-07-09 15:06:51 +02:00
Beniamino Galvani
a9b66e254c nmcli: fix compile error
Running the build script with LTO disabled
("contrib/fedora/rpm/build_clean.sh -W lto") gives the following error:

  In file included from ../src/libnm-std-aux/nm-default-std.h:102,
                   from ../src/libnm-glib-aux/nm-default-glib.h:11,
                   from ../src/libnm-glib-aux/nm-default-glib-i18n-lib.h:13,
                   from ../src/libnm-client-aux-extern/nm-default-client.h:11,
                   from ../src/nmcli/connections.c:6:
  In function ‘_nm_auto_unref_ptrarray’,
      inlined from ‘do_connection_add’ at ../src/nmcli/connections.c:6069:35:
  ../src/libnm-std-aux/nm-std-aux.h:1106:12: error: ‘props’ may be used uninitialized [-Werror=maybe-uninitialized]
   1106 |         if (*v)                               \
        |            ^
  ../src/libnm-glib-aux/nm-macros-internal.h:91:1: note: in expansion of macro ‘NM_AUTO_DEFINE_FCN0’
     91 | NM_AUTO_DEFINE_FCN0(GPtrArray *, _nm_auto_unref_ptrarray, g_ptr_array_unref);
        | ^~~~~~~~~~~~~~~~~~~
  ../src/nmcli/connections.c: In function ‘do_connection_add’:
  ../src/nmcli/connections.c:6069:35: note: ‘props’ was declared here
   6069 |     gs_unref_ptrarray GPtrArray  *props;
        |                                   ^~~~~
  cc1: all warnings being treated as errors

Fix it.

Fixes: bb850fda0e ('nmcli: connection: process port-type, type and controller first')
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2236
2025-07-08 11:21:02 +02:00
Lubomir Rintel
9bbb113987 device: don't disable IPv6 in stage3 on reapply
Currently, when a call to Reapply() results in stage3 being re-run, IPv6
ends up messed up. Like this:

  $ nmcli device modify eth0 ipv4.address ''
  $ nmcli device modify eth0 ipv4.address 172.31.13.37/24
  $

  NetworkManager[666]: <debug> [1751286095.2070] device[c95ca04a69467d81] (eth0): ip4: reapply...
  ...
  NetworkManager[666]: <debug> [1751286095.2104] device[c95ca04a69467d81] (eth0): ip6: addrgenmode6: set none (already set)
  NetworkManager[666]: <debug> [1751286095.2105] device[c95ca04a69467d81] (eth0): ip6: addrgenmode6: toggle disable_ipv6 sysctl after disabling addr-gen-mode
  NetworkManager[666]: <debug> [1751286095.2105] platform-linux: sysctl: setting '/proc/sys/net/ipv6/conf/eth0/disable_ipv6' to '1' (current value is '0')
  NetworkManager[666]: <debug> [1751286095.2106] platform-linux: sysctl: setting '/proc/sys/net/ipv6/conf/eth0/disable_ipv6' to '0' (current value is '1')
  NetworkManager[666]: <debug> [1751286095.2106] platform-linux: sysctl: setting '/proc/sys/net/ipv6/conf/eth0/accept_ra' to '0' (current value is identical)
  NetworkManager[666]: <debug> [1751286095.2106] platform-linux: sysctl: setting '/proc/sys/net/ipv6/conf/eth0/disable_ipv6' to '0' (current value is identical)

Not only is this unnecessary because addr-gen-mode already has the
desired value (as is logged), but also wipes off all IPv6 configuration.
This is fine on initial configuration, but not on Reapply().

Let's look at the device state first: if we've progressed past ip-config
state, then we can't possibly ever touch the offending sysctls. It's
okay -- we don't need to: addr-gen-mode is going to be set right if we
went through ip-config before.

Resolves: https://issues.redhat.com/browse/NMT-1681

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2232
2025-07-07 15:38:51 +02:00
Lubomir Rintel
2de6391f4b device: drop a redundant assert
This is essentially:

  a = b
  assert(a == b)

Not useful.

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2233
2025-07-07 15:16:34 +02:00
Íñigo Huguet
a39fa7ee6c merge: branch 'ih/spec_git_tag'
spec: add git_tag_version

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2238
2025-07-07 13:09:50 +00:00
Íñigo Huguet
3cba4f2627 spec: add git_tag_version
The URL to the tarball needs the git tag, that might be 1.54-rc1 instead
of 1.53.90. Allow to define it as a separate variable in the spec file.
It can be set as `git_tag_version %{real_version}` when they are
identical.

It is not really needed here in the upstream spec file, as the "Source"
line is commented out, but add it as a reference for donwstream spec
files.
2025-07-07 09:27:05 +02:00
Íñigo Huguet
cc5306e1d0 NEWS: update 2025-07-07 09:14:34 +02:00
Beniamino Galvani
37c0e0860e NEWS: update 2025-07-01 14:26:44 +02:00
Beniamino Galvani
165e5df6e0 nmcli: accept certain IP settings on port connections
Commit bb850fda0e ('nmcli: connection: process port-type, type
and controller first') started correctly rejecting IP configuration
on port connections.

However, previously nmcli would accept IP parameters for ports when
using a specific parameters order. To avoid breaking user scripts that
may have relied on this behavior, introduce a backward compatibility
quirk.

Specifically, nmcli accepts a disabled/ignore IP method on a port
connection. For any other IP setting on a port connection, a specific
error message is now shown.

https://issues.redhat.com/browse/RHEL-90756
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2227
2025-07-01 14:21:23 +02:00
Beniamino Galvani
25a5fd7503 merge: branch 'bg/sriov-preserve-capability'
manager: add a capability for "sriov.preserve-on-down"

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2234
2025-07-01 07:37:17 +00:00
Beniamino Galvani
8e40f7e289 manager: add a capability for "sriov.preserve-on-down"
Add a new capability to indicate that NetworkManager supports the
"sriov.preserve-on-down" connection property. With this, clients can
set the property only when supported, without the risk of creating an
invalid connection.
2025-06-30 22:38:18 +02:00
Beniamino Galvani
ea6af6d806 libnm-core: change version of ip4-forwarding capability
NM_VERSION_INFO_CAPABILITY_IP4_FORWARDING was backported to branch
nm-1-54 before the 1.54 release. Update the symbol version.
2025-06-30 22:33:29 +02:00
Beniamino Galvani
5ab04c8f56 libnm: change "sriov.preserve-on-down" symbols version to 1.54
The "sriov.preserve-on-down" libnm symbols were backported to the 1.54
branch before the final release. Change their version on main to be
"1.54".

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2229
2025-06-27 14:11:47 +02:00
Beniamino Galvani
7bb898fa12 libnm: fix g-ir-scanner build warning
Fix the following build warning emitted by g-ir-scanner:

  ../src/libnm-core-public/nm-dbus-interface.h:103: Warning: NM: "@NM_VERSION_INFO_CAPABILITY_IP4_FORWARDING" parameter unexpected at this location:
   * @NM_VERSION_INFO_CAPABILITY_IP4_FORWARDING: Indicates that NetworkManager supports
      ^

Fixes: 6a13e8d369 ('core: expose the version info capability of IPv4 forwarding support')
2025-06-26 13:22:33 +02:00
Beniamino Galvani
9b4569bd94 merge: branch 'bg/route-via'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2222
2025-06-26 11:55:45 +02:00
Beniamino Galvani
24ab3308fe platform: add test for route via attribute 2025-06-26 11:37:17 +02:00
Beniamino Galvani
00257a9cf7 platform: parse the RT_VIA route attribute
Parse the "via" attribute in netlink routes received by kernel, so
that we can update the internal cache.
2025-06-26 11:37:16 +02:00
Beniamino Galvani
9c70a43775 platform: use the "via" attribute in route NMPObject methods
Update the cmd_obj_hash_update(), cmd_obj_cmp(), cmd_obj_to_string()
NMPObject methods for IPv4 routes to consider the "via" attribute.
2025-06-26 11:37:16 +02:00
Mary Strodl
2ffaebd4ae platform: support the RT_VIA attribute for IPv4 routes
The RT_VIA attribute is used to specify a gateway of a different
address family. It is currently used only for IPv4 routes.

[bgalvani@redhat.com: amended the commit message]
2025-06-26 11:37:15 +02:00
Wen Liang
84299ed17c merge: branch 'forwarding_version_info'
core: expose the version info capability sync of forwarding support

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2226
2025-06-24 13:12:28 +00:00
Wen Liang
6a13e8d369 core: expose the version info capability of IPv4 forwarding support
This commit adds NM_VERSION_INFO_CAPABILITY_IPV4_FORWARDING to the
VersionInfo D-Bus property, allowing clients such as nmstate to check
the NetworkManager's support of configuring per-device IPv4 sysctl
forwarding setting directly via the capabilities bitmask instead of
relying on the NetworkManager version comparisons.
2025-06-23 13:30:14 -04:00
Filip Pokryvka
e26e965134 release: bump version to 1.55.1 (development) 2025-06-20 09:19:23 +02:00
Beniamino Galvani
a78f8bbe1b merge: branch 'bg/systemd-fix'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2223
2025-06-19 15:09:07 +02:00
Beniamino Galvani
9f510533f1 systemd: ignore device_is_devtype()
The function uses symbol sd_device_get_devtype() which is currently
commented out. Therefore, NM dynamically links to the symbol from the
libsystemd shared object, which breaks on machines without systemd.

Before:
$ nm -u build/src/core/NetworkManager | grep sd_device
                 U sd_device_get_sysattr_value@LIBSYSTEMD_240
$

After:
$ nm -u build/src/core/NetworkManager | grep sd_device
$

Fixes: 6a4e6fab40 ('merge: branch 'systemd' into jv/systemd-merge')
2025-06-19 15:08:02 +02:00
Beniamino Galvani
77c99b61c0 Revert "sd-device: use sd_device_get_sysattr_value() to read special symlinks"
Revert systemd commit 6ebbdcc0ddba ("sd-device: use
sd_device_get_sysattr_value() to read special symlinks"). In the NM
codebase sd_device_get_sysattr_value() is currently commented out
because it depends on file chase.c which is not imported. Importing
that file would require another long chain of imports. Therefore,
revert the commit.

This reverts commit 6ebbdcc0ddbacce732001823cf2be2a1d4381c60.

Fixes: 6a4e6fab40 ('merge: branch 'systemd' into jv/systemd-merge')
2025-06-19 15:08:02 +02:00
Beniamino Galvani
fcc5352715 Revert "sd-device: use sd_device_get_sysattr_value() to read uevent file"
Revert systemd commit 17dc9ec4b6e8 ("sd-device: use
sd_device_get_sysattr_value() to read uevent file"). In the NM
codebase sd_device_get_sysattr_value() is currently commented out
because it depends on file chase.c which is not imported. Importing
that file would require another long chain of imports. Therefore,
revert the commit.

This reverts commit 17dc9ec4b6e82fc2a4f9809011e154f538eb8b9c.

Fixes: 6a4e6fab40 ('merge: branch 'systemd' into jv/systemd-merge')
2025-06-19 15:08:02 +02:00
Beniamino Galvani
1253cbad5a connectivity: fix compiler warning when building without concheck
Fix the following:

../src/core/nm-connectivity.c:958:1: warning: ‘check_platform_config’ defined but not used [-Wunused-function]
  958 | check_platform_config(NMConnectivity *self,
      | ^~~~~~~~~~~~~~~~~~~~~

Fixes: 91d447df19 ('device: don't start connectivity check on unconfigured devices')

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2224
2025-06-19 15:06:53 +02:00
Íñigo Huguet
dd7f9fdf8e merge: branch 'ih/rm-forwarding-ignore'
ipv4: remove the forwarding=ignore value

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2221
2025-06-19 12:27:49 +00:00
Íñigo Huguet
82692cc75c ipv4: remove the forwarding=ignore value
It is not clear whether we can actually respect this value. For example,
we should not restore the kernel's default value on deactivation or
device's state change, but it is unclear if we can ensure that we'll
still have the connection's configuration in all possible changes of
state.

Also, it is unclear if it's a desirable value that we want to support.
At this point it is mostly clear that trying to configure NM managed
devices externally always ends being dissapointing, no matter how hard
we try.

Remove this value for now, while we discuss whether it makes sense or
not, so it doesn't become stable in the new 1.54 release.
2025-06-19 12:27:35 +00:00
Beniamino Galvani
a4ee55468f merge: branch 'bg/sriov-preserve-on-down'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2219
https://issues.redhat.com/browse/RHEL-69125
2025-06-18 13:22:35 +02:00
Beniamino Galvani
3588c48686 NEWS: update 2025-06-18 13:21:19 +02:00
Beniamino Galvani
6f219aa649 device: allow reapplying the sriov.preserve-on-down property
It is useful when there is an already active device and we want to
bring it down preserving the SR-IOV VFs. For example:

  $ nmcli connection add type ethernet ifname eni1np1 sriov.total-vfs 2 ipv4.method disabled ipv6.method disabled
  $ nmcli connection up ethernet-eni1np1

  $ ip link show eni1np1
  342: eni1np1: <BROADCAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000
      link/ether 6e:cf:f0:08:74:f4 brd ff:ff:ff:ff:ff:ff
      vf 0     link/ether 00:00:00:00:00:00 brd ff:ff:ff:ff:ff:ff, ...
      vf 1     link/ether 00:00:00:00:00:00 brd ff:ff:ff:ff:ff:ff, ...

  $ nmcli device modify eni1np1 sriov.preserve-on-down yes
  $ nmcli connection down ethernet-eni1np1

  $ ip link show eni1np1
  342: eni1np1: <BROADCAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN mode DEFAULT group default qlen 1000
      link/ether 6e:cf:f0:08:74:f4 brd ff:ff:ff:ff:ff:ff
      vf 0     link/ether 00:00:00:00:00:00 brd ff:ff:ff:ff:ff:ff, ...
      vf 1     link/ether 00:00:00:00:00:00 brd ff:ff:ff:ff:ff:ff, ...
2025-06-18 13:20:49 +02:00
Beniamino Galvani
c70b4a98a3 core: use the sriov.preserve-on-down property 2025-06-18 13:20:49 +02:00
Beniamino Galvani
eb0a22a162 libnm,nmcli: add sriov.preserve-on-down property
Add a new "sriov.preserve-on-down" property that controls whether
NetworkManager preserves the SR-IOV parameters set on the device when
the connection is deactivated, or whether it resets them to their
default value. The SR-IOV parameters are those specified in the
"sriov" setting, like the number of VFs to create, the eswitch
configuration, etc.
2025-06-18 13:20:49 +02:00
Beniamino Galvani
7212d8b8e9 version: add 1.56 macros 2025-06-18 13:20:49 +02:00
Beniamino Galvani
cceec45089 merge: branch 'bg/nmcli-wg-peers'
nmcli: allow setting the wireguard peers

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2220
2025-06-18 09:08:17 +00:00
Beniamino Galvani
b4dde691ec nmcli: add support for managing wireguard peers
Even if WireGuard is supported since long time in NetworkManager, it
is still not possible to manage the list of peers via nmcli. The
reason is that in the past we wanted to introduce a special syntax
that would allow to manage the peer list more easily. However, this
requires heavy changes to the nmcli output formatting code, and so it
never happened.

Since perfection is the enemy of good, abandon the idea of a custom
handling of peers and treat them as any other composite property. The
property is named "wireguard.peers" and exposes the peers indexed by
public key, with optional attributes.

Example:

  $ nmcli connection modify wg0 wireguard.peers "8Wgc1a0jJX3rQULwD5NFFLKrKQnbOnTiaNoerLneG1o= preshared-key=16uGwZvROnwyNGoW6Z3pvJB5GKbd6ncYROA/FFleLQA= allowed-ips=0.0.0.0/0 persistent-keepalive=10"
  $ nmcli connection modify wg0 +wireguard.peers "fd2NSxUjkaR/Jft15+gpXU13hKSyZLoe4cp+g+feBCc= allowed-ips=192.168.40.0/24 endpoint=172.25.10.1:8888"
  $ nmcli -g wireguard.peers connection show wg0
  8Wgc1a0jJX3rQULwD5NFFLKrKQnbOnTiaNoerLneG1o= allowed-ips=0.0.0.0/0 persistent-keepalive=10, fd2NSxUjkaR/Jft15+gpXU13hKSyZLoe4cp+g+feBCc= allowed-ips=192.168.40.0/24 endpoint=172.25.10.1\:8888
  $ nmcli connection modify wg0 -wireguard.peers 8Wgc1a0jJX3rQULwD5NFFLKrKQnbOnTiaNoerLneG1o=
  $ nmcli -g wireguard.peers connection show wg0
  fd2NSxUjkaR/Jft15+gpXU13hKSyZLoe4cp+g+feBCc= allowed-ips=192.168.40.0/24 endpoint=172.25.10.1\:8888
2025-06-16 13:20:02 +02:00
Beniamino Galvani
f13aca1aba NEWS: update 2025-06-16 10:23:25 +02:00
Jan Vaclav
9abe5658cc merge: branch 'jv/systemd-merge'
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2213
2025-06-10 09:23:34 +02:00
Beniamino Galvani
46e0d2b4e4 ovs: set the tun interface up before stage3
When using the netdev datapath, we wait that the tun link appears, we
call nm_device_set_ip_ifindex() (which also brings the link up) and
then we check that the link is ready, i.e. that udev has announced the
link and the MAC address is correct. After that, we schedule stage3
(ip-config).

In this, there is a race condition that occurs sometimes in NMCI test
ovs_datapath_type_netdev_with_cloned_mac. In rare conditions,
nm_device_set_ip_ifindex() bring the interface up but then ovs-vswitch
changes again the flags of the interface without IFF_UP. The result is
that the interface stays down, breaking communications.

To fix this, we need to always call nm_device_bring_up() after the tun
device is ready. The problem is that we can't do it in
_netdev_tun_link_cb() because that function is already invoked
synchronously from platform code.

Instead, simplify the handling of the netdev datapath. Every
"link-changed" event from platform is handled by
_netdev_tun_link_cb(), which always schedule a delayed function
_netdev_tun_link_cb_in_idle(). This function just assigns the
ip-ifindex to the device if missing, and starts stage3 if the link is
ready. While doing so, it also bring the interface up.

Fixes: 99a6c6eda6 ('ovs, dpdk: fix creating ovs-interface when the ovs-bridge is netdev')

https://issues.redhat.com/browse/RHEL-17358

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2218
2025-06-06 16:35:12 +02:00
Beniamino Galvani
b678ceab9f merge: branch 'wpa3_transition_fix'
core: fix WPA2 fallback for WPA3 transition APs

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2205
2025-06-05 16:15:49 +00:00
Conn O'Griofa
b00c6749d7 core: fix WPA2 fallback for WPA3 transition APs
When connecting to an AP configured for WPA3 transition mode, the
connection will fail if PMF is disabled on the client due to SAE and
FT-SAE being unconditionally added to the key_mgmt variable's
parameters.

By removing the "!is_ap ||" check, SAE and FT-SAE will no longer be
selected when PMF is disabled, allowing clients to connect via
WPA2/PSK mode as per the original intent of
a0988868ba.

Signed-off-by: Conn O'Griofa <connogriofa@gmail.com>
2025-06-05 11:54:16 +00:00
Jan Vaclav
eac9f828e8 tools/nm-in-container: add --skip-unavailable flag for installing debuginfo 2025-06-02 11:08:19 +00:00
Jan Vaclav
4be97207ed tools/nm-in-container: update package install list for fedora 42
- ausearch is part of audit package
- mlocate is not available anymore
- "openvswitch2*" packages are not available anymore
- ipsec-tools is not available anymore
2025-06-02 11:08:19 +00:00
Jan Vaclav
6a4e6fab40 merge: branch 'systemd' into jv/systemd-merge 2025-06-02 10:00:31 +02:00
Íñigo Huguet
b17a842e1a merge: branch 'manpages'
build: make manpages a mandatory part of the build

Closes #1653

https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/merge_requests/2068
2025-05-30 09:43:14 +00:00
Eli Schwartz
fe62ce6a4b ci: avoid building manpages on Fedora
It appears that xsltproc is not installed there. It is generally needed
for the docs build too, so as a crude CI heuristic, don't build anywhere
that docs are disabled.
2025-05-30 09:42:55 +00:00
Eli Schwartz
a11760ef39 build: make manpages a mandatory part of the build by default
Currently, both man pages and gtk-doc HTML documentation are enabled by
the same build option. It is common for users to want to choose whether
to build HTML docs, as not everyone cares about HTML developer docs, but
manpages are intended directly for end-user consumption and should
always be available. At the very least, there should be a separate
option to disable them to avoid accidentally disabling them while trying
to disable HTML developer docs.

Resolves: https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/issues/1653
2025-05-30 09:42:55 +00:00
Eli Schwartz
f656675b57 build: install pre-disted manpages if available
When building from a release tarball of NetworkManager,
`meson.add_dist_script()` has copied various prebuilt manpages into the
tarball and building them again is not really necessary. We can just
install those directly.

This means that *all* manpages could be installed even without
introspection, even though some of them can only be *built* when
introspection is enabled.

It also means that manpages can be installed even when xsltproc is not
available at build time.
2025-05-30 09:42:55 +00:00
Eli Schwartz
ee078be745 build: remove outdated, commented-out configure.ac snippet
This was likely added during the port to meson. It's just a multiline
string, so it has no effect in meson, and it appears to be entirely for
things which are already implemented in meson, so there's no real point
in keeping it any longer.
2025-05-30 09:42:55 +00:00
Eli Schwartz
897eed184a build: only demand an xsltproc program when it is used
It's intrinsically used when building manpages, and also part of the
introspection-specific parts of the documentation build. There's no
particular guarantee either of those will actually be invoked during a
build, so don't unconditionally look it up.

This allows building with one fewer dependency in many cases.
2025-05-30 09:42:55 +00:00
Vladimír Beneš
872e626342 release: bump version to 1.55.0 (development) 2025-05-30 11:36:41 +02:00
Jan Vaclav
3ae6505d7d systemd: update code from upstream (2025-05-05)
This is a direct dump from systemd git.

  $ git clean -fdx && \
    git cat-file -p HEAD | sed '1,/^======$/ d' | bash - && \
    git add .

======

SYSTEMD_DIR=../systemd
COMMIT=a50fa2a40f4a91d49503d3588a3dd29ea05e559b

(
  cd "$SYSTEMD_DIR"
  git checkout "$COMMIT"
  git reset --hard
  git clean -fdx
)

git ls-files -z :/src/libnm-systemd-core/src/ \
                :/src/libnm-systemd-shared/src/ \
                :/src/libnm-std-aux/unaligned-fundamental.h \
                :/src/libnm-std-aux/unaligned.h | \
  xargs -0 rm -f

nm_copy_sd_shared() {
    mkdir -p "./src/libnm-systemd-shared/$(dirname "$1")"
    cp "$SYSTEMD_DIR/$1" "./src/libnm-systemd-shared/$1"
}

nm_copy_sd_core() {
    mkdir -p "./src/libnm-systemd-core/$(dirname "$1")"
    cp "$SYSTEMD_DIR/$1" "./src/libnm-systemd-core/$1"
}

nm_copy_sd_stdaux() {
    mkdir -p "./src/libnm-std-aux/"
    cp "$SYSTEMD_DIR/$1" "./src/libnm-std-aux/${1##*/}"
}

nm_copy_sd_core "src/libsystemd-network/dhcp-duid-internal.h"
nm_copy_sd_core "src/libsystemd-network/dhcp6-client-internal.h"
nm_copy_sd_core "src/libsystemd-network/dhcp6-internal.h"
nm_copy_sd_core "src/libsystemd-network/dhcp6-lease-internal.h"
nm_copy_sd_core "src/libsystemd-network/dhcp6-network.c"
nm_copy_sd_core "src/libsystemd-network/dhcp6-option.c"
nm_copy_sd_core "src/libsystemd-network/dhcp6-option.h"
nm_copy_sd_core "src/libsystemd-network/dhcp6-protocol.c"
nm_copy_sd_core "src/libsystemd-network/dhcp6-protocol.h"
nm_copy_sd_core "src/libsystemd-network/network-common.c"
nm_copy_sd_core "src/libsystemd-network/network-common.h"
nm_copy_sd_core "src/libsystemd-network/sd-dhcp-duid.c"
nm_copy_sd_core "src/libsystemd-network/sd-dhcp6-client.c"
nm_copy_sd_core "src/libsystemd-network/sd-dhcp6-lease.c"
nm_copy_sd_core "src/libsystemd/sd-device/device-internal.h"
nm_copy_sd_core "src/libsystemd/sd-device/device-private.c"
nm_copy_sd_core "src/libsystemd/sd-device/device-private.h"
nm_copy_sd_core "src/libsystemd/sd-device/device-util.c"
nm_copy_sd_core "src/libsystemd/sd-device/device-util.h"
nm_copy_sd_core "src/libsystemd/sd-device/sd-device.c"
nm_copy_sd_core "src/libsystemd/sd-event/event-source.h"
nm_copy_sd_core "src/libsystemd/sd-event/event-util.c"
nm_copy_sd_core "src/libsystemd/sd-event/event-util.h"
nm_copy_sd_core "src/libsystemd/sd-event/sd-event.c"
nm_copy_sd_core "src/libsystemd/sd-id128/id128-util.c"
nm_copy_sd_core "src/libsystemd/sd-id128/id128-util.h"
nm_copy_sd_core "src/libsystemd/sd-id128/sd-id128.c"
nm_copy_sd_core "src/systemd/_sd-common.h"
nm_copy_sd_core "src/systemd/sd-device.h"
nm_copy_sd_core "src/systemd/sd-dhcp-duid.h"
nm_copy_sd_core "src/systemd/sd-dhcp6-client.h"
nm_copy_sd_core "src/systemd/sd-dhcp6-lease.h"
nm_copy_sd_core "src/systemd/sd-dhcp6-option.h"
nm_copy_sd_core "src/systemd/sd-dhcp6-protocol.h"
nm_copy_sd_core "src/systemd/sd-event.h"
nm_copy_sd_core "src/systemd/sd-id128.h"
nm_copy_sd_core "src/systemd/sd-ndisc.h"
nm_copy_sd_shared "src/basic/alloc-util.c"
nm_copy_sd_shared "src/basic/alloc-util.h"
nm_copy_sd_shared "src/basic/arphrd-util.h"
nm_copy_sd_shared "src/basic/assert-util.h"
nm_copy_sd_shared "src/basic/bitfield.h"
nm_copy_sd_shared "src/basic/btrfs.c"
nm_copy_sd_shared "src/basic/btrfs.h"
nm_copy_sd_shared "src/basic/cgroup-util.h"
nm_copy_sd_shared "src/basic/chase.h"
nm_copy_sd_shared "src/basic/chattr-util.c"
nm_copy_sd_shared "src/basic/chattr-util.h"
nm_copy_sd_shared "src/basic/constants.h"
nm_copy_sd_shared "src/basic/devnum-util.c"
nm_copy_sd_shared "src/basic/devnum-util.h"
nm_copy_sd_shared "src/basic/dns-def.h"
nm_copy_sd_shared "src/basic/env-file.c"
nm_copy_sd_shared "src/basic/env-file.h"
nm_copy_sd_shared "src/basic/env-util.c"
nm_copy_sd_shared "src/basic/env-util.h"
nm_copy_sd_shared "src/basic/errno-util.h"
nm_copy_sd_shared "src/basic/escape.c"
nm_copy_sd_shared "src/basic/escape.h"
nm_copy_sd_shared "src/basic/ether-addr-util.c"
nm_copy_sd_shared "src/basic/ether-addr-util.h"
nm_copy_sd_shared "src/basic/extract-word.c"
nm_copy_sd_shared "src/basic/extract-word.h"
nm_copy_sd_shared "src/basic/fd-util.c"
nm_copy_sd_shared "src/basic/fd-util.h"
nm_copy_sd_shared "src/basic/fileio.c"
nm_copy_sd_shared "src/basic/fileio.h"
nm_copy_sd_shared "src/basic/format-ifname.c"
nm_copy_sd_shared "src/basic/format-ifname.h"
nm_copy_sd_shared "src/basic/format-util.c"
nm_copy_sd_shared "src/basic/format-util.h"
nm_copy_sd_shared "src/basic/fs-util.c"
nm_copy_sd_shared "src/basic/fs-util.h"
nm_copy_sd_shared "src/basic/glyph-util.c"
nm_copy_sd_shared "src/basic/glyph-util.h"
nm_copy_sd_shared "src/basic/hash-funcs.c"
nm_copy_sd_shared "src/basic/hash-funcs.h"
nm_copy_sd_shared "src/basic/hashmap.c"
nm_copy_sd_shared "src/basic/hashmap.h"
nm_copy_sd_shared "src/basic/hexdecoct.c"
nm_copy_sd_shared "src/basic/hexdecoct.h"
nm_copy_sd_shared "src/basic/hostname-util.c"
nm_copy_sd_shared "src/basic/hostname-util.h"
nm_copy_sd_shared "src/basic/in-addr-util.c"
nm_copy_sd_shared "src/basic/in-addr-util.h"
nm_copy_sd_shared "src/basic/inotify-util.c"
nm_copy_sd_shared "src/basic/inotify-util.h"
nm_copy_sd_shared "src/basic/io-util.c"
nm_copy_sd_shared "src/basic/io-util.h"
nm_copy_sd_shared "src/basic/iovec-util.h"
nm_copy_sd_shared "src/basic/label.c"
nm_copy_sd_shared "src/basic/label.h"
nm_copy_sd_shared "src/basic/list.h"
nm_copy_sd_shared "src/basic/locale-util.c"
nm_copy_sd_shared "src/basic/locale-util.h"
nm_copy_sd_shared "src/basic/lock-util.h"
nm_copy_sd_shared "src/basic/log.h"
nm_copy_sd_shared "src/basic/macro.h"
nm_copy_sd_shared "src/basic/memory-util.c"
nm_copy_sd_shared "src/basic/memory-util.h"
nm_copy_sd_shared "src/basic/mempool.c"
nm_copy_sd_shared "src/basic/mempool.h"
nm_copy_sd_shared "src/basic/missing_fcntl.h"
nm_copy_sd_shared "src/basic/missing_fs.h"
nm_copy_sd_shared "src/basic/missing_pidfd.h"
nm_copy_sd_shared "src/basic/missing_random.h"
nm_copy_sd_shared "src/basic/missing_socket.h"
nm_copy_sd_shared "src/basic/missing_syscall.h"
nm_copy_sd_shared "src/basic/missing_wait.h"
nm_copy_sd_shared "src/basic/mountpoint-util.c"
nm_copy_sd_shared "src/basic/mountpoint-util.h"
nm_copy_sd_shared "src/basic/namespace-util.h"
nm_copy_sd_shared "src/basic/ordered-set.c"
nm_copy_sd_shared "src/basic/ordered-set.h"
nm_copy_sd_shared "src/basic/origin-id.h"
nm_copy_sd_shared "src/basic/parse-util.c"
nm_copy_sd_shared "src/basic/parse-util.h"
nm_copy_sd_shared "src/basic/path-util.c"
nm_copy_sd_shared "src/basic/path-util.h"
nm_copy_sd_shared "src/basic/pidfd-util.c"
nm_copy_sd_shared "src/basic/pidfd-util.h"
nm_copy_sd_shared "src/basic/pidref.h"
nm_copy_sd_shared "src/basic/prioq.c"
nm_copy_sd_shared "src/basic/prioq.h"
nm_copy_sd_shared "src/basic/process-util.c"
nm_copy_sd_shared "src/basic/process-util.h"
nm_copy_sd_shared "src/basic/random-util.c"
nm_copy_sd_shared "src/basic/random-util.h"
nm_copy_sd_shared "src/basic/ratelimit.c"
nm_copy_sd_shared "src/basic/ratelimit.h"
nm_copy_sd_shared "src/basic/set.h"
nm_copy_sd_shared "src/basic/sha256.c"
nm_copy_sd_shared "src/basic/sha256.h"
nm_copy_sd_shared "src/basic/signal-util.c"
nm_copy_sd_shared "src/basic/signal-util.h"
nm_copy_sd_shared "src/basic/siphash24.h"
nm_copy_sd_shared "src/basic/socket-util.c"
nm_copy_sd_shared "src/basic/socket-util.h"
nm_copy_sd_shared "src/basic/sort-util.h"
nm_copy_sd_shared "src/basic/sparse-endian.h"
nm_copy_sd_shared "src/basic/stat-util.c"
nm_copy_sd_shared "src/basic/stat-util.h"
nm_copy_sd_shared "src/basic/stdio-util.h"
nm_copy_sd_shared "src/basic/string-table.c"
nm_copy_sd_shared "src/basic/string-table.h"
nm_copy_sd_shared "src/basic/string-util.c"
nm_copy_sd_shared "src/basic/string-util.h"
nm_copy_sd_shared "src/basic/strv.c"
nm_copy_sd_shared "src/basic/strv.h"
nm_copy_sd_shared "src/basic/strxcpyx.c"
nm_copy_sd_shared "src/basic/strxcpyx.h"
nm_copy_sd_shared "src/basic/time-util.c"
nm_copy_sd_shared "src/basic/time-util.h"
nm_copy_sd_shared "src/basic/tmpfile-util.c"
nm_copy_sd_shared "src/basic/tmpfile-util.h"
nm_copy_sd_shared "src/basic/umask-util.h"
nm_copy_sd_shared "src/basic/user-util.c"
nm_copy_sd_shared "src/basic/user-util.h"
nm_copy_sd_shared "src/basic/utf8.c"
nm_copy_sd_shared "src/basic/utf8.h"
nm_copy_sd_shared "src/basic/include/net/if.h"
nm_copy_sd_shared "src/basic/include/netinet/in.h"
nm_copy_sd_shared "src/fundamental/assert-fundamental.h"
nm_copy_sd_shared "src/fundamental/iovec-util-fundamental.h"
nm_copy_sd_shared "src/fundamental/logarithm.h"
nm_copy_sd_shared "src/fundamental/macro-fundamental.h"
nm_copy_sd_shared "src/fundamental/memory-util-fundamental.h"
nm_copy_sd_shared "src/fundamental/sha256-fundamental.c"
nm_copy_sd_shared "src/fundamental/sha256-fundamental.h"
nm_copy_sd_shared "src/fundamental/string-util-fundamental.c"
nm_copy_sd_shared "src/fundamental/string-util-fundamental.h"
nm_copy_sd_shared "src/shared/dns-domain.c"
nm_copy_sd_shared "src/shared/dns-domain.h"
nm_copy_sd_shared "src/shared/log-link.h"
nm_copy_sd_shared "src/shared/web-util.c"
nm_copy_sd_shared "src/shared/web-util.h"
nm_copy_sd_stdaux "src/basic/unaligned.h"
nm_copy_sd_stdaux "src/fundamental/unaligned-fundamental.h"
2025-05-14 12:37:33 +02:00
441 changed files with 76745 additions and 45324 deletions

1
.gitignore vendored
View file

@ -81,7 +81,6 @@ test-*.trs
/data/org.freedesktop.NetworkManager.service /data/org.freedesktop.NetworkManager.service
/data/server.conf /data/server.conf
/data/org.freedesktop.NetworkManager.policy /data/org.freedesktop.NetworkManager.policy
/data/org.freedesktop.NetworkManager.policy.in
/data/nm-sudo.service /data/nm-sudo.service
/data/nm-priv-helper.service /data/nm-priv-helper.service
/data/NetworkManager-config-initrd.service /data/NetworkManager-config-initrd.service

View file

@ -60,11 +60,11 @@ variables:
# #
# This is done by running `ci-fairy generate-template` and possibly bumping # This is done by running `ci-fairy generate-template` and possibly bumping
# ".default_tag". # ".default_tag".
ALPINE_TAG: 'tag-dcc430216167' ALPINE_TAG: 'tag-8e4bbc59695b'
CENTOS_TAG: 'tag-feb1adbc208e' CENTOS_TAG: 'tag-caf6673db1a7'
DEBIAN_TAG: 'tag-afb784497c2f' DEBIAN_TAG: 'tag-e394e8e726e1'
FEDORA_TAG: 'tag-feb1adbc208e' FEDORA_TAG: 'tag-caf6673db1a7'
UBUNTU_TAG: 'tag-afb784497c2f' UBUNTU_TAG: 'tag-e394e8e726e1'
ALPINE_EXEC: 'bash .gitlab-ci/alpine-install.sh' ALPINE_EXEC: 'bash .gitlab-ci/alpine-install.sh'
CENTOS_EXEC: 'bash .gitlab-ci/fedora-install.sh' CENTOS_EXEC: 'bash .gitlab-ci/fedora-install.sh'
@ -102,19 +102,7 @@ variables:
# Build a container for each distribution + version. The ci-templates # Build a container for each distribution + version. The ci-templates
# will re-use the containers if the tag doesn't change. # will re-use the containers if the tag doesn't change.
tier1:fedora:43@prep: tier1:fedora:42@prep:
extends:
- .fdo.container-build@fedora
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: '43'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG
FDO_DISTRIBUTION_EXEC: $FEDORA_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' || $SCHEDULED_PIPELINE_NAME == "weekly"
tier3:fedora:42@prep:
extends: extends:
- .fdo.container-build@fedora - .fdo.container-build@fedora
stage: prep stage: prep
@ -123,6 +111,116 @@ tier3:fedora:42@prep:
FDO_DISTRIBUTION_VERSION: '42' FDO_DISTRIBUTION_VERSION: '42'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG FDO_DISTRIBUTION_TAG: $FEDORA_TAG
FDO_DISTRIBUTION_EXEC: $FEDORA_EXEC FDO_DISTRIBUTION_EXEC: $FEDORA_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' || $SCHEDULED_PIPELINE_NAME == "weekly"
tier2:fedora:rawhide@prep:
extends:
- .fdo.container-build@fedora
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'rawhide'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG
FDO_DISTRIBUTION_EXEC: $FEDORA_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier2:centos:stream10@prep:
extends:
- .fdo.container-build@centos
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'stream10'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
FDO_DISTRIBUTION_EXEC: $CENTOS_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier2:centos:stream9@prep:
extends:
- .fdo.container-build@centos
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'stream9'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
FDO_DISTRIBUTION_EXEC: $CENTOS_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier2:ubuntu:devel@prep:
extends:
- .fdo.container-build@ubuntu
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'devel'
FDO_DISTRIBUTION_TAG: $UBUNTU_TAG
FDO_DISTRIBUTION_EXEC: $UBUNTU_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier2:debian:testing@prep:
extends:
- .fdo.container-build@debian
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'testing'
FDO_DISTRIBUTION_TAG: $DEBIAN_TAG
FDO_DISTRIBUTION_EXEC: $DEBIAN_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier2:debian:sid@prep:
extends:
- .fdo.container-build@debian
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'sid'
FDO_DISTRIBUTION_TAG: $DEBIAN_TAG
FDO_DISTRIBUTION_EXEC: $DEBIAN_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier2:alpine:edge@prep:
extends:
- .fdo.container-build@alpine
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'edge'
FDO_DISTRIBUTION_TAG: $ALPINE_TAG
FDO_DISTRIBUTION_EXEC: $ALPINE_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier3:fedora:43@prep:
extends:
- .fdo.container-build@fedora
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: '43'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG
FDO_DISTRIBUTION_EXEC: $FEDORA_EXEC
rules: rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' - if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual when: manual
@ -268,34 +366,6 @@ tier3:alpine:3.19@prep:
when: manual when: manual
allow_failure: true allow_failure: true
tier3:centos:stream10@prep:
extends:
- .fdo.container-build@centos
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'stream10'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
FDO_DISTRIBUTION_EXEC: $CENTOS_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
tier3:centos:stream9@prep:
extends:
- .fdo.container-build@centos
stage: prep
variables:
GIT_STRATEGY: none
FDO_DISTRIBUTION_VERSION: 'stream9'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
FDO_DISTRIBUTION_EXEC: $CENTOS_EXEC
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
when: manual
allow_failure: true
################################################################# #################################################################
# # # #
# tierN stage # # tierN stage #
@ -312,7 +382,7 @@ tier3:centos:stream9@prep:
dependencies: [] dependencies: []
t_fedora:43: t_fedora:42:
extends: extends:
- .build@template - .build@template
- .fdo.distribution-image@fedora - .fdo.distribution-image@fedora
@ -328,24 +398,122 @@ t_fedora:43:
- tarball - tarball
- subtree - subtree
variables: variables:
FDO_DISTRIBUTION_VERSION: '43' FDO_DISTRIBUTION_VERSION: '42'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG FDO_DISTRIBUTION_TAG: $FEDORA_TAG
needs: needs:
- "tier1:fedora:43@prep" - "tier1:fedora:42@prep"
rules: rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' - if: $CI_PIPELINE_SOURCE != 'schedule'
t_fedora:42: t_fedora:rawhide:
extends:
- .build@template
- .fdo.distribution-image@fedora
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'rawhide'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG
needs:
- "tier2:fedora:rawhide@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_centos:stream10:
extends:
- .build@template
- .fdo.distribution-image@centos
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'stream10'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
needs:
- "tier2:centos:stream10@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_centos:stream9:
extends:
- .build@template
- .fdo.distribution-image@centos
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'stream9'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
needs:
- "tier2:centos:stream9@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_ubuntu:devel:
extends:
- .build@template
- .fdo.distribution-image@ubuntu
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'devel'
FDO_DISTRIBUTION_TAG: $UBUNTU_TAG
needs:
- "tier2:ubuntu:devel@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_debian:testing:
extends:
- .build@template
- .fdo.distribution-image@debian
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'testing'
FDO_DISTRIBUTION_TAG: $DEBIAN_TAG
needs:
- "tier2:debian:testing@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_debian:sid:
extends:
- .build@template
- .fdo.distribution-image@debian
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'sid'
FDO_DISTRIBUTION_TAG: $DEBIAN_TAG
needs:
- "tier2:debian:sid@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_alpine:edge:
extends:
- .build@template
- .fdo.distribution-image@alpine
- .nm_artifacts_debug
stage: tier2
variables:
FDO_DISTRIBUTION_VERSION: 'edge'
FDO_DISTRIBUTION_TAG: $ALPINE_TAG
needs:
- "tier2:alpine:edge@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_fedora:43:
extends: extends:
- .build@template - .build@template
- .fdo.distribution-image@fedora - .fdo.distribution-image@fedora
- .nm_artifacts_debug - .nm_artifacts_debug
stage: tier3 stage: tier3
variables: variables:
FDO_DISTRIBUTION_VERSION: '42' FDO_DISTRIBUTION_VERSION: '43'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG FDO_DISTRIBUTION_TAG: $FEDORA_TAG
needs: needs:
- "tier3:fedora:42@prep" - "tier3:fedora:43@prep"
rules: rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' - if: $CI_PIPELINE_SOURCE != 'schedule'
@ -489,34 +657,6 @@ t_alpine:3.19:
rules: rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' - if: $CI_PIPELINE_SOURCE != 'schedule'
t_centos:stream10:
extends:
- .build@template
- .fdo.distribution-image@centos
- .nm_artifacts_debug
stage: tier3
variables:
FDO_DISTRIBUTION_VERSION: 'stream10'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
needs:
- "tier3:centos:stream10@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
t_centos:stream9:
extends:
- .build@template
- .fdo.distribution-image@centos
- .nm_artifacts_debug
stage: tier3
variables:
FDO_DISTRIBUTION_VERSION: 'stream9'
FDO_DISTRIBUTION_TAG: $CENTOS_TAG
needs:
- "tier3:centos:stream9@prep"
rules:
- if: $CI_PIPELINE_SOURCE != 'schedule'
################################################################# #################################################################
# # # #
# specific jobs # # specific jobs #
@ -527,10 +667,10 @@ check-patch:
extends: extends:
- .fdo.distribution-image@fedora - .fdo.distribution-image@fedora
variables: variables:
FDO_DISTRIBUTION_VERSION: '43' FDO_DISTRIBUTION_VERSION: '42'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG FDO_DISTRIBUTION_TAG: $FEDORA_TAG
needs: needs:
- "tier1:fedora:43@prep" - "tier1:fedora:42@prep"
rules: rules:
- if: $CI_PIPELINE_SOURCE != 'schedule' - if: $CI_PIPELINE_SOURCE != 'schedule'
stage: tier1 stage: tier1
@ -542,10 +682,10 @@ check-tree:
extends: extends:
- .fdo.distribution-image@fedora - .fdo.distribution-image@fedora
variables: variables:
FDO_DISTRIBUTION_VERSION: '43' FDO_DISTRIBUTION_VERSION: '42'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG FDO_DISTRIBUTION_TAG: $FEDORA_TAG
needs: needs:
- "tier1:fedora:43@prep" - "tier1:fedora:42@prep"
rules: rules:
- if: $CI_PIPELINE_SOURCE == 'merge_request_event' && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME != $CI_DEFAULT_BRANCH - if: $CI_PIPELINE_SOURCE == 'merge_request_event' && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME != $CI_DEFAULT_BRANCH
allow_failure: true allow_failure: true
@ -573,11 +713,11 @@ pages:
rules: rules:
- if: $CI_PIPELINE_SOURCE == 'schedule' - if: $CI_PIPELINE_SOURCE == 'schedule'
when: never when: never
- if: $CI_MERGE_REQUEST_SOURCE_BRANCH_NAME == 'main' - if: $CI_PIPELINE_SOURCE == 'push' && $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
dependencies: dependencies:
- "t_fedora:43: [meson+gcc+docs+valgrind]" - "t_fedora:42: [meson+gcc+docs+valgrind]"
needs: needs:
- "t_fedora:43: [meson+gcc+docs+valgrind]" - "t_fedora:42: [meson+gcc+docs+valgrind]"
triage:issues: triage:issues:
stage: triage stage: triage
@ -594,11 +734,11 @@ coverity:
extends: extends:
- .fdo.distribution-image@fedora - .fdo.distribution-image@fedora
variables: variables:
FDO_DISTRIBUTION_VERSION: '43' FDO_DISTRIBUTION_VERSION: '42'
FDO_DISTRIBUTION_TAG: $FEDORA_TAG FDO_DISTRIBUTION_TAG: $FEDORA_TAG
stage: coverity stage: coverity
needs: needs:
- "tier1:fedora:43@prep" - "tier1:fedora:42@prep"
rules: rules:
- if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULED_PIPELINE_NAME == "weekly" - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULED_PIPELINE_NAME == "weekly"
script: script:

View file

@ -240,7 +240,7 @@ pages:
rules: rules:
- if: $CI_PIPELINE_SOURCE == 'schedule' - if: $CI_PIPELINE_SOURCE == 'schedule'
when: never when: never
- if: $CI_MERGE_REQUEST_SOURCE_BRANCH_NAME == 'main' - if: $CI_PIPELINE_SOURCE == 'push' && $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
dependencies: dependencies:
- "t_{{default_distro.name}}:{{default_distro.versions[0]}}: [meson+gcc+docs+valgrind]" - "t_{{default_distro.name}}:{{default_distro.versions[0]}}: [meson+gcc+docs+valgrind]"
needs: needs:

View file

@ -23,17 +23,39 @@ distributions:
- name: fedora - name: fedora
tier: 1 tier: 1
versions: versions:
- '43' - '42'
# TIER 2: distribution versions that will or might use the current NM version. # TIER 2: distribution versions that will or might use the current NM version.
# Run when doing a release. # Run when doing a release.
- name: fedora
tier: 2
versions:
- 'rawhide'
- name: centos
tier: 2
versions:
- 'stream10'
- 'stream9'
- name: ubuntu
tier: 2
versions:
- 'devel'
- name: debian
tier: 2
versions:
- 'testing'
- 'sid'
- name: alpine
tier: 2
versions:
- 'edge'
# TIER 3: distribution versions not in EOL but don't use the current NM version. # TIER 3: distribution versions not in EOL but don't use the current NM version.
# Run when doing a release, but a failure won't be blocking for the release. # Run when doing a release, but a failure won't be blocking for the release.
- name: fedora - name: fedora
tier: 3 tier: 3
versions: versions:
- '42' - '43'
- '41' - '41'
- name: ubuntu - name: ubuntu
tier: 3 tier: 3
@ -53,8 +75,3 @@ distributions:
- '3.21' - '3.21'
- '3.20' - '3.20'
- '3.19' - '3.19'
- name: centos
tier: 3
versions:
- 'stream10'
- 'stream9'

View file

@ -8,6 +8,9 @@ fedora:
- version: rawhide - version: rawhide
support: yes support: yes
nm: main nm: main
- version: 43
support: 2026-12-02
nm: 1.54
- version: 42 - version: 42
support: 2026-05-13 support: 2026-05-13
nm: 1.52 nm: 1.52
@ -18,8 +21,11 @@ fedora:
# CentOS Stream # CentOS Stream
centos: centos:
- version: stream10
support: 2030-12-31 # exact date unknown, only the year
nm: main
- version: stream9 - version: stream9
support: 2027-05-31 support: 2027-12-31 # exact date unknown, only the year
nm: main nm: main
# RHEL: # RHEL:
@ -31,33 +37,43 @@ centos:
# support: 6 months # support: 6 months
# Releases and support info: https://access.redhat.com/support/policy/updates/errata # Releases and support info: https://access.redhat.com/support/policy/updates/errata
rhel: rhel:
- version: 9.6 # not released yet # Not released yet
- version: 10.1
support: yes support: yes
nm: main nm: 1.54
- version: 9.5 - version: 9.7 # not released yet
support: yes support: yes
nm: 1.48 nm: 1.54
# Full support or EUS support:
- version: 10.0
support: 2027-05-31
extended-support: 2029-05-31
nm: 1.52
- version: 9.6
support: 2027-05-31
extended-support: 2029-05-31
nm: 1.52
- version: 9.4 - version: 9.4
support: 2026-04-30 support: 2026-04-30
extended-support: 2028-04-30 extended-support: 2028-04-30
nm: 1.46 nm: 1.46
- version: 9.2
support: 2025-05-31
extended-support: 2027-05-31
nm: 1.42
- version: 8.10 # last RHEL 8 release, maintenaince support only - version: 8.10 # last RHEL 8 release, maintenaince support only
support: 2029-05-31 support: 2029-05-31
extended-support: no extended-support: no
nm: 1.40 nm: 1.40
- version: 8.8 # SAP / Enhaced EUS only:
- version: 9.2
support: 2025-05-31 support: 2025-05-31
extended-support: 2027-05-31 extended-support: 2027-05-31
nm: 1.40 nm: 1.42
# SAP / Enhaced EUS only:
- version: 9.0 - version: 9.0
support: 2024-05-31 support: 2024-05-31
extended-support: 2026-05-31 extended-support: 2026-05-31
nm: 1.36 nm: 1.36
- version: 8.8
support: 2025-05-31
extended-support: 2027-05-31
nm: 1.40
- version: 8.6 - version: 8.6
support: 2024-05-31 support: 2024-05-31
extended-support: 2026-05-31 extended-support: 2026-05-31
@ -81,10 +97,6 @@ ubuntu:
name: plucky name: plucky
support: 2026-01-15 support: 2026-01-15
nm: 1.52 nm: 1.52
- version: 24.10
name: oracular
support: 2025-07-10
nm: 1.48
- version: 24.04 - version: 24.04
name: noble name: noble
support: 2029-05-31 support: 2029-05-31
@ -109,6 +121,11 @@ debian:
- version: sid - version: sid
support: yes support: yes
nm: main nm: main
- version: 13
name: trixie
support: 2028-08-09
extended-support: 2030-06-30
nm: 1.52
- version: 12 - version: 12
name: bookworm name: bookworm
support: 2026-06-11 support: 2026-06-11
@ -130,6 +147,9 @@ alpine:
- version: edge - version: edge
support: yes support: yes
nm: main nm: main
- version: 3.22
support: 2027-05-01
nm: 1.52
- version: 3.21 - version: 3.21
support: 2026-11-01 support: 2026-11-01
nm: 1.50 nm: 1.50

View file

@ -155,12 +155,7 @@ test_subtree() {
do_clean do_clean
pushd ./src/$d pushd ./src/$d
ARGS=() CC="$cc" CFLAGS="-Werror -Wall" meson build
if [ "$d" = n-acd ]; then
ARGS+=('-Debpf=false')
fi
CC="$cc" CFLAGS="-Werror -Wall" meson build "${ARGS[@]}"
ninja -v -C build test ninja -v -C build test
popd popd

View file

@ -12,9 +12,9 @@ Please read
https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/blob/main/CONTRIBUTING.md https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/blob/main/CONTRIBUTING.md
before opening the merge request. In particular, check that: before opening the merge request. In particular, check that:
- [ ] the subject for all commits is concise and explicative - [ ] The subject for all commits is concise, explanatory, and includes a prefix indicating the area of code changed (e.g., "nmcli: ", "core: ")
- [ ] the message for all commits explains the reason for the change - [ ] The message for all commits explains the reason for the change
- [ ] the source is properly formatted - [ ] The source is properly formatted
- [ ] any relevant documentation is up to date - [ ] Any relevant documentation is up to date
- [ ] you have added unit tests if applicable - [ ] You have added unit tests if applicable
- [ ] the NEWS file is updated when the change deserves to be mentioned, for example for new features, behavior changes, API deprecations, etc. - [ ] The NEWS file is updated when the change deserves to be mentioned, for example for new features, behavior changes, API deprecations, etc.

View file

@ -252,17 +252,25 @@ Versioning scheme (version numbers are called MAJOR.MINOR.MICRO):
versioning scheme than the main NM project despite there are no development versioning scheme than the main NM project despite there are no development
versions here. versions here.
Before starting:
- You need to have the maintainer role in the project.
- The GPG key used to sign the release must be added to your GNOME's Gitlab
profile and uploaded to a keyserver.
- All details: https://handbook.gnome.org/maintainers/making-a-release.html
When doing a release, follow this process: When doing a release, follow this process:
1. Ensure that `NEWS` file is up to date. 1. Ensure that `NEWS` file is up to date.
2. Increment the version in `meson.build`, commit and tag the commit. Example: 2. Increment the version in `meson.build` or `configure.ac`.
`git tag -s 1.2.8 -m 'Tag 1.2.8'`. 3. Commit and push to the `main` branch.
3. Ensure that you are on the right commit and create the tarball: 4. Check that the Gitlab's pipeline finishes without errors.
`git clean -fdx && meson setup build && cd build && meson dist` 5. Tag the commit with a signed tag. Example: `git tag -s 1.2.8 -m 'Release 1.2.8'`.
4. Upload the tarball: `scp ./*-*.tar.xz "$user@master.gnome.org:"` 6. Push the tag. Example: `git push origin 1.2.8`.
5. Login to `master.gnome.org` and run `ftpadmin install`. WARN: this is what starts the automatic CI release. As GNOME doesn't allow
Ensure the new tarballs show up at https://download.gnome.org/sources/ to delete tags, any error detected after this will force a new version bump.
(happens after a short delay) 7. Check that the Gitlab's pipeline finishes without errors. If that happens,
6. Announce the release on the mailing list. the release is done and available both in the Gitlab's releases section and
https://download.gnome.org/sources/*
8. Announce the release on the mailing list.
Notes: Notes:
- You need access to master.gnome.org, see [here](https://handbook.gnome.org/infrastructure/accounts.html). - You need access to master.gnome.org, see [here](https://handbook.gnome.org/infrastructure/accounts.html).

108
NEWS
View file

@ -1,25 +1,103 @@
=============================================== =============================================
NetworkManager-1.54.2 NetworkManager-1.58
Overview of changes since NetworkManager-1.54.1 Overview of changes since NetworkManager-1.56
=============================================== =============================================
This is a snapshot of NetworkManager development. The API is
subject to change and not guaranteed to be compatible with
the later release.
USE AT YOUR OWN RISK. NOT RECOMMENDED FOR PRODUCTION USE!
* Unify the versioning to use everywhere the scheme with the -rcX or -dev
suffixes when appropriate. This affects, for example, the URL and filename
of the release tarball and the version reported by nmcli and the daemon.
As an exception, the C API will continue to use the 90+ scheme for RC versions.
* Connection profiles with manual IP addressing and with gateways that are not
directly reachable will generate a warning on activation and when they are
added/modified via nmcli and nmtui. NetworkManager currently adds on-link
routes for them automatically, but this will change in the future. To fix the
warning, users should add addresses or routes whose subnets cover these
gateways. A gateway (either the default gateway or the next-hop of a route) is
considered directly reachable if it falls within the subnet of a direct route
(a route without a next hop) or of a prefix route from a static address.
* Restrict the connectivity check to use the DNS servers defined on the
same link. If the link has no DNS servers, the connectivity check will
use any servers available in the system.
* Install the systemd units in the initramfs using a systemd generator.
* A new "check-connectivity" configuration option is available to disable the
connectivity check for selected interfaces.
* Remove the modify_system build option that allowed setting up the
polkit permissions to allow non-admin users to create system-wide
connection. That configuration is discouraged because it can be used
to bypass filesystem permissions.
* For private connections (the ones that specify a user in the
"connection.permissions" property), verify that the user can access
the 802.1X certificates and keys set in the connection.
* Introduce a libnm function that can be used by VPN plugins to check
user permissions on certificate and keys.
* The support for Wireless Extensions is deprecated and will be
removed in a future release. Wireless Extensions are now disabled by
default.
* Use an internal implementation of the ping functionality when the
"connection.gateway-ping-timeout" or "connection.ip-ping-addresses"
properties are set, instead of relying on the "ping" tool.
* The powersave property now functions with the iwd backend.
* The "band" property of Wi-fi connections now accepts the "6GHz"
value.
* Show the Wi-Fi band of APs in the scan results from nmcli.
* New <Select...> button in nmtui that allows users to chose from list of
available devices when creating connection profiles for physical interfaces
(Ethernet, Wi-Fi, etc.).
* Add support for CLAT (464XLAT) using a BPF program.
* Change the default value of the ipv4.dhcp-ipv6-only-preferred property
to a new value "auto" which automatically enables the option when CLAT
is enabled ("yes" or "auto") in the connection profile.
* WIFI connections using wpa-psk respect the setting connection.auth-retry
and only prompt for new secrets during the last authentication attempt before
failing.
* Add support for GENEVE interface.
* The DHCPv4 internal client now ignores option 3 (Router) if the lease
contains option 121 (Classless Static Route), as recommended by RFC 3442.
* Allow persisting the managed state across reboots from nmcli and the D-Bus API.
* Allow changing the device's administrative state in the kernel at the same
time as a change to the managed state from nmcli and the D-Bus API.
* Allow configuring all bond options in nmtui by introducing a
"other options" field, which covers options not already covered by a
dedicated input field.
=============================================
NetworkManager-1.56
Overview of changes since NetworkManager-1.54
=============================================
* nmcli now supports viewing and managing WireGuard peers.
* Support reapplying the "sriov.vfs" property as long as * Support reapplying the "sriov.vfs" property as long as
"sriov.total-vfs" is not changed. "sriov.total-vfs" is not changed.
* Support configuring the HSR protocol version via the * Support reapplying "bond-port.vlans".
"hsr.protocol-version" property. * Accept hostnames longer than 64 characters from DNS lookup.
* Support configuring the HSR interlink port via the
"hsr.interlink" property.
===============================================
NetworkManager-1.54.1
Overview of changes since NetworkManager-1.54.0
===============================================
* Make that global-dns configuration overwrites DNS searches and * Make that global-dns configuration overwrites DNS searches and
options from connections, instead of merging all together. options from connections, instead of merging all together.
* Add support for a new rd.net.dhcp.client-id option in * Add support for a new rd.net.dhcp.client-id option in
nm-initrd-generator. nm-initrd-generator.
* Minor bug fixes. * Add gsm device-uid setting to restrict the devices the connection applies to.
* Support configuring the HSR protocol version via the
"hsr.protocol-version" property.
* Fix a bug that makes broadband connections auto-connect getting
blocked if the connection tries to reconnect when modem status is
"disconnecting" / "disconnected".
* Treat modem connection not having an operator code available
as a recoverable error.
* Add support for configuring systemd-resolved's DNSSEC option
per-connection via the "connection.dnssec" connection property.
* Support configuring the HSR interlink port via the
"hsr.interlink" property.
* Fix some connection properties not being applied to vpn connections
(connection.mdns, connection.llmnr, connection.dns-over-tls,
connection.mptcp-flags, ipv6.ip6-privacy)
* Update n-acd to always compile with eBPF enabled, as support
for eBPF is now detected at run time.
* Add new MPTCP 'laminar' endpoint type, and set it by default alongside
the 'subflow' one.
============================================= =============================================
NetworkManager-1.54 NetworkManager-1.54

View file

@ -239,6 +239,15 @@
/* Whether we build with OVS plugin */ /* Whether we build with OVS plugin */
#mesondefine WITH_OPENVSWITCH #mesondefine WITH_OPENVSWITCH
/* Whether we build with team support */
#mesondefine WITH_TEAMDCTL
/* Whether we build with Wi-Fi support */
#mesondefine WITH_WIFI
/* Whether we build with WWAN support */
#mesondefine WITH_WWAN
/* Define if you have PPP support */ /* Define if you have PPP support */
#mesondefine WITH_PPP #mesondefine WITH_PPP
@ -285,3 +294,6 @@
/* Define to 1 if dlvsym() is available */ /* Define to 1 if dlvsym() is available */
#mesondefine HAVE_DLVSYM #mesondefine HAVE_DLVSYM
/* Define to 1 if you want CLAT support. */
#mesondefine HAVE_CLAT

View file

@ -8,6 +8,7 @@ apk add \
'alpine-sdk' \ 'alpine-sdk' \
'autoconf' \ 'autoconf' \
'bash' \ 'bash' \
'bpftool' \
'clang' \ 'clang' \
'curl-dev' \ 'curl-dev' \
'dbus' \ 'dbus' \
@ -23,6 +24,7 @@ apk add \
'iproute2' \ 'iproute2' \
'iptables' \ 'iptables' \
'jansson-dev' \ 'jansson-dev' \
'libbpf-dev' \
'libgudev-dev' \ 'libgudev-dev' \
'libndp-dev' \ 'libndp-dev' \
'libnvme-dev' \ 'libnvme-dev' \
@ -30,7 +32,6 @@ apk add \
'libpsl-dev' \ 'libpsl-dev' \
'libsoup-dev' \ 'libsoup-dev' \
'libteam-dev' \ 'libteam-dev' \
'libtool' \
'linux-headers' \ 'linux-headers' \
'meson' \ 'meson' \
'mobile-broadband-provider-info' \ 'mobile-broadband-provider-info' \

View file

@ -32,6 +32,7 @@ install_ignore_missing() {
install \ install \
\ \
bpftool \
clang \ clang \
dbus \ dbus \
dbus-x11 \ dbus-x11 \
@ -43,6 +44,7 @@ install \
iproute2 \ iproute2 \
iptables \ iptables \
libaudit-dev \ libaudit-dev \
libbpf-dev \
libcurl4-gnutls-dev \ libcurl4-gnutls-dev \
libdbus-1-dev \ libdbus-1-dev \
libgirepository1.0-dev \ libgirepository1.0-dev \
@ -62,7 +64,6 @@ install \
libreadline-dev \ libreadline-dev \
libsystemd-dev \ libsystemd-dev \
libteam-dev \ libteam-dev \
libtool \
libudev-dev \ libudev-dev \
locales \ locales \
meson \ meson \

View file

@ -49,6 +49,7 @@ install \
ModemManager-glib-devel \ ModemManager-glib-devel \
audit-libs-devel \ audit-libs-devel \
bluez-libs-devel \ bluez-libs-devel \
bpftool \
clang \ clang \
dbus-devel \ dbus-devel \
dbus-x11 \ dbus-x11 \
@ -64,11 +65,11 @@ install \
iptables \ iptables \
jansson-devel \ jansson-devel \
jq \ jq \
libbpf-devel \
libcurl-devel \ libcurl-devel \
libndp-devel \ libndp-devel \
libnvme-devel \ libnvme-devel \
libselinux-devel \ libselinux-devel \
libtool \
libuuid-devel \ libuuid-devel \
meson \ meson \
mobile-broadband-provider-info-devel \ mobile-broadband-provider-info-devel \

View file

@ -6,18 +6,23 @@
# #
# Note that it contains __PLACEHOLDERS__ that will be replaced by the accompanying 'build.sh' script. # Note that it contains __PLACEHOLDERS__ that will be replaced by the accompanying 'build.sh' script.
Name: NetworkManager
Summary: Network connection manager and user applications
License: GPL-2.0-or-later AND LGPL-2.1-or-later
URL: https://networkmanager.dev/
Group: System Environment/Base
Epoch: 1
Version: __VERSION__
Release: __RELEASE_VERSION__%{?dist}
###############################################################################
%global wpa_supplicant_version 1:1.1 %global wpa_supplicant_version 1:1.1
%global ppp_version %(pkg-config --modversion pppd 2>/dev/null || sed -n 's/^#define\\s*VERSION\\s*"\\([^\\s]*\\)"$/\\1/p' %{_includedir}/pppd/patchlevel.h 2>/dev/null | grep . || echo bad) %global ppp_version %(pkg-config --modversion pppd 2>/dev/null || sed -n 's/^#define\\s*VERSION\\s*"\\([^\\s]*\\)"$/\\1/p' %{_includedir}/pppd/patchlevel.h 2>/dev/null | grep . || echo bad)
%global glib2_version %(pkg-config --modversion glib-2.0 2>/dev/null || echo bad) %global glib2_version %(pkg-config --modversion glib-2.0 2>/dev/null || echo bad)
%global epoch_version 1
%global real_version __VERSION__
%global rpm_version %{real_version}
%global release_version __RELEASE_VERSION__
%global snapshot __SNAPSHOT__
%global git_sha __COMMIT__
%global bcond_default_debug __BCOND_DEFAULT_DEBUG__ %global bcond_default_debug __BCOND_DEFAULT_DEBUG__
%global bcond_default_lto __BCOND_DEFAULT_LTO__ %global bcond_default_lto __BCOND_DEFAULT_LTO__
%global bcond_default_test __BCOND_DEFAULT_TEST__ %global bcond_default_test __BCOND_DEFAULT_TEST__
@ -32,17 +37,6 @@
%global _hardened_build 1 %global _hardened_build 1
%if "x%{?snapshot}" != "x"
%global snapshot_dot .%{snapshot}
%endif
%if "x%{?git_sha}" != "x"
%global git_sha_dot .%{git_sha}
%endif
%global snap %{?snapshot_dot}%{?git_sha_dot}
%global real_version_major %(printf '%s' '%{real_version}' | sed -n 's/^\\([1-9][0-9]*\\.[0-9][0-9]*\\)\\.[0-9][0-9]*$/\\1/p')
%global systemd_units NetworkManager.service NetworkManager-wait-online.service NetworkManager-dispatcher.service nm-priv-helper.service %global systemd_units NetworkManager.service NetworkManager-wait-online.service NetworkManager-dispatcher.service nm-priv-helper.service
%global systemd_units_cloud_setup nm-cloud-setup.service nm-cloud-setup.timer %global systemd_units_cloud_setup nm-cloud-setup.service nm-cloud-setup.timer
@ -106,7 +100,13 @@
%else %else
%bcond_without iwd %bcond_without iwd
%endif %endif
%bcond_without polkit_noauth_group
%ifarch %{ix86}
# there is no bpftool in i686
%bcond_with clat
%else
%bcond_without clat
%endif
############################################################################### ###############################################################################
%global dbus_version 1.9.18 %global dbus_version 1.9.18
@ -153,17 +153,6 @@
%bcond_with ifcfg_migrate %bcond_with ifcfg_migrate
%endif %endif
%if 0%{?fedora}
# Although eBPF would be available on Fedora's kernel, it seems
# we often get SELinux denials (rh#1651654). But even aside them,
# bpf(BPF_MAP_CREATE, ...) randomly fails with EPERM. That might
# be related to `ulimit -l`. Anyway, this is not usable at the
# moment.
%global ebpf_enabled "no"
%else
%global ebpf_enabled "no"
%endif
# Fedora 33 enables LTO by default by setting CFLAGS="-flto -ffat-lto-objects". # Fedora 33 enables LTO by default by setting CFLAGS="-flto -ffat-lto-objects".
# However, we also require "-flto -flto-partition=none", so disable Fedora's # However, we also require "-flto -flto-partition=none", so disable Fedora's
# default and use our configure option --with-lto instead. # default and use our configure option --with-lto instead.
@ -171,16 +160,7 @@
############################################################################### ###############################################################################
Name: NetworkManager #Source: https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/releases/%{version_no_tilde}/downloads/%{name}-%{version_no_tilde}.tar.xz
Summary: Network connection manager and user applications
Epoch: %{epoch_version}
Version: %{rpm_version}
Release: %{release_version}%{?snap}%{?dist}
Group: System Environment/Base
License: GPL-2.0-or-later AND LGPL-2.1-or-later
URL: https://networkmanager.dev/
#Source: https://download.gnome.org/sources/NetworkManager/%{real_version_major}/%{name}-%{real_version}.tar.xz
Source: __SOURCE1__ Source: __SOURCE1__
Source1: NetworkManager.conf Source1: NetworkManager.conf
Source2: 00-server.conf Source2: 00-server.conf
@ -194,17 +174,16 @@ Source9: readme-ifcfg-rh-migrated.txt
#Patch1: 0001-some.patch #Patch1: 0001-some.patch
Requires(post): systemd Requires(post): systemd
Requires(post): systemd-udev
Requires(post): /usr/sbin/update-alternatives
Requires(preun): systemd Requires(preun): systemd
Requires(preun): /usr/sbin/update-alternatives
Requires(postun): systemd Requires(postun): systemd
Requires: dbus >= %{dbus_version} Requires: dbus >= %{dbus_version}
Requires: glib2 >= %{glib2_version} Requires: glib2 >= %{glib2_version}
Requires: %{name}-libnm%{?_isa} = %{epoch}:%{version}-%{release} Requires: %{name}-libnm%{?_isa} = %{epoch}:%{version}-%{release}
Recommends: iputils %if %{with clat}
Requires: libbpf
%endif
%if 0%{?rhel} == 8 %if 0%{?rhel} == 8
# Older libndp versions use select() (rh#1933041). On well known distros, # Older libndp versions use select() (rh#1933041). On well known distros,
@ -253,7 +232,7 @@ Conflicts: NetworkManager-dispatcher-routing-rules <= 1:1.47.5-3
%endif %endif
BuildRequires: gcc BuildRequires: gcc
BuildRequires: libtool BuildRequires: clang
BuildRequires: pkgconfig BuildRequires: pkgconfig
BuildRequires: meson BuildRequires: meson
BuildRequires: gettext-devel >= 0.19.8 BuildRequires: gettext-devel >= 0.19.8
@ -308,6 +287,10 @@ BuildRequires: firewalld-filesystem
BuildRequires: iproute BuildRequires: iproute
BuildRequires: iproute-tc BuildRequires: iproute-tc
BuildRequires: libnvme-devel >= 1.5 BuildRequires: libnvme-devel >= 1.5
%if %{with clat}
BuildRequires: libbpf-devel
BuildRequires: bpftool
%endif
Provides: %{name}-dispatcher%{?_isa} = %{epoch}:%{version}-%{release} Provides: %{name}-dispatcher%{?_isa} = %{epoch}:%{version}-%{release}
@ -576,6 +559,8 @@ Group: System Environment/Base
BuildArch: noarch BuildArch: noarch
Requires: NetworkManager Requires: NetworkManager
Requires: /usr/bin/nmcli Requires: /usr/bin/nmcli
Requires(post): /usr/sbin/update-alternatives
Requires(preun): /usr/sbin/update-alternatives
Obsoletes: NetworkManager < %{obsoletes_initscripts_updown} Obsoletes: NetworkManager < %{obsoletes_initscripts_updown}
%description initscripts-updown %description initscripts-updown
@ -586,7 +571,7 @@ Preferably use nmcli instead.
%prep %prep
%autosetup -p1 -n NetworkManager-%{real_version} %autosetup -p1 -n NetworkManager-%{version_no_tilde}
%build %build
@ -627,19 +612,20 @@ Preferably use nmcli instead.
%endif %endif
%if %{with wifi} %if %{with wifi}
-Dwifi=true \ -Dwifi=true \
%if 0%{?fedora}
-Dwext=true \
%else
-Dwext=false \
%endif
%else %else
-Dwifi=false \ -Dwifi=false \
%endif %endif
-Dwext=false \
%if %{with iwd} %if %{with iwd}
-Diwd=true \ -Diwd=true \
%else %else
-Diwd=false \ -Diwd=false \
%endif %endif
%if %{with clat}
-Dclat=true \
%else
-Dclat=false \
%endif
%if %{with bluetooth} %if %{with bluetooth}
-Dbluez5_dun=true \ -Dbluez5_dun=true \
%else %else
@ -676,21 +662,19 @@ Preferably use nmcli instead.
-Dselinux=true \ -Dselinux=true \
-Dpolkit=true \ -Dpolkit=true \
-Dconfig_auth_polkit_default=true \ -Dconfig_auth_polkit_default=true \
-Dmodify_system=true \ %if %{with polkit_noauth_group}
-Dpolkit_noauth_group=wheel \
%endif
-Dconcheck=true \ -Dconcheck=true \
%if 0%{?fedora} %if 0%{?fedora}
-Dlibpsl=true \ -Dlibpsl=true \
%else %else
-Dlibpsl=false \ -Dlibpsl=false \
%endif
%if %{ebpf_enabled} != "yes"
-Debpf=false \
%else
-Debpf=true \
%endif %endif
-Dsession_tracking=systemd \ -Dsession_tracking=systemd \
-Dsuspend_resume=systemd \ -Dsuspend_resume=systemd \
-Dsystemdsystemunitdir=%{_unitdir} \ -Dsystemdsystemunitdir=%{_unitdir} \
-Dsystemdsystemgeneratordir=%{_systemdgeneratordir} \
-Dsystem_ca_path=/etc/pki/ca-trust/extracted/pem/tls-ca-bundle.pem \ -Dsystem_ca_path=/etc/pki/ca-trust/extracted/pem/tls-ca-bundle.pem \
-Ddbus_conf_dir=%{dbus_sys_dir} \ -Ddbus_conf_dir=%{dbus_sys_dir} \
-Dtests=yes \ -Dtests=yes \
@ -763,6 +747,7 @@ rm -f %{buildroot}%{_libdir}/pppd/%{ppp_version}/*.la
rm -f %{buildroot}%{nmplugindir}/*.la rm -f %{buildroot}%{nmplugindir}/*.la
# Don't use the *-initrd.service files yet, wait dracut to support them # Don't use the *-initrd.service files yet, wait dracut to support them
rm -f %{buildroot}%{_systemdgeneratordir}/nm-initrd-generator.sh
rm -f %{buildroot}%{_unitdir}/NetworkManager-config-initrd.service rm -f %{buildroot}%{_unitdir}/NetworkManager-config-initrd.service
rm -f %{buildroot}%{_unitdir}/NetworkManager-initrd.service rm -f %{buildroot}%{_unitdir}/NetworkManager-initrd.service
rm -f %{buildroot}%{_unitdir}/NetworkManager-wait-online-initrd.service rm -f %{buildroot}%{_unitdir}/NetworkManager-wait-online-initrd.service
@ -771,8 +756,8 @@ rm -f %{buildroot}%{_unitdir}/NetworkManager-wait-online-initrd.service
find %{buildroot}%{_datadir}/gtk-doc -exec touch --reference meson.build '{}' \+ find %{buildroot}%{_datadir}/gtk-doc -exec touch --reference meson.build '{}' \+
%if 0%{?__debug_package} && ! 0%{?flatpak} %if 0%{?__debug_package} && ! 0%{?flatpak}
mkdir -p %{buildroot}%{_prefix}/src/debug/NetworkManager-%{real_version} mkdir -p %{buildroot}%{_prefix}/src/debug/NetworkManager-%{version_no_tilde}
cp valgrind.suppressions %{buildroot}%{_prefix}/src/debug/NetworkManager-%{real_version} cp valgrind.suppressions %{buildroot}%{_prefix}/src/debug/NetworkManager-%{version_no_tilde}
%endif %endif
%if %{with ifcfg_rh} %if %{with ifcfg_rh}
@ -854,8 +839,12 @@ fi
%postun %postun
# skip triggering if udevd isn't even accessible, e.g. containers or
# rpm-ostree-based systems
if [ -S /run/udev/control ]; then
/usr/bin/udevadm control --reload-rules || : /usr/bin/udevadm control --reload-rules || :
/usr/bin/udevadm trigger --subsystem-match=net || : /usr/bin/udevadm trigger --subsystem-match=net || :
fi
%firewalld_reload %firewalld_reload
%systemd_postun %{systemd_units} %systemd_postun %{systemd_units}
@ -896,6 +885,7 @@ fi
%{_libexecdir}/nm-dispatcher %{_libexecdir}/nm-dispatcher
%{_libexecdir}/nm-initrd-generator %{_libexecdir}/nm-initrd-generator
%{_libexecdir}/nm-daemon-helper %{_libexecdir}/nm-daemon-helper
%{_libexecdir}/nm-libnm-helper
%{_libexecdir}/nm-priv-helper %{_libexecdir}/nm-priv-helper
%dir %{_libdir}/%{name} %dir %{_libdir}/%{name}
%dir %{nmplugindir} %dir %{nmplugindir}
@ -927,6 +917,9 @@ fi
%{_datadir}/dbus-1/system-services/org.freedesktop.nm_dispatcher.service %{_datadir}/dbus-1/system-services/org.freedesktop.nm_dispatcher.service
%{_datadir}/dbus-1/system-services/org.freedesktop.nm_priv_helper.service %{_datadir}/dbus-1/system-services/org.freedesktop.nm_priv_helper.service
%{_datadir}/polkit-1/actions/*.policy %{_datadir}/polkit-1/actions/*.policy
%if %{with polkit_noauth_group}
%{_datadir}/polkit-1/rules.d/org.freedesktop.NetworkManager.rules
%endif
%{_prefix}/lib/udev/rules.d/*.rules %{_prefix}/lib/udev/rules.d/*.rules
%{_prefix}/lib/firewalld/zones/nm-shared.xml %{_prefix}/lib/firewalld/zones/nm-shared.xml
# systemd stuff # systemd stuff

View file

@ -110,7 +110,6 @@ exec 2>&1
UUID=`uuidgen` UUID=`uuidgen`
RELEASE_VERSION="${RELEASE_VERSION:-$(git rev-list HEAD | wc -l)}" RELEASE_VERSION="${RELEASE_VERSION:-$(git rev-list HEAD | wc -l)}"
SNAPSHOT="${SNAPSHOT:-%{nil\}}"
VERSION="${VERSION:-$(get_version || die "Could not read $VERSION")}" VERSION="${VERSION:-$(get_version || die "Could not read $VERSION")}"
COMMIT_FULL="${COMMIT_FULL:-$(git rev-parse --verify HEAD || die "Error reading HEAD revision")}" COMMIT_FULL="${COMMIT_FULL:-$(git rev-parse --verify HEAD || die "Error reading HEAD revision")}"
COMMIT="${COMMIT:-$(printf '%s' "$COMMIT_FULL" | sed 's/^\(.\{10\}\).*/\1/' || die "Error reading HEAD revision")}" COMMIT="${COMMIT:-$(printf '%s' "$COMMIT_FULL" | sed 's/^\(.\{10\}\).*/\1/' || die "Error reading HEAD revision")}"
@ -206,12 +205,8 @@ cp "$SOURCE_README_IFCFG_MIGRATED" "$TEMP/SOURCES/readme-ifcfg-rh-migrated.txt"
write_changelog write_changelog
sed -e "s/__VERSION__/$VERSION/g" \ sed -e "s/__VERSION__/${VERSION/-/\~}/g" \
-e "s/__RELEASE_VERSION__/$RELEASE_VERSION/g" \ -e "s/__RELEASE_VERSION__/$RELEASE_VERSION/g" \
-e "s/__SNAPSHOT__/$SNAPSHOT/g" \
-e "s/__COMMIT__/$COMMIT/g" \
-e "s/__COMMIT_FULL__/$COMMIT_FULL/g" \
-e "s/__SNAPSHOT__/$SNAPSHOT/g" \
-e "s/__SOURCE1__/$(basename "$SOURCE")/g" \ -e "s/__SOURCE1__/$(basename "$SOURCE")/g" \
-e "s/__BCOND_DEFAULT_DEBUG__/$BCOND_DEFAULT_DEBUG/g" \ -e "s/__BCOND_DEFAULT_DEBUG__/$BCOND_DEFAULT_DEBUG/g" \
-e "s/__BCOND_DEFAULT_LTO__/${BCOND_DEFAULT_LTO:-"%{nil}"}/g" \ -e "s/__BCOND_DEFAULT_LTO__/${BCOND_DEFAULT_LTO:-"%{nil}"}/g" \
@ -232,7 +227,12 @@ case "$BUILDTYPE" in
;; ;;
esac esac
rpmbuild --define "_topdir $TEMP" $RPM_BUILD_OPTION "$TEMPSPEC" $NM_RPMBUILD_ARGS || die "ERROR: rpmbuild FAILED" DIST=
[[ "$COMMIT" != "" ]] && DIST=".${COMMIT}${DIST}"
[[ "$SNAPSHOT" != "" ]] && DIST=".${SNAPSHOT}${DIST}"
[[ "$DIST" != "" ]] && DIST=("--define" "dist ${DIST}$(rpmbuild --eval '%{dist}')")
rpmbuild --define "_topdir $TEMP" "${DIST[@]}" $RPM_BUILD_OPTION "$TEMPSPEC" $NM_RPMBUILD_ARGS || die "ERROR: rpmbuild FAILED"
LS_EXTRA=() LS_EXTRA=()

View file

@ -155,7 +155,6 @@ P_CRYPTO="${CRYPTO-}"
P_DBUS_SYS_DIR="${DBUS_SYS_DIR-}" P_DBUS_SYS_DIR="${DBUS_SYS_DIR-}"
P_DHCP_DEFAULT="${DHCP_DEFAULT-}" P_DHCP_DEFAULT="${DHCP_DEFAULT-}"
P_DNS_RC_MANAGER_DEFAULT="${DNS_RC_MANAGER_DEFAULT-}" P_DNS_RC_MANAGER_DEFAULT="${DNS_RC_MANAGER_DEFAULT-}"
P_EBPF_ENABLED="${EBPF_ENABLED-no}"
P_FIREWALLD_ZONE="${FIREWALLD_ZONE-}" P_FIREWALLD_ZONE="${FIREWALLD_ZONE-}"
P_IWD="${IWD-}" P_IWD="${IWD-}"
P_LOGGING_BACKEND_DEFAULT="${LOGGING_BACKEND_DEFAULT-}" P_LOGGING_BACKEND_DEFAULT="${LOGGING_BACKEND_DEFAULT-}"
@ -174,6 +173,7 @@ P_WIFI="${WIFI-1}"
P_WWAN="${WWAN-1}" P_WWAN="${WWAN-1}"
P_TEAM="${TEAM-1}" P_TEAM="${TEAM-1}"
P_BLUETOOTH="${BLUETOOTH-1}" P_BLUETOOTH="${BLUETOOTH-1}"
P_IFCFG_RH="${IFCFG_RH-0}"
P_NMTUI="${NMTUI-1}" P_NMTUI="${NMTUI-1}"
P_NM_CLOUD_SETUP="${NM_CLOUD_SETUP-1}" P_NM_CLOUD_SETUP="${NM_CLOUD_SETUP-1}"
P_OVS="${OVS-1}" P_OVS="${OVS-1}"
@ -203,7 +203,7 @@ if [ -z "$P_FEDORA" -a -z "$P_RHEL" ] ; then
P_FEDORA="$x" P_FEDORA="$x"
P_RHEL=0 P_RHEL=0
else else
x="$(grep -q "ID=fedora" /etc/os-release && sed -n 's/VERSION_ID=//p' /etc/os-release)" x="$(grep -q 'ID="rhel"' /etc/os-release && sed -n 's/^VERSION_ID="*\([0-9]*\).*/\1/p' /etc/os-release)"
if test "$x" -gt 0 ; then if test "$x" -gt 0 ; then
P_FEDORA=0 P_FEDORA=0
P_RHEL="$x" P_RHEL="$x"
@ -294,6 +294,14 @@ if [ -z "$P_MODEM_MANAGER_1" ] ; then
fi fi
fi fi
if [ -z "$TEAM" ] && [ "${P_RHEL-0}" -ge 10 ] ; then
P_TEAM=0
fi
if [ -z "$IFCFG_RH" ] && [ -n "$P_RHEL" ] && [ "$P_RHEL" -le 9 ] ; then
P_IFCFG_RH=1
fi
if bool "$P_DEBUG" ; then if bool "$P_DEBUG" ; then
P_CFLAGS="-g -Og -fexceptions${P_CFLAGS:+ }$P_CFLAGS" P_CFLAGS="-g -Og -fexceptions${P_CFLAGS:+ }$P_CFLAGS"
else else
@ -379,7 +387,7 @@ meson setup\
-Db_lto="$(bool_true "$P_LTO")" \ -Db_lto="$(bool_true "$P_LTO")" \
-Dlibaudit=yes-disabled-by-default \ -Dlibaudit=yes-disabled-by-default \
-Dmodem_manager="$(bool_true "$P_MODEM_MANAGER_1")" \ -Dmodem_manager="$(bool_true "$P_MODEM_MANAGER_1")" \
$(args_enable "$P_WIFI" -Dwifi=true -Dwext="$(bool_true "$P_FEDORA")") \ $(args_enable "$P_WIFI" -Dwifi=true -Dwext=false) \
$(args_enable "$(bool_not_true "$P_WIFI")" -Dwifi=false ) \ $(args_enable "$(bool_not_true "$P_WIFI")" -Dwifi=false ) \
-Diwd="$(bool_true "$P_IWD")" \ -Diwd="$(bool_true "$P_IWD")" \
-Dbluez5_dun="$(bool_true "$P_BLUETOOTH")" \ -Dbluez5_dun="$(bool_true "$P_BLUETOOTH")" \
@ -393,18 +401,17 @@ meson setup\
-Dselinux=true \ -Dselinux=true \
-Dpolkit=true \ -Dpolkit=true \
-Dconfig_auth_polkit_default=true \ -Dconfig_auth_polkit_default=true \
-Dmodify_system=true \
-Dconcheck=true \ -Dconcheck=true \
-Dlibpsl="$(bool_true "$P_FEDORA")" \ -Dlibpsl="$(bool_true "$P_FEDORA")" \
-Debpf="$(bool_true "$P_EBPF_ENABLED")" \
-Dsession_tracking=systemd \ -Dsession_tracking=systemd \
-Dsuspend_resume=systemd \ -Dsuspend_resume=systemd \
-Dsystemdsystemunitdir=/usr/lib/systemd/system \ -Dsystemdsystemunitdir=/usr/lib/systemd/system \
-Dsystemdsystemgeneratordir=/usr/lib/systemd/system-generators \
-Dsystem_ca_path=/etc/pki/tls/cert.pem \ -Dsystem_ca_path=/etc/pki/tls/cert.pem \
-Ddbus_conf_dir="$P_DBUS_SYS_DIR" \ -Ddbus_conf_dir="$P_DBUS_SYS_DIR" \
-Dtests=yes \ -Dtests=yes \
-Dvalgrind=no \ -Dvalgrind=no \
-Difcfg_rh=true \ -Difcfg_rh="$(bool_true "$P_IFCFG_RH")" \
-Difupdown=false \ -Difupdown=false \
$(args_enable "$P_PPP" -Dppp=true -Dpppd="$D_SBINDIR/pppd" -Dpppd_plugin_dir="$D_LIBDIR/pppd/$P_PPP_VERSION") \ $(args_enable "$P_PPP" -Dppp=true -Dpppd="$D_SBINDIR/pppd" -Dpppd_plugin_dir="$D_LIBDIR/pppd/$P_PPP_VERSION") \
$(args_enable "$(bool_not_true "$P_PPP")" -Dppp=false ) \ $(args_enable "$(bool_not_true "$P_PPP")" -Dppp=false ) \

View file

@ -27,7 +27,7 @@
# * Run in a "clean" environment, i.e. no unusual environment variables set, on a recent # * Run in a "clean" environment, i.e. no unusual environment variables set, on a recent
# Fedora, with suitable dependencies installed. # Fedora, with suitable dependencies installed.
# #
# * First, ensure that you have a valid Gitlab's private token for gitlab.freedestkop.org # * First, ensure that you have a valid Gitlab's private token for gitlab.freedesktop.org
# stored in ~/.config/nm-release-token, or pass one with --gitlab-token argument. # stored in ~/.config/nm-release-token, or pass one with --gitlab-token argument.
# Also, ensure you have a GPG key that you want to use for signing. Also, have gpg-agent running # Also, ensure you have a GPG key that you want to use for signing. Also, have gpg-agent running
# and possibly configure `git config --get user.signingkey` for the proper key. # and possibly configure `git config --get user.signingkey` for the proper key.
@ -102,14 +102,8 @@ do_command() {
SCRIPTDIR="$(dirname "$(readlink -f "$0")")" SCRIPTDIR="$(dirname "$(readlink -f "$0")")"
GITDIR="$(cd "$SCRIPTDIR" && git rev-parse --show-toplevel || die "Could not get GITDIR")" GITDIR="$(cd "$SCRIPTDIR" && git rev-parse --show-toplevel || die "Could not get GITDIR")"
parse_version() { get_version() {
local VERSION=$(grep -E -m1 '^\s+version:' "$GITDIR/meson.build" \ grep -E -m1 '^\s+version:' "$GITDIR/meson.build" | cut -d"'" -f2
| cut -d"'" -f2 \
| sed 's/\./ /g')
re='^(0|[1-9][0-9]*) (0|[1-9][0-9]*) (0|[1-9][0-9]*)$'
[[ "$VERSION" =~ $re ]] || return 1
echo "$VERSION"
} }
number_is_even() { number_is_even() {
@ -155,14 +149,12 @@ check_gitlab_pipeline() {
set_version_number() { set_version_number() {
sed -i \ sed -i \
-e '1,20 s/^\( *version: *'\''\)[0-9]\+\.[0-9]\+\.[0-9]\+\('\'',\)$/\1'"$1.$2.$3"'\2/' \ -E "1,20 s/^( *version: *')[^']+(',) *\$/\1$1\2/" \
meson.build meson.build
} }
check_news() { check_news() {
local mode="$1" local mode="$1"
shift
local ver_arr=("$@")
case "$mode" in case "$mode" in
major|minor) major|minor)
@ -259,12 +251,18 @@ done
[ -n "$RELEASE_MODE" ] || die_usage "specify the desired release mode" [ -n "$RELEASE_MODE" ] || die_usage "specify the desired release mode"
VERSION_ARR=( $(parse_version) ) || die "cannot detect NetworkManager version" VERSION_STR="$(get_version)"
VERSION_STR="$(IFS=.; echo "${VERSION_ARR[*]}")" VERSION_ARR=( $(echo "$VERSION_STR" | sed 's/[\.\-]/ /g') )
if [[ ${VERSION_ARR[2]} =~ ^rc ]]; then
RC_VERSION=${VERSION_ARR[2]#rc}
VERSION_ARR[2]=0
else
RC_VERSION=
fi
echo "Current version before release: $VERSION_STR (do \"$RELEASE_MODE\" release)" echo "Current version before release: $VERSION_STR (do \"$RELEASE_MODE\" release)"
grep -q "version: '${VERSION_ARR[0]}.${VERSION_ARR[1]}.${VERSION_ARR[2]}'," ./meson.build || die "meson.build does not have expected version" grep -q "version: '$VERSION_STR'," ./meson.build || die "meson.build does not have expected version"
TMP="$(git status --porcelain)" || die "git status failed" TMP="$(git status --porcelain)" || die "git status failed"
test -z "$TMP" || die "git working directory is not clean (git status --porcelain)" test -z "$TMP" || die "git working directory is not clean (git status --porcelain)"
@ -280,50 +278,41 @@ if [ "$CUR_BRANCH" = main ]; then
number_is_odd "${VERSION_ARR[1]}" || die "Unexpected version number on main. Should be an odd development version" number_is_odd "${VERSION_ARR[1]}" || die "Unexpected version number on main. Should be an odd development version"
[ "$RELEASE_MODE" = devel -o "$RELEASE_MODE" = rc1 -o "$RELEASE_MODE" = major-post ] || die "Unexpected branch name \"$CUR_BRANCH\" for \"$RELEASE_MODE\"" [ "$RELEASE_MODE" = devel -o "$RELEASE_MODE" = rc1 -o "$RELEASE_MODE" = major-post ] || die "Unexpected branch name \"$CUR_BRANCH\" for \"$RELEASE_MODE\""
else else
re='^nm-[0-9]+-[0-9]+$'
[[ "$CUR_BRANCH" =~ $re ]] || die "Unexpected current branch $CUR_BRANCH. Should be main or nm-?-??"
if number_is_odd "${VERSION_ARR[1]}"; then
# we are on a release candiate branch.
[ "$RELEASE_MODE" = rc -o "$RELEASE_MODE" = major ] || die "Unexpected branch name \"$CUR_BRANCH\" for \"$RELEASE_MODE\""
[ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))" ] || die "Unexpected current branch $CUR_BRANCH. Should be nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))"
else
[ "$RELEASE_MODE" = minor ] || die "Unexpected branch name \"$CUR_BRANCH\" for \"$RELEASE_MODE\""
[ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}" ] || die "Unexpected current branch $CUR_BRANCH. Should be nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}" [ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}" ] || die "Unexpected current branch $CUR_BRANCH. Should be nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}"
fi [ "$RELEASE_MODE" = rc -o "$RELEASE_MODE" = major -o "$RELEASE_MODE" = minor ] || die "Unexpected branch name \"$CUR_BRANCH\" for \"$RELEASE_MODE\""
fi fi
RC_VERSION=
RELEASE_BRANCH= RELEASE_BRANCH=
case "$RELEASE_MODE" in case "$RELEASE_MODE" in
minor) minor)
number_is_even "${VERSION_ARR[1]}" || die "cannot do minor release on top of version $VERSION_STR" number_is_even "${VERSION_ARR[1]}" || die "cannot do minor release on top of version $VERSION_STR"
[ "$CUR_BRANCH" != main ] || die "cannot do a minor release on main" [ "$RC_VERSION" = "" ] || die "cannot do a minor release on top of an RC version"
[ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}" ] || die "minor release can only be on \"nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}\" branch"
;; ;;
devel) devel)
number_is_odd "${VERSION_ARR[1]}" || die "cannot do devel release on top of version $VERSION_STR" number_is_odd "${VERSION_ARR[1]}" || die "cannot do devel release on top of version $VERSION_STR"
[ "$((${VERSION_ARR[2]} + 1))" -lt 90 ] || die "devel release must have a micro version smaller than 90 but current version is $VERSION_STR" [ "$RC_VERSION" = "" ] || die "cannot do a devel release on top of an RC version"
[ "$CUR_BRANCH" == main ] || die "devel release can only be on main" [ "$CUR_BRANCH" == main ] || die "devel release can only be on main"
;; ;;
rc)
number_is_odd "${VERSION_ARR[1]}" || die "cannot do rc release on top of version $VERSION_STR"
[ "${VERSION_ARR[2]}" -ge 90 ] || die "rc release must have a micro version larger than ${VERSION_ARR[0]}.90 but current version is $VERSION_STR"
RC_VERSION="$((${VERSION_ARR[2]} - 88))"
[ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))" ] || die "devel release can only be on \"nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))\" branch"
;;
rc1) rc1)
number_is_odd "${VERSION_ARR[1]}" || die "cannot do rc release on top of version $VERSION_STR" number_is_odd "${VERSION_ARR[1]}" || die "cannot do rc release on top of version $VERSION_STR"
[ "${VERSION_ARR[2]}" -lt 90 ] || die "rc release must have a micro version smaller than ${VERSION_ARR[0]}.${VERSION_ARR[1]}.90 but current version is $VERSION_STR" [ "$RC_VERSION" = "" ] || die "rc1 release cannot be done on top of an RC version"
[ "$CUR_BRANCH" == main ] || die "rc1 release can only be on main" [ "$CUR_BRANCH" == main ] || die "rc1 release can only be on main"
RELEASE_BRANCH="nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))" RELEASE_BRANCH="nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))"
;; ;;
rc)
number_is_even "${VERSION_ARR[1]}" || die "cannot do rc release on top of version $VERSION_STR"
[ "$RC_VERSION" != "" ] || die "rc release must be done on top of an RC version"
[ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}" ] || die "rc release can only be on \"nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}\" branch"
;;
major) major)
number_is_odd "${VERSION_ARR[1]}" || die "cannot do major release on top of version $VERSION_STR" number_is_even "${VERSION_ARR[1]}" || die "cannot do major release on top of version $VERSION_STR"
[ "${VERSION_ARR[2]}" -ge 90 ] || die "parent version for major release must have a micro version larger than ${VERSION_ARR[0]}.90 but current version is $VERSION_STR" [ "$RC_VERSION" != "" ] || die "major release must be done on top of an RC version"
[ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))" ] || die "major release can only be on \"nm-${VERSION_ARR[0]}-$((${VERSION_ARR[1]} + 1))\" branch" [ "$CUR_BRANCH" == "nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}" ] || die "major release can only be on \"nm-${VERSION_ARR[0]}-${VERSION_ARR[1]}\" branch"
;; ;;
major-post) major-post)
number_is_odd "${VERSION_ARR[1]}" || die "cannot do major-post release on top of version $VERSION_STR" number_is_odd "${VERSION_ARR[1]}" || die "cannot do major-post release on top of version $VERSION_STR"
[ "$((${VERSION_ARR[2]} + 1))" -lt 90 ] || die "major-post release must have a micro version smaller than 90 but current version is $VERSION_STR" [ "$RC_VERSION" = "" ] || die "major-post release cannot be done on top of an RC version"
[ "$CUR_BRANCH" == main ] || die "major-post release can only be on main" [ "$CUR_BRANCH" == main ] || die "major-post release can only be on main"
;; ;;
*) *)
@ -370,7 +359,7 @@ if [ "$ALLOW_LOCAL_BRANCHES" != 1 ]; then
cmp <(git show "$ORIGIN/main:contrib/fedora/rpm/release.sh") "$BASH_SOURCE_ABSOLUTE" || die "$BASH_SOURCE is not identical to \`git show \"$ORIGIN/main:contrib/fedora/rpm/release.sh\"\`" cmp <(git show "$ORIGIN/main:contrib/fedora/rpm/release.sh") "$BASH_SOURCE_ABSOLUTE" || die "$BASH_SOURCE is not identical to \`git show \"$ORIGIN/main:contrib/fedora/rpm/release.sh\"\`"
fi fi
if ! check_news "$RELEASE_MODE" "@{VERSION_ARR[@]}" ; then if ! check_news "$RELEASE_MODE"; then
if [ "$CHECK_NEWS" == 1 ]; then if [ "$CHECK_NEWS" == 1 ]; then
die "NEWS file needs update to mention stable release (skip check with --no-check-news)" die "NEWS file needs update to mention stable release (skip check with --no-check-news)"
fi fi
@ -389,7 +378,7 @@ if [ "$RELEASE_MODE" = major -o "$RELEASE_MODE" = minor ]; then
fi fi
echo "$(echo_color 36 -n "https://gitlab.freedesktop.org/NetworkManager/networkmanager.pages.freedesktop.org.git") by running" echo "$(echo_color 36 -n "https://gitlab.freedesktop.org/NetworkManager/networkmanager.pages.freedesktop.org.git") by running"
if [ "$RELEASE_MODE" = major ]; then if [ "$RELEASE_MODE" = major ]; then
v="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 1)).0" v="${VERSION_ARR[0]}.${VERSION_ARR[1]}.0"
else else
v="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$((${VERSION_ARR[2]} + 1))" v="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$((${VERSION_ARR[2]} + 1))"
fi fi
@ -418,71 +407,36 @@ if [ $CHECK_GITLAB = 1 ]; then
fi fi
fi fi
BRANCHES=() # Work on a temporary branch
BUILD_TAG=
CLEANUP_CHECKOUT_BRANCH="$CUR_BRANCH" CLEANUP_CHECKOUT_BRANCH="$CUR_BRANCH"
git checkout -B "$TMP_BRANCH" git checkout -B "$TMP_BRANCH"
CLEANUP_REFS+=("refs/heads/$TMP_BRANCH") CLEANUP_REFS+=("refs/heads/$TMP_BRANCH")
case "$RELEASE_MODE" in case "$RELEASE_MODE" in
minor) minor)
set_version_number "${VERSION_ARR[0]}" "${VERSION_ARR[1]}" $(("${VERSION_ARR[2]}" + 1)) # Version is already correct in meson.build
git commit -m "release: bump version to ${VERSION_ARR[0]}.${VERSION_ARR[1]}.$(("${VERSION_ARR[2]}" + 1))" -a || die "failed to commit release" BUILD_VERSION="$VERSION_STR"
NEXT_VERSION="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$((${VERSION_ARR[2]} + 1))"
b="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$(("${VERSION_ARR[2]}" + 1))"
git tag -s -a -m "Tag $b" "$b" HEAD || die "failed to tag release"
BRANCHES+=("$b")
CLEANUP_REFS+=("refs/tags/$b")
BUILD_TAG="$b"
TAR_VERSION="$b"
;; ;;
devel) devel)
set_version_number "${VERSION_ARR[0]}" "${VERSION_ARR[1]}" $(("${VERSION_ARR[2]}" + 1)) # Version is already correct in meson.build
git commit -m "release: bump version to ${VERSION_ARR[0]}.${VERSION_ARR[1]}.$(("${VERSION_ARR[2]}" + 1)) (development)" -a || die "failed to commit devel version bump" BUILD_VERSION="$VERSION_STR"
NEXT_VERSION="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$((${VERSION_ARR[2]} + 1))-dev"
b="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$(("${VERSION_ARR[2]}" + 1))"
git tag -s -a -m "Tag $b (development)" "$b-dev" HEAD || die "failed to tag release"
BRANCHES+=("$b-dev")
CLEANUP_REFS+=("refs/tags/$b-dev")
BUILD_TAG="$b-dev"
TAR_VERSION="$b"
;; ;;
rc) rc)
b="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$(("${VERSION_ARR[2]}" + 1))" # Version is already correct in meson.build
t="${VERSION_ARR[0]}.$(("${VERSION_ARR[1]}" + 1))-rc$RC_VERSION" BUILD_VERSION="$VERSION_STR"
set_version_number "${VERSION_ARR[0]}" "${VERSION_ARR[1]}" $(("${VERSION_ARR[2]}" + 1)) NEXT_VERSION="${VERSION_ARR[0]}.${VERSION_ARR[1]}-rc$((RC_VERSION + 1))"
git commit -m "release: bump version to $b ($t) (development)" -a || die "failed to commit rc version bump"
git tag -s -a -m "Tag $b ($t) (development)" "$t" HEAD || die "failed to tag release"
BRANCHES+=("$t")
CLEANUP_REFS+=("refs/tags/$t")
BUILD_TAG="$t"
TAR_VERSION="$b"
;; ;;
rc1) rc1)
set_version_number "${VERSION_ARR[0]}" "${VERSION_ARR[1]}" 90 # Current version is wrong (dev version), need to set rc1 version
b="${VERSION_ARR[0]}.${VERSION_ARR[1]}.90" BUILD_VERSION="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 1))-rc1"
t="${VERSION_ARR[0]}.$(("${VERSION_ARR[1]}" + 1))-rc1" NEXT_VERSION="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 1))-rc2"
git commit -m "release: bump version to $b ($t)" -a || die "failed to commit rc1 version bump"
git tag -s -a -m "Tag $b ($t) (development)" "$t" HEAD || die "failed to tag release $t"
BRANCHES+=("$t")
CLEANUP_REFS+=("refs/tags/$t")
BUILD_TAG="$t"
TAR_VERSION="$b"
;; ;;
major) major)
b="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 1)).0" # Current version is wrong (rc version), need to set major version
set_version_number "${VERSION_ARR[0]}" "$((${VERSION_ARR[1]} + 1))" 0 BUILD_VERSION="${VERSION_ARR[0]}.${VERSION_ARR[1]}.0"
git commit -m "release: bump version to $b" -a || die "failed to commit major version bump" NEXT_VERSION="${VERSION_ARR[0]}.${VERSION_ARR[1]}.1"
git tag -s -a -m "Tag $b" "$b" HEAD || die "failed to tag release"
BRANCHES+=("$b")
CLEANUP_REFS+=("refs/tags/$b")
BUILD_TAG="$b"
TAR_VERSION="$b"
;; ;;
major-post) major-post)
# We create a merge commit with the content of current "main", with two # We create a merge commit with the content of current "main", with two
@ -494,65 +448,77 @@ case "$RELEASE_MODE" in
git merge -Xours --commit -m tmp main || die "merge1" git merge -Xours --commit -m tmp main || die "merge1"
git rm --cached -r . || die "merge2" git rm --cached -r . || die "merge2"
git checkout main -- . || die "merge3" git checkout main -- . || die "merge3"
b="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$((${VERSION_ARR[2]} + 1))"
git commit --amend -m tmp -a || die "failed to commit major version bump" git commit --amend -m tmp -a || die "failed to commit major version bump"
test x = "x$(git diff main HEAD)" || die "there is a diff after merge!" test x = "x$(git diff main HEAD)" || die "there is a diff after merge!"
set_version_number "${VERSION_ARR[0]}" "${VERSION_ARR[1]}" "$((${VERSION_ARR[2]} + 1))" # Version is already correct in meson.build
git commit --amend -m "release: bump version to $b (development)" -a || die "failed to commit major version bump" BUILD_VERSION="$VERSION_STR"
git tag -s -a -m "Tag $b (development)" "$b-dev" HEAD || die "failed to tag release" NEXT_VERSION="${VERSION_ARR[0]}.${VERSION_ARR[1]}.$((${VERSION_ARR[2]} + 1))-dev"
BRANCHES+=("$b-dev")
CLEANUP_REFS+=("refs/tags/$b-dev")
BUILD_TAG="$b-dev"
TAR_VERSION="$b"
;; ;;
*) *)
die "Release mode $RELEASE_MODE not yet implemented" die "Release mode $RELEASE_MODE not yet implemented"
;; ;;
esac esac
build_tag() { build_version() {
local BUILD_TAG="$1" local CURR_VERSION="$(get_version)"
local TAR_FILE="NetworkManager-$2.tar.xz" local BUILD_VERSION="$1"
local NEXT_VERSION="$2"
local BUILD_VERSION_DESCR="${BUILD_VERSION/-dev/ (development)}"
local NEXT_VERSION_DESCR="${NEXT_VERSION/-dev/ (development)}"
local TAR_FILE="NetworkManager-$BUILD_VERSION.tar.xz"
local SUM_FILE="$TAR_FILE.sha256sum" local SUM_FILE="$TAR_FILE.sha256sum"
git checkout "$BUILD_TAG" || die "failed to checkout $BUILD_TAG" # The current version is usually already correct, except for rc1 and major. Bump version in those cases.
if [[ "$BUILD_VERSION" != "$CURR_VERSION" ]]; then
set_version_number "$BUILD_VERSION"
git commit -m "release: bump version to $BUILD_VERSION_DESCR" -a || die "failed to commit release"
fi
# Tag the release
git tag -s -a -m "Release $BUILD_VERSION_DESCR" "$BUILD_VERSION" HEAD || die "failed to tag release"
PUSH_REFS+=("$BUILD_VERSION")
CLEANUP_REFS+=("refs/tags/$BUILD_VERSION")
# Build to get the tarball for the release
./contrib/fedora/rpm/build_clean.sh -r || die "build release failed" ./contrib/fedora/rpm/build_clean.sh -r || die "build release failed"
cp "./build/meson-dist/$TAR_FILE" /tmp/ || die "failed to copy $TAR_FILE to /tmp" cp "./build/meson-dist/$TAR_FILE" /tmp/ || die "failed to copy $TAR_FILE to /tmp"
cp "./build/meson-dist/$SUM_FILE" /tmp/ || die "failed to copy $SUM_FILE to /tmp" cp "./build/meson-dist/$SUM_FILE" /tmp/ || die "failed to copy $SUM_FILE to /tmp"
git clean -fdx git clean -fdx
# Store the release version for later use
RELEASE_VERSIONS+=("$BUILD_VERSION")
# Bump to next version, so that build between now and the next release has the next version already.
# Otherwise the macros in nm_version.h don't work correctly.
set_version_number "$NEXT_VERSION"
git commit -m "release: bump version to $NEXT_VERSION_DESCR" -a || die "failed to commit version bump"
} }
RELEASE_TAR_VERSIONS=() # Build and create tarball. Bump version as needed.
RELEASE_TAGS=() PUSH_REFS=()
if [ -n "$BUILD_TAG" ]; then RELEASE_VERSIONS=()
build_tag "$BUILD_TAG" "$TAR_VERSION" build_version "$BUILD_VERSION" "$NEXT_VERSION"
RELEASE_TAR_VERSIONS+=("$TAR_VERSION")
RELEASE_TAGS+=("$BUILD_TAG")
fi
git checkout -B "$CUR_BRANCH" "$TMP_BRANCH" || die "cannot checkout $CUR_BRANCH"
BRANCHES+=( "$CUR_BRANCH" )
if [ "$RELEASE_MODE" = rc1 ]; then if [ "$RELEASE_MODE" = rc1 ]; then
git branch "$RELEASE_BRANCH" "$TMP_BRANCH" || die "cannot checkout $CUR_BRANCH" # Create the release branch (nm-1-xx)
BRANCHES+=( "$RELEASE_BRANCH" ) git branch "$RELEASE_BRANCH" "$TMP_BRANCH" || die "cannot checkout $RELEASE_BRANCH"
PUSH_REFS+=( "$RELEASE_BRANCH" )
CLEANUP_REFS+=( "refs/heads/$RELEASE_BRANCH" ) CLEANUP_REFS+=( "refs/heads/$RELEASE_BRANCH" )
git checkout "$TMP_BRANCH"
b="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 2)).0" # Go back to the commit of the rc1 release, nm-1-xx is one commit further now.
set_version_number "${VERSION_ARR[0]}" "$((${VERSION_ARR[1]} + 2))" 0 git checkout -B "$TMP_BRANCH" "$BUILD_VERSION" || die "cannot checkout $TMP_BRANCH"
git commit -m "release: bump version to $b (development)" -a || die "failed to commit devel version bump"
git tag -s -a -m "Tag $b (development)" "$b-dev" HEAD || die "failed to tag release" # Second release for rc1: create new dev version on main
BRANCHES+=("$b-dev") BUILD_VERSION="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 2)).0-dev"
CLEANUP_REFS+=("refs/tags/$b-dev") NEXT_VERSION="${VERSION_ARR[0]}.$((${VERSION_ARR[1]} + 2)).1-dev"
BUILD_TAG="$b-dev" build_version "$BUILD_VERSION" "$NEXT_VERSION"
TAR_VERSION="$b"
build_tag "$BUILD_TAG" "$TAR_VERSION"
RELEASE_TAR_VERSIONS+=("$TAR_VERSION")
RELEASE_TAGS+=("$BUILD_TAG")
git checkout -B "$CUR_BRANCH" "$TMP_BRANCH" || die "cannot checkout $CUR_BRANCH"
fi fi
# Work was done on the temporary branch, advance the real branch
git checkout -B "$CUR_BRANCH" "$TMP_BRANCH" || die "cannot checkout $CUR_BRANCH"
PUSH_REFS+=( "$CUR_BRANCH" )
if [[ $GITLAB_TOKEN == "" ]]; then if [[ $GITLAB_TOKEN == "" ]]; then
[[ -r ~/.config/nm-release-token ]] || die "cannot read ~/.config/nm-release-token" [[ -r ~/.config/nm-release-token ]] || die "cannot read ~/.config/nm-release-token"
GITLAB_TOKEN=$(< ~/.config/nm-release-token) GITLAB_TOKEN=$(< ~/.config/nm-release-token)
@ -565,20 +531,21 @@ if [ -z "$GITLAB_USER_ID" ] || [ "$GITLAB_USER_ID" = "null" ]; then
die "failed to authenticate to gitlab.freedesktop.org with the private token" die "failed to authenticate to gitlab.freedesktop.org with the private token"
fi fi
do_command git push "$ORIGIN" "${BRANCHES[@]}" || die "failed to to push branches ${BRANCHES[@]} to $ORIGIN" # Push the modified branches and tags to the origin repository
do_command git push "$ORIGIN" "${PUSH_REFS[@]}" || die "failed to to push branches ${PUSH_REFS[@]} to $ORIGIN"
# Create the releases
CREATE_RELEASE_FAIL=0 CREATE_RELEASE_FAIL=0
for I in "${!RELEASE_TAR_VERSIONS[@]}"; do for BUILD_VERSION in "${RELEASE_VERSIONS[@]}"; do
TAR_FILE="NetworkManager-${RELEASE_TAR_VERSIONS[$I]}.tar.xz" TAR_FILE="NetworkManager-$BUILD_VERSION.tar.xz"
SUM_FILE="$TAR_FILE.sha256sum" SUM_FILE="$TAR_FILE.sha256sum"
BUILD_TAG="${RELEASE_TAGS["$I"]}"
FAIL=0 FAIL=0
# upload tarball and checksum file as generic packages # upload tarball and checksum file as generic packages
for F in "$TAR_FILE" "$SUM_FILE"; do for F in "$TAR_FILE" "$SUM_FILE"; do
do_command curl --location --fail-with-body --header "PRIVATE-TOKEN: $GITLAB_TOKEN" \ do_command curl --location --fail-with-body --header "PRIVATE-TOKEN: $GITLAB_TOKEN" \
--upload-file "/tmp/$F" \ --upload-file "/tmp/$F" \
"https://gitlab.freedesktop.org/api/v4/projects/411/packages/generic/NetworkManager/$BUILD_TAG/$F" \ "https://gitlab.freedesktop.org/api/v4/projects/411/packages/generic/NetworkManager/$BUILD_VERSION/$F" \
|| FAIL=1 || FAIL=1
if [[ $FAIL = 1 ]]; then if [[ $FAIL = 1 ]]; then
@ -595,25 +562,25 @@ for I in "${!RELEASE_TAR_VERSIONS[@]}"; do
--request POST "https://gitlab.freedesktop.org/api/v4/projects/411/releases" \ --request POST "https://gitlab.freedesktop.org/api/v4/projects/411/releases" \
--data "$(cat <<END --data "$(cat <<END
{ {
"name": "NetworkManager $BUILD_TAG", "name": "NetworkManager $BUILD_VERSION",
"tag_name": "$BUILD_TAG", "tag_name": "$BUILD_VERSION",
"assets": { "assets": {
"links": [ "links": [
{ {
"name": "NetworkManager $BUILD_TAG tarball with docs", "name": "NetworkManager $BUILD_VERSION tarball with docs",
"url": "https://gitlab.freedesktop.org/api/v4/projects/411/packages/generic/NetworkManager/$BUILD_TAG/$TAR_FILE", "url": "https://gitlab.freedesktop.org/api/v4/projects/411/packages/generic/NetworkManager/$BUILD_VERSION/$TAR_FILE",
"direct_asset_path": "/$TAR_FILE", "direct_asset_path": "/$TAR_FILE",
"link_type":"package" "link_type":"package"
}, },
{ {
"name": "NetworkManager $BUILD_TAG tarball sha256sum", "name": "NetworkManager $BUILD_VERSION tarball sha256sum",
"url": "https://gitlab.freedesktop.org/api/v4/projects/411/packages/generic/NetworkManager/$BUILD_TAG/$SUM_FILE", "url": "https://gitlab.freedesktop.org/api/v4/projects/411/packages/generic/NetworkManager/$BUILD_VERSION/$SUM_FILE",
"direct_asset_path": "/$SUM_FILE", "direct_asset_path": "/$SUM_FILE",
"link_type":"package" "link_type":"package"
}, },
{ {
"name": "NEWS", "name": "NEWS",
"url": "https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/blob/$BUILD_TAG/NEWS?ref_type=tags", "url": "https://gitlab.freedesktop.org/NetworkManager/NetworkManager/-/blob/$BUILD_VERSION/NEWS?ref_type=tags",
"direct_asset_path": "/NEWS", "direct_asset_path": "/NEWS",
"link_type":"other" "link_type":"other"
} }
@ -623,8 +590,8 @@ for I in "${!RELEASE_TAR_VERSIONS[@]}"; do
END END
)" || FAIL=1 )" || FAIL=1
if [[ $? != 0 ]]; then if [[ $FAIL = 1 ]]; then
fail_msg "failed to create NetworkManager $BUILD_TAG release" fail_msg "failed to create NetworkManager $BUILD_VERSION release"
CREATE_RELEASE_FAIL=1 CREATE_RELEASE_FAIL=1
continue continue
fi fi

View file

@ -55,6 +55,7 @@ _WITH_LIBTEAM="true"
_WITH_DOCS="true" _WITH_DOCS="true"
_WITH_SYSTEMD_LOGIND="true" _WITH_SYSTEMD_LOGIND="true"
_WITH_NBFT="true" _WITH_NBFT="true"
_WITH_CLAT="true"
if [ $IS_ALPINE = 1 ]; then if [ $IS_ALPINE = 1 ]; then
_WITH_SYSTEMD_LOGIND="false" _WITH_SYSTEMD_LOGIND="false"
fi fi
@ -63,6 +64,14 @@ if ! pkgconf 'libnvme >= 1.5'; then
_WITH_NBFT="false" _WITH_NBFT="false"
fi fi
if ! pkgconf 'libndp >= 1.9'; then
_WITH_CLAT="false"
fi
if ! pkgconf 'libbpf >= 1.3'; then
_WITH_CLAT="false"
fi
if [ -z "${NMTST_SEED_RAND+x}" ]; then if [ -z "${NMTST_SEED_RAND+x}" ]; then
NMTST_SEED_RAND="$SRANDOM" NMTST_SEED_RAND="$SRANDOM"
if [ -z "$NMTST_SEED_RAND" ]; then if [ -z "$NMTST_SEED_RAND" ]; then
@ -169,18 +178,18 @@ meson setup build \
-D ld_gc=false \ -D ld_gc=false \
-D session_tracking=no \ -D session_tracking=no \
-D systemdsystemunitdir=no \ -D systemdsystemunitdir=no \
-D systemdsystemgeneratordir=no \
-D systemd_journal=false \ -D systemd_journal=false \
-D selinux=false \ -D selinux=false \
-D libaudit=no \ -D libaudit=no \
-D libpsl=false \ -D libpsl=false \
-D vapi=false \ -D vapi=false \
-D introspection=$_WITH_DOCS \ -D introspection=$_WITH_DOCS \
-D man=$_WITH_DOCS \
-D qt=false \ -D qt=false \
-D crypto=$_WITH_CRYPTO \ -D crypto=$_WITH_CRYPTO \
-D docs=$_WITH_DOCS \ -D docs=$_WITH_DOCS \
\ \
-D ebpf=false \
\
-D iwd=true \ -D iwd=true \
-D ofono=true \ -D ofono=true \
-D teamdctl=$_WITH_LIBTEAM \ -D teamdctl=$_WITH_LIBTEAM \
@ -195,6 +204,7 @@ meson setup build \
-D ifupdown=true \ -D ifupdown=true \
\ \
-D nbft=$_WITH_NBFT \ -D nbft=$_WITH_NBFT \
-D clat=$_WITH_CLAT \
\ \
#end #end

View file

@ -1,10 +1,10 @@
[Unit] [Unit]
Description=NetworkManager Configuration (initrd) Description=NetworkManager Configuration (initrd)
AssertPathExists=/etc/initrd-release
DefaultDependencies=no DefaultDependencies=no
Wants=systemd-journald.socket Wants=systemd-journald.socket
After=systemd-journald.socket After=systemd-journald.socket
Before=systemd-udevd.service systemd-udev-trigger.service Before=systemd-udevd.service systemd-udev-trigger.service
ConditionPathExists=/etc/initrd-release
[Service] [Service]
Type=oneshot Type=oneshot
@ -22,6 +22,3 @@ ExecStartPost=/bin/sh -c ' \
fi \ fi \
' '
RemainAfterExit=yes RemainAfterExit=yes
[Install]
WantedBy=initrd.target

View file

@ -1,11 +1,11 @@
[Unit] [Unit]
Description=NetworkManager (initrd) Description=NetworkManager (initrd)
AssertPathExists=/etc/initrd-release
DefaultDependencies=no DefaultDependencies=no
Wants=systemd-udev-trigger.service network.target Wants=systemd-udev-trigger.service network.target
After=systemd-udev-trigger.service network-pre.target dbus.service NetworkManager-config-initrd.service After=systemd-udev-trigger.service network-pre.target dbus.service NetworkManager-config-initrd.service
Before=network.target Before=network.target
BindsTo=dbus.service BindsTo=dbus.service
ConditionPathExists=/etc/initrd-release
ConditionPathExists=/run/NetworkManager/initrd/neednet ConditionPathExists=/run/NetworkManager/initrd/neednet
ConditionPathExistsGlob=|/usr/lib/NetworkManager/system-connections/* ConditionPathExistsGlob=|/usr/lib/NetworkManager/system-connections/*
ConditionPathExistsGlob=|/run/NetworkManager/system-connections/* ConditionPathExistsGlob=|/run/NetworkManager/system-connections/*
@ -22,11 +22,3 @@ Environment=NM_CONFIG_ENABLE_TAG=initrd
Restart=on-failure Restart=on-failure
ProtectSystem=true ProtectSystem=true
ProtectHome=read-only ProtectHome=read-only
[Install]
WantedBy=initrd.target
# We want to enable NetworkManager-wait-online-initrd.service whenever this
# service is enabled. NetworkManager-wait-online-initrd.service has
# WantedBy=network-online.target, so enabling it only has an effect if
# network-online.target itself is enabled or pulled in by some other unit.
Also=NetworkManager-config-initrd.service NetworkManager-wait-online-initrd.service

View file

@ -1,10 +1,10 @@
[Unit] [Unit]
Description=NetworkManager Wait Online (initrd) Description=NetworkManager Wait Online (initrd)
AssertPathExists=/etc/initrd-release
DefaultDependencies=no DefaultDependencies=no
Requires=NetworkManager-initrd.service Requires=NetworkManager-initrd.service
After=NetworkManager-initrd.service After=NetworkManager-initrd.service
Before=network-online.target Before=network-online.target
ConditionPathExists=/etc/initrd-release
ConditionPathExists=/run/NetworkManager/initrd/neednet ConditionPathExists=/run/NetworkManager/initrd/neednet
[Service] [Service]
@ -21,6 +21,3 @@ Type=oneshot
ExecStart=@bindir@/nm-online -s -q ExecStart=@bindir@/nm-online -s -q
RemainAfterExit=yes RemainAfterExit=yes
Environment=NM_ONLINE_TIMEOUT=3600 Environment=NM_ONLINE_TIMEOUT=3600
[Install]
WantedBy=initrd.target network-online.target

View file

@ -19,10 +19,18 @@ KillMode=process
# With a huge number of interfaces, starting can take a long time. # With a huge number of interfaces, starting can take a long time.
TimeoutStartSec=600 TimeoutStartSec=600
CapabilityBoundingSet=CAP_NET_ADMIN CAP_DAC_OVERRIDE CAP_NET_RAW CAP_NET_BIND_SERVICE CAP_SETGID CAP_SETUID CAP_SYS_MODULE CAP_AUDIT_WRITE CAP_KILL CAP_SYS_CHROOT CapabilityBoundingSet=CAP_NET_ADMIN CAP_DAC_OVERRIDE CAP_NET_RAW CAP_BPF CAP_NET_BIND_SERVICE CAP_SETGID CAP_SETUID CAP_SYS_MODULE CAP_AUDIT_WRITE CAP_KILL CAP_SYS_CHROOT
ProtectSystem=true PrivateTmp=true
ProtectClock=true
ProtectControlGroups=true
ProtectHome=read-only ProtectHome=read-only
ProtectKernelLogs=true
ProtectSystem=true
RestrictRealtime=true
RestrictSUIDSGID=true
# We require file descriptors for DHCP etc. When activating many interfaces, # We require file descriptors for DHCP etc. When activating many interfaces,
# the default limit of 1024 is easily reached. # the default limit of 1024 is easily reached.

View file

@ -55,21 +55,22 @@ if install_udevdir
endif endif
if enable_polkit if enable_polkit
policy = 'org.freedesktop.NetworkManager.policy'
policy_in = configure_file(
input: policy + '.in.in',
output: '@BASENAME@',
configuration: data_conf,
)
i18n.merge_file( i18n.merge_file(
input: policy_in, input: 'org.freedesktop.NetworkManager.policy.in',
output: '@BASENAME@', output: '@BASENAME@',
po_dir: po_dir, po_dir: po_dir,
install: true, install: true,
install_dir: polkit_gobject_policydir, install_dir: polkit_policydir,
) )
if polkit_noauth_group != ''
configure_file(
input: 'org.freedesktop.NetworkManager.rules.in',
output: '@BASENAME@',
install_dir: polkit_rulesdir,
configuration: {'NM_POLKIT_NOAUTH_GROUP': polkit_noauth_group},
)
endif
endif endif
if enable_firewalld_zone if enable_firewalld_zone

View file

@ -117,8 +117,8 @@
<message>System policy prevents modification of network settings for all users</message> <message>System policy prevents modification of network settings for all users</message>
<defaults> <defaults>
<allow_any>auth_admin_keep</allow_any> <allow_any>auth_admin_keep</allow_any>
<allow_inactive>@NM_MODIFY_SYSTEM_POLICY@</allow_inactive> <allow_inactive>auth_admin_keep</allow_inactive>
<allow_active>@NM_MODIFY_SYSTEM_POLICY@</allow_active> <allow_active>auth_admin_keep</allow_active>
</defaults> </defaults>
</action> </action>

View file

@ -0,0 +1,17 @@
// NetworkManager authorizations/policy for the @NM_POLKIT_NOAUTH_GROUP@ group.
//
// DO NOT EDIT THIS FILE, it will be overwritten on update.
//
// Allow users in the @NM_POLKIT_NOAUTH_GROUP@ group to create system-wide connections without being
// prompted for a password if they are in a local console.
// This is optional and is only recommended to maintain backwards compatibility
// in systems where it was already working in this way. It is discouraged
// otherwise.
polkit.addRule(function(action, subject) {
if (action.id == "org.freedesktop.NetworkManager.settings.modify.system" &&
subject.isInGroup("@NM_POLKIT_NOAUTH_GROUP@") &&
subject.local) {
return polkit.Result.YES;
}
});

View file

@ -1,6 +1,8 @@
# SPDX-License-Identifier: LGPL-2.1-or-later # SPDX-License-Identifier: LGPL-2.1-or-later
if enable_introspection if enable_introspection
xsltproc = find_program('xsltproc')
settings = 'settings-spec' settings = 'settings-spec'
output = settings + '.xml' output = settings + '.xml'

View file

@ -183,6 +183,7 @@
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.Bridge.xml"/> <xi:include href="dbus-org.freedesktop.NetworkManager.Device.Bridge.xml"/>
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.Dummy.xml"/> <xi:include href="dbus-org.freedesktop.NetworkManager.Device.Dummy.xml"/>
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.Generic.xml"/> <xi:include href="dbus-org.freedesktop.NetworkManager.Device.Generic.xml"/>
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.Geneve.xml"/>
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.Hsr.xml"/> <xi:include href="dbus-org.freedesktop.NetworkManager.Device.Hsr.xml"/>
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.IPTunnel.xml"/> <xi:include href="dbus-org.freedesktop.NetworkManager.Device.IPTunnel.xml"/>
<xi:include href="dbus-org.freedesktop.NetworkManager.Device.Infiniband.xml"/> <xi:include href="dbus-org.freedesktop.NetworkManager.Device.Infiniband.xml"/>

View file

@ -317,6 +317,7 @@ print ("NetworkManager version " + client.get_version())]]></programlisting></in
<xi:include href="xml/nm-setting-dummy.xml"/> <xi:include href="xml/nm-setting-dummy.xml"/>
<xi:include href="xml/nm-setting-ethtool.xml"/> <xi:include href="xml/nm-setting-ethtool.xml"/>
<xi:include href="xml/nm-setting-generic.xml"/> <xi:include href="xml/nm-setting-generic.xml"/>
<xi:include href="xml/nm-setting-geneve.xml"/>
<xi:include href="xml/nm-setting-gsm.xml"/> <xi:include href="xml/nm-setting-gsm.xml"/>
<xi:include href="xml/nm-setting-hostname.xml"/> <xi:include href="xml/nm-setting-hostname.xml"/>
<xi:include href="xml/nm-setting-hsr.xml"/> <xi:include href="xml/nm-setting-hsr.xml"/>
@ -377,6 +378,7 @@ print ("NetworkManager version " + client.get_version())]]></programlisting></in
<xi:include href="xml/nm-device-dummy.xml"/> <xi:include href="xml/nm-device-dummy.xml"/>
<xi:include href="xml/nm-device-ethernet.xml"/> <xi:include href="xml/nm-device-ethernet.xml"/>
<xi:include href="xml/nm-device-generic.xml"/> <xi:include href="xml/nm-device-generic.xml"/>
<xi:include href="xml/nm-device-geneve.xml"/>
<xi:include href="xml/nm-device-hsr.xml"/> <xi:include href="xml/nm-device-hsr.xml"/>
<xi:include href="xml/nm-device-infiniband.xml"/> <xi:include href="xml/nm-device-infiniband.xml"/>
<xi:include href="xml/nm-device-ip-tunnel.xml"/> <xi:include href="xml/nm-device-ip-tunnel.xml"/>

View file

@ -202,7 +202,7 @@
sodipodi:role="line" sodipodi:role="line"
x="19.192902" x="19.192902"
y="360.40768" y="360.40768"
id="tspan3839">Retrieves, adds, and notifes of changes</tspan><tspan id="tspan3839">Retrieves, adds, and notifies of changes</tspan><tspan
sodipodi:role="line" sodipodi:role="line"
x="19.192902" x="19.192902"
y="372.90768" y="372.90768"

Before

Width:  |  Height:  |  Size: 46 KiB

After

Width:  |  Height:  |  Size: 46 KiB

View file

@ -15,6 +15,7 @@ ifaces = [
'org.freedesktop.NetworkManager.Device.Bridge', 'org.freedesktop.NetworkManager.Device.Bridge',
'org.freedesktop.NetworkManager.Device.Dummy', 'org.freedesktop.NetworkManager.Device.Dummy',
'org.freedesktop.NetworkManager.Device.Generic', 'org.freedesktop.NetworkManager.Device.Generic',
'org.freedesktop.NetworkManager.Device.Geneve',
'org.freedesktop.NetworkManager.Device.Hsr', 'org.freedesktop.NetworkManager.Device.Hsr',
'org.freedesktop.NetworkManager.Device.IPTunnel', 'org.freedesktop.NetworkManager.Device.IPTunnel',
'org.freedesktop.NetworkManager.Device.Infiniband', 'org.freedesktop.NetworkManager.Device.Infiniband',

View file

@ -0,0 +1,63 @@
<?xml version="1.0" encoding="UTF-8"?>
<node name="/">
<!--
org.freedesktop.NetworkManager.Device.Geneve:
@short_description: GENEVE Device.
-->
<interface name="org.freedesktop.NetworkManager.Device.Geneve">
<!--
Id:
@since: 1.58
The GENEVE Virtual Network Identifier (VNI).
-->
<property name="Id" type="u" access="read"/>
<!--
Remote:
@since: 1.58
The IP (v4 or v6) address of the remote endpoint to which GENEVE packets
are sent.
-->
<property name="Remote" type="s" access="read"/>
<!--
Tos:
@since: 1.58
The value to use in the IP ToS field for GENEVE packets sent to the remote
endpoint.
-->
<property name="Tos" type="y" access="read"/>
<!--
Ttl:
@since: 1.58
The value to use in the IP TTL field for GENEVE packets sent to the remote
endpoint.
-->
<property name="Ttl" type="i" access="read"/>
<!--
Df:
@since: 1.58
The Don't Fragment (DF) flag setting for GENEVE packets. 0 means unset,
1 means set, 2 means inherit from the underlying interface.
-->
<property name="Df" type="y" access="read"/>
<!--
DstPort:
@since: 1.58
Destination port for outgoing GENEVE packets.
-->
<property name="DstPort" type="q" access="read"/>
</interface>
</node>

View file

@ -175,6 +175,9 @@
property has a similar effect to configuring the device as unmanaged via property has a similar effect to configuring the device as unmanaged via
the keyfile.unmanaged-devices setting in NetworkManager.conf. Changes to the keyfile.unmanaged-devices setting in NetworkManager.conf. Changes to
this value are not persistent and lost after NetworkManager restart. this value are not persistent and lost after NetworkManager restart.
DEPRECATED: 1.58: Use the SetManaged method instead, which supports
additional features like persisting the state to disk
--> -->
<property name="Managed" type="b" access="readwrite"/> <property name="Managed" type="b" access="readwrite"/>
@ -391,6 +394,20 @@
--> -->
<method name="Delete"/> <method name="Delete"/>
<!--
SetManaged:
@managed:(<link linkend="NMDeviceManaged">NMDeviceManaged</link>) Whether the device is managed. Possible values are "no" (0), "yes" (1) and "reset" (2).
@flags: (<link linkend="NMDeviceManagedFlags">NMDeviceManagedFlags</link>) flags.
@since: 1.58
Set the managed state of the device. With the flags argument different
behaviors can be achieved, like storing the new managed state to disk.
-->
<method name="SetManaged">
<arg name="managed" type="u" direction="in"/>
<arg name="flags" type="u" direction="in"/>
</method>
<!-- <!--
StateChanged: StateChanged:
@new_state: (<link linkend="NMDeviceState">NMDeviceState</link>) The new state of the device. @new_state: (<link linkend="NMDeviceState">NMDeviceState</link>) The new state of the device.

View file

@ -62,7 +62,7 @@
<!-- <!--
GetSecrets: GetSecrets:
@setting_name: Name of the setting to return secrets for. If empty, all secrets will be returned. @setting_name: Name of the setting to return secrets for (mandatory).
@secrets: Nested settings maps containing secrets. @secrets: Nested settings maps containing secrets.
Get the secrets belonging to this network configuration. Only secrets from Get the secrets belonging to this network configuration. Only secrets from

View file

@ -83,6 +83,11 @@
note that your distribution or other packages may drop configuration snippets for NetworkManager, such note that your distribution or other packages may drop configuration snippets for NetworkManager, such
that they are part of the factory default. that they are part of the factory default.
</para> </para>
<para>
The options that are indicated as boolean can be set to one of these values:
<literal>yes</literal>, <literal>true</literal>, <literal>on</literal>, <literal>1</literal>,
<literal>no</literal>, <literal>false</literal>, <literal>off</literal>, <literal>0</literal>.
</para>
</refsect1> </refsect1>
@ -895,11 +900,15 @@ ipv6.ip6-privacy=0
</varlistentry> </varlistentry>
<varlistentry> <varlistentry>
<term><varname>connection.mptcp-flags</varname></term> <term><varname>connection.mptcp-flags</varname></term>
<listitem><para>If unspecified, the fallback is 0x22 (<literal>"enabled,subflow"</literal>). Note that if sysctl <literal>/proc/sys/net/mptcp/enabled</literal> is disabled, NetworkManager will still not configure endpoints.</para></listitem> <listitem><para>If unspecified, the fallback is 0x122 (<literal>"enabled,subflow,laminar"</literal>). Note that if sysctl <literal>/proc/sys/net/mptcp/enabled</literal> is disabled, NetworkManager will still not configure endpoints.</para></listitem>
</varlistentry> </varlistentry>
<varlistentry> <varlistentry>
<term><varname>connection.dns-over-tls</varname></term> <term><varname>connection.dns-over-tls</varname></term>
<listitem><para>If unspecified, the ultimate default values depends on the DNS plugin. With systemd-resolved the default currently is global setting and for all other plugins "no" (0).</para></listitem> <listitem><para>If unspecified, the ultimate default values depends on the DNS plugin. With systemd-resolved the default currently is its global setting and for all other plugins "no" (0).</para></listitem>
</varlistentry>
<varlistentry>
<term><varname>connection.dnssec</varname></term>
<listitem><para>If unspecified, the ultimate default values depends on the DNS plugin. With systemd-resolved the default currently is its global setting and for all other plugins "no" (0).</para></listitem>
</varlistentry> </varlistentry>
<varlistentry> <varlistentry>
<term><varname>connection.stable-id</varname></term> <term><varname>connection.stable-id</varname></term>
@ -945,6 +954,10 @@ ipv6.ip6-privacy=0
<term><varname>ipv4.forwarding</varname></term> <term><varname>ipv4.forwarding</varname></term>
<listitem><para>Whether to configure IPv4 sysctl interface-specific forwarding. When enabled, the interface will act as a router to forward the IPv4 packet from one interface to another. If left unspecified, "auto" is used, so NetworkManager sets the IPv4 forwarding if any shared connection is active, or it will use the kernel default value otherwise. The "ipv4.forwarding" property is ignored when "ipv4.method" is set to "shared", because forwarding is always enabled in this case. The accepted values are: 0: disabled, 1: enabled, 2: auto, 3: ignored (leave the forwarding unchanged).</para></listitem> <listitem><para>Whether to configure IPv4 sysctl interface-specific forwarding. When enabled, the interface will act as a router to forward the IPv4 packet from one interface to another. If left unspecified, "auto" is used, so NetworkManager sets the IPv4 forwarding if any shared connection is active, or it will use the kernel default value otherwise. The "ipv4.forwarding" property is ignored when "ipv4.method" is set to "shared", because forwarding is always enabled in this case. The accepted values are: 0: disabled, 1: enabled, 2: auto, 3: ignored (leave the forwarding unchanged).</para></listitem>
</varlistentry> </varlistentry>
<varlistentry>
<term><varname>ipv4.clat</varname></term>
<listitem><para>If left unspecified, defaults to "no".</para></listitem>
</varlistentry>
<varlistentry> <varlistentry>
<term><varname>ipv4.routed-dns</varname></term> <term><varname>ipv4.routed-dns</varname></term>
</varlistentry> </varlistentry>
@ -963,7 +976,7 @@ ipv6.ip6-privacy=0
</varlistentry> </varlistentry>
<varlistentry> <varlistentry>
<term><varname>ipv4.dhcp-ipv6-only-preferred</varname></term> <term><varname>ipv4.dhcp-ipv6-only-preferred</varname></term>
<listitem><para>If left unspecified, the "IPv6-only preferred" DHCPv4 option is disabled.</para></listitem> <listitem><para>If left unspecified, it defaults to "auto".</para></listitem>
</varlistentry> </varlistentry>
<varlistentry> <varlistentry>
<term><varname>ipv4.dhcp-hostname-flags</varname></term> <term><varname>ipv4.dhcp-hostname-flags</varname></term>
@ -1245,12 +1258,13 @@ managed=1
<term><varname>managed</varname></term> <term><varname>managed</varname></term>
<listitem> <listitem>
<para> <para>
Whether the device is managed or not. A device can be A boolean value specifying whether the device is
marked as managed via udev rules (ENV{NM_UNMANAGED}), managed or not. A device can be marked as managed via
or via setting plugins (keyfile.unmanaged-devices). udev rules (ENV{NM_UNMANAGED}), or via setting plugins
This is yet another way. Note that this configuration (keyfile.unmanaged-devices). This is yet another
can be overruled at runtime via D-Bus. Also, it has way. Note that this configuration can be overruled at
higher priority then udev rules. runtime via D-Bus. Also, it has higher priority than
udev rules.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@ -1319,9 +1333,27 @@ managed=1
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
<varlistentry id="check-connectivity">
<term><varname>check-connectivity</varname></term>
<listitem>
<para>
A boolean value specifying whether NetworkManager will perform a connectivity check
for this device. Defaults to <literal>yes</literal>.
</para>
<para>
This setting does nothing if the connectivity check has been
disabled globally using the
<literal>connectivity.enabled</literal> setting.
</para>
</listitem>
</varlistentry>
<varlistentry id="keep-configuration"> <varlistentry id="keep-configuration">
<term><varname>keep-configuration</varname></term> <term><varname>keep-configuration</varname></term>
<listitem> <listitem>
<para>
A boolean value indicating whether the existing device
configuration is kept at startup.
</para>
<para> <para>
On startup, NetworkManager tries to not interfere with On startup, NetworkManager tries to not interfere with
interfaces that are already configured. It does so by interfaces that are already configured. It does so by
@ -1418,16 +1450,16 @@ managed=1
<term><varname>wifi.iwd.autoconnect</varname></term> <term><varname>wifi.iwd.autoconnect</varname></term>
<listitem> <listitem>
<para> <para>
If <literal>wifi.backend</literal> is <literal>iwd</literal>, setting this to A boolean value. If <literal>wifi.backend</literal> is <literal>iwd</literal>,
<literal>false</literal> forces IWD's autoconnect mechanism to be disabled for setting this to <literal>false</literal> forces IWD's autoconnect mechanism to be
this device and connections will only be initiated by NetworkManager whether disabled for this device and connections will only be initiated by NetworkManager
commanded by a client or automatically. Leaving it <literal>true</literal> (default) whether commanded by a client or automatically. Leaving it <literal>true</literal>
stops NetworkManager from automatically initiating connections and allows (default) stops NetworkManager from automatically initiating connections and allows
IWD to use its network ranking and scanning logic to decide the best networks IWD to use its network ranking and scanning logic to decide the best networks to
to autoconnect to next. Connections' <literal>autoconnect-priority</literal>, autoconnect to next. Connections' <literal>autoconnect-priority</literal>,
<literal>autoconnect-retries</literal> settings will be ignored. Other settings <literal>autoconnect-retries</literal> settings will be ignored. Other settings like
like <literal>permissions</literal> or <literal>multi-connect</literal> may interfere <literal>permissions</literal> or <literal>multi-connect</literal> may interfere with
with IWD connection attempts. IWD connection attempts.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@ -1486,7 +1518,7 @@ managed=1
<variablelist> <variablelist>
<varlistentry> <varlistentry>
<term><varname>enabled</varname></term> <term><varname>enabled</varname></term>
<listitem><para>Whether connectivity check is enabled. <listitem><para>A boolean indicating whether connectivity check is enabled.
Note that to enable connectivity check, a valid uri must Note that to enable connectivity check, a valid uri must
also be configured. The value defaults to true, but since also be configured. The value defaults to true, but since
the uri is unset by default, connectivity check may be disabled. the uri is unset by default, connectivity check may be disabled.

View file

@ -1,29 +1,5 @@
# SPDX-License-Identifier: LGPL-2.1-or-later # SPDX-License-Identifier: LGPL-2.1-or-later
common_ent_file = configure_file(
input: 'common.ent.in',
output: '@BASENAME@',
configuration: data_conf,
)
xsltproc_options = [
xsltproc,
'--output', '@OUTPUT@',
'--path', meson.current_build_dir(),
'--xinclude',
'--nonet',
'--stringparam', 'man.output.quietly', '1',
'--stringparam', 'funcsynopsis.style', 'ansi',
'--stringparam', 'man.th.extra1.suppress', '1',
'--stringparam', 'man.authors.section.enabled', '0',
'--stringparam', 'man.copyright.section.enabled', '0',
'--stringparam', 'man.th.title.max.length', '30',
]
docbook_xls = 'http://docbook.sourceforge.net/release/xsl/current/manpages/docbook.xsl'
mans_xmls = []
mans = [ mans = [
['NetworkManager', '8'], ['NetworkManager', '8'],
['NetworkManager-dispatcher', '8'], ['NetworkManager-dispatcher', '8'],
@ -44,12 +20,62 @@ if enable_nm_cloud_setup
mans += [['nm-cloud-setup', '8']] mans += [['nm-cloud-setup', '8']]
endif endif
introspection_mans = [
['nm-settings-keyfile', '5'],
['nm-settings-dbus', '5'],
['nm-settings-nmcli', '5'],
]
if enable_ifcfg_rh
introspection_mans += [['nm-settings-ifcfg-rh', '5']]
endif
built_mans = []
foreach man: mans + introspection_mans
name = man[0] + '.' + man[1]
if not fs.exists(name)
built_mans = []
break
endif
built_mans += name
endforeach
if enable_introspection or enable_docs
common_ent_file = configure_file(
input: 'common.ent.in',
output: '@BASENAME@',
configuration: data_conf,
)
endif
if enable_introspection and (enable_man or enable_docs)
xsltproc_options = [
find_program('xsltproc'),
'--output', '@OUTPUT@',
'--path', meson.current_build_dir(),
'--xinclude',
'--nonet',
'--stringparam', 'man.output.quietly', '1',
'--stringparam', 'funcsynopsis.style', 'ansi',
'--stringparam', 'man.th.extra1.suppress', '1',
'--stringparam', 'man.authors.section.enabled', '0',
'--stringparam', 'man.copyright.section.enabled', '0',
'--stringparam', 'man.th.title.max.length', '30',
]
docbook_xls = 'http://docbook.sourceforge.net/release/xsl/current/manpages/docbook.xsl'
mans_xmls = []
foreach man: mans foreach man: mans
input = man[0] + '.xml' input = man[0] + '.xml'
content_files += join_paths(meson.current_source_dir(), input) content_files += join_paths(meson.current_source_dir(), input)
output = '@0@.@1@'.format(man[0], man[1]) output = '@0@.@1@'.format(man[0], man[1])
# not needed if only html requested
if enable_man
custom_target( custom_target(
output, output,
input: input, input: input,
@ -59,9 +85,9 @@ foreach man: mans
install: true, install: true,
install_dir: join_paths(nm_mandir, 'man' + man[1]), install_dir: join_paths(nm_mandir, 'man' + man[1]),
) )
endif
endforeach endforeach
if enable_introspection
merge_cmd = files(source_root / 'tools' / 'generate-docs-nm-settings-docs-merge.py') merge_cmd = files(source_root / 'tools' / 'generate-docs-nm-settings-docs-merge.py')
name = 'dbus' name = 'dbus'
@ -124,6 +150,8 @@ if enable_introspection
output = '@0@.@1@'.format(man[0], man[1]) output = '@0@.@1@'.format(man[0], man[1])
# not needed if only html requested
if enable_man
custom_target( custom_target(
output, output,
input: input, input: input,
@ -132,5 +160,13 @@ if enable_introspection
install: true, install: true,
install_dir: join_paths(nm_mandir, 'man' + man[1]), install_dir: join_paths(nm_mandir, 'man' + man[1]),
) )
endforeach endif
endforeach
# not needed if only html requested
elif enable_man
if built_mans.length() > 0
install_man(built_mans)
else
error('Building manpages requires xsltproc and -Dintrospection=true, and no prebuilt manpages were found. Try building from a release tarball or using -Dman=false.')
endif
endif endif

View file

@ -143,7 +143,7 @@
script is to automatically pick up changes to the network.</para> script is to automatically pick up changes to the network.</para>
<para>The dispatcher script will do nothing, unless the systemd service is <para>The dispatcher script will do nothing, unless the systemd service is
enabled. To use the dispatcher script you should therefor run enabled. To use the dispatcher script you should therefore run
<command>systemctl enable nm-cloud-setup.service</command> once.</para> <command>systemctl enable nm-cloud-setup.service</command> once.</para>
</refsect2> </refsect2>
@ -197,7 +197,7 @@
<para>Enable debug logging by setting <literal>NM_CLOUD_SETUP_LOG</literal> environment variable to <literal>TRACE</literal>.</para> <para>Enable debug logging by setting <literal>NM_CLOUD_SETUP_LOG</literal> environment variable to <literal>TRACE</literal>.</para>
<para>In the common case where nm-cloud-setup is running as systemd service, this can be done via <command>systemctl edit nm-cloud-setup.service</command> <para>In the common case where nm-cloud-setup is running as systemd service, this can be done via <command>systemctl edit nm-cloud-setup.service</command>
and add <literal>Environment=NM_CLOUD_SETUP_LOG=TRACE</literal> to the <literal>[Service]</literal> section. Afterwards, the log can and add <literal>Environment=NM_CLOUD_SETUP_LOG=TRACE</literal> to the <literal>[Service]</literal> section. Afterwards, the log can
be found in syslog via <literal>journalctl</literal>. You may also want to enable debug logging in NetworkManager as descibed be found in syslog via <literal>journalctl</literal>. You may also want to enable debug logging in NetworkManager as described
in the DEBUGGING section in <link linkend='NetworkManager'><citerefentry><refentrytitle>NetworkManager</refentrytitle><manvolnum>5</manvolnum></citerefentry></link> in the DEBUGGING section in <link linkend='NetworkManager'><citerefentry><refentrytitle>NetworkManager</refentrytitle><manvolnum>5</manvolnum></citerefentry></link>
manual. When sharing logs, it's best to share complete logs and not preemptively filter for NetworkManager or nm-cloud-setup logs.</para> manual. When sharing logs, it's best to share complete logs and not preemptively filter for NetworkManager or nm-cloud-setup logs.</para>
</refsect1> </refsect1>

View file

@ -1066,15 +1066,16 @@
<listitem><para><literal>dummy</literal></para></listitem> <listitem><para><literal>dummy</literal></para></listitem>
<listitem><para><literal>generic</literal></para></listitem> <listitem><para><literal>generic</literal></para></listitem>
<listitem><para><literal>gsm</literal></para></listitem> <listitem><para><literal>gsm</literal></para></listitem>
<listitem><para><literal>hsr</literal></para></listitem>
<listitem><para><literal>infiniband</literal></para></listitem> <listitem><para><literal>infiniband</literal></para></listitem>
<listitem><para><literal>ip-tunnel</literal></para></listitem> <listitem><para><literal>ip-tunnel</literal></para></listitem>
<listitem><para><literal>ipvlan</literal></para></listitem>
<listitem><para><literal>loopback</literal></para></listitem>
<listitem><para><literal>macsec</literal></para></listitem> <listitem><para><literal>macsec</literal></para></listitem>
<listitem><para><literal>macvlan</literal></para></listitem> <listitem><para><literal>macvlan</literal></para></listitem>
<listitem><para><literal>olpc-mesh</literal></para></listitem> <listitem><para><literal>olpc-mesh</literal></para></listitem>
<listitem><para><literal>ovs-bridge</literal></para></listitem> <listitem><para><literal>ovs-bridge</literal></para></listitem>
<listitem><para><literal>ovs-dpdk</literal></para></listitem>
<listitem><para><literal>ovs-interface</literal></para></listitem> <listitem><para><literal>ovs-interface</literal></para></listitem>
<listitem><para><literal>ovs-patch</literal></para></listitem>
<listitem><para><literal>ovs-port</literal></para></listitem> <listitem><para><literal>ovs-port</literal></para></listitem>
<listitem><para><literal>pppoe</literal></para></listitem> <listitem><para><literal>pppoe</literal></para></listitem>
<listitem><para><literal>team</literal></para></listitem> <listitem><para><literal>team</literal></para></listitem>
@ -1435,15 +1436,31 @@
</arg> </arg>
<arg> <arg>
<option>managed</option> <option>managed</option>
<group>
<arg choice='plain'>--permanent</arg>
<arg choice='plain'>--permanent-only</arg>
</group>
<group choice='req'> <group choice='req'>
<arg choice='plain'>yes</arg> <arg choice='plain'>yes</arg>
<arg choice='plain'>no</arg> <arg choice='plain'>no</arg>
<arg choice='plain'>up</arg>
<arg choice='plain'>down</arg>
<arg choice='plain'>reset</arg>
</group> </group>
</arg> </arg>
</term> </term>
<listitem> <listitem>
<para>Set device properties.</para> <para>Set device properties.</para>
<para>The <option>managed</option> property accepts a <option>--permanent</option>
option to persist the managed state to disk, and not only in runtime. With
<option>--permanent-only</option> only the permanent managed state is set, and not the
runtime managed state. The special values <option>up</option> and <option>down</option>
can be used to set the administrative state of the device at the same time as the runtime
managed state. The <option>reset</option> value clears the explicit managed setting, and
with <option>--permanent</option> or <option>--permanent-only</option> it also removes
the persisted managed setting.</para>
</listitem> </listitem>
</varlistentry> </varlistentry>
@ -1717,6 +1734,7 @@
<group choice='req'> <group choice='req'>
<arg choice='plain'>a</arg> <arg choice='plain'>a</arg>
<arg choice='plain'>bg</arg> <arg choice='plain'>bg</arg>
<arg choice='plain'>6GHz</arg>
</group> </group>
</arg> </arg>
<arg><option>channel</option> <replaceable>channel</replaceable></arg> <arg><option>channel</option> <replaceable>channel</replaceable></arg>
@ -1850,9 +1868,9 @@
connections with an option of restoring the network configuration to a connections with an option of restoring the network configuration to a
known good state in case of an error.</para> known good state in case of an error.</para>
<para>If the a list of interface names is specified, the checkpoint is <para>If a list of interface names is specified, the checkpoint is
taken, the checkpoint is takes only on the specified devices. Otherwise taken only on the specified devices. Otherwise a checkpoint is taken for
a checkpoint is taken for all devices.</para> all devices.</para>
<para>Currently the timeout defaults to 15 seconds. This may change in <para>Currently the timeout defaults to 15 seconds. This may change in
a future version.</para> a future version.</para>

View file

@ -5,23 +5,48 @@ project(
# NOTE: When incrementing version also add corresponding # NOTE: When incrementing version also add corresponding
# NM_VERSION_x_y_z macros in # NM_VERSION_x_y_z macros in
# "src/libnm-core-public/nm-version-macros.h.in" # "src/libnm-core-public/nm-version-macros.h.in"
version: '1.54.2', version: '1.57.4-dev',
license: 'GPL2+', license: 'GPL2+',
default_options: [ default_options: [
'buildtype=debugoptimized', 'buildtype=debugoptimized',
'c_std=gnu11', 'c_std=gnu11',
'warning_level=2' # value "2" will add "-Wall" and "-Wextra" to the compiler flags 'warning_level=2' # value "2" will add "-Wall" and "-Wextra" to the compiler flags
], ],
meson_version: '>= 0.51.0', meson_version: '>= 0.56.0',
) )
nm_name = meson.project_name() nm_name = meson.project_name()
nm_version = meson.project_version() nm_version = meson.project_version()
version_array = nm_version.split('.')
version_and_suffix = nm_version.split('-')
version_array = version_and_suffix[0].split('.')
if version_and_suffix.length() == 2
version_suffix = version_and_suffix[1]
else
assert(version_and_suffix.length() == 1)
version_suffix = ''
endif
# In the C API we encode the version in 90+ scheme (1.56-rc1 = 1.55.90, rc2 = .91, etc)
if version_suffix == '' or version_suffix == 'dev'
assert(version_array.length() == 3)
nm_major_version = version_array[0].to_int() nm_major_version = version_array[0].to_int()
nm_minor_version = version_array[1].to_int() nm_minor_version = version_array[1].to_int()
nm_micro_version = version_array[2].to_int() nm_micro_version = version_array[2].to_int()
elif version_suffix.startswith('rc')
assert(version_array.length() == 2)
nm_major_version = version_array[0].to_int()
nm_minor_version = version_array[1].to_int() - 1
nm_micro_version = version_suffix.substring(2).to_int() + 89
else
error('Invalid suffix: ' + version_suffix)
endif
if nm_minor_version % 2 == 1 and version_suffix == ''
error('Expected a "-dev" or "-rc" suffix')
elif nm_minor_version %2 == 0 and version_suffix != ''
error('Unexpected "' + version_suffix + '" suffix')
endif
nm_id_prefix = 'NM' nm_id_prefix = 'NM'
@ -77,6 +102,7 @@ libnm_version = '@0@.@1@.@2@'.format(current - age, age, revision)
libnm_pkgincludedir = join_paths(nm_includedir, libnm_name) libnm_pkgincludedir = join_paths(nm_includedir, libnm_name)
fs = import('fs')
gnome = import('gnome') gnome = import('gnome')
i18n = import('i18n') i18n = import('i18n')
pkg = import('pkgconfig') pkg = import('pkgconfig')
@ -89,7 +115,6 @@ po_dir = source_root / 'po'
top_inc = include_directories('.') top_inc = include_directories('.')
perl = find_program('perl') perl = find_program('perl')
xsltproc = find_program('xsltproc')
check_exports = find_program(join_paths(source_root, 'tools', 'check-exports.sh')) check_exports = find_program(join_paths(source_root, 'tools', 'check-exports.sh'))
@ -271,7 +296,8 @@ config_h.set10('WITH_JANSSON', jansson_dep.found())
jansson_msg = 'no' jansson_msg = 'no'
if jansson_dep.found() if jansson_dep.found()
jansson_libdir = jansson_dep.get_variable(pkgconfig: 'libdir') jansson_libdir = jansson_dep.get_variable(pkgconfig: 'libdir')
res = run_command(find_program('eu-readelf', 'readelf'), '-d', join_paths(jansson_libdir, 'libjansson.so'), check: false) jansson_sysroot = meson.is_cross_build() ? meson.get_external_property('sys_root', '') : ''
res = run_command(find_program('eu-readelf', 'readelf'), '-d', jansson_sysroot + join_paths(jansson_libdir, 'libjansson.so'), check: false)
jansson_soname = '' jansson_soname = ''
foreach line: res.stdout().split('\n') foreach line: res.stdout().split('\n')
if line.strip().contains('SONAME') if line.strip().contains('SONAME')
@ -327,12 +353,17 @@ config_h.set10('WITH_CONFIG_PLUGIN_IFUPDOWN', enable_ifupdown)
config_h.set_quoted('NM_DIST_VERSION', dist_version) config_h.set_quoted('NM_DIST_VERSION', dist_version)
enable_wifi = get_option('wifi') enable_wifi = get_option('wifi')
config_h.set10('WITH_WIFI', enable_wifi)
enable_iwd = get_option('iwd') enable_iwd = get_option('iwd')
assert((not enable_iwd) or enable_wifi, 'Enabling iwd support requires Wi-Fi support as well') assert((not enable_iwd) or enable_wifi, 'Enabling iwd support requires Wi-Fi support as well')
config_h.set10('WITH_IWD', enable_iwd) config_h.set10('WITH_IWD', enable_iwd)
enable_wext = get_option('wext') wext = get_option('wext')
if wext == 'true'
error('Wireless Extensions support is deprecated and will be removed in the future. Use -Dwext=force to keep using it')
endif
enable_wext = (wext == 'force')
config_h.set10('HAVE_WEXT', enable_wext) config_h.set10('HAVE_WEXT', enable_wext)
# Checks for libdl - on certain platforms its part of libc # Checks for libdl - on certain platforms its part of libc
@ -382,6 +413,14 @@ if install_systemdunitdir and systemd_systemdsystemunitdir == ''
systemd_systemdsystemunitdir = systemd_dep.get_variable(pkgconfig: 'systemdsystemunitdir', pkgconfig_define: ['rootprefix', nm_prefix]) systemd_systemdsystemunitdir = systemd_dep.get_variable(pkgconfig: 'systemdsystemunitdir', pkgconfig_define: ['rootprefix', nm_prefix])
endif endif
systemd_systemdsystemgeneratordir = get_option('systemdsystemgeneratordir')
install_systemdgeneratordir = (systemd_systemdsystemgeneratordir != 'no')
if install_systemdgeneratordir and systemd_systemdsystemgeneratordir == ''
assert(systemd_dep.found(), 'systemd required but not found, please provide a valid systemd user generator dir or disable it')
systemd_systemdsystemgeneratordir = systemd_dep.get_variable(pkgconfig: 'systemdsystemgeneratordir', pkgconfig_define: ['rootprefix', nm_prefix])
endif
enable_systemd_journal = get_option('systemd_journal') enable_systemd_journal = get_option('systemd_journal')
if enable_systemd_journal if enable_systemd_journal
assert(libsystemd_dep.found(), 'Missing systemd-journald support') assert(libsystemd_dep.found(), 'Missing systemd-journald support')
@ -476,18 +515,15 @@ if enable_selinux
endif endif
config_h.set10('HAVE_SELINUX', enable_selinux) config_h.set10('HAVE_SELINUX', enable_selinux)
# eBPF support # CLAT support
ebpf_opt = get_option('ebpf') enable_clat = get_option('clat')
# 'auto' means 'false', because there are still issues. if enable_clat
if ebpf_opt != 'true' libbpf = dependency('libbpf', version: '>= 1.3.0', required: false)
enable_ebpf = false assert(libbpf.found(), 'You must have libbpf >= 1.3.0 installed to build. Use -Dclat=false to disable use of it')
else libndp_dep = dependency('libndp', version: '>= 1.9', required: false)
enable_ebpf = true assert(libndp_dep.found(), 'You must have libndp >= 1.9 installed to build with CLAT support. Use -Dclat=false to disable it')
if not cc.has_header('linux/bpf.h')
assert(ebpf_opt != 'true', 'eBPF requires kernel support')
enable_ebpf = false
endif
endif endif
config_h.set10('HAVE_CLAT', enable_clat)
# libaudit support # libaudit support
libaudit = get_option('libaudit') libaudit = get_option('libaudit')
@ -507,12 +543,14 @@ if enable_teamdctl
libteamdctl_dep = dependency('libteamdctl', version: '>= 1.9') libteamdctl_dep = dependency('libteamdctl', version: '>= 1.9')
assert(libteamdctl_dep.found(), 'You must have libteamdctl installed to build. Use -Dteamdctl=false to disable it') assert(libteamdctl_dep.found(), 'You must have libteamdctl installed to build. Use -Dteamdctl=false to disable it')
endif endif
config_h.set10('WITH_TEAMDCTL', enable_teamdctl)
# polkit # polkit
enable_polkit = get_option('polkit') enable_polkit = get_option('polkit')
if enable_polkit if enable_polkit
# FIXME: policydir should be relative to `datadir`, not `prefix`. Fixed in https://gitlab.freedesktop.org/polkit/polkit/merge_requests/2 # FIXME: policydir should be relative to `datadir`, not `prefix`. Fixed in https://gitlab.freedesktop.org/polkit/polkit/merge_requests/2
polkit_gobject_policydir = dependency('polkit-gobject-1').get_variable(pkgconfig: 'policydir', pkgconfig_define: ['prefix', nm_prefix]) polkit_policydir = dependency('polkit-gobject-1').get_variable(pkgconfig: 'policydir', pkgconfig_define: ['prefix', nm_prefix])
polkit_rulesdir = join_paths(fs.parent(polkit_policydir), 'rules.d')
endif endif
config_auth_polkit_default = get_option('config_auth_polkit_default') config_auth_polkit_default = get_option('config_auth_polkit_default')
@ -522,6 +560,12 @@ endif
config_h.set_quoted('NM_CONFIG_DEFAULT_MAIN_AUTH_POLKIT', config_auth_polkit_default) config_h.set_quoted('NM_CONFIG_DEFAULT_MAIN_AUTH_POLKIT', config_auth_polkit_default)
enable_modify_system = get_option('modify_system') enable_modify_system = get_option('modify_system')
if enable_modify_system
# FIXME: remove this after everyone has stopped using modify_system
error('modify_system=true is no longer allowed due to security reasons')
endif
polkit_noauth_group = get_option('polkit_noauth_group')
polkit_agent_helper_1_path = get_option('polkit_agent_helper_1') polkit_agent_helper_1_path = get_option('polkit_agent_helper_1')
foreach p : [ '/usr/libexec/polkit-agent-helper-1', foreach p : [ '/usr/libexec/polkit-agent-helper-1',
@ -616,6 +660,7 @@ if enable_modem_manager
endif endif
config_h.set_quoted('MOBILE_BROADBAND_PROVIDER_INFO_DATABASE', mobile_broadband_provider_info_database) config_h.set_quoted('MOBILE_BROADBAND_PROVIDER_INFO_DATABASE', mobile_broadband_provider_info_database)
endif endif
config_h.set10('WITH_WWAN', enable_modem_manager)
# Bluez5 DUN support # Bluez5 DUN support
enable_bluez5_dun = get_option('bluez5_dun') enable_bluez5_dun = get_option('bluez5_dun')
@ -816,6 +861,7 @@ if enable_nm_cloud_setup
assert(jansson_dep.found(), 'nm-cloud-setup requires jansson library. Use -Dnm_cloud_setup=false to disable it') assert(jansson_dep.found(), 'nm-cloud-setup requires jansson library. Use -Dnm_cloud_setup=false to disable it')
endif endif
enable_man = get_option('man')
enable_docs = get_option('docs') enable_docs = get_option('docs')
more_asserts = get_option('more_asserts') more_asserts = get_option('more_asserts')
@ -914,7 +960,6 @@ endif
test_args = [ test_args = [
'--called-from-make', '--called-from-make',
build_root, build_root,
'',
enable_valgrind ? valgrind_path : '', enable_valgrind ? valgrind_path : '',
enable_valgrind ? valgrind_suppressions_path : '', enable_valgrind ? valgrind_suppressions_path : '',
'--launch-dbus=auto', '--launch-dbus=auto',
@ -953,7 +998,6 @@ data_conf.set('NM_DHCP_CLIENTS_ENABLED', ', '.join(config_dhcp_c
data_conf.set('NM_MAJOR_VERSION', nm_major_version) data_conf.set('NM_MAJOR_VERSION', nm_major_version)
data_conf.set('NM_MICRO_VERSION', nm_micro_version) data_conf.set('NM_MICRO_VERSION', nm_micro_version)
data_conf.set('NM_MINOR_VERSION', nm_minor_version) data_conf.set('NM_MINOR_VERSION', nm_minor_version)
data_conf.set('NM_MODIFY_SYSTEM_POLICY', (enable_modify_system ? 'yes' : 'auth_admin_keep'))
data_conf.set('NM_VERSION', nm_version) data_conf.set('NM_VERSION', nm_version)
data_conf.set('VERSION', nm_version) data_conf.set('VERSION', nm_version)
data_conf.set('bindir', nm_bindir) data_conf.set('bindir', nm_bindir)
@ -964,38 +1008,6 @@ data_conf.set('nmstatedir', nm_pkgstatedir)
data_conf.set('sbindir', nm_sbindir) data_conf.set('sbindir', nm_sbindir)
data_conf.set('sysconfdir', nm_sysconfdir) data_conf.set('sysconfdir', nm_sysconfdir)
# check if we can build setting property documentation
'''
build_docs=no
if test -n "$INTROSPECTION_MAKEFILE"; then
# If g-i is installed we know we have python, but we might not have pygobject
if ! "$PYTHON" -c 'from gi.repository import GObject' >& /dev/null; then
AC_MSG_ERROR(["--enable-introspection aims to build the settings documentation. This requires GObject introspection for python (pygobject)])
fi
AC_PATH_PROG(PERL, perl)
if test -z "$PERL"; then
AC_MSG_ERROR([--enable-introspection requires perl])
fi
AC_PATH_PROG(XSLTPROC, xsltproc)
if test -z "$XSLTPROC"; then
AC_MSG_ERROR([--enable-introspection requires xsltproc])
fi
have_introspection=yes
if test "$enable_gtk_doc" = "yes"; then
build_docs=yes
fi
else
if test "$enable_gtk_doc" = "yes"; then
# large parts of the documentation require introspection/pygobject to extract
# the documentation out of the source files. You cannot enable gtk-doc without alone.
AC_MSG_ERROR(["--with-gtk-doc requires --enable-introspection"])
fi
have_introspection=no
fi
'''
content_files = [] content_files = []
subdir('introspection') subdir('introspection')
@ -1033,9 +1045,14 @@ if enable_qt != 'false'
endif endif
endif endif
# The man/ directory builds a couple targets needed by the docs build too.
# If we build with docs but no man, then enter the subdir and only build
# some targets.
if enable_docs or enable_man
subdir('man')
endif
if enable_docs if enable_docs
assert(enable_introspection, '-Ddocs=true requires -Dintrospection=true') assert(enable_introspection, '-Ddocs=true requires -Dintrospection=true')
subdir('man')
subdir('docs') subdir('docs')
meson.add_dist_script( meson.add_dist_script(
'tools/meson-dist-data.sh', 'tools/meson-dist-data.sh',
@ -1086,7 +1103,7 @@ meson.add_install_script(
nm_pkgstatedir, nm_pkgstatedir,
nm_mandir, nm_mandir,
nm_sysconfdir, nm_sysconfdir,
enable_docs ? '1' : '0', enable_man ? '1' : '0',
enable_ifcfg_rh ? '1' : '0', enable_ifcfg_rh ? '1' : '0',
enable_nm_cloud_setup ? '1' : '0', enable_nm_cloud_setup ? '1' : '0',
install_systemdunitdir ? '1' : '0', install_systemdunitdir ? '1' : '0',
@ -1096,6 +1113,7 @@ output = '\nSystem paths:\n'
output += ' prefix: ' + nm_prefix + '\n' output += ' prefix: ' + nm_prefix + '\n'
output += ' exec_prefix: ' + nm_prefix + '\n' output += ' exec_prefix: ' + nm_prefix + '\n'
output += ' systemdunitdir: ' + systemd_systemdsystemunitdir + '\n' output += ' systemdunitdir: ' + systemd_systemdsystemunitdir + '\n'
output += ' systemdgeneratordir: ' + systemd_systemdsystemgeneratordir + '\n'
output += ' udev_dir: ' + udev_udevdir + '\n' output += ' udev_dir: ' + udev_udevdir + '\n'
output += ' nmbinary: ' + nm_pkgsbindir + '\n' output += ' nmbinary: ' + nm_pkgsbindir + '\n'
output += ' nmconfdir: ' + nm_pkgconfdir + '\n' output += ' nmconfdir: ' + nm_pkgconfdir + '\n'
@ -1110,17 +1128,7 @@ output += ' dbus_conf_dir: ' + dbus_conf_dir + '\n'
output += '\nPlatform:\n' output += '\nPlatform:\n'
output += ' session tracking: ' + ','.join(session_trackers) + '\n' output += ' session tracking: ' + ','.join(session_trackers) + '\n'
output += ' suspend/resume: ' + suspend_resume + '\n' output += ' suspend/resume: ' + suspend_resume + '\n'
output += ' policykit: ' + enable_polkit.to_string() + ' (default: ' + config_auth_polkit_default + ')' output += ' policykit: ' + enable_polkit.to_string() + ' (default: ' + config_auth_polkit_default + ', noauth_group: "' + polkit_noauth_group + '")\n'
if enable_polkit
output += ' ('
if enable_modify_system
output += 'permissive'
else
output += 'restrictive'
endif
output += ' modify.system)'
endif
output += '\n'
output += ' polkit-agent-helper-1: ' + polkit_agent_helper_1_path + '\n' output += ' polkit-agent-helper-1: ' + polkit_agent_helper_1_path + '\n'
output += ' selinux: ' + enable_selinux.to_string() + '\n' output += ' selinux: ' + enable_selinux.to_string() + '\n'
output += ' systemd-journald: ' + enable_systemd_journal.to_string() + ' (default: logging.backend=' + config_logging_backend_default + ')\n' output += ' systemd-journald: ' + enable_systemd_journal.to_string() + ' (default: logging.backend=' + config_logging_backend_default + ')\n'
@ -1148,6 +1156,7 @@ output += ' ofono: ' + enable_ofono.to_string() + '\n'
output += ' concheck: ' + enable_concheck.to_string() + '\n' output += ' concheck: ' + enable_concheck.to_string() + '\n'
output += ' libteamdctl: ' + enable_teamdctl.to_string() + '\n' output += ' libteamdctl: ' + enable_teamdctl.to_string() + '\n'
output += ' ovs: ' + enable_ovs.to_string() + '\n' output += ' ovs: ' + enable_ovs.to_string() + '\n'
output += ' clat: ' + enable_clat.to_string() + '\n'
output += ' nmcli: ' + enable_nmcli.to_string() + '\n' output += ' nmcli: ' + enable_nmcli.to_string() + '\n'
output += ' nmtui: ' + enable_nmtui.to_string() + '\n' output += ' nmtui: ' + enable_nmtui.to_string() + '\n'
output += ' nm-cloud-setup: ' + enable_nm_cloud_setup.to_string() + '\n' output += ' nm-cloud-setup: ' + enable_nm_cloud_setup.to_string() + '\n'
@ -1184,6 +1193,5 @@ output += 'have-nss: ' + crypto_nss_dep.found().to_string() + ')\n'
output += ' sanitizers: ' + get_option('b_sanitize') + '\n' output += ' sanitizers: ' + get_option('b_sanitize') + '\n'
output += ' Mozilla Public Suffix List: ' + enable_libpsl.to_string() + '\n' output += ' Mozilla Public Suffix List: ' + enable_libpsl.to_string() + '\n'
output += ' vapi: ' + enable_vapi.to_string() + '\n' output += ' vapi: ' + enable_vapi.to_string() + '\n'
output += ' ebpf: ' + enable_ebpf.to_string() + '\n'
output += ' readline: ' + with_readline + '\n' output += ' readline: ' + with_readline + '\n'
message(output) message(output)

View file

@ -1,5 +1,6 @@
# system paths # system paths
option('systemdsystemunitdir', type: 'string', value: '', description: 'Directory for systemd service files') option('systemdsystemunitdir', type: 'string', value: '', description: 'Directory for systemd service files')
option('systemdsystemgeneratordir', type: 'string', value: '', description: 'Directory for systemd generator files')
option('system_ca_path', type: 'string', value: '/etc/ssl/certs', description: 'path to system CA certificates') option('system_ca_path', type: 'string', value: '/etc/ssl/certs', description: 'path to system CA certificates')
option('udev_dir', type: 'string', value: '', description: 'Absolute path of the udev base directory. Set to \'no\' not to install the udev rule') option('udev_dir', type: 'string', value: '', description: 'Absolute path of the udev base directory. Set to \'no\' not to install the udev rule')
option('dbus_conf_dir', type: 'string', value: '', description: 'where D-Bus system.d directory is') option('dbus_conf_dir', type: 'string', value: '', description: 'where D-Bus system.d directory is')
@ -18,7 +19,8 @@ option('session_tracking', type: 'combo', choices: ['systemd', 'elogind', 'no'],
option('suspend_resume', type: 'combo', choices: ['systemd', 'elogind', 'consolekit', 'auto'], value: 'auto', description: 'Build NetworkManager with specific suspend/resume support') option('suspend_resume', type: 'combo', choices: ['systemd', 'elogind', 'consolekit', 'auto'], value: 'auto', description: 'Build NetworkManager with specific suspend/resume support')
option('polkit', type: 'boolean', value: true, description: 'User auth-polkit configuration option.') option('polkit', type: 'boolean', value: true, description: 'User auth-polkit configuration option.')
option('config_auth_polkit_default', type: 'combo', choices: ['default', 'true', 'false', 'root-only'], value: 'default', description: 'Default value for configuration main.auth-polkit.') option('config_auth_polkit_default', type: 'combo', choices: ['default', 'true', 'false', 'root-only'], value: 'default', description: 'Default value for configuration main.auth-polkit.')
option('modify_system', type: 'boolean', value: false, description: 'Allow users to modify system connections') option('modify_system', type: 'boolean', value: false, description: 'Allow users to modify system connections (option no longer supported, don\'t use)')
option('polkit_noauth_group', type: 'string', value: '', description: 'Allow users of the selected group, typically sudo or wheel, to modify system connections without introducing a password (discouraged)')
option('polkit_agent_helper_1', type: 'string', value: '', description: 'Path name to the polkit-agent-helper-1 binary from polkit') option('polkit_agent_helper_1', type: 'string', value: '', description: 'Path name to the polkit-agent-helper-1 binary from polkit')
option('selinux', type: 'boolean', value: true, description: 'Build with SELinux') option('selinux', type: 'boolean', value: true, description: 'Build with SELinux')
option('systemd_journal', type: 'boolean', value: true, description: 'Use systemd journal for logging') option('systemd_journal', type: 'boolean', value: true, description: 'Use systemd journal for logging')
@ -28,7 +30,7 @@ option('hostname_persist', type: 'combo', choices: ['default', 'suse', 'gentoo',
option('libaudit', type: 'combo', choices: ['yes', 'yes-disabled-by-default', 'no'], value: 'yes', description: 'Build with audit daemon support. yes-disabled-by-default enables support, but disables it unless explicitly configured via NetworkManager.conf') option('libaudit', type: 'combo', choices: ['yes', 'yes-disabled-by-default', 'no'], value: 'yes', description: 'Build with audit daemon support. yes-disabled-by-default enables support, but disables it unless explicitly configured via NetworkManager.conf')
# features # features
option('wext', type: 'boolean', value: true, description: 'Enable or disable Linux Wireless Extensions') option('wext', type: 'combo', choices: ['true', 'false', 'force' ], value: 'false', description: 'Enable or disable Linux Wireless Extensions (deprecated). wext support will be removed in a future release, don\'t rely on this.')
option('wifi', type: 'boolean', value: true, description: 'enable Wi-Fi support') option('wifi', type: 'boolean', value: true, description: 'enable Wi-Fi support')
option('iwd', type: 'boolean', value: false, description: 'enable iwd support (experimental)') option('iwd', type: 'boolean', value: false, description: 'enable iwd support (experimental)')
option('ppp', type: 'boolean', value: true, description: 'enable PPP/PPPoE support') option('ppp', type: 'boolean', value: true, description: 'enable PPP/PPPoE support')
@ -44,8 +46,11 @@ option('nmcli', type: 'boolean', value: true, description: 'Build nmcli')
option('nmtui', type: 'boolean', value: true, description: 'Build nmtui') option('nmtui', type: 'boolean', value: true, description: 'Build nmtui')
option('nm_cloud_setup', type: 'boolean', value: true, description: 'Build nm-cloud-setup, a tool for automatically configuring networking in cloud') option('nm_cloud_setup', type: 'boolean', value: true, description: 'Build nm-cloud-setup, a tool for automatically configuring networking in cloud')
option('bluez5_dun', type: 'boolean', value: false, description: 'enable Bluez5 DUN support') option('bluez5_dun', type: 'boolean', value: false, description: 'enable Bluez5 DUN support')
option('ebpf', type: 'combo', choices: ['auto', 'true', 'false'], description: 'Enable eBPF support') option('ebpf', type: 'combo', choices: ['auto', 'true', 'false'], description: 'Enable eBPF support (deprecated)')
option('nbft', type: 'boolean', value: true, description: 'Enable NBFT support in the initrd generator') option('nbft', type: 'boolean', value: true, description: 'Enable NBFT support in the initrd generator')
option('clat', type: 'boolean', value: true, description: 'Build with CLAT support')
option('bpf-compiler', type : 'combo', choices : ['auto', 'clang', 'gcc'],
description : 'compiler used to build BPF programs')
# configuration plugins # configuration plugins
option('config_plugins_default', type: 'string', value: '', description: 'Default configuration option for main.plugins setting, used as fallback if the configuration option is unset') option('config_plugins_default', type: 'string', value: '', description: 'Default configuration option for main.plugins setting, used as fallback if the configuration option is unset')
@ -67,6 +72,7 @@ option('config_dhcp_default', type: 'combo', choices: ['dhclient', 'dhcpcd', 'in
option('introspection', type: 'boolean', value: true, description: 'Enable introspection for this build') option('introspection', type: 'boolean', value: true, description: 'Enable introspection for this build')
option('vapi', type : 'combo', choices : ['auto', 'true', 'false'], description: 'build Vala bindings') option('vapi', type : 'combo', choices : ['auto', 'true', 'false'], description: 'build Vala bindings')
option('docs', type: 'boolean', value: false, description: 'use to build documentation') option('docs', type: 'boolean', value: false, description: 'use to build documentation')
option('man', type: 'boolean', value: true, description: 'Install manpages')
option('tests', type: 'combo', choices: ['yes', 'no', 'root'], value: 'yes', description: 'Build NetworkManager tests') option('tests', type: 'combo', choices: ['yes', 'no', 'root'], value: 'yes', description: 'Build NetworkManager tests')
option('firewalld_zone', type: 'boolean', value: true, description: 'Install and use firewalld zone for shared mode') option('firewalld_zone', type: 'boolean', value: true, description: 'Install and use firewalld zone for shared mode')
option('more_asserts', type: 'string', value: 'auto', description: 'Enable more assertions for debugging (0 = no, 100 = all, default: auto)') option('more_asserts', type: 'string', value: 'auto', description: 'Enable more assertions for debugging (0 = no, 100 = all, default: auto)')

View file

@ -30,6 +30,7 @@ id
it it
ja ja
ka ka
kk
kn kn
ko ko
ku ku

View file

@ -1,16 +1,18 @@
# List of source files containing translatable strings. # List of source files containing translatable strings.
# Please keep this file sorted alphabetically. # Please keep this file sorted alphabetically.
data/org.freedesktop.NetworkManager.policy.in.in data/org.freedesktop.NetworkManager.policy.in
src/core/NetworkManagerUtils.c src/core/NetworkManagerUtils.c
src/core/devices/adsl/nm-device-adsl.c src/core/devices/adsl/nm-device-adsl.c
src/core/devices/bluetooth/nm-bluez-manager.c src/core/devices/bluetooth/nm-bluez-manager.c
src/core/devices/bluetooth/nm-device-bt.c src/core/devices/bluetooth/nm-device-bt.c
src/core/devices/nm-device.c
src/core/devices/nm-device-6lowpan.c src/core/devices/nm-device-6lowpan.c
src/core/devices/nm-device-bond.c src/core/devices/nm-device-bond.c
src/core/devices/nm-device-bridge.c src/core/devices/nm-device-bridge.c
src/core/devices/nm-device-dummy.c src/core/devices/nm-device-dummy.c
src/core/devices/nm-device-ethernet-utils.c src/core/devices/nm-device-ethernet-utils.c
src/core/devices/nm-device-ethernet.c src/core/devices/nm-device-ethernet.c
src/core/devices/nm-device-geneve.c
src/core/devices/nm-device-infiniband.c src/core/devices/nm-device-infiniband.c
src/core/devices/nm-device-ip-tunnel.c src/core/devices/nm-device-ip-tunnel.c
src/core/devices/nm-device-loopback.c src/core/devices/nm-device-loopback.c
@ -46,6 +48,7 @@ src/libnm-client-impl/nm-device-bt.c
src/libnm-client-impl/nm-device-dummy.c src/libnm-client-impl/nm-device-dummy.c
src/libnm-client-impl/nm-device-ethernet.c src/libnm-client-impl/nm-device-ethernet.c
src/libnm-client-impl/nm-device-generic.c src/libnm-client-impl/nm-device-generic.c
src/libnm-client-impl/nm-device-geneve.c
src/libnm-client-impl/nm-device-hsr.c src/libnm-client-impl/nm-device-hsr.c
src/libnm-client-impl/nm-device-infiniband.c src/libnm-client-impl/nm-device-infiniband.c
src/libnm-client-impl/nm-device-ip-tunnel.c src/libnm-client-impl/nm-device-ip-tunnel.c
@ -90,6 +93,7 @@ src/libnm-core-impl/nm-setting-connection.c
src/libnm-core-impl/nm-setting-dcb.c src/libnm-core-impl/nm-setting-dcb.c
src/libnm-core-impl/nm-setting-ethtool.c src/libnm-core-impl/nm-setting-ethtool.c
src/libnm-core-impl/nm-setting-generic.c src/libnm-core-impl/nm-setting-generic.c
src/libnm-core-impl/nm-setting-geneve.c
src/libnm-core-impl/nm-setting-gsm.c src/libnm-core-impl/nm-setting-gsm.c
src/libnm-core-impl/nm-setting-hsr.c src/libnm-core-impl/nm-setting-hsr.c
src/libnm-core-impl/nm-setting-infiniband.c src/libnm-core-impl/nm-setting-infiniband.c

9912
po/bg.po

File diff suppressed because it is too large Load diff

View file

@ -8,14 +8,15 @@
# Lubomir Rintel <lkundrak@v3.sk>, 2016. #zanata # Lubomir Rintel <lkundrak@v3.sk>, 2016. #zanata
# Lubomir Rintel <lkundrak@v3.sk>, 2017. #zanata # Lubomir Rintel <lkundrak@v3.sk>, 2017. #zanata
# Thomas Haller <thaller@redhat.com>, 2017. #zanata # Thomas Haller <thaller@redhat.com>, 2017. #zanata
# Jordi Mas i Hernàndez <jmas@softcatala.org>, 2025
msgid "" msgid ""
msgstr "" msgstr ""
"Project-Id-Version: NetworkManager\n" "Project-Id-Version: NetworkManager\n"
"Report-Msgid-Bugs-To: https://gitlab.freedesktop.org/NetworkManager/" "Report-Msgid-Bugs-To: https://gitlab.freedesktop.org/NetworkManager/"
"NetworkManager/issues\n" "NetworkManager/issues\n"
"POT-Creation-Date: 2023-06-16 15:26+0000\n" "POT-Creation-Date: 2023-06-16 15:26+0000\n"
"PO-Revision-Date: 2023-06-17 00:07+0200\n" "PO-Revision-Date: 2025-09-28 00:07+0200\n"
"Last-Translator: Copied by Zanata <copied-by-zanata@zanata.org>\n" "Last-Translator: Jordi Mas i Hernàndez <jmas@softcatala.org>\n"
"Language-Team: Catalan <tradgnome@softcatala.org>\n" "Language-Team: Catalan <tradgnome@softcatala.org>\n"
"Language: ca\n" "Language: ca\n"
"MIME-Version: 1.0\n" "MIME-Version: 1.0\n"
@ -355,7 +356,7 @@ msgstr "Connexió WPAN"
#: src/core/devices/team/nm-device-team.c:131 #: src/core/devices/team/nm-device-team.c:131
msgid "Team connection" msgid "Team connection"
msgstr "Connexió equip" msgstr "Connexió d'equip"
#: src/core/devices/wifi/nm-device-olpc-mesh.c:112 src/nmcli/devices.c:1400 #: src/core/devices/wifi/nm-device-olpc-mesh.c:112 src/nmcli/devices.c:1400
msgid "Mesh" msgid "Mesh"
@ -648,7 +649,7 @@ msgstr "Surt després de la configuració inicial"
#: src/core/nm-config.c:639 #: src/core/nm-config.c:639
msgid "Don't become a daemon, and log to stderr" msgid "Don't become a daemon, and log to stderr"
msgstr "" msgstr ""
"No et converteixis en un dimoni, i envia el registre a la sortida estàndard" "No et converteixis en un dimoni, i envia el registre a la sortida d'error"
#: src/core/nm-config.c:648 #: src/core/nm-config.c:648
msgid "An http(s) address for checking internet connectivity" msgid "An http(s) address for checking internet connectivity"
@ -795,7 +796,7 @@ msgstr "La connexió no era una connexió Ethernet o PPPoE."
#: src/libnm-client-impl/nm-device-ethernet.c:206 #: src/libnm-client-impl/nm-device-ethernet.c:206
msgid "The connection and device differ in S390 subchannels." msgid "The connection and device differ in S390 subchannels."
msgstr "La connexió i el dispositiu difereixen als subcanals 5930." msgstr "La connexió i el dispositiu difereixen als subcanals S390."
#: src/libnm-client-impl/nm-device-ethernet.c:223 #: src/libnm-client-impl/nm-device-ethernet.c:223
#, c-format #, c-format
@ -881,7 +882,7 @@ msgstr "La connexió no era una connexió tun."
#: src/libnm-client-impl/nm-device-team.c:124 #: src/libnm-client-impl/nm-device-team.c:124
msgid "The connection was not a team connection." msgid "The connection was not a team connection."
msgstr "La connexió no era una connexió equip." msgstr "La connexió no era una connexió d'equip."
#: src/libnm-client-impl/nm-device-tun.c:204 #: src/libnm-client-impl/nm-device-tun.c:204
msgid "The connection was not a tun connection." msgid "The connection was not a tun connection."
@ -1325,27 +1326,27 @@ msgstr ""
#: src/libnm-core-impl/nm-keyfile.c:333 #: src/libnm-core-impl/nm-keyfile.c:333
msgid "ignoring missing number" msgid "ignoring missing number"
msgstr "s'ignora el número faltant" msgstr "s'ignora el número faltant"
#: src/libnm-core-impl/nm-keyfile.c:345 #: src/libnm-core-impl/nm-keyfile.c:345
#, c-format #, c-format
msgid "ignoring invalid number '%s'" msgid "ignoring invalid number '%s'"
msgstr "s'ignora el número «%s» no vàlid" msgstr "s'ignora el número «%s» no vàlid"
#: src/libnm-core-impl/nm-keyfile.c:374 #: src/libnm-core-impl/nm-keyfile.c:374
#, c-format #, c-format
msgid "ignoring invalid %s address: %s" msgid "ignoring invalid %s address: %s"
msgstr "s'ignora l'adreça %s no vàlida: %s" msgstr "s'ignora l'adreça %s no vàlida: %s"
#: src/libnm-core-impl/nm-keyfile.c:420 #: src/libnm-core-impl/nm-keyfile.c:420
#, c-format #, c-format
msgid "ignoring invalid gateway '%s' for %s route" msgid "ignoring invalid gateway '%s' for %s route"
msgstr "s'ignora la passarel·la «%s» no vàlida per a la ruta %s" msgstr "s'ignora la passarel·la «%s» no vàlida per a la ruta %s"
#: src/libnm-core-impl/nm-keyfile.c:442 #: src/libnm-core-impl/nm-keyfile.c:442
#, c-format #, c-format
msgid "ignoring invalid %s route: %s" msgid "ignoring invalid %s route: %s"
msgstr "s'ignora la ruta %s no vàlida: %s" msgstr "s'ignora la ruta %s no vàlida: %s"
#: src/libnm-core-impl/nm-keyfile.c:620 #: src/libnm-core-impl/nm-keyfile.c:620
#, c-format #, c-format
@ -1361,7 +1362,7 @@ msgstr "caràcter «%c» inesperat per a %s: «%s» (posició %td)"
#, c-format #, c-format
msgid "unexpected character '%c' in prefix length for %s: '%s' (position %td)" msgid "unexpected character '%c' in prefix length for %s: '%s' (position %td)"
msgstr "" msgstr ""
"caràcter «%c» inesperat a la longitud de prefix %s: «%s» (posició %td)<" "caràcter «%c» inesperat a la longitud de prefix %s: «%s» (posició %td)"
#: src/libnm-core-impl/nm-keyfile.c:669 #: src/libnm-core-impl/nm-keyfile.c:669
#, c-format #, c-format
@ -1413,11 +1414,11 @@ msgstr "s'ignorarà l'adreça %s no vàlida: %s"
#: src/libnm-core-impl/nm-keyfile.c:1518 #: src/libnm-core-impl/nm-keyfile.c:1518
msgid "ignoring invalid SSID" msgid "ignoring invalid SSID"
msgstr "s'ignora l'SSID no vàlida" msgstr "s'ignora l'SSID no vàlida"
#: src/libnm-core-impl/nm-keyfile.c:1536 #: src/libnm-core-impl/nm-keyfile.c:1536
msgid "ignoring invalid raw password" msgid "ignoring invalid raw password"
msgstr "s'ignora la contrasenya sense processar no vàlida" msgstr "s'ignora la contrasenya sense processar no vàlida"
#: src/libnm-core-impl/nm-keyfile.c:1681 #: src/libnm-core-impl/nm-keyfile.c:1681
msgid "invalid key/cert value" msgid "invalid key/cert value"
@ -1458,7 +1459,7 @@ msgstr "valor de paritat «%s» no vàlid"
#: src/libnm-core-impl/nm-keyfile.c:1958 src/libnm-core-impl/nm-keyfile.c:3540 #: src/libnm-core-impl/nm-keyfile.c:1958 src/libnm-core-impl/nm-keyfile.c:3540
#, c-format #, c-format
msgid "invalid setting: %s" msgid "invalid setting: %s"
msgstr "el paràmetre no és vàlid: «%s»" msgstr "el paràmetre no és vàlid: %s"
#: src/libnm-core-impl/nm-keyfile.c:1978 #: src/libnm-core-impl/nm-keyfile.c:1978
#, fuzzy, c-format #, fuzzy, c-format
@ -1973,7 +1974,7 @@ msgstr "file:// URI no és UTF-8 vàlida"
#: src/libnm-core-impl/nm-setting-connection.c:1501 #: src/libnm-core-impl/nm-setting-connection.c:1501
msgid "invalid permissions not in format \"user:$UNAME[:]\"" msgid "invalid permissions not in format \"user:$UNAME[:]\""
msgstr "els permisos no són vàlids, no estan en el format «user:$UNANE[:]" msgstr "els permisos no són vàlids, no estan en el format «user:$UNAME[:]"
#: src/libnm-core-impl/nm-setting-connection.c:1530 #: src/libnm-core-impl/nm-setting-connection.c:1530
#, c-format #, c-format
@ -2086,7 +2087,7 @@ msgstr "«%s» no és un número"
#: src/libnm-core-impl/nm-setting-gsm.c:479 #: src/libnm-core-impl/nm-setting-gsm.c:479
msgid "property is empty or wrong size" msgid "property is empty or wrong size"
msgstr "la propietat és buda o de mida incorrecta" msgstr "la propietat és buida o de mida incorrecta"
#: src/libnm-core-impl/nm-setting-gsm.c:492 #: src/libnm-core-impl/nm-setting-gsm.c:492
msgid "property must contain only digits" msgid "property must contain only digits"
@ -2098,12 +2099,12 @@ msgstr "no es pot activar quan hi ha una configuració manual"
#: src/libnm-core-impl/nm-setting-infiniband.c:215 #: src/libnm-core-impl/nm-setting-infiniband.c:215
msgid "Must specify a P_Key if specifying parent" msgid "Must specify a P_Key if specifying parent"
msgstr "S'ha d'especificar una P-Key si s'especifica el pare" msgstr "S'ha d'especificar una P_Key si s'especifica el pare"
#: src/libnm-core-impl/nm-setting-infiniband.c:226 #: src/libnm-core-impl/nm-setting-infiniband.c:226
msgid "InfiniBand P_Key connection did not specify parent interface name" msgid "InfiniBand P_Key connection did not specify parent interface name"
msgstr "" msgstr ""
"La connexió InfiniBand P_Key no ha especificat el nom de l'interfície pare" "La connexió InfiniBand P_Key no ha especificat el nom de la interfície pare"
#: src/libnm-core-impl/nm-setting-infiniband.c:234 #: src/libnm-core-impl/nm-setting-infiniband.c:234
msgid "the values 0 and 0x8000 are not allowed" msgid "the values 0 and 0x8000 are not allowed"
@ -2156,12 +2157,12 @@ msgstr "Adreça IPv4 «%s» no és vàlida"
#: src/libnm-core-impl/nm-setting-ip-config.c:106 #: src/libnm-core-impl/nm-setting-ip-config.c:106
#, c-format #, c-format
msgid "Invalid IPv4 address prefix '%u'" msgid "Invalid IPv4 address prefix '%u'"
msgstr "Prefix «%u» d'adreça IPv4 no vàlida" msgstr "Prefix «%u» d'adreça IPv4 no vàlid"
#: src/libnm-core-impl/nm-setting-ip-config.c:107 #: src/libnm-core-impl/nm-setting-ip-config.c:107
#, c-format #, c-format
msgid "Invalid IPv6 address prefix '%u'" msgid "Invalid IPv6 address prefix '%u'"
msgstr "Prefix «%u» d'adreça IPv6 no vàlida<" msgstr "Prefix «%u» d'adreça IPv6 no vàlid"
#: src/libnm-core-impl/nm-setting-ip-config.c:124 #: src/libnm-core-impl/nm-setting-ip-config.c:124
#, c-format #, c-format
@ -2208,7 +2209,7 @@ msgstr "el prefix %s no és vàlid"
#: src/libnm-core-impl/nm-setting-ip-config.c:1423 #: src/libnm-core-impl/nm-setting-ip-config.c:1423
#, c-format #, c-format
msgid "%s is not a valid route type" msgid "%s is not a valid route type"
msgstr "%s no és un nom de ruta vàlid" msgstr "%s no és un tipus de ruta vàlid"
#: src/libnm-core-impl/nm-setting-ip-config.c:1442 #: src/libnm-core-impl/nm-setting-ip-config.c:1442
#, fuzzy #, fuzzy
@ -2432,7 +2433,7 @@ msgstr "La ruta %d. no és vàlida"
#: src/libnm-core-impl/nm-setting-ip-config.c:5638 #: src/libnm-core-impl/nm-setting-ip-config.c:5638
#, c-format #, c-format
msgid "invalid attribute: %s" msgid "invalid attribute: %s"
msgstr "atribut no vàlid: «%s»" msgstr "atribut no vàlid: %s"
#: src/libnm-core-impl/nm-setting-ip-config.c:5658 #: src/libnm-core-impl/nm-setting-ip-config.c:5658
#, c-format #, c-format
@ -4105,7 +4106,7 @@ msgstr "«%s» no és vàlid; useu [%s] or [%s]"
#: src/libnmc-base/nm-client-utils.c:176 #: src/libnmc-base/nm-client-utils.c:176
#, c-format #, c-format
msgid "'%s' is not valid; use [%s], [%s] or [%s]" msgid "'%s' is not valid; use [%s], [%s] or [%s]"
msgstr "«%s» no és vàld, useu [%s], [%s] o [%s]" msgstr "«%s» no és vàlid, useu [%s], [%s] o [%s]"
#: src/libnmc-base/nm-client-utils.c:230 #: src/libnmc-base/nm-client-utils.c:230
#, c-format #, c-format
@ -4676,7 +4677,7 @@ msgstr "clau privada no vàlida"
#, fuzzy, c-format #, fuzzy, c-format
msgid "Secrets are required to connect WireGuard VPN '%s'" msgid "Secrets are required to connect WireGuard VPN '%s'"
msgstr "" msgstr ""
"Es requereixen contrasenyes o claus d'encriptació per accedir la xarxa sens " "Es requereixen contrasenyes o claus d'encriptació per accedir la xarxa sense "
"fil «%s»." "fil «%s»."
#: src/libnmc-base/nm-secret-agent-simple.c:620 #: src/libnmc-base/nm-secret-agent-simple.c:620
@ -4698,7 +4699,7 @@ msgid ""
"Passwords or encryption keys are required to access the wireless network " "Passwords or encryption keys are required to access the wireless network "
"'%s'." "'%s'."
msgstr "" msgstr ""
"Es requereixen contrasenyes o claus d'encriptació per accedir la xarxa sens " "Es requereixen contrasenyes o claus d'encriptació per accedir la xarxa sense "
"fil «%s»." "fil «%s»."
#: src/libnmc-base/nm-secret-agent-simple.c:886 #: src/libnmc-base/nm-secret-agent-simple.c:886
@ -4709,7 +4710,7 @@ msgstr "Autenticació 802.1X de xarxa amb fil"
#, fuzzy, c-format #, fuzzy, c-format
msgid "Secrets are required to access the wired network '%s'" msgid "Secrets are required to access the wired network '%s'"
msgstr "" msgstr ""
"Es requereixen contrasenyes o claus d'encriptació per accedir la xarxa sens " "Es requereixen contrasenyes o claus d'encriptació per accedir la xarxa sense "
"fil «%s»." "fil «%s»."
#: src/libnmc-base/nm-secret-agent-simple.c:893 #: src/libnmc-base/nm-secret-agent-simple.c:893
@ -5418,9 +5419,9 @@ msgid ""
msgstr "" msgstr ""
"Entreu els bytes com una llista de valors hexadecimals.\n" "Entreu els bytes com una llista de valors hexadecimals.\n"
"S'accepten dos formats:\n" "S'accepten dos formats:\n"
"(a) una cadena de dígits exadecimals, on cada dos dígits representen un " "(a) una cadena de dígits hexadecimals, on cada dos dígits representen un "
"byte\n" "byte\n"
"(b) una llista separada per espais de bytes escrits com a dígits hexadecimas " "(b) una llista separada per espais de bytes escrits com a dígits hexadecimals "
"(amb prefix opcional 0x/0X,i un 0 inicial opcional).\n" "(amb prefix opcional 0x/0X,i un 0 inicial opcional).\n"
"\n" "\n"
"Exemples: ab0455a6ea3a74C2\n" "Exemples: ab0455a6ea3a74C2\n"
@ -5493,7 +5494,7 @@ msgstr "Demora cap endavant"
#: src/libnmc-setting/nm-meta-setting-desc.c:5280 #: src/libnmc-setting/nm-meta-setting-desc.c:5280
#: src/nmtui/nmt-page-bridge.c:134 #: src/nmtui/nmt-page-bridge.c:134
msgid "Hello time" msgid "Hello time"
msgstr "Temps de benviguda" msgstr "Temps de benvinguda"
#: src/libnmc-setting/nm-meta-setting-desc.c:5286 #: src/libnmc-setting/nm-meta-setting-desc.c:5286
#: src/nmtui/nmt-page-bridge.c:148 #: src/nmtui/nmt-page-bridge.c:148
@ -5567,7 +5568,7 @@ msgid ""
msgstr "" msgstr ""
"Entreu les connexions secundàries que s'haurien d'activar quan s'activa " "Entreu les connexions secundàries que s'haurien d'activar quan s'activa "
"aquesta connexió. Les connexions es poden especificar o bé per UUID o per ID " "aquesta connexió. Les connexions es poden especificar o bé per UUID o per ID "
"(nom). L'nmcli tradueix transparentment els noms a UUID. Noteu que el " "(nom). nmcli tradueix transparentment els noms a UUID. Noteu que el "
"NetworkManager actualment sols dóna suport els VPN com a connexions " "NetworkManager actualment sols dóna suport els VPN com a connexions "
"secundàries.\n" "secundàries.\n"
"Els elements es poden separar per comes o espais.\n" "Els elements es poden separar per comes o espais.\n"
@ -5676,7 +5677,7 @@ msgid ""
" priority [prio] [from [src]] [to [dst]], ,...\n" " priority [prio] [from [src]] [to [dst]], ,...\n"
"\n" "\n"
msgstr "" msgstr ""
"Introduïu una llista de regles d'encaminanent IPv4 amb el següent format:\n" "Introduïu una llista de regles d'encaminament IPv4 amb el següent format:\n"
" priority [prioritat] [from [origen]] [to [destí]], ,...\n" " priority [prioritat] [from [origen]] [to [destí]], ,...\n"
"\n" "\n"
"\n" "\n"
@ -5696,7 +5697,7 @@ msgstr ""
"configuració IPv6 \n" "configuració IPv6 \n"
"és «auto» aquests servidors DNS s'annexen als que retorna (si retorna cap) " "és «auto» aquests servidors DNS s'annexen als que retorna (si retorna cap) "
"la \n" "la \n"
"configuració automatica. Els servidors DNS no es poden usar amb els métodes " "configuració automàtica. Els servidors DNS no es poden usar amb els mètodes "
"de \n" "de \n"
"configuracó DNS «shared» o «link-local», atès que no hi una xarxa superior. " "configuracó DNS «shared» o «link-local», atès que no hi una xarxa superior. "
"A tots\n" "A tots\n"
@ -8151,12 +8152,12 @@ msgstr ""
"canonada (|) o un ampersand (&). El primer indica que l'element és opcional " "canonada (|) o un ampersand (&). El primer indica que l'element és opcional "
"i el segon significa que és obligatori. Si hi ha algun element opcional, " "i el segon significa que és obligatori. Si hi ha algun element opcional, "
"llavors la coincidència avalua a cert si almenys un dels elements opcionals " "llavors la coincidència avalua a cert si almenys un dels elements opcionals "
"coincideix (O lògicà). Si hi ha elements obligatoris, llavors tots han de " "coincideix (O lògica). Si hi ha elements obligatoris, llavors tots han de "
"coincidir (I lògica). Per defecte, un element és opcional. Això significa " "coincidir (I lògica). Per defecte, un element és opcional. Això significa "
"que un element «foo» es comporta igual que «|foo». Un element també es pot " "que un element «foo» es comporta igual que «|foo». Un element també es pot "
"invertir amb el símbol d'exclamació (!) entre el símbol de la canonada (o de " "invertir amb el símbol d'exclamació (!) entre el símbol de la canonada (o de "
"l'ampersand) i abans del patró. Tingueu en compte que «!foo» és una drecera " "l'ampersand) i abans del patró. Tingueu en compte que «!foo» és una drecera "
"per al patró obligatòri «&!foo». Finalment, es pot utilitzar una barra " "per al patró obligatori «&!foo». Finalment, es pot utilitzar una barra "
"inversa al començament de l'element (després dels caràcters especials " "inversa al començament de l'element (després dels caràcters especials "
"opcionals) per no considerar-lo inici del patró. Per exemple, «\\!a» és una " "opcionals) per no considerar-lo inici del patró. Per exemple, «\\!a» és una "
"coincidència obligatòria per literalment «!a»." "coincidència obligatòria per literalment «!a»."
@ -10722,7 +10723,7 @@ msgstr "Error: «%s» no és una connexió activa.\n"
#: src/nmcli/connections.c:3436 #: src/nmcli/connections.c:3436
msgid "Error: not all active connections found." msgid "Error: not all active connections found."
msgstr "Error: No s'han trobar totes les connexions actives." msgstr "Error: No s'han trobat totes les connexions actives."
#: src/nmcli/connections.c:3444 #: src/nmcli/connections.c:3444
msgid "Error: no active connection provided." msgid "Error: no active connection provided."
@ -11041,7 +11042,7 @@ msgstr ""
"Verifica si el paràmetre o la connexió és vàlida i es pot desar més tard.\n" "Verifica si el paràmetre o la connexió és vàlida i es pot desar més tard.\n"
"Indica valors no vàlids quan hi ha un error. Alguns errors es poden " "Indica valors no vàlids quan hi ha un error. Alguns errors es poden "
"corregir\n" "corregir\n"
"automàticaent amb l'opció «fix».\n" "automàticament amb l'opció «fix».\n"
"\n" "\n"
"Exemples: nmcli> verify\n" "Exemples: nmcli> verify\n"
" nmcli> verify fix\n" " nmcli> verify fix\n"
@ -11063,7 +11064,7 @@ msgid ""
msgstr "" msgstr ""
"save [persistent|temporary] :: desa la connexió\n" "save [persistent|temporary] :: desa la connexió\n"
"\n" "\n"
"Envia el perfil de la connexió al NetworManager que o bé la desarà de forma\n" "Envia el perfil de la connexió al NetworkManager que o bé la desarà de forma\n"
"persistent o bé sols la mantindrà a la memòria. «desa» sense cap argument\n" "persistent o bé sols la mantindrà a la memòria. «desa» sense cap argument\n"
"significa «desa de forma persistent».\n" "significa «desa de forma persistent».\n"
"Noteu que un cop que deseu el perfile de forma persistent aquestes " "Noteu que un cop que deseu el perfile de forma persistent aquestes "
@ -11485,7 +11486,7 @@ msgstr "Opció no vàlida de verificació: %s\n"
#: src/nmcli/connections.c:8486 #: src/nmcli/connections.c:8486
#, c-format #, c-format
msgid "Verify setting '%s': %s\n" msgid "Verify setting '%s': %s\n"
msgstr "Verifica el paràmere «%s»: %s\n" msgstr "Verifica el paràmetre «%s»: %s\n"
#: src/nmcli/connections.c:8501 #: src/nmcli/connections.c:8501
#, c-format #, c-format
@ -11552,12 +11553,12 @@ msgstr "Error: no es pot activar la connexió: %s.\n"
#: src/nmcli/connections.c:8679 #: src/nmcli/connections.c:8679
#, c-format #, c-format
msgid "Error: Failed to activate '%s' (%s) connection: %s\n" msgid "Error: Failed to activate '%s' (%s) connection: %s\n"
msgstr "Error: no s'ha pogut desconnectar la connexió «%s» (%s): %s\n" msgstr "Error: no s'ha pogut activar la connexió «%s» (%s): %s\n"
#: src/nmcli/connections.c:8686 #: src/nmcli/connections.c:8686
msgid "Monitoring connection activation (press any key to continue)\n" msgid "Monitoring connection activation (press any key to continue)\n"
msgstr "" msgstr ""
"S'està supervisant l'activació de la connexio (premeu qualsevol teclar per " "S'està supervisant l'activació de la connexió (premeu qualsevol tecla per "
"continuar)\n" "continuar)\n"
#: src/nmcli/connections.c:8721 #: src/nmcli/connections.c:8721
@ -11582,7 +11583,7 @@ msgstr "Configuració actual del nmcli:\n"
#: src/nmcli/connections.c:8753 #: src/nmcli/connections.c:8753
#, c-format #, c-format
msgid "Invalid configuration option '%s'; allowed [%s]\n" msgid "Invalid configuration option '%s'; allowed [%s]\n"
msgstr "Opció de configuració no vàida: «%s»; es permet [%s]\n" msgstr "Opció de configuració no vàlida: «%s»; es permet [%s]\n"
#: src/nmcli/connections.c:8985 #: src/nmcli/connections.c:8985
#, fuzzy #, fuzzy
@ -12396,7 +12397,7 @@ msgstr "Error: no s'ha pogut afegir/activar la connexió nova: %s"
#: src/nmcli/devices.c:2266 #: src/nmcli/devices.c:2266
#, c-format #, c-format
msgid "Error: Device activation failed: %s" msgid "Error: Device activation failed: %s"
msgstr "Error: no s'ha pogut activar el dispositu: %s" msgstr "Error: no s'ha pogut activar el dispositiu: %s"
#: src/nmcli/devices.c:2322 #: src/nmcli/devices.c:2322
#, c-format #, c-format
@ -12603,7 +12604,7 @@ msgstr "Contrasenya: "
#: src/nmcli/devices.c:4172 #: src/nmcli/devices.c:4172
#, c-format #, c-format
msgid "'%s' is not valid WPA PSK" msgid "'%s' is not valid WPA PSK"
msgstr "«%s» no és una WPS PSK vàlida" msgstr "«%s» no és una WPA PSK vàlida"
#: src/nmcli/devices.c:4193 #: src/nmcli/devices.c:4193
#, c-format #, c-format
@ -13538,7 +13539,7 @@ msgstr "Error: s'esperava l'argument «%s», però s'ha proporcionat «%s»."
#: src/nmcli/utils.c:315 #: src/nmcli/utils.c:315
#, c-format #, c-format
msgid "Error: Unexpected argument '%s'" msgid "Error: Unexpected argument '%s'"
msgstr "Error: argument inesperat «%s»." msgstr "Error: argument inesperat «%s»"
#: src/nmcli/utils.c:702 #: src/nmcli/utils.c:702
#, fuzzy, c-format #, fuzzy, c-format
@ -13897,7 +13898,7 @@ msgstr "«%s» <"
#. NB: the ordering/numbering here corresponds to NmtPageBondMonitoringMode #. NB: the ordering/numbering here corresponds to NmtPageBondMonitoringMode
#: src/nmtui/nmt-page-bond.c:92 #: src/nmtui/nmt-page-bond.c:92
msgid "MII (recommended)" msgid "MII (recommended)"
msgstr "MII (recomendat)" msgstr "MII (recomanat)"
#: src/nmtui/nmt-page-bond.c:93 #: src/nmtui/nmt-page-bond.c:93
msgid "ARP" msgid "ARP"
@ -14543,7 +14544,7 @@ msgstr ""
#: src/nmtui/nmtui-edit.c:394 src/nmtui/nmtui-edit.c:410 #: src/nmtui/nmtui-edit.c:394 src/nmtui/nmtui-edit.c:410
msgid "New Connection" msgid "New Connection"
msgstr "Connexions nova" msgstr "Connexió nova"
#: src/nmtui/nmtui-edit.c:452 #: src/nmtui/nmtui-edit.c:452
#, c-format #, c-format

View file

@ -12596,7 +12596,7 @@ msgstr "Digitare «help» o «?» per i comandi disponibili."
#. TRANSLATORS: do not translate 'print', leave it as it is #. TRANSLATORS: do not translate 'print', leave it as it is
#: src/nmcli/connections.c:9072 #: src/nmcli/connections.c:9072
msgid "Type 'print' to show all the connection properties." msgid "Type 'print' to show all the connection properties."
msgstr "Digitare «stampa» per mostrare tutte le proprietà della connessione." msgstr "Digitare «print» per mostrare tutte le proprietà della connessione."
#. TRANSLATORS: do not translate 'describe', leave it as it is #. TRANSLATORS: do not translate 'describe', leave it as it is
#: src/nmcli/connections.c:9075 #: src/nmcli/connections.c:9075

16300
po/kk.po Normal file

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

4793
po/ru.po

File diff suppressed because it is too large Load diff

368
po/sk.po

File diff suppressed because it is too large Load diff

10236
po/sl.po

File diff suppressed because it is too large Load diff

15967
po/sr.po

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

5388
po/tr.po

File diff suppressed because it is too large Load diff

View file

@ -155,3 +155,33 @@ nm_vpn_plugin_utils_load_editor(const char *module_path,
g_return_val_if_fail(NM_IS_VPN_EDITOR(editor), NULL); g_return_val_if_fail(NM_IS_VPN_EDITOR(editor), NULL);
return editor; return editor;
} }
char *
nm_vpn_plugin_utils_get_cert_path(const char *plugin)
{
const char *path;
g_return_val_if_fail(plugin, NULL);
/* Users can set NM_CERT_PATH=~/.cert to be compatible with the certificate
* directory used in the past. */
path = g_getenv("NM_CERT_PATH");
if (path)
return g_build_filename(path, plugin, NULL);
/* Otherwise use XDG_DATA_HOME. We use subdirectory "networkmanagement/certificates"
* because the SELinux policy already has rules to set the correct labels in that
* directory. */
path = g_getenv("XDG_DATA_HOME");
if (path)
return g_build_filename(path, "networkmanagement", "certificates", plugin, NULL);
/* Use the default value for XDG_DATA_HOME */
return g_build_filename(g_get_home_dir(),
".local",
"share",
"networkmanagement",
"certificates",
plugin,
NULL);
}

View file

@ -24,4 +24,6 @@ NMVpnEditor *nm_vpn_plugin_utils_load_editor(const char *modul
gpointer user_data, gpointer user_data,
GError **error); GError **error);
char *nm_vpn_plugin_utils_get_cert_path(const char *plugin);
#endif /* __NM_VPN_PLUGIN_UTILS_H__ */ #endif /* __NM_VPN_PLUGIN_UTILS_H__ */

View file

@ -1495,11 +1495,10 @@ nm_utils_ip_route_attribute_to_platform(int addr_family,
r4->scope_inv = nm_platform_route_scope_inv(scope); r4->scope_inv = nm_platform_route_scope_inv(scope);
} }
/* Note that for IPv4 routes in kernel, the onlink flag can be set for /* For IPv4 routes in kernel, the onlink flag is per-nexthop (rtnh_flags).
* each next hop separately (rtnh_flags). Not for NetworkManager. We can * Here we set the flag on r_rtm_flags which represents the first nexthop's
* only merge routes as ECMP routes (when setting a weight) if they all * flags. For ECMP routes, each nexthop carries its own onlink flag, so
* share the same onlink flag. See NM_PLATFORM_IP_ROUTE_CMP_TYPE_ECMP_ID. * routes with different onlink settings per-nexthop can be merged. */
* That simplifies the code. */
GET_ATTR(NM_IP_ROUTE_ATTRIBUTE_ONLINK, onlink, BOOLEAN, boolean, FALSE); GET_ATTR(NM_IP_ROUTE_ATTRIBUTE_ONLINK, onlink, BOOLEAN, boolean, FALSE);
r->r_rtm_flags = ((onlink) ? (unsigned) RTNH_F_ONLINK : 0u); r->r_rtm_flags = ((onlink) ? (unsigned) RTNH_F_ONLINK : 0u);

1203
src/core/bpf/clat.bpf.c Normal file

File diff suppressed because it is too large Load diff

30
src/core/bpf/clat.h Normal file
View file

@ -0,0 +1,30 @@
/* SPDX-License-Identifier: GPL-2.0 */
#ifndef __NAT64_H__
#define __NAT64_H__
#include <linux/in6.h>
struct clat_config {
struct in6_addr local_v6;
struct in6_addr pref64;
struct in_addr local_v4;
unsigned pref64_len;
};
struct clat_stats {
/* egress: v4 to v6 */
__u64 egress_tcp;
__u64 egress_udp;
__u64 egress_icmp;
__u64 egress_other;
__u64 egress_dropped;
/* ingress: v6 to v4 */
__u64 ingress_tcp;
__u64 ingress_udp;
__u64 ingress_icmp;
__u64 ingress_other;
__u64 ingress_fragment;
__u64 ingress_dropped;
};
#endif

239
src/core/bpf/meson.build Normal file
View file

@ -0,0 +1,239 @@
# SPDX-License-Identifier: LGPL-2.1+
# Ripped from systemd: https://github.com/systemd/systemd/pull/20429
if not enable_clat
subdir_done()
endif
bpf_compiler = get_option('bpf-compiler')
clang_found = false
clang_supports_bpf = false
bpf_gcc_found = false
bpftool_strip = false
if bpf_compiler == 'clang' or bpf_compiler == 'auto'
# Support 'versioned' clang/llvm-strip binaries, as seen on Debian/Ubuntu
# (like clang-10/llvm-strip-10)
if meson.is_cross_build() or cc.get_id() != 'clang' or cc.cmd_array()[0].contains('afl-clang') or cc.cmd_array()[0].contains('hfuzz-clang')
r = find_program('clang',
version : '>= 10.0.0')
clang_found = r.found()
if clang_found
if meson.version().version_compare('>= 0.55')
clang = r.full_path()
else
clang = r.path()
endif
endif
else
clang_found = true
clang = cc.cmd_array()
endif
if clang_found
# Check if 'clang -target bpf' is supported.
clang_supports_bpf = run_command(clang, '-target', 'bpf', '--print-supported-cpus', check : false).returncode() == 0
endif
elif bpf_compiler == 'gcc' or bpf_compiler == 'auto'
bpf_gcc = find_program('bpf-gcc',
'bpf-none-gcc',
'bpf-unknown-none-gcc',
version : '>= 13.1.0')
bpf_gcc_found = bpf_gcc.found()
endif
if bpf_compiler == 'auto'
if clang_supports_bpf and bpf_gcc_found
# Both supported, prefer the one matching our compiler:
if cc.get_id() == 'gcc'
bpf_compiler = 'gcc'
else
# Default to clang if we don't know this compiler
bpf_compiler = 'clang'
endif
elif clang_supports_bpf
bpf_compiler = 'clang'
elif bpf_gcc_found
bpf_compiler = 'clang'
endif
endif
if clang_supports_bpf or bpf_gcc_found
# Debian installs this in /usr/sbin/ which is not in $PATH.
# We check for 'bpftool' first, honouring $PATH, and in /usr/sbin/ for Debian.
# We use 'bpftool gen object' subcommand for bpftool strip, it was added by d80b2fcbe0a023619e0fc73112f2a02c2662f6ab (v5.13).
bpftool = find_program('bpftool',
'/usr/sbin/bpftool',
required : bpf_compiler == 'gcc',
version : bpf_compiler == 'gcc' ? '>= 7.0.0' : '>= 5.13.0')
if bpftool.found()
bpftool_strip = true
elif bpf_compiler == 'clang'
# We require the 'bpftool gen skeleton' subcommand, it was added by 985ead416df39d6fe8e89580cc1db6aa273e0175 (v5.6).
bpftool = find_program('bpftool',
'/usr/sbin/bpftool',
required : true,
version : '>= 5.6.0')
endif
# We use `llvm-strip` as a fallback if `bpftool gen object` strip support is not available.
if not bpftool_strip and bpftool.found() and clang_supports_bpf
if not meson.is_cross_build()
llvm_strip_bin = run_command(clang, '--print-prog-name', 'llvm-strip',
check : true).stdout().strip()
else
llvm_strip_bin = 'llvm-strip'
endif
llvm_strip = find_program(llvm_strip_bin,
required : true,
version : '>= 10.0.0')
endif
else
error('clat support was enabled but couldn\'t find a suitable BPF compiler!')
endif
bpf_clang_flags = [
'-std=gnu17',
'-Wunused',
'-Wimplicit-fallthrough',
'-Wno-compare-distinct-pointer-types',
'-fno-stack-protector',
'-O2',
'-target',
'bpf',
'-g',
'-c',
]
bpf_gcc_flags = [
'-std=gnu17',
'-Wunused',
'-Wimplicit-fallthrough',
'-fno-stack-protector',
'-fno-ssa-phiopt',
'-O2',
'-mcpu=v3',
'-mco-re',
'-gbtf',
'-c',
]
clang_arch_flag = '-D__@0@__'.format(host_machine.cpu_family())
libbpf_include_dir = dependency('libbpf').get_variable(pkgconfig : 'includedir')
# Generate defines that are appropriate to tell the compiler what architecture
# we're compiling for. By default we just map meson's cpu_family to __<cpu_family>__.
# This dictionary contains the exceptions where this doesn't work.
#
# C.f. https://mesonbuild.com/Reference-tables.html#cpu-families
# and src/basic/missing_syscall_def.h.
cpu_arch_defines = {
'ppc' : ['-D__powerpc__', '-D__TARGET_ARCH_powerpc'],
'ppc64' : ['-D__powerpc64__', '-D__TARGET_ARCH_powerpc', '-D_CALL_ELF=2'],
'riscv32' : ['-D__riscv', '-D__riscv_xlen=32', '-D__TARGET_ARCH_riscv'],
'riscv64' : ['-D__riscv', '-D__riscv_xlen=64', '-D__TARGET_ARCH_riscv'],
'x86' : ['-D__i386__', '-D__TARGET_ARCH_x86'],
's390x' : ['-D__s390__', '-D__s390x__', '-D__TARGET_ARCH_s390'],
# For arm, assume hardware fp is available.
'arm' : ['-D__arm__', '-D__ARM_PCS_VFP', '-D__TARGET_ARCH_arm'],
'loongarch64' : ['-D__loongarch__', '-D__loongarch_grlen=64', '-D__TARGET_ARCH_loongarch']
}
bpf_arch_flags = cpu_arch_defines.get(host_machine.cpu_family(),
['-D__@0@__'.format(host_machine.cpu_family())])
if bpf_compiler == 'gcc'
bpf_arch_flags += ['-m' + host_machine.endian() + '-endian']
endif
bpf_o_unstripped_cmd = []
if bpf_compiler == 'clang'
bpf_o_unstripped_cmd += [
clang,
bpf_clang_flags,
bpf_arch_flags,
]
elif bpf_compiler == 'gcc'
bpf_o_unstripped_cmd += [
bpf_gcc,
bpf_gcc_flags,
bpf_arch_flags,
]
endif
bpf_o_unstripped_cmd += ['-I.']
if cc.get_id() == 'gcc' or meson.is_cross_build()
if cc.get_id() != 'gcc'
warning('Cross compiler is not gcc. Guessing the target triplet for bpf likely fails.')
endif
target_triplet_cmd = run_command(cc.cmd_array(), '-print-multiarch', check: false)
else
# clang does not support -print-multiarch (D133170) and its -dump-machine
# does not match multiarch. Query gcc instead.
target_triplet_cmd = run_command('gcc', '-print-multiarch', check: false)
endif
if target_triplet_cmd.returncode() == 0
target_triplet = target_triplet_cmd.stdout().strip()
bpf_o_unstripped_cmd += [
'-isystem',
'/usr/include/@0@'.format(target_triplet)
]
endif
bpf_o_unstripped_cmd += [
'-idirafter',
libbpf_include_dir,
'@INPUT@',
'-o',
'@OUTPUT@'
]
if bpftool_strip
bpf_o_cmd = [
bpftool,
'gen',
'object',
'@OUTPUT@',
'@INPUT@'
]
elif bpf_compiler == 'clang'
bpf_o_cmd = [
llvm_strip,
'-g',
'@INPUT@',
'-o',
'@OUTPUT@'
]
endif
skel_h_cmd = [
bpftool,
'g',
's',
'@INPUT@'
]
clat_bpf_o_unstripped = custom_target(
'clat.bpf.unstripped.o',
input : 'clat.bpf.c',
output : 'clat.bpf.unstripped.o',
command : bpf_o_unstripped_cmd)
clat_bpf_o = custom_target(
'clat.bpf.o',
input : clat_bpf_o_unstripped,
output : 'clat.bpf.o',
command : bpf_o_cmd)
clat_skel_h = custom_target(
'clat.skel.h',
input : clat_bpf_o,
output : 'clat.skel.h',
command : skel_h_cmd,
capture : true)

View file

@ -52,11 +52,12 @@
NM_SETTING_BOND_OPTION_PACKETS_PER_SLAVE, NM_SETTING_BOND_OPTION_PRIMARY_RESELECT, \ NM_SETTING_BOND_OPTION_PACKETS_PER_SLAVE, NM_SETTING_BOND_OPTION_PRIMARY_RESELECT, \
NM_SETTING_BOND_OPTION_RESEND_IGMP, NM_SETTING_BOND_OPTION_USE_CARRIER, \ NM_SETTING_BOND_OPTION_RESEND_IGMP, NM_SETTING_BOND_OPTION_USE_CARRIER, \
NM_SETTING_BOND_OPTION_XMIT_HASH_POLICY, NM_SETTING_BOND_OPTION_NUM_GRAT_ARP, \ NM_SETTING_BOND_OPTION_XMIT_HASH_POLICY, NM_SETTING_BOND_OPTION_NUM_GRAT_ARP, \
NM_SETTING_BOND_OPTION_PEER_NOTIF_DELAY, NM_SETTING_BOND_OPTION_ARP_MISSED_MAX NM_SETTING_BOND_OPTION_PEER_NOTIF_DELAY
#define OPTIONS_REAPPLY_FULL \ #define OPTIONS_REAPPLY_FULL \
OPTIONS_REAPPLY_SUBSET, NM_SETTING_BOND_OPTION_ACTIVE_SLAVE, \ OPTIONS_REAPPLY_SUBSET, NM_SETTING_BOND_OPTION_ACTIVE_SLAVE, \
NM_SETTING_BOND_OPTION_ARP_IP_TARGET, NM_SETTING_BOND_OPTION_NS_IP6_TARGET NM_SETTING_BOND_OPTION_ARP_IP_TARGET, NM_SETTING_BOND_OPTION_NS_IP6_TARGET, \
NM_SETTING_BOND_OPTION_ARP_MISSED_MAX
/*****************************************************************************/ /*****************************************************************************/
@ -501,6 +502,8 @@ _platform_lnk_bond_init_from_setting(NMSettingBond *s_bond, NMPlatformLnkBond *p
props->lp_interval_has = props->lp_interval != 1; props->lp_interval_has = props->lp_interval != 1;
props->tlb_dynamic_lb_has = NM_IN_SET(props->mode, NM_BOND_MODE_TLB, NM_BOND_MODE_ALB); props->tlb_dynamic_lb_has = NM_IN_SET(props->mode, NM_BOND_MODE_TLB, NM_BOND_MODE_ALB);
props->lacp_active_has = NM_IN_SET(props->mode, NM_BOND_MODE_8023AD); props->lacp_active_has = NM_IN_SET(props->mode, NM_BOND_MODE_8023AD);
props->arp_missed_max_has =
!NM_IN_SET(props->mode, NM_BOND_MODE_TLB, NM_BOND_MODE_ALB, NM_BOND_MODE_8023AD);
} }
static void static void
@ -907,6 +910,8 @@ reapply_connection(NMDevice *device, NMConnection *con_old, NMConnection *con_ne
set_bond_arp_ip_targets(device, s_bond); set_bond_arp_ip_targets(device, s_bond);
set_bond_attrs_or_default(device, s_bond, NM_MAKE_STRV(OPTIONS_REAPPLY_SUBSET)); set_bond_attrs_or_default(device, s_bond, NM_MAKE_STRV(OPTIONS_REAPPLY_SUBSET));
if (!NM_IN_SET(mode, NM_BOND_MODE_TLB, NM_BOND_MODE_ALB, NM_BOND_MODE_8023AD))
set_bond_attr_or_default(device, s_bond, NM_SETTING_BOND_OPTION_ARP_MISSED_MAX);
_balance_slb_setup(self, con_new); _balance_slb_setup(self, con_new);
} }

View file

@ -1066,7 +1066,7 @@ attach_port(NMDevice *device,
plat_vlans = setting_vlans_to_platform(vlans, &num_vlans); plat_vlans = setting_vlans_to_platform(vlans, &num_vlans);
/* Since the link was just enportd, there are no existing VLANs /* Since the link was just attached, there are no existing VLANs
* (except for the default one) and so there's no need to flush. */ * (except for the default one) and so there's no need to flush. */
if (plat_vlans if (plat_vlans

View file

@ -14,7 +14,6 @@
#include <libudev.h> #include <libudev.h>
#include <linux/if_ether.h> #include <linux/if_ether.h>
#include "NetworkManagerUtils.h"
#include "NetworkManagerUtils.h" #include "NetworkManagerUtils.h"
#include "libnm-core-aux-intern/nm-libnm-core-utils.h" #include "libnm-core-aux-intern/nm-libnm-core-utils.h"
#include "libnm-core-intern/nm-core-internal.h" #include "libnm-core-intern/nm-core-internal.h"
@ -630,10 +629,17 @@ build_supplicant_config(NMDeviceEthernet *self, GError **error)
mtu = nm_platform_link_get_mtu(nm_device_get_platform(NM_DEVICE(self)), mtu = nm_platform_link_get_mtu(nm_device_get_platform(NM_DEVICE(self)),
nm_device_get_ifindex(NM_DEVICE(self))); nm_device_get_ifindex(NM_DEVICE(self)));
config = nm_supplicant_config_new(NM_SUPPL_CAP_MASK_NONE); config = nm_supplicant_config_new(NM_SUPPL_CAP_MASK_NONE,
nm_utils_get_connection_first_permissions_user(connection));
security = nm_connection_get_setting_802_1x(connection); security = nm_connection_get_setting_802_1x(connection);
if (!nm_supplicant_config_add_setting_8021x(config, security, con_uuid, mtu, TRUE, error)) { if (!nm_supplicant_config_add_setting_8021x(config,
security,
con_uuid,
mtu,
TRUE,
nm_device_get_private_files(NM_DEVICE(self)),
error)) {
g_prefix_error(error, "802-1x-setting: "); g_prefix_error(error, "802-1x-setting: ");
g_clear_object(&config); g_clear_object(&config);
} }
@ -701,6 +707,9 @@ supplicant_iface_start(NMDeviceEthernet *self)
NMDeviceEthernetPrivate *priv = NM_DEVICE_ETHERNET_GET_PRIVATE(self); NMDeviceEthernetPrivate *priv = NM_DEVICE_ETHERNET_GET_PRIVATE(self);
gs_unref_object NMSupplicantConfig *config = NULL; gs_unref_object NMSupplicantConfig *config = NULL;
gs_free_error GError *error = NULL; gs_free_error GError *error = NULL;
NMActRequest *request;
NMActiveConnection *controller_ac;
NMDevice *controller;
config = build_supplicant_config(self, &error); config = build_supplicant_config(self, &error);
if (!config) { if (!config) {
@ -715,6 +724,16 @@ supplicant_iface_start(NMDeviceEthernet *self)
} }
nm_supplicant_interface_disconnect(priv->supplicant.iface); nm_supplicant_interface_disconnect(priv->supplicant.iface);
/* Tell the supplicant in which bridge the interface is */
if ((request = nm_device_get_act_request(NM_DEVICE(self)))
&& (controller_ac = nm_active_connection_get_controller(NM_ACTIVE_CONNECTION(request)))
&& (controller = nm_active_connection_get_device(controller_ac))
&& nm_device_get_device_type(controller) == NM_DEVICE_TYPE_BRIDGE) {
nm_supplicant_interface_set_bridge(priv->supplicant.iface, nm_device_get_iface(controller));
} else
nm_supplicant_interface_set_bridge(priv->supplicant.iface, NULL);
nm_supplicant_interface_assoc(priv->supplicant.iface, config, supplicant_iface_assoc_cb, self); nm_supplicant_interface_assoc(priv->supplicant.iface, config, supplicant_iface_assoc_cb, self);
return TRUE; return TRUE;
} }
@ -1894,7 +1913,7 @@ get_ip_method_auto(NMDevice *device, int addr_family)
/* We cannot do DHCPv4 on a PPP link, instead we get "auto" IP addresses /* We cannot do DHCPv4 on a PPP link, instead we get "auto" IP addresses
* by pppd. Return "manual" here, which has the suitable effect to a * by pppd. Return "manual" here, which has the suitable effect to a
* (zero) manual addresses in addition. */ * (zero) manual addresses in addition. */
return NM_SETTING_IP6_CONFIG_METHOD_MANUAL; return NM_SETTING_IP4_CONFIG_METHOD_MANUAL;
} }
return NM_SETTING_IP6_CONFIG_METHOD_AUTO; return NM_SETTING_IP6_CONFIG_METHOD_AUTO;

View file

@ -412,6 +412,7 @@ nm_device_factory_manager_load_factories(NMDeviceFactoryManagerFactoryFunc callb
_ADD_INTERNAL(nm_dummy_device_factory_get_type); _ADD_INTERNAL(nm_dummy_device_factory_get_type);
_ADD_INTERNAL(nm_ethernet_device_factory_get_type); _ADD_INTERNAL(nm_ethernet_device_factory_get_type);
_ADD_INTERNAL(nm_generic_device_factory_get_type); _ADD_INTERNAL(nm_generic_device_factory_get_type);
_ADD_INTERNAL(nm_geneve_device_factory_get_type);
_ADD_INTERNAL(nm_hsr_device_factory_get_type); _ADD_INTERNAL(nm_hsr_device_factory_get_type);
_ADD_INTERNAL(nm_infiniband_device_factory_get_type); _ADD_INTERNAL(nm_infiniband_device_factory_get_type);
_ADD_INTERNAL(nm_ip_tunnel_device_factory_get_type); _ADD_INTERNAL(nm_ip_tunnel_device_factory_get_type);

View file

@ -0,0 +1,487 @@
/* SPDX-License-Identifier: LGPL-2.1-or-later */
/*
* Copyright (C) 2026 Red Hat, Inc.
*/
#include "src/core/nm-default-daemon.h"
#include "nm-manager.h"
#include "nm-device-geneve.h"
#include "libnm-core-intern/nm-core-internal.h"
#include "nm-act-request.h"
#include "nm-device-private.h"
#include "nm-setting-geneve.h"
#include "libnm-platform/nm-platform.h"
#include "nm-device-factory.h"
#define _NMLOG_DEVICE_TYPE NMDeviceGeneve
#include "nm-device-logging.h"
NM_GOBJECT_PROPERTIES_DEFINE(NMDeviceGeneve,
PROP_ID,
PROP_REMOTE,
PROP_TOS,
PROP_TTL,
PROP_DF,
PROP_DST_PORT, );
typedef struct {
NMPlatformLnkGeneve props;
} NMDeviceGenevePrivate;
struct _NMDeviceGeneve {
NMDevice parent;
NMDeviceGenevePrivate _priv;
};
struct _NMDeviceGeneveClass {
NMDeviceClass parent;
};
G_DEFINE_TYPE(NMDeviceGeneve, nm_device_geneve, NM_TYPE_DEVICE)
#define NM_DEVICE_GENEVE_GET_PRIVATE(self) \
_NM_GET_PRIVATE(self, NMDeviceGeneve, NM_IS_DEVICE_GENEVE, NMDevice)
/*****************************************************************************/
static NMDeviceCapabilities
get_generic_capabilities(NMDevice *dev)
{
return NM_DEVICE_CAP_IS_SOFTWARE;
}
static void
update_properties(NMDevice *device)
{
NMDeviceGeneve *self;
NMDeviceGenevePrivate *priv;
const NMPlatformLink *plink;
const NMPlatformLnkGeneve *props;
int ifindex;
g_return_if_fail(NM_IS_DEVICE_GENEVE(device));
self = NM_DEVICE_GENEVE(device);
priv = NM_DEVICE_GENEVE_GET_PRIVATE(self);
ifindex = nm_device_get_ifindex(device);
g_return_if_fail(ifindex > 0);
props = nm_platform_link_get_lnk_geneve(nm_device_get_platform(device), ifindex, &plink);
if (!props) {
_LOGW(LOGD_PLATFORM, "could not get GENEVE properties");
return;
}
g_object_freeze_notify((GObject *) device);
#define CHECK_PROPERTY_CHANGED(field, prop) \
G_STMT_START \
{ \
if (priv->props.field != props->field) { \
priv->props.field = props->field; \
_notify(self, prop); \
} \
} \
G_STMT_END
#define CHECK_PROPERTY_CHANGED_IN6ADDR(field, prop) \
G_STMT_START \
{ \
if (memcmp(&priv->props.field, &props->field, sizeof(props->field)) != 0) { \
priv->props.field = props->field; \
_notify(self, prop); \
} \
} \
G_STMT_END
CHECK_PROPERTY_CHANGED(id, PROP_ID);
CHECK_PROPERTY_CHANGED(remote, PROP_REMOTE);
CHECK_PROPERTY_CHANGED_IN6ADDR(remote6, PROP_REMOTE);
CHECK_PROPERTY_CHANGED(tos, PROP_TOS);
CHECK_PROPERTY_CHANGED(ttl, PROP_TTL);
CHECK_PROPERTY_CHANGED(df, PROP_DF);
CHECK_PROPERTY_CHANGED(dst_port, PROP_DST_PORT);
g_object_thaw_notify((GObject *) device);
}
static void
link_changed(NMDevice *device, const NMPlatformLink *pllink)
{
NM_DEVICE_CLASS(nm_device_geneve_parent_class)->link_changed(device, pllink);
update_properties(device);
}
static void
unrealize_notify(NMDevice *device)
{
NMDeviceGeneve *self = NM_DEVICE_GENEVE(device);
NMDeviceGenevePrivate *priv = NM_DEVICE_GENEVE_GET_PRIVATE(self);
guint i;
NM_DEVICE_CLASS(nm_device_geneve_parent_class)->unrealize_notify(device);
memset(&priv->props, 0, sizeof(NMPlatformLnkGeneve));
for (i = 1; i < _PROPERTY_ENUMS_LAST; i++)
g_object_notify_by_pspec(G_OBJECT(self), obj_properties[i]);
}
static gboolean
create_and_realize(NMDevice *device,
NMConnection *connection,
NMDevice *parent,
const NMPlatformLink **out_plink,
GError **error)
{
const char *iface = nm_device_get_iface(device);
NMPlatformLnkGeneve props = {};
NMSettingGeneve *s_geneve;
const char *str;
int r;
s_geneve = nm_connection_get_setting_geneve(connection);
g_return_val_if_fail(s_geneve, FALSE);
props.id = nm_setting_geneve_get_id(s_geneve);
str = nm_setting_geneve_get_remote(s_geneve);
if (!nm_inet_parse_bin(AF_INET, str, NULL, &props.remote)
&& !nm_inet_parse_bin(AF_INET6, str, NULL, &props.remote6)) {
return nm_assert_unreachable_val(FALSE);
}
props.tos = nm_setting_geneve_get_tos(s_geneve);
props.ttl = nm_setting_geneve_get_ttl(s_geneve);
props.df = nm_setting_geneve_get_df(s_geneve);
props.dst_port = nm_setting_geneve_get_destination_port(s_geneve);
r = nm_platform_link_geneve_add(nm_device_get_platform(device), iface, &props, out_plink);
if (r < 0) {
g_set_error(error,
NM_DEVICE_ERROR,
NM_DEVICE_ERROR_CREATION_FAILED,
"Failed to create geneve interface '%s' for '%s': %s",
iface,
nm_connection_get_id(connection),
nm_strerror(r));
return FALSE;
}
return TRUE;
}
static gboolean
address_matches(const char *candidate, in_addr_t addr4, struct in6_addr *addr6)
{
NMIPAddr candidate_addr;
int addr_family;
if (!candidate)
return addr4 == 0u && IN6_IS_ADDR_UNSPECIFIED(addr6);
if (!nm_inet_parse_bin(AF_UNSPEC, candidate, &addr_family, &candidate_addr))
return FALSE;
if (!nm_ip_addr_equal(addr_family,
&candidate_addr,
NM_IS_IPv4(addr_family) ? (gpointer) &addr4 : addr6))
return FALSE;
if (NM_IS_IPv4(addr_family))
return IN6_IS_ADDR_UNSPECIFIED(addr6);
else
return addr4 == 0u;
}
static gboolean
check_connection_compatible(NMDevice *device,
NMConnection *connection,
gboolean check_properties,
GError **error)
{
NMDeviceGenevePrivate *priv = NM_DEVICE_GENEVE_GET_PRIVATE(device);
NMSettingGeneve *s_geneve;
if (!NM_DEVICE_CLASS(nm_device_geneve_parent_class)
->check_connection_compatible(device, connection, check_properties, error))
return FALSE;
if (check_properties && nm_device_is_real(device)) {
s_geneve = nm_connection_get_setting_geneve(connection);
if (priv->props.id != nm_setting_geneve_get_id(s_geneve)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"geneve id mismatches");
return FALSE;
}
if (!address_matches(nm_setting_geneve_get_remote(s_geneve),
priv->props.remote,
&priv->props.remote6)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"geneve remote address mismatches");
return FALSE;
}
if (priv->props.dst_port != nm_setting_geneve_get_destination_port(s_geneve)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"geneve destination port mismatches");
return FALSE;
}
if (priv->props.tos != nm_setting_geneve_get_tos(s_geneve)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"geneve TOS mismatches");
return FALSE;
}
if (priv->props.ttl != nm_setting_geneve_get_ttl(s_geneve)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"geneve TTL mismatches");
return FALSE;
}
if (priv->props.df != nm_setting_geneve_get_df(s_geneve)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"geneve DF mismatches");
return FALSE;
}
}
return TRUE;
}
static gboolean
complete_connection(NMDevice *device,
NMConnection *connection,
const char *specific_object,
NMConnection *const *existing_connections,
GError **error)
{
NMSettingGeneve *s_geneve;
nm_utils_complete_generic(nm_device_get_platform(device),
connection,
NM_SETTING_GENEVE_SETTING_NAME,
existing_connections,
NULL,
_("Geneve connection"),
NULL,
NULL);
s_geneve = nm_connection_get_setting_geneve(connection);
if (!s_geneve) {
g_set_error_literal(error,
NM_DEVICE_ERROR,
NM_DEVICE_ERROR_INVALID_CONNECTION,
"A 'geneve' setting is required.");
return FALSE;
}
return TRUE;
}
static void
update_connection(NMDevice *device, NMConnection *connection)
{
NMDeviceGenevePrivate *priv = NM_DEVICE_GENEVE_GET_PRIVATE(device);
NMSettingGeneve *s_geneve = _nm_connection_ensure_setting(connection, NM_TYPE_SETTING_GENEVE);
char sbuf[NM_INET_ADDRSTRLEN];
if (priv->props.id != nm_setting_geneve_get_id(s_geneve))
g_object_set(G_OBJECT(s_geneve), NM_SETTING_GENEVE_ID, priv->props.id, NULL);
/* Handle remote (IPv4 or IPv6) */
if (priv->props.remote) {
g_object_set(s_geneve,
NM_SETTING_GENEVE_REMOTE,
nm_inet4_ntop(priv->props.remote, sbuf),
NULL);
} else if (memcmp(&priv->props.remote6, &in6addr_any, sizeof(in6addr_any))) {
g_object_set(s_geneve,
NM_SETTING_GENEVE_REMOTE,
nm_inet6_ntop(&priv->props.remote6, sbuf),
NULL);
}
if (priv->props.dst_port != nm_setting_geneve_get_destination_port(s_geneve))
g_object_set(G_OBJECT(s_geneve),
NM_SETTING_GENEVE_DESTINATION_PORT,
priv->props.dst_port,
NULL);
if (priv->props.tos != nm_setting_geneve_get_tos(s_geneve))
g_object_set(G_OBJECT(s_geneve), NM_SETTING_GENEVE_TOS, priv->props.tos, NULL);
if (priv->props.ttl != nm_setting_geneve_get_ttl(s_geneve))
g_object_set(G_OBJECT(s_geneve), NM_SETTING_GENEVE_TTL, priv->props.ttl, NULL);
if (priv->props.df != nm_setting_geneve_get_df(s_geneve))
g_object_set(G_OBJECT(s_geneve), NM_SETTING_GENEVE_DF, priv->props.df, NULL);
}
static void
get_property(GObject *object, guint prop_id, GValue *value, GParamSpec *pspec)
{
NMDeviceGenevePrivate *priv = NM_DEVICE_GENEVE_GET_PRIVATE(object);
switch (prop_id) {
case PROP_ID:
g_value_set_uint(value, priv->props.id);
break;
case PROP_REMOTE:
if (priv->props.remote)
g_value_take_string(value, nm_inet4_ntop_dup(priv->props.remote));
else if (!IN6_IS_ADDR_UNSPECIFIED(&priv->props.remote6))
g_value_take_string(value, nm_inet6_ntop_dup(&priv->props.remote6));
break;
case PROP_TOS:
g_value_set_uchar(value, priv->props.tos);
break;
case PROP_TTL:
g_value_set_uchar(value, priv->props.ttl);
break;
case PROP_DF:
g_value_set_uint(value, priv->props.df);
break;
case PROP_DST_PORT:
g_value_set_uint(value, priv->props.dst_port);
break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
break;
}
}
/*****************************************************************************/
static void
nm_device_geneve_init(NMDeviceGeneve *self)
{}
static const NMDBusInterfaceInfoExtended interface_info_device_geneve = {
.parent = NM_DEFINE_GDBUS_INTERFACE_INFO_INIT(
NM_DBUS_INTERFACE_DEVICE_GENEVE,
.properties = NM_DEFINE_GDBUS_PROPERTY_INFOS(
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Id", "u", NM_DEVICE_GENEVE_ID),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Remote", "s", NM_DEVICE_GENEVE_REMOTE),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Tos", "y", NM_DEVICE_GENEVE_TOS),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Ttl", "y", NM_DEVICE_GENEVE_TTL),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Df", "u", NM_DEVICE_GENEVE_DF),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("DstPort",
"q",
NM_DEVICE_GENEVE_DST_PORT), ), ),
};
static void
nm_device_geneve_class_init(NMDeviceGeneveClass *klass)
{
GObjectClass *object_class = G_OBJECT_CLASS(klass);
NMDBusObjectClass *dbus_object_class = NM_DBUS_OBJECT_CLASS(klass);
NMDeviceClass *device_class = NM_DEVICE_CLASS(klass);
object_class->get_property = get_property;
dbus_object_class->interface_infos = NM_DBUS_INTERFACE_INFOS(&interface_info_device_geneve);
device_class->connection_type_supported = NM_SETTING_GENEVE_SETTING_NAME;
device_class->connection_type_check_compatible = NM_SETTING_GENEVE_SETTING_NAME;
device_class->link_types = NM_DEVICE_DEFINE_LINK_TYPES(NM_LINK_TYPE_GENEVE);
device_class->link_changed = link_changed;
device_class->unrealize_notify = unrealize_notify;
device_class->create_and_realize = create_and_realize;
device_class->check_connection_compatible = check_connection_compatible;
device_class->complete_connection = complete_connection;
device_class->get_generic_capabilities = get_generic_capabilities;
device_class->update_connection = update_connection;
obj_properties[PROP_ID] = g_param_spec_uint(NM_DEVICE_GENEVE_ID,
"",
"",
0,
G_MAXUINT32,
0,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
obj_properties[PROP_REMOTE] = g_param_spec_string(NM_DEVICE_GENEVE_REMOTE,
"",
"",
NULL,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
obj_properties[PROP_TOS] = g_param_spec_uchar(NM_DEVICE_GENEVE_TOS,
"",
"",
0,
255,
0,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
obj_properties[PROP_TTL] = g_param_spec_uchar(NM_DEVICE_GENEVE_TTL,
"",
"",
0,
255,
0,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
obj_properties[PROP_DF] = g_param_spec_uint(NM_DEVICE_GENEVE_DF,
"",
"",
0,
2,
0,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
obj_properties[PROP_DST_PORT] = g_param_spec_uint(NM_DEVICE_GENEVE_DST_PORT,
"",
"",
0,
65535,
0,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
g_object_class_install_properties(object_class, _PROPERTY_ENUMS_LAST, obj_properties);
}
/*****************************************************************************/
#define NM_TYPE_GENEVE_DEVICE_FACTORY (nm_geneve_device_factory_get_type())
#define NM_GENEVE_DEVICE_FACTORY(obj) \
(_NM_G_TYPE_CHECK_INSTANCE_CAST((obj), NM_TYPE_GENEVE_DEVICE_FACTORY, NMGeneveDeviceFactory))
static NMDevice *
create_device(NMDeviceFactory *factory,
const char *iface,
const NMPlatformLink *plink,
NMConnection *connection,
gboolean *out_ignore)
{
return g_object_new(NM_TYPE_DEVICE_GENEVE,
NM_DEVICE_IFACE,
iface,
NM_DEVICE_TYPE_DESC,
"Geneve",
NM_DEVICE_DEVICE_TYPE,
NM_DEVICE_TYPE_GENEVE,
NM_DEVICE_LINK_TYPE,
NM_LINK_TYPE_GENEVE,
NULL);
}
NM_DEVICE_FACTORY_DEFINE_INTERNAL(
GENEVE,
Geneve,
geneve,
NM_DEVICE_FACTORY_DECLARE_LINK_TYPES(NM_LINK_TYPE_GENEVE)
NM_DEVICE_FACTORY_DECLARE_SETTING_TYPES(NM_SETTING_GENEVE_SETTING_NAME),
factory_class->create_device = create_device;);

View file

@ -0,0 +1,33 @@
/* SPDX-License-Identifier: LGPL-2.1-or-later */
/*
* Copyright (C) 2026 Red Hat, Inc.
*/
#ifndef __NETWORKMANAGER_DEVICE_GENEVE_H__
#define __NETWORKMANAGER_DEVICE_GENEVE_H__
#include "nm-device.h"
#define NM_TYPE_DEVICE_GENEVE (nm_device_geneve_get_type())
#define NM_DEVICE_GENEVE(obj) \
(_NM_G_TYPE_CHECK_INSTANCE_CAST((obj), NM_TYPE_DEVICE_GENEVE, NMDeviceGeneve))
#define NM_DEVICE_GENEVE_CLASS(klass) \
(G_TYPE_CHECK_CLASS_CAST((klass), NM_TYPE_DEVICE_GENEVE, NMDeviceGeneveClass))
#define NM_IS_DEVICE_GENEVE(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), NM_TYPE_DEVICE_GENEVE))
#define NM_IS_DEVICE_GENEVE_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), NM_TYPE_DEVICE_GENEVE))
#define NM_DEVICE_GENEVE_GET_CLASS(obj) \
(G_TYPE_INSTANCE_GET_CLASS((obj), NM_TYPE_DEVICE_GENEVE, NMDeviceGeneveClass))
#define NM_DEVICE_GENEVE_ID "id"
#define NM_DEVICE_GENEVE_REMOTE "remote"
#define NM_DEVICE_GENEVE_TOS "tos"
#define NM_DEVICE_GENEVE_TTL "ttl"
#define NM_DEVICE_GENEVE_DF "df"
#define NM_DEVICE_GENEVE_DST_PORT "dst-port"
typedef struct _NMDeviceGeneve NMDeviceGeneve;
typedef struct _NMDeviceGeneveClass NMDeviceGeneveClass;
GType nm_device_geneve_get_type(void);
#endif /* __NETWORKMANAGER_DEVICE_GENEVE_H__ */

View file

@ -201,7 +201,8 @@ build_supplicant_config(NMDeviceMacsec *self, GError **error)
mtu = nm_platform_link_get_mtu(nm_device_get_platform(NM_DEVICE(self)), mtu = nm_platform_link_get_mtu(nm_device_get_platform(NM_DEVICE(self)),
nm_device_get_ifindex(NM_DEVICE(self))); nm_device_get_ifindex(NM_DEVICE(self)));
config = nm_supplicant_config_new(NM_SUPPL_CAP_MASK_NONE); config = nm_supplicant_config_new(NM_SUPPL_CAP_MASK_NONE,
nm_utils_get_connection_first_permissions_user(connection));
s_macsec = nm_device_get_applied_setting(NM_DEVICE(self), NM_TYPE_SETTING_MACSEC); s_macsec = nm_device_get_applied_setting(NM_DEVICE(self), NM_TYPE_SETTING_MACSEC);
@ -227,7 +228,13 @@ build_supplicant_config(NMDeviceMacsec *self, GError **error)
if (nm_setting_macsec_get_mode(s_macsec) == NM_SETTING_MACSEC_MODE_EAP) { if (nm_setting_macsec_get_mode(s_macsec) == NM_SETTING_MACSEC_MODE_EAP) {
s_8021x = nm_connection_get_setting_802_1x(connection); s_8021x = nm_connection_get_setting_802_1x(connection);
if (!nm_supplicant_config_add_setting_8021x(config, s_8021x, con_uuid, mtu, TRUE, error)) { if (!nm_supplicant_config_add_setting_8021x(config,
s_8021x,
con_uuid,
mtu,
TRUE,
nm_device_get_private_files(NM_DEVICE(self)),
error)) {
g_prefix_error(error, "802-1x-setting: "); g_prefix_error(error, "802-1x-setting: ");
return NULL; return NULL;
} }
@ -433,6 +440,9 @@ supplicant_iface_start(NMDeviceMacsec *self)
NMDeviceMacsecPrivate *priv = NM_DEVICE_MACSEC_GET_PRIVATE(self); NMDeviceMacsecPrivate *priv = NM_DEVICE_MACSEC_GET_PRIVATE(self);
gs_unref_object NMSupplicantConfig *config = NULL; gs_unref_object NMSupplicantConfig *config = NULL;
gs_free_error GError *error = NULL; gs_free_error GError *error = NULL;
NMActRequest *request;
NMActiveConnection *controller_ac;
NMDevice *controller;
config = build_supplicant_config(self, &error); config = build_supplicant_config(self, &error);
if (!config) { if (!config) {
@ -445,6 +455,16 @@ supplicant_iface_start(NMDeviceMacsec *self)
} }
nm_supplicant_interface_disconnect(priv->supplicant.iface); nm_supplicant_interface_disconnect(priv->supplicant.iface);
/* Tell the supplicant in which bridge the interface is */
if ((request = nm_device_get_act_request(NM_DEVICE(self)))
&& (controller_ac = nm_active_connection_get_controller(NM_ACTIVE_CONNECTION(request)))
&& (controller = nm_active_connection_get_device(controller_ac))
&& nm_device_get_device_type(controller) == NM_DEVICE_TYPE_BRIDGE) {
nm_supplicant_interface_set_bridge(priv->supplicant.iface, nm_device_get_iface(controller));
} else
nm_supplicant_interface_set_bridge(priv->supplicant.iface, NULL);
nm_supplicant_interface_assoc(priv->supplicant.iface, config, supplicant_iface_assoc_cb, self); nm_supplicant_interface_assoc(priv->supplicant.iface, config, supplicant_iface_assoc_cb, self);
return TRUE; return TRUE;
} }

View file

@ -468,7 +468,12 @@ static const NMDBusInterfaceInfoExtended interface_info_device_macvlan = {
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("NoPromisc", NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("NoPromisc",
"b", "b",
NM_DEVICE_MACVLAN_NO_PROMISC), NM_DEVICE_MACVLAN_NO_PROMISC),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Tab", "b", NM_DEVICE_MACVLAN_TAP), ), ), NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE("Tap", "b", NM_DEVICE_MACVLAN_TAP),
NM_DEFINE_DBUS_PROPERTY_INFO_EXTENDED_READABLE(
"Tab",
"b",
NM_DEVICE_MACVLAN_TAP,
.annotations = NM_GDBUS_ANNOTATION_INFO_LIST_DEPRECATED(), ), ), ),
}; };
static void static void

View file

@ -115,9 +115,6 @@ gboolean nm_device_sysctl_ip_conf_set(NMDevice *self,
NML3ConfigData *nm_device_create_l3_config_data(NMDevice *self, NMIPConfigSource source); NML3ConfigData *nm_device_create_l3_config_data(NMDevice *self, NMIPConfigSource source);
NML3ConfigData *nm_device_create_l3_config_data_from_connection(NMDevice *self,
NMConnection *connection);
void nm_device_ip_method_dhcp4_start(NMDevice *self); void nm_device_ip_method_dhcp4_start(NMDevice *self);
void nm_device_ip_method_autoconf6_start(NMDevice *self); void nm_device_ip_method_autoconf6_start(NMDevice *self);
@ -179,4 +176,6 @@ void nm_device_auth_request(NMDevice *self,
void nm_device_link_properties_set(NMDevice *self, gboolean reapply); void nm_device_link_properties_set(NMDevice *self, gboolean reapply);
GHashTable *nm_device_get_private_files(NMDevice *self);
#endif /* NM_DEVICE_PRIVATE_H */ #endif /* NM_DEVICE_PRIVATE_H */

View file

@ -143,7 +143,9 @@ NM_UTILS_LOOKUP_STR_DEFINE(
NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_UNMANAGED_USER_SETTINGS, NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_UNMANAGED_USER_SETTINGS,
"unmanaged-user-settings"), "unmanaged-user-settings"),
NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_UNMANAGED_USER_UDEV, "unmanaged-user-udev"), NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_UNMANAGED_USER_UDEV, "unmanaged-user-udev"),
NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_NETWORKING_OFF, "networking-off"), ); NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_NETWORKING_OFF, "networking-off"),
NM_UTILS_LOOKUP_STR_ITEM(NM_DEVICE_STATE_REASON_MODEM_NO_OPERATOR_CODE,
"modem-no-operator-code"), );
NM_UTILS_LOOKUP_STR_DEFINE(nm_device_mtu_source_to_string, NM_UTILS_LOOKUP_STR_DEFINE(nm_device_mtu_source_to_string,
NMDeviceMtuSource, NMDeviceMtuSource,
@ -237,7 +239,7 @@ resolve_addr_helper_cb(GObject *source, GAsyncResult *result, gpointer user_data
gs_free_error GError *error = NULL; gs_free_error GError *error = NULL;
gs_free char *output = NULL; gs_free char *output = NULL;
output = nm_utils_spawn_helper_finish(result, &error); output = nm_utils_spawn_helper_finish_string(result, &error);
if (nm_utils_error_is_cancelled(error)) if (nm_utils_error_is_cancelled(error))
return; return;
@ -276,6 +278,7 @@ resolve_addr_spawn_helper(ResolveAddrInfo *info, ResolveAddrService services)
nm_inet_ntop(info->addr_family, &info->address, addr_str); nm_inet_ntop(info->addr_family, &info->address, addr_str);
_LOG2D(info, "start lookup via nm-daemon-helper using services: %s", str); _LOG2D(info, "start lookup via nm-daemon-helper using services: %s", str);
nm_utils_spawn_helper(NM_MAKE_STRV("resolve-address", addr_str, str), nm_utils_spawn_helper(NM_MAKE_STRV("resolve-address", addr_str, str),
FALSE,
g_task_get_cancellable(info->task), g_task_get_cancellable(info->task),
resolve_addr_helper_cb, resolve_addr_helper_cb,
info); info);

View file

@ -53,7 +53,7 @@ update_properties(NMDevice *device)
nm_device_parent_set_ifindex(device, peer_ifindex); nm_device_parent_set_ifindex(device, peer_ifindex);
peer = nm_device_parent_get_device(device); peer = nm_device_parent_get_device(device);
if (peer && NM_IS_DEVICE_VETH(peer) && nm_device_parent_get_ifindex(peer) <= 0) if (peer && NM_IS_DEVICE_VETH(peer) && !nm_device_parent_get_device(peer))
update_properties(peer); update_properties(peer);
} }

View file

@ -176,14 +176,14 @@ create_and_realize(NMDevice *device,
if (str) { if (str) {
if (!nm_inet_parse_bin(AF_INET, str, NULL, &props.local) if (!nm_inet_parse_bin(AF_INET, str, NULL, &props.local)
&& !nm_inet_parse_bin(AF_INET6, str, NULL, &props.local6)) && !nm_inet_parse_bin(AF_INET6, str, NULL, &props.local6))
return FALSE; return nm_assert_unreachable_val(FALSE);
} }
str = nm_setting_vxlan_get_remote(s_vxlan); str = nm_setting_vxlan_get_remote(s_vxlan);
if (str) { if (str) {
if (!nm_inet_parse_bin(AF_INET, str, NULL, &props.group) if (!nm_inet_parse_bin(AF_INET, str, NULL, &props.group)
&& !nm_inet_parse_bin(AF_INET6, str, NULL, &props.group6)) && !nm_inet_parse_bin(AF_INET6, str, NULL, &props.group6))
return FALSE; return nm_assert_unreachable_val(FALSE);
} }
props.tos = nm_setting_vxlan_get_tos(s_vxlan); props.tos = nm_setting_vxlan_get_tos(s_vxlan);

View file

@ -1672,6 +1672,57 @@ act_stage2_config(NMDevice *device, NMDeviceStateReason *out_failure_reason)
return ret; return ret;
} }
static gboolean
skip_peer_route(const NMIPAddr *peer_addr,
guint peer_addr_prefix,
int addr_family,
NMSettingIPConfig *s_ip)
{
guint num_addresses;
guint i;
/*
* If the allowed-ip subnet is already reachable on the interface via the
* prefix route of a static IP address, skip adding the peer route.
* We don't want to override the prefix route with a new one because the
* prefix route also specifies the correct source IP address.
*
* wg-quick does something similar here:
* https://git.zx2c4.com/wireguard-tools/tree/src/wg-quick/linux.bash?h=v1.0.20250521#n177
* The condition in wg-quick is a bit different because it checks that no
* duplicate route exists on the interface. We can't do exactly the same
* because here we don't have visibility on all the platform routes.
*/
if (!s_ip)
return FALSE;
num_addresses = nm_setting_ip_config_get_num_addresses(s_ip);
for (i = 0; i < num_addresses; i++) {
NMIPAddr setting_addr;
NMIPAddr peer_addr_tmp;
guint setting_prefix;
NMIPAddress *a;
peer_addr_tmp = *peer_addr;
a = nm_setting_ip_config_get_address(s_ip, i);
nm_ip_address_get_address_binary(a, &setting_addr);
setting_prefix = nm_ip_address_get_prefix(a);
if (setting_prefix > peer_addr_prefix)
continue;
nm_ip_addr_clear_host_address(addr_family, &setting_addr, NULL, setting_prefix);
nm_ip_addr_clear_host_address(addr_family, &peer_addr_tmp, NULL, setting_prefix);
if (nm_ip_addr_equal(addr_family, &peer_addr_tmp, &setting_addr))
return TRUE;
}
return FALSE;
}
static const NML3ConfigData * static const NML3ConfigData *
_get_dev2_ip_config(NMDeviceWireGuard *self, int addr_family) _get_dev2_ip_config(NMDeviceWireGuard *self, int addr_family)
{ {
@ -1738,6 +1789,7 @@ _get_dev2_ip_config(NMDeviceWireGuard *self, int addr_family)
n_aips = nm_wireguard_peer_get_allowed_ips_len(peer); n_aips = nm_wireguard_peer_get_allowed_ips_len(peer);
for (j = 0; j < n_aips; j++) { for (j = 0; j < n_aips; j++) {
NMSettingIPConfig *s_ip;
NMPlatformIPXRoute rt; NMPlatformIPXRoute rt;
NMIPAddr addrbin; NMIPAddr addrbin;
const char *aip; const char *aip;
@ -1746,6 +1798,7 @@ _get_dev2_ip_config(NMDeviceWireGuard *self, int addr_family)
guint32 rtable_coerced; guint32 rtable_coerced;
aip = nm_wireguard_peer_get_allowed_ip(peer, j, &valid); aip = nm_wireguard_peer_get_allowed_ip(peer, j, &valid);
s_ip = nm_connection_get_setting_ip_config(connection, addr_family);
if (!valid || !nm_inet_parse_with_prefix_bin(addr_family, aip, NULL, &addrbin, &prefix)) if (!valid || !nm_inet_parse_with_prefix_bin(addr_family, aip, NULL, &addrbin, &prefix))
continue; continue;
@ -1754,9 +1807,6 @@ _get_dev2_ip_config(NMDeviceWireGuard *self, int addr_family)
prefix = (addr_family == AF_INET) ? 32 : 128; prefix = (addr_family == AF_INET) ? 32 : 128;
if (prefix == 0) { if (prefix == 0) {
NMSettingIPConfig *s_ip;
s_ip = nm_connection_get_setting_ip_config(connection, addr_family);
if (nm_setting_ip_config_get_never_default(s_ip)) if (nm_setting_ip_config_get_never_default(s_ip))
continue; continue;
} }
@ -1769,6 +1819,9 @@ _get_dev2_ip_config(NMDeviceWireGuard *self, int addr_family)
nm_ip_addr_clear_host_address(addr_family, &addrbin, NULL, prefix); nm_ip_addr_clear_host_address(addr_family, &addrbin, NULL, prefix);
if (skip_peer_route(&addrbin, prefix, addr_family, s_ip))
continue;
rtable_coerced = route_table_coerced; rtable_coerced = route_table_coerced;
if (prefix == 0 && auto_default_route_enabled) { if (prefix == 0 && auto_default_route_enabled) {

File diff suppressed because it is too large Load diff

View file

@ -791,6 +791,7 @@ void nm_device_update_permanent_hw_address(NMDevice *self, gboolean force_fr
void nm_device_update_dynamic_ip_setup(NMDevice *self, const char *reason); void nm_device_update_dynamic_ip_setup(NMDevice *self, const char *reason);
guint nm_device_get_supplicant_timeout(NMDevice *self); guint nm_device_get_supplicant_timeout(NMDevice *self);
gboolean nm_device_auth_retries_has_next(NMDevice *self);
gboolean nm_device_auth_retries_try_next(NMDevice *self); gboolean nm_device_auth_retries_try_next(NMDevice *self);
gboolean nm_device_hw_addr_get_cloned(NMDevice *self, gboolean nm_device_hw_addr_get_cloned(NMDevice *self,
@ -853,4 +854,7 @@ void nm_routing_rules_sync(NMConnection *applied_connection,
NMDevice *self, NMDevice *self,
NMNetns *netns); NMNetns *netns);
NML3ConfigData *nm_device_create_l3_config_data_from_connection(NMDevice *self,
NMConnection *connection);
#endif /* __NETWORKMANAGER_DEVICE_H__ */ #endif /* __NETWORKMANAGER_DEVICE_H__ */

View file

@ -1890,7 +1890,7 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
== -1) { == -1) {
/* This doesn't really have to be an error; the key might /* This doesn't really have to be an error; the key might
* be missing if there really are no bridges present. */ * be missing if there really are no bridges present. */
_LOGD("Bad update: %s", json_error.text); _LOGD("monitor: bad update: %s", json_error.text);
} }
if (ovs) { if (ovs) {
@ -1936,12 +1936,12 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
&unused)) &unused))
continue; continue;
_LOGT("obj[iface:%s]: removed an '%s' interface: %s%s%s", _LOGT("monitor: %s: interface removed: type=%s, obj[iface:%s]%s%s",
key,
ovs_interface->type,
ovs_interface->name, ovs_interface->name,
ovs_interface->type,
key,
NM_PRINT_FMT_QUOTED2(ovs_interface->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_interface->connection_uuid,
", ", ", connection=",
ovs_interface->connection_uuid, ovs_interface->connection_uuid,
"")); ""));
_signal_emit_device_removed(self, _signal_emit_device_removed(self,
@ -1989,13 +1989,14 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
gs_free char *strtmp1 = NULL; gs_free char *strtmp1 = NULL;
gs_free char *strtmp2 = NULL; gs_free char *strtmp2 = NULL;
_LOGT("obj[iface:%s]: changed an '%s' interface: %s%s%s, external-ids=%s, " _LOGT(
"monitor: %s: interface changed: type=%s, obj[iface:%s]%s%s, external-ids=%s, "
"other-config=%s", "other-config=%s",
key,
type,
ovs_interface->name, ovs_interface->name,
type,
key,
NM_PRINT_FMT_QUOTED2(ovs_interface->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_interface->connection_uuid,
", ", ", connection=",
ovs_interface->connection_uuid, ovs_interface->connection_uuid,
""), ""),
(strtmp1 = _strdict_to_string(ovs_interface->external_ids)), (strtmp1 = _strdict_to_string(ovs_interface->external_ids)),
@ -2015,13 +2016,13 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
.other_config = g_steal_pointer(&other_config_arr), .other_config = g_steal_pointer(&other_config_arr),
}; };
g_hash_table_add(priv->interfaces, ovs_interface); g_hash_table_add(priv->interfaces, ovs_interface);
_LOGT( _LOGT("monitor: %s: interface added: type=%s, obj[iface:%s]%s%s, external-ids=%s, "
"obj[iface:%s]: added an '%s' interface: %s%s%s, external-ids=%s, other-config=%s", "other-config=%s",
key,
ovs_interface->type,
ovs_interface->name, ovs_interface->name,
ovs_interface->type,
key,
NM_PRINT_FMT_QUOTED2(ovs_interface->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_interface->connection_uuid,
", ", ", connection=",
ovs_interface->connection_uuid, ovs_interface->connection_uuid,
""), ""),
(strtmp1 = _strdict_to_string(ovs_interface->external_ids)), (strtmp1 = _strdict_to_string(ovs_interface->external_ids)),
@ -2071,11 +2072,11 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
if (!g_hash_table_steal_extended(priv->ports, &key, (gpointer *) &ovs_port, &unused)) if (!g_hash_table_steal_extended(priv->ports, &key, (gpointer *) &ovs_port, &unused))
continue; continue;
_LOGT("obj[port:%s]: removed a port: %s%s%s", _LOGT("monitor: %s: port removed: obj[port:%s]%s%s",
key,
ovs_port->name, ovs_port->name,
key,
NM_PRINT_FMT_QUOTED2(ovs_port->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_port->connection_uuid,
", ", ", connection=",
ovs_port->connection_uuid, ovs_port->connection_uuid,
"")); ""));
_signal_emit_device_removed(self, ovs_port->name, NM_DEVICE_TYPE_OVS_PORT, NULL); _signal_emit_device_removed(self, ovs_port->name, NM_DEVICE_TYPE_OVS_PORT, NULL);
@ -2122,11 +2123,12 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
gs_free char *strtmp1 = NULL; gs_free char *strtmp1 = NULL;
gs_free char *strtmp2 = NULL; gs_free char *strtmp2 = NULL;
_LOGT("obj[port:%s]: changed a port: %s%s%s, external-ids=%s, other-config=%s", _LOGT(
key, "monitor: %s: port changed: obj[port:%s]%s%s, external-ids=%s, other-config=%s",
ovs_port->name, ovs_port->name,
key,
NM_PRINT_FMT_QUOTED2(ovs_port->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_port->connection_uuid,
", ", ", connection=",
ovs_port->connection_uuid, ovs_port->connection_uuid,
""), ""),
(strtmp1 = _strdict_to_string(ovs_port->external_ids)), (strtmp1 = _strdict_to_string(ovs_port->external_ids)),
@ -2146,11 +2148,11 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
.other_config = g_steal_pointer(&other_config_arr), .other_config = g_steal_pointer(&other_config_arr),
}; };
g_hash_table_add(priv->ports, ovs_port); g_hash_table_add(priv->ports, ovs_port);
_LOGT("obj[port:%s]: added a port: %s%s%s, external-ids=%s, other-config=%s", _LOGT("monitor: %s: port added: obj[port:%s]%s%s, external-ids=%s, other-config=%s",
key,
ovs_port->name, ovs_port->name,
key,
NM_PRINT_FMT_QUOTED2(ovs_port->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_port->connection_uuid,
", ", ", connection=",
ovs_port->connection_uuid, ovs_port->connection_uuid,
""), ""),
(strtmp1 = _strdict_to_string(ovs_port->external_ids)), (strtmp1 = _strdict_to_string(ovs_port->external_ids)),
@ -2192,11 +2194,11 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
&unused)) &unused))
continue; continue;
_LOGT("obj[bridge:%s]: removed a bridge: %s%s%s", _LOGT("monitor: %s: bridge removed: obj[bridge:%s]%s%s",
key,
ovs_bridge->name, ovs_bridge->name,
key,
NM_PRINT_FMT_QUOTED2(ovs_bridge->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_bridge->connection_uuid,
", ", ", connection=",
ovs_bridge->connection_uuid, ovs_bridge->connection_uuid,
"")); ""));
_signal_emit_device_removed(self, ovs_bridge->name, NM_DEVICE_TYPE_OVS_BRIDGE, NULL); _signal_emit_device_removed(self, ovs_bridge->name, NM_DEVICE_TYPE_OVS_BRIDGE, NULL);
@ -2243,11 +2245,12 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
gs_free char *strtmp1 = NULL; gs_free char *strtmp1 = NULL;
gs_free char *strtmp2 = NULL; gs_free char *strtmp2 = NULL;
_LOGT("obj[bridge:%s]: changed a bridge: %s%s%s, external-ids=%s, other-config=%s", _LOGT("monitor: %s: bridge changed: obj[bridge:%s]%s%s, external-ids=%s, "
key, "other-config=%s",
ovs_bridge->name, ovs_bridge->name,
key,
NM_PRINT_FMT_QUOTED2(ovs_bridge->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_bridge->connection_uuid,
", ", ", connection=",
ovs_bridge->connection_uuid, ovs_bridge->connection_uuid,
""), ""),
(strtmp1 = _strdict_to_string(ovs_bridge->external_ids)), (strtmp1 = _strdict_to_string(ovs_bridge->external_ids)),
@ -2267,11 +2270,11 @@ ovsdb_got_update(NMOvsdb *self, json_t *msg)
.other_config = g_steal_pointer(&other_config_arr), .other_config = g_steal_pointer(&other_config_arr),
}; };
g_hash_table_add(priv->bridges, ovs_bridge); g_hash_table_add(priv->bridges, ovs_bridge);
_LOGT("obj[bridge:%s]: added a bridge: %s%s%s, external-ids=%s, other-config=%s", _LOGT("monitor: %s: bridge added: obj[bridge:%s]%s%s, external-ids=%s, other-config=%s",
key,
ovs_bridge->name, ovs_bridge->name,
key,
NM_PRINT_FMT_QUOTED2(ovs_bridge->connection_uuid, NM_PRINT_FMT_QUOTED2(ovs_bridge->connection_uuid,
", ", ", connection=",
ovs_bridge->connection_uuid, ovs_bridge->connection_uuid,
""), ""),
(strtmp1 = _strdict_to_string(ovs_bridge->external_ids)), (strtmp1 = _strdict_to_string(ovs_bridge->external_ids)),

View file

@ -2270,6 +2270,37 @@ add_new:
return NM_ACT_STAGE_RETURN_SUCCESS; return NM_ACT_STAGE_RETURN_SUCCESS;
} }
static void
set_powersave(NMDevice *device)
{
NMDeviceIwd *self = NM_DEVICE_IWD(device);
NMSettingWireless *s_wireless;
NMSettingWirelessPowersave val;
s_wireless = nm_device_get_applied_setting(device, NM_TYPE_SETTING_WIRELESS);
g_return_if_fail(s_wireless);
val = nm_setting_wireless_get_powersave(s_wireless);
if (val == NM_SETTING_WIRELESS_POWERSAVE_DEFAULT) {
val = nm_config_data_get_connection_default_int64(NM_CONFIG_GET_DATA,
"wifi.powersave",
device,
NM_SETTING_WIRELESS_POWERSAVE_IGNORE,
NM_SETTING_WIRELESS_POWERSAVE_ENABLE,
NM_SETTING_WIRELESS_POWERSAVE_IGNORE);
}
_LOGT(LOGD_WIFI, "powersave is set to %u", (unsigned) val);
if (val == NM_SETTING_WIRELESS_POWERSAVE_IGNORE)
return;
nm_platform_wifi_set_powersave(nm_device_get_platform(device),
nm_device_get_ifindex(device),
val == NM_SETTING_WIRELESS_POWERSAVE_ENABLE);
}
static NMActStageReturn static NMActStageReturn
act_stage2_config(NMDevice *device, NMDeviceStateReason *out_failure_reason) act_stage2_config(NMDevice *device, NMDeviceStateReason *out_failure_reason)
{ {
@ -2297,6 +2328,8 @@ act_stage2_config(NMDevice *device, NMDeviceStateReason *out_failure_reason)
goto out_fail; goto out_fail;
} }
set_powersave(device);
/* With priv->iwd_autoconnect we have to let IWD handle retries for /* With priv->iwd_autoconnect we have to let IWD handle retries for
* infrastructure networks. IWD will not necessarily retry the same * infrastructure networks. IWD will not necessarily retry the same
* network after a failure but it will likely go into an autoconnect * network after a failure but it will likely go into an autoconnect

View file

@ -191,6 +191,12 @@ static void supplicant_iface_notify_p2p_available(NMSupplicantInterface *iface,
GParamSpec *pspec, GParamSpec *pspec,
NMDeviceWifi *self); NMDeviceWifi *self);
static void supplicant_iface_notify_wpa_psk_mismatch_cb(NMSupplicantInterface *iface,
NMDeviceWifi *self);
static void supplicant_iface_notify_wpa_sae_mismatch_cb(NMSupplicantInterface *iface,
NMDeviceWifi *self);
static void periodic_update(NMDeviceWifi *self); static void periodic_update(NMDeviceWifi *self);
static void ap_add_remove(NMDeviceWifi *self, static void ap_add_remove(NMDeviceWifi *self,
@ -624,6 +630,14 @@ supplicant_interface_acquire_cb(NMSupplicantManager *supplicant_manager,
"notify::" NM_SUPPLICANT_INTERFACE_P2P_AVAILABLE, "notify::" NM_SUPPLICANT_INTERFACE_P2P_AVAILABLE,
G_CALLBACK(supplicant_iface_notify_p2p_available), G_CALLBACK(supplicant_iface_notify_p2p_available),
self); self);
g_signal_connect(priv->sup_iface,
NM_SUPPLICANT_INTERFACE_PSK_MISMATCH,
G_CALLBACK(supplicant_iface_notify_wpa_psk_mismatch_cb),
self);
g_signal_connect(priv->sup_iface,
NM_SUPPLICANT_INTERFACE_SAE_MISMATCH,
G_CALLBACK(supplicant_iface_notify_wpa_sae_mismatch_cb),
self);
_scan_notify_is_scanning(self); _scan_notify_is_scanning(self);
@ -2237,6 +2251,26 @@ wps_timeout_cb(gpointer user_data)
return G_SOURCE_REMOVE; return G_SOURCE_REMOVE;
} }
static gboolean
wifi_connection_is_new(NMDeviceWifi *self)
{
NMDevice *device = NM_DEVICE(self);
NMActRequest *req;
NMSettingsConnection *connection;
guint64 timestamp = 0;
req = nm_device_get_act_request(device);
g_return_val_if_fail(NM_IS_ACT_REQUEST(req), TRUE);
connection = nm_act_request_get_settings_connection(req);
g_return_val_if_fail(NM_IS_SETTINGS_CONNECTION(connection), TRUE);
if (nm_settings_connection_get_timestamp(connection, &timestamp) && timestamp != 0)
return FALSE;
return TRUE;
}
static void static void
wifi_secrets_get_secrets(NMDeviceWifi *self, wifi_secrets_get_secrets(NMDeviceWifi *self,
const char *setting_name, const char *setting_name,
@ -2394,15 +2428,18 @@ handle_8021x_or_psk_auth_fail(NMDeviceWifi *self,
NMDevice *device = NM_DEVICE(self); NMDevice *device = NM_DEVICE(self);
NMActRequest *req; NMActRequest *req;
const char *setting_name = NULL; const char *setting_name = NULL;
gboolean handled = FALSE; NMSecretAgentGetSecretsFlags secret_flags = NM_SECRET_AGENT_GET_SECRETS_FLAG_ALLOW_INTERACTION
| NM_SECRET_AGENT_GET_SECRETS_FLAG_REQUEST_NEW;
g_return_val_if_fail(new_state == NM_SUPPLICANT_INTERFACE_STATE_DISCONNECTED, FALSE); g_return_val_if_fail(new_state == NM_SUPPLICANT_INTERFACE_STATE_DISCONNECTED, FALSE);
if (nm_device_get_state(device) != NM_DEVICE_STATE_CONFIG)
return FALSE;
req = nm_device_get_act_request(NM_DEVICE(self)); req = nm_device_get_act_request(NM_DEVICE(self));
g_return_val_if_fail(req != NULL, FALSE); g_return_val_if_fail(req != NULL, FALSE);
if (need_new_8021x_secrets(self, old_state, &setting_name) if (need_new_8021x_secrets(self, old_state, &setting_name)) {
|| need_new_wpa_psk(self, old_state, disconnect_reason, &setting_name)) {
nm_act_request_clear_secrets(req); nm_act_request_clear_secrets(req);
_LOGI(LOGD_DEVICE | LOGD_WIFI, _LOGI(LOGD_DEVICE | LOGD_WIFI,
@ -2412,14 +2449,54 @@ handle_8021x_or_psk_auth_fail(NMDeviceWifi *self,
nm_device_state_changed(device, nm_device_state_changed(device,
NM_DEVICE_STATE_NEED_AUTH, NM_DEVICE_STATE_NEED_AUTH,
NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT); NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT);
wifi_secrets_get_secrets(self, wifi_secrets_get_secrets(self, setting_name, secret_flags);
setting_name, return TRUE;
NM_SECRET_AGENT_GET_SECRETS_FLAG_ALLOW_INTERACTION
| NM_SECRET_AGENT_GET_SECRETS_FLAG_REQUEST_NEW);
handled = TRUE;
} }
return handled; if (need_new_wpa_psk(self, old_state, disconnect_reason, &setting_name)) {
nm_act_request_clear_secrets(req);
cleanup_association_attempt(self, TRUE);
if (wifi_connection_is_new(self)) {
_LOGI(LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) new connection disconnected during association, asking for "
"new key");
nm_device_state_changed(device,
NM_DEVICE_STATE_NEED_AUTH,
NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT);
wifi_secrets_get_secrets(self, setting_name, secret_flags);
return TRUE;
}
if (!nm_device_auth_retries_try_next(device)) {
nm_device_state_changed(device,
NM_DEVICE_STATE_FAILED,
NM_DEVICE_STATE_REASON_NO_SECRETS);
return TRUE;
}
if (nm_device_auth_retries_has_next(device)) {
secret_flags &= ~NM_SECRET_AGENT_GET_SECRETS_FLAG_REQUEST_NEW;
_LOGI(
LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) disconnected during association, reauthenticating connection");
} else {
_LOGI(LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) disconnected during association, asking for new key");
}
nm_device_state_changed(device,
NM_DEVICE_STATE_NEED_AUTH,
NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT);
wifi_secrets_get_secrets(self, setting_name, secret_flags);
return TRUE;
}
_LOGI(LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) disconnected during association, retrying connection");
return FALSE;
} }
static gboolean static gboolean
@ -2841,6 +2918,68 @@ handle_auth_or_fail(NMDeviceWifi *self, NMActRequest *req, gboolean new_secrets)
return TRUE; return TRUE;
} }
static void
supplicant_iface_notify_wpa_psk_mismatch_cb(NMSupplicantInterface *iface, NMDeviceWifi *self)
{
NMDevice *device = NM_DEVICE(self);
NMActRequest *req;
const char *setting_name = NM_SETTING_WIRELESS_SECURITY_SETTING_NAME;
if (nm_device_get_state(device) != NM_DEVICE_STATE_CONFIG)
return;
if (!wifi_connection_is_new(self) && nm_device_auth_retries_has_next(device)) {
_LOGI(LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) psk mismatch reported by supplicant, retrying connection");
return;
}
_LOGI(LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) psk mismatch reported by supplicant, asking for new key");
req = nm_device_get_act_request(NM_DEVICE(self));
g_return_if_fail(req != NULL);
nm_act_request_clear_secrets(req);
cleanup_association_attempt(self, TRUE);
nm_device_state_changed(device,
NM_DEVICE_STATE_NEED_AUTH,
NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT);
wifi_secrets_get_secrets(self,
setting_name,
NM_SECRET_AGENT_GET_SECRETS_FLAG_ALLOW_INTERACTION
| NM_SECRET_AGENT_GET_SECRETS_FLAG_REQUEST_NEW);
}
static void
supplicant_iface_notify_wpa_sae_mismatch_cb(NMSupplicantInterface *iface, NMDeviceWifi *self)
{
NMDevice *device = NM_DEVICE(self);
NMActRequest *req;
const char *setting_name = NM_SETTING_WIRELESS_SECURITY_SETTING_NAME;
if (nm_device_get_state(device) != NM_DEVICE_STATE_CONFIG)
return;
_LOGI(LOGD_DEVICE | LOGD_WIFI,
"Activation: (wifi) SAE password mismatch reported by supplicant, asking for new key");
req = nm_device_get_act_request(NM_DEVICE(self));
g_return_if_fail(req != NULL);
nm_act_request_clear_secrets(req);
cleanup_association_attempt(self, TRUE);
nm_device_state_changed(device,
NM_DEVICE_STATE_NEED_AUTH,
NM_DEVICE_STATE_REASON_SUPPLICANT_DISCONNECT);
wifi_secrets_get_secrets(self,
setting_name,
NM_SECRET_AGENT_GET_SECRETS_FLAG_ALLOW_INTERACTION
| NM_SECRET_AGENT_GET_SECRETS_FLAG_REQUEST_NEW);
}
/* /*
* supplicant_connection_timeout_cb * supplicant_connection_timeout_cb
* *
@ -2946,7 +3085,8 @@ build_supplicant_config(NMDeviceWifi *self,
s_wireless = nm_connection_get_setting_wireless(connection); s_wireless = nm_connection_get_setting_wireless(connection);
g_return_val_if_fail(s_wireless != NULL, NULL); g_return_val_if_fail(s_wireless != NULL, NULL);
config = nm_supplicant_config_new(nm_supplicant_interface_get_capabilities(priv->sup_iface)); config = nm_supplicant_config_new(nm_supplicant_interface_get_capabilities(priv->sup_iface),
nm_utils_get_connection_first_permissions_user(connection));
/* Warn if AP mode may not be supported */ /* Warn if AP mode may not be supported */
if (nm_streq0(nm_setting_wireless_get_mode(s_wireless), NM_SETTING_WIRELESS_MODE_AP) if (nm_streq0(nm_setting_wireless_get_mode(s_wireless), NM_SETTING_WIRELESS_MODE_AP)
@ -3022,6 +3162,7 @@ build_supplicant_config(NMDeviceWifi *self,
mtu, mtu,
pmf, pmf,
fils, fils,
nm_device_get_private_files(NM_DEVICE(self)),
error)) { error)) {
g_prefix_error(error, "802-11-wireless-security: "); g_prefix_error(error, "802-11-wireless-security: ");
goto error; goto error;
@ -3182,8 +3323,19 @@ act_stage1_prepare(NMDevice *device, NMDeviceStateReason *out_failure_reason)
static void static void
ensure_hotspot_frequency(NMDeviceWifi *self, NMSettingWireless *s_wifi, NMWifiAP *ap) ensure_hotspot_frequency(NMDeviceWifi *self, NMSettingWireless *s_wifi, NMWifiAP *ap)
{ {
guint32 a_freqs[] = {5180, 5200, 5220, 5745, 5765, 5785, 5805, 0}; guint32 freqs_a[] = {5180, /* only U-NII-1 channels: non-DFS and available everywhere */
guint32 bg_freqs[] = {2412, 2437, 2462, 2472, 0}; 5200,
5220,
5240,
0};
guint32 freqs_bg[] = {2412, 2437, 2462, 2472, 0};
guint32 freqs_6ghz[] = {5975, /* only U-NII-5 PSC channels, for better compatibility */
6055,
6135,
6215,
6295,
6375,
0};
guint32 *rnd_freqs; guint32 *rnd_freqs;
guint rnd_freqs_len; guint rnd_freqs_len;
NMDevice *device = NM_DEVICE(self); NMDevice *device = NM_DEVICE(self);
@ -3194,7 +3346,7 @@ ensure_hotspot_frequency(NMDeviceWifi *self, NMSettingWireless *s_wifi, NMWifiAP
guint l; guint l;
nm_assert(ap); nm_assert(ap);
nm_assert(NM_IN_STRSET(band, NULL, "a", "bg")); nm_assert(NM_IN_STRSET(band, NULL, "a", "bg", "6GHz"));
if (nm_wifi_ap_get_freq(ap)) if (nm_wifi_ap_get_freq(ap))
return; return;
@ -3228,11 +3380,14 @@ ensure_hotspot_frequency(NMDeviceWifi *self, NMSettingWireless *s_wifi, NMWifiAP
} }
if (nm_streq0(band, "a")) { if (nm_streq0(band, "a")) {
rnd_freqs = a_freqs; rnd_freqs = freqs_a;
rnd_freqs_len = G_N_ELEMENTS(a_freqs) - 1; rnd_freqs_len = G_N_ELEMENTS(freqs_a) - 1;
} else if (nm_streq0(band, "6GHz")) {
rnd_freqs = freqs_6ghz;
rnd_freqs_len = G_N_ELEMENTS(freqs_6ghz) - 1;
} else { } else {
rnd_freqs = bg_freqs; rnd_freqs = freqs_bg;
rnd_freqs_len = G_N_ELEMENTS(bg_freqs) - 1; rnd_freqs_len = G_N_ELEMENTS(freqs_bg) - 1;
} }
/* shuffle the frequencies (inplace). The idea is to choose /* shuffle the frequencies (inplace). The idea is to choose

View file

@ -684,7 +684,7 @@ iwd_config_write(GKeyFile *config,
* in the last few filename characters -- it cannot end in .open, .psk * in the last few filename characters -- it cannot end in .open, .psk
* or .8021x. * or .8021x.
*/ */
return nm_utils_file_set_contents(filepath, data, length, 0600, times, NULL, error); return nm_utils_file_set_contents(filepath, data, length, 0600, times, NULL, NULL, error);
} }
static const char * static const char *

View file

@ -574,16 +574,6 @@ nm_wifi_ap_to_string(const NMWifiAP *self, char *str_buf, gulong buf_len, gint64
return str_buf; return str_buf;
} }
static guint
freq_to_band(guint32 freq)
{
if (freq >= 4915 && freq <= 5825)
return 5;
else if (freq >= 2412 && freq <= 2484)
return 2;
return 0;
}
gboolean gboolean
nm_wifi_ap_check_compatible(NMWifiAP *self, NMConnection *connection) nm_wifi_ap_check_compatible(NMWifiAP *self, NMConnection *connection)
{ {
@ -631,12 +621,12 @@ nm_wifi_ap_check_compatible(NMWifiAP *self, NMConnection *connection)
band = nm_setting_wireless_get_band(s_wireless); band = nm_setting_wireless_get_band(s_wireless);
if (band) { if (band) {
guint ap_band = freq_to_band(priv->freq); const char *ap_band = nm_wifi_freq_to_band_prop(priv->freq);
if (!strcmp(band, "a") && ap_band != 5) if (!nm_streq(band, ap_band))
return FALSE;
else if (!strcmp(band, "bg") && ap_band != 2)
return FALSE; return FALSE;
return TRUE;
} }
channel = nm_setting_wireless_get_channel(s_wireless); channel = nm_setting_wireless_get_channel(s_wireless);

View file

@ -639,7 +639,7 @@ nm_wifi_utils_complete_connection(GBytes *ap_ssid,
chan_valid = FALSE; chan_valid = FALSE;
} }
band = nm_utils_wifi_freq_to_band(ap_freq); band = nm_wifi_freq_to_band_prop(ap_freq);
if (band) { if (band) {
g_object_set(s_wifi, NM_SETTING_WIRELESS_BAND, band, NULL); g_object_set(s_wifi, NM_SETTING_WIRELESS_BAND, band, NULL);
} else { } else {
@ -1929,3 +1929,19 @@ nm_wifi_utils_wfd_info_eq(const NMIwdWfdInfo *a, const NMIwdWfdInfo *b)
return a->source == b->source && a->sink == b->sink && a->port == b->port return a->source == b->source && a->sink == b->sink && a->port == b->port
&& a->has_audio == b->has_audio && a->has_uibc == b->has_uibc && a->has_cp == b->has_cp; && a->has_audio == b->has_audio && a->has_uibc == b->has_uibc && a->has_cp == b->has_cp;
} }
const char *
nm_wifi_freq_to_band_prop(guint32 freq)
{
switch (nm_utils_wifi_freq_to_band(freq)) {
case NM_WIFI_BAND_2_4_GHZ:
return "bg";
case NM_WIFI_BAND_5_GHZ:
return "a";
case NM_WIFI_BAND_6_GHZ:
return "6GHz";
default:
case NM_WIFI_BAND_UNKNOWN:
return NULL;
}
}

View file

@ -56,4 +56,6 @@ bool nm_wifi_utils_parse_wfd_ies(GBytes *ies, NMIwdWfdInfo *out_wfd);
GBytes *nm_wifi_utils_build_wfd_ies(const NMIwdWfdInfo *wfd); GBytes *nm_wifi_utils_build_wfd_ies(const NMIwdWfdInfo *wfd);
bool nm_wifi_utils_wfd_info_eq(const NMIwdWfdInfo *a, const NMIwdWfdInfo *b); bool nm_wifi_utils_wfd_info_eq(const NMIwdWfdInfo *a, const NMIwdWfdInfo *b);
const char *nm_wifi_freq_to_band_prop(guint32 freq);
#endif /* __NM_WIFI_UTILS_H__ */ #endif /* __NM_WIFI_UTILS_H__ */

View file

@ -510,6 +510,7 @@ try_create_connect_properties(NMModemBroadband *self)
{ {
NMModemBroadbandPrivate *priv = NM_MODEM_BROADBAND_GET_PRIVATE(self); NMModemBroadbandPrivate *priv = NM_MODEM_BROADBAND_GET_PRIVATE(self);
ConnectContext *ctx = priv->ctx; ConnectContext *ctx = priv->ctx;
NMDeviceStateReason fail_reason = NM_DEVICE_STATE_REASON_MODEM_INIT_FAILED;
if (MODEM_CAPS_3GPP(ctx->caps)) { if (MODEM_CAPS_3GPP(ctx->caps)) {
NMSettingGsm *s_gsm = nm_connection_get_setting_gsm(ctx->connection); NMSettingGsm *s_gsm = nm_connection_get_setting_gsm(ctx->connection);
@ -522,7 +523,7 @@ try_create_connect_properties(NMModemBroadband *self)
if (s_gsm) if (s_gsm)
network_id = nm_setting_gsm_get_network_id(s_gsm); network_id = nm_setting_gsm_get_network_id(s_gsm);
if (!network_id) { if (!network_id) {
if (mm_modem_get_state(self->_priv.modem_iface) < MM_MODEM_STATE_REGISTERED) if (mm_modem_get_state(self->_priv.modem_iface) != MM_MODEM_STATE_REGISTERED)
return FALSE; return FALSE;
modem_3gpp = mm_object_get_modem_3gpp(priv->modem_object); modem_3gpp = mm_object_get_modem_3gpp(priv->modem_object);
network_id = mm_modem_3gpp_get_operator_code(modem_3gpp); network_id = mm_modem_3gpp_get_operator_code(modem_3gpp);
@ -530,6 +531,7 @@ try_create_connect_properties(NMModemBroadband *self)
if (!network_id) { if (!network_id) {
_LOGW("failed to connect '%s': unable to determine the network id", _LOGW("failed to connect '%s': unable to determine the network id",
nm_connection_get_id(ctx->connection)); nm_connection_get_id(ctx->connection));
fail_reason = NM_DEVICE_STATE_REASON_MODEM_NO_OPERATOR_CODE;
goto out; goto out;
} }
@ -558,7 +560,7 @@ try_create_connect_properties(NMModemBroadband *self)
} }
out: out:
nm_modem_emit_prepare_result(NM_MODEM(self), FALSE, NM_DEVICE_STATE_REASON_MODEM_INIT_FAILED); nm_modem_emit_prepare_result(NM_MODEM(self), FALSE, fail_reason);
connect_context_clear(self); connect_context_clear(self);
return TRUE; return TRUE;
} }
@ -1649,6 +1651,8 @@ nm_modem_broadband_new(GObject *object, GError **error)
driver, driver,
NM_MODEM_OPERATOR_CODE, NM_MODEM_OPERATOR_CODE,
operator_code, operator_code,
NM_MODEM_DEVICE_UID,
mm_modem_get_device(modem_iface),
NULL); NULL);
} }

View file

@ -258,16 +258,7 @@ modm_handle_name_owner_changed(MMManager *modem_manager, GParamSpec *pspec, NMMo
/* Available! */ /* Available! */
g_free(name_owner); g_free(name_owner);
/* Hack alert: GDBusObjectManagerClient won't signal neither 'object-added' modm_manager_available(self);
* nor 'object-removed' if it was created while there was no ModemManager in
* the bus. This hack avoids this issue until we get a GIO with the fix
* included... */
modm_clear_manager(self);
modm_ensure_manager(self);
/* Whenever GDBusObjectManagerClient is fixed, we can just do the following:
* modm_manager_available (self);
*/
} }
static void static void

View file

@ -39,7 +39,8 @@ NM_GOBJECT_PROPERTIES_DEFINE(NMModem,
PROP_IP_TYPES, PROP_IP_TYPES,
PROP_SIM_OPERATOR_ID, PROP_SIM_OPERATOR_ID,
PROP_OPERATOR_CODE, PROP_OPERATOR_CODE,
PROP_APN, ); PROP_APN,
PROP_DEVICE_UID, );
enum { enum {
PPP_STATS, PPP_STATS,
@ -78,6 +79,7 @@ typedef struct _NMModemPrivate {
char *sim_operator_id; char *sim_operator_id;
char *operator_code; char *operator_code;
char *apn; char *apn;
char *device_uid;
NMPPPManager *ppp_manager; NMPPPManager *ppp_manager;
NMPppMgr *ppp_mgr; NMPppMgr *ppp_mgr;
@ -618,6 +620,12 @@ nm_modem_get_apn(NMModem *self)
return NM_MODEM_GET_PRIVATE(self)->apn; return NM_MODEM_GET_PRIVATE(self)->apn;
} }
const char *
nm_modem_get_device_uid(NMModem *self)
{
return NM_MODEM_GET_PRIVATE(self)->device_uid;
}
/*****************************************************************************/ /*****************************************************************************/
static void static void
@ -1121,6 +1129,22 @@ nm_modem_check_connection_compatible(NMModem *self, NMConnection *connection, GE
} }
} }
str = nm_setting_gsm_get_device_uid(s_gsm);
if (str) {
if (!priv->device_uid) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"GSM profile has device-uid, device does not");
return FALSE;
}
if (!nm_streq(str, priv->device_uid)) {
nm_utils_error_set_literal(error,
NM_UTILS_ERROR_CONNECTION_AVAILABLE_TEMPORARY,
"device has differing device-uid than GSM profile");
return FALSE;
}
}
/* SIM properties may not be available before the SIM is unlocked, so /* SIM properties may not be available before the SIM is unlocked, so
* to ensure that autoconnect works, the connection's SIM properties * to ensure that autoconnect works, the connection's SIM properties
* are only compared if present on the device. * are only compared if present on the device.
@ -1644,6 +1668,9 @@ get_property(GObject *object, guint prop_id, GValue *value, GParamSpec *pspec)
case PROP_APN: case PROP_APN:
g_value_set_string(value, priv->apn); g_value_set_string(value, priv->apn);
break; break;
case PROP_DEVICE_UID:
g_value_set_string(value, priv->device_uid);
break;
default: default:
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec); G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
break; break;
@ -1699,6 +1726,10 @@ set_property(GObject *object, guint prop_id, const GValue *value, GParamSpec *ps
/* construct-only */ /* construct-only */
priv->operator_code = g_value_dup_string(value); priv->operator_code = g_value_dup_string(value);
break; break;
case PROP_DEVICE_UID:
/* construct-only */
priv->device_uid = g_value_dup_string(value);
break;
default: default:
G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec); G_OBJECT_WARN_INVALID_PROPERTY_ID(object, prop_id, pspec);
break; break;
@ -1758,6 +1789,7 @@ finalize(GObject *object)
g_free(priv->sim_operator_id); g_free(priv->sim_operator_id);
g_free(priv->operator_code); g_free(priv->operator_code);
g_free(priv->apn); g_free(priv->apn);
g_free(priv->device_uid);
G_OBJECT_CLASS(nm_modem_parent_class)->finalize(object); G_OBJECT_CLASS(nm_modem_parent_class)->finalize(object);
} }
@ -1863,6 +1895,13 @@ nm_modem_class_init(NMModemClass *klass)
obj_properties[PROP_APN] = obj_properties[PROP_APN] =
g_param_spec_string(NM_MODEM_APN, "", "", NULL, G_PARAM_READABLE | G_PARAM_STATIC_STRINGS); g_param_spec_string(NM_MODEM_APN, "", "", NULL, G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
obj_properties[PROP_DEVICE_UID] =
g_param_spec_string(NM_MODEM_DEVICE_UID,
"",
"",
NULL,
G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS);
g_object_class_install_properties(object_class, _PROPERTY_ENUMS_LAST, obj_properties); g_object_class_install_properties(object_class, _PROPERTY_ENUMS_LAST, obj_properties);
signals[PPP_STATS] = g_signal_new(NM_MODEM_PPP_STATS, signals[PPP_STATS] = g_signal_new(NM_MODEM_PPP_STATS,

View file

@ -30,6 +30,7 @@
#define NM_MODEM_SIM_OPERATOR_ID "sim-operator-id" #define NM_MODEM_SIM_OPERATOR_ID "sim-operator-id"
#define NM_MODEM_OPERATOR_CODE "operator-code" #define NM_MODEM_OPERATOR_CODE "operator-code"
#define NM_MODEM_APN "apn" #define NM_MODEM_APN "apn"
#define NM_MODEM_DEVICE_UID "device-uid"
/* Signals */ /* Signals */
#define NM_MODEM_PPP_STATS "ppp-stats" #define NM_MODEM_PPP_STATS "ppp-stats"
@ -154,6 +155,7 @@ const char *nm_modem_get_sim_id(NMModem *modem);
const char *nm_modem_get_sim_operator_id(NMModem *modem); const char *nm_modem_get_sim_operator_id(NMModem *modem);
const char *nm_modem_get_operator_code(NMModem *modem); const char *nm_modem_get_operator_code(NMModem *modem);
const char *nm_modem_get_apn(NMModem *modem); const char *nm_modem_get_apn(NMModem *modem);
const char *nm_modem_get_device_uid(NMModem *modem);
gboolean nm_modem_set_data_port(NMModem *self, gboolean nm_modem_set_data_port(NMModem *self,
NMPlatform *platform, NMPlatform *platform,

View file

@ -1460,7 +1460,9 @@ nm_dhcp_client_schedule_ipv6_only_restart(NMDhcpClient *self, guint timeout)
nm_assert(!priv->is_stopped); nm_assert(!priv->is_stopped);
timeout = NM_MAX(priv->v4.ipv6_only_min_wait, timeout); timeout = NM_MAX(priv->v4.ipv6_only_min_wait, timeout);
_LOGI("received option \"ipv6-only-preferred\": stopping DHCPv4 for %u seconds", timeout); _LOGI("received option \"ipv6-only-preferred\": stopping DHCPv4 for %u seconds. Set "
"ipv4.dhcp-ipv6-only-preferred=no to force the use of IPv4 on this IPv6-mostly network",
timeout);
nm_dhcp_client_stop(self, FALSE); nm_dhcp_client_stop(self, FALSE);
nm_clear_g_source_inst(&priv->no_lease_timeout_source); nm_clear_g_source_inst(&priv->no_lease_timeout_source);

View file

@ -289,8 +289,10 @@ nm_dhcp_manager_init(NMDhcpManager *self)
NM_CONFIG_GET_VALUE_STRIP | NM_CONFIG_GET_VALUE_NO_EMPTY); NM_CONFIG_GET_VALUE_STRIP | NM_CONFIG_GET_VALUE_NO_EMPTY);
client = client_free; client = client_free;
if (client) { if (client) {
client_factory = _client_factory_available(_client_factory_find_by_name(client)); client_factory = _client_factory_find_by_name(client);
if (!client_factory) if (!client_factory)
_LOGW(AF_UNSPEC, "init: unknown DHCP client '%s', ignoring", client);
else if (!(client_factory = _client_factory_available(client_factory)))
_LOGW(AF_UNSPEC, "init: DHCP client '%s' not available", client); _LOGW(AF_UNSPEC, "init: DHCP client '%s' not available", client);
} }
if (!client_factory) { if (!client_factory) {

View file

@ -418,7 +418,6 @@ lease_parse_routes(NDhcp4ClientLease *lease,
in_addr_t gateway; in_addr_t gateway;
uint8_t plen; uint8_t plen;
guint32 m; guint32 m;
gboolean has_router_from_classless = FALSE;
gboolean has_classless = FALSE; gboolean has_classless = FALSE;
guint32 default_route_metric_offset = 0; guint32 default_route_metric_offset = 0;
const guint8 *l_data; const guint8 *l_data;
@ -434,7 +433,7 @@ lease_parse_routes(NDhcp4ClientLease *lease,
* We will however also parse one of the options into the "l3cd" for configuring routing. * We will however also parse one of the options into the "l3cd" for configuring routing.
* Thereby we prefer 121 over 249 over 33. * Thereby we prefer 121 over 249 over 33.
* *
* Preferring 121 over 33 is defined by RFC 3443. * Preferring 121 over 33 is defined by RFC 3442.
* Preferring 121 over 249 over 33 is made up as it makes sense (the MS docs are not very clear). * Preferring 121 over 249 over 33 is made up as it makes sense (the MS docs are not very clear).
*/ */
for (i = 0; i < 2; i++) { for (i = 0; i < 2; i++) {
@ -461,7 +460,6 @@ lease_parse_routes(NDhcp4ClientLease *lease,
/* if there are multiple default routes, we add them with differing /* if there are multiple default routes, we add them with differing
* metrics. */ * metrics. */
m = default_route_metric_offset++; m = default_route_metric_offset++;
has_router_from_classless = TRUE;
} else } else
m = 0; m = 0;
@ -495,7 +493,7 @@ lease_parse_routes(NDhcp4ClientLease *lease,
nm_str_buf_append_printf(sbuf, "%s/%d %s", dest_str, (int) plen, gateway_str); nm_str_buf_append_printf(sbuf, "%s/%d %s", dest_str, (int) plen, gateway_str);
if (has_classless) { if (has_classless) {
/* RFC 3443: if the DHCP server returns both a Classless Static Routes /* RFC 3442: if the DHCP server returns both a Classless Static Routes
* option and a Static Routes option, the DHCP client MUST ignore the * option and a Static Routes option, the DHCP client MUST ignore the
* Static Routes option. */ * Static Routes option. */
continue; continue;
@ -539,13 +537,10 @@ lease_parse_routes(NDhcp4ClientLease *lease,
continue; continue;
} }
if (has_router_from_classless) { if (has_classless) {
/* If the DHCP server returns both a Classless Static Routes option and a /* RFC 3442: if the DHCP server returns both a Classless Static Routes
* Router option, the DHCP client MUST ignore the Router option [RFC 3442]. * option and a Router option, the DHCP client MUST ignore the Router
* * option. */
* Be more lenient and ignore the Router option only if Classless Static
* Routes contain a default gateway (as other DHCP backends do).
*/
continue; continue;
} }

View file

@ -32,11 +32,11 @@ ip4_process_dhcpcd_rfc3442_routes(const char *iface,
in_addr_t address, in_addr_t address,
guint32 *out_gwaddr) guint32 *out_gwaddr)
{ {
gs_free const char **routes = NULL; gs_free char **routes = NULL;
const char **r; char **r;
gboolean have_routes = FALSE; gboolean have_routes = FALSE;
routes = nm_strsplit_set(str, " "); routes = (char **) nm_strsplit_set(str, " ");
if (!routes) if (!routes)
return FALSE; return FALSE;

View file

@ -374,7 +374,7 @@ server_builder_append_base(GVariantBuilder *argument_builder,
NMDnsServer dns_server; NMDnsServer dns_server;
gsize addr_size; gsize addr_size;
if (!nm_dns_uri_parse(address_family, address_string, &dns_server)) if (!nm_dns_uri_parse(address_family, address_string, &dns_server, NULL))
return FALSE; return FALSE;
addr_size = nm_utils_addr_family_to_size(dns_server.addr_family); addr_size = nm_utils_addr_family_to_size(dns_server.addr_family);

View file

@ -521,9 +521,10 @@ _gl_pid_spawn_next_step(void)
argv[argv_idx++] = "--no-resolv"; /* Use only commandline */ argv[argv_idx++] = "--no-resolv"; /* Use only commandline */
argv[argv_idx++] = "--keep-in-foreground"; argv[argv_idx++] = "--keep-in-foreground";
argv[argv_idx++] = "--no-hosts"; /* don't use /etc/hosts to resolve */ argv[argv_idx++] = "--no-hosts"; /* don't use /etc/hosts to resolve */
argv[argv_idx++] = "--bind-interfaces"; argv[argv_idx++] = "--bind-dynamic";
argv[argv_idx++] = "--pid-file=" PIDFILE; argv[argv_idx++] = "--pid-file=" PIDFILE;
argv[argv_idx++] = "--listen-address=127.0.0.1"; /* Should work for both 4 and 6 */ argv[argv_idx++] = "--listen-address=127.0.0.1";
argv[argv_idx++] = "--listen-address=::1";
argv[argv_idx++] = "--cache-size=400"; argv[argv_idx++] = "--cache-size=400";
argv[argv_idx++] = "--clear-on-reload"; /* clear cache when dns server changes */ argv[argv_idx++] = "--clear-on-reload"; /* clear cache when dns server changes */
argv[argv_idx++] = "--conf-file=/dev/null"; /* avoid loading /etc/dnsmasq.conf */ argv[argv_idx++] = "--conf-file=/dev/null"; /* avoid loading /etc/dnsmasq.conf */

View file

@ -26,6 +26,7 @@
#include "libnm-core-intern/nm-core-internal.h" #include "libnm-core-intern/nm-core-internal.h"
#include "libnm-glib-aux/nm-str-buf.h" #include "libnm-glib-aux/nm-str-buf.h"
#include "libnm-glib-aux/nm-io-utils.h"
#include "NetworkManagerUtils.h" #include "NetworkManagerUtils.h"
#include "devices/nm-device.h" #include "devices/nm-device.h"
@ -370,7 +371,7 @@ _ASSERT_dns_config_ip_data(const NMDnsConfigIPData *ip_data)
gboolean has_default = FALSE; gboolean has_default = FALSE;
gsize i; gsize i;
for (i = 0; ip_data->domains.search && ip_data->domains.search; i++) { for (i = 0; ip_data->domains.search && ip_data->domains.search[i]; i++) {
const char *d = ip_data->domains.search[i]; const char *d = ip_data->domains.search[i];
d = nm_utils_parse_dns_domain(d, NULL); d = nm_utils_parse_dns_domain(d, NULL);
@ -1007,6 +1008,7 @@ _read_link_cached(const char *path, gboolean *is_cached, char **cached)
#define RESOLV_CONF_TMP "/etc/.resolv.conf.NetworkManager" #define RESOLV_CONF_TMP "/etc/.resolv.conf.NetworkManager"
#define NO_STUB_RESOLV_CONF NMRUNDIR "/no-stub-resolv.conf" #define NO_STUB_RESOLV_CONF NMRUNDIR "/no-stub-resolv.conf"
#define NO_STUB_RESOLV_CONF_TMP NMRUNDIR "/no-stub-resolv.conf.tmp"
static void static void
update_resolv_conf_no_stub(NMDnsManager *self, update_resolv_conf_no_stub(NMDnsManager *self,
@ -1019,7 +1021,14 @@ update_resolv_conf_no_stub(NMDnsManager *self,
content = create_resolv_conf(searches, nameservers, options); content = create_resolv_conf(searches, nameservers, options);
if (!g_file_set_contents(NO_STUB_RESOLV_CONF, content, -1, &local)) { if (!nm_utils_file_set_contents(NO_STUB_RESOLV_CONF,
content,
-1,
0644,
NULL,
NO_STUB_RESOLV_CONF_TMP,
NULL,
&local)) {
_LOGD("update-resolv-no-stub: failure to write file: %s", local->message); _LOGD("update-resolv-no-stub: failure to write file: %s", local->message);
g_error_free(local); g_error_free(local);
return; return;
@ -1501,7 +1510,7 @@ _domain_track_is_shadowed(GHashTable *ht,
const char **out_parent, const char **out_parent,
int *out_parent_priority) int *out_parent_priority)
{ {
char *parent; const char *parent;
int parent_priority; int parent_priority;
if (!ht) if (!ht)

View file

@ -37,6 +37,7 @@
static const char *const DBUS_OP_SET_LINK_DEFAULT_ROUTE = "SetLinkDefaultRoute"; static const char *const DBUS_OP_SET_LINK_DEFAULT_ROUTE = "SetLinkDefaultRoute";
static const char *const DBUS_OP_SET_LINK_DNS_OVER_TLS = "SetLinkDNSOverTLS"; static const char *const DBUS_OP_SET_LINK_DNS_OVER_TLS = "SetLinkDNSOverTLS";
static const char *const DBUS_OP_SET_LINK_DNS_EX = "SetLinkDNSEx"; static const char *const DBUS_OP_SET_LINK_DNS_EX = "SetLinkDNSEx";
static const char *const DBUS_OP_SET_LINK_DNSSEC = "SetLinkDNSSEC";
/*****************************************************************************/ /*****************************************************************************/
@ -398,7 +399,7 @@ update_add_ip_config(NMDnsSystemdResolved *self,
for (i = 0; i < n; i++) { for (i = 0; i < n; i++) {
NMDnsServer dns_server; NMDnsServer dns_server;
if (!nm_dns_uri_parse(ip_data->addr_family, strarr[i], &dns_server)) if (!nm_dns_uri_parse(ip_data->addr_family, strarr[i], &dns_server, NULL))
continue; continue;
if (!NM_IN_SET(dns_server.scheme, if (!NM_IN_SET(dns_server.scheme,
@ -484,9 +485,11 @@ prepare_one_interface(NMDnsSystemdResolved *self, const InterfaceConfig *ic)
NMSettingConnectionMdns mdns = NM_SETTING_CONNECTION_MDNS_DEFAULT; NMSettingConnectionMdns mdns = NM_SETTING_CONNECTION_MDNS_DEFAULT;
NMSettingConnectionLlmnr llmnr = NM_SETTING_CONNECTION_LLMNR_DEFAULT; NMSettingConnectionLlmnr llmnr = NM_SETTING_CONNECTION_LLMNR_DEFAULT;
NMSettingConnectionDnsOverTls dns_over_tls = NM_SETTING_CONNECTION_DNS_OVER_TLS_DEFAULT; NMSettingConnectionDnsOverTls dns_over_tls = NM_SETTING_CONNECTION_DNS_OVER_TLS_DEFAULT;
NMSettingConnectionDnssec dnssec = NM_SETTING_CONNECTION_DNSSEC_DEFAULT;
const char *mdns_arg = NULL; const char *mdns_arg = NULL;
const char *llmnr_arg = NULL; const char *llmnr_arg = NULL;
const char *dns_over_tls_arg = NULL; const char *dns_over_tls_arg = NULL;
const char *dnssec_arg = NULL;
gboolean has_config = FALSE; gboolean has_config = FALSE;
gboolean has_default_route = FALSE; gboolean has_default_route = FALSE;
guint i; guint i;
@ -517,6 +520,7 @@ prepare_one_interface(NMDnsSystemdResolved *self, const InterfaceConfig *ic)
llmnr = NM_MAX(llmnr, nm_l3_config_data_get_llmnr(ip_data->l3cd)); llmnr = NM_MAX(llmnr, nm_l3_config_data_get_llmnr(ip_data->l3cd));
dns_over_tls = dns_over_tls =
NM_MAX(dns_over_tls, nm_l3_config_data_get_dns_over_tls(ip_data->l3cd)); NM_MAX(dns_over_tls, nm_l3_config_data_get_dns_over_tls(ip_data->l3cd));
dnssec = NM_MAX(dnssec, nm_l3_config_data_get_dnssec(ip_data->l3cd));
} }
} }
} }
@ -589,8 +593,24 @@ prepare_one_interface(NMDnsSystemdResolved *self, const InterfaceConfig *ic)
} }
nm_assert(dns_over_tls_arg); nm_assert(dns_over_tls_arg);
switch (dnssec) {
case NM_SETTING_CONNECTION_DNSSEC_NO:
dnssec_arg = "no";
break;
case NM_SETTING_CONNECTION_DNSSEC_ALLOW_DOWNGRADE:
dnssec_arg = "allow-downgrade";
break;
case NM_SETTING_CONNECTION_DNSSEC_YES:
dnssec_arg = "yes";
break;
case NM_SETTING_CONNECTION_DNSSEC_DEFAULT:
dnssec_arg = "";
break;
}
nm_assert(dnssec_arg);
if (!nm_str_is_empty(mdns_arg) || !nm_str_is_empty(llmnr_arg) if (!nm_str_is_empty(mdns_arg) || !nm_str_is_empty(llmnr_arg)
|| !nm_str_is_empty(dns_over_tls_arg)) || !nm_str_is_empty(dns_over_tls_arg) || !nm_str_is_empty(dnssec_arg))
has_config = TRUE; has_config = TRUE;
_request_item_append(self, "SetLinkDomains", ic->ifindex, g_variant_builder_end(&domains)); _request_item_append(self, "SetLinkDomains", ic->ifindex, g_variant_builder_end(&domains));
@ -618,6 +638,10 @@ prepare_one_interface(NMDnsSystemdResolved *self, const InterfaceConfig *ic)
DBUS_OP_SET_LINK_DNS_OVER_TLS, DBUS_OP_SET_LINK_DNS_OVER_TLS,
ic->ifindex, ic->ifindex,
g_variant_new("(is)", ic->ifindex, dns_over_tls_arg ?: "")); g_variant_new("(is)", ic->ifindex, dns_over_tls_arg ?: ""));
_request_item_append(self,
DBUS_OP_SET_LINK_DNSSEC,
ic->ifindex,
g_variant_new("(is)", ic->ifindex, dnssec_arg ?: ""));
return has_config; return has_config;
} }

View file

@ -81,7 +81,7 @@ nm_main_utils_write_pidfile(const char *pidfile)
char pid[16]; char pid[16];
nm_sprintf_buf(pid, "%lld", (long long) getpid()); nm_sprintf_buf(pid, "%lld", (long long) getpid());
if (!nm_utils_file_set_contents(pidfile, pid, -1, 00644, NULL, NULL, &error)) { if (!nm_utils_file_set_contents(pidfile, pid, -1, 00644, NULL, NULL, NULL, &error)) {
fprintf(stderr, _("Writing to %s failed: %s\n"), pidfile, error->message); fprintf(stderr, _("Writing to %s failed: %s\n"), pidfile, error->message);
return FALSE; return FALSE;
} }

View file

@ -298,12 +298,6 @@ main(int argc, char *argv[])
_nm_utils_is_manager_process = TRUE; _nm_utils_is_manager_process = TRUE;
/* Known to cause a possible deadlock upon GDBus initialization:
* https://bugzilla.gnome.org/show_bug.cgi?id=674885 */
g_type_ensure(G_TYPE_SOCKET);
g_type_ensure(G_TYPE_DBUS_CONNECTION);
g_type_ensure(NM_TYPE_DBUS_MANAGER);
/* we determine a first-start (contrary to a restart during the same boot) /* we determine a first-start (contrary to a restart during the same boot)
* based on the existence of NM_CONFIG_DEVICE_STATE_DIR directory. */ * based on the existence of NM_CONFIG_DEVICE_STATE_DIR directory. */
config_cli = nm_config_cmd_line_options_new( config_cli = nm_config_cmd_line_options_new(
@ -328,6 +322,12 @@ main(int argc, char *argv[])
exit(result); exit(result);
} }
/* Known to cause a possible deadlock upon GDBus initialization:
* https://bugzilla.gnome.org/show_bug.cgi?id=674885 */
g_type_ensure(G_TYPE_SOCKET);
g_type_ensure(G_TYPE_DBUS_CONNECTION);
g_type_ensure(NM_TYPE_DBUS_MANAGER);
nm_main_utils_ensure_not_running_pidfile(global_opt.pidfile); nm_main_utils_ensure_not_running_pidfile(global_opt.pidfile);
nm_main_utils_ensure_statedir(); nm_main_utils_ensure_statedir();
@ -339,7 +339,7 @@ main(int argc, char *argv[])
char *path, *slash; char *path, *slash;
int g; int g;
/* exe is <basedir>/src/.libs/lt-NetworkManager, so chop off /* exe is <builddir>/src/core/NetworkManager, so chop off
* the last three components */ * the last three components */
path = realpath("/proc/self/exe", NULL); path = realpath("/proc/self/exe", NULL);
g_assert(path != NULL); g_assert(path != NULL);
@ -461,14 +461,8 @@ main(int argc, char *argv[])
/* the first access to State causes the file to be read (and possibly print a warning) */ /* the first access to State causes the file to be read (and possibly print a warning) */
nm_config_state_get(config); nm_config_state_get(config);
nm_log_dbg(LOGD_CORE, nm_log_dbg(LOGD_CORE, "WEXT support is %s", HAVE_WEXT ? "enabled" : "disabled");
"WEXT support is %s", nm_log_dbg(LOGD_CORE, "CLAT support is %s", HAVE_CLAT ? "enabled" : "disabled");
#if HAVE_WEXT
"enabled"
#else
"disabled"
#endif
);
if (!_dbus_manager_init(config)) if (!_dbus_manager_init(config))
goto done_no_manager; goto done_no_manager;

View file

@ -32,6 +32,15 @@ install_data(
core_plugins = [] core_plugins = []
subdir('bpf')
base_sources_addon = []
base_deps_addon = []
if enable_clat
base_sources_addon += [clat_skel_h]
base_deps_addon += [libbpf]
endif
libNetworkManagerBase = static_library( libNetworkManagerBase = static_library(
'NetworkManagerBase', 'NetworkManagerBase',
sources: files( sources: files(
@ -55,13 +64,13 @@ libNetworkManagerBase = static_library(
'nm-l3cfg.c', 'nm-l3cfg.c',
'nm-bond-manager.c', 'nm-bond-manager.c',
'nm-ip-config.c', 'nm-ip-config.c',
), ) + base_sources_addon,
dependencies: [ dependencies: [
core_default_dep, core_default_dep,
libnm_core_public_dep, libnm_core_public_dep,
libsystemd_dep, libsystemd_dep,
libudev_dep, libudev_dep,
], ] + base_deps_addon,
) )
nm_deps = [ nm_deps = [
@ -102,6 +111,7 @@ libNetworkManager = static_library(
'devices/nm-device-ethernet-utils.c', 'devices/nm-device-ethernet-utils.c',
'devices/nm-device-factory.c', 'devices/nm-device-factory.c',
'devices/nm-device-generic.c', 'devices/nm-device-generic.c',
'devices/nm-device-geneve.c',
'devices/nm-device-hsr.c', 'devices/nm-device-hsr.c',
'devices/nm-device-infiniband.c', 'devices/nm-device-infiniband.c',
'devices/nm-device-ip-tunnel.c', 'devices/nm-device-ip-tunnel.c',

View file

@ -19,6 +19,7 @@
#include "libnm-systemd-shared/nm-sd-utils-shared.h" #include "libnm-systemd-shared/nm-sd-utils-shared.h"
#include "nm-l3cfg.h" #include "nm-l3cfg.h"
#include "nm-ndisc-private.h" #include "nm-ndisc-private.h"
#include "nm-core-utils.h"
#define _NMLOG_PREFIX_NAME "ndisc-lndp" #define _NMLOG_PREFIX_NAME "ndisc-lndp"
@ -27,6 +28,14 @@
typedef struct { typedef struct {
struct ndp *ndp; struct ndp *ndp;
GSource *event_source; GSource *event_source;
struct {
NMRateLimit pio_lft;
NMRateLimit mtu;
NMRateLimit omit_prefix;
NMRateLimit omit_dns;
NMRateLimit omit_dnssl;
} msg_ratelimit;
} NMLndpNDiscPrivate; } NMLndpNDiscPrivate;
/*****************************************************************************/ /*****************************************************************************/
@ -49,6 +58,36 @@ G_DEFINE_TYPE(NMLndpNDisc, nm_lndp_ndisc, NM_TYPE_NDISC)
/*****************************************************************************/ /*****************************************************************************/
/*
* If we log a message about an invalid RA packet, don't repeat the same message
* at every packet received or sent. Rate limit the message to 6 every 12 hours
* per type and per ndisc instance.
*/
#define LOG_INV_RA_WINDOW (12 * 3600)
#define LOG_INV_RA_BURST 6
#define _LOG_INVALID_RA(ndisc, rate_limit, ...) \
G_STMT_START \
{ \
NMNDisc *__ndisc = (ndisc); \
NMRateLimit *__rl = (rate_limit); \
const char *__ifname = nm_ndisc_get_ifname(__ndisc); \
\
if (__ifname && nm_logging_enabled(LOGL_WARN, LOGD_IP6) \
&& nm_rate_limit_check(__rl, LOG_INV_RA_WINDOW, LOG_INV_RA_BURST)) { \
nm_log(LOGL_WARN, \
LOGD_IP6, \
__ifname, \
NULL, \
"ndisc (%s): " _NM_UTILS_MACRO_FIRST(__VA_ARGS__), \
__ifname _NM_UTILS_MACRO_REST(__VA_ARGS__)); \
} \
} \
G_STMT_END
/*****************************************************************************/
static gboolean static gboolean
send_rs(NMNDisc *ndisc, GError **error) send_rs(NMNDisc *ndisc, GError **error)
{ {
@ -113,6 +152,7 @@ static int
receive_ra(struct ndp *ndp, struct ndp_msg *msg, gpointer user_data) receive_ra(struct ndp *ndp, struct ndp_msg *msg, gpointer user_data)
{ {
NMNDisc *ndisc = (NMNDisc *) user_data; NMNDisc *ndisc = (NMNDisc *) user_data;
NMLndpNDiscPrivate *priv = NM_LNDP_NDISC_GET_PRIVATE(ndisc);
NMNDiscDataInternal *rdata = ndisc->rdata; NMNDiscDataInternal *rdata = ndisc->rdata;
NMNDiscConfigMap changed = 0; NMNDiscConfigMap changed = 0;
NMNDiscGateway gateway; NMNDiscGateway gateway;
@ -229,7 +269,11 @@ receive_ra(struct ndp *ndp, struct ndp_msg *msg, gpointer user_data)
* log a system management error in this case. * log a system management error in this case.
*/ */
if (preferred_time > valid_time) { if (preferred_time > valid_time) {
_LOGW("skipping PIO - preferred lifetime > valid lifetime"); _LOG_INVALID_RA(
ndisc,
&priv->msg_ratelimit.pio_lft,
"ignoring Prefix Information Option with invalid lifetimes in received IPv6 "
"router advertisement");
continue; continue;
} }
@ -349,10 +393,38 @@ receive_ra(struct ndp *ndp, struct ndp_msg *msg, gpointer user_data)
* Kernel would set it, but would flush out all IPv6 addresses away * Kernel would set it, but would flush out all IPv6 addresses away
* from the link, even the link-local, and we wouldn't be able to * from the link, even the link-local, and we wouldn't be able to
* listen for further RAs that could fix the MTU. */ * listen for further RAs that could fix the MTU. */
_LOGW("MTU too small for IPv6 ignored: %d", mtu); _LOG_INVALID_RA(ndisc,
&priv->msg_ratelimit.mtu,
"ignoring too small MTU %u in received IPv6 "
"router advertisement",
mtu);
} }
} }
#if HAVE_CLAT
/* PREF64 */
ndp_msg_opt_for_each_offset (offset, msg, NDP_MSG_OPT_PREF64) {
NMNDiscPref64 pref64;
pref64 = (NMNDiscPref64) {
.prefix = *ndp_msg_opt_pref64_prefix(msg, offset),
.plen = ndp_msg_opt_pref64_prefix_length(msg, offset),
.gateway = gateway.address,
.gateway_preference = gateway.preference,
.expiry_msec =
_nm_ndisc_lifetime_to_expiry(now_msec, ndp_msg_opt_pref64_lifetime(msg, offset)),
.gateway_expiry_msec = gateway.expiry_msec,
};
/* libndp should only return lengths defined in RFC 8781 */
nm_assert(NM_IN_SET(pref64.plen, 96, 64, 56, 48, 40, 32));
if (nm_ndisc_add_pref64(ndisc, &pref64, now_msec)) {
changed |= NM_NDISC_CONFIG_PREF64;
}
}
#endif
nm_ndisc_ra_received(ndisc, now_msec, changed); nm_ndisc_ra_received(ndisc, now_msec, changed);
return 0; return 0;
} }
@ -445,8 +517,11 @@ send_ra(NMNDisc *ndisc, GError **error)
prefix = _ndp_msg_add_option(msg, sizeof(*prefix)); prefix = _ndp_msg_add_option(msg, sizeof(*prefix));
if (!prefix) { if (!prefix) {
/* Maybe we could sent separate RAs, but why bother... */ /* Maybe we could send separate RAs, but why bother... */
_LOGW("The RA is too big, had to omit some some prefixes."); _LOG_INVALID_RA(
ndisc,
&priv->msg_ratelimit.omit_prefix,
"the outgoing IPv6 router advertisement is too big: omitting some prefixes");
break; break;
} }
@ -475,7 +550,10 @@ send_ra(NMNDisc *ndisc, GError **error)
option = _ndp_msg_add_option(msg, len); option = _ndp_msg_add_option(msg, len);
if (!option) { if (!option) {
_LOGW("The RA is too big, had to omit DNS information."); _LOG_INVALID_RA(
ndisc,
&priv->msg_ratelimit.omit_dns,
"the outgoing IPv6 router advertisement is too big: omitting DNS information");
goto dns_servers_done; goto dns_servers_done;
} }
@ -553,7 +631,10 @@ dns_servers_done:
nm_assert(len / 8u >= 2u); nm_assert(len / 8u >= 2u);
if (len / 8u >= 256u || !(option = _ndp_msg_add_option(msg, len))) { if (len / 8u >= 256u || !(option = _ndp_msg_add_option(msg, len))) {
_LOGW("The RA is too big, had to omit DNS search list."); _LOG_INVALID_RA(
ndisc,
&priv->msg_ratelimit.omit_dnssl,
"the outgoing IPv6 router advertisement is too big: omitting DNS search list");
goto dns_domains_done; goto dns_domains_done;
} }

View file

@ -14,6 +14,7 @@ struct _NMNDiscDataInternal {
NMNDiscData public; NMNDiscData public;
GArray *gateways; GArray *gateways;
GArray *addresses; GArray *addresses;
GArray *pref64;
GArray *routes; GArray *routes;
GArray *dns_servers; GArray *dns_servers;
GArray *dns_domains; GArray *dns_domains;
@ -28,6 +29,7 @@ gboolean nm_ndisc_add_gateway(NMNDisc *ndisc, const NMNDiscGateway *new_item, gi
gboolean gboolean
nm_ndisc_complete_and_add_address(NMNDisc *ndisc, const NMNDiscAddress *new_item, gint64 now_msec); nm_ndisc_complete_and_add_address(NMNDisc *ndisc, const NMNDiscAddress *new_item, gint64 now_msec);
gboolean nm_ndisc_add_route(NMNDisc *ndisc, const NMNDiscRoute *new_item, gint64 now_msec); gboolean nm_ndisc_add_route(NMNDisc *ndisc, const NMNDiscRoute *new_item, gint64 now_msec);
gboolean nm_ndisc_add_pref64(NMNDisc *ndisc, const NMNDiscPref64 *new_item, gint64 now_msec);
gboolean nm_ndisc_add_dns_server(NMNDisc *ndisc, const NMNDiscDNSServer *new_item, gint64 now_msec); gboolean nm_ndisc_add_dns_server(NMNDisc *ndisc, const NMNDiscDNSServer *new_item, gint64 now_msec);
gboolean nm_ndisc_add_dns_domain(NMNDisc *ndisc, const NMNDiscDNSDomain *new_item, gint64 now_msec); gboolean nm_ndisc_add_dns_domain(NMNDisc *ndisc, const NMNDiscDNSDomain *new_item, gint64 now_msec);

View file

@ -34,6 +34,7 @@
#define _SIZE_MAX_ROUTES 1000u #define _SIZE_MAX_ROUTES 1000u
#define _SIZE_MAX_DNS_SERVERS 64u #define _SIZE_MAX_DNS_SERVERS 64u
#define _SIZE_MAX_DNS_DOMAINS 64u #define _SIZE_MAX_DNS_DOMAINS 64u
#define _SIZE_MAX_PREF64 8u
/*****************************************************************************/ /*****************************************************************************/
@ -109,7 +110,8 @@ nm_ndisc_data_to_l3cd(NMDedupMultiIndex *multi_idx,
int ifindex, int ifindex,
const NMNDiscData *rdata, const NMNDiscData *rdata,
NMSettingIP6ConfigPrivacy ip6_privacy, NMSettingIP6ConfigPrivacy ip6_privacy,
NMUtilsIPv6IfaceId *token) NMUtilsIPv6IfaceId *token,
const char *network_id)
{ {
nm_auto_unref_l3cd_init NML3ConfigData *l3cd = NULL; nm_auto_unref_l3cd_init NML3ConfigData *l3cd = NULL;
guint32 ifa_flags; guint32 ifa_flags;
@ -211,13 +213,21 @@ nm_ndisc_data_to_l3cd(NMDedupMultiIndex *multi_idx,
for (i = 0; i < rdata->dns_domains_n; i++) for (i = 0; i < rdata->dns_domains_n; i++)
nm_l3_config_data_add_search(l3cd, AF_INET6, rdata->dns_domains[i].domain); nm_l3_config_data_add_search(l3cd, AF_INET6, rdata->dns_domains[i].domain);
if (rdata->pref64_n > 0) {
nm_l3_config_data_set_pref64(l3cd, rdata->pref64[0].prefix, rdata->pref64[0].plen);
} else {
nm_l3_config_data_set_pref64_valid(l3cd, FALSE);
}
nm_l3_config_data_set_ndisc_hop_limit(l3cd, rdata->hop_limit); nm_l3_config_data_set_ndisc_hop_limit(l3cd, rdata->hop_limit);
nm_l3_config_data_set_ndisc_reachable_time_msec(l3cd, rdata->reachable_time_ms); nm_l3_config_data_set_ndisc_reachable_time_msec(l3cd, rdata->reachable_time_ms);
nm_l3_config_data_set_ndisc_retrans_timer_msec(l3cd, rdata->retrans_timer_ms); nm_l3_config_data_set_ndisc_retrans_timer_msec(l3cd, rdata->retrans_timer_ms);
nm_l3_config_data_set_ip6_mtu(l3cd, rdata->mtu); nm_l3_config_data_set_ip6_mtu_ra(l3cd, rdata->mtu);
if (token) if (token)
nm_l3_config_data_set_ip6_token(l3cd, *token); nm_l3_config_data_set_ip6_token(l3cd, *token);
if (network_id)
nm_l3_config_data_set_network_id(l3cd, network_id);
return g_steal_pointer(&l3cd); return g_steal_pointer(&l3cd);
} }
@ -416,6 +426,7 @@ _data_complete(NMNDiscDataInternal *data)
_SET(data, gateways); _SET(data, gateways);
_SET(data, addresses); _SET(data, addresses);
_SET(data, routes); _SET(data, routes);
_SET(data, pref64);
_SET(data, dns_servers); _SET(data, dns_servers);
_SET(data, dns_domains); _SET(data, dns_domains);
#undef _SET #undef _SET
@ -437,7 +448,8 @@ nm_ndisc_emit_config_change(NMNDisc *self, NMNDiscConfigMap changed)
nm_l3cfg_get_ifindex(priv->config.l3cfg), nm_l3cfg_get_ifindex(priv->config.l3cfg),
rdata, rdata,
priv->config.ip6_privacy, priv->config.ip6_privacy,
priv->iid_is_token ? &priv->iid : NULL); priv->iid_is_token ? &priv->iid : NULL,
priv->config.network_id);
l3cd = nm_l3_config_data_seal(l3cd); l3cd = nm_l3_config_data_seal(l3cd);
if (!nm_l3_config_data_equal(priv->l3cd, l3cd)) if (!nm_l3_config_data_equal(priv->l3cd, l3cd))
@ -760,6 +772,59 @@ nm_ndisc_add_route(NMNDisc *ndisc, const NMNDiscRoute *new_item, gint64 now_msec
return TRUE; return TRUE;
} }
gboolean
nm_ndisc_add_pref64(NMNDisc *ndisc, const NMNDiscPref64 *new_item, gint64 now_msec)
{
NMNDiscDataInternal *rdata = &NM_NDISC_GET_PRIVATE(ndisc)->rdata;
guint i;
guint insert_idx = G_MAXUINT;
for (i = 0; i < rdata->pref64->len;) {
NMNDiscPref64 *item = &nm_g_array_index(rdata->pref64, NMNDiscPref64, i);
if (item->plen == new_item->plen && IN6_ARE_ADDR_EQUAL(&item->prefix, &new_item->prefix)
&& IN6_ARE_ADDR_EQUAL(&item->gateway, &new_item->gateway)) {
if (new_item->expiry_msec <= now_msec) {
g_array_remove_index(rdata->pref64, i);
return TRUE;
}
if (item->gateway_preference != new_item->gateway_preference) {
g_array_remove_index(rdata->pref64, i);
continue;
}
item->gateway_expiry_msec = new_item->gateway_expiry_msec;
if (item->expiry_msec == new_item->expiry_msec)
return FALSE;
item->expiry_msec = new_item->expiry_msec;
return TRUE;
}
/* Put before less preferable gateways. */
if (_preference_to_priority(item->gateway_preference)
< _preference_to_priority(new_item->gateway_preference)
&& insert_idx == G_MAXUINT)
insert_idx = i;
i++;
}
if (rdata->pref64->len >= _SIZE_MAX_PREF64)
return FALSE;
if (new_item->expiry_msec <= now_msec)
return FALSE;
g_array_insert_val(rdata->pref64,
insert_idx == G_MAXUINT ? rdata->pref64->len : insert_idx,
*new_item);
return TRUE;
}
gboolean gboolean
nm_ndisc_add_dns_server(NMNDisc *ndisc, const NMNDiscDNSServer *new_item, gint64 now_msec) nm_ndisc_add_dns_server(NMNDisc *ndisc, const NMNDiscDNSServer *new_item, gint64 now_msec)
{ {
@ -1400,6 +1465,17 @@ _config_changed_log(NMNDisc *ndisc, NMNDiscConfigMap changed)
nm_icmpv6_router_pref_to_string(route->preference, str_pref, sizeof(str_pref)), nm_icmpv6_router_pref_to_string(route->preference, str_pref, sizeof(str_pref)),
get_exp(str_exp, now_msec, route)); get_exp(str_exp, now_msec, route));
} }
for (i = 0; i < rdata->pref64->len; i++) {
const NMNDiscPref64 *pref64 = &nm_g_array_index(rdata->pref64, NMNDiscPref64, i);
char addrstr2[NM_INET_ADDRSTRLEN];
_LOGD(" pref64 %s/%u via %s exp %s",
nm_inet6_ntop(&pref64->prefix, addrstr),
pref64->plen,
nm_inet6_ntop(&pref64->gateway, addrstr2),
get_exp(str_exp, now_msec, pref64));
}
for (i = 0; i < rdata->dns_servers->len; i++) { for (i = 0; i < rdata->dns_servers->len; i++) {
const NMNDiscDNSServer *dns_server = const NMNDiscDNSServer *dns_server =
&nm_g_array_index(rdata->dns_servers, NMNDiscDNSServer, i); &nm_g_array_index(rdata->dns_servers, NMNDiscDNSServer, i);
@ -1524,6 +1600,45 @@ clean_routes(NMNDisc *ndisc, gint64 now_msec, NMNDiscConfigMap *changed, gint64
*changed |= NM_NDISC_CONFIG_ROUTES; *changed |= NM_NDISC_CONFIG_ROUTES;
} }
static void
clean_pref64(NMNDisc *ndisc, gint64 now_msec, NMNDiscConfigMap *changed, gint64 *next_msec)
{
NMNDiscDataInternal *rdata = &NM_NDISC_GET_PRIVATE(ndisc)->rdata;
NMNDiscPref64 *arr;
guint i;
guint j;
if (rdata->pref64->len == 0)
return;
arr = &nm_g_array_first(rdata->pref64, NMNDiscPref64);
for (i = 0, j = 0; i < rdata->pref64->len; i++) {
if (!expiry_next(now_msec, arr[i].expiry_msec, next_msec)
|| !expiry_next(now_msec,
arr[i].gateway_expiry_msec,
next_msec)) { /* no gateway no party */
if (i == 0) {
/* Emit the changed signal only when the first PREF64 expires,
* because only the first item is exported into the l3cd. Changes
* in other PREF64s are not relevant. */
*changed |= NM_NDISC_CONFIG_PREF64;
}
continue;
}
if (i != j)
arr[j] = arr[i];
j++;
}
if (i != j) {
g_array_set_size(rdata->pref64, j);
}
_array_set_size_max(rdata->pref64, _SIZE_MAX_PREF64);
}
static void static void
clean_dns_servers(NMNDisc *ndisc, gint64 now_msec, NMNDiscConfigMap *changed, gint64 *next_msec) clean_dns_servers(NMNDisc *ndisc, gint64 now_msec, NMNDiscConfigMap *changed, gint64 *next_msec)
{ {
@ -1600,6 +1715,7 @@ check_timestamps(NMNDisc *ndisc, gint64 now_msec, NMNDiscConfigMap changed)
clean_gateways(ndisc, now_msec, &changed, &next_msec); clean_gateways(ndisc, now_msec, &changed, &next_msec);
clean_addresses(ndisc, now_msec, &changed, &next_msec); clean_addresses(ndisc, now_msec, &changed, &next_msec);
clean_routes(ndisc, now_msec, &changed, &next_msec); clean_routes(ndisc, now_msec, &changed, &next_msec);
clean_pref64(ndisc, now_msec, &changed, &next_msec);
clean_dns_servers(ndisc, now_msec, &changed, &next_msec); clean_dns_servers(ndisc, now_msec, &changed, &next_msec);
clean_dns_domains(ndisc, now_msec, &changed, &next_msec); clean_dns_domains(ndisc, now_msec, &changed, &next_msec);
@ -1919,6 +2035,7 @@ nm_ndisc_init(NMNDisc *ndisc)
rdata->gateways = g_array_new(FALSE, FALSE, sizeof(NMNDiscGateway)); rdata->gateways = g_array_new(FALSE, FALSE, sizeof(NMNDiscGateway));
rdata->addresses = g_array_new(FALSE, FALSE, sizeof(NMNDiscAddress)); rdata->addresses = g_array_new(FALSE, FALSE, sizeof(NMNDiscAddress));
rdata->routes = g_array_new(FALSE, FALSE, sizeof(NMNDiscRoute)); rdata->routes = g_array_new(FALSE, FALSE, sizeof(NMNDiscRoute));
rdata->pref64 = g_array_new(FALSE, FALSE, sizeof(NMNDiscPref64));
rdata->dns_servers = g_array_new(FALSE, FALSE, sizeof(NMNDiscDNSServer)); rdata->dns_servers = g_array_new(FALSE, FALSE, sizeof(NMNDiscDNSServer));
rdata->dns_domains = g_array_new(FALSE, FALSE, sizeof(NMNDiscDNSDomain)); rdata->dns_domains = g_array_new(FALSE, FALSE, sizeof(NMNDiscDNSDomain));
g_array_set_clear_func(rdata->dns_domains, dns_domain_free); g_array_set_clear_func(rdata->dns_domains, dns_domain_free);
@ -1951,6 +2068,7 @@ finalize(GObject *object)
g_array_unref(rdata->gateways); g_array_unref(rdata->gateways);
g_array_unref(rdata->addresses); g_array_unref(rdata->addresses);
g_array_unref(rdata->routes); g_array_unref(rdata->routes);
g_array_unref(rdata->pref64);
g_array_unref(rdata->dns_servers); g_array_unref(rdata->dns_servers);
g_array_unref(rdata->dns_domains); g_array_unref(rdata->dns_domains);

View file

@ -119,6 +119,15 @@ typedef struct _NMNDiscRoute {
bool duplicate : 1; bool duplicate : 1;
} NMNDiscRoute; } NMNDiscRoute;
typedef struct _NMNDiscPref64 {
struct in6_addr prefix;
struct in6_addr gateway;
gint64 expiry_msec;
gint64 gateway_expiry_msec;
NMIcmpv6RouterPref gateway_preference;
guint8 plen;
} NMNDiscPref64;
typedef struct { typedef struct {
struct in6_addr address; struct in6_addr address;
gint64 expiry_msec; gint64 expiry_msec;
@ -141,6 +150,7 @@ typedef enum {
NM_NDISC_CONFIG_MTU = 1 << 7, NM_NDISC_CONFIG_MTU = 1 << 7,
NM_NDISC_CONFIG_REACHABLE_TIME = 1 << 8, NM_NDISC_CONFIG_REACHABLE_TIME = 1 << 8,
NM_NDISC_CONFIG_RETRANS_TIMER = 1 << 9, NM_NDISC_CONFIG_RETRANS_TIMER = 1 << 9,
NM_NDISC_CONFIG_PREF64 = 1 << 10,
} NMNDiscConfigMap; } NMNDiscConfigMap;
typedef enum { typedef enum {
@ -188,12 +198,14 @@ typedef struct {
guint gateways_n; guint gateways_n;
guint addresses_n; guint addresses_n;
guint routes_n; guint routes_n;
guint pref64_n;
guint dns_servers_n; guint dns_servers_n;
guint dns_domains_n; guint dns_domains_n;
const NMNDiscGateway *gateways; const NMNDiscGateway *gateways;
const NMNDiscAddress *addresses; const NMNDiscAddress *addresses;
const NMNDiscRoute *routes; const NMNDiscRoute *routes;
const NMNDiscPref64 *pref64;
const NMNDiscDNSServer *dns_servers; const NMNDiscDNSServer *dns_servers;
const NMNDiscDNSDomain *dns_domains; const NMNDiscDNSDomain *dns_domains;
} NMNDiscData; } NMNDiscData;
@ -282,6 +294,7 @@ struct _NML3ConfigData *nm_ndisc_data_to_l3cd(NMDedupMultiIndex *multi_id
int ifindex, int ifindex,
const NMNDiscData *rdata, const NMNDiscData *rdata,
NMSettingIP6ConfigPrivacy ip6_privacy, NMSettingIP6ConfigPrivacy ip6_privacy,
NMUtilsIPv6IfaceId *token); NMUtilsIPv6IfaceId *token,
const char *network_id);
#endif /* __NETWORKMANAGER_NDISC_H__ */ #endif /* __NETWORKMANAGER_NDISC_H__ */

View file

@ -39,7 +39,9 @@ typedef struct {
bool activation_lifetime_bound_to_profile_visibility : 1; bool activation_lifetime_bound_to_profile_visibility : 1;
bool settings_connection_is_unsaved : 1; bool settings_connection_is_unsaved : 1;
bool settings_connection_is_shadowed_owned : 1; bool settings_connection_is_shadowed_owned : 1;
bool permanent_managed_by_mac : 1;
NMUnmanFlagOp unmanaged_explicit; NMUnmanFlagOp unmanaged_explicit;
NMTernary permanent_managed;
NMActivationReason activation_reason; NMActivationReason activation_reason;
gulong dev_exported_change_id; gulong dev_exported_change_id;
} DeviceCheckpoint; } DeviceCheckpoint;
@ -160,7 +162,7 @@ parse_connection_from_shadowed_file(const char *path, GError **error)
{ {
nm_auto_unref_keyfile GKeyFile *keyfile = NULL; nm_auto_unref_keyfile GKeyFile *keyfile = NULL;
gs_free char *base_dir = NULL; gs_free char *base_dir = NULL;
char *sep; const char *sep;
keyfile = g_key_file_new(); keyfile = g_key_file_new();
if (!g_key_file_load_from_file(keyfile, path, G_KEY_FILE_NONE, error)) if (!g_key_file_load_from_file(keyfile, path, G_KEY_FILE_NONE, error))
@ -497,13 +499,18 @@ nm_checkpoint_rollback(NMCheckpoint *self)
g_hash_table_iter_init(&iter, priv->devices); g_hash_table_iter_init(&iter, priv->devices);
while (g_hash_table_iter_next(&iter, (gpointer *) &device, (gpointer *) &dev_checkpoint)) { while (g_hash_table_iter_next(&iter, (gpointer *) &device, (gpointer *) &dev_checkpoint)) {
guint32 result = NM_ROLLBACK_RESULT_OK; guint32 result = NM_ROLLBACK_RESULT_OK;
NMTernary perm_managed = NM_TERNARY_DEFAULT;
gboolean perm_managed_by_mac = FALSE;
gboolean force_perm_managed;
_LOGD("rollback: restoring device %s (state %d, realized %d, explicitly unmanaged %d, " _LOGD("rollback: restoring device %s (state %d, realized %d, explicitly unmanaged %d, "
"connection-unsaved %d, connection-shadowed %d, connection-shadowed-owned %d)", "permanently managed %d, connection-unsaved %d, connection-shadowed %d, "
"connection-shadowed-owned %d)",
dev_checkpoint->original_dev_name, dev_checkpoint->original_dev_name,
(int) dev_checkpoint->state, (int) dev_checkpoint->state,
dev_checkpoint->realized, dev_checkpoint->realized,
dev_checkpoint->unmanaged_explicit, dev_checkpoint->unmanaged_explicit,
dev_checkpoint->permanent_managed,
dev_checkpoint->settings_connection_is_unsaved, dev_checkpoint->settings_connection_is_unsaved,
!!dev_checkpoint->settings_connection_shadowed, !!dev_checkpoint->settings_connection_shadowed,
dev_checkpoint->settings_connection_is_shadowed_owned); dev_checkpoint->settings_connection_is_shadowed_owned);
@ -541,6 +548,43 @@ nm_checkpoint_rollback(NMCheckpoint *self)
NM_DEVICE_STATE_REASON_NOW_MANAGED); NM_DEVICE_STATE_REASON_NOW_MANAGED);
} }
force_perm_managed = !nm_config_get_device_managed(nm_config_get(),
device,
&perm_managed,
&perm_managed_by_mac,
NULL);
if (force_perm_managed || (perm_managed != dev_checkpoint->permanent_managed)
|| (dev_checkpoint->permanent_managed != NM_TERNARY_DEFAULT
&& perm_managed_by_mac != dev_checkpoint->permanent_managed_by_mac)) {
gs_free_error GError *error = NULL;
NMUnmanFlagOp set_op;
_LOGD("rollback: restore permanent managed state");
if (!nm_config_set_device_managed(nm_config_get(),
device,
dev_checkpoint->permanent_managed,
dev_checkpoint->permanent_managed_by_mac,
&error)) {
_LOGE("rollback: failed to restore permanent managed state: %s", error->message);
result = NM_ROLLBACK_RESULT_ERR_FAILED;
/* even if this failed, we try to continue the rollback */
}
if (dev_checkpoint->permanent_managed == NM_TERNARY_TRUE)
set_op = NM_UNMAN_FLAG_OP_SET_MANAGED;
else if (dev_checkpoint->permanent_managed == NM_TERNARY_FALSE)
set_op = NM_UNMAN_FLAG_OP_SET_UNMANAGED;
else
set_op = NM_UNMAN_FLAG_OP_FORGET;
nm_device_set_unmanaged_by_flags_queue(device,
NM_UNMANAGED_USER_CONF,
set_op,
NM_DEVICE_STATE_REASON_NOW_MANAGED);
}
if (dev_checkpoint->state == NM_DEVICE_STATE_UNMANAGED) { if (dev_checkpoint->state == NM_DEVICE_STATE_UNMANAGED) {
if (nm_device_get_state(device) != NM_DEVICE_STATE_UNMANAGED if (nm_device_get_state(device) != NM_DEVICE_STATE_UNMANAGED
|| dev_checkpoint->unmanaged_explicit == NM_UNMAN_FLAG_OP_SET_UNMANAGED) { || dev_checkpoint->unmanaged_explicit == NM_UNMAN_FLAG_OP_SET_UNMANAGED) {
@ -703,6 +747,8 @@ device_checkpoint_create(NMCheckpoint *self, NMDevice *device)
NMSettingsConnection *settings_connection; NMSettingsConnection *settings_connection;
const char *path; const char *path;
NMActRequest *act_request; NMActRequest *act_request;
gboolean perm_managed_by_mac;
gs_free_error GError *error = NULL;
nm_assert(NM_IS_DEVICE(device)); nm_assert(NM_IS_DEVICE(device));
nm_assert(nm_device_is_real(device)); nm_assert(nm_device_is_real(device));
@ -728,12 +774,26 @@ device_checkpoint_create(NMCheckpoint *self, NMDevice *device)
} else } else
dev_checkpoint->unmanaged_explicit = NM_UNMAN_FLAG_OP_FORGET; dev_checkpoint->unmanaged_explicit = NM_UNMAN_FLAG_OP_FORGET;
if (nm_config_get_device_managed(nm_config_get(),
device,
&dev_checkpoint->permanent_managed,
&perm_managed_by_mac,
NULL)) {
dev_checkpoint->permanent_managed_by_mac = perm_managed_by_mac;
} else {
dev_checkpoint->permanent_managed = NM_TERNARY_DEFAULT;
dev_checkpoint->permanent_managed_by_mac = FALSE;
_LOGW("error getting permanent managed state for %s: %s",
nm_device_get_iface(device),
error->message);
g_clear_error(&error);
}
act_request = nm_device_get_act_request(device); act_request = nm_device_get_act_request(device);
if (act_request) { if (act_request) {
NMSettingsStorage *storage; NMSettingsStorage *storage;
gboolean shadowed_owned = FALSE; gboolean shadowed_owned = FALSE;
const char *shadowed_file; const char *shadowed_file;
gs_free_error GError *error = NULL;
settings_connection = nm_act_request_get_settings_connection(act_request); settings_connection = nm_act_request_get_settings_connection(act_request);
applied_connection = nm_act_request_get_applied_connection(act_request); applied_connection = nm_act_request_get_applied_connection(act_request);
@ -764,6 +824,7 @@ device_checkpoint_create(NMCheckpoint *self, NMDevice *device)
_LOGW("error reading shadowed connection file for %s: %s", _LOGW("error reading shadowed connection file for %s: %s",
nm_device_get_iface(device), nm_device_get_iface(device),
error->message); error->message);
g_clear_error(&error);
} }
} }
} }

Some files were not shown because too many files have changed in this diff Show more