mirror of
https://git.proxmox.com/git/systemd
synced 2025-10-18 03:00:19 +00:00
New upstream version 249.4
This commit is contained in:
parent
9d66932971
commit
2c6f20efa6
@ -1706,7 +1706,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2eservice {
|
||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||
readonly b DefaultDependencies = ...;
|
||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||
readonly s OnSuccesJobMode = '...';
|
||||
readonly s OnSuccessJobMode = '...';
|
||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||
readonly s OnFailureJobMode = '...';
|
||||
@org.freedesktop.DBus.Property.EmitsChangedSignal("const")
|
||||
@ -1815,7 +1815,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2eservice {
|
||||
|
||||
<!--property CanFreeze is not documented!-->
|
||||
|
||||
<!--property OnSuccesJobMode is not documented!-->
|
||||
<!--property OnSuccessJobMode is not documented!-->
|
||||
|
||||
<!--property OnFailureJobMode is not documented!-->
|
||||
|
||||
@ -2019,7 +2019,7 @@ node /org/freedesktop/systemd1/unit/avahi_2ddaemon_2eservice {
|
||||
|
||||
<variablelist class="dbus-property" generated="True" extra-ref="DefaultDependencies"/>
|
||||
|
||||
<variablelist class="dbus-property" generated="True" extra-ref="OnSuccesJobMode"/>
|
||||
<variablelist class="dbus-property" generated="True" extra-ref="OnSuccessJobMode"/>
|
||||
|
||||
<variablelist class="dbus-property" generated="True" extra-ref="OnFailureJobMode"/>
|
||||
|
||||
|
@ -662,49 +662,49 @@
|
||||
<varlistentry>
|
||||
<term><varname>ReceiveChecksumOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the hardware offload for checksumming of ingress
|
||||
<para>Takes a boolean. If set to true, hardware offload for checksumming of ingress
|
||||
network packets is enabled. When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>TransmitChecksumOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the hardware offload for checksumming of egress
|
||||
<para>Takes a boolean. If set to true, hardware offload for checksumming of egress
|
||||
network packets is enabled. When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>TCPSegmentationOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the TCP Segmentation Offload (TSO) is enabled.
|
||||
<para>Takes a boolean. If set to true, TCP Segmentation Offload (TSO) is enabled.
|
||||
When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>TCP6SegmentationOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the TCP6 Segmentation Offload (tx-tcp6-segmentation) is enabled.
|
||||
<para>Takes a boolean. If set to true, TCP6 Segmentation Offload (tx-tcp6-segmentation) is enabled.
|
||||
When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>GenericSegmentationOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the Generic Segmentation Offload (GSO) is enabled.
|
||||
<para>Takes a boolean. If set to true, Generic Segmentation Offload (GSO) is enabled.
|
||||
When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>GenericReceiveOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the Generic Receive Offload (GRO) is enabled.
|
||||
<para>Takes a boolean. If set to true, Generic Receive Offload (GRO) is enabled.
|
||||
When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>LargeReceiveOffload=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. If set to true, the Large Receive Offload (LRO) is enabled.
|
||||
<para>Takes a boolean. If set to true, Large Receive Offload (LRO) is enabled.
|
||||
When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
@ -763,7 +763,7 @@
|
||||
<varlistentry>
|
||||
<term><varname>RxFlowControl=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. When set, enables the receive flow control, also known as the ethernet
|
||||
<para>Takes a boolean. When set, enables receive flow control, also known as the ethernet
|
||||
receive PAUSE message (generate and send ethernet PAUSE frames). When unset, the kernel's
|
||||
default will be used.</para>
|
||||
</listitem>
|
||||
@ -771,7 +771,7 @@
|
||||
<varlistentry>
|
||||
<term><varname>TxFlowControl=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. When set, enables the transmit flow control, also known as the ethernet
|
||||
<para>Takes a boolean. When set, enables transmit flow control, also known as the ethernet
|
||||
transmit PAUSE message (respond to received ethernet PAUSE frames). When unset, the kernel's
|
||||
default will be used.</para>
|
||||
</listitem>
|
||||
@ -779,7 +779,7 @@
|
||||
<varlistentry>
|
||||
<term><varname>AutoNegotiationFlowControl=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a boolean. When set, the auto negotiation enables the interface to exchange state
|
||||
<para>Takes a boolean. When set, auto negotiation enables the interface to exchange state
|
||||
advertisements with the connected peer so that the two devices can agree on the ethernet
|
||||
PAUSE configuration. When unset, the kernel's default will be used.</para>
|
||||
</listitem>
|
||||
|
@ -1238,7 +1238,9 @@ IPv6Token=prefixstable:2002:da8:1::</programlisting></para>
|
||||
<term><varname>Priority=</varname></term>
|
||||
<listitem>
|
||||
<para>Specifies the priority of this rule. <varname>Priority=</varname> is an unsigned
|
||||
integer. Higher number means lower priority, and rules get processed in order of increasing number.</para>
|
||||
integer in the range 0…4294967295. Higher number means lower priority, and rules get
|
||||
processed in order of increasing number. Defaults to unset, and the kernel will pick
|
||||
a value dynamically.</para>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
|
@ -23,7 +23,7 @@ _udevadm_trigger(){
|
||||
'--dry-run[Do not actually trigger the event.]' \
|
||||
'--quiet[Suppress error logging in triggering events.]' \
|
||||
'--type=[Trigger a specific type of devices.]:types:(devices subsystems failed)' \
|
||||
'--action=[Type of event to be triggered.]:actions:(add change remove)' \
|
||||
'--action=[Type of event to be triggered.]:actions:(add change remove move online offline bind unbind)' \
|
||||
'--subsystem-match=[Trigger events for devices which belong to a matching subsystem.]' \
|
||||
'--subsystem-nomatch=[Do not trigger events for devices which belong to a matching subsystem.]' \
|
||||
'--attr-match=attribute=[Trigger events for devices with a matching sysfs attribute.]' \
|
||||
@ -74,7 +74,7 @@ _udevadm_monitor(){
|
||||
(( $+functions[_udevadm_test] )) ||
|
||||
_udevadm_test(){
|
||||
_arguments \
|
||||
'--action=[The action string.]:actions:(add change remove)' \
|
||||
'--action=[The action string.]:actions:(add change remove move online offline bind unbind)' \
|
||||
'--subsystem=[The subsystem string.]' \
|
||||
'--help[Print help text.]' \
|
||||
'*::devpath:_files -P /sys/ -W /sys'
|
||||
|
@ -1910,7 +1910,7 @@ static int property_read_ip_filters(
|
||||
if (streq(member, "IPIngressFilterPath"))
|
||||
info->ip_filters_custom_ingress = !strv_isempty(l);
|
||||
else if (streq(member, "IPEgressFilterPath"))
|
||||
info->ip_filters_custom_ingress = !strv_isempty(l);
|
||||
info->ip_filters_custom_egress = !strv_isempty(l);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -1724,7 +1724,7 @@ static ConfigEntry *config_entry_add_loader(
|
||||
*entry = (ConfigEntry) {
|
||||
.type = type,
|
||||
.title = StrDuplicate(title),
|
||||
.version = StrDuplicate(version),
|
||||
.version = version ? StrDuplicate(version) : NULL,
|
||||
.device = device,
|
||||
.loader = StrDuplicate(loader),
|
||||
.id = StrDuplicate(id),
|
||||
|
@ -25,7 +25,7 @@ static VOID linux_efi_handover(EFI_HANDLE image, struct boot_params *params) {
|
||||
handover(image, ST, params);
|
||||
}
|
||||
|
||||
EFI_STATUS linux_exec(EFI_HANDLE *image,
|
||||
EFI_STATUS linux_exec(EFI_HANDLE image,
|
||||
CHAR8 *cmdline, UINTN cmdline_len,
|
||||
UINTN linux_addr,
|
||||
UINTN initrd_addr, UINTN initrd_size) {
|
||||
|
@ -83,7 +83,7 @@ struct boot_params {
|
||||
UINT8 _pad9[276];
|
||||
} __attribute__((packed));
|
||||
|
||||
EFI_STATUS linux_exec(EFI_HANDLE *image,
|
||||
EFI_STATUS linux_exec(EFI_HANDLE image,
|
||||
CHAR8 *cmdline, UINTN cmdline_size,
|
||||
UINTN linux_addr,
|
||||
UINTN initrd_addr, UINTN initrd_size);
|
||||
|
@ -245,7 +245,7 @@ EFI_STATUS process_random_seed(EFI_FILE *root_dir, RandomSeedMode mode) {
|
||||
|
||||
err = uefi_call_wrapper(root_dir->Open, 5, root_dir, &handle, (CHAR16*) L"\\loader\\random-seed", EFI_FILE_MODE_READ|EFI_FILE_MODE_WRITE, 0ULL);
|
||||
if (EFI_ERROR(err)) {
|
||||
if (err != EFI_NOT_FOUND)
|
||||
if (err != EFI_NOT_FOUND && err != EFI_WRITE_PROTECTED)
|
||||
Print(L"Failed to open random seed file: %r\n", err);
|
||||
return err;
|
||||
}
|
||||
|
@ -3039,6 +3039,9 @@ static int unit_check_cgroup_events(Unit *u) {
|
||||
|
||||
assert(u);
|
||||
|
||||
if (!u->cgroup_path)
|
||||
return 0;
|
||||
|
||||
r = cg_get_keyed_attribute_graceful(SYSTEMD_CGROUP_CONTROLLER, u->cgroup_path, "cgroup.events",
|
||||
STRV_MAKE("populated", "frozen"), values);
|
||||
if (r < 0)
|
||||
@ -3871,6 +3874,21 @@ void unit_invalidate_cgroup_bpf(Unit *u) {
|
||||
}
|
||||
}
|
||||
|
||||
void unit_cgroup_catchup(Unit *u) {
|
||||
assert(u);
|
||||
|
||||
if (!UNIT_HAS_CGROUP_CONTEXT(u))
|
||||
return;
|
||||
|
||||
/* We dropped the inotify watch during reexec/reload, so we need to
|
||||
* check these as they may have changed.
|
||||
* Note that (currently) the kernel doesn't actually update cgroup
|
||||
* file modification times, so we can't just serialize and then check
|
||||
* the mtime for file(s) we are interested in. */
|
||||
(void) unit_check_cgroup_events(u);
|
||||
unit_add_to_cgroup_oom_queue(u);
|
||||
}
|
||||
|
||||
bool unit_cgroup_delegate(Unit *u) {
|
||||
CGroupContext *c;
|
||||
|
||||
|
@ -313,6 +313,8 @@ void manager_invalidate_startup_units(Manager *m);
|
||||
const char* cgroup_device_policy_to_string(CGroupDevicePolicy i) _const_;
|
||||
CGroupDevicePolicy cgroup_device_policy_from_string(const char *s) _pure_;
|
||||
|
||||
void unit_cgroup_catchup(Unit *u);
|
||||
|
||||
bool unit_cgroup_delegate(Unit *u);
|
||||
|
||||
int compare_job_priority(const void *a, const void *b);
|
||||
|
@ -905,7 +905,8 @@ const sd_bus_vtable bus_unit_vtable[] = {
|
||||
SD_BUS_PROPERTY("RefuseManualStop", "b", bus_property_get_bool, offsetof(Unit, refuse_manual_stop), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("AllowIsolate", "b", bus_property_get_bool, offsetof(Unit, allow_isolate), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("DefaultDependencies", "b", bus_property_get_bool, offsetof(Unit, default_dependencies), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("OnSuccesJobMode", "s", property_get_job_mode, offsetof(Unit, on_success_job_mode), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("OnSuccesJobMode", "s", property_get_job_mode, offsetof(Unit, on_success_job_mode), SD_BUS_VTABLE_PROPERTY_CONST|SD_BUS_VTABLE_HIDDEN), /* deprecated */
|
||||
SD_BUS_PROPERTY("OnSuccessJobMode", "s", property_get_job_mode, offsetof(Unit, on_success_job_mode), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("OnFailureJobMode", "s", property_get_job_mode, offsetof(Unit, on_failure_job_mode), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("IgnoreOnIsolate", "b", bus_property_get_bool, offsetof(Unit, ignore_on_isolate), SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
SD_BUS_PROPERTY("NeedDaemonReload", "b", property_get_need_daemon_reload, 0, SD_BUS_VTABLE_PROPERTY_CONST),
|
||||
|
@ -1410,6 +1410,10 @@ static void manager_clear_jobs_and_units(Manager *m) {
|
||||
assert(!m->cleanup_queue);
|
||||
assert(!m->gc_unit_queue);
|
||||
assert(!m->gc_job_queue);
|
||||
assert(!m->cgroup_realize_queue);
|
||||
assert(!m->cgroup_empty_queue);
|
||||
assert(!m->cgroup_oom_queue);
|
||||
assert(!m->target_deps_queue);
|
||||
assert(!m->stop_when_unneeded_queue);
|
||||
assert(!m->start_when_upheld_queue);
|
||||
assert(!m->stop_when_bound_queue);
|
||||
|
@ -733,6 +733,9 @@ Unit* unit_free(Unit *u) {
|
||||
if (u->in_dbus_queue)
|
||||
LIST_REMOVE(dbus_queue, u->manager->dbus_unit_queue, u);
|
||||
|
||||
if (u->in_cleanup_queue)
|
||||
LIST_REMOVE(cleanup_queue, u->manager->cleanup_queue, u);
|
||||
|
||||
if (u->in_gc_queue)
|
||||
LIST_REMOVE(gc_queue, u->manager->gc_unit_queue, u);
|
||||
|
||||
@ -742,8 +745,8 @@ Unit* unit_free(Unit *u) {
|
||||
if (u->in_cgroup_empty_queue)
|
||||
LIST_REMOVE(cgroup_empty_queue, u->manager->cgroup_empty_queue, u);
|
||||
|
||||
if (u->in_cleanup_queue)
|
||||
LIST_REMOVE(cleanup_queue, u->manager->cleanup_queue, u);
|
||||
if (u->in_cgroup_oom_queue)
|
||||
LIST_REMOVE(cgroup_oom_queue, u->manager->cgroup_oom_queue, u);
|
||||
|
||||
if (u->in_target_deps_queue)
|
||||
LIST_REMOVE(target_deps_queue, u->manager->target_deps_queue, u);
|
||||
@ -3578,7 +3581,6 @@ int unit_add_blockdev_dependency(Unit *u, const char *what, UnitDependencyMask m
|
||||
int unit_coldplug(Unit *u) {
|
||||
int r = 0, q;
|
||||
char **i;
|
||||
Job *uj;
|
||||
|
||||
assert(u);
|
||||
|
||||
@ -3601,9 +3603,13 @@ int unit_coldplug(Unit *u) {
|
||||
r = q;
|
||||
}
|
||||
|
||||
uj = u->job ?: u->nop_job;
|
||||
if (uj) {
|
||||
q = job_coldplug(uj);
|
||||
if (u->job) {
|
||||
q = job_coldplug(u->job);
|
||||
if (q < 0 && r >= 0)
|
||||
r = q;
|
||||
}
|
||||
if (u->nop_job) {
|
||||
q = job_coldplug(u->nop_job);
|
||||
if (q < 0 && r >= 0)
|
||||
r = q;
|
||||
}
|
||||
@ -3616,6 +3622,8 @@ void unit_catchup(Unit *u) {
|
||||
|
||||
if (UNIT_VTABLE(u)->catchup)
|
||||
UNIT_VTABLE(u)->catchup(u);
|
||||
|
||||
unit_cgroup_catchup(u);
|
||||
}
|
||||
|
||||
static bool fragment_mtime_newer(const char *path, usec_t mtime, bool path_masked) {
|
||||
|
@ -435,7 +435,8 @@ static int add_mount(
|
||||
|
||||
/* Order the mount unit we generate relative to the post unit, so that DefaultDependencies= on the
|
||||
* target unit won't affect us. */
|
||||
if (post && !FLAGS_SET(flags, MOUNT_AUTOMOUNT) && !FLAGS_SET(flags, MOUNT_NOAUTO))
|
||||
if (post && !FLAGS_SET(flags, MOUNT_AUTOMOUNT) && !FLAGS_SET(flags, MOUNT_NOAUTO) &&
|
||||
!FLAGS_SET(flags, MOUNT_NOFAIL))
|
||||
fprintf(f, "Before=%s\n", post);
|
||||
|
||||
if (passno != 0) {
|
||||
|
@ -256,6 +256,9 @@ int curl_glue_make(CURL **ret, const char *url, void *userdata) {
|
||||
if (curl_easy_setopt(c, CURLOPT_LOW_SPEED_LIMIT, 30L) != CURLE_OK)
|
||||
return -EIO;
|
||||
|
||||
if (curl_easy_setopt(c, CURLOPT_PROTOCOLS, CURLPROTO_HTTP|CURLPROTO_HTTPS|CURLPROTO_FILE) != CURLE_OK)
|
||||
return -EIO;
|
||||
|
||||
*ret = TAKE_PTR(c);
|
||||
return 0;
|
||||
}
|
||||
|
@ -415,6 +415,13 @@ static JournalFile* find_journal(Server *s, uid_t uid) {
|
||||
if (s->runtime_journal)
|
||||
return s->runtime_journal;
|
||||
|
||||
/* If we are not in persistent mode, then we need return NULL immediately rather than opening a
|
||||
* persistent journal of any sort.
|
||||
*
|
||||
* Fixes https://github.com/systemd/systemd/issues/20390 */
|
||||
if (!IN_SET(s->storage, STORAGE_AUTO, STORAGE_PERSISTENT))
|
||||
return NULL;
|
||||
|
||||
if (uid_for_system_journal(uid))
|
||||
return s->system_journal;
|
||||
|
||||
|
@ -1107,7 +1107,7 @@ int dhcp_server_handle_message(sd_dhcp_server *server, DHCPMessage *message, siz
|
||||
|
||||
if (server->bound_leases[pool_offset] == existing_lease) {
|
||||
server->bound_leases[pool_offset] = NULL;
|
||||
hashmap_remove(server->leases_by_client_id, existing_lease);
|
||||
hashmap_remove(server->leases_by_client_id, &existing_lease->client_id);
|
||||
dhcp_lease_free(existing_lease);
|
||||
|
||||
if (server->callback)
|
||||
|
@ -1219,7 +1219,7 @@ static int client_parse_message(
|
||||
|
||||
if (lease->ia.addresses) {
|
||||
lt_t1 = MIN(lt_t1, be32toh(lease->ia.ia_na.lifetime_t1));
|
||||
lt_t2 = MIN(lt_t2, be32toh(lease->ia.ia_na.lifetime_t1));
|
||||
lt_t2 = MIN(lt_t2, be32toh(lease->ia.ia_na.lifetime_t2));
|
||||
}
|
||||
|
||||
break;
|
||||
@ -1328,17 +1328,16 @@ static int client_parse_message(
|
||||
dhcp6_message_type_to_string(message->type));
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
|
||||
} else {
|
||||
if (lease->ia.addresses) {
|
||||
lease->ia.ia_na.lifetime_t1 = htobe32(lt_t1);
|
||||
lease->ia.ia_na.lifetime_t2 = htobe32(lt_t2);
|
||||
}
|
||||
if (lease->ia.addresses) {
|
||||
lease->ia.ia_na.lifetime_t1 = htobe32(lt_t1);
|
||||
lease->ia.ia_na.lifetime_t2 = htobe32(lt_t2);
|
||||
}
|
||||
|
||||
if (lease->pd.addresses) {
|
||||
lease->pd.ia_pd.lifetime_t1 = htobe32(lt_t1);
|
||||
lease->pd.ia_pd.lifetime_t2 = htobe32(lt_t2);
|
||||
}
|
||||
if (lease->pd.addresses) {
|
||||
lease->pd.ia_pd.lifetime_t1 = htobe32(lt_t1);
|
||||
lease->pd.ia_pd.lifetime_t2 = htobe32(lt_t2);
|
||||
}
|
||||
|
||||
client->information_refresh_time_usec = MAX(irt, IRT_MINIMUM);
|
||||
|
@ -5,6 +5,7 @@
|
||||
#include "conf-parser.h"
|
||||
#include "macvlan.h"
|
||||
#include "macvlan-util.h"
|
||||
#include "networkd-network.h"
|
||||
#include "parse-util.h"
|
||||
|
||||
DEFINE_CONFIG_PARSE_ENUM(config_parse_macvlan_mode, macvlan_mode, MacVlanMode, "Failed to parse macvlan mode");
|
||||
@ -16,6 +17,7 @@ static int netdev_macvlan_fill_message_create(NetDev *netdev, Link *link, sd_net
|
||||
assert(netdev);
|
||||
assert(link);
|
||||
assert(netdev->ifname);
|
||||
assert(link->network);
|
||||
|
||||
if (netdev->kind == NETDEV_KIND_MACVLAN)
|
||||
m = MACVLAN(netdev);
|
||||
@ -52,6 +54,13 @@ static int netdev_macvlan_fill_message_create(NetDev *netdev, Link *link, sd_net
|
||||
return log_netdev_error_errno(netdev, r, "Could not append IFLA_MACVLAN_MODE attribute: %m");
|
||||
}
|
||||
|
||||
/* set the nopromisc flag if Promiscuous= of the link is explicitly set to false */
|
||||
if (m->mode == NETDEV_MACVLAN_MODE_PASSTHRU && link->network->promiscuous == 0) {
|
||||
r = sd_netlink_message_append_u16(req, IFLA_MACVLAN_FLAGS, MACVLAN_FLAG_NOPROMISC);
|
||||
if (r < 0)
|
||||
return log_netdev_error_errno(netdev, r, "Could not append IFLA_MACVLAN_FLAGS attribute: %m");
|
||||
}
|
||||
|
||||
if (m->bc_queue_length != UINT32_MAX) {
|
||||
r = sd_netlink_message_append_u32(req, IFLA_MACVLAN_BC_QUEUE_LEN, m->bc_queue_length);
|
||||
if (r < 0)
|
||||
|
@ -1272,17 +1272,17 @@ int request_process_address(Request *req) {
|
||||
if (r <= 0)
|
||||
return r;
|
||||
|
||||
r = address_get(link, req->address, &a);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = address_configure(a, link, req->netlink_handler);
|
||||
r = address_configure(req->address, link, req->netlink_handler);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
/* To prevent a double decrement on failure in after_configure(). */
|
||||
req->message_counter = NULL;
|
||||
|
||||
r = address_get(link, req->address, &a);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (req->after_configure) {
|
||||
r = req->after_configure(req, a);
|
||||
if (r < 0)
|
||||
|
@ -1,5 +1,6 @@
|
||||
/* SPDX-License-Identifier: LGPL-2.1-or-later */
|
||||
|
||||
#include <net/if.h>
|
||||
#include <netinet/in.h>
|
||||
#include <linux/if.h>
|
||||
#include <linux/if_arp.h>
|
||||
@ -21,6 +22,7 @@
|
||||
#include "ethtool-util.h"
|
||||
#include "fd-util.h"
|
||||
#include "fileio.h"
|
||||
#include "format-util.h"
|
||||
#include "fs-util.h"
|
||||
#include "ipvlan.h"
|
||||
#include "missing_network.h"
|
||||
@ -2161,6 +2163,7 @@ static int link_update_alternative_names(Link *link, sd_netlink_message *message
|
||||
}
|
||||
|
||||
static int link_update_name(Link *link, sd_netlink_message *message) {
|
||||
char ifname_from_index[IF_NAMESIZE + 1];
|
||||
const char *ifname;
|
||||
int r;
|
||||
|
||||
@ -2177,6 +2180,16 @@ static int link_update_name(Link *link, sd_netlink_message *message) {
|
||||
if (streq(ifname, link->ifname))
|
||||
return 0;
|
||||
|
||||
if (!format_ifname(link->ifindex, ifname_from_index))
|
||||
return log_link_debug_errno(link, SYNTHETIC_ERRNO(ENXIO), "Could not get interface name for index %i.", link->ifindex);
|
||||
|
||||
if (!streq(ifname, ifname_from_index)) {
|
||||
log_link_debug(link, "New interface name '%s' received from the kernel does not correspond "
|
||||
"with the name currently configured on the actual interface '%s'. Ignoring.",
|
||||
ifname, ifname_from_index);
|
||||
return 0;
|
||||
}
|
||||
|
||||
log_link_info(link, "Interface name change detected, renamed to %s.", ifname);
|
||||
|
||||
hashmap_remove(link->manager->links_by_name, link->ifname);
|
||||
|
@ -765,7 +765,9 @@ static int ndisc_router_process_autonomous_prefix(Link *link, sd_ndisc_router *r
|
||||
assert(link);
|
||||
assert(rt);
|
||||
|
||||
r = sd_ndisc_router_get_timestamp(rt, clock_boottime_or_monotonic(), &time_now);
|
||||
/* Do not use clock_boottime_or_monotonic() here, as the kernel internally manages cstamp and
|
||||
* tstamp with jiffies, and it is not increased while the system is suspended. */
|
||||
r = sd_ndisc_router_get_timestamp(rt, CLOCK_MONOTONIC, &time_now);
|
||||
if (r < 0)
|
||||
return log_link_error_errno(link, r, "Failed to get RA timestamp: %m");
|
||||
|
||||
|
@ -791,12 +791,7 @@ static bool nexthop_is_ready_to_configure(Link *link, const NextHop *nexthop) {
|
||||
}
|
||||
}
|
||||
|
||||
if (nexthop->onlink <= 0 &&
|
||||
in_addr_is_set(nexthop->family, &nexthop->gw) &&
|
||||
!manager_address_is_reachable(link->manager, nexthop->family, &nexthop->gw))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
return gateway_is_ready(link, nexthop->onlink, nexthop->family, &nexthop->gw);
|
||||
}
|
||||
|
||||
int request_process_nexthop(Request *req) {
|
||||
|
@ -746,21 +746,54 @@ static bool route_address_is_reachable(const Route *route, int family, const uni
|
||||
FAMILY_ADDRESS_SIZE(family) * 8) > 0;
|
||||
}
|
||||
|
||||
bool manager_address_is_reachable(Manager *manager, int family, const union in_addr_union *address) {
|
||||
Link *link;
|
||||
|
||||
assert(manager);
|
||||
static bool prefix_route_address_is_reachable(const Address *a, int family, const union in_addr_union *address) {
|
||||
assert(a);
|
||||
assert(IN_SET(family, AF_INET, AF_INET6));
|
||||
assert(address);
|
||||
|
||||
HASHMAP_FOREACH(link, manager->links_by_index) {
|
||||
Route *route;
|
||||
if (a->family != family)
|
||||
return false;
|
||||
if (!address_is_ready(a))
|
||||
return false;
|
||||
if (FLAGS_SET(a->flags, IFA_F_NOPREFIXROUTE))
|
||||
return false;
|
||||
if (in_addr_is_set(a->family, &a->in_addr_peer))
|
||||
return false;
|
||||
|
||||
SET_FOREACH(route, link->routes)
|
||||
if (route_address_is_reachable(route, family, address))
|
||||
return in_addr_prefix_intersect(
|
||||
family,
|
||||
&a->in_addr,
|
||||
a->prefixlen,
|
||||
address,
|
||||
FAMILY_ADDRESS_SIZE(family) * 8) > 0;
|
||||
}
|
||||
|
||||
static bool link_address_is_reachable(Link *link, int family, const union in_addr_union *address) {
|
||||
Route *route;
|
||||
|
||||
assert(link);
|
||||
assert(link->manager);
|
||||
assert(IN_SET(family, AF_INET, AF_INET6));
|
||||
assert(address);
|
||||
|
||||
|
||||
SET_FOREACH(route, link->routes)
|
||||
if (route_address_is_reachable(route, family, address))
|
||||
return true;
|
||||
SET_FOREACH(route, link->routes_foreign)
|
||||
if (route_address_is_reachable(route, family, address))
|
||||
return true;
|
||||
|
||||
/* If we do not manage foreign routes, then there may exist a prefix route we do not know,
|
||||
* which was created on configuring an address. Hence, also check the addresses. */
|
||||
if (!link->manager->manage_foreign_routes) {
|
||||
Address *a;
|
||||
|
||||
SET_FOREACH(a, link->addresses)
|
||||
if (prefix_route_address_is_reachable(a, family, address))
|
||||
return true;
|
||||
SET_FOREACH(route, link->routes_foreign)
|
||||
if (route_address_is_reachable(route, family, address))
|
||||
SET_FOREACH(a, link->addresses_foreign)
|
||||
if (prefix_route_address_is_reachable(a, family, address))
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -1658,6 +1691,22 @@ int link_request_static_routes(Link *link, bool only_ipv4) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
bool gateway_is_ready(Link *link, int onlink, int family, const union in_addr_union *gw) {
|
||||
assert(link);
|
||||
assert(gw);
|
||||
|
||||
if (onlink > 0)
|
||||
return true;
|
||||
|
||||
if (!in_addr_is_set(family, gw))
|
||||
return true;
|
||||
|
||||
if (family == AF_INET6 && in6_addr_is_link_local(&gw->in6))
|
||||
return true;
|
||||
|
||||
return link_address_is_reachable(link, family, gw);
|
||||
}
|
||||
|
||||
static int route_is_ready_to_configure(const Route *route, Link *link) {
|
||||
MultipathRoute *m;
|
||||
NextHop *nh = NULL;
|
||||
@ -1701,19 +1750,13 @@ static int route_is_ready_to_configure(const Route *route, Link *link) {
|
||||
return r;
|
||||
}
|
||||
|
||||
if (route->gateway_onlink <= 0 &&
|
||||
in_addr_is_set(route->gw_family, &route->gw) > 0 &&
|
||||
!manager_address_is_reachable(link->manager, route->gw_family, &route->gw))
|
||||
if (!gateway_is_ready(link, route->gateway_onlink, route->gw_family, &route->gw))
|
||||
return false;
|
||||
|
||||
ORDERED_SET_FOREACH(m, route->multipath_routes) {
|
||||
union in_addr_union a = m->gateway.address;
|
||||
Link *l = NULL;
|
||||
|
||||
if (route->gateway_onlink <= 0 &&
|
||||
!manager_address_is_reachable(link->manager, m->gateway.family, &a))
|
||||
return false;
|
||||
|
||||
if (m->ifname) {
|
||||
if (link_get_by_name(link->manager, m->ifname, &l) < 0)
|
||||
return false;
|
||||
@ -1725,6 +1768,9 @@ static int route_is_ready_to_configure(const Route *route, Link *link) {
|
||||
}
|
||||
if (l && !link_is_ready_to_configure(l, true))
|
||||
return false;
|
||||
|
||||
if (!gateway_is_ready(l ?: link, route->gateway_onlink, m->gateway.family, &a))
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
|
@ -78,8 +78,8 @@ int route_configure_handler_internal(sd_netlink *rtnl, sd_netlink_message *m, Li
|
||||
int route_remove(const Route *route, Manager *manager, Link *link);
|
||||
|
||||
int link_has_route(Link *link, const Route *route);
|
||||
bool manager_address_is_reachable(Manager *manager, int family, const union in_addr_union *address);
|
||||
int manager_find_uplink(Manager *m, int family, Link *exclude, Link **ret);
|
||||
bool gateway_is_ready(Link *link, int onlink, int family, const union in_addr_union *gw);
|
||||
|
||||
int link_drop_routes(Link *link);
|
||||
int link_drop_foreign_routes(Link *link);
|
||||
|
@ -163,7 +163,9 @@ void routing_policy_rule_hash_func(const RoutingPolicyRule *rule, struct siphash
|
||||
siphash24_compress(&rule->type, sizeof(rule->type), state);
|
||||
siphash24_compress(&rule->fwmark, sizeof(rule->fwmark), state);
|
||||
siphash24_compress(&rule->fwmask, sizeof(rule->fwmask), state);
|
||||
siphash24_compress(&rule->priority, sizeof(rule->priority), state);
|
||||
siphash24_compress_boolean(rule->priority_set, state);
|
||||
if (rule->priority_set)
|
||||
siphash24_compress(&rule->priority, sizeof(rule->priority), state);
|
||||
siphash24_compress(&rule->table, sizeof(rule->table), state);
|
||||
siphash24_compress(&rule->suppress_prefixlen, sizeof(rule->suppress_prefixlen), state);
|
||||
|
||||
@ -229,10 +231,16 @@ int routing_policy_rule_compare_func(const RoutingPolicyRule *a, const RoutingPo
|
||||
if (r != 0)
|
||||
return r;
|
||||
|
||||
r = CMP(a->priority, b->priority);
|
||||
r = CMP(a->priority_set, b->priority_set);
|
||||
if (r != 0)
|
||||
return r;
|
||||
|
||||
if (a->priority_set) {
|
||||
r = CMP(a->priority, b->priority);
|
||||
if (r != 0)
|
||||
return r;
|
||||
}
|
||||
|
||||
r = CMP(a->table, b->table);
|
||||
if (r != 0)
|
||||
return r;
|
||||
@ -293,8 +301,9 @@ DEFINE_PRIVATE_HASH_OPS_WITH_KEY_DESTRUCTOR(
|
||||
routing_policy_rule_compare_func,
|
||||
routing_policy_rule_free);
|
||||
|
||||
static int routing_policy_rule_get(Manager *m, const RoutingPolicyRule *rule, RoutingPolicyRule **ret) {
|
||||
static int routing_policy_rule_get(Manager *m, const RoutingPolicyRule *rule, bool require_priority, RoutingPolicyRule **ret) {
|
||||
RoutingPolicyRule *existing;
|
||||
int r;
|
||||
|
||||
assert(m);
|
||||
|
||||
@ -312,6 +321,23 @@ static int routing_policy_rule_get(Manager *m, const RoutingPolicyRule *rule, Ro
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!require_priority && rule->priority_set) {
|
||||
_cleanup_(routing_policy_rule_freep) RoutingPolicyRule *tmp = NULL;
|
||||
|
||||
r = routing_policy_rule_dup(rule, &tmp);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
tmp->priority_set = false;
|
||||
|
||||
existing = set_get(m->rules, tmp);
|
||||
if (existing) {
|
||||
if (ret)
|
||||
*ret = existing;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return -ENOENT;
|
||||
}
|
||||
|
||||
@ -328,7 +354,7 @@ static int routing_policy_rule_add(Manager *m, const RoutingPolicyRule *in, Rout
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = routing_policy_rule_get(m, rule, &existing);
|
||||
r = routing_policy_rule_get(m, rule, true, &existing);
|
||||
if (r == -ENOENT) {
|
||||
/* Rule does not exist, use a new one. */
|
||||
r = set_ensure_put(&m->rules, &routing_policy_rule_hash_ops, rule);
|
||||
@ -371,6 +397,32 @@ static int routing_policy_rule_consume_foreign(Manager *m, RoutingPolicyRule *ru
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int routing_policy_rule_update_priority(RoutingPolicyRule *rule, uint32_t priority) {
|
||||
int r;
|
||||
|
||||
assert(rule);
|
||||
assert(rule->manager);
|
||||
|
||||
if (rule->priority_set)
|
||||
return 0;
|
||||
|
||||
if (!set_remove(rule->manager->rules, rule))
|
||||
return -ENOENT;
|
||||
|
||||
rule->priority = priority;
|
||||
rule->priority_set = true;
|
||||
|
||||
r = set_put(rule->manager->rules, rule);
|
||||
if (r <= 0) {
|
||||
/* Undo */
|
||||
rule->priority_set = false;
|
||||
assert_se(set_put(rule->manager->rules, rule) > 0);
|
||||
return r == 0 ? -EEXIST : r;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void log_routing_policy_rule_debug(const RoutingPolicyRule *rule, const char *str, const Link *link, const Manager *m) {
|
||||
_cleanup_free_ char *from = NULL, *to = NULL, *table = NULL;
|
||||
|
||||
@ -422,9 +474,11 @@ static int routing_policy_rule_set_netlink_message(const RoutingPolicyRule *rule
|
||||
return log_link_error_errno(link, r, "Could not set destination prefix length: %m");
|
||||
}
|
||||
|
||||
r = sd_netlink_message_append_u32(m, FRA_PRIORITY, rule->priority);
|
||||
if (r < 0)
|
||||
return log_link_error_errno(link, r, "Could not append FRA_PRIORITY attribute: %m");
|
||||
if (rule->priority_set) {
|
||||
r = sd_netlink_message_append_u32(m, FRA_PRIORITY, rule->priority);
|
||||
if (r < 0)
|
||||
return log_link_error_errno(link, r, "Could not append FRA_PRIORITY attribute: %m");
|
||||
}
|
||||
|
||||
if (rule->tos > 0) {
|
||||
r = sd_rtnl_message_routing_policy_rule_set_tos(m, rule->tos);
|
||||
@ -662,6 +716,28 @@ int manager_drop_routing_policy_rules_internal(Manager *m, bool foreign, const L
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!foreign) {
|
||||
_cleanup_(routing_policy_rule_freep) RoutingPolicyRule *tmp = NULL;
|
||||
|
||||
/* The rule may be configured without priority. Try to find without priority. */
|
||||
|
||||
k = routing_policy_rule_dup(rule, &tmp);
|
||||
if (k < 0) {
|
||||
if (r >= 0)
|
||||
r = k;
|
||||
continue;
|
||||
}
|
||||
|
||||
tmp->priority_set = false;
|
||||
|
||||
k = links_have_routing_policy_rule(m, tmp, except);
|
||||
if (k != 0) {
|
||||
if (k < 0 && r >= 0)
|
||||
r = k;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
k = routing_policy_rule_remove(rule, m);
|
||||
if (k < 0 && r >= 0)
|
||||
r = k;
|
||||
@ -821,11 +897,11 @@ int request_process_routing_policy_rule(Request *req) {
|
||||
}
|
||||
|
||||
static const RoutingPolicyRule kernel_rules[] = {
|
||||
{ .family = AF_INET, .priority = 0, .table = RT_TABLE_LOCAL, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET, .priority = 32766, .table = RT_TABLE_MAIN, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET, .priority = 32767, .table = RT_TABLE_DEFAULT, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET6, .priority = 0, .table = RT_TABLE_LOCAL, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET6, .priority = 32766, .table = RT_TABLE_MAIN, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET, .priority_set = true, .priority = 0, .table = RT_TABLE_LOCAL, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET, .priority_set = true, .priority = 32766, .table = RT_TABLE_MAIN, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET, .priority_set = true, .priority = 32767, .table = RT_TABLE_DEFAULT, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET6, .priority_set = true, .priority = 0, .table = RT_TABLE_LOCAL, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
{ .family = AF_INET6, .priority_set = true, .priority = 32766, .table = RT_TABLE_MAIN, .type = FR_ACT_TO_TBL, .uid_range.start = UID_INVALID, .uid_range.end = UID_INVALID, .suppress_prefixlen = -1, },
|
||||
};
|
||||
|
||||
static bool routing_policy_rule_is_created_by_kernel(const RoutingPolicyRule *rule) {
|
||||
@ -936,6 +1012,9 @@ int manager_rtnl_process_rule(sd_netlink *rtnl, sd_netlink_message *message, Man
|
||||
log_warning_errno(r, "rtnl: could not get FRA_PRIORITY attribute, ignoring: %m");
|
||||
return 0;
|
||||
}
|
||||
/* The kernel does not send priority if priority is zero. So, the flag below must be always set
|
||||
* even if the message does not contain FRA_PRIORITY. */
|
||||
tmp->priority_set = true;
|
||||
|
||||
r = sd_netlink_message_read_u32(message, FRA_TABLE, &tmp->table);
|
||||
if (r < 0 && r != -ENODATA) {
|
||||
@ -1027,13 +1106,16 @@ int manager_rtnl_process_rule(sd_netlink *rtnl, sd_netlink_message *message, Man
|
||||
* protocol of the received rule is RTPROT_KERNEL or RTPROT_STATIC. */
|
||||
tmp->protocol = routing_policy_rule_is_created_by_kernel(tmp) ? RTPROT_KERNEL : RTPROT_STATIC;
|
||||
|
||||
(void) routing_policy_rule_get(m, tmp, &rule);
|
||||
(void) routing_policy_rule_get(m, tmp, false, &rule);
|
||||
|
||||
switch (type) {
|
||||
case RTM_NEWRULE:
|
||||
if (rule)
|
||||
if (rule) {
|
||||
log_routing_policy_rule_debug(tmp, "Received remembered", NULL, m);
|
||||
else if (!m->manage_foreign_routes)
|
||||
r = routing_policy_rule_update_priority(rule, tmp->priority);
|
||||
if (r < 0)
|
||||
log_warning_errno(r, "Failed to update priority of remembered routing policy rule, ignoring: %m");
|
||||
} else if (!m->manage_foreign_routes)
|
||||
log_routing_policy_rule_debug(tmp, "Ignoring received foreign", NULL, m);
|
||||
else {
|
||||
log_routing_policy_rule_debug(tmp, "Remembering foreign", NULL, m);
|
||||
@ -1155,11 +1237,19 @@ int config_parse_routing_policy_rule_priority(
|
||||
if (r < 0)
|
||||
return log_oom();
|
||||
|
||||
if (isempty(rvalue)) {
|
||||
n->priority = 0;
|
||||
n->priority_set = false;
|
||||
TAKE_PTR(n);
|
||||
return 0;
|
||||
}
|
||||
|
||||
r = safe_atou32(rvalue, &n->priority);
|
||||
if (r < 0) {
|
||||
log_syntax(unit, LOG_WARNING, filename, line, r, "Failed to parse RPDB rule priority, ignoring: %s", rvalue);
|
||||
return 0;
|
||||
}
|
||||
n->priority_set = true;
|
||||
|
||||
TAKE_PTR(n);
|
||||
return 0;
|
||||
|
@ -20,6 +20,7 @@ typedef struct RoutingPolicyRule {
|
||||
NetworkConfigSection *section;
|
||||
|
||||
bool invert_rule;
|
||||
bool priority_set;
|
||||
|
||||
uint8_t tos;
|
||||
uint8_t type;
|
||||
|
@ -229,10 +229,14 @@ static int link_configure(
|
||||
|
||||
log_link_debug(link, "Setting %s", set_link_operation_to_string(op));
|
||||
|
||||
if (IN_SET(op, SET_LINK_BOND, SET_LINK_CAN)) {
|
||||
if (op == SET_LINK_BOND) {
|
||||
r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_NEWLINK, link->master_ifindex);
|
||||
if (r < 0)
|
||||
return log_link_debug_errno(link, r, "Could not allocate RTM_NEWLINK message: %m");
|
||||
} else if (op == SET_LINK_CAN) {
|
||||
r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_NEWLINK, link->ifindex);
|
||||
if (r < 0)
|
||||
return log_link_debug_errno(link, r, "Could not allocate RTM_NEWLINK message: %m");
|
||||
} else {
|
||||
r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_SETLINK, link->ifindex);
|
||||
if (r < 0)
|
||||
|
@ -362,9 +362,8 @@ void dns_server_packet_rcode_downgrade(DnsServer *s, DnsServerFeatureLevel level
|
||||
if (s->possible_feature_level > level) {
|
||||
s->possible_feature_level = level;
|
||||
dns_server_reset_counters(s);
|
||||
log_debug("Downgrading transaction feature level fixed an RCODE error, downgrading server %s too.", strna(dns_server_string_full(s)));
|
||||
}
|
||||
|
||||
log_debug("Downgrading transaction feature level fixed an RCODE error, downgrading server %s too.", strna(dns_server_string_full(s)));
|
||||
}
|
||||
|
||||
void dns_server_packet_invalid(DnsServer *s, DnsServerFeatureLevel level) {
|
||||
|
@ -585,7 +585,7 @@ static int dns_stub_send_reply(
|
||||
DNS_PACKET_RD(q->request_packet),
|
||||
!!q->request_packet->opt,
|
||||
edns0_do,
|
||||
DNS_PACKET_AD(q->request_packet) && dns_query_fully_authenticated(q),
|
||||
(DNS_PACKET_AD(q->request_packet) || DNS_PACKET_DO(q->request_packet)) && dns_query_fully_authenticated(q),
|
||||
DNS_PACKET_CD(q->request_packet),
|
||||
q->stub_listener_extra ? ADVERTISE_EXTRA_DATAGRAM_SIZE_MAX : ADVERTISE_DATAGRAM_SIZE_MAX,
|
||||
dns_packet_has_nsid_request(q->request_packet) > 0 && !q->stub_listener_extra);
|
||||
@ -627,7 +627,7 @@ static int dns_stub_send_failure(
|
||||
DNS_PACKET_RD(p),
|
||||
!!p->opt,
|
||||
DNS_PACKET_DO(p),
|
||||
DNS_PACKET_AD(p) && authenticated,
|
||||
(DNS_PACKET_AD(p) || DNS_PACKET_DO(p)) && authenticated,
|
||||
DNS_PACKET_CD(p),
|
||||
l ? ADVERTISE_EXTRA_DATAGRAM_SIZE_MAX : ADVERTISE_DATAGRAM_SIZE_MAX,
|
||||
dns_packet_has_nsid_request(p) > 0 && !l);
|
||||
|
@ -1142,22 +1142,35 @@ void dns_transaction_process_reply(DnsTransaction *t, DnsPacket *p, bool encrypt
|
||||
break;
|
||||
}
|
||||
|
||||
/* Reduce this feature level by one and try again. */
|
||||
switch (t->current_feature_level) {
|
||||
case DNS_SERVER_FEATURE_LEVEL_TLS_DO:
|
||||
t->clamp_feature_level_servfail = DNS_SERVER_FEATURE_LEVEL_TLS_PLAIN;
|
||||
break;
|
||||
case DNS_SERVER_FEATURE_LEVEL_TLS_PLAIN + 1:
|
||||
/* Skip plain TLS when TLS is not supported */
|
||||
t->clamp_feature_level_servfail = DNS_SERVER_FEATURE_LEVEL_TLS_PLAIN - 1;
|
||||
break;
|
||||
default:
|
||||
t->clamp_feature_level_servfail = t->current_feature_level - 1;
|
||||
}
|
||||
/* SERVFAIL can happen for many reasons and may be transient.
|
||||
* To avoid unnecessary downgrades retry once with the initial level.
|
||||
* Check for clamp_feature_level_servfail having an invalid value as a sign that this is the
|
||||
* first attempt to downgrade. If so, clamp to the current value so that the transaction
|
||||
* is retried without actually downgrading. If the next try also fails we will downgrade by
|
||||
* hitting the else branch below. */
|
||||
if (DNS_PACKET_RCODE(p) == DNS_RCODE_SERVFAIL &&
|
||||
t->clamp_feature_level_servfail < 0) {
|
||||
t->clamp_feature_level_servfail = t->current_feature_level;
|
||||
log_debug("Server returned error %s, retrying transaction.",
|
||||
dns_rcode_to_string(DNS_PACKET_RCODE(p)));
|
||||
} else {
|
||||
/* Reduce this feature level by one and try again. */
|
||||
switch (t->current_feature_level) {
|
||||
case DNS_SERVER_FEATURE_LEVEL_TLS_DO:
|
||||
t->clamp_feature_level_servfail = DNS_SERVER_FEATURE_LEVEL_TLS_PLAIN;
|
||||
break;
|
||||
case DNS_SERVER_FEATURE_LEVEL_TLS_PLAIN + 1:
|
||||
/* Skip plain TLS when TLS is not supported */
|
||||
t->clamp_feature_level_servfail = DNS_SERVER_FEATURE_LEVEL_TLS_PLAIN - 1;
|
||||
break;
|
||||
default:
|
||||
t->clamp_feature_level_servfail = t->current_feature_level - 1;
|
||||
}
|
||||
|
||||
log_debug("Server returned error %s, retrying transaction with reduced feature level %s.",
|
||||
dns_rcode_to_string(DNS_PACKET_RCODE(p)),
|
||||
dns_server_feature_level_to_string(t->clamp_feature_level_servfail));
|
||||
log_debug("Server returned error %s, retrying transaction with reduced feature level %s.",
|
||||
dns_rcode_to_string(DNS_PACKET_RCODE(p)),
|
||||
dns_server_feature_level_to_string(t->clamp_feature_level_servfail));
|
||||
}
|
||||
|
||||
dns_transaction_retry(t, false /* use the same server */);
|
||||
return;
|
||||
|
@ -305,7 +305,7 @@ static int image_make(
|
||||
}
|
||||
|
||||
/* Get directory creation time (not available everywhere, but that's OK */
|
||||
(void) fd_getcrtime(dfd, &crtime);
|
||||
(void) fd_getcrtime(fd, &crtime);
|
||||
|
||||
/* If the IMMUTABLE bit is set, we consider the directory read-only. Since the ioctl is not
|
||||
* supported everywhere we ignore failures. */
|
||||
|
@ -20,11 +20,11 @@
|
||||
#include "util.h"
|
||||
|
||||
static int sethostname_idempotent_full(const char *s, bool really) {
|
||||
char buf[HOST_NAME_MAX + 1] = {};
|
||||
char buf[HOST_NAME_MAX + 1];
|
||||
|
||||
assert(s);
|
||||
|
||||
if (gethostname(buf, sizeof(buf) - 1) < 0)
|
||||
if (gethostname(buf, sizeof(buf)) < 0)
|
||||
return -errno;
|
||||
|
||||
if (streq(buf, s))
|
||||
@ -42,11 +42,11 @@ int sethostname_idempotent(const char *s) {
|
||||
}
|
||||
|
||||
bool get_hostname_filtered(char ret[static HOST_NAME_MAX + 1]) {
|
||||
char buf[HOST_NAME_MAX + 1] = {};
|
||||
char buf[HOST_NAME_MAX + 1];
|
||||
|
||||
/* Returns true if we got a good hostname, false otherwise. */
|
||||
|
||||
if (gethostname(buf, sizeof(buf) - 1) < 0)
|
||||
if (gethostname(buf, sizeof(buf)) < 0)
|
||||
return false; /* This can realistically only fail with ENAMETOOLONG.
|
||||
* Let's treat that case the same as an invalid hostname. */
|
||||
|
||||
|
@ -215,13 +215,14 @@ int utmp_put_init_process(const char *id, pid_t pid, pid_t sid, const char *line
|
||||
}
|
||||
|
||||
int utmp_put_dead_process(const char *id, pid_t pid, int code, int status) {
|
||||
_cleanup_(utxent_cleanup) bool utmpx = false;
|
||||
struct utmpx lookup = {
|
||||
.ut_type = INIT_PROCESS /* looks for DEAD_PROCESS, LOGIN_PROCESS, USER_PROCESS, too */
|
||||
}, store, store_wtmp, *found;
|
||||
|
||||
assert(id);
|
||||
|
||||
setutxent();
|
||||
utmpx = utxent_start();
|
||||
|
||||
/* Copy the whole string if it fits, or just the suffix without the terminating NUL. */
|
||||
copy_suffix(store.ut_id, sizeof(store.ut_id), id);
|
||||
@ -339,6 +340,7 @@ int utmp_wall(
|
||||
bool (*match_tty)(const char *tty, void *userdata),
|
||||
void *userdata) {
|
||||
|
||||
_cleanup_(utxent_cleanup) bool utmpx = false;
|
||||
_cleanup_free_ char *text = NULL, *hn = NULL, *un = NULL, *stdin_tty = NULL;
|
||||
char date[FORMAT_TIMESTAMP_MAX];
|
||||
struct utmpx *u;
|
||||
@ -368,7 +370,7 @@ int utmp_wall(
|
||||
message) < 0)
|
||||
return -ENOMEM;
|
||||
|
||||
setutxent();
|
||||
utmpx = utxent_start();
|
||||
|
||||
r = 0;
|
||||
|
||||
|
@ -89,5 +89,7 @@ int main(void) {
|
||||
printf("big_enum2_pos → %zu\n", sizeof(big_enum2_pos));
|
||||
printf("big_enum2_neg → %zu\n", sizeof(big_enum2_neg));
|
||||
|
||||
printf("timeval: %zu\n", sizeof(struct timeval));
|
||||
printf("timespec: %zu\n", sizeof(struct timespec));
|
||||
return 0;
|
||||
}
|
||||
|
@ -412,7 +412,7 @@ static int manager_receive_response(sd_event_source *source, int fd, uint32_t re
|
||||
.iov_base = &ntpmsg,
|
||||
.iov_len = sizeof(ntpmsg),
|
||||
};
|
||||
CMSG_BUFFER_TYPE(CMSG_SPACE(sizeof(struct timeval))) control;
|
||||
CMSG_BUFFER_TYPE(CMSG_SPACE(sizeof(struct timespec))) control;
|
||||
union sockaddr_union server_addr;
|
||||
struct msghdr msghdr = {
|
||||
.msg_iov = &iov,
|
||||
|
@ -28,10 +28,12 @@ static int builtin_net_setup_link(sd_device *dev, int argc, char **argv, bool te
|
||||
|
||||
r = link_config_get(ctx, dev, &link);
|
||||
if (r < 0) {
|
||||
if (r == -ENOENT)
|
||||
return log_device_debug_errno(dev, r, "No matching link configuration found.");
|
||||
if (r == -ENODEV)
|
||||
return log_device_debug_errno(dev, r, "Link vanished while searching for configuration for it.");
|
||||
if (r == -ENOENT) {
|
||||
log_device_debug_errno(dev, r, "No matching link configuration found, ignoring device.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
return log_device_error_errno(dev, r, "Failed to get link config: %m");
|
||||
}
|
||||
|
@ -348,12 +348,14 @@ run_qemu() {
|
||||
[ "$ARCH" ] || ARCH=$(uname -m)
|
||||
case $ARCH in
|
||||
ppc64*)
|
||||
KERNEL_BIN="/boot/vmlinux-$KERNEL_VER"
|
||||
CONSOLE=hvc0
|
||||
;;
|
||||
# Ubuntu ppc64* calls the kernel binary as vmlinux-*, RHEL/CentOS
|
||||
# uses the "standard" vmlinuz- prefix
|
||||
[[ -e "/boot/vmlinux-$KERNEL_VER" ]] && KERNEL_BIN="/boot/vmlinux-$KERNEL_VER" || KERNEL_BIN="/boot/vmlinuz-$KERNEL_VER"
|
||||
CONSOLE=hvc0
|
||||
;;
|
||||
*)
|
||||
KERNEL_BIN="/boot/vmlinuz-$KERNEL_VER"
|
||||
;;
|
||||
KERNEL_BIN="/boot/vmlinuz-$KERNEL_VER"
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
fi
|
||||
|
@ -38,6 +38,10 @@ Id=7
|
||||
Family=ipv6
|
||||
Blackhole=yes
|
||||
|
||||
[NextHop]
|
||||
Id=8
|
||||
Gateway=fe80::222:4dff:ff:ff:ff:ff
|
||||
|
||||
[NextHop]
|
||||
Gateway=192.168.5.2
|
||||
|
||||
|
@ -17,6 +17,10 @@ Destination=2001:1234:5:9fff:ff:ff:ff:ff/128
|
||||
[Route]
|
||||
Gateway=2001:1234:5:8fff:ff:ff:ff:ff
|
||||
|
||||
[Route]
|
||||
Destination=2001:1234:5:afff:ff:ff:ff:ff/128
|
||||
Gateway=fe80::222:4dff:ff:ff:ff:ff
|
||||
|
||||
[Route]
|
||||
Destination=149.10.124.64
|
||||
Scope=link
|
||||
|
@ -0,0 +1,2 @@
|
||||
[Network]
|
||||
ManageForeignRoutes=no
|
@ -16,6 +16,7 @@ from shutil import copytree
|
||||
|
||||
network_unit_file_path='/run/systemd/network'
|
||||
networkd_runtime_directory='/run/systemd/netif'
|
||||
networkd_conf_dropin_path='/run/systemd/networkd.conf.d'
|
||||
networkd_ci_path='/run/networkd-ci'
|
||||
network_sysctl_ipv6_path='/proc/sys/net/ipv6/conf'
|
||||
network_sysctl_ipv4_path='/proc/sys/net/ipv4/conf'
|
||||
@ -263,6 +264,7 @@ def setUpModule():
|
||||
global running_units
|
||||
|
||||
os.makedirs(network_unit_file_path, exist_ok=True)
|
||||
os.makedirs(networkd_conf_dropin_path, exist_ok=True)
|
||||
os.makedirs(networkd_ci_path, exist_ok=True)
|
||||
|
||||
shutil.rmtree(networkd_ci_path)
|
||||
@ -460,6 +462,17 @@ def remove_unit_from_networkd_path(units):
|
||||
if (os.path.exists(os.path.join(network_unit_file_path, unit + '.d'))):
|
||||
shutil.rmtree(os.path.join(network_unit_file_path, unit + '.d'))
|
||||
|
||||
def copy_networkd_conf_dropin(*dropins):
|
||||
"""Copy networkd.conf dropin files into the testbed."""
|
||||
for dropin in dropins:
|
||||
shutil.copy(os.path.join(networkd_ci_path, dropin), networkd_conf_dropin_path)
|
||||
|
||||
def remove_networkd_conf_dropin(dropins):
|
||||
"""Remove previously copied networkd.conf dropin files from the testbed."""
|
||||
for dropin in dropins:
|
||||
if (os.path.exists(os.path.join(networkd_conf_dropin_path, dropin))):
|
||||
os.remove(os.path.join(networkd_conf_dropin_path, dropin))
|
||||
|
||||
def start_dnsmasq(additional_options='', ipv4_range='192.168.5.10,192.168.5.200', ipv6_range='2600::10,2600::20', lease_time='1h'):
|
||||
dnsmasq_command = f'dnsmasq -8 /var/run/networkd-ci/test-dnsmasq-log-file --log-queries=extra --log-dhcp --pid-file=/var/run/networkd-ci/test-test-dnsmasq.pid --conf-file=/dev/null --interface=veth-peer --enable-ra --dhcp-range={ipv6_range},{lease_time} --dhcp-range={ipv4_range},{lease_time} -R --dhcp-leasefile=/var/run/networkd-ci/lease --dhcp-option=26,1492 --dhcp-option=option:router,192.168.5.1 --port=0 ' + additional_options
|
||||
check_output(dnsmasq_command)
|
||||
@ -1858,6 +1871,10 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
|
||||
'routing-policy-rule-reconfigure2.network',
|
||||
]
|
||||
|
||||
networkd_conf_dropins = [
|
||||
'networkd-manage-foreign-routes-no.conf',
|
||||
]
|
||||
|
||||
routing_policy_rule_tables = ['7', '8', '9', '10', '1011']
|
||||
routes = [['blackhole', '202.54.1.2'], ['unreachable', '202.54.1.3'], ['prohibit', '202.54.1.4']]
|
||||
|
||||
@ -1875,6 +1892,7 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
|
||||
remove_routes(self.routes)
|
||||
remove_links(self.links)
|
||||
remove_unit_from_networkd_path(self.units)
|
||||
remove_networkd_conf_dropin(self.networkd_conf_dropins)
|
||||
stop_networkd(show_logs=True)
|
||||
call('ip netns del ns99', stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL)
|
||||
|
||||
@ -2253,7 +2271,10 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
|
||||
self.assertRegex(output, 'lookup 7')
|
||||
self.assertRegex(output, 'uidrange 100-200')
|
||||
|
||||
def test_route_static(self):
|
||||
def _test_route_static(self, manage_foreign_routes):
|
||||
if not manage_foreign_routes:
|
||||
copy_networkd_conf_dropin('networkd-manage-foreign-routes-no.conf')
|
||||
|
||||
copy_unit_to_networkd_unit_path('25-route-static.network', '12-dummy.netdev')
|
||||
start_networkd()
|
||||
self.wait_online(['dummy98:routable'])
|
||||
@ -2266,6 +2287,7 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
|
||||
print(output)
|
||||
self.assertIn('2001:1234:5:8fff:ff:ff:ff:ff proto static', output)
|
||||
self.assertIn('2001:1234:5:8f63::1 proto kernel', output)
|
||||
self.assertIn('2001:1234:5:afff:ff:ff:ff:ff via fe80:0:222:4dff:ff:ff:ff:ff proto static', output)
|
||||
|
||||
print('### ip -6 route show default')
|
||||
output = check_output('ip -6 route show default')
|
||||
@ -2459,6 +2481,13 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
|
||||
print(output)
|
||||
self.assertEqual(output, '')
|
||||
|
||||
self.tearDown()
|
||||
|
||||
def test_route_static(self):
|
||||
for manage_foreign_routes in [True, False]:
|
||||
with self.subTest(manage_foreign_routes=manage_foreign_routes):
|
||||
self._test_route_static(manage_foreign_routes)
|
||||
|
||||
@expectedFailureIfRTA_VIAIsNotSupported()
|
||||
def test_route_via_ipv6(self):
|
||||
copy_unit_to_networkd_unit_path('25-route-via-ipv6.network', '12-dummy.netdev')
|
||||
@ -2907,6 +2936,7 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
|
||||
self.assertIn('id 3 dev veth99', output)
|
||||
self.assertIn('id 4 dev veth99', output)
|
||||
self.assertRegex(output, 'id 5 via 192.168.10.1 dev veth99 .*onlink')
|
||||
self.assertIn('id 8 via fe80:0:222:4dff:ff:ff:ff:ff dev veth99', output)
|
||||
self.assertRegex(output, r'id [0-9]* via 192.168.5.2 dev veth99')
|
||||
|
||||
output = check_output('ip nexthop list dev dummy98')
|
||||
@ -3614,7 +3644,7 @@ class NetworkdBridgeTests(unittest.TestCase, Utilities):
|
||||
|
||||
output = check_output('ip rule list table 100')
|
||||
print(output)
|
||||
self.assertIn('0: from all to 8.8.8.8 lookup 100', output)
|
||||
self.assertIn('from all to 8.8.8.8 lookup 100', output)
|
||||
|
||||
class NetworkdLLDPTests(unittest.TestCase, Utilities):
|
||||
links = ['veth99']
|
||||
|
Loading…
Reference in New Issue
Block a user