diff options
99 files changed, 1908 insertions, 752 deletions
diff --git a/.gitignore b/.gitignore index dd887902ad..0e1d428ab0 100644 --- a/.gitignore +++ b/.gitignore @@ -182,7 +182,7 @@ /test-efi-disk.img /test-ellipsize /test-engine -/test-env-replace +/test-env-util /test-escape /test-event /test-execute diff --git a/Makefile-man.am b/Makefile-man.am index a7e348b1f1..a4835a533f 100644 --- a/Makefile-man.am +++ b/Makefile-man.am @@ -144,6 +144,7 @@ MANPAGES += \ man/systemd.link.5 \ man/systemd.mount.5 \ man/systemd.nspawn.5 \ + man/systemd.offline-updates.7 \ man/systemd.path.5 \ man/systemd.preset.5 \ man/systemd.resource-control.5 \ @@ -2651,6 +2652,7 @@ EXTRA_DIST += \ man/systemd.netdev.xml \ man/systemd.network.xml \ man/systemd.nspawn.xml \ + man/systemd.offline-updates.xml \ man/systemd.path.xml \ man/systemd.preset.xml \ man/systemd.resource-control.xml \ diff --git a/Makefile.am b/Makefile.am index 0f1f79e62d..7668c541cb 100644 --- a/Makefile.am +++ b/Makefile.am @@ -744,6 +744,7 @@ noinst_LTLIBRARIES += \ libbasic_la_SOURCES = \ src/basic/missing.h \ + src/basic/missing_syscall.h \ src/basic/capability-util.c \ src/basic/capability-util.h \ src/basic/c-rbtree.c \ @@ -1420,7 +1421,7 @@ tests += \ test-watchdog \ test-cgroup-mask \ test-job-type \ - test-env-replace \ + test-env-util \ test-strbuf \ test-strv \ test-path \ @@ -1562,6 +1563,7 @@ EXTRA_DIST += \ test/test-execute/exec-passenvironment-repeated.service \ test/test-execute/exec-passenvironment.service \ test/test-execute/exec-group.service \ + test/test-execute/exec-group-nfsnobody.service \ test/test-execute/exec-ignoresigpipe-no.service \ test/test-execute/exec-ignoresigpipe-yes.service \ test/test-execute/exec-personality-x86-64.service \ @@ -1577,7 +1579,10 @@ EXTRA_DIST += \ test/test-execute/exec-systemcallfilter-failing.service \ test/test-execute/exec-systemcallfilter-not-failing2.service \ test/test-execute/exec-systemcallfilter-not-failing.service \ + test/test-execute/exec-systemcallfilter-system-user.service \ + test/test-execute/exec-systemcallfilter-system-user-nfsnobody.service \ test/test-execute/exec-user.service \ + test/test-execute/exec-user-nfsnobody.service \ test/test-execute/exec-workingdirectory.service \ test/test-execute/exec-umask-0177.service \ test/test-execute/exec-umask-default.service \ @@ -1594,10 +1599,13 @@ EXTRA_DIST += \ test/test-execute/exec-capabilityboundingset-reset.service \ test/test-execute/exec-capabilityboundingset-simple.service \ test/test-execute/exec-capabilityambientset.service \ + test/test-execute/exec-capabilityambientset-nfsnobody.service \ test/test-execute/exec-capabilityambientset-merge.service \ + test/test-execute/exec-capabilityambientset-merge-nfsnobody.service \ test/test-execute/exec-runtimedirectory.service \ test/test-execute/exec-runtimedirectory-mode.service \ test/test-execute/exec-runtimedirectory-owner.service \ + test/test-execute/exec-runtimedirectory-owner-nfsnobody.service \ test/bus-policy/hello.conf \ test/bus-policy/methods.conf \ test/bus-policy/ownerships.conf \ @@ -2189,10 +2197,10 @@ test_cgroup_util_SOURCES = \ test_cgroup_util_LDADD = \ libshared.la -test_env_replace_SOURCES = \ - src/test/test-env-replace.c +test_env_util_SOURCES = \ + src/test/test-env-util.c -test_env_replace_LDADD = \ +test_env_util_LDADD = \ libshared.la test_strbuf_SOURCES = \ @@ -3415,7 +3423,6 @@ libsystemd_network_la_SOURCES = \ src/libsystemd-network/sd-dhcp6-lease.c \ src/libsystemd-network/dhcp-identifier.h \ src/libsystemd-network/dhcp-identifier.c \ - src/libsystemd-network/lldp.h \ src/libsystemd-network/lldp-internal.h \ src/libsystemd-network/lldp-network.h \ src/libsystemd-network/lldp-network.c \ @@ -3944,6 +3951,34 @@ systemd_cat_SOURCES = \ systemd_cat_LDADD = \ libjournal-core.la +if HAVE_LIBCURL +rootlibexec_PROGRAMS += \ + systemd-journal-upload + +systemd_journal_upload_SOURCES = \ + src/journal-remote/journal-upload.h \ + src/journal-remote/journal-upload.c \ + src/journal-remote/journal-upload-journal.c + +systemd_journal_upload_CFLAGS = \ + $(AM_CFLAGS) \ + $(LIBCURL_CFLAGS) + +systemd_journal_upload_LDADD = \ + libshared.la \ + $(LIBCURL_LIBS) + +nodist_systemunit_DATA += \ + units/systemd-journal-upload.service + +nodist_pkgsysconf_DATA += \ + src/journal-remote/journal-upload.conf +endif + +EXTRA_DIST += \ + units/systemd-journal-upload.service.in \ + src/journal-remote/journal-upload.conf.in + if HAVE_MICROHTTPD rootlibexec_PROGRAMS += \ systemd-journal-remote @@ -4003,34 +4038,6 @@ EXTRA_DIST += \ src/journal-remote/log-generator.py endif -if HAVE_LIBCURL -rootlibexec_PROGRAMS += \ - systemd-journal-upload - -systemd_journal_upload_SOURCES = \ - src/journal-remote/journal-upload.h \ - src/journal-remote/journal-upload.c \ - src/journal-remote/journal-upload-journal.c - -systemd_journal_upload_CFLAGS = \ - $(AM_CFLAGS) \ - $(LIBCURL_CFLAGS) - -systemd_journal_upload_LDADD = \ - libshared.la \ - $(LIBCURL_LIBS) - -nodist_systemunit_DATA += \ - units/systemd-journal-upload.service - -nodist_pkgsysconf_DATA += \ - src/journal-remote/journal-upload.conf -endif - -EXTRA_DIST += \ - units/systemd-journal-upload.service.in \ - src/journal-remote/journal-upload.conf.in - # using _CFLAGS = in the conditional below would suppress AM_CFLAGS journalctl_CFLAGS = \ $(AM_CFLAGS) @@ -4254,7 +4261,9 @@ libsystemd_journal_internal_la_SOURCES = \ src/journal/mmap-cache.h \ src/journal/compress.c \ src/journal/audit-type.h \ - src/journal/audit-type.c + src/journal/audit-type.c \ + src/shared/gcrypt-util.h \ + src/shared/gcrypt-util.c nodist_libsystemd_journal_internal_la_SOURCES = \ src/journal/audit_type-to-name.h @@ -4286,9 +4295,7 @@ libsystemd_journal_internal_la_SOURCES += \ src/journal/journal-authenticate.c \ src/journal/journal-authenticate.h \ src/journal/fsprg.c \ - src/journal/fsprg.h \ - src/shared/gcrypt-util.c \ - src/shared/gcrypt-util.h + src/journal/fsprg.h libsystemd_journal_internal_la_LIBADD += \ $(GCRYPT_LIBS) @@ -19,10 +19,58 @@ CHANGES WITH 230 in spe: again don't consider turning this on in your stable, LTS or production release just yet. + * systemd-resolve conveniently resolves DANE records with the --tlsa + option and OPENPGPKEY records with the --openpgp option. + * Testing tool /usr/lib/systemd/systemd-activate is renamed to systemd-socket-activate and installed into /usr/bin. It is now fully supported. + * The unified cgroup hierarchy added in Linux 4.5 is now supported. + Use systemd.unified_cgroup_hierarchy=1 on the kernel command line + to enable. + WARNING: it is not possible to use previous systemd versions with + systemd.unified_cgroup_hierarchy=1 and the new kernel. Therefore it + is necessary to also update systemd in the initramfs if using the + unified hierarchy. Updated selinux policy is also required. + + * LLDP support has been extended, and both passive (receive-only) + and active (sender) modes are supported. Passive mode + ("routers-only") is enabled by default in systemd-networkd. + Active LLDP mode is enabled by default for containers on the + internal network. + "networkctl lldp" can be used to list information gathered. + + * Headers for LLDP support (sd-lldp.h) are now public. + + * The Unique Identifier sent in DHCP requests can be configured. + + * systemd-journald now uses separate threads to flush changes to + disk when closing journal files. + + * systemd-ask-password skips printing of the password to stdout + with --no-output which can be useful in scripts. + + * Framebuffer devices (/dev/fb*) and 3D printers and scanners + (devices tagged with ID_MAKER_TOOL) are now tagged with + "uaccess" and are available to logged in users. + + * systemd-bootchart has been split out to a separate repository: + https://github.com/systemd/systemd-bootchart + + * Compatibility libraries libsystemd-daemon.so, libsystemd-journal.so, + libsystemd-id128.so, and libsystemd-login.so which have been + deprecated since systemd-209 have been removed along along with the + corresponding pkg-config files. All symbols provided by the those + libraries are provided by libsystemd.so. + + * Capabilities= setting has been removed (it is ignored for backwards + compatibility). AmbientCapabilities= and CapabilityBoundingSet= + should be used instead. + + * systemd-bus-proxyd has been removed, as kdbus will not be merged + in current form. + CHANGES WITH 229: * The systemd-resolved DNS resolver service has gained a substantial @@ -1345,7 +1393,7 @@ CHANGES WITH 219: * machinectl is now able to clone container images efficiently, if the underlying file system (btrfs) supports - it, with the new "machinectl list-images" command. It also + it, with the new "machinectl clone" command. It also gained commands for renaming and removing images, as well as marking them read-only or read-write (supported also on legacy file systems). @@ -49,8 +49,6 @@ Features: * cache sd_event_now() result from before the first iteration... -* support for the new copy_file_range() syscall - * add systemctl stop --job-mode=triggering that follows TRIGGERED_BY deps and adds them to the same transaction * Maybe add a way how users can "pin" units into memory, so that they are not subject to automatic GC? diff --git a/configure.ac b/configure.ac index 79340bcca9..cb14abda05 100644 --- a/configure.ac +++ b/configure.ac @@ -296,8 +296,19 @@ LIBS="$save_LIBS" AC_SUBST(CAP_LIBS) AC_CHECK_FUNCS([__secure_getenv secure_getenv]) -AC_CHECK_DECLS([memfd_create, gettid, pivot_root, name_to_handle_at, setns, getrandom, renameat2, kcmp, keyctl, LO_FLAGS_PARTSCAN], - [], [], [[ +AC_CHECK_DECLS([ + memfd_create, + gettid, + pivot_root, + name_to_handle_at, + setns, + getrandom, + renameat2, + kcmp, + keyctl, + LO_FLAGS_PARTSCAN, + copy_file_range], + [], [], [[ #include <sys/types.h> #include <unistd.h> #include <sys/mount.h> diff --git a/hwdb/20-bluetooth-vendor-product.hwdb b/hwdb/20-bluetooth-vendor-product.hwdb index 516abad246..821d3e96bd 100644 --- a/hwdb/20-bluetooth-vendor-product.hwdb +++ b/hwdb/20-bluetooth-vendor-product.hwdb @@ -1111,7 +1111,7 @@ bluetooth:v016F* ID_VENDOR_FROM_DATABASE=Podo Labs, Inc bluetooth:v0170* - ID_VENDOR_FROM_DATABASE=Roche Diabetes Care AG + ID_VENDOR_FROM_DATABASE=F. Hoffmann-La Roche AG bluetooth:v0171* ID_VENDOR_FROM_DATABASE=Amazon Fulfillment Service @@ -2231,3 +2231,240 @@ bluetooth:v02E4* bluetooth:v02E5* ID_VENDOR_FROM_DATABASE=Espressif Incorporated ( 乐鑫信息科技(上海)有限公司 ) + +bluetooth:v02E6* + ID_VENDOR_FROM_DATABASE=Unwire + +bluetooth:v02E7* + ID_VENDOR_FROM_DATABASE=Connected Yard, Inc. + +bluetooth:v02E8* + ID_VENDOR_FROM_DATABASE=American Music Environments + +bluetooth:v02E9* + ID_VENDOR_FROM_DATABASE=Sensogram Technologies, Inc. + +bluetooth:v02EA* + ID_VENDOR_FROM_DATABASE=Fujitsu Limited + +bluetooth:v02EB* + ID_VENDOR_FROM_DATABASE=Ardic Technology + +bluetooth:v02EC* + ID_VENDOR_FROM_DATABASE=Delta Systems, Inc + +bluetooth:v02ED* + ID_VENDOR_FROM_DATABASE=HTC Corporation + +bluetooth:v02EE* + ID_VENDOR_FROM_DATABASE=Citizen Holdings Co., Ltd. + +bluetooth:v02EF* + ID_VENDOR_FROM_DATABASE=SMART-INNOVATION.inc + +bluetooth:v02F0* + ID_VENDOR_FROM_DATABASE=Blackrat Software + +bluetooth:v02F1* + ID_VENDOR_FROM_DATABASE=The Idea Cave, LLC + +bluetooth:v02F2* + ID_VENDOR_FROM_DATABASE=GoPro, Inc. + +bluetooth:v02F3* + ID_VENDOR_FROM_DATABASE=AuthAir, Inc + +bluetooth:v02F4* + ID_VENDOR_FROM_DATABASE=Vensi, Inc. + +bluetooth:v02F5* + ID_VENDOR_FROM_DATABASE=Indagem Tech LLC + +bluetooth:v02F6* + ID_VENDOR_FROM_DATABASE=Intemo Technologies + +bluetooth:v02F7* + ID_VENDOR_FROM_DATABASE=DreamVisions co., Ltd. + +bluetooth:v02F8* + ID_VENDOR_FROM_DATABASE=Runteq Oy Ltd + +bluetooth:v02F9* + ID_VENDOR_FROM_DATABASE=IMAGINATION TECHNOLOGIES LTD + +bluetooth:v02FA* + ID_VENDOR_FROM_DATABASE=CoSTAR Technologies + +bluetooth:v02FB* + ID_VENDOR_FROM_DATABASE=Clarius Mobile Health Corp. + +bluetooth:v02FC* + ID_VENDOR_FROM_DATABASE=Shanghai Frequen Microelectronics Co., Ltd. + +bluetooth:v02FD* + ID_VENDOR_FROM_DATABASE=Uwanna, Inc. + +bluetooth:v02FE* + ID_VENDOR_FROM_DATABASE=Lierda Science & Technology Group Co., Ltd. + +bluetooth:v02FF* + ID_VENDOR_FROM_DATABASE=Silicon Laboratories + +bluetooth:v0300* + ID_VENDOR_FROM_DATABASE=World Moto Inc. + +bluetooth:v0301* + ID_VENDOR_FROM_DATABASE=Giatec Scientific Inc. + +bluetooth:v0302* + ID_VENDOR_FROM_DATABASE=Loop Devices, Inc + +bluetooth:v0303* + ID_VENDOR_FROM_DATABASE=IACA electronique + +bluetooth:v0304* + ID_VENDOR_FROM_DATABASE=Martians Inc + +bluetooth:v0305* + ID_VENDOR_FROM_DATABASE=Swipp ApS + +bluetooth:v0306* + ID_VENDOR_FROM_DATABASE=Life Laboratory Inc. + +bluetooth:v0307* + ID_VENDOR_FROM_DATABASE=FUJI INDUSTRIAL CO.,LTD. + +bluetooth:v0308* + ID_VENDOR_FROM_DATABASE=Surefire, LLC + +bluetooth:v0309* + ID_VENDOR_FROM_DATABASE=Dolby Labs + +bluetooth:v030A* + ID_VENDOR_FROM_DATABASE=Ellisys + +bluetooth:v030B* + ID_VENDOR_FROM_DATABASE=Magnitude Lighting Converters + +bluetooth:v030C* + ID_VENDOR_FROM_DATABASE=Hilti AG + +bluetooth:v030D* + ID_VENDOR_FROM_DATABASE=Devdata S.r.l. + +bluetooth:v030E* + ID_VENDOR_FROM_DATABASE=Deviceworx + +bluetooth:v030F* + ID_VENDOR_FROM_DATABASE=Shortcut Labs + +bluetooth:v0310* + ID_VENDOR_FROM_DATABASE=SGL Italia S.r.l. + +bluetooth:v0311* + ID_VENDOR_FROM_DATABASE=PEEQ DATA + +bluetooth:v0312* + ID_VENDOR_FROM_DATABASE=Ducere Technologies Pvt Ltd + +bluetooth:v0313* + ID_VENDOR_FROM_DATABASE=DiveNav, Inc. + +bluetooth:v0314* + ID_VENDOR_FROM_DATABASE=RIIG AI Sp. z o.o. + +bluetooth:v0315* + ID_VENDOR_FROM_DATABASE=Thermo Fisher Scientific + +bluetooth:v0316* + ID_VENDOR_FROM_DATABASE=AG Measurematics Pvt. Ltd. + +bluetooth:v0317* + ID_VENDOR_FROM_DATABASE=CHUO Electronics CO., LTD. + +bluetooth:v0318* + ID_VENDOR_FROM_DATABASE=Aspenta International + +bluetooth:v0319* + ID_VENDOR_FROM_DATABASE=Eugster Frismag AG + +bluetooth:v031A* + ID_VENDOR_FROM_DATABASE=Amber wireless GmbH + +bluetooth:v031B* + ID_VENDOR_FROM_DATABASE=HQ Inc + +bluetooth:v031C* + ID_VENDOR_FROM_DATABASE=Lab Sensor Solutions + +bluetooth:v031D* + ID_VENDOR_FROM_DATABASE=Enterlab ApS + +bluetooth:v031E* + ID_VENDOR_FROM_DATABASE=Eyefi, Inc. + +bluetooth:v031F* + ID_VENDOR_FROM_DATABASE=MetaSystem S.p.A + +bluetooth:v0320* + ID_VENDOR_FROM_DATABASE=SONO ELECTRONICS. CO., LTD + +bluetooth:v0321* + ID_VENDOR_FROM_DATABASE=Jewelbots + +bluetooth:v0322* + ID_VENDOR_FROM_DATABASE=Compumedics Limited + +bluetooth:v0323* + ID_VENDOR_FROM_DATABASE=Rotor Bike Components + +bluetooth:v0324* + ID_VENDOR_FROM_DATABASE=Astro, Inc. + +bluetooth:v0325* + ID_VENDOR_FROM_DATABASE=Amotus Solutions + +bluetooth:v0326* + ID_VENDOR_FROM_DATABASE=Healthwear Technologies (Changzhou)Ltd + +bluetooth:v0327* + ID_VENDOR_FROM_DATABASE=Essex Electronics + +bluetooth:v0328* + ID_VENDOR_FROM_DATABASE=Grundfos A/S + +bluetooth:v0329* + ID_VENDOR_FROM_DATABASE=Eargo, Inc. + +bluetooth:v032A* + ID_VENDOR_FROM_DATABASE=Electronic Design Lab + +bluetooth:v032B* + ID_VENDOR_FROM_DATABASE=ESYLUX + +bluetooth:v032C* + ID_VENDOR_FROM_DATABASE=NIPPON SMT.CO.,Ltd + +bluetooth:v032D* + ID_VENDOR_FROM_DATABASE=BM innovations GmbH + +bluetooth:v032E* + ID_VENDOR_FROM_DATABASE=indoormap + +bluetooth:v032F* + ID_VENDOR_FROM_DATABASE=OttoQ Inc + +bluetooth:v0330* + ID_VENDOR_FROM_DATABASE=North Pole Engineering + +bluetooth:v0331* + ID_VENDOR_FROM_DATABASE=3flares Technologies Inc. + +bluetooth:v0332* + ID_VENDOR_FROM_DATABASE=Electrocompaniet A.S. + +bluetooth:v0333* + ID_VENDOR_FROM_DATABASE=Mul-T-Lock + +bluetooth:v0334* + ID_VENDOR_FROM_DATABASE=Corentium AS diff --git a/man/networkd.conf.xml b/man/networkd.conf.xml index 5e2927ba54..30674e12bc 100644 --- a/man/networkd.conf.xml +++ b/man/networkd.conf.xml @@ -5,7 +5,7 @@ <!-- This file is part of systemd. - Copyright 2014 Tom Gundersen + Copyright 2014 Vinay Kulkarni systemd is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by @@ -67,9 +67,19 @@ <refsect1> <title>[DUID] Section Options</title> - <para>This section configures the DUID value used by the DHCP protocol. The DUID value - specified here overrides the DUID that systemd-networkd generates using the machine-id - from the <filename>/etc/machine-id</filename> file.</para> + <para>This section configures the DHCP Unique Idendifier (DUID) value used by DHCP + protocol. DHCPv6 client protocol sends the DHCP Unique Identifier and the interface + Identity Association Identifier (IAID) to a DHCP server when acquiring a dynamic IPv6 + address. DHCPv4 client protocol sends IAID and DUID to the DHCP server when acquiring + a dynamic IPv4 address if <option>ClientIdentifier=duid</option>. IAID and DUID allows + a DHCP server to uniquely identify the machine and the interface requesting a DHCP IP. + To configure IAID and ClientIdentifier, see <citerefentry><refentrytitle>systemd.network + </refentrytitle><manvolnum>5</manvolnum></citerefentry>.</para> + + <para>The DUID value specified here overrides the DUID that systemd-networkd + generates using the machine-id from the <filename>/etc/machine-id</filename> file. + To configure DUID per-network, see <citerefentry><refentrytitle>systemd.network + </refentrytitle><manvolnum>5</manvolnum></citerefentry>.</para> <para>The configured DHCP DUID should conform to the specification in <ulink url="http://tools.ietf.org/html/rfc3315#section-9">RFC 3315</ulink>, @@ -88,7 +98,18 @@ <para>raw : If <literal>Type=raw</literal>, then <literal>RawData=</literal> specifies the entire DUID. For e.g: <literal>RawData=00:02:00:00:ab:11:f9:2a:c2:77:29:f9:5c:00</literal> specifies a 14 byte long DUID-EN ("00:02"), with enterprise number 43793 ("00:00:ab:11"), - and identifier value "f9:2a:c2:77:29:f9:5c:00".</para></listitem> + and identifier value "f9:2a:c2:77:29:f9:5c:00".</para><para>If Type is not specified and + RawData is specified, Type defaults to 'raw'.</para> + <para>Type will support the following values in the future:</para> + <para>link-layer-and-time : If <literal>Type=link-layer-and-time</literal>, then + <literal>MACAddress=</literal> and <literal>TimeStamp=</literal> specify the hardware + address and time-stamp for DUID-LLT.</para> + <para>vendor : If <literal>Type=vendor</literal>, then <literal>EnterpriseNumber=</literal> + and <literal>RawData=</literal> specify the enterprise number and identifier for DUID-EN.</para> + <para>link-layer : If <literal>Type=link-layer</literal>, then <literal>MACAddress=</literal> + specifies the hardware address for DUID-LL.</para> + <para>uuid : If <literal>Type=uuid</literal>, then <literal>UUID=</literal> specifies DUID-UUID. + </para></listitem> </varlistentry> <varlistentry> @@ -96,7 +117,33 @@ <listitem><para>Specifies the DUID bytes as a single newline-terminated, hexadecimal string, with each byte separated by a ':'.</para></listitem> </varlistentry> + </variablelist> + </refsect1> + <refsect1> + <para>The following options will be supported in the future: + </para> + <variablelist> + <varlistentry> + <term><varname>MACAddress=</varname></term> + <listitem><para>Specifies the link-layer address for DUID Type <option>link-layer + </option> or <option>link-layer-and-time</option>.</para></listitem> + </varlistentry> + <varlistentry> + <term><varname>TimeStamp=</varname></term> + <listitem><para>Specifies the DUID generation time for DUID Type <option> + link-layer-and-time</option>.</para></listitem> + </varlistentry> + <varlistentry> + <term><varname>EnterpriseNumber=</varname></term> + <listitem><para>Specifies the enterprise number for DUID Type + <option>vendor</option>.</para></listitem> + </varlistentry> + <varlistentry> + <term><varname>UUID=</varname></term> + <listitem><para>Specifies the UUID for DUID Type <option>uuid</option>.</para> + </listitem> + </varlistentry> </variablelist> </refsect1> diff --git a/man/nss-myhostname.xml b/man/nss-myhostname.xml index f8837745ae..a920ec334f 100644 --- a/man/nss-myhostname.xml +++ b/man/nss-myhostname.xml @@ -70,9 +70,10 @@ is on the local loopback) and the IPv6 address ::1 (which is the local host).</para></listitem> - <listitem><para>The hostname <literal>localhost</literal> (as well as any hostname ending in - <literal>.localhost</literal>, <literal>.localdomain</literal> or equal to <literal>localdomain</literal>) is - resolved to the IP addresses 127.0.0.1 and ::1.</para></listitem> + <listitem><para>The hostnames <literal>localhost</literal> and + <literal>localhost.localdomain</literal> (as well as any hostname + ending in <literal>.localhost</literal> or <literal>.localhost.localdomain</literal>) + are resolved to the IP addresses 127.0.0.1 and ::1.</para></listitem> <listitem><para>The hostname <literal>gateway</literal> is resolved to all current default routing gateway addresses, diff --git a/man/systemd-resolved.service.xml b/man/systemd-resolved.service.xml index 7a9e23a2c6..829729ca09 100644 --- a/man/systemd-resolved.service.xml +++ b/man/systemd-resolved.service.xml @@ -87,9 +87,10 @@ is on the local loopback) and the IPv6 address ::1 (which is the local host).</para></listitem> - <listitem><para>The hostname <literal>localhost</literal> (as well as any hostname ending in - <literal>.localhost</literal>, <literal>.localdomain</literal> or equal to <literal>localdomain</literal>) is - resolved to the IP addresses 127.0.0.1 and ::1.</para></listitem> + <listitem><para>The hostnames <literal>localhost</literal> and + <literal>localhost.localdomain</literal> (as well as any hostname + ending in <literal>.localhost</literal> or <literal>.localhost.localdomain</literal>) + are resolved to the IP addresses 127.0.0.1 and ::1.</para></listitem> <listitem><para>The hostname <literal>gateway</literal> is resolved to all current default routing gateway addresses, diff --git a/man/systemd-run.xml b/man/systemd-run.xml index 414e1c8335..473f83eac6 100644 --- a/man/systemd-run.xml +++ b/man/systemd-run.xml @@ -345,7 +345,7 @@ provided by systemd to services:</para> <programlisting># systemd-run env -Running as unit run-19945.service. +Running as unit: run-19945.service # journalctl -u run-19945.service Sep 08 07:37:21 bupkis systemd[1]: Starting /usr/bin/env... Sep 08 07:37:21 bupkis systemd[1]: Started /usr/bin/env. @@ -366,8 +366,8 @@ Sep 08 07:37:21 bupkis env[19948]: BOOT_IMAGE=/vmlinuz-3.11.0-0.rc5.git6.2.fc20. <programlisting># date; systemd-run --on-active=30 --timer-property=AccuracySec=100ms /bin/touch /tmp/foo Mon Dec 8 20:44:24 KST 2014 -Running as unit run-71.timer. -Will run as unit run-71.service. +Running as unit: run-71.timer +Will run service as unit: run-71.service # journalctl -b -u run-71.timer -- Logs begin at Fri 2014-12-05 19:09:21 KST, end at Mon 2014-12-08 20:44:54 KST. -- Dec 08 20:44:38 container systemd[1]: Starting /bin/touch /tmp/foo. diff --git a/man/systemd-sysv-generator.xml b/man/systemd-sysv-generator.xml index bb5cc55e9f..2353eb3efe 100644 --- a/man/systemd-sysv-generator.xml +++ b/man/systemd-sysv-generator.xml @@ -77,7 +77,7 @@ which correspond to runlevels for which the script is enabled.</para> - <para><command>systemd</command> does not supports SysV scripts as + <para><command>systemd</command> does not support SysV scripts as part of early boot, so all wrapper units are ordered after <filename>basic.target</filename>.</para> diff --git a/man/systemd.exec.xml b/man/systemd.exec.xml index c1f47e84e6..3e1a2cb224 100644 --- a/man/systemd.exec.xml +++ b/man/systemd.exec.xml @@ -1155,7 +1155,9 @@ first character of the list is <literal>~</literal>, the effect is inverted: only the listed system calls will result in immediate process termination (blacklisting). If running in - user mode and this option is used, + user mode, or in system mode, but without the + <constant>CAP_SYS_ADMIN</constant> capabiblity (e.g. setting + <varname>User=nobody</varname>), <varname>NoNewPrivileges=yes</varname> is implied. This feature makes use of the Secure Computing Mode 2 interfaces of the kernel ('seccomp filtering') and is useful for enforcing a @@ -1214,8 +1216,10 @@ systems. The special <constant>native</constant> identifier implicitly maps to the native architecture of the system (or more strictly: to the architecture the system manager is - compiled for). If running in user mode and this option is - used, <varname>NoNewPrivileges=yes</varname> is implied. Note + compiled for). If running in user mode, or in system mode, + but without the <constant>CAP_SYS_ADMIN</constant> + capabiblity (e.g. setting <varname>User=nobody</varname>), + <varname>NoNewPrivileges=yes</varname> is implied. Note that setting this option to a non-empty list implies that <constant>native</constant> is included too. By default, this option is set to the empty list, i.e. no architecture system @@ -1244,8 +1248,10 @@ <function>socketpair()</function> (which creates connected AF_UNIX sockets only) are unaffected. Note that this option has no effect on 32-bit x86 and is ignored (but works - correctly on x86-64). If running in user mode and this option - is used, <varname>NoNewPrivileges=yes</varname> is implied. By + correctly on x86-64). If running in user mode, or in system + mode, but without the <constant>CAP_SYS_ADMIN</constant> + capabiblity (e.g. setting <varname>User=nobody</varname>), + <varname>NoNewPrivileges=yes</varname> is implied. By default, no restriction applies, all address families are accessible to processes. If assigned the empty string, any previous list changes are undone.</para> diff --git a/man/systemd.network.xml b/man/systemd.network.xml index 73b9c00543..b2e1d40287 100644 --- a/man/systemd.network.xml +++ b/man/systemd.network.xml @@ -205,9 +205,9 @@ </listitem> </varlistentry> <varlistentry> - <term><varname>IAIDValue=</varname></term> + <term><varname>IAID=</varname></term> <listitem> - <para>Identity Association Identifier for the interface. This is a 32-bit value specified in host byte order.</para> + <para>Identity Association Identifier for the interface, a 32-bit unsigned integer.</para> </listitem> </varlistentry> </variablelist> @@ -830,6 +830,86 @@ </refsect1> <refsect1> + <title>[DUID] Section Options</title> + + <para>This section configures the DHCP Unique Idendifier (DUID) value used by DHCP + protocol. DHCPv6 client protocol sends the DHCP Unique Identifier and the interface + Identity Association Identifier (IAID) to a DHCP server when acquiring a dynamic IPv6 + address. DHCPv4 client protocol sends IAID and DUID to the DHCP server when acquiring + a dynamic IPv4 address if <option>ClientIdentifier=duid</option>. IAID and DUID allows a + DHCP server to uniquely identify the machine and the interface requesting a DHCP IP.</para> + + <para>The DUID value specified here overrides the DUID that systemd-networkd generates + using the machine-id from the <filename>/etc/machine-id</filename> file, as well as the + global DUID that may be specified in <citerefentry><refentrytitle>networkd.conf + </refentrytitle><manvolnum>5</manvolnum></citerefentry>.</para> + + <para>The configured DHCP DUID should conform to the specification in + <ulink url="http://tools.ietf.org/html/rfc3315#section-9">RFC 3315</ulink>, + <ulink url="http://tools.ietf.org/html/rfc6355">RFC 6355</ulink>.</para> + + <para>The following options are available in <literal>[DUID]</literal> section:</para> + + <variablelist class='network-directives'> + + <varlistentry> + <term><varname>Type=</varname></term> + <listitem><para>The type of DUID specified in this section. The following values are + supported:</para> + <para>raw : If <literal>Type=raw</literal>, then <literal>RawData=</literal> specifies + the entire DUID. For e.g: <literal>RawData=00:02:00:00:ab:11:f9:2a:c2:77:29:f9:5c:00</literal> + specifies a 14 byte long DUID-EN ("00:02"), with enterprise number 43793 ("00:00:ab:11"), + and identifier value "f9:2a:c2:77:29:f9:5c:00".</para><para>If Type is not specified and + RawData is specified, Type defaults to 'raw'.</para> + <para>Type will support the following values in the future:</para> + <para>link-layer-and-time : If <literal>Type=link-layer-and-time</literal>, then + <literal>MACAddress=</literal> and <literal>TimeStamp=</literal> specify the hardware + address and time-stamp for DUID-LLT.</para> + <para>vendor : If <literal>Type=vendor</literal>, then <literal>EnterpriseNumber=</literal> + and <literal>RawData=</literal> specify the enterprise number and identifier for DUID-EN.</para> + <para>link-layer : If <literal>Type=link-layer</literal>, then <literal>MACAddress=</literal> + specifies the hardware address for DUID-LL.</para> + <para>uuid : If <literal>Type=uuid</literal>, then <literal>UUID=</literal> specifies DUID-UUID. + </para></listitem> + </varlistentry> + + <varlistentry> + <term><varname>RawData=</varname></term> + <listitem><para>Specifies the DUID bytes as a single newline-terminated, hexadecimal + string, with each byte separated by a ':'.</para></listitem> + </varlistentry> + + </variablelist> + </refsect1> + + <refsect1> + <para>The following options will be supported in the future: + </para> + <variablelist> + <varlistentry> + <term><varname>MACAddress=</varname></term> + <listitem><para>Specifies the link-layer address for DUID Type <option>link-layer + </option> or <option>link-layer-and-time</option>.</para></listitem> + </varlistentry> + <varlistentry> + <term><varname>TimeStamp=</varname></term> + <listitem><para>Specifies the DUID generation time for DUID Type <option> + link-layer-and-time</option>.</para></listitem> + </varlistentry> + <varlistentry> + <term><varname>EnterpriseNumber=</varname></term> + <listitem><para>Specifies the enterprise number for DUID Type <option> + vendor</option>.</para></listitem> + </varlistentry> + <varlistentry> + <term><varname>UUID=</varname></term> + <listitem><para>Specifies the UUID for DUID Type <option>uuid</option>.</para> + </listitem> + </varlistentry> + </variablelist> + </refsect1> + + <refsect1> <title>[DHCPServer] Section Options</title> <para>The <literal>[DHCPServer]</literal> section contains settings for the DHCP server, if enabled via the diff --git a/man/systemd.offline-updates.xml b/man/systemd.offline-updates.xml new file mode 100644 index 0000000000..946234ad90 --- /dev/null +++ b/man/systemd.offline-updates.xml @@ -0,0 +1,169 @@ +<?xml version='1.0'?> <!--*-nxml-*--> +<!DOCTYPE refentry PUBLIC "-//OASIS//DTD DocBook XML V4.2//EN" + "http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd"> + +<!-- + This file is part of systemd. + + Copyright 2013 Lennart Poettering + Copyright 2016 Zbigniew Jędrzejewski-Szmek + + systemd is free software; you can redistribute it and/or modify it + under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or + (at your option) any later version. + + systemd is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with systemd; If not, see <http://www.gnu.org/licenses/>. +--> + +<refentry id="systemd.offline-updates"> + <refentryinfo> + <title>systemd.offline-updates</title> + <productname>systemd</productname> + + <authorgroup> + <author> + <contrib>Developer</contrib> + <firstname>Lennart</firstname> + <surname>Poettering</surname> + <email>lennart@poettering.net</email> + </author> + </authorgroup> + </refentryinfo> + + <refmeta> + <refentrytitle>systemd.offline-updates</refentrytitle> + <manvolnum>7</manvolnum> + </refmeta> + + <refnamediv> + <refname>systemd.offline-updates</refname> + <refpurpose>Implementation of offline updates in systemd</refpurpose> + </refnamediv> + + <refsect1> + <title>Implementing Offline System Updates</title> + + <para>This man page describes how to implement "offline" system updates with systemd. By "offline" + OS updates we mean package installations and updates that are run with the system booted into a + special system update mode, in order to avoid problems related to conflicts of libraries and + services that are currently running with those on disk. This document is inspired by this + <ulink url="https://wiki.gnome.org/Design/OS/SoftwareUpdates">GNOME design whiteboard</ulink>. + </para> + + <para>The logic:</para> + + <orderedlist> + <listitem> + <para>The package manager prepares system updates by downloading all (RPM or DEB or + whatever) packages to update off-line in a special directory + <filename noindex="true">/var/lib/system-update</filename> (or + another directory of the package/upgrade manager's choice).</para> + </listitem> + + <listitem> + <para>When the user OK'ed the update, the symlink <filename>/system-update</filename> is + created that points to <filename noindex="true">/var/lib/system-update</filename> (or + wherever the directory with the upgrade files is located) and the system is rebooted. This + symlink is in the root directory, since we need to check for it very early at boot, at a + time where <filename>/var</filename> is not available yet.</para> + </listitem> + + <listitem> + <para>Very early in the new boot + <citerefentry><refentrytitle>systemd-update-generator</refentrytitle><manvolnum>8</manvolnum></citerefentry> + checks whether <filename>/system-update</filename> exists. If so, it (temporarily and for + this boot only) redirects (i.e. symlinks) <filename>default.target</filename> to + <filename>system-update.target</filename>, a special target that is pulls in the base system + (i.e. <filename>sysinit.target</filename>, so that all file systems are mounted but little + else) and the system update units.</para> + </listitem> + + <listitem> + <para>The system now continues to boot into <filename>default.target</filename>, and thus + into <filename>system-update.target</filename>. This target pulls in the system update unit, + which starts the system update script after all file systems have been mounted.</para> + </listitem> + + <listitem> + <para>As the first step, the update script should check if the + <filename>/system-update</filename> symlink points to the the location used by that update + script. In case it does not exists or points to a different location, the script must exit + without error. It is possible for multiple update services to be installed, and for multiple + update scripts to be launched in parallel, and only the one that corresponds to the tool + that <emphasis>created</emphasis> the symlink before reboot should perform any actions. It + is unsafe to run multiple updates in parallel.</para> + </listitem> + + <listitem> + <para>The update script should now do its job. If applicable and possible, it should + create a file system snapshot, then install all packages. + After completion (regardless whether the update succeeded or failed) the machine + must be rebooted, for example by calling <command>systemctl reboot</command>. + In addition, on failure the script should revert to the old file system snapshot + (without the symlink).</para> + </listitem> + + <listitem> + <para>The system is rebooted. Since the <filename>/system-update</filename> symlink is gone, + the generator won't redirect <filename>default.target</filename> after reboot and the + system now boots into the default target again.</para> + </listitem> + </orderedlist> + </refsect1> + + <refsect1> + <title>Recommendations</title> + + <orderedlist> + <listitem> + <para>To make things a bit more robust we recommend hooking the update script into + <filename>system-update.target</filename> via a <filename noindex='true'>.wants/</filename> + symlink in the distribution package, rather than depending on <command>systemctl + enable</command> in the postinst scriptlets of your package. More specifically, for your + update script create a .service file, without [Install] section, and then add a symlink like + <filename noindex='true'>/usr/lib/systemd/system-update.target.wants/foobar.service</filename> + → <filename noindex='true'>../foobar.service</filename> to your package.</para> + </listitem> + + <listitem> + <para>Make sure to remove the <filename>/system-update</filename> symlink as early as + possible in the update script to avoid reboot loops in case the update fails.</para> + </listitem> + + <listitem> + <para>Use <varname>FailureAction=reboot</varname> in the service file for your update script + to ensure that a reboot is automatically triggered if the update fails. + <varname>FailureAction=</varname> makes sure that the specified unit is activated if your + script exits uncleanly (by non-zero error code, or signal/coredump). If your script succeeds + you should trigger the reboot in your own code, for example by invoking logind's + <command>Reboot()</command> call or calling <command>systemct reboot</command>. See + <ulink url="http://www.freedesktop.org/wiki/Software/systemd/logind">logind dbus API</ulink> + for details.</para> + </listitem> + + <listitem> + <para>The update service should declare <varname>DefaultDependencies=false</varname>, + and pull in any services it requires explicitly.</para> + </listitem> + </orderedlist> + </refsect1> + + <refsect1> + <title>See also</title> + + <para> + <ulink url="http://www.freedesktop.org/wiki/Software/systemd/SystemUpdates/">Implementing Offline System Updates</ulink>, + <citerefentry><refentrytitle>systemd</refentrytitle><manvolnum>1</manvolnum></citerefentry>, + <citerefentry><refentrytitle>systemd.generator</refentrytitle><manvolnum>7</manvolnum></citerefentry>, + <citerefentry><refentrytitle>systemd-update-generator</refentrytitle><manvolnum>8</manvolnum></citerefentry>, + <citerefentry><refentrytitle>dnf.plugin.system-upgrade</refentrytitle><manvolnum>8</manvolnum></citerefentry> + </para> + </refsect1> +</refentry> diff --git a/man/systemd.resource-control.xml b/man/systemd.resource-control.xml index 08cdf06e23..fd6f7a1b69 100644 --- a/man/systemd.resource-control.xml +++ b/man/systemd.resource-control.xml @@ -202,7 +202,7 @@ controls the <literal>memory.limit_in_bytes</literal> control group attribute. For details about this control group attribute, see <ulink - url="https://www.kernel.org/doc/Documentation/cgroups/memory.txt">memory.txt</ulink>.</para> + url="https://www.kernel.org/doc/Documentation/cgroup-v1/memory.txt">memory.txt</ulink>.</para> <para>Implies <literal>MemoryAccounting=true</literal>.</para> </listitem> @@ -239,7 +239,7 @@ controls the <literal>pids.max</literal> control group attribute. For details about this control group attribute, see <ulink - url="https://www.kernel.org/doc/Documentation/cgroups/pids.txt">pids.txt</ulink>.</para> + url="https://www.kernel.org/doc/Documentation/cgroup-v1/pids.txt">pids.txt</ulink>.</para> <para>Implies <literal>TasksAccounting=true</literal>. The system default for this setting may be controlled with @@ -273,7 +273,7 @@ the <literal>blkio.weight</literal> control group attribute, which defaults to 500. For details about this control group attribute, see <ulink - url="https://www.kernel.org/doc/Documentation/cgroups/blkio-controller.txt">blkio-controller.txt</ulink>. + url="https://www.kernel.org/doc/Documentation/cgroup-v1/blkio-controller.txt">blkio-controller.txt</ulink>. The available I/O bandwidth is split up among all units within one slice relative to their block I/O weight.</para> @@ -305,7 +305,7 @@ attribute, which defaults to 1000. Use this option multiple times to set weights for multiple devices. For details about this control group attribute, see <ulink - url="https://www.kernel.org/doc/Documentation/cgroups/blkio-controller.txt">blkio-controller.txt</ulink>.</para> + url="https://www.kernel.org/doc/Documentation/cgroup-v1/blkio-controller.txt">blkio-controller.txt</ulink>.</para> <para>Implies <literal>BlockIOAccounting=true</literal>.</para> @@ -328,12 +328,12 @@ Gigabytes, or Terabytes, respectively, to the base of 1000. (Example: "/dev/disk/by-path/pci-0000:00:1f.2-scsi-0:0:0:0 5M"). This - controls the <literal>blkio.read_bps_device</literal> and - <literal>blkio.write_bps_device</literal> control group + controls the <literal>blkio.throttle.read_bps_device</literal> and + <literal>blkio.throttle.write_bps_device</literal> control group attributes. Use this option multiple times to set bandwidth limits for multiple devices. For details about these control group attributes, see <ulink - url="https://www.kernel.org/doc/Documentation/cgroups/blkio-controller.txt">blkio-controller.txt</ulink>. + url="https://www.kernel.org/doc/Documentation/cgroup-v1/blkio-controller.txt">blkio-controller.txt</ulink>. </para> <para>Implies @@ -357,7 +357,7 @@ <literal>devices.deny</literal> control group attributes. For details about these control group attributes, see <ulink - url="https://www.kernel.org/doc/Documentation/cgroups/devices.txt">devices.txt</ulink>.</para> + url="https://www.kernel.org/doc/Documentation/cgroup-v1/devices.txt">devices.txt</ulink>.</para> <para>The device node specifier is either a path to a device node in the file system, starting with @@ -482,10 +482,10 @@ <citerefentry><refentrytitle>systemd.directives</refentrytitle><manvolnum>7</manvolnum></citerefentry>, <citerefentry><refentrytitle>systemd.special</refentrytitle><manvolnum>7</manvolnum></citerefentry>, The documentation for control groups and specific controllers in the Linux kernel: - <ulink url="https://www.kernel.org/doc/Documentation/cgroups/cgroups.txt">cgroups.txt</ulink>, - <ulink url="https://www.kernel.org/doc/Documentation/cgroups/cpuacct.txt">cpuacct.txt</ulink>, - <ulink url="https://www.kernel.org/doc/Documentation/cgroups/memory.txt">memory.txt</ulink>, - <ulink url="https://www.kernel.org/doc/Documentation/cgroups/blkio-controller.txt">blkio-controller.txt</ulink>. + <ulink url="https://www.kernel.org/doc/Documentation/cgroup-v1/cgroups.txt">cgroups.txt</ulink>, + <ulink url="https://www.kernel.org/doc/Documentation/cgroup-v1/cpuacct.txt">cpuacct.txt</ulink>, + <ulink url="https://www.kernel.org/doc/Documentation/cgroup-v1/memory.txt">memory.txt</ulink>, + <ulink url="https://www.kernel.org/doc/Documentation/cgroup-v1/blkio-controller.txt">blkio-controller.txt</ulink>. </para> </refsect1> </refentry> diff --git a/man/udev_device_get_syspath.xml b/man/udev_device_get_syspath.xml index ca9763fedf..b54749ed56 100644 --- a/man/udev_device_get_syspath.xml +++ b/man/udev_device_get_syspath.xml @@ -127,6 +127,8 @@ <funcprototype> <funcdef>struct udev_device *<function>udev_device_get_parent_with_subsystem_devtype</function></funcdef> <paramdef>struct udev_device *<parameter>udev_device</parameter></paramdef> + <paramdef>const char *<parameter>subsystem</parameter></paramdef> + <paramdef>const char *<parameter>devtype</parameter></paramdef> </funcprototype> <funcprototype> @@ -137,8 +139,6 @@ <funcprototype> <funcdef>const char *<function>udev_device_get_action</function></funcdef> <paramdef>struct udev_device *<parameter>udev_device</parameter></paramdef> - <paramdef>const char *<parameter>subsystem</parameter></paramdef> - <paramdef>const char *<parameter>devtype</parameter></paramdef> </funcprototype> </funcsynopsis> diff --git a/shell-completion/bash/systemd-nspawn b/shell-completion/bash/systemd-nspawn index 8318f6e590..0cf249d8ce 100644 --- a/shell-completion/bash/systemd-nspawn +++ b/shell-completion/bash/systemd-nspawn @@ -60,14 +60,14 @@ _systemd_nspawn() { [ARG]='-D --directory -u --user --uuid --capability --drop-capability --link-journal --bind --bind-ro -M --machine -S --slice --setenv -Z --selinux-context -L --selinux-apifs-context --register --network-interface --network-bridge --personality -i --image --tmpfs --volatile - --network-macvlan --kill-signal' + --network-macvlan --kill-signal --template' ) _init_completion || return if __contains_word "$prev" ${OPTS[ARG]}; then case $prev in - --directory|-D) + --directory|-D|--template) compopt -o nospace comps=$(compgen -S/ -A directory -- "$cur" ) ;; diff --git a/src/activate/activate.c b/src/activate/activate.c index 8ac8dd8e72..a0cfc22000 100644 --- a/src/activate/activate.c +++ b/src/activate/activate.c @@ -316,19 +316,31 @@ static int do_accept(const char* name, char **argv, char **envp, int fd) { } /* SIGCHLD handler. */ -static void sigchld_hdl(int sig, siginfo_t *t, void *data) { +static void sigchld_hdl(int sig) { PROTECT_ERRNO; - log_info("Child %d died with code %d", t->si_pid, t->si_status); + for (;;) { + siginfo_t si; + int r; - /* Wait for a dead child. */ - (void) waitpid(t->si_pid, NULL, 0); + si.si_pid = 0; + r = waitid(P_ALL, 0, &si, WEXITED|WNOHANG); + if (r < 0) { + if (errno != ECHILD) + log_error_errno(errno, "Failed to reap children: %m"); + return; + } + if (si.si_pid == 0) + return; + + log_info("Child %d died with code %d", si.si_pid, si.si_status); + } } static int install_chld_handler(void) { static const struct sigaction act = { - .sa_flags = SA_SIGINFO, - .sa_sigaction = sigchld_hdl, + .sa_flags = SA_NOCLDSTOP, + .sa_handler = sigchld_hdl, }; int r; diff --git a/src/basic/c-rbtree.c b/src/basic/c-rbtree.c index 914d7e5229..cf5a7242df 100644 --- a/src/basic/c-rbtree.c +++ b/src/basic/c-rbtree.c @@ -195,11 +195,6 @@ static inline void c_rbnode_set_parent_and_color(CRBNode *n, CRBNode *p, unsigne n->__parent_and_color = (CRBNode*)((unsigned long)p | c); } -/* same as c_rbnode_set_parent_and_color(), but keeps the current parent */ -static inline void c_rbnode_set_color(CRBNode *n, unsigned long c) { - c_rbnode_set_parent_and_color(n, c_rbnode_parent(n), c); -} - /* same as c_rbnode_set_parent_and_color(), but keeps the current color */ static inline void c_rbnode_set_parent(CRBNode *n, CRBNode *p) { c_rbnode_set_parent_and_color(n, p, c_rbnode_color(n)); diff --git a/src/basic/cgroup-util.c b/src/basic/cgroup-util.c index 56c1fcaab9..5043180747 100644 --- a/src/basic/cgroup-util.c +++ b/src/basic/cgroup-util.c @@ -101,6 +101,39 @@ int cg_read_pid(FILE *f, pid_t *_pid) { return 1; } +int cg_read_event(const char *controller, const char *path, const char *event, + char **val) +{ + _cleanup_free_ char *events = NULL, *content = NULL; + char *p, *line; + int r; + + r = cg_get_path(controller, path, "cgroup.events", &events); + if (r < 0) + return r; + + r = read_full_file(events, &content, NULL); + if (r < 0) + return r; + + p = content; + while ((line = strsep(&p, "\n"))) { + char *key; + + key = strsep(&line, " "); + if (!key || !line) + return -EINVAL; + + if (strcmp(key, event)) + continue; + + *val = strdup(line); + return 0; + } + + return -ENOENT; +} + int cg_enumerate_subgroups(const char *controller, const char *path, DIR **_d) { _cleanup_free_ char *fs = NULL; int r; @@ -1007,18 +1040,12 @@ int cg_is_empty_recursive(const char *controller, const char *path) { return unified; if (unified > 0) { - _cleanup_free_ char *populated = NULL, *t = NULL; + _cleanup_free_ char *t = NULL; /* On the unified hierarchy we can check empty state - * via the "cgroup.populated" attribute. */ + * via the "populated" attribute of "cgroup.events". */ - r = cg_get_path(controller, path, "cgroup.populated", &populated); - if (r < 0) - return r; - - r = read_one_line_file(populated, &t); - if (r == -ENOENT) - return 1; + r = cg_read_event(controller, path, "populated", &t); if (r < 0) return r; @@ -2129,7 +2156,7 @@ int cg_unified(void) { if (statfs("/sys/fs/cgroup/", &fs) < 0) return -errno; - if (F_TYPE_EQUAL(fs.f_type, CGROUP_SUPER_MAGIC)) + if (F_TYPE_EQUAL(fs.f_type, CGROUP2_SUPER_MAGIC)) unified_cache = true; else if (F_TYPE_EQUAL(fs.f_type, TMPFS_MAGIC)) unified_cache = false; diff --git a/src/basic/cgroup-util.h b/src/basic/cgroup-util.h index ad1edd9cdb..4254e51e5d 100644 --- a/src/basic/cgroup-util.h +++ b/src/basic/cgroup-util.h @@ -96,6 +96,8 @@ static inline bool CGROUP_BLKIO_WEIGHT_IS_OK(uint64_t x) { int cg_enumerate_processes(const char *controller, const char *path, FILE **_f); int cg_read_pid(FILE *f, pid_t *_pid); +int cg_read_event(const char *controller, const char *path, const char *event, + char **val); int cg_enumerate_subgroups(const char *controller, const char *path, DIR **_d); int cg_read_subgroup(DIR *d, char **fn); diff --git a/src/basic/copy.c b/src/basic/copy.c index 519b412941..41dc8ca79a 100644 --- a/src/basic/copy.c +++ b/src/basic/copy.c @@ -40,17 +40,38 @@ #include "fs-util.h" #include "io-util.h" #include "macro.h" +#include "missing.h" #include "string-util.h" #include "strv.h" #include "time-util.h" #include "umask-util.h" #include "xattr-util.h" -#define COPY_BUFFER_SIZE (16*1024) +#define COPY_BUFFER_SIZE (16*1024u) + +static ssize_t try_copy_file_range(int fd_in, loff_t *off_in, + int fd_out, loff_t *off_out, + size_t len, + unsigned int flags) { + static int have = -1; + ssize_t r; + + if (have == false) + return -ENOSYS; + + r = copy_file_range(fd_in, off_in, fd_out, off_out, len, flags); + if (_unlikely_(have < 0)) + have = r >= 0 || errno != ENOSYS; + if (r >= 0) + return r; + else + return -errno; +} int copy_bytes(int fdf, int fdt, uint64_t max_bytes, bool try_reflink) { - bool try_sendfile = true, try_splice = true; + bool try_cfr = true, try_sendfile = true, try_splice = true; int r; + size_t m = SSIZE_MAX; /* that the maximum that sendfile and c_f_r accept */ assert(fdf >= 0); assert(fdt >= 0); @@ -67,11 +88,9 @@ int copy_bytes(int fdf, int fdt, uint64_t max_bytes, bool try_reflink) { } for (;;) { - size_t m = COPY_BUFFER_SIZE; ssize_t n; if (max_bytes != (uint64_t) -1) { - if (max_bytes <= 0) return 1; /* return > 0 if we hit the max_bytes limit */ @@ -79,44 +98,59 @@ int copy_bytes(int fdf, int fdt, uint64_t max_bytes, bool try_reflink) { m = (size_t) max_bytes; } + /* First try copy_file_range(), unless we already tried */ + if (try_cfr) { + n = try_copy_file_range(fdf, NULL, fdt, NULL, m, 0u); + if (n < 0) { + if (!IN_SET(n, -EINVAL, -ENOSYS, -EXDEV)) + return n; + + try_cfr = false; + /* use fallback below */ + } else if (n == 0) /* EOF */ + break; + else + /* Success! */ + goto next; + } + /* First try sendfile(), unless we already tried */ if (try_sendfile) { - n = sendfile(fdt, fdf, NULL, m); if (n < 0) { - if (errno != EINVAL && errno != ENOSYS) + if (!IN_SET(errno, EINVAL, ENOSYS)) return -errno; try_sendfile = false; /* use fallback below */ } else if (n == 0) /* EOF */ break; - else if (n > 0) + else /* Success! */ goto next; } - /* The try splice, unless we already tried */ + /* Then try splice, unless we already tried */ if (try_splice) { n = splice(fdf, NULL, fdt, NULL, m, 0); if (n < 0) { - if (errno != EINVAL && errno != ENOSYS) + if (!IN_SET(errno, EINVAL, ENOSYS)) return -errno; try_splice = false; /* use fallback below */ } else if (n == 0) /* EOF */ break; - else if (n > 0) + else /* Success! */ goto next; } /* As a fallback just copy bits by hand */ { - uint8_t buf[m]; + uint8_t buf[MIN(m, COPY_BUFFER_SIZE)]; - n = read(fdf, buf, m); + n = read(fdf, buf, sizeof buf); if (n < 0) return -errno; if (n == 0) /* EOF */ @@ -132,6 +166,11 @@ int copy_bytes(int fdf, int fdt, uint64_t max_bytes, bool try_reflink) { assert(max_bytes >= (uint64_t) n); max_bytes -= n; } + /* sendfile accepts at most SSIZE_MAX-offset bytes to copy, + * so reduce our maximum by the amount we already copied, + * but don't go below our copy buffer size, unless we are + * close the the limit of bytes we are allowed to copy. */ + m = MAX(MIN(COPY_BUFFER_SIZE, max_bytes), m - n); } return 0; /* return 0 if we hit EOF earlier than the size limit */ diff --git a/src/basic/hostname-util.c b/src/basic/hostname-util.c index 5a7ee87a20..13c3bb6446 100644 --- a/src/basic/hostname-util.c +++ b/src/basic/hostname-util.c @@ -178,16 +178,16 @@ bool is_localhost(const char *hostname) { assert(hostname); /* This tries to identify local host and domain names - * described in RFC6761 plus the redhatism of .localdomain */ + * described in RFC6761 plus the redhatism of localdomain */ return strcaseeq(hostname, "localhost") || strcaseeq(hostname, "localhost.") || - strcaseeq(hostname, "localdomain.") || - strcaseeq(hostname, "localdomain") || + strcaseeq(hostname, "localhost.localdomain") || + strcaseeq(hostname, "localhost.localdomain.") || endswith_no_case(hostname, ".localhost") || endswith_no_case(hostname, ".localhost.") || - endswith_no_case(hostname, ".localdomain") || - endswith_no_case(hostname, ".localdomain."); + endswith_no_case(hostname, ".localhost.localdomain") || + endswith_no_case(hostname, ".localhost.localdomain."); } bool is_gateway_hostname(const char *hostname) { diff --git a/src/basic/locale-util.c b/src/basic/locale-util.c index cda6b2895d..eaad25e65b 100644 --- a/src/basic/locale-util.c +++ b/src/basic/locale-util.c @@ -153,6 +153,8 @@ static int add_locales_from_libdir (Set *locales) { FOREACH_DIRENT(entry, dir, return -errno) { char *z; + dirent_ensure_type(dir, entry); + if (entry->d_type != DT_DIR) continue; diff --git a/src/basic/log.h b/src/basic/log.h index f9fb1742a1..b6356228d9 100644 --- a/src/basic/log.h +++ b/src/basic/log.h @@ -246,5 +246,4 @@ int log_syntax_internal( log_syntax_internal(unit, _level, config_file, config_line, 0, __FILE__, __LINE__, __func__, \ "String is not UTF-8 clean, ignoring assignment: %s", strna(_p)); \ } \ - -EINVAL; \ }) diff --git a/src/basic/macro.h b/src/basic/macro.h index b36a95675a..e41aa4260f 100644 --- a/src/basic/macro.h +++ b/src/basic/macro.h @@ -27,7 +27,11 @@ #include <sys/types.h> #define _printf_(a,b) __attribute__ ((format (printf, a, b))) -#define _alloc_(...) __attribute__ ((alloc_size(__VA_ARGS__))) +#ifdef __clang__ +# define _alloc_(...) +#else +# define _alloc_(...) __attribute__ ((alloc_size(__VA_ARGS__))) +#endif #define _sentinel_ __attribute__ ((sentinel)) #define _unused_ __attribute__ ((unused)) #define _destructor_ __attribute__ ((destructor)) diff --git a/src/basic/missing.h b/src/basic/missing.h index 417604aa64..66cd5921ad 100644 --- a/src/basic/missing.h +++ b/src/basic/missing.h @@ -135,84 +135,6 @@ #define SOL_SCTP 132 #endif -#if !HAVE_DECL_PIVOT_ROOT -static inline int pivot_root(const char *new_root, const char *put_old) { - return syscall(SYS_pivot_root, new_root, put_old); -} -#endif - -#ifndef __NR_memfd_create -# if defined __x86_64__ -# define __NR_memfd_create 319 -# elif defined __arm__ -# define __NR_memfd_create 385 -# elif defined __aarch64__ -# define __NR_memfd_create 279 -# elif defined __s390__ -# define __NR_memfd_create 350 -# elif defined _MIPS_SIM -# if _MIPS_SIM == _MIPS_SIM_ABI32 -# define __NR_memfd_create 4354 -# endif -# if _MIPS_SIM == _MIPS_SIM_NABI32 -# define __NR_memfd_create 6318 -# endif -# if _MIPS_SIM == _MIPS_SIM_ABI64 -# define __NR_memfd_create 5314 -# endif -# elif defined __i386__ -# define __NR_memfd_create 356 -# else -# warning "__NR_memfd_create unknown for your architecture" -# define __NR_memfd_create 0xffffffff -# endif -#endif - -#if !HAVE_DECL_MEMFD_CREATE -static inline int memfd_create(const char *name, unsigned int flags) { - return syscall(__NR_memfd_create, name, flags); -} -#endif - -#ifndef __NR_getrandom -# if defined __x86_64__ -# define __NR_getrandom 318 -# elif defined(__i386__) -# define __NR_getrandom 355 -# elif defined(__arm__) -# define __NR_getrandom 384 -# elif defined(__aarch64__) -# define __NR_getrandom 278 -# elif defined(__ia64__) -# define __NR_getrandom 1339 -# elif defined(__m68k__) -# define __NR_getrandom 352 -# elif defined(__s390x__) -# define __NR_getrandom 349 -# elif defined(__powerpc__) -# define __NR_getrandom 359 -# elif defined _MIPS_SIM -# if _MIPS_SIM == _MIPS_SIM_ABI32 -# define __NR_getrandom 4353 -# endif -# if _MIPS_SIM == _MIPS_SIM_NABI32 -# define __NR_getrandom 6317 -# endif -# if _MIPS_SIM == _MIPS_SIM_ABI64 -# define __NR_getrandom 5313 -# endif -# else -# warning "__NR_getrandom unknown for your architecture" -# define __NR_getrandom 0xffffffff -# endif -#endif - -#if !HAVE_DECL_GETRANDOM -static inline int getrandom(void *buffer, size_t count, unsigned flags) { - return syscall(__NR_getrandom, buffer, count, flags); -} -#endif - #ifndef GRND_NONBLOCK #define GRND_NONBLOCK 0x0001 #endif @@ -515,6 +437,10 @@ struct btrfs_ioctl_quota_ctl_args { #define CGROUP_SUPER_MAGIC 0x27e0eb #endif +#ifndef CGROUP2_SUPER_MAGIC +#define CGROUP2_SUPER_MAGIC 0x63677270 +#endif + #ifndef TMPFS_MAGIC #define TMPFS_MAGIC 0x01021994 #endif @@ -527,12 +453,6 @@ struct btrfs_ioctl_quota_ctl_args { #define MS_PRIVATE (1 << 18) #endif -#if !HAVE_DECL_GETTID -static inline pid_t gettid(void) { - return (pid_t) syscall(SYS_gettid); -} -#endif - #ifndef SCM_SECURITY #define SCM_SECURITY 0x03 #endif @@ -561,32 +481,6 @@ static inline pid_t gettid(void) { #define MAX_HANDLE_SZ 128 #endif -#ifndef __NR_name_to_handle_at -# if defined(__x86_64__) -# define __NR_name_to_handle_at 303 -# elif defined(__i386__) -# define __NR_name_to_handle_at 341 -# elif defined(__arm__) -# define __NR_name_to_handle_at 370 -# elif defined(__powerpc__) -# define __NR_name_to_handle_at 345 -# else -# error "__NR_name_to_handle_at is not defined" -# endif -#endif - -#if !HAVE_DECL_NAME_TO_HANDLE_AT -struct file_handle { - unsigned int handle_bytes; - int handle_type; - unsigned char f_handle[0]; -}; - -static inline int name_to_handle_at(int fd, const char *name, struct file_handle *handle, int *mnt_id, int flags) { - return syscall(__NR_name_to_handle_at, fd, name, handle, mnt_id, flags); -} -#endif - #ifndef HAVE_SECURE_GETENV # ifdef HAVE___SECURE_GETENV # define secure_getenv __secure_getenv @@ -635,22 +529,6 @@ static inline int name_to_handle_at(int fd, const char *name, struct file_handle #endif -#ifndef __NR_setns -# if defined(__x86_64__) -# define __NR_setns 308 -# elif defined(__i386__) -# define __NR_setns 346 -# else -# error "__NR_setns is not defined" -# endif -#endif - -#if !HAVE_DECL_SETNS -static inline int setns(int fd, int nstype) { - return syscall(__NR_setns, fd, nstype); -} -#endif - #if !HAVE_DECL_LO_FLAGS_PARTSCAN #define LO_FLAGS_PARTSCAN 8 #endif @@ -1018,69 +896,10 @@ static inline int setns(int fd, int nstype) { #define CAP_AUDIT_READ 37 #endif -static inline int raw_clone(unsigned long flags, void *child_stack) { -#if defined(__s390__) || defined(__CRIS__) - /* On s390 and cris the order of the first and second arguments - * of the raw clone() system call is reversed. */ - return (int) syscall(__NR_clone, child_stack, flags); -#else - return (int) syscall(__NR_clone, flags, child_stack); -#endif -} - -static inline pid_t raw_getpid(void) { -#if defined(__alpha__) - return (pid_t) syscall(__NR_getxpid); -#else - return (pid_t) syscall(__NR_getpid); -#endif -} - -#if !HAVE_DECL_RENAMEAT2 - -#ifndef __NR_renameat2 -# if defined __x86_64__ -# define __NR_renameat2 316 -# elif defined __arm__ -# define __NR_renameat2 382 -# elif defined _MIPS_SIM -# if _MIPS_SIM == _MIPS_SIM_ABI32 -# define __NR_renameat2 4351 -# endif -# if _MIPS_SIM == _MIPS_SIM_NABI32 -# define __NR_renameat2 6315 -# endif -# if _MIPS_SIM == _MIPS_SIM_ABI64 -# define __NR_renameat2 5311 -# endif -# elif defined __i386__ -# define __NR_renameat2 353 -# else -# warning "__NR_renameat2 unknown for your architecture" -# define __NR_renameat2 0xffffffff -# endif -#endif - -static inline int renameat2(int oldfd, const char *oldname, int newfd, const char *newname, unsigned flags) { - return syscall(__NR_renameat2, oldfd, oldname, newfd, newname, flags); -} -#endif - #ifndef RENAME_NOREPLACE #define RENAME_NOREPLACE (1 << 0) #endif -#if !HAVE_DECL_KCMP -static inline int kcmp(pid_t pid1, pid_t pid2, int type, unsigned long idx1, unsigned long idx2) { -#if defined(__NR_kcmp) - return syscall(__NR_kcmp, pid1, pid2, type, idx1, idx2); -#else - errno = ENOSYS; - return -1; -#endif -} -#endif - #ifndef KCMP_FILE #define KCMP_FILE 0 #endif @@ -1097,35 +916,6 @@ static inline int kcmp(pid_t pid1, pid_t pid2, int type, unsigned long idx1, uns typedef int32_t key_serial_t; #endif -#if !HAVE_DECL_KEYCTL -static inline long keyctl(int cmd, unsigned long arg2, unsigned long arg3, unsigned long arg4,unsigned long arg5) { -#if defined(__NR_keyctl) - return syscall(__NR_keyctl, cmd, arg2, arg3, arg4, arg5); -#else - errno = ENOSYS; - return -1; -#endif -} - -static inline key_serial_t add_key(const char *type, const char *description, const void *payload, size_t plen, key_serial_t ringid) { -#if defined (__NR_add_key) - return syscall(__NR_add_key, type, description, payload, plen, ringid); -#else - errno = ENOSYS; - return -1; -#endif -} - -static inline key_serial_t request_key(const char *type, const char *description, const char * callout_info, key_serial_t destringid) { -#if defined (__NR_request_key) - return syscall(__NR_request_key, type, description, callout_info, destringid); -#else - errno = ENOSYS; - return -1; -#endif -} -#endif - #ifndef KEYCTL_READ #define KEYCTL_READ 11 #endif @@ -1177,3 +967,5 @@ static inline key_serial_t request_key(const char *type, const char *description #endif #endif + +#include "missing_syscall.h" diff --git a/src/basic/missing_syscall.h b/src/basic/missing_syscall.h new file mode 100644 index 0000000000..d502d3b9ca --- /dev/null +++ b/src/basic/missing_syscall.h @@ -0,0 +1,310 @@ +#pragma once + +/*** + This file is part of systemd. + + Copyright 2010 Lennart Poettering + Copyright 2016 Zbigniew Jędrzejewski-Szmek + + systemd is free software; you can redistribute it and/or modify it + under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation; either version 2.1 of the License, or + (at your option) any later version. + + systemd is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with systemd; If not, see <http://www.gnu.org/licenses/>. +***/ + +/* Missing glibc definitions to access certain kernel APIs */ + +#if !HAVE_DECL_PIVOT_ROOT +static inline int pivot_root(const char *new_root, const char *put_old) { + return syscall(SYS_pivot_root, new_root, put_old); +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_MEMFD_CREATE +# ifndef __NR_memfd_create +# if defined __x86_64__ +# define __NR_memfd_create 319 +# elif defined __arm__ +# define __NR_memfd_create 385 +# elif defined __aarch64__ +# define __NR_memfd_create 279 +# elif defined __s390__ +# define __NR_memfd_create 350 +# elif defined _MIPS_SIM +# if _MIPS_SIM == _MIPS_SIM_ABI32 +# define __NR_memfd_create 4354 +# endif +# if _MIPS_SIM == _MIPS_SIM_NABI32 +# define __NR_memfd_create 6318 +# endif +# if _MIPS_SIM == _MIPS_SIM_ABI64 +# define __NR_memfd_create 5314 +# endif +# elif defined __i386__ +# define __NR_memfd_create 356 +# else +# warning "__NR_memfd_create unknown for your architecture" +# endif +# endif + +static inline int memfd_create(const char *name, unsigned int flags) { +# ifdef __NR_memfd_create + return syscall(__NR_memfd_create, name, flags); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_GETRANDOM +# ifndef __NR_getrandom +# if defined __x86_64__ +# define __NR_getrandom 318 +# elif defined(__i386__) +# define __NR_getrandom 355 +# elif defined(__arm__) +# define __NR_getrandom 384 +# elif defined(__aarch64__) +# define __NR_getrandom 278 +# elif defined(__ia64__) +# define __NR_getrandom 1339 +# elif defined(__m68k__) +# define __NR_getrandom 352 +# elif defined(__s390x__) +# define __NR_getrandom 349 +# elif defined(__powerpc__) +# define __NR_getrandom 359 +# elif defined _MIPS_SIM +# if _MIPS_SIM == _MIPS_SIM_ABI32 +# define __NR_getrandom 4353 +# endif +# if _MIPS_SIM == _MIPS_SIM_NABI32 +# define __NR_getrandom 6317 +# endif +# if _MIPS_SIM == _MIPS_SIM_ABI64 +# define __NR_getrandom 5313 +# endif +# else +# warning "__NR_getrandom unknown for your architecture" +# endif +# endif + +static inline int getrandom(void *buffer, size_t count, unsigned flags) { +# ifdef __NR_getrandom + return syscall(__NR_getrandom, buffer, count, flags); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_GETTID +static inline pid_t gettid(void) { + return (pid_t) syscall(SYS_gettid); +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_NAME_TO_HANDLE_AT +# ifndef __NR_name_to_handle_at +# if defined(__x86_64__) +# define __NR_name_to_handle_at 303 +# elif defined(__i386__) +# define __NR_name_to_handle_at 341 +# elif defined(__arm__) +# define __NR_name_to_handle_at 370 +# elif defined(__powerpc__) +# define __NR_name_to_handle_at 345 +# else +# error "__NR_name_to_handle_at is not defined" +# endif +# endif + +struct file_handle { + unsigned int handle_bytes; + int handle_type; + unsigned char f_handle[0]; +}; + +static inline int name_to_handle_at(int fd, const char *name, struct file_handle *handle, int *mnt_id, int flags) { +# ifdef __NR_name_to_handle_at + return syscall(__NR_name_to_handle_at, fd, name, handle, mnt_id, flags); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_SETNS +# ifndef __NR_setns +# if defined(__x86_64__) +# define __NR_setns 308 +# elif defined(__i386__) +# define __NR_setns 346 +# else +# error "__NR_setns is not defined" +# endif +# endif + +static inline int setns(int fd, int nstype) { +# ifdef __NR_setns + return syscall(__NR_setns, fd, nstype); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +static inline int raw_clone(unsigned long flags, void *child_stack) { +#if defined(__s390__) || defined(__CRIS__) + /* On s390 and cris the order of the first and second arguments + * of the raw clone() system call is reversed. */ + return (int) syscall(__NR_clone, child_stack, flags); +#else + return (int) syscall(__NR_clone, flags, child_stack); +#endif +} + +/* ======================================================================= */ + +static inline pid_t raw_getpid(void) { +#if defined(__alpha__) + return (pid_t) syscall(__NR_getxpid); +#else + return (pid_t) syscall(__NR_getpid); +#endif +} + +/* ======================================================================= */ + +#if !HAVE_DECL_RENAMEAT2 +# ifndef __NR_renameat2 +# if defined __x86_64__ +# define __NR_renameat2 316 +# elif defined __arm__ +# define __NR_renameat2 382 +# elif defined _MIPS_SIM +# if _MIPS_SIM == _MIPS_SIM_ABI32 +# define __NR_renameat2 4351 +# endif +# if _MIPS_SIM == _MIPS_SIM_NABI32 +# define __NR_renameat2 6315 +# endif +# if _MIPS_SIM == _MIPS_SIM_ABI64 +# define __NR_renameat2 5311 +# endif +# elif defined __i386__ +# define __NR_renameat2 353 +# else +# warning "__NR_renameat2 unknown for your architecture" +# endif +# endif + +static inline int renameat2(int oldfd, const char *oldname, int newfd, const char *newname, unsigned flags) { +# ifdef __NR_renameat2 + return syscall(__NR_renameat2, oldfd, oldname, newfd, newname, flags); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_KCMP +static inline int kcmp(pid_t pid1, pid_t pid2, int type, unsigned long idx1, unsigned long idx2) { +# ifdef __NR_kcmp + return syscall(__NR_kcmp, pid1, pid2, type, idx1, idx2); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_KEYCTL +static inline long keyctl(int cmd, unsigned long arg2, unsigned long arg3, unsigned long arg4,unsigned long arg5) { +# ifdef __NR_keyctl + return syscall(__NR_keyctl, cmd, arg2, arg3, arg4, arg5); +# else + errno = ENOSYS; + return -1; +# endif +} + +static inline key_serial_t add_key(const char *type, const char *description, const void *payload, size_t plen, key_serial_t ringid) { +# ifdef __NR_add_key + return syscall(__NR_add_key, type, description, payload, plen, ringid); +# else + errno = ENOSYS; + return -1; +# endif +} + +static inline key_serial_t request_key(const char *type, const char *description, const char * callout_info, key_serial_t destringid) { +# ifdef __NR_request_key + return syscall(__NR_request_key, type, description, callout_info, destringid); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif + +/* ======================================================================= */ + +#if !HAVE_DECL_COPY_FILE_RANGE +# ifndef __NR_copy_file_range +# if defined(__x86_64__) +# define __NR_copy_file_range 326 +# elif defined(__i386__) +# define __NR_copy_file_range 377 +# elif defined __s390__ +# define __NR_copy_file_range 375 +# elif defined __arm__ +# define __NR_copy_file_range 391 +# elif defined __aarch64__ +# define __NR_copy_file_range 285 +# else +# warning "__NR_copy_file_range not defined for your architecture" +# endif +# endif + +static inline ssize_t copy_file_range(int fd_in, loff_t *off_in, + int fd_out, loff_t *off_out, + size_t len, + unsigned int flags) { +# ifdef __NR_copy_file_range + return syscall(__NR_copy_file_range, fd_in, off_in, fd_out, off_out, len, flags); +# else + errno = ENOSYS; + return -1; +# endif +} +#endif diff --git a/src/basic/selinux-util.c b/src/basic/selinux-util.c index 5e6181f662..10c2f39369 100644 --- a/src/basic/selinux-util.c +++ b/src/basic/selinux-util.c @@ -152,7 +152,7 @@ int mac_selinux_fix(const char *path, bool ignore_enoent, bool ignore_erofs) { return 0; if (r >= 0) { - r = lsetfilecon(path, fcon); + r = lsetfilecon_raw(path, fcon); /* If the FS doesn't support labels, then exit without warning */ if (r < 0 && errno == EOPNOTSUPP) @@ -262,7 +262,7 @@ int mac_selinux_get_child_mls_label(int socket_fd, const char *exe, const char * if (r < 0) return -errno; - r = getpeercon(socket_fd, &peercon); + r = getpeercon_raw(socket_fd, &peercon); if (r < 0) return -errno; @@ -371,7 +371,7 @@ void mac_selinux_create_file_clear(void) { if (!mac_selinux_use()) return; - setfscreatecon(NULL); + setfscreatecon_raw(NULL); #endif } @@ -402,7 +402,7 @@ void mac_selinux_create_socket_clear(void) { if (!mac_selinux_use()) return; - setsockcreatecon(NULL); + setsockcreatecon_raw(NULL); #endif } @@ -461,7 +461,7 @@ int mac_selinux_bind(int fd, const struct sockaddr *addr, socklen_t addrlen) { return -errno; } else { - if (setfscreatecon(fcon) < 0) { + if (setfscreatecon_raw(fcon) < 0) { log_enforcing("Failed to set SELinux security context %s for %s: %m", fcon, path); if (security_getenforce() > 0) return -errno; @@ -472,7 +472,7 @@ int mac_selinux_bind(int fd, const struct sockaddr *addr, socklen_t addrlen) { r = bind(fd, addr, addrlen) < 0 ? -errno : 0; if (context_changed) - setfscreatecon(NULL); + setfscreatecon_raw(NULL); return r; diff --git a/src/basic/time-util.c b/src/basic/time-util.c index c16460a198..7ca764abeb 100644 --- a/src/basic/time-util.c +++ b/src/basic/time-util.c @@ -47,15 +47,12 @@ static clockid_t map_clock_id(clockid_t c) { /* Some more exotic archs (s390, ppc, …) lack the "ALARM" flavour of the clocks. Thus, clock_gettime() will * fail for them. Since they are essentially the same as their non-ALARM pendants (their only difference is * when timers are set on them), let's just map them accordingly. This way, we can get the correct time even on - * those archs. - * - * Also, older kernels don't support CLOCK_BOOTTIME: fall back to CLOCK_MONOTONIC. */ + * those archs. */ switch (c) { - case CLOCK_BOOTTIME: case CLOCK_BOOTTIME_ALARM: - return clock_boottime_or_monotonic (); + return CLOCK_BOOTTIME; case CLOCK_REALTIME_ALARM: return CLOCK_REALTIME; diff --git a/src/basic/utf8.h b/src/basic/utf8.h index 12c272d66e..f9b9c9468b 100644 --- a/src/basic/utf8.h +++ b/src/basic/utf8.h @@ -28,6 +28,7 @@ #include "missing.h" #define UTF8_REPLACEMENT_CHARACTER "\xef\xbf\xbd" +#define UTF8_BYTE_ORDER_MARK "\xef\xbb\xbf" bool unichar_is_valid(char32_t c); diff --git a/src/core/cgroup.c b/src/core/cgroup.c index 39235a95f6..9c34928052 100644 --- a/src/core/cgroup.c +++ b/src/core/cgroup.c @@ -765,7 +765,7 @@ int unit_set_cgroup_path(Unit *u, const char *path) { } int unit_watch_cgroup(Unit *u) { - _cleanup_free_ char *populated = NULL; + _cleanup_free_ char *events = NULL; int r; assert(u); @@ -791,11 +791,11 @@ int unit_watch_cgroup(Unit *u) { if (r < 0) return log_oom(); - r = cg_get_path(SYSTEMD_CGROUP_CONTROLLER, u->cgroup_path, "cgroup.populated", &populated); + r = cg_get_path(SYSTEMD_CGROUP_CONTROLLER, u->cgroup_path, "cgroup.events", &events); if (r < 0) return log_oom(); - u->cgroup_inotify_wd = inotify_add_watch(u->manager->cgroup_inotify_fd, populated, IN_MODIFY); + u->cgroup_inotify_wd = inotify_add_watch(u->manager->cgroup_inotify_fd, events, IN_MODIFY); if (u->cgroup_inotify_wd < 0) { if (errno == ENOENT) /* If the directory is already diff --git a/src/core/execute.c b/src/core/execute.c index 517c2fb45b..ac2ac39892 100644 --- a/src/core/execute.c +++ b/src/core/execute.c @@ -24,6 +24,7 @@ #include <poll.h> #include <signal.h> #include <string.h> +#include <sys/capability.h> #include <sys/personality.h> #include <sys/prctl.h> #include <sys/socket.h> @@ -1824,6 +1825,11 @@ static int exec_child( if (params->apply_permissions) { + bool use_address_families = context->address_families_whitelist || + !set_isempty(context->address_families); + bool use_syscall_filter = context->syscall_whitelist || + !set_isempty(context->syscall_filter) || + !set_isempty(context->syscall_archs); int secure_bits = context->secure_bits; for (i = 0; i < _RLIMIT_MAX; i++) { @@ -1890,15 +1896,15 @@ static int exec_child( return -errno; } - if (context->no_new_privileges) + if (context->no_new_privileges || + (!have_effective_cap(CAP_SYS_ADMIN) && (use_address_families || use_syscall_filter))) if (prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0) < 0) { *exit_status = EXIT_NO_NEW_PRIVILEGES; return -errno; } #ifdef HAVE_SECCOMP - if (context->address_families_whitelist || - !set_isempty(context->address_families)) { + if (use_address_families) { r = apply_address_families(context); if (r < 0) { *exit_status = EXIT_ADDRESS_FAMILIES; @@ -1906,9 +1912,7 @@ static int exec_child( } } - if (context->syscall_whitelist || - !set_isempty(context->syscall_filter) || - !set_isempty(context->syscall_archs)) { + if (use_syscall_filter) { r = apply_seccomp(context); if (r < 0) { *exit_status = EXIT_SECCOMP; diff --git a/src/core/job.c b/src/core/job.c index 012cf72d1f..5557a6a942 100644 --- a/src/core/job.c +++ b/src/core/job.c @@ -645,7 +645,7 @@ _pure_ static const char *job_get_status_message_format(Unit *u, JobType t, JobR static const char *const generic_finished_stop_job[_JOB_RESULT_MAX] = { [JOB_DONE] = "Stopped %s.", [JOB_FAILED] = "Stopped (with error) %s.", - [JOB_TIMEOUT] = "Timed out stoppping %s.", + [JOB_TIMEOUT] = "Timed out stopping %s.", }; static const char *const generic_finished_reload_job[_JOB_RESULT_MAX] = { [JOB_DONE] = "Reloaded %s.", @@ -690,17 +690,20 @@ _pure_ static const char *job_get_status_message_format(Unit *u, JobType t, JobR } static void job_print_status_message(Unit *u, JobType t, JobResult result) { - static const char* const job_result_status_table[_JOB_RESULT_MAX] = { - [JOB_DONE] = ANSI_GREEN " OK " ANSI_NORMAL, - [JOB_TIMEOUT] = ANSI_HIGHLIGHT_RED " TIME " ANSI_NORMAL, - [JOB_FAILED] = ANSI_HIGHLIGHT_RED "FAILED" ANSI_NORMAL, - [JOB_DEPENDENCY] = ANSI_HIGHLIGHT_YELLOW "DEPEND" ANSI_NORMAL, - [JOB_SKIPPED] = ANSI_HIGHLIGHT " INFO " ANSI_NORMAL, - [JOB_ASSERT] = ANSI_HIGHLIGHT_YELLOW "ASSERT" ANSI_NORMAL, - [JOB_UNSUPPORTED] = ANSI_HIGHLIGHT_YELLOW "UNSUPP" ANSI_NORMAL, + static struct { + const char *color, *word; + } const statuses[_JOB_RESULT_MAX] = { + [JOB_DONE] = {ANSI_GREEN, " OK "}, + [JOB_TIMEOUT] = {ANSI_HIGHLIGHT_RED, " TIME "}, + [JOB_FAILED] = {ANSI_HIGHLIGHT_RED, "FAILED"}, + [JOB_DEPENDENCY] = {ANSI_HIGHLIGHT_YELLOW, "DEPEND"}, + [JOB_SKIPPED] = {ANSI_HIGHLIGHT, " INFO "}, + [JOB_ASSERT] = {ANSI_HIGHLIGHT_YELLOW, "ASSERT"}, + [JOB_UNSUPPORTED] = {ANSI_HIGHLIGHT_YELLOW, "UNSUPP"}, }; const char *format; + const char *status; assert(u); assert(t >= 0); @@ -714,11 +717,16 @@ static void job_print_status_message(Unit *u, JobType t, JobResult result) { if (!format) return; + if (log_get_show_color()) + status = strjoina(statuses[result].color, statuses[result].word, ANSI_NORMAL); + else + status = statuses[result].word; + if (result != JOB_DONE) manager_flip_auto_status(u->manager, true); DISABLE_WARNING_FORMAT_NONLITERAL; - unit_status_printf(u, job_result_status_table[result], format); + unit_status_printf(u, status, format); REENABLE_WARNING; if (t == JOB_START && result == JOB_FAILED) { diff --git a/src/core/load-fragment.c b/src/core/load-fragment.c index e1bfdccbca..d078924c5b 100644 --- a/src/core/load-fragment.c +++ b/src/core/load-fragment.c @@ -3507,7 +3507,19 @@ static int merge_by_names(Unit **u, Set *names, const char *id) { * ours? Then let's try it the other way * round */ - other = manager_get_unit((*u)->manager, k); + /* If the symlink name we are looking at is unit template, then + we must search for instance of this template */ + if (unit_name_is_valid(k, UNIT_NAME_TEMPLATE)) { + _cleanup_free_ char *instance = NULL; + + r = unit_name_replace_instance(k, (*u)->instance, &instance); + if (r < 0) + return r; + + other = manager_get_unit((*u)->manager, instance); + } else + other = manager_get_unit((*u)->manager, k); + free(k); if (other) { diff --git a/src/core/main.c b/src/core/main.c index 1783b9c7af..56df32426a 100644 --- a/src/core/main.c +++ b/src/core/main.c @@ -1218,10 +1218,15 @@ static int status_welcome(void) { if (r < 0 && r != -ENOENT) log_warning_errno(r, "Failed to read os-release file: %m"); - return status_printf(NULL, false, false, - "\nWelcome to \x1B[%sm%s\x1B[0m!\n", - isempty(ansi_color) ? "1" : ansi_color, - isempty(pretty_name) ? "Linux" : pretty_name); + if (log_get_show_color()) + return status_printf(NULL, false, false, + "\nWelcome to \x1B[%sm%s\x1B[0m!\n", + isempty(ansi_color) ? "1" : ansi_color, + isempty(pretty_name) ? "Linux" : pretty_name); + else + return status_printf(NULL, false, false, + "\nWelcome to %s!\n", + isempty(pretty_name) ? "Linux" : pretty_name); } static int write_container_id(void) { @@ -1659,7 +1664,7 @@ int main(int argc, char *argv[]) { test_usr(); } - if (arg_running_as == MANAGER_SYSTEM && arg_runtime_watchdog > 0) + if (arg_running_as == MANAGER_SYSTEM && arg_runtime_watchdog > 0 && arg_runtime_watchdog != USEC_INFINITY) watchdog_set_timeout(&arg_runtime_watchdog); if (arg_timer_slack_nsec != NSEC_INFINITY) @@ -2090,7 +2095,7 @@ finish: assert(pos < ELEMENTSOF(command_line)); - if (arm_reboot_watchdog && arg_shutdown_watchdog > 0) { + if (arm_reboot_watchdog && arg_shutdown_watchdog > 0 && arg_shutdown_watchdog != USEC_INFINITY) { char *e; /* If we reboot let's set the shutdown diff --git a/src/core/manager.c b/src/core/manager.c index f13e933578..e739795e70 100644 --- a/src/core/manager.c +++ b/src/core/manager.c @@ -1333,8 +1333,12 @@ int manager_load_unit_prepare( t = unit_name_to_type(name); - if (t == _UNIT_TYPE_INVALID || !unit_name_is_valid(name, UNIT_NAME_PLAIN|UNIT_NAME_INSTANCE)) + if (t == _UNIT_TYPE_INVALID || !unit_name_is_valid(name, UNIT_NAME_PLAIN|UNIT_NAME_INSTANCE)) { + if (unit_name_is_valid(name, UNIT_NAME_TEMPLATE)) + return sd_bus_error_setf(e, SD_BUS_ERROR_INVALID_ARGS, "Unit name %s is missing the instance name.", name); + return sd_bus_error_setf(e, SD_BUS_ERROR_INVALID_ARGS, "Unit name %s is not valid.", name); + } ret = manager_get_unit(m, name); if (ret) { @@ -1631,7 +1635,9 @@ static void invoke_sigchld_event(Manager *m, Unit *u, const siginfo_t *si) { log_unit_debug(u, "Child "PID_FMT" belongs to %s", si->si_pid, u->id); unit_unwatch_pid(u, si->si_pid); - UNIT_VTABLE(u)->sigchld_event(u, si->si_pid, si->si_code, si->si_status); + + if (UNIT_VTABLE(u)->sigchld_event) + UNIT_VTABLE(u)->sigchld_event(u, si->si_pid, si->si_code, si->si_status); } static int manager_dispatch_sigchld(Manager *m) { @@ -2016,7 +2022,7 @@ int manager_loop(Manager *m) { while (m->exit_code == MANAGER_OK) { usec_t wait_usec; - if (m->runtime_watchdog > 0 && m->running_as == MANAGER_SYSTEM) + if (m->runtime_watchdog > 0 && m->runtime_watchdog != USEC_INFINITY && m->running_as == MANAGER_SYSTEM) watchdog_ping(); if (!ratelimit_test(&rl)) { @@ -2041,7 +2047,7 @@ int manager_loop(Manager *m) { continue; /* Sleep for half the watchdog time */ - if (m->runtime_watchdog > 0 && m->running_as == MANAGER_SYSTEM) { + if (m->runtime_watchdog > 0 && m->runtime_watchdog != USEC_INFINITY && m->running_as == MANAGER_SYSTEM) { wait_usec = m->runtime_watchdog / 2; if (wait_usec <= 0) wait_usec = 1; diff --git a/src/core/mount-setup.c b/src/core/mount-setup.c index de1a361cc4..32fe51c67e 100644 --- a/src/core/mount-setup.c +++ b/src/core/mount-setup.c @@ -94,7 +94,7 @@ static const MountPoint mount_table[] = { #endif { "tmpfs", "/run", "tmpfs", "mode=755", MS_NOSUID|MS_NODEV|MS_STRICTATIME, NULL, MNT_FATAL|MNT_IN_CONTAINER }, - { "cgroup", "/sys/fs/cgroup", "cgroup", "__DEVEL__sane_behavior", MS_NOSUID|MS_NOEXEC|MS_NODEV, + { "cgroup", "/sys/fs/cgroup", "cgroup2", NULL, MS_NOSUID|MS_NOEXEC|MS_NODEV, cg_is_unified_wanted, MNT_FATAL|MNT_IN_CONTAINER }, { "tmpfs", "/sys/fs/cgroup", "tmpfs", "mode=755", MS_NOSUID|MS_NOEXEC|MS_NODEV|MS_STRICTATIME, cg_is_legacy_wanted, MNT_FATAL|MNT_IN_CONTAINER }, diff --git a/src/core/selinux-setup.c b/src/core/selinux-setup.c index 9a115a4387..4072df58e6 100644 --- a/src/core/selinux-setup.c +++ b/src/core/selinux-setup.c @@ -88,7 +88,7 @@ int mac_selinux_setup(bool *loaded_policy) { log_open(); log_error("Failed to compute init label, ignoring."); } else { - r = setcon(label); + r = setcon_raw(label); log_open(); if (r < 0) diff --git a/src/core/socket.c b/src/core/socket.c index 87586c1c2e..dd515a17a5 100644 --- a/src/core/socket.c +++ b/src/core/socket.c @@ -1341,8 +1341,12 @@ static int socket_open_fds(Socket *s) { break; case SOCKET_USB_FUNCTION: + { + _cleanup_free_ char *ep = NULL; - p->fd = usbffs_address_create(p->path); + ep = path_make_absolute("ep0", p->path); + + p->fd = usbffs_address_create(ep); if (p->fd < 0) { r = p->fd; goto rollback; @@ -1357,7 +1361,7 @@ static int socket_open_fds(Socket *s) { goto rollback; break; - + } default: assert_not_reached("Unknown port type"); } diff --git a/src/core/transaction.c b/src/core/transaction.c index b28fc76785..c894001cf9 100644 --- a/src/core/transaction.c +++ b/src/core/transaction.c @@ -391,6 +391,7 @@ static int transaction_verify_order_one(Transaction *tr, Job *j, Job *from, unsi if (delete) { + const char *status; /* logging for j not k here here to provide consistent narrative */ log_unit_warning(j->unit, "Breaking ordering cycle by deleting job %s/%s", @@ -399,7 +400,13 @@ static int transaction_verify_order_one(Transaction *tr, Job *j, Job *from, unsi "Job %s/%s deleted to break ordering cycle starting with %s/%s", delete->unit->id, job_type_to_string(delete->type), j->unit->id, job_type_to_string(j->type)); - unit_status_printf(delete->unit, ANSI_HIGHLIGHT_RED " SKIP " ANSI_NORMAL, + + if (log_get_show_color()) + status = ANSI_HIGHLIGHT_RED " SKIP " ANSI_NORMAL; + else + status = " SKIP "; + + unit_status_printf(delete->unit, status, "Ordering cycle found, skipping %s"); transaction_delete_unit(tr, delete->unit); return -EAGAIN; diff --git a/src/cryptsetup/cryptsetup.c b/src/cryptsetup/cryptsetup.c index 2ef966257a..9927621ea0 100644 --- a/src/cryptsetup/cryptsetup.c +++ b/src/cryptsetup/cryptsetup.c @@ -719,8 +719,12 @@ int main(int argc, char *argv[]) { int k; k = crypt_init_by_name(&cd, argv[2]); - if (k) { - log_error_errno(k, "crypt_init() failed: %m"); + if (k == -ENODEV) { + log_info("Volume %s already inactive.", argv[2]); + r = EXIT_SUCCESS; + goto finish; + } else if (k) { + log_error_errno(k, "crypt_init_by_name() failed: %m"); goto finish; } diff --git a/src/import/import-common.c b/src/import/import-common.c index 18a30be36d..287a3382a1 100644 --- a/src/import/import-common.c +++ b/src/import/import-common.c @@ -136,7 +136,7 @@ int import_fork_tar_x(const char *path, pid_t *ret) { if (r < 0) log_error_errno(r, "Failed to drop capabilities, ignoring: %m"); - execlp("tar", "tar", "--numeric-owner", "-C", path, "-px", NULL); + execlp("tar", "tar", "--numeric-owner", "-C", path, "-px", "--xattrs", "--xattrs-include=*", NULL); log_error_errno(errno, "Failed to execute tar: %m"); _exit(EXIT_FAILURE); } @@ -210,7 +210,7 @@ int import_fork_tar_c(const char *path, pid_t *ret) { if (r < 0) log_error_errno(r, "Failed to drop capabilities, ignoring: %m"); - execlp("tar", "tar", "-C", path, "-c", ".", NULL); + execlp("tar", "tar", "-C", path, "-c", "--xattrs", "--xattrs-include=*", ".", NULL); log_error_errno(errno, "Failed to execute tar: %m"); _exit(EXIT_FAILURE); } diff --git a/src/libsystemd-network/dhcp-identifier.c b/src/libsystemd-network/dhcp-identifier.c index 1bef368852..4f7d4d8bf2 100644 --- a/src/libsystemd-network/dhcp-identifier.c +++ b/src/libsystemd-network/dhcp-identifier.c @@ -43,7 +43,7 @@ int dhcp_identifier_set_duid_en(struct duid *duid, size_t *len) { if (r < 0) return r; - unaligned_write_be16(&duid->type, DHCP_DUID_TYPE_EN); + unaligned_write_be16(&duid->type, DUID_TYPE_EN); unaligned_write_be32(&duid->en.pen, SYSTEMD_PEN); *len = sizeof(duid->type) + sizeof(duid->en); diff --git a/src/libsystemd-network/dhcp-identifier.h b/src/libsystemd-network/dhcp-identifier.h index cb953cb416..e6486b78f8 100644 --- a/src/libsystemd-network/dhcp-identifier.h +++ b/src/libsystemd-network/dhcp-identifier.h @@ -25,15 +25,15 @@ #include "sparse-endian.h" #include "unaligned.h" -typedef enum DHCPDUIDType { - DHCP_DUID_TYPE_RAW = 0, - DHCP_DUID_TYPE_LLT = 1, - DHCP_DUID_TYPE_EN = 2, - DHCP_DUID_TYPE_LL = 3, - DHCP_DUID_TYPE_UUID = 4, - _DHCP_DUID_TYPE_MAX, - _DHCP_DUID_TYPE_INVALID = -1, -} DHCPDUIDType; +typedef enum DUIDType { + DUID_TYPE_RAW = 0, + DUID_TYPE_LLT = 1, + DUID_TYPE_EN = 2, + DUID_TYPE_LL = 3, + DUID_TYPE_UUID = 4, + _DUID_TYPE_MAX, + _DUID_TYPE_INVALID = -1, +} DUIDType; /* RFC 3315 section 9.1: * A DUID can be no more than 128 octets long (not including the type code). @@ -72,29 +72,31 @@ struct duid { int dhcp_identifier_set_duid_en(struct duid *duid, size_t *len); int dhcp_identifier_set_iaid(int ifindex, uint8_t *mac, size_t mac_len, void *_id); -static inline int dhcp_validate_duid_len(be16_t duid_type, size_t duid_len) { +static inline int dhcp_validate_duid_len(uint16_t duid_type, size_t duid_len) { struct duid d; - assert_return(duid_len > 0 && duid_len <= MAX_DUID_LEN, -EINVAL); + assert(duid_len > 0); - switch (be16toh(duid_type)) { - case DHCP_DUID_TYPE_LLT: + switch (duid_type) { + case DUID_TYPE_LLT: if (duid_len <= sizeof(d.llt)) return -EINVAL; break; - case DHCP_DUID_TYPE_EN: + case DUID_TYPE_EN: if (duid_len != sizeof(d.en)) return -EINVAL; break; - case DHCP_DUID_TYPE_LL: + case DUID_TYPE_LL: if (duid_len <= sizeof(d.ll)) return -EINVAL; break; - case DHCP_DUID_TYPE_UUID: + case DUID_TYPE_UUID: if (duid_len != sizeof(d.uuid)) return -EINVAL; break; default: + if (duid_len > sizeof(d.raw)) + return -EINVAL; /* accept unknown type in order to be forward compatible */ break; } diff --git a/src/libsystemd-network/lldp-neighbor.c b/src/libsystemd-network/lldp-neighbor.c index 190c9baece..6a716430e3 100644 --- a/src/libsystemd-network/lldp-neighbor.c +++ b/src/libsystemd-network/lldp-neighbor.c @@ -24,7 +24,6 @@ #include "in-addr-util.h" #include "lldp-internal.h" #include "lldp-neighbor.h" -#include "lldp.h" #include "unaligned.h" static void lldp_neighbor_id_hash_func(const void *p, struct siphash *state) { @@ -245,7 +244,7 @@ int lldp_neighbor_parse(sd_lldp_neighbor *n) { switch (type) { - case LLDP_TYPE_END: + case SD_LLDP_TYPE_END: if (length != 0) { log_lldp("End marker TLV not zero-sized, ignoring datagram."); return -EBADMSG; @@ -257,7 +256,7 @@ int lldp_neighbor_parse(sd_lldp_neighbor *n) { goto end_marker; - case LLDP_TYPE_CHASSIS_ID: + case SD_LLDP_TYPE_CHASSIS_ID: if (length < 2 || length > 256) { /* includes the chassis subtype, hence one extra byte */ log_lldp("Chassis ID field size out of range, ignoring datagram."); return -EBADMSG; @@ -274,7 +273,7 @@ int lldp_neighbor_parse(sd_lldp_neighbor *n) { n->id.chassis_id_size = length; break; - case LLDP_TYPE_PORT_ID: + case SD_LLDP_TYPE_PORT_ID: if (length < 2 || length > 256) { /* includes the port subtype, hence one extra byte */ log_lldp("Port ID field size out of range, ignoring datagram."); return -EBADMSG; @@ -291,7 +290,7 @@ int lldp_neighbor_parse(sd_lldp_neighbor *n) { n->id.port_id_size = length; break; - case LLDP_TYPE_TTL: + case SD_LLDP_TYPE_TTL: if (length != 2) { log_lldp("TTL field has wrong size, ignoring datagram."); return -EBADMSG; @@ -306,25 +305,25 @@ int lldp_neighbor_parse(sd_lldp_neighbor *n) { n->has_ttl = true; break; - case LLDP_TYPE_PORT_DESCRIPTION: + case SD_LLDP_TYPE_PORT_DESCRIPTION: r = parse_string(&n->port_description, p, length); if (r < 0) return r; break; - case LLDP_TYPE_SYSTEM_NAME: + case SD_LLDP_TYPE_SYSTEM_NAME: r = parse_string(&n->system_name, p, length); if (r < 0) return r; break; - case LLDP_TYPE_SYSTEM_DESCRIPTION: + case SD_LLDP_TYPE_SYSTEM_DESCRIPTION: r = parse_string(&n->system_description, p, length); if (r < 0) return r; break; - case LLDP_TYPE_SYSTEM_CAPABILITIES: + case SD_LLDP_TYPE_SYSTEM_CAPABILITIES: if (length != 4) log_lldp("System capabilities field has wrong size, ignoring."); else { @@ -335,7 +334,7 @@ int lldp_neighbor_parse(sd_lldp_neighbor *n) { break; - case LLDP_TYPE_PRIVATE: + case SD_LLDP_TYPE_PRIVATE: if (length < 4) log_lldp("Found private TLV that is too short, ignoring."); @@ -479,18 +478,18 @@ _public_ int sd_lldp_neighbor_get_chassis_id_as_string(sd_lldp_neighbor *n, cons switch (*(uint8_t*) n->id.chassis_id) { - case LLDP_CHASSIS_SUBTYPE_CHASSIS_COMPONENT: - case LLDP_CHASSIS_SUBTYPE_INTERFACE_ALIAS: - case LLDP_CHASSIS_SUBTYPE_PORT_COMPONENT: - case LLDP_CHASSIS_SUBTYPE_INTERFACE_NAME: - case LLDP_CHASSIS_SUBTYPE_LOCALLY_ASSIGNED: + case SD_LLDP_CHASSIS_SUBTYPE_CHASSIS_COMPONENT: + case SD_LLDP_CHASSIS_SUBTYPE_INTERFACE_ALIAS: + case SD_LLDP_CHASSIS_SUBTYPE_PORT_COMPONENT: + case SD_LLDP_CHASSIS_SUBTYPE_INTERFACE_NAME: + case SD_LLDP_CHASSIS_SUBTYPE_LOCALLY_ASSIGNED: k = cescape_length((char*) n->id.chassis_id + 1, n->id.chassis_id_size - 1); if (!k) return -ENOMEM; goto done; - case LLDP_CHASSIS_SUBTYPE_MAC_ADDRESS: + case SD_LLDP_CHASSIS_SUBTYPE_MAC_ADDRESS: r = format_mac_address(n->id.chassis_id, n->id.chassis_id_size, &k); if (r < 0) return r; @@ -499,7 +498,7 @@ _public_ int sd_lldp_neighbor_get_chassis_id_as_string(sd_lldp_neighbor *n, cons break; - case LLDP_CHASSIS_SUBTYPE_NETWORK_ADDRESS: + case SD_LLDP_CHASSIS_SUBTYPE_NETWORK_ADDRESS: r = format_network_address(n->id.chassis_id, n->id.chassis_id_size, &k); if (r < 0) return r; @@ -550,17 +549,17 @@ _public_ int sd_lldp_neighbor_get_port_id_as_string(sd_lldp_neighbor *n, const c switch (*(uint8_t*) n->id.port_id) { - case LLDP_PORT_SUBTYPE_INTERFACE_ALIAS: - case LLDP_PORT_SUBTYPE_PORT_COMPONENT: - case LLDP_PORT_SUBTYPE_INTERFACE_NAME: - case LLDP_PORT_SUBTYPE_LOCALLY_ASSIGNED: + case SD_LLDP_PORT_SUBTYPE_INTERFACE_ALIAS: + case SD_LLDP_PORT_SUBTYPE_PORT_COMPONENT: + case SD_LLDP_PORT_SUBTYPE_INTERFACE_NAME: + case SD_LLDP_PORT_SUBTYPE_LOCALLY_ASSIGNED: k = cescape_length((char*) n->id.port_id + 1, n->id.port_id_size - 1); if (!k) return -ENOMEM; goto done; - case LLDP_PORT_SUBTYPE_MAC_ADDRESS: + case SD_LLDP_PORT_SUBTYPE_MAC_ADDRESS: r = format_mac_address(n->id.port_id, n->id.port_id_size, &k); if (r < 0) return r; @@ -569,7 +568,7 @@ _public_ int sd_lldp_neighbor_get_port_id_as_string(sd_lldp_neighbor *n, const c break; - case LLDP_PORT_SUBTYPE_NETWORK_ADDRESS: + case SD_LLDP_PORT_SUBTYPE_NETWORK_ADDRESS: r = format_network_address(n->id.port_id, n->id.port_id_size, &k); if (r < 0) return r; @@ -738,7 +737,7 @@ _public_ int sd_lldp_neighbor_tlv_get_oui(sd_lldp_neighbor *n, uint8_t oui[3], u assert_return(oui, -EINVAL); assert_return(subtype, -EINVAL); - r = sd_lldp_neighbor_tlv_is_type(n, LLDP_TYPE_PRIVATE); + r = sd_lldp_neighbor_tlv_is_type(n, SD_LLDP_TYPE_PRIVATE); if (r < 0) return r; if (r == 0) diff --git a/src/libsystemd-network/lldp.h b/src/libsystemd-network/lldp.h deleted file mode 100644 index d61ecabcfc..0000000000 --- a/src/libsystemd-network/lldp.h +++ /dev/null @@ -1,102 +0,0 @@ -#pragma once - -/*** - This file is part of systemd. - - Copyright (C) 2014 Tom Gundersen - Copyright (C) 2014 Susant Sahani - - systemd is free software; you can redistribute it and/or modify it - under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation; either version 2.1 of the License, or - (at your option) any later version. - - systemd is distributed in the hope that it will be useful, but - WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with systemd; If not, see <http://www.gnu.org/licenses/>. -***/ - -#define LLDP_MULTICAST_ADDR { 0x01, 0x80, 0xc2, 0x00, 0x00, 0x0e } - -/* IEEE 802.3AB Clause 9: TLV Types */ -enum { - LLDP_TYPE_END = 0, - LLDP_TYPE_CHASSIS_ID = 1, - LLDP_TYPE_PORT_ID = 2, - LLDP_TYPE_TTL = 3, - LLDP_TYPE_PORT_DESCRIPTION = 4, - LLDP_TYPE_SYSTEM_NAME = 5, - LLDP_TYPE_SYSTEM_DESCRIPTION = 6, - LLDP_TYPE_SYSTEM_CAPABILITIES = 7, - LLDP_TYPE_MGMT_ADDRESS = 8, - LLDP_TYPE_PRIVATE = 127, -}; - -/* IEEE 802.3AB Clause 9.5.2: Chassis subtypes */ -enum { - LLDP_CHASSIS_SUBTYPE_RESERVED = 0, - LLDP_CHASSIS_SUBTYPE_CHASSIS_COMPONENT = 1, - LLDP_CHASSIS_SUBTYPE_INTERFACE_ALIAS = 2, - LLDP_CHASSIS_SUBTYPE_PORT_COMPONENT = 3, - LLDP_CHASSIS_SUBTYPE_MAC_ADDRESS = 4, - LLDP_CHASSIS_SUBTYPE_NETWORK_ADDRESS = 5, - LLDP_CHASSIS_SUBTYPE_INTERFACE_NAME = 6, - LLDP_CHASSIS_SUBTYPE_LOCALLY_ASSIGNED = 7, -}; - -/* IEEE 802.3AB Clause 9.5.3: Port subtype */ -enum { - LLDP_PORT_SUBTYPE_RESERVED = 0, - LLDP_PORT_SUBTYPE_INTERFACE_ALIAS = 1, - LLDP_PORT_SUBTYPE_PORT_COMPONENT = 2, - LLDP_PORT_SUBTYPE_MAC_ADDRESS = 3, - LLDP_PORT_SUBTYPE_NETWORK_ADDRESS = 4, - LLDP_PORT_SUBTYPE_INTERFACE_NAME = 5, - LLDP_PORT_SUBTYPE_AGENT_CIRCUIT_ID = 6, - LLDP_PORT_SUBTYPE_LOCALLY_ASSIGNED = 7, -}; - -enum { - LLDP_SYSTEM_CAPABILITIES_OTHER = 1 << 0, - LLDP_SYSTEM_CAPABILITIES_REPEATER = 1 << 1, - LLDP_SYSTEM_CAPABILITIES_BRIDGE = 1 << 2, - LLDP_SYSTEM_CAPABILITIES_WLAN_AP = 1 << 3, - LLDP_SYSTEM_CAPABILITIES_ROUTER = 1 << 4, - LLDP_SYSTEM_CAPABILITIES_PHONE = 1 << 5, - LLDP_SYSTEM_CAPABILITIES_DOCSIS = 1 << 6, - LLDP_SYSTEM_CAPABILITIES_STATION = 1 << 7, - LLDP_SYSTEM_CAPABILITIES_CVLAN = 1 << 8, - LLDP_SYSTEM_CAPABILITIES_SVLAN = 1 << 9, - LLDP_SYSTEM_CAPABILITIES_TPMR = 1 << 10, -}; - -#define _LLDP_SYSTEM_CAPABILITIES_ALL ((uint16_t) -1) - -#define _LLDP_SYSTEM_CAPABILITIES_ALL_ROUTERS \ - ((uint16_t) \ - (LLDP_SYSTEM_CAPABILITIES_REPEATER| \ - LLDP_SYSTEM_CAPABILITIES_BRIDGE| \ - LLDP_SYSTEM_CAPABILITIES_WLAN_AP| \ - LLDP_SYSTEM_CAPABILITIES_ROUTER| \ - LLDP_SYSTEM_CAPABILITIES_DOCSIS| \ - LLDP_SYSTEM_CAPABILITIES_CVLAN| \ - LLDP_SYSTEM_CAPABILITIES_SVLAN| \ - LLDP_SYSTEM_CAPABILITIES_TPMR)) - - -#define LLDP_OUI_802_1 (uint8_t[]) { 0x00, 0x80, 0xc2 } -#define LLDP_OUI_802_3 (uint8_t[]) { 0x00, 0x12, 0x0f } - -enum { - LLDP_OUI_802_1_SUBTYPE_PORT_VLAN_ID = 1, - LLDP_OUI_802_1_SUBTYPE_PORT_PROTOCOL_VLAN_ID = 2, - LLDP_OUI_802_1_SUBTYPE_VLAN_NAME = 3, - LLDP_OUI_802_1_SUBTYPE_PROTOCOL_IDENTITY = 4, - LLDP_OUI_802_1_SUBTYPE_VID_USAGE_DIGEST = 5, - LLDP_OUI_802_1_SUBTYPE_MANAGEMENT_VID = 6, - LLDP_OUI_802_1_SUBTYPE_LINK_AGGREGATION = 7, -}; diff --git a/src/libsystemd-network/network-internal.c b/src/libsystemd-network/network-internal.c index 7c21f42591..0e2d757b2b 100644 --- a/src/libsystemd-network/network-internal.c +++ b/src/libsystemd-network/network-internal.c @@ -335,17 +335,17 @@ int config_parse_hwaddr(const char *unit, return 0; } -int config_parse_iaid_value(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) { - uint32_t iaid_value; +int config_parse_iaid(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) { + uint32_t iaid; int r; assert(filename); @@ -353,12 +353,13 @@ int config_parse_iaid_value(const char *unit, assert(rvalue); assert(data); - if ((r = safe_atou32(rvalue, &iaid_value)) < 0) { + r = safe_atou32(rvalue, &iaid); + if (r < 0) { log_syntax(unit, LOG_ERR, filename, line, 0, "Unable to read IAID: %s", rvalue); return r; } - *((be32_t *)data) = htobe32(iaid_value); + *((uint32_t *)data) = iaid; return 0; } diff --git a/src/libsystemd-network/network-internal.h b/src/libsystemd-network/network-internal.h index d8b551e8ce..72432774d7 100644 --- a/src/libsystemd-network/network-internal.h +++ b/src/libsystemd-network/network-internal.h @@ -62,9 +62,9 @@ int config_parse_ifalias(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); -int config_parse_iaid_value(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); +int config_parse_iaid(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); int net_get_unique_predictable_data(struct udev_device *device, uint64_t *result); const char *net_get_name(struct udev_device *device); diff --git a/src/libsystemd-network/sd-dhcp-client.c b/src/libsystemd-network/sd-dhcp-client.c index b108e35386..287b6e26fa 100644 --- a/src/libsystemd-network/sd-dhcp-client.c +++ b/src/libsystemd-network/sd-dhcp-client.c @@ -298,8 +298,8 @@ int sd_dhcp_client_set_client_id(sd_dhcp_client *client, uint8_t type, return 0; } -int sd_dhcp_client_set_iaid_duid(sd_dhcp_client *client, be32_t iaid, - size_t duid_len, struct duid *duid) { +int sd_dhcp_client_set_iaid_duid(sd_dhcp_client *client, uint32_t iaid, + uint16_t duid_type, uint8_t *duid, size_t duid_len) { DHCP_CLIENT_DONT_DESTROY(client); int r; assert_return(client, -EINVAL); @@ -315,7 +315,7 @@ int sd_dhcp_client_set_iaid_duid(sd_dhcp_client *client, be32_t iaid, if (r < 0) return r; } else - client->client_id.ns.iaid = iaid; + client->client_id.ns.iaid = htobe32(iaid); /* If DUID is not configured, generate DUID-EN. */ if (duid_len == 0) { @@ -324,11 +324,12 @@ int sd_dhcp_client_set_iaid_duid(sd_dhcp_client *client, be32_t iaid, if (r < 0) return r; } else { - r = dhcp_validate_duid_len(client->client_id.type, - duid_len - sizeof(client->client_id.type)); + r = dhcp_validate_duid_len(client->client_id.type, duid_len); if (r < 0) return r; - memcpy(&client->client_id.ns.duid, duid, duid_len); + client->client_id.ns.duid.type = htobe16(duid_type); + memcpy(&client->client_id.ns.duid.raw.data, duid, duid_len); + duid_len += sizeof(client->client_id.ns.duid.type); } client->client_id_len = sizeof(client->client_id.type) + duid_len + @@ -514,6 +515,7 @@ static int client_message_init(sd_dhcp_client *client, DHCPPacket **ret, if (client->arp_type == ARPHRD_ETHER) memcpy(&packet->dhcp.chaddr, &client->mac_addr, ETH_ALEN); + /* If no client identifier exists, construct an RFC 4361-compliant one */ if (client->client_id_len == 0) { size_t duid_len; diff --git a/src/libsystemd-network/sd-dhcp6-client.c b/src/libsystemd-network/sd-dhcp6-client.c index 7cecba120c..ee4fb4fc1e 100644 --- a/src/libsystemd-network/sd-dhcp6-client.c +++ b/src/libsystemd-network/sd-dhcp6-client.c @@ -180,30 +180,29 @@ static int client_ensure_duid(sd_dhcp6_client *client) { return dhcp_identifier_set_duid_en(&client->duid, &client->duid_len); } -int sd_dhcp6_client_set_duid(sd_dhcp6_client *client, size_t duid_len, - struct duid *duid) { +int sd_dhcp6_client_set_duid(sd_dhcp6_client *client, uint16_t duid_type, + uint8_t *duid, size_t duid_len) { int r; assert_return(client, -EINVAL); assert_return(IN_SET(client->state, DHCP6_STATE_STOPPED), -EBUSY); if (duid_len > 0) { - r = dhcp_validate_duid_len(duid->type, - duid_len - sizeof(duid->type)); + r = dhcp_validate_duid_len(duid_type, duid_len); if (r < 0) return r; - - memcpy(&client->duid, duid, duid_len); - client->duid_len = duid_len; + client->duid.type = htobe16(duid_type); + memcpy(&client->duid.raw.data, duid, duid_len); + client->duid_len = duid_len + sizeof(client->duid.type); } return 0; } -int sd_dhcp6_client_set_iaid(sd_dhcp6_client *client, be32_t iaid) { +int sd_dhcp6_client_set_iaid(sd_dhcp6_client *client, uint32_t iaid) { assert_return(client, -EINVAL); assert_return(IN_SET(client->state, DHCP6_STATE_STOPPED), -EBUSY); - client->ia_na.id = iaid; + client->ia_na.id = htobe32(iaid); return 0; } diff --git a/src/libsystemd-network/sd-lldp.c b/src/libsystemd-network/sd-lldp.c index d0743cf3e2..9d4587c80e 100644 --- a/src/libsystemd-network/sd-lldp.c +++ b/src/libsystemd-network/sd-lldp.c @@ -112,6 +112,8 @@ static bool lldp_keep_neighbor(sd_lldp *lldp, sd_lldp_neighbor *n) { return true; } +static int lldp_start_timer(sd_lldp *lldp, sd_lldp_neighbor *neighbor); + static int lldp_add_neighbor(sd_lldp *lldp, sd_lldp_neighbor *n) { _cleanup_(sd_lldp_neighbor_unrefp) sd_lldp_neighbor *old = NULL; bool keep; @@ -136,7 +138,7 @@ static int lldp_add_neighbor(sd_lldp *lldp, sd_lldp_neighbor *n) { if (lldp_neighbor_equal(n, old)) { /* Is this equal, then restart the TTL counter, but don't do anyting else. */ - lldp_neighbor_start_ttl(old); + lldp_start_timer(lldp, old); lldp_callback(lldp, SD_LLDP_EVENT_REFRESHED, old); return 0; } @@ -162,7 +164,7 @@ static int lldp_add_neighbor(sd_lldp *lldp, sd_lldp_neighbor *n) { n->lldp = lldp; - lldp_neighbor_start_ttl(n); + lldp_start_timer(lldp, n); lldp_callback(lldp, old ? SD_LLDP_EVENT_UPDATED : SD_LLDP_EVENT_ADDED, n); return 1; @@ -368,8 +370,6 @@ static int neighbor_compare_func(const void *a, const void *b) { return lldp_neighbor_id_hash_ops.compare(&(*x)->id, &(*y)->id); } -static int lldp_start_timer(sd_lldp *lldp); - static int on_timer_event(sd_event_source *s, uint64_t usec, void *userdata) { sd_lldp *lldp = userdata; int r, q; @@ -378,19 +378,22 @@ static int on_timer_event(sd_event_source *s, uint64_t usec, void *userdata) { if (r < 0) return log_lldp_errno(r, "Failed to make space: %m"); - q = lldp_start_timer(lldp); + q = lldp_start_timer(lldp, NULL); if (q < 0) return log_lldp_errno(q, "Failed to restart timer: %m"); return 0; } -static int lldp_start_timer(sd_lldp *lldp) { +static int lldp_start_timer(sd_lldp *lldp, sd_lldp_neighbor *neighbor) { sd_lldp_neighbor *n; int r; assert(lldp); + if (neighbor) + lldp_neighbor_start_ttl(neighbor); + n = prioq_peek(lldp->neighbor_by_expiry); if (!n) { @@ -440,7 +443,7 @@ _public_ int sd_lldp_get_neighbors(sd_lldp *lldp, sd_lldp_neighbor ***ret) { if (!l) return -ENOMEM; - r = lldp_start_timer(lldp); + r = lldp_start_timer(lldp, NULL); if (r < 0) { free(l); return r; diff --git a/src/libsystemd-network/test-lldp.c b/src/libsystemd-network/test-lldp.c index da4ce293bc..1aae2253c0 100644 --- a/src/libsystemd-network/test-lldp.c +++ b/src/libsystemd-network/test-lldp.c @@ -30,7 +30,6 @@ #include "alloc-util.h" #include "fd-util.h" #include "lldp-network.h" -#include "lldp.h" #include "macro.h" #include "string-util.h" @@ -127,12 +126,12 @@ static void test_receive_basic_packet(sd_event *e) { assert_se(sd_lldp_get_neighbors(lldp, &neighbors) == 1); assert_se(sd_lldp_neighbor_get_chassis_id(neighbors[0], &type, &data, &length) == 0); - assert_se(type == LLDP_CHASSIS_SUBTYPE_MAC_ADDRESS); + assert_se(type == SD_LLDP_CHASSIS_SUBTYPE_MAC_ADDRESS); assert_se(length == ETH_ALEN); assert_se(!memcmp(data, "\x00\x01\x02\x03\x04\x05", ETH_ALEN)); assert_se(sd_lldp_neighbor_get_port_id(neighbors[0], &type, &data, &length) == 0); - assert_se(type == LLDP_PORT_SUBTYPE_INTERFACE_NAME); + assert_se(type == SD_LLDP_PORT_SUBTYPE_INTERFACE_NAME); assert_se(length == 3); assert_se(strneq((char *) data, "1/3", 3)); @@ -218,23 +217,23 @@ static void test_receive_oui_packet(sd_event *e) { assert_se(sd_lldp_get_neighbors(lldp, &neighbors) == 1); assert_se(sd_lldp_neighbor_tlv_rewind(neighbors[0]) >= 0); - assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], LLDP_TYPE_CHASSIS_ID) > 0); + assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], SD_LLDP_TYPE_CHASSIS_ID) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], LLDP_TYPE_PORT_ID) > 0); + assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], SD_LLDP_TYPE_PORT_ID) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], LLDP_TYPE_TTL) > 0); + assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], SD_LLDP_TYPE_TTL) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], LLDP_OUI_802_1, LLDP_OUI_802_1_SUBTYPE_PORT_VLAN_ID) > 0); + assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], SD_LLDP_OUI_802_1, SD_LLDP_OUI_802_1_SUBTYPE_PORT_VLAN_ID) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], LLDP_OUI_802_1, LLDP_OUI_802_1_SUBTYPE_PORT_PROTOCOL_VLAN_ID) > 0); + assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], SD_LLDP_OUI_802_1, SD_LLDP_OUI_802_1_SUBTYPE_PORT_PROTOCOL_VLAN_ID) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], LLDP_OUI_802_1, LLDP_OUI_802_1_SUBTYPE_VLAN_NAME) > 0); + assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], SD_LLDP_OUI_802_1, SD_LLDP_OUI_802_1_SUBTYPE_VLAN_NAME) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], LLDP_OUI_802_1, LLDP_OUI_802_1_SUBTYPE_MANAGEMENT_VID) > 0); + assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], SD_LLDP_OUI_802_1, SD_LLDP_OUI_802_1_SUBTYPE_MANAGEMENT_VID) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], LLDP_OUI_802_1, LLDP_OUI_802_1_SUBTYPE_LINK_AGGREGATION) > 0); + assert_se(sd_lldp_neighbor_tlv_is_oui(neighbors[0], SD_LLDP_OUI_802_1, SD_LLDP_OUI_802_1_SUBTYPE_LINK_AGGREGATION) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) > 0); - assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], LLDP_TYPE_END) > 0); + assert_se(sd_lldp_neighbor_tlv_is_type(neighbors[0], SD_LLDP_TYPE_END) > 0); assert_se(sd_lldp_neighbor_tlv_next(neighbors[0]) == 0); sd_lldp_neighbor_unref(neighbors[0]); diff --git a/src/libsystemd/sd-device/sd-device.c b/src/libsystemd/sd-device/sd-device.c index 8657e61cd9..e9f8970d2c 100644 --- a/src/libsystemd/sd-device/sd-device.c +++ b/src/libsystemd/sd-device/sd-device.c @@ -1457,15 +1457,20 @@ static int device_properties_prepare(sd_device *device) { return r; if (device->property_devlinks_outdated) { - char *devlinks = NULL; + _cleanup_free_ char *devlinks = NULL; + size_t devlinks_allocated = 0, devlinks_len = 0; const char *devlink; - devlink = sd_device_get_devlink_first(device); - if (devlink) - devlinks = strdupa(devlink); + for (devlink = sd_device_get_devlink_first(device); devlink; devlink = sd_device_get_devlink_next(device)) { + char *e; - while ((devlink = sd_device_get_devlink_next(device))) - devlinks = strjoina(devlinks, " ", devlink); + if (!GREEDY_REALLOC(devlinks, devlinks_allocated, devlinks_len + strlen(devlink) + 2)) + return -ENOMEM; + if (devlinks_len > 0) + stpcpy(devlinks + devlinks_len++, " "); + e = stpcpy(devlinks + devlinks_len, devlink); + devlinks_len = e - devlinks; + } r = device_add_property_internal(device, "DEVLINKS", devlinks); if (r < 0) @@ -1475,17 +1480,23 @@ static int device_properties_prepare(sd_device *device) { } if (device->property_tags_outdated) { - char *tags = NULL; + _cleanup_free_ char *tags = NULL; + size_t tags_allocated = 0, tags_len = 0; const char *tag; - tag = sd_device_get_tag_first(device); - if (tag) - tags = strjoina(":", tag); + if (!GREEDY_REALLOC(tags, tags_allocated, 2)) + return -ENOMEM; + stpcpy(tags, ":"); + tags_len++; - while ((tag = sd_device_get_tag_next(device))) - tags = strjoina(tags, ":", tag); + for (tag = sd_device_get_tag_first(device); tag; tag = sd_device_get_tag_next(device)) { + char *e; - tags = strjoina(tags, ":"); + if (!GREEDY_REALLOC(tags, tags_allocated, tags_len + strlen(tag) + 1)) + return -ENOMEM; + e = stpcpy(stpcpy(tags + tags_len, tag), ":"); + tags_len = e - tags; + } r = device_add_property_internal(device, "TAGS", tags); if (r < 0) diff --git a/src/locale/localectl.c b/src/locale/localectl.c index cde33bdf41..4865335349 100644 --- a/src/locale/localectl.c +++ b/src/locale/localectl.c @@ -116,11 +116,11 @@ static void print_overridden_variables(void) { if (variables[j]) { if (print_warning) { log_warning("Warning: Settings on kernel command line override system locale settings in /etc/locale.conf.\n" - " Command Line: %s=%s", locale_variable_to_string(j), variables[j]); + " Command Line: %s=%s", locale_variable_to_string(j), variables[j]); print_warning = false; } else - log_warning(" %s=%s", locale_variable_to_string(j), variables[j]); + log_warning(" %s=%s", locale_variable_to_string(j), variables[j]); } finish: for (j = 0; j < _VARIABLE_LC_MAX; j++) @@ -131,7 +131,7 @@ static void print_status_info(StatusInfo *i) { assert(i); if (strv_isempty(i->locale)) - puts(" System Locale: n/a\n"); + puts(" System Locale: n/a"); else { char **j; diff --git a/src/login/70-uaccess.rules b/src/login/70-uaccess.rules index 694df2cfc8..886c5bfcdf 100644 --- a/src/login/70-uaccess.rules +++ b/src/login/70-uaccess.rules @@ -42,8 +42,9 @@ SUBSYSTEM=="firewire", ATTR{units}=="*0x00b09d:0x00010*", TAG+="uaccess" SUBSYSTEM=="firewire", ATTR{units}=="*0x00a02d:0x010001*", TAG+="uaccess" SUBSYSTEM=="firewire", ATTR{units}=="*0x00a02d:0x014001*", TAG+="uaccess" -# DRI video devices +# DRI and frame buffer video devices SUBSYSTEM=="drm", KERNEL=="card*|renderD*", TAG+="uaccess" +SUBSYSTEM=="graphics", KERNEL=="fb*", TAG+="uaccess" # KVM SUBSYSTEM=="misc", KERNEL=="kvm", TAG+="uaccess" @@ -75,4 +76,7 @@ SUBSYSTEM=="usb", ENV{ID_MEDIA_PLAYER}=="?*", TAG+="uaccess" # software-defined radio communication devices ENV{ID_SOFTWARE_RADIO}=="?*", TAG+="uaccess" +# 3D printers, CNC machines, laser cutters, 3D scanners, etc. +ENV{ID_MAKER_TOOL}=="?*", TAG+="uaccess" + LABEL="uaccess_end" diff --git a/src/login/logind-utmp.c b/src/login/logind-utmp.c index 11a91c3947..29ab00eb1f 100644 --- a/src/login/logind-utmp.c +++ b/src/login/logind-utmp.c @@ -65,7 +65,7 @@ bool logind_wall_tty_filter(const char *tty, void *userdata) { assert(m); - if (!startswith(tty, "/dev/")) + if (!startswith(tty, "/dev/") || !m->scheduled_shutdown_tty) return true; return !streq(tty + 5, m->scheduled_shutdown_tty); diff --git a/src/network/networkctl.c b/src/network/networkctl.c index 6ec7a911ca..b22a0f648a 100644 --- a/src/network/networkctl.c +++ b/src/network/networkctl.c @@ -33,7 +33,6 @@ #include "ether-addr-util.h" #include "fd-util.h" #include "hwdb-util.h" -#include "lldp.h" #include "local-addresses.h" #include "locale-util.h" #include "netlink-util.h" diff --git a/src/network/networkd-conf.c b/src/network/networkd-conf.c index 4bc92b8171..8b149124b3 100644 --- a/src/network/networkd-conf.c +++ b/src/network/networkd-conf.c @@ -3,7 +3,7 @@ /*** This file is part of systemd. - Copyright 2014 Tom Gundersen <teg@jklm.no> + Copyright 2014 Vinay Kulkarni <kulkarniv@vmware.com> systemd is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by @@ -37,17 +37,17 @@ int manager_parse_config_file(Manager *m) { false, m); } -static const char* const dhcp_duid_type_table[_DHCP_DUID_TYPE_MAX] = { - [DHCP_DUID_TYPE_RAW] = "raw", - [DHCP_DUID_TYPE_LLT] = "link-layer-time", - [DHCP_DUID_TYPE_EN] = "vendor", - [DHCP_DUID_TYPE_LL] = "link-layer", - [DHCP_DUID_TYPE_UUID] = "uuid" +static const char* const duid_type_table[_DUID_TYPE_MAX] = { + [DUID_TYPE_RAW] = "raw", + [DUID_TYPE_LLT] = "link-layer-time", + [DUID_TYPE_EN] = "vendor", + [DUID_TYPE_LL] = "link-layer", + [DUID_TYPE_UUID] = "uuid" }; -DEFINE_PRIVATE_STRING_TABLE_LOOKUP_FROM_STRING(dhcp_duid_type, DHCPDUIDType); -DEFINE_CONFIG_PARSE_ENUM(config_parse_dhcp_duid_type, dhcp_duid_type, DHCPDUIDType, "Failed to parse DHCP DUID type"); +DEFINE_PRIVATE_STRING_TABLE_LOOKUP_FROM_STRING(duid_type, DUIDType); +DEFINE_CONFIG_PARSE_ENUM(config_parse_duid_type, duid_type, DUIDType, "Failed to parse DUID type"); -int config_parse_dhcp_duid_raw( +int config_parse_duid_rawdata( const char *unit, const char *filename, unsigned line, @@ -61,39 +61,61 @@ int config_parse_dhcp_duid_raw( int r; long byte; char *cbyte, *pnext; - const char *pduid = (const char *)rvalue; - size_t count = 0, duid_len = 0; - Manager *m = userdata; + const char *pduid = rvalue; + size_t count = 0, duid_index = 0; + Manager *m; + Network *n; + DUIDType *duid_type; + uint16_t *dhcp_duid_type; + size_t *dhcp_duid_len; + uint8_t *dhcp_duid; assert(filename); assert(lvalue); assert(rvalue); - assert(m); - assert(m->dhcp_duid_type != _DHCP_DUID_TYPE_INVALID); + assert(userdata); + + if (ltype == DUID_CONFIG_SOURCE_GLOBAL) { + m = userdata; + duid_type = &m->duid_type; + dhcp_duid_type = &m->dhcp_duid_type; + dhcp_duid_len = &m->dhcp_duid_len; + dhcp_duid = m->dhcp_duid; + } else { + /* DUID_CONFIG_SOURCE_NETWORK */ + n = userdata; + duid_type = &n->duid_type; + dhcp_duid_type = &n->dhcp_duid_type; + dhcp_duid_len = &n->dhcp_duid_len; + dhcp_duid = n->dhcp_duid; + } + + if (*duid_type == _DUID_TYPE_INVALID) + *duid_type = DUID_TYPE_RAW; - switch (m->dhcp_duid_type) { - case DHCP_DUID_TYPE_LLT: + switch (*duid_type) { + case DUID_TYPE_LLT: /* RawData contains DUID-LLT link-layer address (offset 6) */ - duid_len = 6; + duid_index = 6; break; - case DHCP_DUID_TYPE_EN: + case DUID_TYPE_EN: /* RawData contains DUID-EN identifier (offset 4) */ - duid_len = 4; + duid_index = 4; break; - case DHCP_DUID_TYPE_LL: + case DUID_TYPE_LL: /* RawData contains DUID-LL link-layer address (offset 2) */ - duid_len = 2; + duid_index = 2; break; - case DHCP_DUID_TYPE_UUID: + case DUID_TYPE_UUID: /* RawData specifies UUID (offset 0) - fall thru */ - case DHCP_DUID_TYPE_RAW: + case DUID_TYPE_RAW: /* First two bytes of RawData is DUID Type - fall thru */ default: break; } - if (m->dhcp_duid_type != DHCP_DUID_TYPE_RAW) - m->dhcp_duid.type = htobe16(m->dhcp_duid_type); + if (*duid_type != DUID_TYPE_RAW) + *dhcp_duid_type = (uint16_t)(*duid_type); /* RawData contains DUID in format " NN:NN:NN... " */ while (true) { @@ -104,7 +126,7 @@ int config_parse_dhcp_duid_raw( } if (r == 0) break; - if (duid_len >= MAX_DUID_LEN) { + if (duid_index >= MAX_DUID_LEN) { log_error("DUID length exceeds maximum length."); return -EINVAL; } @@ -117,17 +139,17 @@ int config_parse_dhcp_duid_raw( return -EINVAL; } - /* If DHCP_DUID_TYPE_RAW, first two bytes holds DUID Type */ - if ((m->dhcp_duid_type == DHCP_DUID_TYPE_RAW) && (count < 2)) { - m->dhcp_duid.type |= (byte << (8 * count)); + /* If DUID_TYPE_RAW, first two bytes hold DHCP DUID type code */ + if ((*duid_type == DUID_TYPE_RAW) && (count < 2)) { + *dhcp_duid_type |= (byte << (8 * (1 - count))); count++; continue; } - m->dhcp_duid.raw.data[duid_len++] = byte; + dhcp_duid[duid_index++] = byte; } - m->dhcp_duid_len = sizeof(m->dhcp_duid.type) + duid_len; + *dhcp_duid_len = duid_index; return 0; } diff --git a/src/network/networkd-conf.h b/src/network/networkd-conf.h index 6d9ce010e3..efc370f839 100644 --- a/src/network/networkd-conf.h +++ b/src/network/networkd-conf.h @@ -5,7 +5,7 @@ /*** This file is part of systemd. - Copyright 2014 Tom Gundersen <teg@jklm.no> + Copyright 2014 Vinay Kulkarni <kulkarniv@vmware.com> systemd is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by @@ -23,10 +23,14 @@ #include "networkd.h" +typedef enum DuidConfigSource { + DUID_CONFIG_SOURCE_GLOBAL = 0, + DUID_CONFIG_SOURCE_NETWORK, +} DuidConfigSource; int manager_parse_config_file(Manager *m); const struct ConfigPerfItem* networkd_gperf_lookup(const char *key, unsigned length); -int config_parse_dhcp_duid_type(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); -int config_parse_dhcp_duid_raw(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); +int config_parse_duid_type(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); +int config_parse_duid_rawdata(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); diff --git a/src/network/networkd-dhcp4.c b/src/network/networkd-dhcp4.c index 3bbb21295c..0589ebf227 100644 --- a/src/network/networkd-dhcp4.c +++ b/src/network/networkd-dhcp4.c @@ -626,10 +626,18 @@ int dhcp4_configure(Link *link) { switch (link->network->dhcp_client_identifier) { case DHCP_CLIENT_ID_DUID: /* If configured, apply user specified DUID and/or IAID */ - r = sd_dhcp_client_set_iaid_duid(link->dhcp_client, - link->network->iaid_value, - link->manager->dhcp_duid_len, - &link->manager->dhcp_duid); + if (link->network->duid_type != _DUID_TYPE_INVALID) + r = sd_dhcp_client_set_iaid_duid(link->dhcp_client, + link->network->iaid, + link->network->dhcp_duid_type, + link->network->dhcp_duid, + link->network->dhcp_duid_len); + else + r = sd_dhcp_client_set_iaid_duid(link->dhcp_client, + link->network->iaid, + link->manager->dhcp_duid_type, + link->manager->dhcp_duid, + link->manager->dhcp_duid_len); if (r < 0) return r; break; diff --git a/src/network/networkd-dhcp6.c b/src/network/networkd-dhcp6.c index 9f59cb3f8a..d4b2fbfc57 100644 --- a/src/network/networkd-dhcp6.c +++ b/src/network/networkd-dhcp6.c @@ -230,13 +230,20 @@ int dhcp6_configure(Link *link) { if (r < 0) goto error; - r = sd_dhcp6_client_set_iaid(client, link->network->iaid_value); + r = sd_dhcp6_client_set_iaid(client, link->network->iaid); if (r < 0) goto error; - r = sd_dhcp6_client_set_duid(client, - link->manager->dhcp_duid_len, - &link->manager->dhcp_duid); + if (link->network->duid_type != _DUID_TYPE_INVALID) + r = sd_dhcp6_client_set_duid(client, + link->network->dhcp_duid_type, + link->network->dhcp_duid, + link->network->dhcp_duid_len); + else + r = sd_dhcp6_client_set_duid(client, + link->manager->dhcp_duid_type, + link->manager->dhcp_duid, + link->manager->dhcp_duid_len); if (r < 0) goto error; diff --git a/src/network/networkd-gperf.gperf b/src/network/networkd-gperf.gperf index 3ef4155476..0625fb335b 100644 --- a/src/network/networkd-gperf.gperf +++ b/src/network/networkd-gperf.gperf @@ -14,5 +14,5 @@ struct ConfigPerfItem; %struct-type %includes %% -DUID.Type, config_parse_dhcp_duid_type, 0, offsetof(Manager, dhcp_duid_type) -DUID.RawData, config_parse_dhcp_duid_raw, 0, offsetof(Manager, dhcp_duid) +DUID.Type, config_parse_duid_type, 0, offsetof(Manager, duid_type) +DUID.RawData, config_parse_duid_rawdata, DUID_CONFIG_SOURCE_GLOBAL, offsetof(Manager, dhcp_duid) diff --git a/src/network/networkd-link.c b/src/network/networkd-link.c index 67b04560cd..88b3cbe90a 100644 --- a/src/network/networkd-link.c +++ b/src/network/networkd-link.c @@ -26,7 +26,6 @@ #include "dhcp-lease-internal.h" #include "fd-util.h" #include "fileio.h" -#include "lldp.h" #include "netlink-util.h" #include "network-internal.h" #include "networkd-link.h" @@ -2234,8 +2233,8 @@ static int link_configure(Link *link) { r = sd_lldp_match_capabilities(link->lldp, link->network->lldp_mode == LLDP_MODE_ROUTERS_ONLY ? - _LLDP_SYSTEM_CAPABILITIES_ALL_ROUTERS : - _LLDP_SYSTEM_CAPABILITIES_ALL); + SD_LLDP_SYSTEM_CAPABILITIES_ALL_ROUTERS : + SD_LLDP_SYSTEM_CAPABILITIES_ALL); if (r < 0) return r; @@ -2782,10 +2781,18 @@ int link_update(Link *link, sd_netlink_message *m) { if (r < 0) return log_link_warning_errno(link, r, "Could not update MAC address in DHCP client: %m"); - r = sd_dhcp_client_set_iaid_duid(link->dhcp_client, - link->network->iaid_value, - link->manager->dhcp_duid_len, - &link->manager->dhcp_duid); + if (link->network->duid_type != _DUID_TYPE_INVALID) + r = sd_dhcp_client_set_iaid_duid(link->dhcp_client, + link->network->iaid, + link->network->dhcp_duid_type, + link->network->dhcp_duid, + link->network->dhcp_duid_len); + else + r = sd_dhcp_client_set_iaid_duid(link->dhcp_client, + link->network->iaid, + link->manager->dhcp_duid_type, + link->manager->dhcp_duid, + link->manager->dhcp_duid_len); if (r < 0) return log_link_warning_errno(link, r, "Could not update DUID/IAID in DHCP client: %m"); } @@ -2799,13 +2806,20 @@ int link_update(Link *link, sd_netlink_message *m) { return log_link_warning_errno(link, r, "Could not update MAC address in DHCPv6 client: %m"); r = sd_dhcp6_client_set_iaid(link->dhcp6_client, - link->network->iaid_value); + link->network->iaid); if (r < 0) return log_link_warning_errno(link, r, "Could not update DHCPv6 IAID: %m"); - r = sd_dhcp6_client_set_duid(link->dhcp6_client, - link->manager->dhcp_duid_len, - &link->manager->dhcp_duid); + if (link->network->duid_type != _DUID_TYPE_INVALID) + r = sd_dhcp6_client_set_duid(link->dhcp6_client, + link->network->dhcp_duid_type, + link->network->dhcp_duid, + link->network->dhcp_duid_len); + else + r = sd_dhcp6_client_set_duid(link->dhcp6_client, + link->manager->dhcp_duid_type, + link->manager->dhcp_duid, + link->manager->dhcp_duid_len); if (r < 0) return log_link_warning_errno(link, r, "Could not update DHCPv6 DUID: %m"); } diff --git a/src/network/networkd-lldp-tx.c b/src/network/networkd-lldp-tx.c index ae8367a60e..5af2a31ea7 100644 --- a/src/network/networkd-lldp-tx.c +++ b/src/network/networkd-lldp-tx.c @@ -24,7 +24,6 @@ #include "fd-util.h" #include "fileio.h" #include "hostname-util.h" -#include "lldp.h" #include "networkd-lldp-tx.h" #include "random-util.h" #include "socket-util.h" @@ -128,51 +127,51 @@ static int lldp_make_packet( h = (struct ether_header*) packet; h->ether_type = htobe16(ETHERTYPE_LLDP); - memcpy(h->ether_dhost, &(struct ether_addr) { LLDP_MULTICAST_ADDR }, ETH_ALEN); + memcpy(h->ether_dhost, &(struct ether_addr) { SD_LLDP_MULTICAST_ADDR }, ETH_ALEN); memcpy(h->ether_shost, hwaddr, ETH_ALEN); p = (uint8_t*) packet + sizeof(struct ether_header); - r = lldp_write_tlv_header(&p, LLDP_TYPE_CHASSIS_ID, 1 + machine_id_length); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_CHASSIS_ID, 1 + machine_id_length); if (r < 0) return r; - *(p++) = LLDP_CHASSIS_SUBTYPE_LOCALLY_ASSIGNED; + *(p++) = SD_LLDP_CHASSIS_SUBTYPE_LOCALLY_ASSIGNED; p = mempcpy(p, machine_id, machine_id_length); - r = lldp_write_tlv_header(&p, LLDP_TYPE_PORT_ID, 1 + ifname_length); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_PORT_ID, 1 + ifname_length); if (r < 0) return r; - *(p++) = LLDP_PORT_SUBTYPE_INTERFACE_NAME; + *(p++) = SD_LLDP_PORT_SUBTYPE_INTERFACE_NAME; p = mempcpy(p, ifname, ifname_length); - r = lldp_write_tlv_header(&p, LLDP_TYPE_TTL, 2); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_TTL, 2); if (r < 0) return r; unaligned_write_be16(p, ttl); p += 2; if (port_description) { - r = lldp_write_tlv_header(&p, LLDP_TYPE_PORT_DESCRIPTION, port_description_length); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_PORT_DESCRIPTION, port_description_length); if (r < 0) return r; p = mempcpy(p, port_description, port_description_length); } if (hostname) { - r = lldp_write_tlv_header(&p, LLDP_TYPE_SYSTEM_NAME, hostname_length); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_SYSTEM_NAME, hostname_length); if (r < 0) return r; p = mempcpy(p, hostname, hostname_length); } if (pretty_hostname) { - r = lldp_write_tlv_header(&p, LLDP_TYPE_SYSTEM_DESCRIPTION, pretty_hostname_length); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_SYSTEM_DESCRIPTION, pretty_hostname_length); if (r < 0) return r; p = mempcpy(p, pretty_hostname, pretty_hostname_length); } - r = lldp_write_tlv_header(&p, LLDP_TYPE_SYSTEM_CAPABILITIES, 4); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_SYSTEM_CAPABILITIES, 4); if (r < 0) return r; unaligned_write_be16(p, system_capabilities); @@ -180,7 +179,7 @@ static int lldp_make_packet( unaligned_write_be16(p, enabled_capabilities); p += 2; - r = lldp_write_tlv_header(&p, LLDP_TYPE_END, 0); + r = lldp_write_tlv_header(&p, SD_LLDP_TYPE_END, 0); if (r < 0) return r; @@ -200,7 +199,7 @@ static int lldp_send_packet(int ifindex, const void *packet, size_t packet_size) .ll.sll_protocol = htobe16(ETHERTYPE_LLDP), .ll.sll_ifindex = ifindex, .ll.sll_halen = ETH_ALEN, - .ll.sll_addr = LLDP_MULTICAST_ADDR, + .ll.sll_addr = SD_LLDP_MULTICAST_ADDR, }; _cleanup_close_ int fd = -1; @@ -245,8 +244,8 @@ static int link_send_lldp(Link *link) { ttl = (usec_t) UINT16_MAX; caps = (link->network && link->network->ip_forward != ADDRESS_FAMILY_NO) ? - LLDP_SYSTEM_CAPABILITIES_ROUTER : - LLDP_SYSTEM_CAPABILITIES_STATION; + SD_LLDP_SYSTEM_CAPABILITIES_ROUTER : + SD_LLDP_SYSTEM_CAPABILITIES_STATION; r = lldp_make_packet(&link->mac, sd_id128_to_string(machine_id, machine_id_string), @@ -255,7 +254,7 @@ static int link_send_lldp(Link *link) { link->network ? link->network->description : NULL, hostname, pretty_hostname, - LLDP_SYSTEM_CAPABILITIES_STATION|LLDP_SYSTEM_CAPABILITIES_BRIDGE|LLDP_SYSTEM_CAPABILITIES_ROUTER, + SD_LLDP_SYSTEM_CAPABILITIES_STATION|SD_LLDP_SYSTEM_CAPABILITIES_BRIDGE|SD_LLDP_SYSTEM_CAPABILITIES_ROUTER, caps, &packet, &packet_size); if (r < 0) diff --git a/src/network/networkd-manager.c b/src/network/networkd-manager.c index 8d443f7b0f..d355aaa19c 100644 --- a/src/network/networkd-manager.c +++ b/src/network/networkd-manager.c @@ -1037,7 +1037,7 @@ int manager_new(Manager **ret) { if (r < 0) return r; - m->dhcp_duid_type = _DHCP_DUID_TYPE_INVALID; + m->duid_type = _DUID_TYPE_INVALID; *ret = m; m = NULL; diff --git a/src/network/networkd-network-gperf.gperf b/src/network/networkd-network-gperf.gperf index 7a9a136d5b..9793938080 100644 --- a/src/network/networkd-network-gperf.gperf +++ b/src/network/networkd-network-gperf.gperf @@ -2,6 +2,7 @@ #include <stddef.h> #include "conf-parser.h" #include "networkd.h" +#include "networkd-conf.h" #include "network-internal.h" %} struct ConfigPerfItem; @@ -26,7 +27,9 @@ Match.KernelCommandLine, config_parse_net_condition, Match.Architecture, config_parse_net_condition, CONDITION_ARCHITECTURE, offsetof(Network, match_arch) Link.MACAddress, config_parse_hwaddr, 0, offsetof(Network, mac) Link.MTUBytes, config_parse_iec_size, 0, offsetof(Network, mtu) -Link.IAIDValue, config_parse_iaid_value, 0, offsetof(Network, iaid_value) +Link.IAID, config_parse_iaid, 0, offsetof(Network, iaid) +DUID.Type, config_parse_duid_type, 0, offsetof(Network, duid_type) +DUID.RawData, config_parse_duid_rawdata, DUID_CONFIG_SOURCE_NETWORK, offsetof(Network, dhcp_duid) Network.Description, config_parse_string, 0, offsetof(Network, description) Network.Bridge, config_parse_netdev, 0, offsetof(Network, bridge) Network.Bond, config_parse_netdev, 0, offsetof(Network, bond) diff --git a/src/network/networkd-network.c b/src/network/networkd-network.c index 491b9a3efa..5946ba18dc 100644 --- a/src/network/networkd-network.c +++ b/src/network/networkd-network.c @@ -131,10 +131,12 @@ static int network_load_one(Manager *manager, const char *filename) { network->ipv6_accept_ra = -1; network->ipv6_dad_transmits = -1; network->ipv6_hop_limit = -1; + network->duid_type = _DUID_TYPE_INVALID; r = config_parse(NULL, filename, file, "Match\0" "Link\0" + "DUID\0" "Network\0" "Address\0" "Route\0" diff --git a/src/network/networkd-network.h b/src/network/networkd-network.h index c5530cdfba..5400a8bc9d 100644 --- a/src/network/networkd-network.h +++ b/src/network/networkd-network.h @@ -24,13 +24,13 @@ typedef struct Network Network; +#include "dhcp-identifier.h" #include "networkd-address.h" #include "networkd-fdb.h" #include "networkd-netdev.h" #include "networkd-route.h" #include "networkd-util.h" #include "networkd.h" -#include "sparse-endian.h" #define DHCP_ROUTE_METRIC 1024 #define IPV4LL_ROUTE_METRIC 2048 @@ -145,7 +145,13 @@ struct Network { struct ether_addr *mac; unsigned mtu; - be32_t iaid_value; + uint32_t iaid; + /* Value of Type in [DUID] section */ + DUIDType duid_type; + /* DUID type code - RFC 3315 */ + uint16_t dhcp_duid_type; + size_t dhcp_duid_len; + uint8_t dhcp_duid[MAX_DUID_LEN]; LLDPMode lldp_mode; /* LLDP reception */ bool lldp_emit; /* LLDP transmission */ diff --git a/src/network/networkd.h b/src/network/networkd.h index d815f30610..72a2438ac8 100644 --- a/src/network/networkd.h +++ b/src/network/networkd.h @@ -31,11 +31,11 @@ typedef struct Manager Manager; +#include "dhcp-identifier.h" #include "networkd-address-pool.h" #include "networkd-link.h" #include "networkd-network.h" #include "networkd-util.h" -#include "dhcp-identifier.h" struct Manager { sd_netlink *rtnl; @@ -63,9 +63,12 @@ struct Manager { usec_t network_dirs_ts_usec; - DHCPDUIDType dhcp_duid_type; + /* Value of Type in [DUID] section */ + DUIDType duid_type; + /* DUID type code - RFC 3315 */ + uint16_t dhcp_duid_type; size_t dhcp_duid_len; - struct duid dhcp_duid; + uint8_t dhcp_duid[MAX_DUID_LEN]; }; extern const char* const network_dirs[]; diff --git a/src/nspawn/nspawn-cgroup.c b/src/nspawn/nspawn-cgroup.c index 1db5ba7116..f50f1ad6c2 100644 --- a/src/nspawn/nspawn-cgroup.c +++ b/src/nspawn/nspawn-cgroup.c @@ -55,8 +55,7 @@ int chown_cgroup(pid_t pid, uid_t uid_shift) { "cgroup.events", "cgroup.clone_children", "cgroup.controllers", - "cgroup.subtree_control", - "cgroup.populated") + "cgroup.subtree_control") if (fchownat(fd, fn, uid_shift, uid_shift, 0) < 0) log_full_errno(errno == ENOENT ? LOG_DEBUG : LOG_WARNING, errno, "Failed to chown() cgroup file %s, ignoring: %m", fn); @@ -73,7 +72,7 @@ int sync_cgroup(pid_t pid, bool unified_requested) { unified = cg_unified(); if (unified < 0) - return log_error_errno(unified, "Failed to determine whether the unified hierachy is used: %m"); + return log_error_errno(unified, "Failed to determine whether the unified hierarchy is used: %m"); if ((unified > 0) == unified_requested) return 0; @@ -94,7 +93,7 @@ int sync_cgroup(pid_t pid, bool unified_requested) { if (unified) r = mount("cgroup", tree, "cgroup", MS_NOSUID|MS_NOEXEC|MS_NODEV, "none,name=systemd,xattr"); else - r = mount("cgroup", tree, "cgroup", MS_NOSUID|MS_NOEXEC|MS_NODEV, "__DEVEL__sane_behavior"); + r = mount("cgroup", tree, "cgroup2", MS_NOSUID|MS_NOEXEC|MS_NODEV, NULL); if (r < 0) { r = log_error_errno(errno, "Failed to mount unified hierarchy: %m"); goto finish; @@ -135,7 +134,7 @@ int create_subcgroup(pid_t pid, bool unified_requested) { unified = cg_unified(); if (unified < 0) - return log_error_errno(unified, "Failed to determine whether the unified hierachy is used: %m"); + return log_error_errno(unified, "Failed to determine whether the unified hierarchy is used: %m"); if (unified == 0) return 0; diff --git a/src/nspawn/nspawn-mount.c b/src/nspawn/nspawn-mount.c index 70cca15278..8e2d2d543c 100644 --- a/src/nspawn/nspawn-mount.c +++ b/src/nspawn/nspawn-mount.c @@ -438,21 +438,22 @@ static int mount_bind(const char *dest, CustomMount *m) { r = mkdir_parents_label(where, 0755); if (r < 0) return log_error_errno(r, "Failed to make parents of %s: %m", where); + + /* Create the mount point. Any non-directory file can be + * mounted on any non-directory file (regular, fifo, socket, + * char, block). + */ + if (S_ISDIR(source_st.st_mode)) + r = mkdir_label(where, 0755); + else + r = touch(where); + if (r < 0) + return log_error_errno(r, "Failed to create mount point %s: %m", where); + } else { return log_error_errno(errno, "Failed to stat %s: %m", where); } - /* Create the mount point. Any non-directory file can be - * mounted on any non-directory file (regular, fifo, socket, - * char, block). - */ - if (S_ISDIR(source_st.st_mode)) - r = mkdir_label(where, 0755); - else - r = touch(where); - if (r < 0 && r != -EEXIST) - return log_error_errno(r, "Failed to create mount point %s: %m", where); - if (mount(m->source, where, NULL, mount_flags, mount_opts) < 0) return log_error_errno(errno, "mount(%s) failed: %m", where); @@ -750,7 +751,7 @@ static int mount_unified_cgroups(const char *dest) { return -EINVAL; } - if (mount("cgroup", p, "cgroup", MS_NOSUID|MS_NOEXEC|MS_NODEV, "__DEVEL__sane_behavior") < 0) + if (mount("cgroup", p, "cgroup2", MS_NOSUID|MS_NOEXEC|MS_NODEV, NULL) < 0) return log_error_errno(errno, "Failed to mount unified cgroup hierarchy to %s: %m", p); return 0; diff --git a/src/nspawn/nspawn.c b/src/nspawn/nspawn.c index be07625a03..eb89916b7e 100644 --- a/src/nspawn/nspawn.c +++ b/src/nspawn/nspawn.c @@ -977,6 +977,13 @@ static int verify_arguments(void) { return -EINVAL; } +#ifndef HAVE_LIBIPTC + if (arg_expose_ports) { + log_error("--port= is not supported, compiled without libiptc support."); + return -EOPNOTSUPP; + } +#endif + if (arg_start_mode == START_BOOT && arg_kill_signal <= 0) arg_kill_signal = SIGRTMIN+3; diff --git a/src/resolve/resolve-tool.c b/src/resolve/resolve-tool.c index 009cc73aec..14ee01c49d 100644 --- a/src/resolve/resolve-tool.c +++ b/src/resolve/resolve-tool.c @@ -17,7 +17,6 @@ along with systemd; If not, see <http://www.gnu.org/licenses/>. ***/ -#include <gcrypt.h> #include <getopt.h> #include <net/if.h> @@ -863,7 +862,7 @@ static int resolve_openpgp(sd_bus *bus, const char *address) { } domain++; - r = string_hashsum(address, domain - 1 - address, GCRY_MD_SHA224, &hashed); + r = string_hashsum_sha224(address, domain - 1 - address, &hashed); if (r < 0) return log_error_errno(r, "Hashing failed: %m"); diff --git a/src/run/run.c b/src/run/run.c index 1ed1bd96bf..f92a7f4e2e 100644 --- a/src/run/run.c +++ b/src/run/run.c @@ -878,7 +878,7 @@ static int start_transient_service( (void) sd_event_add_signal(event, NULL, SIGTERM, NULL, NULL); if (!arg_quiet) - log_info("Running as unit %s.\nPress ^] three times within 1s to disconnect TTY.", service); + log_info("Running as unit: %s\nPress ^] three times within 1s to disconnect TTY.", service); r = pty_forward_new(event, master, PTY_FORWARD_IGNORE_INITIAL_VHANGUP, &forward); if (r < 0) @@ -896,7 +896,7 @@ static int start_transient_service( fputc('\n', stdout); } else if (!arg_quiet) - log_info("Running as unit %s.", service); + log_info("Running as unit: %s", service); return 0; } @@ -1038,7 +1038,7 @@ static int start_transient_scope( return r; if (!arg_quiet) - log_info("Running scope as unit %s.", scope); + log_info("Running scope as unit: %s", scope); execvpe(argv[0], argv, env); @@ -1189,9 +1189,9 @@ static int start_transient_timer( if (r < 0) return r; - log_info("Running timer as unit %s.", timer); + log_info("Running timer as unit: %s", timer); if (argv[0]) - log_info("Will run service as unit %s.", service); + log_info("Will run service as unit: %s", service); return 0; } diff --git a/src/shared/bus-util.c b/src/shared/bus-util.c index 0fa04da935..0caaca03c7 100644 --- a/src/shared/bus-util.c +++ b/src/shared/bus-util.c @@ -1078,7 +1078,7 @@ static int map_basic(sd_bus *bus, const char *member, sd_bus_message *m, sd_bus_ } case SD_BUS_TYPE_UINT32: { - uint64_t u; + uint32_t u; uint32_t *p = userdata; r = sd_bus_message_read_basic(m, type, &u); @@ -2040,7 +2040,7 @@ static const struct { static void log_job_error_with_service_result(const char* service, const char *result, const char* const* extra_args) { _cleanup_free_ char *service_shell_quoted = NULL; - const char *systemctl = "systemctl", *journalctl = "journalct"; + const char *systemctl = "systemctl", *journalctl = "journalctl"; assert(service); diff --git a/src/shared/conf-parser.c b/src/shared/conf-parser.c index e7fe9ac21e..bd0a1f483b 100644 --- a/src/shared/conf-parser.c +++ b/src/shared/conf-parser.c @@ -294,7 +294,7 @@ int config_parse(const char *unit, _cleanup_free_ char *section = NULL, *continuation = NULL; _cleanup_fclose_ FILE *ours = NULL; unsigned line = 0, section_line = 0; - bool section_ignored = false; + bool section_ignored = false, allow_bom = true; int r; assert(filename); @@ -314,11 +314,11 @@ int config_parse(const char *unit, fd_warn_permissions(filename, fileno(f)); - while (!feof(f)) { - char l[LINE_MAX], *p, *c = NULL, *e; + for (;;) { + char buf[LINE_MAX], *l, *p, *c = NULL, *e; bool escaped = false; - if (!fgets(l, sizeof(l), f)) { + if (!fgets(buf, sizeof buf, f)) { if (feof(f)) break; @@ -326,6 +326,11 @@ int config_parse(const char *unit, return -errno; } + l = buf; + if (allow_bom && startswith(l, UTF8_BYTE_ORDER_MARK)) + l += strlen(UTF8_BYTE_ORDER_MARK); + allow_bom = false; + truncate_nl(l); if (continuation) { diff --git a/src/shared/gcrypt-util.c b/src/shared/gcrypt-util.c index 4ff94520c3..39b544b6f0 100644 --- a/src/shared/gcrypt-util.c +++ b/src/shared/gcrypt-util.c @@ -19,10 +19,11 @@ along with systemd; If not, see <http://www.gnu.org/licenses/>. ***/ +#ifdef HAVE_GCRYPT #include <gcrypt.h> -#include "hexdecoct.h" #include "gcrypt-util.h" +#include "hexdecoct.h" void initialize_libgcrypt(bool secmem) { const char *p; @@ -67,3 +68,4 @@ int string_hashsum(const char *s, size_t len, int md_algorithm, char **out) { *out = enc; return 0; } +#endif diff --git a/src/shared/gcrypt-util.h b/src/shared/gcrypt-util.h index c7652c22d1..cf33b3c59c 100644 --- a/src/shared/gcrypt-util.h +++ b/src/shared/gcrypt-util.h @@ -19,7 +19,21 @@ along with systemd; If not, see <http://www.gnu.org/licenses/>. ***/ +#include <errno.h> #include <stdbool.h> +#include <stddef.h> + +#ifdef HAVE_GCRYPT +#include <gcrypt.h> void initialize_libgcrypt(bool secmem); int string_hashsum(const char *s, size_t len, int md_algorithm, char **out); +#endif + +static inline int string_hashsum_sha224(const char *s, size_t len, char **out) { +#ifdef HAVE_GCRYPT + return string_hashsum(s, len, GCRY_MD_SHA224, out); +#else + return -EOPNOTSUPP; +#endif +} diff --git a/src/shared/spawn-polkit-agent.c b/src/shared/spawn-polkit-agent.c index cf3c8ad5a3..7dae4d14fe 100644 --- a/src/shared/spawn-polkit-agent.c +++ b/src/shared/spawn-polkit-agent.c @@ -44,6 +44,10 @@ int polkit_agent_open(void) { if (agent_pid > 0) return 0; + /* Clients that run as root don't need to activate/query polkit */ + if (geteuid() == 0) + return 0; + /* We check STDIN here, not STDOUT, since this is about input, * not output */ if (!isatty(STDIN_FILENO)) diff --git a/src/systemctl/systemctl.c b/src/systemctl/systemctl.c index 57e62a607b..62cff3a677 100644 --- a/src/systemctl/systemctl.c +++ b/src/systemctl/systemctl.c @@ -341,6 +341,11 @@ static bool output_show_unit(const UnitInfo *u, char **patterns) { if (arg_all) return true; + if (!strv_isempty(arg_states)) + return true; + + /* By default show all units except the ones in inactive + * state and with no pending job */ if (u->job_id > 0) return true; @@ -1892,13 +1897,13 @@ static void output_machines_list(struct machine_info *machine_infos, unsigned n) printf("%s%s%s ", on_state, circle ? draw_special_char(DRAW_BLACK_CIRCLE) : " ", off_state); if (m->is_host) - printf("%-*s (host) %s%-*s%s %s%*u%s %*u\n", + printf("%-*s (host) %s%-*s%s %s%*" PRIu32 "%s %*" PRIu32 "\n", (int) (namelen - (sizeof(" (host)")-1)), strna(m->name), on_state, statelen, strna(m->state), off_state, on_failed, failedlen, m->n_failed_units, off_failed, jobslen, m->n_jobs); else - printf("%-*s %s%-*s%s %s%*u%s %*u\n", + printf("%-*s %s%-*s%s %s%*" PRIu32 "%s %*" PRIu32 "\n", namelen, strna(m->name), on_state, statelen, strna(m->state), off_state, on_failed, failedlen, m->n_failed_units, off_failed, @@ -4645,8 +4650,8 @@ static int show_system_status(sd_bus *bus) { printf(" State: %s%s%s\n", on, strna(mi.state), off); - printf(" Jobs: %u queued\n", mi.n_jobs); - printf(" Failed: %u units\n", mi.n_failed_units); + printf(" Jobs: %" PRIu32 " queued\n", mi.n_jobs); + printf(" Failed: %" PRIu32 " units\n", mi.n_failed_units); printf(" Since: %s; %s\n", format_timestamp(since2, sizeof(since2), mi.timestamp), diff --git a/src/systemd/sd-dhcp-client.h b/src/systemd/sd-dhcp-client.h index 7873cb1e04..374ff8774e 100644 --- a/src/systemd/sd-dhcp-client.h +++ b/src/systemd/sd-dhcp-client.h @@ -27,7 +27,6 @@ #include "sd-dhcp-lease.h" #include "sd-event.h" -#include "sparse-endian.h" #include "_sd-common.h" @@ -83,7 +82,6 @@ enum { SD_DHCP_OPTION_END = 255, }; -struct duid; typedef struct sd_dhcp_client sd_dhcp_client; typedef void (*sd_dhcp_client_callback_t)(sd_dhcp_client *client, int event, @@ -100,8 +98,8 @@ int sd_dhcp_client_set_mac(sd_dhcp_client *client, const uint8_t *addr, size_t addr_len, uint16_t arp_type); int sd_dhcp_client_set_client_id(sd_dhcp_client *client, uint8_t type, const uint8_t *data, size_t data_len); -int sd_dhcp_client_set_iaid_duid(sd_dhcp_client *client, be32_t iaid, - size_t duid_len, struct duid *duid); +int sd_dhcp_client_set_iaid_duid(sd_dhcp_client *client, uint32_t iaid, + uint16_t duid_type, uint8_t *duid, size_t duid_len); int sd_dhcp_client_get_client_id(sd_dhcp_client *client, uint8_t *type, const uint8_t **data, size_t *data_len); int sd_dhcp_client_set_mtu(sd_dhcp_client *client, uint32_t mtu); diff --git a/src/systemd/sd-dhcp6-client.h b/src/systemd/sd-dhcp6-client.h index ebdd017628..4604cb6382 100644 --- a/src/systemd/sd-dhcp6-client.h +++ b/src/systemd/sd-dhcp6-client.h @@ -26,7 +26,6 @@ #include "sd-dhcp6-lease.h" #include "sd-event.h" -#include "sparse-endian.h" #include "_sd-common.h" @@ -75,7 +74,6 @@ enum { /* option codes 144-65535 are unassigned */ }; -struct duid; typedef struct sd_dhcp6_client sd_dhcp6_client; typedef void (*sd_dhcp6_client_callback_t)(sd_dhcp6_client *client, int event, @@ -87,9 +85,9 @@ int sd_dhcp6_client_set_index(sd_dhcp6_client *client, int interface_index); int sd_dhcp6_client_set_local_address(sd_dhcp6_client *client, const struct in6_addr *local_address); int sd_dhcp6_client_set_mac(sd_dhcp6_client *client, const uint8_t *addr, size_t addr_len, uint16_t arp_type); -int sd_dhcp6_client_set_duid(sd_dhcp6_client *client, size_t duid_len, - struct duid *duid); -int sd_dhcp6_client_set_iaid(sd_dhcp6_client *client, be32_t iaid); +int sd_dhcp6_client_set_duid(sd_dhcp6_client *client, uint16_t duid_type, + uint8_t *duid, size_t duid_len); +int sd_dhcp6_client_set_iaid(sd_dhcp6_client *client, uint32_t iaid); int sd_dhcp6_client_set_information_request(sd_dhcp6_client *client, int enabled); int sd_dhcp6_client_get_information_request(sd_dhcp6_client *client, int *enabled); int sd_dhcp6_client_set_request_option(sd_dhcp6_client *client, diff --git a/src/systemd/sd-lldp.h b/src/systemd/sd-lldp.h index f7eff58769..4f2a3b50c0 100644 --- a/src/systemd/sd-lldp.h +++ b/src/systemd/sd-lldp.h @@ -33,6 +33,87 @@ _SD_BEGIN_DECLARATIONS; typedef struct sd_lldp sd_lldp; typedef struct sd_lldp_neighbor sd_lldp_neighbor; +#define SD_LLDP_MULTICAST_ADDR { 0x01, 0x80, 0xc2, 0x00, 0x00, 0x0e } + +/* IEEE 802.3AB Clause 9: TLV Types */ +enum { + SD_LLDP_TYPE_END = 0, + SD_LLDP_TYPE_CHASSIS_ID = 1, + SD_LLDP_TYPE_PORT_ID = 2, + SD_LLDP_TYPE_TTL = 3, + SD_LLDP_TYPE_PORT_DESCRIPTION = 4, + SD_LLDP_TYPE_SYSTEM_NAME = 5, + SD_LLDP_TYPE_SYSTEM_DESCRIPTION = 6, + SD_LLDP_TYPE_SYSTEM_CAPABILITIES = 7, + SD_LLDP_TYPE_MGMT_ADDRESS = 8, + SD_LLDP_TYPE_PRIVATE = 127, +}; + +/* IEEE 802.3AB Clause 9.5.2: Chassis subtypes */ +enum { + SD_LLDP_CHASSIS_SUBTYPE_RESERVED = 0, + SD_LLDP_CHASSIS_SUBTYPE_CHASSIS_COMPONENT = 1, + SD_LLDP_CHASSIS_SUBTYPE_INTERFACE_ALIAS = 2, + SD_LLDP_CHASSIS_SUBTYPE_PORT_COMPONENT = 3, + SD_LLDP_CHASSIS_SUBTYPE_MAC_ADDRESS = 4, + SD_LLDP_CHASSIS_SUBTYPE_NETWORK_ADDRESS = 5, + SD_LLDP_CHASSIS_SUBTYPE_INTERFACE_NAME = 6, + SD_LLDP_CHASSIS_SUBTYPE_LOCALLY_ASSIGNED = 7, +}; + +/* IEEE 802.3AB Clause 9.5.3: Port subtype */ +enum { + SD_LLDP_PORT_SUBTYPE_RESERVED = 0, + SD_LLDP_PORT_SUBTYPE_INTERFACE_ALIAS = 1, + SD_LLDP_PORT_SUBTYPE_PORT_COMPONENT = 2, + SD_LLDP_PORT_SUBTYPE_MAC_ADDRESS = 3, + SD_LLDP_PORT_SUBTYPE_NETWORK_ADDRESS = 4, + SD_LLDP_PORT_SUBTYPE_INTERFACE_NAME = 5, + SD_LLDP_PORT_SUBTYPE_AGENT_CIRCUIT_ID = 6, + SD_LLDP_PORT_SUBTYPE_LOCALLY_ASSIGNED = 7, +}; + +enum { + SD_LLDP_SYSTEM_CAPABILITIES_OTHER = 1 << 0, + SD_LLDP_SYSTEM_CAPABILITIES_REPEATER = 1 << 1, + SD_LLDP_SYSTEM_CAPABILITIES_BRIDGE = 1 << 2, + SD_LLDP_SYSTEM_CAPABILITIES_WLAN_AP = 1 << 3, + SD_LLDP_SYSTEM_CAPABILITIES_ROUTER = 1 << 4, + SD_LLDP_SYSTEM_CAPABILITIES_PHONE = 1 << 5, + SD_LLDP_SYSTEM_CAPABILITIES_DOCSIS = 1 << 6, + SD_LLDP_SYSTEM_CAPABILITIES_STATION = 1 << 7, + SD_LLDP_SYSTEM_CAPABILITIES_CVLAN = 1 << 8, + SD_LLDP_SYSTEM_CAPABILITIES_SVLAN = 1 << 9, + SD_LLDP_SYSTEM_CAPABILITIES_TPMR = 1 << 10, +}; + +#define SD_LLDP_SYSTEM_CAPABILITIES_ALL ((uint16_t) -1) + +#define SD_LLDP_SYSTEM_CAPABILITIES_ALL_ROUTERS \ + ((uint16_t) \ + (SD_LLDP_SYSTEM_CAPABILITIES_REPEATER| \ + SD_LLDP_SYSTEM_CAPABILITIES_BRIDGE| \ + SD_LLDP_SYSTEM_CAPABILITIES_WLAN_AP| \ + SD_LLDP_SYSTEM_CAPABILITIES_ROUTER| \ + SD_LLDP_SYSTEM_CAPABILITIES_DOCSIS| \ + SD_LLDP_SYSTEM_CAPABILITIES_CVLAN| \ + SD_LLDP_SYSTEM_CAPABILITIES_SVLAN| \ + SD_LLDP_SYSTEM_CAPABILITIES_TPMR)) + + +#define SD_LLDP_OUI_802_1 (uint8_t[]) { 0x00, 0x80, 0xc2 } +#define SD_LLDP_OUI_802_3 (uint8_t[]) { 0x00, 0x12, 0x0f } + +enum { + SD_LLDP_OUI_802_1_SUBTYPE_PORT_VLAN_ID = 1, + SD_LLDP_OUI_802_1_SUBTYPE_PORT_PROTOCOL_VLAN_ID = 2, + SD_LLDP_OUI_802_1_SUBTYPE_VLAN_NAME = 3, + SD_LLDP_OUI_802_1_SUBTYPE_PROTOCOL_IDENTITY = 4, + SD_LLDP_OUI_802_1_SUBTYPE_VID_USAGE_DIGEST = 5, + SD_LLDP_OUI_802_1_SUBTYPE_MANAGEMENT_VID = 6, + SD_LLDP_OUI_802_1_SUBTYPE_LINK_AGGREGATION = 7, +}; + typedef enum sd_lldp_event { SD_LLDP_EVENT_ADDED = 'a', SD_LLDP_EVENT_REMOVED = 'r', diff --git a/src/test/test-copy.c b/src/test/test-copy.c index ad57cb0202..cb437754b4 100644 --- a/src/test/test-copy.c +++ b/src/test/test-copy.c @@ -24,6 +24,7 @@ #include "fd-util.h" #include "fileio.h" #include "fs-util.h" +#include "log.h" #include "macro.h" #include "mkdir.h" #include "path-util.h" @@ -39,6 +40,8 @@ static void test_copy_file(void) { size_t sz = 0; int fd; + log_info("%s", __func__); + fd = mkostemp_safe(fn, O_RDWR|O_CLOEXEC); assert_se(fd >= 0); close(fd); @@ -66,6 +69,8 @@ static void test_copy_file_fd(void) { char text[] = "boohoo\nfoo\n\tbar\n"; char buf[64] = {0}; + log_info("%s", __func__); + in_fd = mkostemp_safe(in_fn, O_RDWR); assert_se(in_fd >= 0); out_fd = mkostemp_safe(out_fn, O_RDWR); @@ -91,6 +96,8 @@ static void test_copy_tree(void) { "link2", "dir1/file"); char **p, **link; + log_info("%s", __func__); + (void) rm_rf(copy_dir, REMOVE_ROOT|REMOVE_PHYSICAL); (void) rm_rf(original_dir, REMOVE_ROOT|REMOVE_PHYSICAL); @@ -173,11 +180,65 @@ static void test_copy_bytes(void) { assert_se(r == -EBADF); } +static void test_copy_bytes_regular_file(const char *src, bool try_reflink, uint64_t max_bytes) { + char fn2[] = "/tmp/test-copy-file-XXXXXX"; + char fn3[] = "/tmp/test-copy-file-XXXXXX"; + _cleanup_close_ int fd = -1, fd2 = -1, fd3 = -1; + int r; + struct stat buf, buf2, buf3; + + log_info("%s try_reflink=%s max_bytes=%" PRIu64, __func__, yes_no(try_reflink), max_bytes); + + fd = open(src, O_RDONLY | O_CLOEXEC | O_NOCTTY); + assert_se(fd >= 0); + + fd2 = mkostemp_safe(fn2, O_RDWR); + assert_se(fd2 >= 0); + + fd3 = mkostemp_safe(fn3, O_WRONLY); + assert_se(fd3 >= 0); + + r = copy_bytes(fd, fd2, max_bytes, try_reflink); + if (max_bytes == (uint64_t) -1) + assert_se(r == 0); + else + assert_se(IN_SET(r, 0, 1)); + + assert_se(lseek(fd2, 0, SEEK_SET) == 0); + + r = copy_bytes(fd2, fd3, max_bytes, try_reflink); + if (max_bytes == (uint64_t) -1) + assert_se(r == 0); + else + /* We cannot distinguish between the input being exactly max_bytes + * or longer than max_bytes (without trying to read one more byte, + * or calling stat, or FION_READ, etc, and we don't want to do any + * of that). So we expect "truncation" since we know that file we + * are copying is exactly max_bytes bytes. */ + assert_se(r == 1); + + assert_se(fstat(fd, &buf) == 0); + assert_se(fstat(fd2, &buf2) == 0); + assert_se(fstat(fd3, &buf3) == 0); + + assert_se((uint64_t) buf2.st_size == MIN((uint64_t) buf.st_size, max_bytes)); + assert_se(buf3.st_size == buf2.st_size); + + unlink(fn2); + unlink(fn3); +} + int main(int argc, char *argv[]) { test_copy_file(); test_copy_file_fd(); test_copy_tree(); test_copy_bytes(); + test_copy_bytes_regular_file(argv[0], false, (uint64_t) -1); + test_copy_bytes_regular_file(argv[0], true, (uint64_t) -1); + test_copy_bytes_regular_file(argv[0], false, 1000); /* smaller than copy buffer size */ + test_copy_bytes_regular_file(argv[0], true, 1000); + test_copy_bytes_regular_file(argv[0], false, 32000); /* larger than copy buffer size */ + test_copy_bytes_regular_file(argv[0], true, 32000); return 0; } diff --git a/src/test/test-env-replace.c b/src/test/test-env-util.c index 264acc6ea6..35bb62906e 100644 --- a/src/test/test-env-replace.c +++ b/src/test/test-env-util.c @@ -2,6 +2,7 @@ This file is part of systemd. Copyright 2010 Lennart Poettering + Copyright 2016 Zbigniew Jędrzejewski-Szmek systemd is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by @@ -177,10 +178,37 @@ static void test_env_name_is_valid(void) { assert_se(!env_name_is_valid(NULL)); assert_se(!env_name_is_valid("")); + assert_se(!env_name_is_valid("xxx\a")); + assert_se(!env_name_is_valid("xxx\007b")); + assert_se(!env_name_is_valid("\007\009")); assert_se(!env_name_is_valid("5_starting_with_a_number_is_wrong")); assert_se(!env_name_is_valid("#¤%&?_only_numbers_letters_and_underscore_allowed")); } +static void test_env_value_is_valid(void) { + assert_se(env_value_is_valid("")); + assert_se(env_value_is_valid("głąb kapuściany")); + assert_se(env_value_is_valid("printf \"\\x1b]0;<mock-chroot>\\x07<mock-chroot>\"")); +} + +static void test_env_assignment_is_valid(void) { + assert_se(env_assignment_is_valid("a=")); + assert_se(env_assignment_is_valid("b=głąb kapuściany")); + assert_se(env_assignment_is_valid("c=\\007\\009\\011")); + assert_se(env_assignment_is_valid("e=printf \"\\x1b]0;<mock-chroot>\\x07<mock-chroot>\"")); + + assert_se(!env_assignment_is_valid("=")); + assert_se(!env_assignment_is_valid("a b=")); + assert_se(!env_assignment_is_valid("a =")); + assert_se(!env_assignment_is_valid(" b=")); + /* no dots or dashes: http://tldp.org/LDP/abs/html/gotchas.html */ + assert_se(!env_assignment_is_valid("a.b=")); + assert_se(!env_assignment_is_valid("a-b=")); + assert_se(!env_assignment_is_valid("\007=głąb kapuściany")); + assert_se(!env_assignment_is_valid("c\009=\007\009\011")); + assert_se(!env_assignment_is_valid("głąb=printf \"\x1b]0;<mock-chroot>\x07<mock-chroot>\"")); +} + int main(int argc, char *argv[]) { test_strv_env_delete(); test_strv_env_unset(); @@ -189,6 +217,8 @@ int main(int argc, char *argv[]) { test_replace_env_arg(); test_env_clean(); test_env_name_is_valid(); + test_env_value_is_valid(); + test_env_assignment_is_valid(); return 0; } diff --git a/src/test/test-execute.c b/src/test/test-execute.c index 0d2e4bfc15..901cc44af6 100644 --- a/src/test/test-execute.c +++ b/src/test/test-execute.c @@ -130,18 +130,33 @@ static void test_exec_systemcallerrornumber(Manager *m) { #endif } +static void test_exec_systemcall_system_mode_with_user(Manager *m) { +#ifdef HAVE_SECCOMP + if (getpwnam("nobody")) + test(m, "exec-systemcallfilter-system-user.service", 0, CLD_EXITED); + else if (getpwnam("nfsnobody")) + test(m, "exec-systemcallfilter-system-user-nfsnobody.service", 0, CLD_EXITED); + else + log_error_errno(errno, "Skipping test_exec_systemcall_system_mode_with_user, could not find nobody/nfsnobody user: %m"); +#endif +} + static void test_exec_user(Manager *m) { if (getpwnam("nobody")) test(m, "exec-user.service", 0, CLD_EXITED); + else if (getpwnam("nfsnobody")) + test(m, "exec-user-nfsnobody.service", 0, CLD_EXITED); else - log_error_errno(errno, "Skipping test_exec_user, could not find nobody user: %m"); + log_error_errno(errno, "Skipping test_exec_user, could not find nobody/nfsnobody user: %m"); } static void test_exec_group(Manager *m) { if (getgrnam("nobody")) test(m, "exec-group.service", 0, CLD_EXITED); + else if (getgrnam("nfsnobody")) + test(m, "exec-group-nfsnobody.service", 0, CLD_EXITED); else - log_error_errno(errno, "Skipping test_exec_group, could not find nobody group: %m"); + log_error_errno(errno, "Skipping test_exec_group, could not find nobody/nfsnobody group: %m"); } static void test_exec_environment(Manager *m) { @@ -204,8 +219,10 @@ static void test_exec_runtimedirectory(Manager *m) { test(m, "exec-runtimedirectory-mode.service", 0, CLD_EXITED); if (getgrnam("nobody")) test(m, "exec-runtimedirectory-owner.service", 0, CLD_EXITED); + else if (getgrnam("nfsnobody")) + test(m, "exec-runtimedirectory-owner-nfsnobody.service", 0, CLD_EXITED); else - log_error_errno(errno, "Skipping test_exec_runtimedirectory-owner, could not find nobody group: %m"); + log_error_errno(errno, "Skipping test_exec_runtimedirectory-owner, could not find nobody/nfsnobody group: %m"); } static void test_exec_capabilityboundingset(Manager *m) { @@ -234,9 +251,16 @@ static void test_exec_capabilityambientset(Manager *m) { * in the first place for the tests. */ r = prctl(PR_CAP_AMBIENT, PR_CAP_AMBIENT_CLEAR_ALL, 0, 0, 0); if (r >= 0 || errno != EINVAL) { - test(m, "exec-capabilityambientset.service", 0, CLD_EXITED); - test(m, "exec-capabilityambientset-merge.service", 0, CLD_EXITED); - } + if (getpwnam("nobody")) { + test(m, "exec-capabilityambientset.service", 0, CLD_EXITED); + test(m, "exec-capabilityambientset-merge.service", 0, CLD_EXITED); + } else if (getpwnam("nfsnobody")) { + test(m, "exec-capabilityambientset-nfsnobody.service", 0, CLD_EXITED); + test(m, "exec-capabilityambientset-merge-nfsnobody.service", 0, CLD_EXITED); + } else + log_error_errno(errno, "Skipping test_exec_capabilityambientset, could not find nobody/nfsnobody user: %m"); + } else + log_error_errno(errno, "Skipping test_exec_capabilityambientset, the kernel does not support ambient capabilities: %m"); } static void test_exec_privatenetwork(Manager *m) { @@ -267,8 +291,31 @@ static void test_exec_spec_interpolation(Manager *m) { test(m, "exec-spec-interpolation.service", 0, CLD_EXITED); } +static int run_tests(ManagerRunningAs running_as, test_function_t *tests) { + test_function_t *test = NULL; + Manager *m = NULL; + int r; + + assert_se(tests); + + r = manager_new(running_as, true, &m); + if (MANAGER_SKIP_TEST(r)) { + printf("Skipping test: manager_new: %s\n", strerror(-r)); + return EXIT_TEST_SKIP; + } + assert_se(r >= 0); + assert_se(manager_startup(m, NULL, NULL) >= 0); + + for (test = tests; test && *test; test++) + (*test)(m); + + manager_free(m); + + return 0; +} + int main(int argc, char *argv[]) { - test_function_t tests[] = { + test_function_t user_tests[] = { test_exec_workingdirectory, test_exec_personality, test_exec_ignoresigpipe, @@ -291,8 +338,10 @@ int main(int argc, char *argv[]) { test_exec_spec_interpolation, NULL, }; - test_function_t *test = NULL; - Manager *m = NULL; + test_function_t system_tests[] = { + test_exec_systemcall_system_mode_with_user, + NULL, + }; int r; log_parse_environment(); @@ -317,18 +366,9 @@ int main(int argc, char *argv[]) { assert_se(unsetenv("VAR2") == 0); assert_se(unsetenv("VAR3") == 0); - r = manager_new(MANAGER_USER, true, &m); - if (MANAGER_SKIP_TEST(r)) { - printf("Skipping test: manager_new: %s\n", strerror(-r)); - return EXIT_TEST_SKIP; - } - assert_se(r >= 0); - assert_se(manager_startup(m, NULL, NULL) >= 0); - - for (test = tests; test && *test; test++) - (*test)(m); + r = run_tests(MANAGER_USER, user_tests); + if (r != 0) + return r; - manager_free(m); - - return 0; + return run_tests(MANAGER_SYSTEM, system_tests); } diff --git a/src/test/test-udev.c b/src/test/test-udev.c index d01789fe08..64ef08652c 100644 --- a/src/test/test-udev.c +++ b/src/test/test-udev.c @@ -40,11 +40,11 @@ static int fake_filesystems(void) { const char *target; const char *error; } fakefss[] = { - { "test/sys", "/sys", "failed to mount test /sys" }, - { "test/dev", "/dev", "failed to mount test /dev" }, - { "test/run", "/run", "failed to mount test /run" }, - { "test/run", "/etc/udev/rules.d", "failed to mount empty /etc/udev/rules.d" }, - { "test/run", UDEVLIBEXECDIR "/rules.d","failed to mount empty " UDEVLIBEXECDIR "/rules.d" }, + { "test/tmpfs/sys", "/sys", "failed to mount test /sys" }, + { "test/dev", "/dev", "failed to mount test /dev" }, + { "test/run", "/run", "failed to mount test /run" }, + { "test/run", "/etc/udev/rules.d", "failed to mount empty /etc/udev/rules.d" }, + { "test/run", UDEVLIBEXECDIR "/rules.d","failed to mount empty " UDEVLIBEXECDIR "/rules.d" }, }; unsigned int i; int err; diff --git a/test/test-execute/exec-capabilityambientset-merge-nfsnobody.service b/test/test-execute/exec-capabilityambientset-merge-nfsnobody.service new file mode 100644 index 0000000000..00bec581b5 --- /dev/null +++ b/test/test-execute/exec-capabilityambientset-merge-nfsnobody.service @@ -0,0 +1,9 @@ +[Unit] +Description=Test for AmbientCapabilities + +[Service] +ExecStart=/bin/sh -x -c 'c=$$(grep "CapAmb:" /proc/self/status); test "$$c" = "CapAmb: 0000000000003000"' +Type=oneshot +User=nfsnobody +AmbientCapabilities=CAP_NET_ADMIN +AmbientCapabilities=CAP_NET_RAW diff --git a/test/test-execute/exec-capabilityambientset-nfsnobody.service b/test/test-execute/exec-capabilityambientset-nfsnobody.service new file mode 100644 index 0000000000..614cfdd584 --- /dev/null +++ b/test/test-execute/exec-capabilityambientset-nfsnobody.service @@ -0,0 +1,8 @@ +[Unit] +Description=Test for AmbientCapabilities + +[Service] +ExecStart=/bin/sh -x -c 'c=$$(grep "CapAmb:" /proc/self/status); test "$$c" = "CapAmb: 0000000000003000"' +Type=oneshot +User=nfsnobody +AmbientCapabilities=CAP_NET_ADMIN CAP_NET_RAW diff --git a/test/test-execute/exec-group-nfsnobody.service b/test/test-execute/exec-group-nfsnobody.service new file mode 100644 index 0000000000..e02100a869 --- /dev/null +++ b/test/test-execute/exec-group-nfsnobody.service @@ -0,0 +1,7 @@ +[Unit] +Description=Test for Group + +[Service] +ExecStart=/bin/sh -x -c 'test "$$(id -n -g)" = "nfsnobody"' +Type=oneshot +Group=nfsnobody diff --git a/test/test-execute/exec-runtimedirectory-owner-nfsnobody.service b/test/test-execute/exec-runtimedirectory-owner-nfsnobody.service new file mode 100644 index 0000000000..e962af8a4b --- /dev/null +++ b/test/test-execute/exec-runtimedirectory-owner-nfsnobody.service @@ -0,0 +1,9 @@ +[Unit] +Description=Test for RuntimeDirectory owner (must not be the default group of the user if Group is set) + +[Service] +ExecStart=/bin/sh -x -c 'group=$$(stat -c %%G /tmp/test-exec_runtimedirectory-owner); test "$$group" = "nfsnobody"' +Type=oneshot +Group=nfsnobody +User=root +RuntimeDirectory=test-exec_runtimedirectory-owner diff --git a/test/test-execute/exec-systemcallfilter-system-user-nfsnobody.service b/test/test-execute/exec-systemcallfilter-system-user-nfsnobody.service new file mode 100644 index 0000000000..9393e0a998 --- /dev/null +++ b/test/test-execute/exec-systemcallfilter-system-user-nfsnobody.service @@ -0,0 +1,11 @@ +[Unit] +Description=Test for SystemCallFilter in system mode with User set + +[Service] +ExecStart=/bin/echo "Foo bar" +Type=oneshot +User=nfsnobody +SystemCallFilter=~read write open execve ioperm +SystemCallFilter=ioctl +SystemCallFilter=read write open execve +SystemCallFilter=~ioperm diff --git a/test/test-execute/exec-systemcallfilter-system-user.service b/test/test-execute/exec-systemcallfilter-system-user.service new file mode 100644 index 0000000000..462f94133d --- /dev/null +++ b/test/test-execute/exec-systemcallfilter-system-user.service @@ -0,0 +1,11 @@ +[Unit] +Description=Test for SystemCallFilter in system mode with User set + +[Service] +ExecStart=/bin/echo "Foo bar" +Type=oneshot +User=nobody +SystemCallFilter=~read write open execve ioperm +SystemCallFilter=ioctl +SystemCallFilter=read write open execve +SystemCallFilter=~ioperm diff --git a/test/test-execute/exec-user-nfsnobody.service b/test/test-execute/exec-user-nfsnobody.service new file mode 100644 index 0000000000..aafda3aa26 --- /dev/null +++ b/test/test-execute/exec-user-nfsnobody.service @@ -0,0 +1,7 @@ +[Unit] +Description=Test for User + +[Service] +ExecStart=/bin/sh -x -c 'test "$$USER" = "nfsnobody"' +Type=oneshot +User=nfsnobody diff --git a/test/test-functions b/test/test-functions index 92e1ae9f8d..8bbcddab59 100644 --- a/test/test-functions +++ b/test/test-functions @@ -199,9 +199,23 @@ EOF chmod 0755 $_valgrind_wrapper } +create_strace_wrapper() { + local _strace_wrapper=$initdir/$ROOTLIBDIR/systemd-under-strace + ddebug "Create $_strace_wrapper" + cat >$_strace_wrapper <<EOF +#!/bin/bash + +exec strace -D -o /strace.out $ROOTLIBDIR/systemd "\$@" +EOF + chmod 0755 $_strace_wrapper +} + install_fsck() { dracut_install /sbin/fsck* dracut_install -o /bin/fsck* + + # fskc.reiserfs calls reiserfsck. so, install it + dracut_install -o reiserfsck } install_dmevent() { @@ -246,7 +260,13 @@ create_empty_image() { , EOF - mkfs -t "$FSTYPE" -L systemd "${LOOPDEV}p1" + local _label="-L systemd" + # mkfs.reiserfs doesn't know -L. so, use --label instead + [[ "$FSTYPE" == "reiserfs" ]] && _label="--label systemd" + if ! mkfs -t "${FSTYPE}" ${_label} "${LOOPDEV}p1" -q; then + dfatal "Failed to mkfs -t ${FSTYPE}" + exit 1 + fi } check_result_nspawn() { @@ -340,7 +360,7 @@ install_config_files() { echo systemd-testsuite > $initdir/etc/hostname # fstab cat >$initdir/etc/fstab <<EOF -LABEL=systemd / ext3 rw 0 1 +LABEL=systemd / ${FSTYPE} rw 0 1 EOF } diff --git a/test/udev-test.pl b/test/udev-test.pl index b047493f6b..3c8a480d0f 100755 --- a/test/udev-test.pl +++ b/test/udev-test.pl @@ -29,6 +29,7 @@ my $udev_bin_gdb = "gdb --args $udev_bin"; my $udev_bin_strace = "strace -efile $udev_bin"; my $udev_dev = "test/dev"; my $udev_run = "test/run"; +my $udev_tmpfs = "test/tmpfs"; my $udev_rules_dir = "$udev_run/udev/rules.d"; my $udev_rules = "$udev_rules_dir/udev-test.rules"; my $EXIT_TEST_SKIP = 77; @@ -1412,6 +1413,12 @@ sub udev_setup { chown (0, 0, $udev_dev) || die "unable to chown $udev_dev\n"; chmod (0755, $udev_dev) || die "unable to chmod $udev_dev\n"; + system("umount", "$udev_tmpfs"); + system("rm", "-rf", "$udev_tmpfs"); + mkdir($udev_tmpfs) || die "unable to create udev_tmpfs: $udev_tmpfs\n"; + system("mount", "-o", "rw,mode=755,nosuid,noexec,nodev", "-t", "tmpfs", "tmpfs", "$udev_tmpfs") && die "unable to mount tmpfs"; + system("cp", "-r", "test/sys/", "$udev_tmpfs") && die "unable to copy test/sys"; + system("rm", "-rf", "$udev_run"); } @@ -1545,6 +1552,8 @@ print "$error errors occurred\n\n"; # cleanup system("rm", "-rf", "$udev_dev"); system("rm", "-rf", "$udev_run"); +system("umount", "$udev_tmpfs"); +system("rm", "-rf", "$udev_tmpfs"); if ($error > 0) { exit(1); diff --git a/units/ldconfig.service b/units/ldconfig.service index 994edd9908..0910fff054 100644 --- a/units/ldconfig.service +++ b/units/ldconfig.service @@ -10,9 +10,8 @@ Description=Rebuild Dynamic Linker Cache Documentation=man:ldconfig(8) DefaultDependencies=no Conflicts=shutdown.target -After=systemd-remount-fs.service +After=local-fs.target Before=sysinit.target shutdown.target systemd-update-done.service -ConditionNeedsUpdate=|/etc ConditionFileNotEmpty=|!/etc/ld.so.cache [Service] |