Compare commits

...

20 Commits

Author SHA1 Message Date
Zbigniew Jędrzejewski-Szmek a68da22257 NEWS: tweak WithoutRA= description a bit more
Follow-up for cbdf02952e.
2020-07-02 18:12:03 +02:00
Yu Watanabe c03ef420fa network: tc: rename several settings which take size in bytes 2020-07-02 16:51:11 +02:00
hadess 25b67032a8
Merge pull request #16343 from jirislaby/master
hwdb: Add accel orientation quirk for UMAX VisionBook 10Wi Pro
2020-07-02 15:19:33 +02:00
Zbigniew Jędrzejewski-Szmek cc832f9772
Merge pull request #16338 from keszybz/spelling2
Tree-wide spelling fixes
2020-07-02 15:10:27 +02:00
Zbigniew Jędrzejewski-Szmek 63b7e7b4ba
Merge pull request #16336 from yuwata/ifindex-cleanups
tiny cleanups related to ifindex
2020-07-02 15:08:41 +02:00
Yu Watanabe cbdf02952e NEWS: update document about WithoutRA=
Follow-up for 838d39af93.
2020-07-02 20:25:48 +09:00
Yu Watanabe 1447dc625a
Merge pull request #16219 from ssahani/network-sr-iov
network: Introduce SR-IOV
2020-07-02 20:24:13 +09:00
Jiri Slaby 74986a0f88 hwdb: Add accel orientation quirk for UMAX VisionBook 10Wi Pro 2020-07-02 13:06:04 +02:00
Zbigniew Jędrzejewski-Szmek 52e085af82 tree-wide: "unparseable" → "unparsable"
"unparsable" is the more common spelling. We already pick "movable" over
"moveable". Let's do the same with this pair.
2020-07-02 09:58:23 +02:00
Yu Watanabe 13adf35343 resolve: use appropriate type 2020-07-02 16:58:06 +09:00
Yu Watanabe 5e958e1d6c util: use setsockopt_int() at one more place 2020-07-02 16:58:06 +09:00
Yu Watanabe 1a6c913676 libsystemd-network: rename index -> ifindex 2020-07-02 16:58:06 +09:00
Yu Watanabe 7fa69c0a6f dhcp6, radv: only accept valid ifindex 2020-07-02 16:58:06 +09:00
Zbigniew Jędrzejewski-Szmek 15e6a6e87b tree-wide: spell "lifecycle" without hyphen everywhere
We had 2 more instances of unhyphentated spelling.
2020-07-02 09:55:44 +02:00
Zbigniew Jędrzejewski-Szmek 37b22b3b47 tree: wide "the the" and other trivial grammar fixes 2020-07-02 09:51:38 +02:00
Yu Watanabe 3d2c26925f test-network: add tests for SR-IOV
This also adjusts test_sysctl_disable_ipv6(), as rt_trap flag may be
added to routes on some environments.
2020-07-01 13:51:35 +09:00
Yu Watanabe c3a5025dc6 network: add MACAddress= setting in [SR-IOV] section 2020-07-01 13:51:35 +09:00
Yu Watanabe e64b31c848 network: add VLANProtocol= setting in [SR-IOV] section 2020-07-01 13:51:35 +09:00
Susant Sahani 518cd6b527 network: Introduce SR-IOV
SR-IOV provides the ability to partition a single physical PCI
resource into virtual PCI functions which can then be injected in
to a VM. In the case of network VFs, SR-IOV improves north-south n
etwork performance (that is, traffic with endpoints outside the
host machine) by allowing traffic to bypass the host machine’s network stack.
2020-07-01 13:51:33 +09:00
Susant Sahani 5908ddd763 sd-netlink: Add SR-IOV netlink properties 2020-07-01 13:50:49 +09:00
61 changed files with 1055 additions and 158 deletions

12
NEWS
View File

@ -178,12 +178,12 @@ CHANGES WITH 246 in spe:
traffic). DataBitRate=, DataSamplePoint=, FDMode=, FDNonISO= have
been added to configure various CAN-FD aspects.
* systemd-networkd's [DHCPv6] section gained a new WithoutRA= boolean
setting. If enabled, DHCPv6 will be attempted right-away without
requiring an Router Advertisement packet suggesting it
first. Conversely, the [IPv6AcceptRA] gained a boolean option
DHCPv6Client= that may be used to turn off the DHCPv6 client even if
the RA packets suggest it.
* systemd-networkd's [DHCPv6] section gained a new boolean option
WithoutRA=. When enabled, DHCPv6 will be attempted right-away without
requiring an Router Advertisement packet suggesting it first
(i.e. without the 'M' or 'O' flags set). The [IPv6AcceptRA] section
gained a boolean option DHCPv6Client= that may be used to turn off
the DHCPv6 client even if the RA packets suggest it.
* systemd-networkd's [DHCPv4] section gained a new setting UseGateway=
which may be used to turn off use of the gateway information provided

View File

@ -47,7 +47,7 @@ functionality. Here's why we think that it is not enough for our uses:
* The various EFI implementations implement the boot order/boot item logic to different levels. Some firmware implementations do not offer a boot menu at all and instead unconditionally follow the EFI boot order, booting the first item that is working.
* If the firmware setup is used to reset all data usually all EFI boot entries are lost, making the system entirely unbootable, as the firmware setups generally do not offer a UI to define additional boot items. By placing the menu item information on disk, it is always available, regardless if the BIOS setup data is lost.
* Harddisk images should be moveable between machines and be bootable without requiring explicit EFI variables to be set. This also requires that the list of boot options is defined on disk, and not in EFI variables alone.
* Harddisk images should be movable between machines and be bootable without requiring explicit EFI variables to be set. This also requires that the list of boot options is defined on disk, and not in EFI variables alone.
* EFI is not universal yet (especially on non-x86 platforms), this specification is useful both for EFI and non-EFI boot loaders.
* Many EFI systems disable USB support during early boot to optimize boot times, thus making keyboard input unavailable in the EFI menu. It is thus useful if the OS UI has a standardized way to discover available boot options which can be booted to.

View File

@ -125,7 +125,7 @@ medium. (Moreover it allows to embed additional partitions later on, for
example for allowing a multi-purpose USB stick that contains both a home
directory and a generic storage volume.)
Rationale for including the encrypted user record in the the LUKS2 header:
Rationale for including the encrypted user record in the LUKS2 header:
Linux kernel file system implementations are generally not robust towards
maliciously formatted file systems; there's a good chance that file system
images can be used as attack vectors, exploiting the kernel. Thus it is

View File

@ -36,7 +36,7 @@ interfaces are currently used by dracut and the ArchLinux initrds.
optionally followed (in `argv[2]`, `argv[3]`, … systemd's original command
line options, for example `--log-level=` and similar.
* Storage daemons run from the initrd should follow the the guide on [systemd
* Storage daemons run from the initrd should follow the guide on [systemd
and Storage Daemons for the Root File
System](https://systemd.io/ROOT_STORAGE_DAEMONS) to survive properly from the
boot initrd all the way to the point where systemd jumps back into the initrd

View File

@ -212,10 +212,10 @@ boot, in order to ensure the entropy pool is filled up quickly.
random-seed`](https://www.freedesktop.org/software/systemd/man/bootctl.html#random-seed))
a seed file with an initial seed is placed in a file `/loader/random-seed`
in the ESP. In addition, an identically sized randomized EFI variable called
the the 'system token' is set, which is written to the machine's firmware
NVRAM. During boot, when `systemd-boot` finds both the random seed file and
the system token they are combined and hashed with SHA256 (in counter mode,
to generate sufficient data), to generate a new random seed file to store in
the 'system token' is set, which is written to the machine's firmware NVRAM.
During boot, when `systemd-boot` finds both the random seed file and the
system token they are combined and hashed with SHA256 (in counter mode, to
generate sufficient data), to generate a new random seed file to store in
the ESP as well as a random seed to pass to the OS kernel. The new random
seed file for the ESP is then written to the ESP, ensuring this is completed
before the OS is invoked. Very early during initialization PID 1 will read

View File

@ -689,6 +689,9 @@ sensor:modalias:acpi:KIOX020A*:dmi:*:svnTREKSTOR:pnPRIMEBOOKC11B:*
#########################################
# Umax
#########################################
sensor:modalias:acpi:KIOX000A*:dmi:*:svnUMAX:pnVisionBook10WiPro:*
ACCEL_MOUNT_MATRIX=1, 0, 0; 0, -1, 0; 0, 0, 1
sensor:modalias:acpi:SMO8500*:dmi:*:svnUMAX:pnVisionBook10WiPlus:*
ACCEL_MOUNT_MATRIX=0, -1, 0; -1, 0, 0; 0, 0, 1

View File

@ -401,7 +401,7 @@
<option>--password-change-min=</option> configures how much time has to pass after changing the
password of the user until the password may be changed again. If the user tries to change their
password before this time passes the attempt is refused. <option>--password-change-max=</option>
configures how much time has to pass after the the password is changed until the password expires and
configures how much time has to pass after the password is changed until the password expires and
needs to be changed again. After this time passes any attempts to log in may only proceed after the
password is changed. <option>--password-change-warn=</option> specifies how much earlier than then
the time configured with <option>--password-change-max=</option> the user is warned at login to

View File

@ -83,7 +83,7 @@ node /org/freedesktop/LogControl1 {
<para><varname>LogTarget</varname> describes the log target (mechanism). It should be one of
<literal>console</literal> (log to the console or standard output),
<literal>kmsg</literal> (log to the kernel ring buffer),
<literal>journal</literal> (log the the journal natively, see
<literal>journal</literal> (log to the journal natively, see
<citerefentry><refentrytitle>systemd-journald.service</refentrytitle><manvolnum>8</manvolnum></citerefentry>),
<literal>syslog</literal> (log using the
<citerefentry project='man-pages'><refentrytitle>syslog</refentrytitle><manvolnum>3</manvolnum></citerefentry> call).

View File

@ -64,7 +64,7 @@
<para><function>sd_hwdb_get()</function> queries the <parameter>hwdb</parameter> object created earlier
with <citerefentry><refentrytitle>sd_hwdb_new</refentrytitle><manvolnum>3</manvolnum></citerefentry> for
entries matching the specified string <parameter>modalias</parameter>, and returns the value
corresponding to the the key <parameter>key</parameter>. The value is returned as a
corresponding to the key <parameter>key</parameter>. The value is returned as a
<constant>NUL</constant>-terminated string in <parameter>value</parameter>. It must not be modified by
the caller and is valid as long as a reference to <parameter>hwdb</parameter> is kept. When multiple
patterns in the database match <parameter>modalias</parameter>, the one with the highest priority is

View File

@ -13,7 +13,7 @@
<para>Configuration files are read from directories in <filename>/etc/</filename>,
<filename>/run/</filename>, <filename>/usr/local/lib/</filename>, and <filename>/usr/lib/</filename>, in
order of precedence, as listed in the SYNOPSIS section above. Files must have the the
order of precedence, as listed in the SYNOPSIS section above. Files must have the
<literal>.conf</literal> extension. Files in <filename>/etc/</filename> override files with the same name
in <filename>/run/</filename>, <filename>/usr/local/lib/</filename>, and
<filename>/usr/lib/</filename>. Files in <filename>/run/</filename> override files with the same name

View File

@ -237,6 +237,93 @@
</variablelist>
</refsect1>
<refsect1>
<title>[SR-IOV] Section Options</title>
<para>The <literal>[SR-IOV]</literal> section accepts the
following keys. Specify several <literal>[SR-IOV]</literal>
sections to configure several SR-IOVs. SR-IOV provides the ability to partition a single physical PCI resource
into virtual PCI functions which can then be injected into a VM. In the case of network VFs, SR-IOV improves
north-south network performance (that is, traffic with endpoints outside the host machine) by allowing traffic to
bypass the host machines network stack.</para>
<variablelist class='network-directives'>
<varlistentry>
<term><varname>VirtualFunction=</varname></term>
<listitem>
<para>Specifies a Virtual Function (VF), lightweight PCIe function designed solely to move data
in and out. Takes an unsigned integer in the range 0..2147483646. This option is compulsory.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>VLANId=</varname></term>
<listitem>
<para>Specifies VLAN ID of the virtual function. Takes an unsigned integer in the range 1..4095.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>QualityOfService=</varname></term>
<listitem>
<para>Specifies quality of service of the virtual function. Takes an unsigned integer in the range 1..4294967294.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>VLANProtocol=</varname></term>
<listitem>
<para>Specifies VLAN protocol of the virtual function. Takes <literal>802.1Q</literal> or
<literal>802.1ad</literal>.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>MACSpoofCheck=</varname></term>
<listitem>
<para>Takes a boolean. Controls the MAC spoof checking. When unset, the kernel's default will be used.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>QueryReceiveSideScaling=</varname></term>
<listitem>
<para>Takes a boolean. Toggle the ability of querying the receive side scaling (RSS)
configuration of the virtual function (VF). The VF RSS information like RSS hash key may be
considered sensitive on some devices where this information is shared between VF and the
physical function (PF). When unset, the kernel's default will be used.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>Trust=</varname></term>
<listitem>
<para>Takes a boolean. Allows to set trust mode of the virtual function (VF). When set, VF
users can set a specific feature which may impact security and/or performance. When unset,
the kernel's default will be used.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>LinkState=</varname></term>
<listitem>
<para>Allows to set the link state of the virtual function (VF). Takes a boolean or a
special value <literal>auto</literal>. Setting to <literal>auto</literal> means a
reflection of the physical function (PF) link state, <literal>yes</literal> lets the VF to
communicate with other VFs on this host even if the PF link state is down,
<literal>no</literal> causes the hardware to drop any packets sent by the VF. When unset,
the kernel's default will be used.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>MACAddress=</varname></term>
<listitem>
<para>Specifies the MAC address for the virtual function.</para>
</listitem>
</varlistentry>
</variablelist>
</refsect1>
<refsect1>
<title>[Network] Section Options</title>
@ -2637,20 +2724,20 @@
</varlistentry>
<varlistentry>
<term><varname>LimitSize=</varname></term>
<term><varname>LimitBytes=</varname></term>
<listitem>
<para>Takes the number of bytes that can be queued waiting for tokens to become available.
When the size is suffixed with K, M, or G, it is parsed as Kilobytes, Megabytes, or Gigabytes,
respectively, to the base of 1000. Defaults to unset.</para>
respectively, to the base of 1024. Defaults to unset.</para>
</listitem>
</varlistentry>
<varlistentry>
<term><varname>Burst=</varname></term>
<term><varname>BurstBytes=</varname></term>
<listitem>
<para>Specifies the size of the bucket. This is the maximum amount of bytes that tokens
can be available for instantaneous transfer. When the size is suffixed with K, M, or G, it is
parsed as Kilobytes, Megabytes, or Gigabytes, respectively, to the base of 1000. Defaults to
parsed as Kilobytes, Megabytes, or Gigabytes, respectively, to the base of 1024. Defaults to
unset.</para>
</listitem>
</varlistentry>
@ -2669,7 +2756,7 @@
<listitem>
<para>The Minimum Packet Unit (MPU) determines the minimal token usage (specified in bytes)
for a packet. When suffixed with K, M, or G, the specified size is parsed as Kilobytes,
Megabytes, or Gigabytes, respectively, to the base of 1000. Defaults to zero.</para>
Megabytes, or Gigabytes, respectively, to the base of 1024. Defaults to zero.</para>
</listitem>
</varlistentry>
@ -2686,7 +2773,7 @@
<term><varname>MTUBytes=</varname></term>
<listitem>
<para>Specifies the size of the peakrate bucket. When suffixed with K, M, or G, the specified
size is parsed as Kilobytes, Megabytes, or Gigabytes, respectively, to the base of 1000.
size is parsed as Kilobytes, Megabytes, or Gigabytes, respectively, to the base of 1024.
Defaults to unset.</para>
</listitem>
</varlistentry>
@ -2759,7 +2846,7 @@
<xi:include href="tc.xml" xpointer="qdisc-handle" />
<varlistentry>
<term><varname>LimitSize=</varname></term>
<term><varname>LimitBytes=</varname></term>
<listitem>
<para>Specifies the hard limit on the FIFO size in bytes. The size limit (a buffer size) to prevent it
from overflowing in case it is unable to dequeue packets as quickly as it receives them. When this limit
@ -2828,7 +2915,7 @@
<xi:include href="tc.xml" xpointer="qdisc-handle" />
<varlistentry>
<term><varname>Overhead=</varname></term>
<term><varname>OverheadBytes=</varname></term>
<listitem>
<para>Specifies that bytes to be addeded to the size of each packet. Bytes may be negative.
Takes an integer ranges -64 to 256. Defaults to unset and kernel's default is used.</para>
@ -2918,11 +3005,12 @@
<xi:include href="tc.xml" xpointer="tclass-classid" />
<varlistentry>
<term><varname>Quantum=</varname></term>
<term><varname>QuantumBytes=</varname></term>
<listitem>
<para>Specifies the amount of bytes a flow is allowed to dequeue before the
scheduler moves to the next class. An unsigned integer ranges 1 to 4294967294.
Defaults to the MTU of the interface.</para>
<para>Specifies the amount of bytes a flow is allowed to dequeue before the scheduler moves
to the next class. When suffixed with K, M, or G, the specified size is parsed as Kilobytes,
Megabytes, or Gigabytes, respectively, to the base of 1024. Defaults to the MTU of the
interface.</para>
</listitem>
</varlistentry>
@ -3033,7 +3121,7 @@
</varlistentry>
<varlistentry>
<term><varname>MemoryLimit=</varname></term>
<term><varname>MemoryLimitBytes=</varname></term>
<listitem>
<para>Specifies the limit on the total number of bytes that can be queued in this FQ-CoDel instance.
When suffixed with K, M, or G, the specified size is parsed as Kilobytes, Megabytes, or Gigabytes,
@ -3066,7 +3154,7 @@
</varlistentry>
<varlistentry>
<term><varname>Quantum=</varname></term>
<term><varname>QuantumBytes=</varname></term>
<listitem>
<para>Specifies the number of bytes used as 'deficit' in the fair queuing algorithmtimespan.
When suffixed with K, M, or G, the specified size is parsed as Kilobytes, Megabytes, or Gigabytes,
@ -3118,7 +3206,7 @@
</varlistentry>
<varlistentry>
<term><varname>Quantum=</varname></term>
<term><varname>QuantumBytes=</varname></term>
<listitem>
<para>Specifies the credit per dequeue RR round, i.e. the amount of bytes a flow is allowed
to dequeue at once. When suffixed with K, M, or G, the specified size is parsed as Kilobytes,
@ -3128,7 +3216,7 @@
</varlistentry>
<varlistentry>
<term><varname>InitialQuantum=</varname></term>
<term><varname>InitialQuantumBytes=</varname></term>
<listitem>
<para>Specifies the initial sending rate credit, i.e. the amount of bytes a new flow is
allowed to dequeue initially. When suffixed with K, M, or G, the specified size is parsed as
@ -3359,10 +3447,10 @@
</varlistentry>
<varlistentry>
<term><varname>MaxPacketSize=</varname></term>
<term><varname>MaxPacketBytes=</varname></term>
<listitem>
<para>Specifies the maximum packet size in bytes for the class. When suffixed with K, M, or G, the specified
size is parsed as Kilobytes, Megabytes, or Gigabytes, respectively, to the base of 1000. When unset,
size is parsed as Kilobytes, Megabytes, or Gigabytes, respectively, to the base of 1024. When unset,
the kernel default is used.</para>
</listitem>
</varlistentry>

View File

@ -884,7 +884,7 @@
project='man-pages'><refentrytitle>signal</refentrytitle><manvolnum>7</manvolnum></citerefentry> for
a list of signal names.</para>
<para>Note that this setting does not change the the mapping between numeric exit statuses and their
<para>Note that this setting does not change the mapping between numeric exit statuses and their
names, i.e. regardless how this setting is used 0 will still be mapped to <literal>SUCCESS</literal>
(and thus typically shown as <literal>0/SUCCESS</literal> in tool outputs) and 1 to
<literal>FAILURE</literal> (and thus typically shown as <literal>1/FAILURE</literal>), and so on. It

View File

@ -218,7 +218,7 @@
<para>Note that <command>userdbctl</command> has internal support for NSS-based lookups too. This means
that if neither <constant>io.systemd.Multiplexer</constant> nor
<constant>io.systemd.NameSeviceSwitch</constant> are running look-ups into the the basic user/group
<constant>io.systemd.NameSeviceSwitch</constant> are running look-ups into the basic user/group
databases will still work.</para>
</refsect1>

View File

@ -1130,6 +1130,7 @@ int socket_bind_to_ifname(int fd, const char *ifname) {
int socket_bind_to_ifindex(int fd, int ifindex) {
char ifname[IF_NAMESIZE + 1];
int r;
assert(fd >= 0);
@ -1141,10 +1142,9 @@ int socket_bind_to_ifindex(int fd, int ifindex) {
return 0;
}
if (setsockopt(fd, SOL_SOCKET, SO_BINDTOIFINDEX, &ifindex, sizeof(ifindex)) >= 0)
return 0;
if (errno != ENOPROTOOPT)
return -errno;
r = setsockopt_int(fd, SOL_SOCKET, SO_BINDTOIFINDEX, ifindex);
if (r != -ENOPROTOOPT)
return r;
/* Fall back to SO_BINDTODEVICE on kernels < 5.0 which didn't have SO_BINDTOIFINDEX */
if (!format_ifname(ifindex, ifname))

View File

@ -544,7 +544,7 @@ int bpf_firewall_compile(Unit *u) {
"BPF_F_ALLOW_MULTI is not supported on this manager, not doing BPF firewall on slice units.");
/* Note that when we compile a new firewall we first flush out the access maps and the BPF programs themselves,
* but we reuse the the accounting maps. That way the firewall in effect always maps to the actual
* but we reuse the accounting maps. That way the firewall in effect always maps to the actual
* configuration, but we don't flush out the accounting unnecessarily */
u->ip_bpf_ingress = bpf_program_unref(u->ip_bpf_ingress);

View File

@ -2855,7 +2855,7 @@ static int setup_keyring(
}
out:
/* Revert back uid & gid for the the last time, and exit */
/* Revert back uid & gid for the last time, and exit */
/* no extra logging, as only the first already reported error matters */
if (getuid() != saved_uid)
(void) setreuid(saved_uid, -1);

View File

@ -668,7 +668,7 @@ int config_parse_kill_mode(
if (m == KILL_NONE)
log_syntax(unit, LOG_WARNING, filename, line, 0,
"Unit configured to use KillMode=none. "
"This is unsafe, as it disables systemd's process life-cycle management for the service. "
"This is unsafe, as it disables systemd's process lifecycle management for the service. "
"Please update your service to use a safer KillMode=, such as 'mixed' or 'control-group'. "
"Support for KillMode=none is deprecated and will eventually be removed.");

View File

@ -747,7 +747,7 @@ static int mount_private_dev(MountEntry *m) {
NULSTR_FOREACH(d, devnodes) {
r = clone_device_node(d, temporary_mount, &can_mknod);
/* ENXIO means the the *source* is not a device file, skip creation in that case */
/* ENXIO means the *source* is not a device file, skip creation in that case */
if (r < 0 && r != -ENXIO)
goto fail;
}

View File

@ -499,7 +499,7 @@ static int acquire_home(
return r;
/* Implement our own retry loop here instead of relying on the PAM client's one. That's because it
* might happen that the the record we stored on the host does not match the encryption password of
* might happen that the record we stored on the host does not match the encryption password of
* the LUKS image in case the image was used in a different system where the password was
* changed. In that case it will happen that the LUKS password and the host password are
* different, and we handle that by collecting and passing multiple passwords in that case. Hence we

View File

@ -172,7 +172,7 @@ int user_record_reconcile(
* -REMCHG: identity records are not about the same user
* -ESTALE: embedded identity record is equally new or newer than supplied record
*
* Return the new record to use, which is either the the embedded record updated with the host
* Return the new record to use, which is either the embedded record updated with the host
* binding or the host record. In both cases the secret data is stripped. */
assert(host);

View File

@ -112,7 +112,7 @@ int dhcp6_option_parse_ip6addrs(uint8_t *optval, uint16_t optlen,
int dhcp6_option_parse_domainname(const uint8_t *optval, uint16_t optlen,
char ***str_arr);
int dhcp6_network_bind_udp_socket(int index, struct in6_addr *address);
int dhcp6_network_bind_udp_socket(int ifindex, struct in6_addr *address);
int dhcp6_network_send_udp_socket(int s, struct in6_addr *address,
const void *packet, size_t len);

View File

@ -17,16 +17,16 @@
#include "fd-util.h"
#include "socket-util.h"
int dhcp6_network_bind_udp_socket(int index, struct in6_addr *local_address) {
int dhcp6_network_bind_udp_socket(int ifindex, struct in6_addr *local_address) {
union sockaddr_union src = {
.in6.sin6_family = AF_INET6,
.in6.sin6_port = htobe16(DHCP6_PORT_CLIENT),
.in6.sin6_scope_id = index,
.in6.sin6_scope_id = ifindex,
};
_cleanup_close_ int s = -1;
int r;
assert(index > 0);
assert(ifindex > 0);
assert(local_address);
src.in6.sin6_addr = *local_address;

View File

@ -81,11 +81,11 @@ static int icmp6_bind_router_message(const struct icmp6_filter *filter,
return TAKE_FD(s);
}
int icmp6_bind_router_solicitation(int index) {
int icmp6_bind_router_solicitation(int ifindex) {
struct icmp6_filter filter = {};
struct ipv6_mreq mreq = {
.ipv6mr_multiaddr = IN6ADDR_ALL_NODES_MULTICAST_INIT,
.ipv6mr_interface = index,
.ipv6mr_interface = ifindex,
};
ICMP6_FILTER_SETBLOCKALL(&filter);
@ -94,11 +94,11 @@ int icmp6_bind_router_solicitation(int index) {
return icmp6_bind_router_message(&filter, &mreq);
}
int icmp6_bind_router_advertisement(int index) {
int icmp6_bind_router_advertisement(int ifindex) {
struct icmp6_filter filter = {};
struct ipv6_mreq mreq = {
.ipv6mr_multiaddr = IN6ADDR_ALL_ROUTERS_MULTICAST_INIT,
.ipv6mr_interface = index,
.ipv6mr_interface = ifindex,
};
ICMP6_FILTER_SETBLOCKALL(&filter);

View File

@ -17,8 +17,8 @@
{ { { 0xff, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 } } }
int icmp6_bind_router_solicitation(int index);
int icmp6_bind_router_advertisement(int index);
int icmp6_bind_router_solicitation(int ifindex);
int icmp6_bind_router_advertisement(int ifindex);
int icmp6_send_router_solicitation(int s, const struct ether_addr *ether_addr);
int icmp6_receive(int fd, void *buffer, size_t size, struct in6_addr *dst,
triple_timestamp *timestamp);

View File

@ -159,7 +159,7 @@ int sd_dhcp6_client_set_callback(
int sd_dhcp6_client_set_ifindex(sd_dhcp6_client *client, int ifindex) {
assert_return(client, -EINVAL);
assert_return(ifindex >= -1, -EINVAL);
assert_return(ifindex > 0, -EINVAL);
assert_return(IN_SET(client->state, DHCP6_STATE_STOPPED), -EBUSY);
client->ifindex = ifindex;

View File

@ -415,7 +415,7 @@ _public_ int sd_radv_start(sd_radv *ra) {
_public_ int sd_radv_set_ifindex(sd_radv *ra, int ifindex) {
assert_return(ra, -EINVAL);
assert_return(ifindex >= -1, -EINVAL);
assert_return(ifindex > 0, -EINVAL);
if (ra->state != SD_RADV_STATE_IDLE)
return -EBUSY;

View File

@ -258,7 +258,7 @@ int dhcp_network_send_raw_socket(int s, const union sockaddr_union *link, const
}
int dhcp_network_bind_raw_socket(
int index,
int ifindex,
union sockaddr_union *link,
uint32_t id,
const uint8_t *addr, size_t addr_len,

View File

@ -30,7 +30,7 @@ static struct ether_addr mac_addr = {
static sd_event_source *hangcheck;
static int test_dhcp_fd[2];
static int test_index = 42;
static int test_ifindex = 42;
static int test_client_message_num;
static be32_t test_iaid = 0;
static uint8_t test_duid[14] = { };
@ -48,7 +48,7 @@ static int test_client_basic(sd_event *e) {
assert_se(sd_dhcp6_client_set_ifindex(client, 15) == 0);
assert_se(sd_dhcp6_client_set_ifindex(client, -42) == -EINVAL);
assert_se(sd_dhcp6_client_set_ifindex(client, -1) == 0);
assert_se(sd_dhcp6_client_set_ifindex(client, -1) == -EINVAL);
assert_se(sd_dhcp6_client_set_ifindex(client, 42) >= 0);
assert_se(sd_dhcp6_client_set_mac(client, (const uint8_t *) &mac_addr,
@ -877,8 +877,8 @@ int dhcp6_network_send_udp_socket(int s, struct in6_addr *server_address,
return len;
}
int dhcp6_network_bind_udp_socket(int index, struct in6_addr *local_address) {
assert_se(index == test_index);
int dhcp6_network_bind_udp_socket(int ifindex, struct in6_addr *local_address) {
assert_se(ifindex == test_ifindex);
if (socketpair(AF_UNIX, SOCK_STREAM | SOCK_CLOEXEC | SOCK_NONBLOCK, 0, test_dhcp_fd) < 0)
return -errno;
@ -899,7 +899,7 @@ static int test_client_solicit(sd_event *e) {
assert_se(sd_dhcp6_client_attach_event(client, e, 0) >= 0);
assert_se(sd_dhcp6_client_set_ifindex(client, test_index) == 0);
assert_se(sd_dhcp6_client_set_ifindex(client, test_ifindex) == 0);
assert_se(sd_dhcp6_client_set_mac(client, (const uint8_t *) &mac_addr,
sizeof (mac_addr),
ARPHRD_ETHER) >= 0);

View File

@ -78,7 +78,7 @@ int arp_send_announcement(int fd, int ifindex,
return arp_network_send_raw_socket(fd, ifindex, &ea);
}
int arp_network_bind_raw_socket(int index, be32_t address, const struct ether_addr *eth_mac) {
int arp_network_bind_raw_socket(int ifindex, be32_t address, const struct ether_addr *eth_mac) {
if (socketpair(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC | SOCK_NONBLOCK, 0, test_fd) < 0)
return -errno;

View File

@ -159,8 +159,8 @@ static void test_radv(void) {
assert_se(ra);
assert_se(sd_radv_set_ifindex(NULL, 0) < 0);
assert_se(sd_radv_set_ifindex(ra, 0) >= 0);
assert_se(sd_radv_set_ifindex(ra, -1) >= 0);
assert_se(sd_radv_set_ifindex(ra, 0) < 0);
assert_se(sd_radv_set_ifindex(ra, -1) < 0);
assert_se(sd_radv_set_ifindex(ra, -2) < 0);
assert_se(sd_radv_set_ifindex(ra, 42) >= 0);
@ -219,12 +219,12 @@ static void test_radv(void) {
assert_se(!ra);
}
int icmp6_bind_router_solicitation(int index) {
int icmp6_bind_router_solicitation(int ifindex) {
return -ENOSYS;
}
int icmp6_bind_router_advertisement(int index) {
assert_se(index == 42);
int icmp6_bind_router_advertisement(int ifindex) {
assert_se(ifindex == 42);
return test_fd[1];
}

View File

@ -174,8 +174,8 @@ static int test_rs_hangcheck(sd_event_source *s, uint64_t usec,
return 0;
}
int icmp6_bind_router_solicitation(int index) {
assert_se(index == 42);
int icmp6_bind_router_solicitation(int ifindex) {
assert_se(ifindex == 42);
if (socketpair(AF_UNIX, SOCK_DGRAM | SOCK_CLOEXEC | SOCK_NONBLOCK, 0, test_fd) < 0)
return -errno;
@ -183,8 +183,7 @@ int icmp6_bind_router_solicitation(int index) {
return test_fd[0];
}
int icmp6_bind_router_advertisement(int index) {
int icmp6_bind_router_advertisement(int ifindex) {
return -ENOSYS;
}

View File

@ -537,6 +537,43 @@ static const NLTypeSystem rtnl_prop_list_type_system = {
.types = rtnl_prop_list_types,
};
static const NLType rtnl_vf_vlan_list_types[] = {
[IFLA_VF_VLAN_INFO] = { .size = sizeof(struct ifla_vf_vlan_info) },
};
static const NLTypeSystem rtnl_vf_vlan_type_system = {
.count = ELEMENTSOF(rtnl_vf_vlan_list_types),
.types = rtnl_vf_vlan_list_types,
};
static const NLType rtnl_vf_vlan_info_types[] = {
[IFLA_VF_MAC] = { .size = sizeof(struct ifla_vf_mac) },
[IFLA_VF_VLAN] = { .size = sizeof(struct ifla_vf_vlan) },
[IFLA_VF_VLAN_LIST] = { .type = NETLINK_TYPE_NESTED, .type_system = &rtnl_vf_vlan_type_system},
[IFLA_VF_TX_RATE] = { .size = sizeof(struct ifla_vf_tx_rate) },
[IFLA_VF_SPOOFCHK] = { .size = sizeof(struct ifla_vf_spoofchk) },
[IFLA_VF_RATE] = { .size = sizeof(struct ifla_vf_rate) },
[IFLA_VF_LINK_STATE] = { .size = sizeof(struct ifla_vf_link_state) },
[IFLA_VF_RSS_QUERY_EN] = { .size = sizeof(struct ifla_vf_rss_query_en) },
[IFLA_VF_TRUST] = { .size = sizeof(struct ifla_vf_trust) },
[IFLA_VF_IB_NODE_GUID] = { .size = sizeof(struct ifla_vf_guid) },
[IFLA_VF_IB_PORT_GUID] = { .size = sizeof(struct ifla_vf_guid) },
};
static const NLTypeSystem rtnl_vf_vlan_info_type_system = {
.count = ELEMENTSOF(rtnl_vf_vlan_info_types),
.types = rtnl_vf_vlan_info_types,
};
static const NLType rtnl_link_io_srv_types[] = {
[IFLA_VF_INFO] = { .type = NETLINK_TYPE_NESTED, .type_system = &rtnl_vf_vlan_info_type_system },
};
static const NLTypeSystem rtnl_io_srv_type_system = {
.count = ELEMENTSOF(rtnl_link_io_srv_types),
.types = rtnl_link_io_srv_types,
};
static const NLType rtnl_link_types[] = {
[IFLA_ADDRESS] = { .type = NETLINK_TYPE_ETHER_ADDR },
[IFLA_BROADCAST] = { .type = NETLINK_TYPE_ETHER_ADDR },
@ -564,10 +601,8 @@ static const NLType rtnl_link_types[] = {
[IFLA_LINKINFO] = { .type = NETLINK_TYPE_NESTED, .type_system = &rtnl_link_info_type_system },
[IFLA_NET_NS_PID] = { .type = NETLINK_TYPE_U32 },
[IFLA_IFALIAS] = { .type = NETLINK_TYPE_STRING, .size = IFALIASZ - 1 },
/*
[IFLA_NUM_VF],
[IFLA_VFINFO_LIST] = {. type = NETLINK_TYPE_NESTED, },
*/
[IFLA_NUM_VF] = { .type = NETLINK_TYPE_U32 },
[IFLA_VFINFO_LIST] = { .type = NETLINK_TYPE_NESTED, .type_system = &rtnl_io_srv_type_system },
[IFLA_STATS64] = { .size = sizeof(struct rtnl_link_stats64) },
/*
[IFLA_VF_PORTS] = { .type = NETLINK_TYPE_NESTED },

View File

@ -468,7 +468,7 @@ static bool validate_runtime_directory(pam_handle_t *handle, const char *path, u
/* Some extra paranoia: let's not set $XDG_RUNTIME_DIR if the directory we'd set it to isn't actually
* set up properly for us. This is supposed to provide a careful safety net for supporting su/sudo
* type transitions: in that case the UID changes, but the session and thus the user owning it
* doesn't change. Since the $XDG_RUNTIME_DIR life-cycle is bound to the session's user being logged
* doesn't change. Since the $XDG_RUNTIME_DIR lifecycle is bound to the session's user being logged
* in at least once we should be particularly careful when setting the environment variable, since
* otherwise we might end up setting $XDG_RUNTIME_DIR to some directory owned by the wrong user. */

View File

@ -105,6 +105,8 @@ sources = files('''
networkd-routing-policy-rule.h
networkd-speed-meter.c
networkd-speed-meter.h
networkd-sriov.c
networkd-sriov.h
networkd-util.c
networkd-util.h
networkd-wifi.c

View File

@ -3,6 +3,7 @@
#include <netinet/in.h>
#include <linux/if.h>
#include <linux/if_arp.h>
#include <linux/if_link.h>
#include <unistd.h>
#include "alloc-util.h"
@ -31,6 +32,7 @@
#include "networkd-manager.h"
#include "networkd-ndisc.h"
#include "networkd-neighbor.h"
#include "networkd-sriov.h"
#include "networkd-radv.h"
#include "networkd-routing-policy-rule.h"
#include "networkd-wifi.h"
@ -1127,6 +1129,9 @@ void link_check_ready(Link *link) {
if (!link->tc_configured)
return;
if (!link->sr_iov_configured)
return;
if (link_has_carrier(link) || !link->network->configure_without_carrier) {
if (link_ipv4ll_enabled(link, ADDRESS_FAMILY_IPV4) && !link->ipv4ll_address)
@ -2838,6 +2843,28 @@ static int link_configure_traffic_control(Link *link) {
return 0;
}
static int link_configure_sr_iov(Link *link) {
SRIOV *sr_iov;
Iterator i;
int r;
link->sr_iov_configured = false;
link->sr_iov_messages = 0;
ORDERED_HASHMAP_FOREACH(sr_iov, link->network->sr_iov_by_section, i) {
r = sr_iov_configure(link, sr_iov);
if (r < 0)
return r;
}
if (link->sr_iov_messages == 0)
link->sr_iov_configured = true;
else
log_link_debug(link, "Configuring SR-IOV");
return 0;
}
static int link_configure(Link *link) {
int r;
@ -2849,6 +2876,10 @@ static int link_configure(Link *link) {
if (r < 0)
return r;
r = link_configure_sr_iov(link);
if (r < 0)
return r;
if (link->iftype == ARPHRD_CAN)
return link_configure_can(link);

View File

@ -82,6 +82,7 @@ typedef struct Link {
unsigned routing_policy_rule_messages;
unsigned routing_policy_rule_remove_messages;
unsigned tc_messages;
unsigned sr_iov_messages;
unsigned enslaving;
Set *addresses;
@ -118,6 +119,7 @@ typedef struct Link {
bool static_nexthops_configured:1;
bool routing_policy_rules_configured:1;
bool tc_configured:1;
bool sr_iov_configured:1;
bool setting_mtu:1;
bool setting_genmode:1;
bool ipv6_mtu_set:1;

View File

@ -15,6 +15,7 @@ _Pragma("GCC diagnostic ignored \"-Wimplicit-fallthrough\"")
#include "networkd-ipv4ll.h"
#include "networkd-ndisc.h"
#include "networkd-network.h"
#include "networkd-sriov.h"
#include "qdisc.h"
#include "tclass.h"
#include "vlan-util.h"
@ -53,6 +54,15 @@ Link.Multicast, config_parse_tristate,
Link.AllMulticast, config_parse_tristate, 0, offsetof(Network, allmulticast)
Link.Unmanaged, config_parse_bool, 0, offsetof(Network, unmanaged)
Link.RequiredForOnline, config_parse_required_for_online, 0, 0
SR-IOV.VirtualFunction, config_parse_sr_iov_uint32, 0, 0
SR-IOV.VLANId, config_parse_sr_iov_uint32, 0, 0
SR-IOV.QualityOfService, config_parse_sr_iov_uint32, 0, 0
SR-IOV.VLANProtocol, config_parse_sr_iov_vlan_proto, 0, 0
SR-IOV.MACSpoofCheck, config_parse_sr_iov_boolean, 0, 0
SR-IOV.QueryReceiveSideScaling, config_parse_sr_iov_boolean, 0, 0
SR-IOV.Trust, config_parse_sr_iov_boolean, 0, 0
SR-IOV.LinkState, config_parse_sr_iov_link_state, 0, 0
SR-IOV.MACAddress, config_parse_sr_iov_mac, 0, 0
Network.Description, config_parse_string, 0, offsetof(Network, description)
Network.Bridge, config_parse_ifname, 0, offsetof(Network, bridge_name)
Network.Bond, config_parse_ifname, 0, offsetof(Network, bond_name)
@ -294,11 +304,11 @@ QDisc.Parent, config_parse_qdisc_parent,
QDisc.Handle, config_parse_qdisc_handle, _QDISC_KIND_INVALID, 0
BFIFO.Parent, config_parse_qdisc_parent, QDISC_KIND_BFIFO, 0
BFIFO.Handle, config_parse_qdisc_handle, QDISC_KIND_BFIFO, 0
BFIFO.LimitSize, config_parse_bfifo_size, QDISC_KIND_BFIFO, 0
BFIFO.LimitBytes, config_parse_bfifo_size, QDISC_KIND_BFIFO, 0
CAKE.Parent, config_parse_qdisc_parent, QDISC_KIND_CAKE, 0
CAKE.Handle, config_parse_qdisc_handle, QDISC_KIND_CAKE, 0
CAKE.Bandwidth, config_parse_cake_bandwidth, QDISC_KIND_CAKE, 0
CAKE.Overhead, config_parse_cake_overhead, QDISC_KIND_CAKE, 0
CAKE.OverheadBytes, config_parse_cake_overhead, QDISC_KIND_CAKE, 0
ControlledDelay.Parent, config_parse_qdisc_parent, QDISC_KIND_CODEL, 0
ControlledDelay.Handle, config_parse_qdisc_handle, QDISC_KIND_CODEL, 0
ControlledDelay.PacketLimit, config_parse_controlled_delay_u32, QDISC_KIND_CODEL, 0
@ -310,7 +320,7 @@ DeficitRoundRobinScheduler.Parent, config_parse_qdisc_parent,
DeficitRoundRobinScheduler.Handle, config_parse_qdisc_handle, QDISC_KIND_DRR, 0
DeficitRoundRobinSchedulerClass.Parent, config_parse_tclass_parent, TCLASS_KIND_DRR, 0
DeficitRoundRobinSchedulerClass.ClassId, config_parse_tclass_classid, TCLASS_KIND_DRR, 0
DeficitRoundRobinSchedulerClass.Quantum, config_parse_drr_size, TCLASS_KIND_DRR, 0
DeficitRoundRobinSchedulerClass.QuantumBytes, config_parse_drr_size, TCLASS_KIND_DRR, 0
EnhancedTransmissionSelection.Parent, config_parse_qdisc_parent, QDISC_KIND_ETS, 0
EnhancedTransmissionSelection.Handle, config_parse_qdisc_handle, QDISC_KIND_ETS, 0
EnhancedTransmissionSelection.Bands, config_parse_ets_u8, QDISC_KIND_ETS, 0
@ -330,13 +340,13 @@ QuickFairQueueing.Handle, config_parse_qdisc_handle,
QuickFairQueueingClass.Parent, config_parse_tclass_parent, TCLASS_KIND_QFQ, 0
QuickFairQueueingClass.ClassId, config_parse_tclass_classid, TCLASS_KIND_QFQ, 0
QuickFairQueueingClass.Weight, config_parse_quick_fair_queueing_weight, TCLASS_KIND_QFQ, 0
QuickFairQueueingClass.MaxPacketSize, config_parse_quick_fair_queueing_max_packet, TCLASS_KIND_QFQ, 0
QuickFairQueueingClass.MaxPacketBytes, config_parse_quick_fair_queueing_max_packet, TCLASS_KIND_QFQ, 0
FairQueueing.Parent, config_parse_qdisc_parent, QDISC_KIND_FQ, 0
FairQueueing.Handle, config_parse_qdisc_handle, QDISC_KIND_FQ, 0
FairQueueing.PacketLimit, config_parse_fair_queueing_u32, QDISC_KIND_FQ, 0
FairQueueing.FlowLimit, config_parse_fair_queueing_u32, QDISC_KIND_FQ, 0
FairQueueing.Quantum, config_parse_fair_queueing_size, QDISC_KIND_FQ, 0
FairQueueing.InitialQuantum, config_parse_fair_queueing_size, QDISC_KIND_FQ, 0
FairQueueing.QuantumBytes, config_parse_fair_queueing_size, QDISC_KIND_FQ, 0
FairQueueing.InitialQuantumBytes, config_parse_fair_queueing_size, QDISC_KIND_FQ, 0
FairQueueing.MaximumRate, config_parse_fair_queueing_max_rate, QDISC_KIND_FQ, 0
FairQueueing.Buckets, config_parse_fair_queueing_u32, QDISC_KIND_FQ, 0
FairQueueing.OrphanMask, config_parse_fair_queueing_u32, QDISC_KIND_FQ, 0
@ -345,9 +355,9 @@ FairQueueing.CEThresholdSec, config_parse_fair_queueing_usec,
FairQueueingControlledDelay.Parent, config_parse_qdisc_parent, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.Handle, config_parse_qdisc_handle, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.PacketLimit, config_parse_fair_queueing_controlled_delay_u32, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.MemoryLimit, config_parse_fair_queueing_controlled_delay_size, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.MemoryLimitBytes, config_parse_fair_queueing_controlled_delay_size, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.Flows, config_parse_fair_queueing_controlled_delay_u32, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.Quantum, config_parse_fair_queueing_controlled_delay_size, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.QuantumBytes, config_parse_fair_queueing_controlled_delay_size, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.TargetSec, config_parse_fair_queueing_controlled_delay_usec, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.IntervalSec, config_parse_fair_queueing_controlled_delay_usec, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.CEThresholdSec, config_parse_fair_queueing_controlled_delay_usec, QDISC_KIND_FQ_CODEL, 0
@ -392,12 +402,12 @@ StochasticFairnessQueueing.Handle, config_parse_qdisc_handle,
StochasticFairnessQueueing.PerturbPeriodSec, config_parse_stochastic_fairness_queueing_perturb_period, QDISC_KIND_SFQ, 0
TokenBucketFilter.Parent, config_parse_qdisc_parent, QDISC_KIND_TBF, 0
TokenBucketFilter.Handle, config_parse_qdisc_handle, QDISC_KIND_TBF, 0
TokenBucketFilter.Rate, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.Burst, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.LimitSize, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.Rate, config_parse_token_bucket_filter_rate, QDISC_KIND_TBF, 0
TokenBucketFilter.BurstBytes, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.LimitBytes, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.MTUBytes, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.MPUBytes, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.PeakRate, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.PeakRate, config_parse_token_bucket_filter_rate, QDISC_KIND_TBF, 0
TokenBucketFilter.LatencySec, config_parse_token_bucket_filter_latency, QDISC_KIND_TBF, 0
TrivialLinkEqualizer.Parent, config_parse_qdisc_parent, QDISC_KIND_TEQL, 0
TrivialLinkEqualizer.Handle, config_parse_qdisc_handle, QDISC_KIND_TEQL, 0
@ -436,3 +446,9 @@ TrafficControlQueueingDiscipline.NetworkEmulatorDelayJitterSec, config_parse_net
TrafficControlQueueingDiscipline.NetworkEmulatorLossRate, config_parse_network_emulator_rate, 0, 0
TrafficControlQueueingDiscipline.NetworkEmulatorDuplicateRate, config_parse_network_emulator_rate, 0, 0
TrafficControlQueueingDiscipline.NetworkEmulatorPacketLimit, config_parse_network_emulator_packet_limit, 0, 0
FairQueueing.Quantum, config_parse_fair_queueing_size, QDISC_KIND_FQ, 0
FairQueueing.InitialQuantum, config_parse_fair_queueing_size, QDISC_KIND_FQ, 0
FairQueueingControlledDelay.MemoryLimit, config_parse_fair_queueing_controlled_delay_size, QDISC_KIND_FQ_CODEL, 0
FairQueueingControlledDelay.Quantum, config_parse_fair_queueing_controlled_delay_size, QDISC_KIND_FQ_CODEL, 0
TokenBucketFilter.Burst, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0
TokenBucketFilter.LimitSize, config_parse_token_bucket_filter_size, QDISC_KIND_TBF, 0

View File

@ -16,6 +16,7 @@
#include "network-internal.h"
#include "networkd-manager.h"
#include "networkd-network.h"
#include "networkd-sriov.h"
#include "parse-util.h"
#include "path-lookup.h"
#include "set.h"
@ -158,6 +159,7 @@ int network_verify(Network *network) {
Route *route, *route_next;
FdbEntry *fdb, *fdb_next;
TrafficControl *tc;
SRIOV *sr_iov;
Iterator i;
assert(network);
@ -330,6 +332,10 @@ int network_verify(Network *network) {
if (traffic_control_section_verify(tc, &has_root, &has_clsact) < 0)
traffic_control_free(tc);
ORDERED_HASHMAP_FOREACH(sr_iov, network->sr_iov_by_section, i)
if (sr_iov_section_verify(sr_iov) < 0)
sr_iov_free(sr_iov);
return 0;
}
@ -484,6 +490,7 @@ int network_load_one(Manager *manager, OrderedHashmap **networks, const char *fi
filename, NETWORK_DIRS, dropin_dirname,
"Match\0"
"Link\0"
"SR-IOV\0"
"Network\0"
"Address\0"
"Neighbor\0"
@ -731,6 +738,7 @@ static Network *network_free(Network *network) {
hashmap_free(network->prefixes_by_section);
hashmap_free(network->route_prefixes_by_section);
hashmap_free(network->rules_by_section);
ordered_hashmap_free_with_destructor(network->sr_iov_by_section, sr_iov_free);
ordered_hashmap_free_with_destructor(network->tc_by_section, traffic_control_free);
if (network->manager &&

View File

@ -312,6 +312,7 @@ struct Network {
Hashmap *route_prefixes_by_section;
Hashmap *rules_by_section;
OrderedHashmap *tc_by_section;
OrderedHashmap *sr_iov_by_section;
/* All kinds of DNS configuration */
struct in_addr_data *dns;

View File

@ -0,0 +1,501 @@
/* SPDX-License-Identifier: LGPL-2.1+
* Copyright © 2020 VMware, Inc. */
#include "alloc-util.h"
#include "netlink-util.h"
#include "networkd-manager.h"
#include "networkd-sriov.h"
#include "parse-util.h"
#include "set.h"
#include "string-util.h"
static int sr_iov_new(SRIOV **ret) {
SRIOV *sr_iov;
sr_iov = new(SRIOV, 1);
if (!sr_iov)
return -ENOMEM;
*sr_iov = (SRIOV) {
.vf = (uint32_t) -1,
.vlan_proto = ETH_P_8021Q,
.vf_spoof_check_setting = -1,
.trust = -1,
.query_rss = -1,
.link_state = _SR_IOV_LINK_STATE_INVALID,
};
*ret = TAKE_PTR(sr_iov);
return 0;
}
static int sr_iov_new_static(Network *network, const char *filename, unsigned section_line, SRIOV **ret) {
_cleanup_(network_config_section_freep) NetworkConfigSection *n = NULL;
_cleanup_(sr_iov_freep) SRIOV *sr_iov = NULL;
SRIOV *existing = NULL;
int r;
assert(network);
assert(ret);
assert(filename);
assert(section_line > 0);
r = network_config_section_new(filename, section_line, &n);
if (r < 0)
return r;
existing = ordered_hashmap_get(network->sr_iov_by_section, n);
if (existing) {
*ret = existing;
return 0;
}
r = sr_iov_new(&sr_iov);
if (r < 0)
return r;
sr_iov->network = network;
sr_iov->section = TAKE_PTR(n);
r = ordered_hashmap_ensure_allocated(&network->sr_iov_by_section, &network_config_hash_ops);
if (r < 0)
return r;
r = ordered_hashmap_put(network->sr_iov_by_section, sr_iov->section, sr_iov);
if (r < 0)
return r;
*ret = TAKE_PTR(sr_iov);
return 0;
}
SRIOV *sr_iov_free(SRIOV *sr_iov) {
if (!sr_iov)
return NULL;
if (sr_iov->network && sr_iov->section)
ordered_hashmap_remove(sr_iov->network->sr_iov_by_section, sr_iov->section);
network_config_section_free(sr_iov->section);
return mfree(sr_iov);
}
static int sr_iov_handler(sd_netlink *rtnl, sd_netlink_message *m, Link *link) {
int r;
assert(link);
assert(link->sr_iov_messages > 0);
link->sr_iov_messages--;
if (IN_SET(link->state, LINK_STATE_FAILED, LINK_STATE_LINGER))
return 1;
r = sd_netlink_message_get_errno(m);
if (r < 0 && r != -EEXIST) {
log_link_message_error_errno(link, m, r, "Could not set up SR-IOV");
link_enter_failed(link);
return 1;
}
if (link->sr_iov_messages == 0) {
log_link_debug(link, "SR-IOV configured");
link->sr_iov_configured = true;
link_check_ready(link);
}
return 1;
}
int sr_iov_configure(Link *link, SRIOV *sr_iov) {
_cleanup_(sd_netlink_message_unrefp) sd_netlink_message *req = NULL;
int r;
assert(link);
assert(link->manager);
assert(link->manager->rtnl);
assert(link->ifindex > 0);
log_link_debug(link, "Setting SR-IOV virtual function %"PRIu32, sr_iov->vf);
r = sd_rtnl_message_new_link(link->manager->rtnl, &req, RTM_SETLINK, link->ifindex);
if (r < 0)
return log_link_error_errno(link, r, "Could not allocate RTM_SETLINK message: %m");
r = sd_netlink_message_open_container(req, IFLA_VFINFO_LIST);
if (r < 0)
return log_link_error_errno(link, r, "Could not open IFLA_VFINFO_LIST container: %m");
r = sd_netlink_message_open_container(req, IFLA_VF_INFO);
if (r < 0)
return log_link_error_errno(link, r, "Could not open IFLA_VF_INFO container: %m");
if (!ether_addr_is_null(&sr_iov->mac)) {
struct ifla_vf_mac ivm = {
.vf = sr_iov->vf,
};
memcpy(ivm.mac, &sr_iov->mac, ETH_ALEN);
r = sd_netlink_message_append_data(req, IFLA_VF_MAC, &ivm, sizeof(struct ifla_vf_mac));
if (r < 0)
return log_link_error_errno(link, r, "Could not append IFLA_VF_MAC: %m");
}
if (sr_iov->vf_spoof_check_setting >= 0) {
struct ifla_vf_spoofchk ivs = {
.vf = sr_iov->vf,
.setting = sr_iov->vf_spoof_check_setting,
};
r = sd_netlink_message_append_data(req, IFLA_VF_SPOOFCHK, &ivs, sizeof(struct ifla_vf_spoofchk));
if (r < 0)
return log_link_error_errno(link, r, "Could not append IFLA_VF_SPOOFCHK: %m");
}
if (sr_iov->query_rss >= 0) {
struct ifla_vf_rss_query_en ivs = {
.vf = sr_iov->vf,
.setting = sr_iov->query_rss,
};
r = sd_netlink_message_append_data(req, IFLA_VF_RSS_QUERY_EN, &ivs, sizeof(struct ifla_vf_rss_query_en));
if (r < 0)
return log_link_error_errno(link, r, "Could not append IFLA_VF_RSS_QUERY_EN: %m");
}
if (sr_iov->trust >= 0) {
struct ifla_vf_trust ivt = {
.vf = sr_iov->vf,
.setting = sr_iov->trust,
};
r = sd_netlink_message_append_data(req, IFLA_VF_TRUST, &ivt, sizeof(struct ifla_vf_trust));
if (r < 0)
return log_link_error_errno(link, r, "Could not append IFLA_VF_TRUST: %m");
}
if (sr_iov->link_state >= 0) {
struct ifla_vf_link_state ivl = {
.vf = sr_iov->vf,
.link_state = sr_iov->link_state,
};
r = sd_netlink_message_append_data(req, IFLA_VF_LINK_STATE, &ivl, sizeof(struct ifla_vf_link_state));
if (r < 0)
return log_link_error_errno(link, r, "Could not append IFLA_VF_LINK_STATE: %m");
}
if (sr_iov->vlan > 0) {
/* Because of padding, first the buffer must be initialized with 0. */
struct ifla_vf_vlan_info ivvi = {};
ivvi.vf = sr_iov->vf;
ivvi.vlan = sr_iov->vlan;
ivvi.qos = sr_iov->qos;
ivvi.vlan_proto = htobe16(sr_iov->vlan_proto);
r = sd_netlink_message_open_container(req, IFLA_VF_VLAN_LIST);
if (r < 0)
return log_link_error_errno(link, r, "Could not open IFLA_VF_VLAN_LIST container: %m");
r = sd_netlink_message_append_data(req, IFLA_VF_VLAN_INFO, &ivvi, sizeof(struct ifla_vf_vlan_info));
if (r < 0)
return log_link_error_errno(link, r, "Could not append IFLA_VF_VLAN_INFO: %m");
r = sd_netlink_message_close_container(req);
if (r < 0)
return log_link_error_errno(link, r, "Could not close IFLA_VF_VLAN_LIST container: %m");
}
r = sd_netlink_message_close_container(req);
if (r < 0)
return log_link_error_errno(link, r, "Could not close IFLA_VF_INFO container: %m");
r = sd_netlink_message_close_container(req);
if (r < 0)
return log_link_error_errno(link, r, "Could not close IFLA_VFINFO_LIST container: %m");
r = netlink_call_async(link->manager->rtnl, NULL, req, sr_iov_handler,
link_netlink_destroy_callback, link);
if (r < 0)
return log_link_error_errno(link, r, "Could not send rtnetlink message: %m");
link_ref(link);
link->sr_iov_messages++;
return 0;
}
int sr_iov_section_verify(SRIOV *sr_iov) {
assert(sr_iov);
if (section_is_invalid(sr_iov->section))
return -EINVAL;
if (sr_iov->vf == (uint32_t) -1)
return log_warning_errno(SYNTHETIC_ERRNO(EINVAL),
"%s: [SRIOV] section without VirtualFunction= field configured. "
"Ignoring [SRIOV] section from line %u.",
sr_iov->section->filename, sr_iov->section->line);
return 0;
}
int config_parse_sr_iov_uint32(
const char *unit,
const char *filename,
unsigned line,
const char *section,
unsigned section_line,
const char *lvalue,
int ltype,
const char *rvalue,
void *data,
void *userdata) {
_cleanup_(sr_iov_free_or_set_invalidp) SRIOV *sr_iov = NULL;
Network *network = data;
uint32_t k;
int r;
assert(filename);
assert(lvalue);
assert(rvalue);
assert(data);
r = sr_iov_new_static(network, filename, section_line, &sr_iov);
if (r < 0)
return r;
if (isempty(rvalue)) {
if (streq(lvalue, "VirtualFunction"))
sr_iov->vf = (uint32_t) -1;
else if (streq(lvalue, "VLANId"))
sr_iov->vlan = 0;
else if (streq(lvalue, "QualityOfService"))
sr_iov->qos = 0;
else
assert_not_reached("Invalid lvalue");
TAKE_PTR(sr_iov);
return 0;
}
r = safe_atou32(rvalue, &k);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse SR-IOV '%s=', ignoring assignment: %s", lvalue, rvalue);
return 0;
}
if (streq(lvalue, "VLANId")) {
if (k == 0 || k > 4095) {
log_syntax(unit, LOG_ERR, filename, line, 0, "Invalid SR-IOV VLANId: %d", k);
return 0;
}
sr_iov->vlan = k;
} else if (streq(lvalue, "VirtualFunction")) {
if (k >= INT_MAX) {
log_syntax(unit, LOG_ERR, filename, line, 0, "Invalid SR-IOV virtual function: %d", k);
return 0;
}
sr_iov->vf = k;
} else if (streq(lvalue, "QualityOfService"))
sr_iov->qos = k;
else
assert_not_reached("Invalid lvalue");
TAKE_PTR(sr_iov);
return 0;
}
int config_parse_sr_iov_vlan_proto(
const char *unit,
const char *filename,
unsigned line,
const char *section,
unsigned section_line,
const char *lvalue,
int ltype,
const char *rvalue,
void *data,
void *userdata) {
_cleanup_(sr_iov_free_or_set_invalidp) SRIOV *sr_iov = NULL;
Network *network = data;
int r;
assert(filename);
assert(lvalue);
assert(rvalue);
assert(data);
r = sr_iov_new_static(network, filename, section_line, &sr_iov);
if (r < 0)
return r;
if (isempty(rvalue) || streq(rvalue, "802.1Q"))
sr_iov->vlan_proto = ETH_P_8021Q;
else if (streq(rvalue, "802.1ad"))
sr_iov->vlan_proto = ETH_P_8021AD;
else {
log_syntax(unit, LOG_ERR, filename, line, 0,
"Invalid SR-IOV '%s=', ignoring assignment: %s", lvalue, rvalue);
return 0;
}
TAKE_PTR(sr_iov);
return 0;
}
int config_parse_sr_iov_link_state(
const char *unit,
const char *filename,
unsigned line,
const char *section,
unsigned section_line,
const char *lvalue,
int ltype,
const char *rvalue,
void *data,
void *userdata) {
_cleanup_(sr_iov_free_or_set_invalidp) SRIOV *sr_iov = NULL;
Network *network = data;
int r;
assert(filename);
assert(lvalue);
assert(rvalue);
assert(data);
r = sr_iov_new_static(network, filename, section_line, &sr_iov);
if (r < 0)
return r;
/* Unfortunately, SR_IOV_LINK_STATE_DISABLE is 2, not 0. So, we cannot use
* DEFINE_STRING_TABLE_LOOKUP_WITH_BOOLEAN() macro. */
if (isempty(rvalue)) {
sr_iov->link_state = _SR_IOV_LINK_STATE_INVALID;
TAKE_PTR(sr_iov);
return 0;
}
if (streq(rvalue, "auto")) {
sr_iov->link_state = SR_IOV_LINK_STATE_AUTO;
TAKE_PTR(sr_iov);
return 0;
}
r = parse_boolean(rvalue);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse SR-IOV '%s=', ignoring assignment: %s", lvalue, rvalue);
return 0;
}
sr_iov->link_state = r ? SR_IOV_LINK_STATE_ENABLE : SR_IOV_LINK_STATE_DISABLE;
TAKE_PTR(sr_iov);
return 0;
}
int config_parse_sr_iov_boolean(
const char *unit,
const char *filename,
unsigned line,
const char *section,
unsigned section_line,
const char *lvalue,
int ltype,
const char *rvalue,
void *data,
void *userdata) {
_cleanup_(sr_iov_free_or_set_invalidp) SRIOV *sr_iov = NULL;
Network *network = data;
int r;
assert(filename);
assert(lvalue);
assert(rvalue);
assert(data);
r = sr_iov_new_static(network, filename, section_line, &sr_iov);
if (r < 0)
return r;
if (isempty(rvalue)) {
if (streq(lvalue, "MACSpoofCheck"))
sr_iov->vf_spoof_check_setting = -1;
else if (streq(lvalue, "QueryReceiveSideScaling"))
sr_iov->query_rss = -1;
else if (streq(lvalue, "Trust"))
sr_iov->trust = -1;
else
assert_not_reached("Invalid lvalue");
TAKE_PTR(sr_iov);
return 0;
}
r = parse_boolean(rvalue);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r, "Failed to parse '%s=', ignoring: %s", lvalue, rvalue);
return 0;
}
if (streq(lvalue, "MACSpoofCheck"))
sr_iov->vf_spoof_check_setting = r;
else if (streq(lvalue, "QueryReceiveSideScaling"))
sr_iov->query_rss = r;
else if (streq(lvalue, "Trust"))
sr_iov->trust = r;
else
assert_not_reached("Invalid lvalue");
TAKE_PTR(sr_iov);
return 0;
}
int config_parse_sr_iov_mac(
const char *unit,
const char *filename,
unsigned line,
const char *section,
unsigned section_line,
const char *lvalue,
int ltype,
const char *rvalue,
void *data,
void *userdata) {
_cleanup_(sr_iov_free_or_set_invalidp) SRIOV *sr_iov = NULL;
Network *network = data;
int r;
assert(filename);
assert(lvalue);
assert(rvalue);
assert(data);
r = sr_iov_new_static(network, filename, section_line, &sr_iov);
if (r < 0)
return r;
if (isempty(rvalue)) {
sr_iov->mac = ETHER_ADDR_NULL;
TAKE_PTR(sr_iov);
return 0;
}
r = ether_addr_from_string(rvalue, &sr_iov->mac);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, 0,
"Failed to parse SR-IOV '%s=', ignoring assignment: %s", lvalue, rvalue);
return 0;
}
TAKE_PTR(sr_iov);
return 0;
}

View File

@ -0,0 +1,46 @@
/* SPDX-License-Identifier: LGPL-2.1+
* Copyright © 2020 VMware, Inc. */
#pragma once
#include <linux/if_link.h>
#include "conf-parser.h"
#include "networkd-link.h"
#include "networkd-network.h"
#include "networkd-util.h"
typedef enum SRIOVLinkState {
SR_IOV_LINK_STATE_AUTO = IFLA_VF_LINK_STATE_AUTO,
SR_IOV_LINK_STATE_ENABLE = IFLA_VF_LINK_STATE_ENABLE,
SR_IOV_LINK_STATE_DISABLE = IFLA_VF_LINK_STATE_DISABLE,
_SR_IOV_LINK_STATE_MAX,
_SR_IOV_LINK_STATE_INVALID = -1,
} SRIOVLinkState;
typedef struct SRIOV {
NetworkConfigSection *section;
Network *network;
uint32_t vf; /* 0 - 2147483646 */
uint32_t vlan; /* 0 - 4095, 0 disables VLAN filter */
uint32_t qos;
uint16_t vlan_proto; /* ETH_P_8021Q or ETH_P_8021AD */
int vf_spoof_check_setting;
int query_rss;
int trust;
SRIOVLinkState link_state;
struct ether_addr mac;
} SRIOV;
SRIOV *sr_iov_free(SRIOV *sr_iov);
int sr_iov_configure(Link *link, SRIOV *sr_iov);
int sr_iov_section_verify(SRIOV *sr_iov);
DEFINE_NETWORK_SECTION_FUNCTIONS(SRIOV, sr_iov_free);
CONFIG_PARSER_PROTOTYPE(config_parse_sr_iov_uint32);
CONFIG_PARSER_PROTOTYPE(config_parse_sr_iov_boolean);
CONFIG_PARSER_PROTOTYPE(config_parse_sr_iov_link_state);
CONFIG_PARSER_PROTOTYPE(config_parse_sr_iov_vlan_proto);
CONFIG_PARSER_PROTOTYPE(config_parse_sr_iov_mac);

View File

@ -136,14 +136,14 @@ int config_parse_cake_overhead(
r = safe_atoi32(rvalue, &v);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse 'Overhead=', ignoring assignment: %s",
rvalue);
"Failed to parse '%s=', ignoring assignment: %s",
lvalue, rvalue);
return 0;
}
if (v < -64 || v > 256) {
log_syntax(unit, LOG_ERR, filename, line, 0,
"Invalid 'Overhead=', ignoring assignment: %s",
rvalue);
"Invalid '%s=', ignoring assignment: %s",
lvalue, rvalue);
return 0;
}

View File

@ -79,7 +79,7 @@ int config_parse_drr_size(
return 0;
}
r = parse_size(rvalue, 1000, &u);
r = parse_size(rvalue, 1024, &u);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse '%s=', ignoring assignment: %s",

View File

@ -140,7 +140,7 @@ int config_parse_bfifo_size(
return 0;
}
r = parse_size(rvalue, 1000, &u);
r = parse_size(rvalue, 1024, &u);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse '%s=', ignoring assignment: %s",

View File

@ -9,6 +9,7 @@
#include "parse-util.h"
#include "qdisc.h"
#include "string-util.h"
#include "strv.h"
static int fair_queueing_controlled_delay_init(QDisc *qdisc) {
FairQueueingControlledDelay *fqcd;
@ -301,15 +302,15 @@ int config_parse_fair_queueing_controlled_delay_size(
fqcd = FQ_CODEL(qdisc);
if (streq(lvalue, "MemoryLimit"))
if (STR_IN_SET(lvalue, "MemoryLimitBytes", "MemoryLimit"))
p = &fqcd->memory_limit;
else if (streq(lvalue, "Quantum"))
else if (STR_IN_SET(lvalue, "QuantumBytes", "Quantum"))
p = &fqcd->quantum;
else
assert_not_reached("Invalid lvalue.");
if (isempty(rvalue)) {
if (streq(lvalue, "MemoryLimit"))
if (STR_IN_SET(lvalue, "MemoryLimitBytes", "MemoryLimit"))
*p = UINT32_MAX;
else
*p = 0;

View File

@ -9,7 +9,7 @@
#include "netlink-util.h"
#include "parse-util.h"
#include "string-util.h"
#include "util.h"
#include "strv.h"
static int fair_queueing_init(QDisc *qdisc) {
FairQueueing *fq;
@ -198,9 +198,9 @@ int config_parse_fair_queueing_size(
fq = FQ(qdisc);
if (streq(lvalue, "Quantum"))
if (STR_IN_SET(lvalue, "QuantumBytes", "Quantum"))
p = &fq->quantum;
else if (streq(lvalue, "InitialQuantum"))
else if (STR_IN_SET(lvalue, "InitialQuantumBytes", "InitialQuantum"))
p = &fq->initial_quantum;
else
assert_not_reached("Invalid lvalue");

View File

@ -142,7 +142,7 @@ int config_parse_quick_fair_queueing_max_packet(
return 0;
}
r = parse_size(rvalue, 1000, &v);
r = parse_size(rvalue, 1024, &v);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse '%s=', ignoring assignment: %s",

View File

@ -12,8 +12,8 @@
#include "parse-util.h"
#include "qdisc.h"
#include "string-util.h"
#include "strv.h"
#include "tc-util.h"
#include "util.h"
static int token_bucket_filter_fill_message(Link *link, QDisc *qdisc, sd_netlink_message *req) {
uint32_t rtab[256], ptab[256];
@ -143,18 +143,85 @@ int config_parse_token_bucket_filter_size(
tbf = TBF(qdisc);
if (isempty(rvalue)) {
if (streq(lvalue, "Rate"))
tbf->rate = 0;
else if (streq(lvalue, "Burst"))
if (STR_IN_SET(lvalue, "BurstBytes", "Burst"))
tbf->burst = 0;
else if (streq(lvalue, "LimitSize"))
else if (STR_IN_SET(lvalue, "LimitBytes", "LimitSize"))
tbf->limit = 0;
else if (streq(lvalue, "MTUBytes"))
tbf->mtu = 0;
else if (streq(lvalue, "MPUBytes"))
tbf->mpu = 0;
else if (streq(lvalue, "PeakRate"))
tbf->peak_rate = 0;
else
assert_not_reached("unknown lvalue");
qdisc = NULL;
return 0;
}
r = parse_size(rvalue, 1024, &k);
if (r < 0) {
log_syntax(unit, LOG_ERR, filename, line, r,
"Failed to parse '%s=', ignoring assignment: %s",
lvalue, rvalue);
return 0;
}
if (STR_IN_SET(lvalue, "BurstBytes", "Burst"))
tbf->burst = k;
else if (STR_IN_SET(lvalue, "LimitBytes", "LimitSize"))
tbf->limit = k;
else if (streq(lvalue, "MPUBytes"))
tbf->mpu = k;
else if (streq(lvalue, "MTUBytes"))
tbf->mtu = k;
else
assert_not_reached("unknown lvalue");
qdisc = NULL;
return 0;
}
int config_parse_token_bucket_filter_rate(
const char *unit,
const char *filename,
unsigned line,
const char *section,
unsigned section_line,
const char *lvalue,
int ltype,
const char *rvalue,
void *data,
void *userdata) {
_cleanup_(qdisc_free_or_set_invalidp) QDisc *qdisc = NULL;
Network *network = data;
TokenBucketFilter *tbf;
uint64_t k, *p;
int r;
assert(filename);
assert(lvalue);
assert(rvalue);
assert(data);
r = qdisc_new_static(QDISC_KIND_TBF, network, filename, section_line, &qdisc);
if (r == -ENOMEM)
return log_oom();
if (r < 0)
return log_syntax(unit, LOG_ERR, filename, line, r,
"More than one kind of queueing discipline, ignoring assignment: %m");
tbf = TBF(qdisc);
if (streq(lvalue, "Rate"))
p = &tbf->rate;
else if (streq(lvalue, "PeakRate"))
p = &tbf->peak_rate;
else
assert_not_reached("unknown lvalue");
if (isempty(rvalue)) {
*p = 0;
qdisc = NULL;
return 0;
@ -168,18 +235,7 @@ int config_parse_token_bucket_filter_size(
return 0;
}
if (streq(lvalue, "Rate"))
tbf->rate = k / 8;
else if (streq(lvalue, "Burst"))
tbf->burst = k;
else if (streq(lvalue, "LimitSize"))
tbf->limit = k;
else if (streq(lvalue, "MPUBytes"))
tbf->mpu = k;
else if (streq(lvalue, "MTUBytes"))
tbf->mtu = k;
else if (streq(lvalue, "PeakRate"))
tbf->peak_rate = k / 8;
*p = k / 8;
qdisc = NULL;

View File

@ -23,3 +23,4 @@ extern const QDiscVTable tbf_vtable;
CONFIG_PARSER_PROTOTYPE(config_parse_token_bucket_filter_latency);
CONFIG_PARSER_PROTOTYPE(config_parse_token_bucket_filter_size);
CONFIG_PARSER_PROTOTYPE(config_parse_token_bucket_filter_rate);

View File

@ -839,7 +839,7 @@ int dns_packet_append_rr(DnsPacket *p, const DnsResourceRecord *rr, const DnsAns
rds = p->size - saved_size;
switch (rr->unparseable ? _DNS_TYPE_INVALID : rr->key->type) {
switch (rr->unparsable ? _DNS_TYPE_INVALID : rr->key->type) {
case DNS_TYPE_SRV:
r = dns_packet_append_uint16(p, rr->srv.priority, NULL);
@ -1125,7 +1125,7 @@ int dns_packet_append_rr(DnsPacket *p, const DnsResourceRecord *rr, const DnsAns
case DNS_TYPE_OPT:
case DNS_TYPE_OPENPGPKEY:
case _DNS_TYPE_INVALID: /* unparseable */
case _DNS_TYPE_INVALID: /* unparsable */
default:
r = dns_packet_append_blob(p, rr->generic.data, rr->generic.data_size, NULL);
@ -1815,8 +1815,8 @@ int dns_packet_read_rr(DnsPacket *p, DnsResourceRecord **ret, bool *ret_cache_fl
break;
} else {
dns_packet_rewind(p, pos);
rr->unparseable = true;
goto unparseable;
rr->unparsable = true;
goto unparsable;
}
}
@ -2059,7 +2059,7 @@ int dns_packet_read_rr(DnsPacket *p, DnsResourceRecord **ret, bool *ret_cache_fl
case DNS_TYPE_OPT: /* we only care about the header of OPT for now. */
case DNS_TYPE_OPENPGPKEY:
default:
unparseable:
unparsable:
r = dns_packet_read_memdup(p, rdlength, &rr->generic.data, &rr->generic.data_size, NULL);
break;

View File

@ -474,11 +474,11 @@ static DnsResourceRecord* dns_resource_record_free(DnsResourceRecord *rr) {
case DNS_TYPE_OPENPGPKEY:
default:
if (!rr->unparseable)
if (!rr->unparsable)
free(rr->generic.data);
}
if (rr->unparseable)
if (rr->unparsable)
free(rr->generic.data);
free(rr->wire_format);
@ -563,10 +563,10 @@ int dns_resource_record_payload_equal(const DnsResourceRecord *a, const DnsResou
/* Check if a and b are the same, but don't look at their keys */
if (a->unparseable != b->unparseable)
if (a->unparsable != b->unparsable)
return 0;
switch (a->unparseable ? _DNS_TYPE_INVALID : a->key->type) {
switch (a->unparsable ? _DNS_TYPE_INVALID : a->key->type) {
case DNS_TYPE_SRV:
r = dns_name_equal(a->srv.name, b->srv.name);
@ -828,7 +828,7 @@ const char *dns_resource_record_to_string(DnsResourceRecord *rr) {
dns_resource_key_to_string(rr->key, k, sizeof(k));
switch (rr->unparseable ? _DNS_TYPE_INVALID : rr->key->type) {
switch (rr->unparsable ? _DNS_TYPE_INVALID : rr->key->type) {
case DNS_TYPE_SRV:
r = asprintf(&s, "%s %u %u %u %s",
@ -1175,7 +1175,7 @@ ssize_t dns_resource_record_payload(DnsResourceRecord *rr, void **out) {
assert(rr);
assert(out);
switch(rr->unparseable ? _DNS_TYPE_INVALID : rr->key->type) {
switch(rr->unparsable ? _DNS_TYPE_INVALID : rr->key->type) {
case DNS_TYPE_SRV:
case DNS_TYPE_PTR:
case DNS_TYPE_NS:
@ -1343,7 +1343,7 @@ void dns_resource_record_hash_func(const DnsResourceRecord *rr, struct siphash *
dns_resource_key_hash_func(rr->key, state);
switch (rr->unparseable ? _DNS_TYPE_INVALID : rr->key->type) {
switch (rr->unparsable ? _DNS_TYPE_INVALID : rr->key->type) {
case DNS_TYPE_SRV:
siphash24_compress(&rr->srv.priority, sizeof(rr->srv.priority), state);
@ -1510,9 +1510,9 @@ DnsResourceRecord *dns_resource_record_copy(DnsResourceRecord *rr) {
copy->expiry = rr->expiry;
copy->n_skip_labels_signer = rr->n_skip_labels_signer;
copy->n_skip_labels_source = rr->n_skip_labels_source;
copy->unparseable = rr->unparseable;
copy->unparsable = rr->unparsable;
switch (rr->unparseable ? _DNS_TYPE_INVALID : rr->key->type) {
switch (rr->unparsable ? _DNS_TYPE_INVALID : rr->key->type) {
case DNS_TYPE_SRV:
copy->srv.priority = rr->srv.priority;

View File

@ -102,7 +102,7 @@ struct DnsResourceRecord {
/* How many labels to strip to determine "synthesizing source" of this RR, i.e. the wildcard's immediate parent. -1 if not signed. */
unsigned n_skip_labels_source;
bool unparseable:1;
bool unparsable:1;
bool wire_format_canonical:1;
void *wire_format;

View File

@ -190,7 +190,7 @@ static int dns_stream_identify(DnsStream *s) {
s->ifindex = manager_find_ifindex(s->manager, s->local.sa.sa_family, s->local.sa.sa_family == AF_INET ? (union in_addr_union*) &s->local.in.sin_addr : (union in_addr_union*) &s->local.in6.sin6_addr);
if (s->protocol == DNS_PROTOCOL_LLMNR && s->ifindex > 0) {
uint32_t ifindex = htobe32(s->ifindex);
be32_t ifindex = htobe32(s->ifindex);
/* Make sure all packets for this connection are sent on the same interface */
if (s->local.sa.sa_family == AF_INET) {

View File

@ -387,7 +387,7 @@ DEFINE_TRIVIAL_REF_UNREF_FUNC(Varlink, varlink, varlink_destroy);
static int varlink_test_disconnect(Varlink *v) {
assert(v);
/* Tests whether we the the connection has been terminated. We are careful to not stop processing it
/* Tests whether we the connection has been terminated. We are careful to not stop processing it
* prematurely, since we want to handle half-open connections as well as possible and want to flush
* out and read data before we close down if we can. */

View File

@ -38,6 +38,16 @@ MTUBytes=
Multicast=
MACAddress=
Group=
[SR-IOV]
VirtualFunction=
MACSpoofCheck=
VLANId=
VLANProtocol=
QualityOfService=
QueryReceiveSideScaling=
Trust=
LinkState=
MACAddress=
[BridgeFDB]
VLANId=
MACAddress=
@ -322,7 +332,9 @@ PacketLimit=
Parent=
Handle=
Rate=
BurstBytes=
Burst=
LimitBytes=
LimitSize=
MTUBytes=
MPUBytes=
@ -336,8 +348,10 @@ PerturbPeriodSec=
Parent=
Handle=
PacketLimit=
MemoryLimitBytes=
MemoryLimit=
Flows=
QuantumBytes=
Quantum=
TargetSec=
IntervalSec=
@ -348,7 +362,9 @@ Parent=
Handle=
PacketLimit=
FlowLimit=
QuantumBytes=
Quantum=
InitialQuantumBytes=
InitialQuantum=
MaximumRate=
Buckets=
@ -367,7 +383,7 @@ ECN=
Parent=
Handle=
Bandwidth=
Overhead=
OverheadBytes=
[TrafficControlQueueingDiscipline]
Parent=
NetworkEmulatorDelaySec=
@ -398,7 +414,7 @@ CeilBufferBytes=
[BFIFO]
Parent=
Handle=
LimitSize=
LimitBytes=
[PFIFO]
Parent=
Handle=
@ -431,14 +447,14 @@ Handle=
Parent=
ClassId=
Weight=
MaxPacketSize=
MaxPacketBytes=
[DeficitRoundRobinScheduler]
Parent=
Handle=
[DeficitRoundRobinSchedulerClass]
Parent=
ClassId=
Quantum=
QuantumBytes=
[EnhancedTransmissionSelection]
Parent=
Handle=

View File

@ -8,5 +8,5 @@ Address=10.1.2.3/16
[CAKE]
Parent=root
Handle=3a
Overhead=128
OverheadBytes=128
Bandwidth=500M

View File

@ -58,8 +58,8 @@ Parent=2:32
Handle=0032
PacketLimit=1000
FlowLimit=200
Quantum=1500
InitialQuantum=13000
QuantumBytes=1500
InitialQuantumBytes=13000
MaximumRate=1M
Buckets=512
OrphanMask=511
@ -93,11 +93,11 @@ CeilRate=0.5M
Parent=2:34
Handle=0034
PacketLimit=20480
MemoryLimit=64M
MemoryLimitBytes=64M
Flows=2048
TargetSec=10ms
IntervalSec=200ms
Quantum=1400
QuantumBytes=1400
ECN=yes
CEThresholdSec=100ms
@ -112,10 +112,10 @@ CeilRate=0.5M
Parent=2:35
Handle=0035
Rate=1G
Burst=5K
BurstBytes=5000
LatencySec=70msec
PeakRate=100G
MTUBytes=1M
MTUBytes=1000000
[HierarchyTokenBucketClass]
Parent=root
@ -177,7 +177,7 @@ CeilRate=0.5M
[BFIFO]
Parent=2:3a
Handle=003a
LimitSize=1M
LimitBytes=1000000
[HierarchyTokenBucketClass]
Parent=root

View File

@ -12,4 +12,4 @@ Handle=0002
[DeficitRoundRobinSchedulerClass]
Parent=root
ClassId=0002:0030
Quantum=2000
QuantumBytes=2000

View File

@ -13,10 +13,10 @@ Handle=0002
Parent=root
ClassId=0002:0030
Weight=2
MaxPacketSize=16000
MaxPacketBytes=16000
[QuickFairQueueingClass]
Parent=root
ClassId=0002:0031
Weight=10
MaxPacketSize=8000
MaxPacketBytes=8000

View File

@ -0,0 +1,37 @@
[Match]
Name=eni99np1
[Network]
Address=192.168.100.100/24
[SR-IOV]
VirtualFunction=0
VLANId=5
VLANProtocol=802.1ad
QualityOfService=1
MACSpoofCheck=yes
QueryReceiveSideScaling=yes
Trust=yes
LinkState=yes
MACAddress=00:11:22:33:44:55
[SR-IOV]
VirtualFunction=1
VLANId=6
VLANProtocol=802.1Q
QualityOfService=2
MACSpoofCheck=no
QueryReceiveSideScaling=no
Trust=no
LinkState=no
MACAddress=00:11:22:33:44:56
[SR-IOV]
VirtualFunction=2
VLANId=7
QualityOfService=3
MACSpoofCheck=no
QueryReceiveSideScaling=no
Trust=no
LinkState=auto
MACAddress=00:11:22:33:44:57

View File

@ -158,6 +158,33 @@ def expectedFailureIfAlternativeNameIsNotAvailable():
return f
def expectedFailureIfNetdevsimWithSRIOVIsNotAvailable():
def f(func):
call('rmmod netdevsim', stderr=subprocess.DEVNULL)
rc = call('modprobe netdevsim', stderr=subprocess.DEVNULL)
if rc != 0:
return unittest.expectedFailure(func)
try:
with open('/sys/bus/netdevsim/new_device', mode='w') as f:
f.write('99 1')
except Exception as error:
return unittest.expectedFailure(func)
call('udevadm settle')
call('udevadm info -w10s /sys/devices/netdevsim99/net/eni99np1', stderr=subprocess.DEVNULL)
try:
with open('/sys/class/net/eni99np1/device/sriov_numvfs', mode='w') as f:
f.write('3')
except Exception as error:
call('rmmod netdevsim', stderr=subprocess.DEVNULL)
return unittest.expectedFailure(func)
call('rmmod netdevsim', stderr=subprocess.DEVNULL)
return func
return f
def expectedFailureIfCAKEIsNotAvailable():
def f(func):
call('ip link add dummy98 type dummy', stderr=subprocess.DEVNULL)
@ -1695,6 +1722,7 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
'25-route-vrf.network',
'25-gateway-static.network',
'25-gateway-next-static.network',
'25-sriov.network',
'25-sysctl-disable-ipv6.network',
'25-sysctl.network',
'25-test1.network',
@ -2237,7 +2265,7 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
self.assertRegex(output, 'inet6 .* scope link')
output = check_output('ip -4 route show dev dummy98')
print(output)
self.assertEqual(output, '10.2.0.0/16 proto kernel scope link src 10.2.3.4')
self.assertRegex(output, '10.2.0.0/16 proto kernel scope link src 10.2.3.4')
output = check_output('ip -6 route show dev dummy98')
print(output)
self.assertRegex(output, 'default via 2607:5300:203:39ff:ff:ff:ff:ff proto static')
@ -2260,7 +2288,7 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
self.assertRegex(output, 'inet6 .* scope link')
output = check_output('ip -4 route show dev dummy98')
print(output)
self.assertEqual(output, '10.2.0.0/16 proto kernel scope link src 10.2.3.4')
self.assertRegex(output, '10.2.0.0/16 proto kernel scope link src 10.2.3.4')
output = check_output('ip -6 route show dev dummy98')
print(output)
self.assertRegex(output, 'default via 2607:5300:203:39ff:ff:ff:ff:ff proto static')
@ -2508,6 +2536,32 @@ class NetworkdNetworkTests(unittest.TestCase, Utilities):
self.assertRegex(output, 'quanta 1 2 3 4 5')
self.assertRegex(output, 'priomap 3 4 5 6 7')
@expectedFailureIfNetdevsimWithSRIOVIsNotAvailable()
def test_sriov(self):
call('rmmod netdevsim', stderr=subprocess.DEVNULL)
call('modprobe netdevsim', stderr=subprocess.DEVNULL)
with open('/sys/bus/netdevsim/new_device', mode='w') as f:
f.write('99 1')
call('udevadm settle')
call('udevadm info -w10s /sys/devices/netdevsim99/net/eni99np1', stderr=subprocess.DEVNULL)
with open('/sys/class/net/eni99np1/device/sriov_numvfs', mode='w') as f:
f.write('3')
copy_unit_to_networkd_unit_path('25-sriov.network')
start_networkd()
self.wait_online(['eni99np1:routable'])
output = check_output('ip link show dev eni99np1')
print(output)
self.assertRegex(output,
'vf 0 .*00:11:22:33:44:55.*vlan 5, qos 1, vlan protocol 802.1ad, spoof checking on, link-state enable, trust on, query_rss on\n *'
'vf 1 .*00:11:22:33:44:56.*vlan 6, qos 2, spoof checking off, link-state disable, trust off, query_rss off\n *'
'vf 2 .*00:11:22:33:44:57.*vlan 7, qos 3, spoof checking off, link-state auto, trust off, query_rss off'
)
call('rmmod netdevsim', stderr=subprocess.DEVNULL)
class NetworkdStateFileTests(unittest.TestCase, Utilities):
links = [
'dummy98',