systemd-239-75
Resolves: #2175624,#2176892,#2179309
This commit is contained in:
parent
8a31f7d49d
commit
04f2672d6d
@ -1,4 +1,4 @@
|
|||||||
From 47cc8f7e1d153e576f146d309b4043739997a673 Mon Sep 17 00:00:00 2001
|
From 0491902d0eff9f4480ce873decc5dd29e5e189d7 Mon Sep 17 00:00:00 2001
|
||||||
From: David Tardon <dtardon@redhat.com>
|
From: David Tardon <dtardon@redhat.com>
|
||||||
Date: Mon, 13 Mar 2023 14:22:28 +0100
|
Date: Mon, 13 Mar 2023 14:22:28 +0100
|
||||||
Subject: [PATCH] journald-server: always create state file in signal handler
|
Subject: [PATCH] journald-server: always create state file in signal handler
|
||||||
@ -8,7 +8,7 @@ nothing has really happened.
|
|||||||
|
|
||||||
RHEL-only
|
RHEL-only
|
||||||
|
|
||||||
Resolves: #2174645
|
Resolves: #2176892
|
||||||
---
|
---
|
||||||
src/journal/journald-server.c | 5 +++++
|
src/journal/journald-server.c | 5 +++++
|
||||||
1 file changed, 5 insertions(+)
|
1 file changed, 5 insertions(+)
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
From 7a7b0c4ec7a5595a44d9c70d8270b0724a8b8c45 Mon Sep 17 00:00:00 2001
|
From 62c8e07498c9dd13aa79371fc169bb51652ef3a9 Mon Sep 17 00:00:00 2001
|
||||||
From: David Tardon <dtardon@redhat.com>
|
From: David Tardon <dtardon@redhat.com>
|
||||||
Date: Mon, 13 Mar 2023 14:31:38 +0100
|
Date: Mon, 13 Mar 2023 14:31:38 +0100
|
||||||
Subject: [PATCH] journald-server: move relinquish code into function
|
Subject: [PATCH] journald-server: move relinquish code into function
|
||||||
@ -7,7 +7,7 @@ No functional change, just refactoring.
|
|||||||
|
|
||||||
RHEL-only
|
RHEL-only
|
||||||
|
|
||||||
Related: #2174645
|
Related: #2176892
|
||||||
---
|
---
|
||||||
src/journal/journald-server.c | 23 ++++++++++++++++-------
|
src/journal/journald-server.c | 23 ++++++++++++++++-------
|
||||||
1 file changed, 16 insertions(+), 7 deletions(-)
|
1 file changed, 16 insertions(+), 7 deletions(-)
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
From 980add7d84084a474c6c604c0670743c2d1e624c Mon Sep 17 00:00:00 2001
|
From 05a06e34ac8a38c1cff2a08ba071386141e0b78d Mon Sep 17 00:00:00 2001
|
||||||
From: David Tardon <dtardon@redhat.com>
|
From: David Tardon <dtardon@redhat.com>
|
||||||
Date: Mon, 13 Mar 2023 14:32:20 +0100
|
Date: Mon, 13 Mar 2023 14:32:20 +0100
|
||||||
Subject: [PATCH] journald-server: always touch state file in signal handler
|
Subject: [PATCH] journald-server: always touch state file in signal handler
|
||||||
@ -8,7 +8,7 @@ even if nothing has really happened.
|
|||||||
|
|
||||||
RHEL-only
|
RHEL-only
|
||||||
|
|
||||||
Related: #2174645
|
Related: #2176892
|
||||||
---
|
---
|
||||||
src/journal/journald-server.c | 12 +++++++-----
|
src/journal/journald-server.c | 12 +++++++-----
|
||||||
1 file changed, 7 insertions(+), 5 deletions(-)
|
1 file changed, 7 insertions(+), 5 deletions(-)
|
||||||
|
299
0905-test-make-TEST-35-LOGIN-stable-again.patch
Normal file
299
0905-test-make-TEST-35-LOGIN-stable-again.patch
Normal file
@ -0,0 +1,299 @@
|
|||||||
|
From 96e69cb655c703d5312c4aa44912e6ce90b4f76f Mon Sep 17 00:00:00 2001
|
||||||
|
From: Frantisek Sumsal <fsumsal@redhat.com>
|
||||||
|
Date: Wed, 29 Mar 2023 22:38:55 +0200
|
||||||
|
Subject: [PATCH] test: make TEST-35-LOGIN stable again
|
||||||
|
|
||||||
|
The expect stuff was anything but expected, so let's just backport
|
||||||
|
the upstream test case and tweak it a bit to account for the missing
|
||||||
|
parts in our downstream testing infrastructure.
|
||||||
|
|
||||||
|
Follow-up to 638c2418e7.
|
||||||
|
Related: #2179309
|
||||||
|
rhel-only
|
||||||
|
---
|
||||||
|
test/TEST-35-LOGIN/testsuite.sh | 225 ++++++++++++++++++++++++--------
|
||||||
|
test/test-functions | 2 +-
|
||||||
|
2 files changed, 175 insertions(+), 52 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/test/TEST-35-LOGIN/testsuite.sh b/test/TEST-35-LOGIN/testsuite.sh
|
||||||
|
index e4d72beb74..149b2354a1 100755
|
||||||
|
--- a/test/TEST-35-LOGIN/testsuite.sh
|
||||||
|
+++ b/test/TEST-35-LOGIN/testsuite.sh
|
||||||
|
@@ -3,6 +3,141 @@
|
||||||
|
set -eux
|
||||||
|
set -o pipefail
|
||||||
|
|
||||||
|
+cleanup_test_user() (
|
||||||
|
+ set +ex
|
||||||
|
+
|
||||||
|
+ pkill -u "$(id -u logind-test-user)"
|
||||||
|
+ sleep 1
|
||||||
|
+ pkill -KILL -u "$(id -u logind-test-user)"
|
||||||
|
+ userdel -r logind-test-user
|
||||||
|
+
|
||||||
|
+ return 0
|
||||||
|
+)
|
||||||
|
+
|
||||||
|
+setup_test_user() {
|
||||||
|
+ mkdir -p /var/spool/cron /var/spool/mail /var/run/console
|
||||||
|
+ useradd -m -s /bin/bash logind-test-user
|
||||||
|
+ trap cleanup_test_user EXIT
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+test_enable_debug() {
|
||||||
|
+ mkdir -p /run/systemd/system/systemd-logind.service.d
|
||||||
|
+ cat >/run/systemd/system/systemd-logind.service.d/debug.conf <<EOF
|
||||||
|
+[Service]
|
||||||
|
+Environment=SYSTEMD_LOG_LEVEL=debug
|
||||||
|
+EOF
|
||||||
|
+ systemctl daemon-reload
|
||||||
|
+ systemctl stop systemd-logind.service
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+check_session() (
|
||||||
|
+ set +ex
|
||||||
|
+
|
||||||
|
+ local seat session leader_pid
|
||||||
|
+
|
||||||
|
+ if [[ $(loginctl --no-legend | grep -c "logind-test-user") != 1 ]]; then
|
||||||
|
+ echo "no session or multiple sessions for logind-test-user." >&2
|
||||||
|
+ return 1
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ seat=$(loginctl --no-legend | grep 'logind-test-user *seat' | awk '{ print $4 }')
|
||||||
|
+ if [[ -z "$seat" ]]; then
|
||||||
|
+ echo "no seat found for user logind-test-user" >&2
|
||||||
|
+ return 1
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ session=$(loginctl --no-legend | awk '$3 == "logind-test-user" { print $1 }')
|
||||||
|
+ if [[ -z "$session" ]]; then
|
||||||
|
+ echo "no session found for user logind-test-user" >&2
|
||||||
|
+ return 1
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ if ! loginctl session-status "$session" | grep -q "Unit: session-${session}\.scope"; then
|
||||||
|
+ echo "cannot find scope unit for session $session" >&2
|
||||||
|
+ return 1
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ leader_pid=$(loginctl session-status "$session" | awk '$1 == "Leader:" { print $2 }')
|
||||||
|
+ if [[ -z "$leader_pid" ]]; then
|
||||||
|
+ echo "cannot found leader process for session $session" >&2
|
||||||
|
+ return 1
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ # cgroup v1: "1:name=systemd:/user.slice/..."; unified hierarchy: "0::/user.slice"
|
||||||
|
+ if ! grep -q -E '(name=systemd|^0:):.*session.*scope' /proc/"$leader_pid"/cgroup; then
|
||||||
|
+ echo "FAIL: process $leader_pid is not in the session cgroup" >&2
|
||||||
|
+ cat /proc/self/cgroup
|
||||||
|
+ return 1
|
||||||
|
+ fi
|
||||||
|
+)
|
||||||
|
+
|
||||||
|
+create_session() {
|
||||||
|
+ # login with the test user to start a session
|
||||||
|
+ mkdir -p /run/systemd/system/getty@tty2.service.d
|
||||||
|
+ cat >/run/systemd/system/getty@tty2.service.d/override.conf <<EOF
|
||||||
|
+[Service]
|
||||||
|
+Type=simple
|
||||||
|
+ExecStart=
|
||||||
|
+ExecStart=-/sbin/agetty --autologin logind-test-user --noclear %I $TERM
|
||||||
|
+Restart=no
|
||||||
|
+EOF
|
||||||
|
+ systemctl daemon-reload
|
||||||
|
+
|
||||||
|
+ systemctl restart getty@tty2.service
|
||||||
|
+
|
||||||
|
+ # check session
|
||||||
|
+ for ((i = 0; i < 30; i++)); do
|
||||||
|
+ (( i != 0 )) && sleep 1
|
||||||
|
+ check_session && break
|
||||||
|
+ done
|
||||||
|
+ check_session
|
||||||
|
+ [[ "$(loginctl --no-legend | awk '$3=="logind-test-user" { print $5 }')" == "tty2" ]]
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
+cleanup_session() (
|
||||||
|
+ set +ex
|
||||||
|
+
|
||||||
|
+ local uid s
|
||||||
|
+
|
||||||
|
+ uid=$(id -u logind-test-user)
|
||||||
|
+
|
||||||
|
+ loginctl disable-linger logind-test-user
|
||||||
|
+
|
||||||
|
+ systemctl stop getty@tty2.service
|
||||||
|
+
|
||||||
|
+ for s in $(loginctl --no-legend list-sessions | awk '$3 == "logind-test-user" { print $1 }'); do
|
||||||
|
+ echo "INFO: stopping session $s"
|
||||||
|
+ loginctl terminate-session "$s"
|
||||||
|
+ done
|
||||||
|
+
|
||||||
|
+ loginctl terminate-user logind-test-user
|
||||||
|
+
|
||||||
|
+ if ! timeout 30 bash -c "while loginctl --no-legend | grep -q logind-test-user; do sleep 1; done"; then
|
||||||
|
+ echo "WARNING: session for logind-test-user still active, ignoring."
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ pkill -u "$uid"
|
||||||
|
+ sleep 1
|
||||||
|
+ pkill -KILL -u "$uid"
|
||||||
|
+
|
||||||
|
+ if ! timeout 30 bash -c "while systemctl is-active --quiet user@${uid}.service; do sleep 1; done"; then
|
||||||
|
+ echo "WARNING: user@${uid}.service is still active, ignoring."
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ if ! timeout 30 bash -c "while systemctl is-active --quiet user-runtime-dir@${uid}.service; do sleep 1; done"; then
|
||||||
|
+ echo "WARNING: user-runtime-dir@${uid}.service is still active, ignoring."
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ if ! timeout 30 bash -c "while systemctl is-active --quiet user-${uid}.slice; do sleep 1; done"; then
|
||||||
|
+ echo "WARNING: user-${uid}.slice is still active, ignoring."
|
||||||
|
+ fi
|
||||||
|
+
|
||||||
|
+ rm -rf /run/systemd/system/getty@tty2.service.d
|
||||||
|
+ systemctl daemon-reload
|
||||||
|
+
|
||||||
|
+ return 0
|
||||||
|
+)
|
||||||
|
+
|
||||||
|
setup_idle_action_lock() {
|
||||||
|
useradd testuser ||:
|
||||||
|
|
||||||
|
@@ -19,83 +154,71 @@ EOF
|
||||||
|
Environment=SYSTEMD_LOG_LEVEL=debug
|
||||||
|
EOF
|
||||||
|
|
||||||
|
+ systemd-analyze cat-config --no-pager systemd/logind.conf
|
||||||
|
systemctl restart systemd-logind.service
|
||||||
|
}
|
||||||
|
|
||||||
|
-teardown_idle_action_lock() {(
|
||||||
|
- set +ex
|
||||||
|
+teardown_lock_idle_action() (
|
||||||
|
+ set +eux
|
||||||
|
+
|
||||||
|
rm -f /run/systemd/logind.conf.d/idle-action-lock.conf
|
||||||
|
- rm -f /run/systemd/systemd-logind.service.d/debug.conf
|
||||||
|
- pkill -9 -u "$(id -u testuser)"
|
||||||
|
- userdel -r testuser
|
||||||
|
systemctl restart systemd-logind.service
|
||||||
|
-)}
|
||||||
|
|
||||||
|
-test_lock_idle_action() {
|
||||||
|
- if ! command -v expect >/dev/null ; then
|
||||||
|
- echo >&2 "expect not installed, skiping test ${FUNCNAME[0]}"
|
||||||
|
- return 0
|
||||||
|
- fi
|
||||||
|
+ cleanup_session
|
||||||
|
|
||||||
|
- setup_idle_action_lock
|
||||||
|
- trap teardown_idle_action_lock RETURN
|
||||||
|
+ return 0
|
||||||
|
+)
|
||||||
|
|
||||||
|
- if loginctl --no-legend | awk '{ print $3; }' | sort -u | grep -q testuser ; then
|
||||||
|
- echo >&2 "Session of the \'testuser\' is already present."
|
||||||
|
- return 1
|
||||||
|
+test_lock_idle_action() {
|
||||||
|
+ local ts
|
||||||
|
+
|
||||||
|
+ if [[ ! -c /dev/tty2 ]]; then
|
||||||
|
+ echo "/dev/tty2 does not exist, skipping test ${FUNCNAME[0]}."
|
||||||
|
+ return
|
||||||
|
fi
|
||||||
|
|
||||||
|
- # IdleActionSec is set 1s but the accuracy of associated timer is 30s so we
|
||||||
|
- # need to sleep in worst case for 31s to make sure timer elapsed. We sleep
|
||||||
|
- # here for 35s to accomodate for any possible scheudling delays.
|
||||||
|
- cat > /tmp/test.exp <<EOF
|
||||||
|
-spawn systemd-run -G -t -p PAMName=login -p User=testuser bash
|
||||||
|
-send "sleep 35\r"
|
||||||
|
-send "echo foobar\r"
|
||||||
|
-send "sleep 35\r"
|
||||||
|
-send "exit\r"
|
||||||
|
-interact
|
||||||
|
-wait
|
||||||
|
-EOF
|
||||||
|
+ if loginctl --no-legend | grep -q logind-test-user; then
|
||||||
|
+ echo >&2 "Session of the \'logind-test-user\' is already present."
|
||||||
|
+ exit 1
|
||||||
|
+ fi
|
||||||
|
|
||||||
|
- ts="$(date '+%H:%M:%S')"
|
||||||
|
- busctl --match "type='signal',sender='org.freedesktop.login1',interface='org.freedesktop.login1.Session',member='Lock'" monitor > dbus.log &
|
||||||
|
+ trap teardown_lock_idle_action RETURN
|
||||||
|
|
||||||
|
- expect /tmp/test.exp &
|
||||||
|
+ create_session
|
||||||
|
|
||||||
|
- # Sleep a bit to give expect time to spawn systemd-run before we check for
|
||||||
|
- # the presence of resulting session.
|
||||||
|
- sleep 2
|
||||||
|
- if [ "$(loginctl --no-legend | awk '{ print $3; }' | sort -u | grep -c testuser)" != 1 ] ; then
|
||||||
|
- echo >&2 "\'testuser\' is expected to have exactly one session running."
|
||||||
|
- return 1
|
||||||
|
- fi
|
||||||
|
+ ts="$(date '+%H:%M:%S')"
|
||||||
|
|
||||||
|
- wait %2
|
||||||
|
- sleep 20
|
||||||
|
- kill %1
|
||||||
|
+ mkdir -p /run/systemd/logind.conf.d
|
||||||
|
+ cat >/run/systemd/logind.conf.d/idle-action-lock.conf <<EOF
|
||||||
|
+[Login]
|
||||||
|
+IdleAction=lock
|
||||||
|
+IdleActionSec=1s
|
||||||
|
+EOF
|
||||||
|
+ systemctl restart systemd-logind.service
|
||||||
|
|
||||||
|
- # We slept for 35s , in that interval all sessions should have become idle
|
||||||
|
+ # Wait for 35s, in that interval all sessions should have become idle
|
||||||
|
# and "Lock" signal should have been sent out. Then we wrote to tty to make
|
||||||
|
# session active again and next we slept for another 35s so sessions have
|
||||||
|
# become idle again. 'Lock' signal is sent out for each session, we have at
|
||||||
|
# least one session, so minimum of 2 "Lock" signals must have been sent.
|
||||||
|
- if [ "$(grep -c Member=Lock dbus.log)" -lt 2 ]; then
|
||||||
|
- echo >&2 "Too few 'Lock' D-Bus signal sent, expected at least 2."
|
||||||
|
- return 1
|
||||||
|
- fi
|
||||||
|
+ timeout 35 bash -c "while [[ \"\$(journalctl -b -u systemd-logind.service --since=$ts | grep -c 'Sent message type=signal .* member=Lock')\" -lt 1 ]]; do sleep 1; done"
|
||||||
|
+
|
||||||
|
+ # Wakeup
|
||||||
|
+ touch /dev/tty2
|
||||||
|
+
|
||||||
|
+ # Wait again
|
||||||
|
+ timeout 35 bash -c "while [[ \"\$(journalctl -b -u systemd-logind.service --since=$ts | grep -c 'Sent message type=signal .* member=Lock')\" -lt 2 ]]; do sleep 1; done"
|
||||||
|
|
||||||
|
- journalctl -b -u systemd-logind.service --since="$ts" > logind.log
|
||||||
|
- if [ "$(grep -c 'System idle. Doing lock operation.' logind.log)" -lt 2 ]; then
|
||||||
|
+ if [[ "$(journalctl -b -u systemd-logind.service --since="$ts" | grep -c 'System idle. Doing lock operation.')" -lt 2 ]]; then
|
||||||
|
echo >&2 "System haven't entered idle state at least 2 times."
|
||||||
|
- return 1
|
||||||
|
+ exit 1
|
||||||
|
fi
|
||||||
|
-
|
||||||
|
- rm -f dbus.log logind.log
|
||||||
|
}
|
||||||
|
|
||||||
|
: >/failed
|
||||||
|
|
||||||
|
+setup_test_user
|
||||||
|
+test_enable_debug
|
||||||
|
test_lock_idle_action
|
||||||
|
|
||||||
|
touch /testok
|
||||||
|
diff --git a/test/test-functions b/test/test-functions
|
||||||
|
index 9606a1b085..e5d4d28a5f 100644
|
||||||
|
--- a/test/test-functions
|
||||||
|
+++ b/test/test-functions
|
||||||
|
@@ -23,7 +23,7 @@ fi
|
||||||
|
|
||||||
|
PATH_TO_INIT=$ROOTLIBDIR/systemd
|
||||||
|
|
||||||
|
-BASICTOOLS="test sh bash setsid loadkeys setfont login sulogin gzip sleep echo mount umount cryptsetup date dmsetup modprobe sed cmp tee rm true false chmod chown ln xargs env mktemp mountpoint useradd userdel"
|
||||||
|
+BASICTOOLS="test sh bash setsid loadkeys setfont login sulogin gzip sleep echo mount umount cryptsetup date dmsetup modprobe sed cmp tee rm true false chmod chown ln xargs env mktemp mountpoint useradd userdel timeout"
|
||||||
|
DEBUGTOOLS="df free ls stty cat ps ln ip route dmesg dhclient mkdir cp ping dhclient strace less grep id tty touch du sort hostname find"
|
||||||
|
|
||||||
|
STATEDIR="${BUILD_DIR:-.}/test/$(basename $(dirname $(realpath $0)))"
|
113
0906-pager-set-LESSSECURE-whenver-we-invoke-a-pager.patch
Normal file
113
0906-pager-set-LESSSECURE-whenver-we-invoke-a-pager.patch
Normal file
@ -0,0 +1,113 @@
|
|||||||
|
From c971d99ffc43df89ca4e15cd81f9e44f4139ba91 Mon Sep 17 00:00:00 2001
|
||||||
|
From: Lennart Poettering <lennart@poettering.net>
|
||||||
|
Date: Mon, 31 Aug 2020 19:37:13 +0200
|
||||||
|
Subject: [PATCH] pager: set $LESSSECURE whenver we invoke a pager
|
||||||
|
|
||||||
|
Some extra safety when invoked via "sudo". With this we address a
|
||||||
|
genuine design flaw of sudo, and we shouldn't need to deal with this.
|
||||||
|
But it's still a good idea to disable this surface given how exotic it
|
||||||
|
is.
|
||||||
|
|
||||||
|
Prompted by #5666
|
||||||
|
|
||||||
|
(cherry picked from commit 612ebf6c913dd0e4197c44909cb3157f5c51a2f0)
|
||||||
|
|
||||||
|
Related: #2175624
|
||||||
|
---
|
||||||
|
man/less-variables.xml | 8 ++++++++
|
||||||
|
man/systemctl.xml | 1 +
|
||||||
|
man/systemd.xml | 2 ++
|
||||||
|
src/basic/pager.c | 23 +++++++++++++++++++++--
|
||||||
|
4 files changed, 32 insertions(+), 2 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/man/less-variables.xml b/man/less-variables.xml
|
||||||
|
index a3faa38997..9dad4247da 100644
|
||||||
|
--- a/man/less-variables.xml
|
||||||
|
+++ b/man/less-variables.xml
|
||||||
|
@@ -36,5 +36,13 @@
|
||||||
|
the invoking terminal is determined to be UTF-8 compatible).</para></listitem>
|
||||||
|
</varlistentry>
|
||||||
|
|
||||||
|
+ <varlistentry id='lesssecure'>
|
||||||
|
+ <term><varname>$SYSTEMD_LESSSECURE</varname></term>
|
||||||
|
+
|
||||||
|
+ <listitem><para>Takes a boolean argument. Overrides the <varname>$LESSSECURE</varname> environment
|
||||||
|
+ variable when invoking the pager, which controls the "secure" mode of less (which disables commands
|
||||||
|
+ such as <literal>|</literal> which allow to easily shell out to external command lines). By default
|
||||||
|
+ less secure mode is enabled, with this setting it may be disabled.</para></listitem>
|
||||||
|
+ </varlistentry>
|
||||||
|
</variablelist>
|
||||||
|
</refsect1>
|
||||||
|
diff --git a/man/systemctl.xml b/man/systemctl.xml
|
||||||
|
index a71e6c7c4f..abc386e6fb 100644
|
||||||
|
--- a/man/systemctl.xml
|
||||||
|
+++ b/man/systemctl.xml
|
||||||
|
@@ -2010,6 +2010,7 @@ Jan 12 10:46:45 example.com bluetoothd[8900]: gatt-time-server: Input/output err
|
||||||
|
<xi:include href="less-variables.xml" xpointer="pager"/>
|
||||||
|
<xi:include href="less-variables.xml" xpointer="less"/>
|
||||||
|
<xi:include href="less-variables.xml" xpointer="lesscharset"/>
|
||||||
|
+ <xi:include href="less-variables.xml" xpointer="lesssecure"/>
|
||||||
|
</refsect1>
|
||||||
|
|
||||||
|
<refsect1>
|
||||||
|
diff --git a/man/systemd.xml b/man/systemd.xml
|
||||||
|
index 17ab59beb5..66ae4d841d 100644
|
||||||
|
--- a/man/systemd.xml
|
||||||
|
+++ b/man/systemd.xml
|
||||||
|
@@ -862,6 +862,8 @@
|
||||||
|
</listitem>
|
||||||
|
</varlistentry>
|
||||||
|
|
||||||
|
+ <xi:include href="less-variables.xml" xpointer="lesssecure"/>
|
||||||
|
+
|
||||||
|
<varlistentry>
|
||||||
|
<term><varname>$LISTEN_PID</varname></term>
|
||||||
|
<term><varname>$LISTEN_FDS</varname></term>
|
||||||
|
diff --git a/src/basic/pager.c b/src/basic/pager.c
|
||||||
|
index f241261119..4efb01c483 100644
|
||||||
|
--- a/src/basic/pager.c
|
||||||
|
+++ b/src/basic/pager.c
|
||||||
|
@@ -11,6 +11,7 @@
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
#include "copy.h"
|
||||||
|
+#include "env-util.h"
|
||||||
|
#include "fd-util.h"
|
||||||
|
#include "locale-util.h"
|
||||||
|
#include "log.h"
|
||||||
|
@@ -94,8 +95,7 @@ int pager_open(bool no_pager, bool jump_to_end) {
|
||||||
|
if (setenv("LESS", less_opts, 1) < 0)
|
||||||
|
_exit(EXIT_FAILURE);
|
||||||
|
|
||||||
|
- /* Initialize a good charset for less. This is
|
||||||
|
- * particularly important if we output UTF-8
|
||||||
|
+ /* Initialize a good charset for less. This is particularly important if we output UTF-8
|
||||||
|
* characters. */
|
||||||
|
less_charset = getenv("SYSTEMD_LESSCHARSET");
|
||||||
|
if (!less_charset && is_locale_utf8())
|
||||||
|
@@ -104,6 +104,25 @@ int pager_open(bool no_pager, bool jump_to_end) {
|
||||||
|
setenv("LESSCHARSET", less_charset, 1) < 0)
|
||||||
|
_exit(EXIT_FAILURE);
|
||||||
|
|
||||||
|
+ /* People might invoke us from sudo, don't needlessly allow less to be a way to shell out
|
||||||
|
+ * privileged stuff. */
|
||||||
|
+ r = getenv_bool("SYSTEMD_LESSSECURE");
|
||||||
|
+ if (r == 0) { /* Remove env var if off */
|
||||||
|
+ if (unsetenv("LESSSECURE") < 0) {
|
||||||
|
+ log_error_errno(errno, "Failed to uset environment variable LESSSECURE: %m");
|
||||||
|
+ _exit(EXIT_FAILURE);
|
||||||
|
+ }
|
||||||
|
+ } else {
|
||||||
|
+ /* Set env var otherwise */
|
||||||
|
+ if (r < 0)
|
||||||
|
+ log_warning_errno(r, "Unable to parse $SYSTEMD_LESSSECURE, ignoring: %m");
|
||||||
|
+
|
||||||
|
+ if (setenv("LESSSECURE", "1", 1) < 0) {
|
||||||
|
+ log_error_errno(errno, "Failed to set environment variable LESSSECURE: %m");
|
||||||
|
+ _exit(EXIT_FAILURE);
|
||||||
|
+ }
|
||||||
|
+ }
|
||||||
|
+
|
||||||
|
if (pager) {
|
||||||
|
execlp(pager, pager, NULL);
|
||||||
|
execl("/bin/sh", "sh", "-c", pager, NULL);
|
264
0907-test-login-always-test-sd_pid_get_owner_uid-moderniz.patch
Normal file
264
0907-test-login-always-test-sd_pid_get_owner_uid-moderniz.patch
Normal file
@ -0,0 +1,264 @@
|
|||||||
|
From a45636228c7000aef000e45d9853585e51bfb9ef Mon Sep 17 00:00:00 2001
|
||||||
|
From: =?UTF-8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= <zbyszek@in.waw.pl>
|
||||||
|
Date: Mon, 12 Oct 2020 18:57:32 +0200
|
||||||
|
Subject: [PATCH] test-login: always test sd_pid_get_owner_uid(), modernize
|
||||||
|
|
||||||
|
A long time some function only worked when in a session, and the test
|
||||||
|
didn't execute them when sd_pid_get_session() failed. Let's always call
|
||||||
|
them to increase coverage.
|
||||||
|
|
||||||
|
While at it, let's test for ==0 not >=0 where we don't expect the function
|
||||||
|
to return anything except 0 or error.
|
||||||
|
|
||||||
|
(cherry picked from commit 1b5b507cd2d1d7a2b053151abb548475ad9c5c3b)
|
||||||
|
|
||||||
|
Related: #2175624
|
||||||
|
---
|
||||||
|
src/libsystemd/sd-login/test-login.c | 132 ++++++++++++++-------------
|
||||||
|
1 file changed, 71 insertions(+), 61 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/src/libsystemd/sd-login/test-login.c b/src/libsystemd/sd-login/test-login.c
|
||||||
|
index ccb1905a46..60ef889ec0 100644
|
||||||
|
--- a/src/libsystemd/sd-login/test-login.c
|
||||||
|
+++ b/src/libsystemd/sd-login/test-login.c
|
||||||
|
@@ -8,20 +8,22 @@
|
||||||
|
#include "sd-login.h"
|
||||||
|
|
||||||
|
#include "alloc-util.h"
|
||||||
|
+#include "errno-list.h"
|
||||||
|
#include "fd-util.h"
|
||||||
|
#include "format-util.h"
|
||||||
|
#include "log.h"
|
||||||
|
#include "string-util.h"
|
||||||
|
#include "strv.h"
|
||||||
|
-#include "util.h"
|
||||||
|
+#include "time-util.h"
|
||||||
|
+#include "user-util.h"
|
||||||
|
|
||||||
|
static char* format_uids(char **buf, uid_t* uids, int count) {
|
||||||
|
- int pos = 0, k, inc;
|
||||||
|
+ int pos = 0, inc;
|
||||||
|
size_t size = (DECIMAL_STR_MAX(uid_t) + 1) * count + 1;
|
||||||
|
|
||||||
|
assert_se(*buf = malloc(size));
|
||||||
|
|
||||||
|
- for (k = 0; k < count; k++) {
|
||||||
|
+ for (int k = 0; k < count; k++) {
|
||||||
|
sprintf(*buf + pos, "%s"UID_FMT"%n", k > 0 ? " " : "", uids[k], &inc);
|
||||||
|
pos += inc;
|
||||||
|
}
|
||||||
|
@@ -32,6 +34,10 @@ static char* format_uids(char **buf, uid_t* uids, int count) {
|
||||||
|
return *buf;
|
||||||
|
}
|
||||||
|
|
||||||
|
+static const char *e(int r) {
|
||||||
|
+ return r == 0 ? "OK" : errno_to_name(r);
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
static void test_login(void) {
|
||||||
|
_cleanup_close_pair_ int pair[2] = { -1, -1 };
|
||||||
|
_cleanup_free_ char *pp = NULL, *qq = NULL,
|
||||||
|
@@ -41,65 +47,71 @@ static void test_login(void) {
|
||||||
|
*seat = NULL, *session = NULL,
|
||||||
|
*unit = NULL, *user_unit = NULL, *slice = NULL;
|
||||||
|
int r;
|
||||||
|
- uid_t u, u2;
|
||||||
|
- char *t, **seats, **sessions;
|
||||||
|
+ uid_t u, u2 = UID_INVALID;
|
||||||
|
+ char *t, **seats = NULL, **sessions = NULL;
|
||||||
|
|
||||||
|
r = sd_pid_get_unit(0, &unit);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
- log_info("sd_pid_get_unit(0, …) → \"%s\"", strna(unit));
|
||||||
|
+ log_info("sd_pid_get_unit(0, …) → %s / \"%s\"", e(r), strnull(unit));
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
|
||||||
|
r = sd_pid_get_user_unit(0, &user_unit);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
- log_info("sd_pid_get_user_unit(0, …) → \"%s\"", strna(user_unit));
|
||||||
|
+ log_info("sd_pid_get_user_unit(0, …) → %s / \"%s\"", e(r), strnull(user_unit));
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
|
||||||
|
r = sd_pid_get_slice(0, &slice);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
- log_info("sd_pid_get_slice(0, …) → \"%s\"", strna(slice));
|
||||||
|
+ log_info("sd_pid_get_slice(0, …) → %s / \"%s\"", e(r), strnull(slice));
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
+
|
||||||
|
+ r = sd_pid_get_owner_uid(0, &u2);
|
||||||
|
+ log_info("sd_pid_get_owner_uid(0, …) → %s / "UID_FMT, e(r), u2);
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
|
||||||
|
r = sd_pid_get_session(0, &session);
|
||||||
|
- if (r < 0) {
|
||||||
|
- log_warning_errno(r, "sd_pid_get_session(0, …): %m");
|
||||||
|
- if (r == -ENODATA)
|
||||||
|
- log_info("Seems we are not running in a session, skipping some tests.");
|
||||||
|
- } else {
|
||||||
|
- log_info("sd_pid_get_session(0, …) → \"%s\"", session);
|
||||||
|
-
|
||||||
|
- assert_se(sd_pid_get_owner_uid(0, &u2) == 0);
|
||||||
|
- log_info("sd_pid_get_owner_uid(0, …) → "UID_FMT, u2);
|
||||||
|
-
|
||||||
|
- assert_se(sd_pid_get_cgroup(0, &cgroup) == 0);
|
||||||
|
- log_info("sd_pid_get_cgroup(0, …) → \"%s\"", cgroup);
|
||||||
|
-
|
||||||
|
- r = sd_uid_get_display(u2, &display_session);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
- log_info("sd_uid_get_display("UID_FMT", …) → \"%s\"",
|
||||||
|
- u2, strnull(display_session));
|
||||||
|
-
|
||||||
|
- assert_se(socketpair(AF_UNIX, SOCK_STREAM, 0, pair) == 0);
|
||||||
|
- sd_peer_get_session(pair[0], &pp);
|
||||||
|
- sd_peer_get_session(pair[1], &qq);
|
||||||
|
- assert_se(streq_ptr(pp, qq));
|
||||||
|
-
|
||||||
|
- r = sd_uid_get_sessions(u2, false, &sessions);
|
||||||
|
+ log_info("sd_pid_get_session(0, …) → %s / \"%s\"", e(r), strnull(session));
|
||||||
|
+
|
||||||
|
+ r = sd_pid_get_cgroup(0, &cgroup);
|
||||||
|
+ log_info("sd_pid_get_cgroup(0, …) → %s / \"%s\"", e(r), strnull(cgroup));
|
||||||
|
+ assert_se(r == 0);
|
||||||
|
+
|
||||||
|
+ r = sd_uid_get_display(u2, &display_session);
|
||||||
|
+ log_info("sd_uid_get_display("UID_FMT", …) → %s / \"%s\"", u2, e(r), strnull(display_session));
|
||||||
|
+ if (u2 == UID_INVALID)
|
||||||
|
+ assert_se(r == -EINVAL);
|
||||||
|
+ else
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
+
|
||||||
|
+ assert_se(socketpair(AF_UNIX, SOCK_STREAM, 0, pair) == 0);
|
||||||
|
+ sd_peer_get_session(pair[0], &pp);
|
||||||
|
+ sd_peer_get_session(pair[1], &qq);
|
||||||
|
+ assert_se(streq_ptr(pp, qq));
|
||||||
|
+
|
||||||
|
+ r = sd_uid_get_sessions(u2, false, &sessions);
|
||||||
|
+ assert_se(t = strv_join(sessions, " "));
|
||||||
|
+ log_info("sd_uid_get_sessions("UID_FMT", …) → %s \"%s\"", u2, e(r), t);
|
||||||
|
+ if (u2 == UID_INVALID)
|
||||||
|
+ assert_se(r == -EINVAL);
|
||||||
|
+ else {
|
||||||
|
assert_se(r >= 0);
|
||||||
|
assert_se(r == (int) strv_length(sessions));
|
||||||
|
- assert_se(t = strv_join(sessions, " "));
|
||||||
|
- strv_free(sessions);
|
||||||
|
- log_info("sd_uid_get_sessions("UID_FMT", …) → [%i] \"%s\"", u2, r, t);
|
||||||
|
- free(t);
|
||||||
|
+ }
|
||||||
|
+ sessions = strv_free(sessions);
|
||||||
|
+ free(t);
|
||||||
|
|
||||||
|
- assert_se(r == sd_uid_get_sessions(u2, false, NULL));
|
||||||
|
+ assert_se(r == sd_uid_get_sessions(u2, false, NULL));
|
||||||
|
|
||||||
|
- r = sd_uid_get_seats(u2, false, &seats);
|
||||||
|
+ r = sd_uid_get_seats(u2, false, &seats);
|
||||||
|
+ assert_se(t = strv_join(seats, " "));
|
||||||
|
+ log_info("sd_uid_get_seats("UID_FMT", …) → %s \"%s\"", u2, e(r), t);
|
||||||
|
+ if (u2 == UID_INVALID)
|
||||||
|
+ assert_se(r == -EINVAL);
|
||||||
|
+ else {
|
||||||
|
assert_se(r >= 0);
|
||||||
|
assert_se(r == (int) strv_length(seats));
|
||||||
|
- assert_se(t = strv_join(seats, " "));
|
||||||
|
- strv_free(seats);
|
||||||
|
- log_info("sd_uid_get_seats("UID_FMT", …) → [%i] \"%s\"", u2, r, t);
|
||||||
|
- free(t);
|
||||||
|
-
|
||||||
|
- assert_se(r == sd_uid_get_seats(u2, false, NULL));
|
||||||
|
}
|
||||||
|
+ seats = strv_free(seats);
|
||||||
|
+ free(t);
|
||||||
|
+
|
||||||
|
+ assert_se(r == sd_uid_get_seats(u2, false, NULL));
|
||||||
|
|
||||||
|
if (session) {
|
||||||
|
r = sd_session_is_active(session);
|
||||||
|
@@ -111,7 +123,7 @@ static void test_login(void) {
|
||||||
|
log_info("sd_session_is_remote(\"%s\") → %s", session, yes_no(r));
|
||||||
|
|
||||||
|
r = sd_session_get_state(session, &state);
|
||||||
|
- assert_se(r >= 0);
|
||||||
|
+ assert_se(r == 0);
|
||||||
|
log_info("sd_session_get_state(\"%s\") → \"%s\"", session, state);
|
||||||
|
|
||||||
|
assert_se(sd_session_get_uid(session, &u) >= 0);
|
||||||
|
@@ -125,16 +137,16 @@ static void test_login(void) {
|
||||||
|
log_info("sd_session_get_class(\"%s\") → \"%s\"", session, class);
|
||||||
|
|
||||||
|
r = sd_session_get_display(session, &display);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
log_info("sd_session_get_display(\"%s\") → \"%s\"", session, strna(display));
|
||||||
|
|
||||||
|
r = sd_session_get_remote_user(session, &remote_user);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
log_info("sd_session_get_remote_user(\"%s\") → \"%s\"",
|
||||||
|
session, strna(remote_user));
|
||||||
|
|
||||||
|
r = sd_session_get_remote_host(session, &remote_host);
|
||||||
|
- assert_se(r >= 0 || r == -ENODATA);
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
log_info("sd_session_get_remote_host(\"%s\") → \"%s\"",
|
||||||
|
session, strna(remote_host));
|
||||||
|
|
||||||
|
@@ -160,7 +172,7 @@ static void test_login(void) {
|
||||||
|
assert_se(r == -ENODATA);
|
||||||
|
}
|
||||||
|
|
||||||
|
- assert_se(sd_uid_get_state(u, &state2) >= 0);
|
||||||
|
+ assert_se(sd_uid_get_state(u, &state2) == 0);
|
||||||
|
log_info("sd_uid_get_state("UID_FMT", …) → %s", u, state2);
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -172,11 +184,11 @@ static void test_login(void) {
|
||||||
|
assert_se(sd_uid_is_on_seat(u, 0, seat) > 0);
|
||||||
|
|
||||||
|
r = sd_seat_get_active(seat, &session2, &u2);
|
||||||
|
- assert_se(r >= 0);
|
||||||
|
+ assert_se(r == 0);
|
||||||
|
log_info("sd_seat_get_active(\"%s\", …) → \"%s\", "UID_FMT, seat, session2, u2);
|
||||||
|
|
||||||
|
r = sd_uid_is_on_seat(u, 1, seat);
|
||||||
|
- assert_se(r >= 0);
|
||||||
|
+ assert_se(IN_SET(r, 0, 1));
|
||||||
|
assert_se(!!r == streq(session, session2));
|
||||||
|
|
||||||
|
r = sd_seat_get_sessions(seat, &sessions, &uids, &n);
|
||||||
|
@@ -184,8 +196,8 @@ static void test_login(void) {
|
||||||
|
assert_se(r == (int) strv_length(sessions));
|
||||||
|
assert_se(t = strv_join(sessions, " "));
|
||||||
|
strv_free(sessions);
|
||||||
|
- log_info("sd_seat_get_sessions(\"%s\", …) → %i, \"%s\", [%i] {%s}",
|
||||||
|
- seat, r, t, n, format_uids(&buf, uids, n));
|
||||||
|
+ log_info("sd_seat_get_sessions(\"%s\", …) → %s, \"%s\", [%u] {%s}",
|
||||||
|
+ seat, e(r), t, n, format_uids(&buf, uids, n));
|
||||||
|
free(t);
|
||||||
|
|
||||||
|
assert_se(sd_seat_get_sessions(seat, NULL, NULL, NULL) == r);
|
||||||
|
@@ -203,7 +215,7 @@ static void test_login(void) {
|
||||||
|
|
||||||
|
r = sd_seat_get_active(NULL, &t, NULL);
|
||||||
|
assert_se(IN_SET(r, 0, -ENODATA));
|
||||||
|
- log_info("sd_seat_get_active(NULL, …) (active session on current seat) → %s", strnull(t));
|
||||||
|
+ log_info("sd_seat_get_active(NULL, …) (active session on current seat) → %s / \"%s\"", e(r), strnull(t));
|
||||||
|
free(t);
|
||||||
|
|
||||||
|
r = sd_get_sessions(&sessions);
|
||||||
|
@@ -243,13 +255,11 @@ static void test_login(void) {
|
||||||
|
|
||||||
|
static void test_monitor(void) {
|
||||||
|
sd_login_monitor *m = NULL;
|
||||||
|
- unsigned n;
|
||||||
|
int r;
|
||||||
|
|
||||||
|
- r = sd_login_monitor_new("session", &m);
|
||||||
|
- assert_se(r >= 0);
|
||||||
|
+ assert_se(sd_login_monitor_new("session", &m) == 0);
|
||||||
|
|
||||||
|
- for (n = 0; n < 5; n++) {
|
||||||
|
+ for (unsigned n = 0; n < 5; n++) {
|
||||||
|
struct pollfd pollfd = {};
|
||||||
|
usec_t timeout, nw;
|
||||||
|
|
198
0908-pager-make-pager-secure-when-under-euid-is-changed-o.patch
Normal file
198
0908-pager-make-pager-secure-when-under-euid-is-changed-o.patch
Normal file
@ -0,0 +1,198 @@
|
|||||||
|
From 7955f053c498a70616ac6c4d57c0fd47dfa8e5ac Mon Sep 17 00:00:00 2001
|
||||||
|
From: =?UTF-8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= <zbyszek@in.waw.pl>
|
||||||
|
Date: Wed, 7 Oct 2020 11:15:05 +0200
|
||||||
|
Subject: [PATCH] pager: make pager secure when under euid is changed or
|
||||||
|
explicitly requested
|
||||||
|
|
||||||
|
The variable is renamed to SYSTEMD_PAGERSECURE (because it's not just about
|
||||||
|
less now), and we automatically enable secure mode in certain cases, but not
|
||||||
|
otherwise.
|
||||||
|
|
||||||
|
This approach is more nuanced, but should provide a better experience for
|
||||||
|
users:
|
||||||
|
|
||||||
|
- Previusly we would set LESSSECURE=1 and trust the pager to make use of
|
||||||
|
it. But this has an effect only on less. We need to not start pagers which
|
||||||
|
are insecure when in secure mode. In particular more is like that and is a
|
||||||
|
very popular pager.
|
||||||
|
|
||||||
|
- We don't enable secure mode always, which means that those other pagers can
|
||||||
|
reasonably used.
|
||||||
|
|
||||||
|
- We do the right thing by default, but the user has ultimate control by
|
||||||
|
setting SYSTEMD_PAGERSECURE.
|
||||||
|
|
||||||
|
Fixes #5666.
|
||||||
|
|
||||||
|
v2:
|
||||||
|
- also check $PKEXEC_UID
|
||||||
|
|
||||||
|
v3:
|
||||||
|
- use 'sd_pid_get_owner_uid() != geteuid()' as the condition
|
||||||
|
|
||||||
|
(cherry picked from commit 0a42426d797406b4b01a0d9c13bb759c2629d108)
|
||||||
|
|
||||||
|
Resolves: #2175624
|
||||||
|
---
|
||||||
|
man/less-variables.xml | 28 ++++++++++++++---
|
||||||
|
meson.build | 3 +-
|
||||||
|
src/basic/pager.c | 69 +++++++++++++++++++++++++++---------------
|
||||||
|
3 files changed, 69 insertions(+), 31 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/man/less-variables.xml b/man/less-variables.xml
|
||||||
|
index 9dad4247da..5f3a53c8dd 100644
|
||||||
|
--- a/man/less-variables.xml
|
||||||
|
+++ b/man/less-variables.xml
|
||||||
|
@@ -37,12 +37,30 @@
|
||||||
|
</varlistentry>
|
||||||
|
|
||||||
|
<varlistentry id='lesssecure'>
|
||||||
|
- <term><varname>$SYSTEMD_LESSSECURE</varname></term>
|
||||||
|
+ <term><varname>$SYSTEMD_PAGERSECURE</varname></term>
|
||||||
|
|
||||||
|
- <listitem><para>Takes a boolean argument. Overrides the <varname>$LESSSECURE</varname> environment
|
||||||
|
- variable when invoking the pager, which controls the "secure" mode of less (which disables commands
|
||||||
|
- such as <literal>|</literal> which allow to easily shell out to external command lines). By default
|
||||||
|
- less secure mode is enabled, with this setting it may be disabled.</para></listitem>
|
||||||
|
+ <listitem><para>Takes a boolean argument. When true, the "secure" mode of the pager is enabled; if
|
||||||
|
+ false, disabled. If <varname>$SYSTEMD_PAGERSECURE</varname> is not set at all, secure mode is enabled
|
||||||
|
+ if the effective UID is not the same as the owner of the login session, see <citerefentry
|
||||||
|
+ project='man-pages'><refentrytitle>geteuid</refentrytitle><manvolnum>2</manvolnum></citerefentry> and
|
||||||
|
+ <citerefentry><refentrytitle>sd_pid_get_owner_uid</refentrytitle><manvolnum>3</manvolnum></citerefentry>.
|
||||||
|
+ In secure mode, <option>LESSSECURE=1</option> will be set when invoking the pager, and the pager shall
|
||||||
|
+ disable commands that open or create new files or start new subprocesses. When
|
||||||
|
+ <varname>$SYSTEMD_PAGERSECURE</varname> is not set at all, pagers which are not known to implement
|
||||||
|
+ secure mode will not be used. (Currently only
|
||||||
|
+ <citerefentry><refentrytitle>less</refentrytitle><manvolnum>1</manvolnum></citerefentry> implements
|
||||||
|
+ secure mode.)</para>
|
||||||
|
+
|
||||||
|
+ <para>Note: when commands are invoked with elevated privileges, for example under <citerefentry
|
||||||
|
+ project='man-pages'><refentrytitle>sudo</refentrytitle><manvolnum>8</manvolnum></citerefentry> or
|
||||||
|
+ <citerefentry
|
||||||
|
+ project='die-net'><refentrytitle>pkexec</refentrytitle><manvolnum>1</manvolnum></citerefentry>, care
|
||||||
|
+ must be taken to ensure that unintended interactive features are not enabled. "Secure" mode for the
|
||||||
|
+ pager may be enabled automatically as describe above. Setting <varname>SYSTEMD_PAGERSECURE=0</varname>
|
||||||
|
+ or not removing it from the inherited environment allows the user to invoke arbitrary commands. Note
|
||||||
|
+ that if the <varname>$SYSTEMD_PAGER</varname> or <varname>$PAGER</varname> variables are to be
|
||||||
|
+ honoured, <varname>$SYSTEMD_PAGERSECURE</varname> must be set too. It might be reasonable to completly
|
||||||
|
+ disable the pager using <option>--no-pager</option> instead.</para></listitem>
|
||||||
|
</varlistentry>
|
||||||
|
</variablelist>
|
||||||
|
</refsect1>
|
||||||
|
diff --git a/meson.build b/meson.build
|
||||||
|
index 673800a1a7..d986dd24ac 100644
|
||||||
|
--- a/meson.build
|
||||||
|
+++ b/meson.build
|
||||||
|
@@ -1467,7 +1467,8 @@ test_dlopen = executable(
|
||||||
|
'test-dlopen',
|
||||||
|
test_dlopen_c,
|
||||||
|
include_directories : includes,
|
||||||
|
- link_with : [libbasic],
|
||||||
|
+ link_with : [libsystemd_static,
|
||||||
|
+ libbasic],
|
||||||
|
dependencies : [libdl])
|
||||||
|
|
||||||
|
foreach tuple : [['myhostname', 'ENABLE_NSS_MYHOSTNAME'],
|
||||||
|
diff --git a/src/basic/pager.c b/src/basic/pager.c
|
||||||
|
index 4efb01c483..c7e101235d 100644
|
||||||
|
--- a/src/basic/pager.c
|
||||||
|
+++ b/src/basic/pager.c
|
||||||
|
@@ -10,6 +10,8 @@
|
||||||
|
#include <sys/prctl.h>
|
||||||
|
#include <unistd.h>
|
||||||
|
|
||||||
|
+#include "sd-login.h"
|
||||||
|
+
|
||||||
|
#include "copy.h"
|
||||||
|
#include "env-util.h"
|
||||||
|
#include "fd-util.h"
|
||||||
|
@@ -79,7 +81,7 @@ int pager_open(bool no_pager, bool jump_to_end) {
|
||||||
|
if (r < 0)
|
||||||
|
return r;
|
||||||
|
if (r == 0) {
|
||||||
|
- const char* less_opts, *less_charset;
|
||||||
|
+ const char* less_opts, *less_charset, *exe;
|
||||||
|
|
||||||
|
/* In the child start the pager */
|
||||||
|
|
||||||
|
@@ -105,39 +107,56 @@ int pager_open(bool no_pager, bool jump_to_end) {
|
||||||
|
_exit(EXIT_FAILURE);
|
||||||
|
|
||||||
|
/* People might invoke us from sudo, don't needlessly allow less to be a way to shell out
|
||||||
|
- * privileged stuff. */
|
||||||
|
- r = getenv_bool("SYSTEMD_LESSSECURE");
|
||||||
|
- if (r == 0) { /* Remove env var if off */
|
||||||
|
- if (unsetenv("LESSSECURE") < 0) {
|
||||||
|
- log_error_errno(errno, "Failed to uset environment variable LESSSECURE: %m");
|
||||||
|
- _exit(EXIT_FAILURE);
|
||||||
|
- }
|
||||||
|
- } else {
|
||||||
|
- /* Set env var otherwise */
|
||||||
|
+ * privileged stuff. If the user set $SYSTEMD_PAGERSECURE, trust their configuration of the
|
||||||
|
+ * pager. If they didn't, use secure mode when under euid is changed. If $SYSTEMD_PAGERSECURE
|
||||||
|
+ * wasn't explicitly set, and we autodetect the need for secure mode, only use the pager we
|
||||||
|
+ * know to be good. */
|
||||||
|
+ int use_secure_mode = getenv_bool("SYSTEMD_PAGERSECURE");
|
||||||
|
+ bool trust_pager = use_secure_mode >= 0;
|
||||||
|
+ if (use_secure_mode == -ENXIO) {
|
||||||
|
+ uid_t uid;
|
||||||
|
+
|
||||||
|
+ r = sd_pid_get_owner_uid(0, &uid);
|
||||||
|
if (r < 0)
|
||||||
|
- log_warning_errno(r, "Unable to parse $SYSTEMD_LESSSECURE, ignoring: %m");
|
||||||
|
+ log_debug_errno(r, "sd_pid_get_owner_uid() failed, enabling pager secure mode: %m");
|
||||||
|
+
|
||||||
|
+ use_secure_mode = r < 0 || uid != geteuid();
|
||||||
|
+
|
||||||
|
+ } else if (use_secure_mode < 0) {
|
||||||
|
+ log_warning_errno(use_secure_mode, "Unable to parse $SYSTEMD_PAGERSECURE, assuming true: %m");
|
||||||
|
+ use_secure_mode = true;
|
||||||
|
+ }
|
||||||
|
|
||||||
|
- if (setenv("LESSSECURE", "1", 1) < 0) {
|
||||||
|
- log_error_errno(errno, "Failed to set environment variable LESSSECURE: %m");
|
||||||
|
- _exit(EXIT_FAILURE);
|
||||||
|
- }
|
||||||
|
+ /* We generally always set variables used by less, even if we end up using a different pager.
|
||||||
|
+ * They shouldn't hurt in any case, and ideally other pagers would look at them too. */
|
||||||
|
+ if (use_secure_mode)
|
||||||
|
+ r = setenv("LESSSECURE", "1", 1);
|
||||||
|
+ else
|
||||||
|
+ r = unsetenv("LESSSECURE");
|
||||||
|
+ if (r < 0) {
|
||||||
|
+ log_error_errno(errno, "Failed to adjust environment variable LESSSECURE: %m");
|
||||||
|
+ _exit(EXIT_FAILURE);
|
||||||
|
}
|
||||||
|
|
||||||
|
- if (pager) {
|
||||||
|
+ if (trust_pager && pager) { /* The pager config might be set globally, and we cannot
|
||||||
|
+ * know if the user adjusted it to be appropriate for the
|
||||||
|
+ * secure mode. Thus, start the pager specified through
|
||||||
|
+ * envvars only when $SYSTEMD_PAGERSECURE was explicitly set
|
||||||
|
+ * as well. */
|
||||||
|
execlp(pager, pager, NULL);
|
||||||
|
execl("/bin/sh", "sh", "-c", pager, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
- /* Debian's alternatives command for pagers is
|
||||||
|
- * called 'pager'. Note that we do not call
|
||||||
|
- * sensible-pagers here, since that is just a
|
||||||
|
- * shell script that implements a logic that
|
||||||
|
- * is similar to this one anyway, but is
|
||||||
|
- * Debian-specific. */
|
||||||
|
- execlp("pager", "pager", NULL);
|
||||||
|
+ /* Debian's alternatives command for pagers is called 'pager'. Note that we do not call
|
||||||
|
+ * sensible-pagers here, since that is just a shell script that implements a logic that is
|
||||||
|
+ * similar to this one anyway, but is Debian-specific. */
|
||||||
|
+ FOREACH_STRING(exe, "pager", "less", "more") {
|
||||||
|
+ /* Only less implements secure mode right now. */
|
||||||
|
+ if (use_secure_mode && !streq(exe, "less"))
|
||||||
|
+ continue;
|
||||||
|
|
||||||
|
- execlp("less", "less", NULL);
|
||||||
|
- execlp("more", "more", NULL);
|
||||||
|
+ execlp(exe, exe, NULL);
|
||||||
|
+ }
|
||||||
|
|
||||||
|
pager_fallback();
|
||||||
|
/* not reached */
|
@ -0,0 +1,49 @@
|
|||||||
|
From c4c9126b1d64fbe77ef1a74b464646711ced8f83 Mon Sep 17 00:00:00 2001
|
||||||
|
From: Jan Macku <jamacku@redhat.com>
|
||||||
|
Date: Thu, 30 Mar 2023 17:16:44 +0200
|
||||||
|
Subject: [PATCH] ci: trigger differential-shellcheck workflow on push
|
||||||
|
|
||||||
|
Fixes: redhat-plumbers-in-action/differential-shellcheck#215
|
||||||
|
|
||||||
|
rhel-only
|
||||||
|
|
||||||
|
Related: #2179309
|
||||||
|
---
|
||||||
|
.github/workflows/differential-shellcheck.yml | 9 ++++++---
|
||||||
|
1 file changed, 6 insertions(+), 3 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/.github/workflows/differential-shellcheck.yml b/.github/workflows/differential-shellcheck.yml
|
||||||
|
index 4399f0bc64..19634c07b3 100644
|
||||||
|
--- a/.github/workflows/differential-shellcheck.yml
|
||||||
|
+++ b/.github/workflows/differential-shellcheck.yml
|
||||||
|
@@ -3,9 +3,13 @@
|
||||||
|
|
||||||
|
name: Differential ShellCheck
|
||||||
|
on:
|
||||||
|
+ push:
|
||||||
|
+ branches:
|
||||||
|
+ - main
|
||||||
|
+ - rhel-8.*.0
|
||||||
|
pull_request:
|
||||||
|
branches:
|
||||||
|
- - master
|
||||||
|
+ - main
|
||||||
|
- rhel-8.*.0
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
@@ -18,7 +22,6 @@ jobs:
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
security-events: write
|
||||||
|
- pull-requests: write
|
||||||
|
|
||||||
|
steps:
|
||||||
|
- name: Repository checkout
|
||||||
|
@@ -27,6 +30,6 @@ jobs:
|
||||||
|
fetch-depth: 0
|
||||||
|
|
||||||
|
- name: Differential ShellCheck
|
||||||
|
- uses: redhat-plumbers-in-action/differential-shellcheck@v3
|
||||||
|
+ uses: redhat-plumbers-in-action/differential-shellcheck@v4
|
||||||
|
with:
|
||||||
|
token: ${{ secrets.GITHUB_TOKEN }}
|
34
0910-ci-codeql-master-main.patch
Normal file
34
0910-ci-codeql-master-main.patch
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
From 5e5c1425db0982c9d5e5d51e164895aa780f76b2 Mon Sep 17 00:00:00 2001
|
||||||
|
From: Jan Macku <jamacku@redhat.com>
|
||||||
|
Date: Thu, 30 Mar 2023 17:18:17 +0200
|
||||||
|
Subject: [PATCH] ci: codeql `master` -> `main`
|
||||||
|
|
||||||
|
rhel-only
|
||||||
|
|
||||||
|
Related: #2179309
|
||||||
|
---
|
||||||
|
.github/workflows/codeql.yml | 4 ++--
|
||||||
|
1 file changed, 2 insertions(+), 2 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/.github/workflows/codeql.yml b/.github/workflows/codeql.yml
|
||||||
|
index c5426d5686..cc4fcf4754 100644
|
||||||
|
--- a/.github/workflows/codeql.yml
|
||||||
|
+++ b/.github/workflows/codeql.yml
|
||||||
|
@@ -7,7 +7,7 @@ name: "CodeQL"
|
||||||
|
on:
|
||||||
|
pull_request:
|
||||||
|
branches:
|
||||||
|
- - master
|
||||||
|
+ - main
|
||||||
|
- rhel-*
|
||||||
|
paths:
|
||||||
|
- '**/meson.build'
|
||||||
|
@@ -17,7 +17,7 @@ on:
|
||||||
|
- 'tools/**'
|
||||||
|
push:
|
||||||
|
branches:
|
||||||
|
- - master
|
||||||
|
+ - main
|
||||||
|
- rhel-*
|
||||||
|
|
||||||
|
permissions:
|
@ -0,0 +1,30 @@
|
|||||||
|
From d9e2735b88513e3b3af9ab468f4d2ba0f6bec64d Mon Sep 17 00:00:00 2001
|
||||||
|
From: Dan Streetman <ddstreet@canonical.com>
|
||||||
|
Date: Fri, 23 Oct 2020 15:50:28 -0400
|
||||||
|
Subject: [PATCH] test: ignore ENOMEDIUM error from sd_pid_get_cgroup()
|
||||||
|
|
||||||
|
Ubuntu builds on the Launchpad infrastructure run inside a chroot that does
|
||||||
|
not have the sysfs cgroup dirs mounted, so this call will return ENOMEDIUM
|
||||||
|
from cg_unified_cached() during the build-time testing, for example when
|
||||||
|
building the package in a Launchpad PPA.
|
||||||
|
|
||||||
|
(cherry picked from commit 352ab9d74049b4ac694fdba1a6e67339f12ded93)
|
||||||
|
|
||||||
|
Resolves: #2175622
|
||||||
|
---
|
||||||
|
src/libsystemd/sd-login/test-login.c | 2 +-
|
||||||
|
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||||
|
|
||||||
|
diff --git a/src/libsystemd/sd-login/test-login.c b/src/libsystemd/sd-login/test-login.c
|
||||||
|
index 60ef889ec0..d24a04ccc8 100644
|
||||||
|
--- a/src/libsystemd/sd-login/test-login.c
|
||||||
|
+++ b/src/libsystemd/sd-login/test-login.c
|
||||||
|
@@ -71,7 +71,7 @@ static void test_login(void) {
|
||||||
|
|
||||||
|
r = sd_pid_get_cgroup(0, &cgroup);
|
||||||
|
log_info("sd_pid_get_cgroup(0, …) → %s / \"%s\"", e(r), strnull(cgroup));
|
||||||
|
- assert_se(r == 0);
|
||||||
|
+ assert_se(IN_SET(r, 0, -ENOMEDIUM));
|
||||||
|
|
||||||
|
r = sd_uid_get_display(u2, &display_session);
|
||||||
|
log_info("sd_uid_get_display("UID_FMT", …) → %s / \"%s\"", u2, e(r), strnull(display_session));
|
21
systemd.spec
21
systemd.spec
@ -13,7 +13,7 @@
|
|||||||
Name: systemd
|
Name: systemd
|
||||||
Url: http://www.freedesktop.org/wiki/Software/systemd
|
Url: http://www.freedesktop.org/wiki/Software/systemd
|
||||||
Version: 239
|
Version: 239
|
||||||
Release: 74%{?dist}
|
Release: 75%{?dist}
|
||||||
# For a breakdown of the licensing, see README
|
# For a breakdown of the licensing, see README
|
||||||
License: LGPLv2+ and MIT and GPLv2+
|
License: LGPLv2+ and MIT and GPLv2+
|
||||||
Summary: System and Service Manager
|
Summary: System and Service Manager
|
||||||
@ -954,6 +954,13 @@ Patch0901: 0901-man-document-the-new-_LINE_BREAK-type.patch
|
|||||||
Patch0902: 0902-journald-server-always-create-state-file-in-signal-h.patch
|
Patch0902: 0902-journald-server-always-create-state-file-in-signal-h.patch
|
||||||
Patch0903: 0903-journald-server-move-relinquish-code-into-function.patch
|
Patch0903: 0903-journald-server-move-relinquish-code-into-function.patch
|
||||||
Patch0904: 0904-journald-server-always-touch-state-file-in-signal-ha.patch
|
Patch0904: 0904-journald-server-always-touch-state-file-in-signal-ha.patch
|
||||||
|
Patch0905: 0905-test-make-TEST-35-LOGIN-stable-again.patch
|
||||||
|
Patch0906: 0906-pager-set-LESSSECURE-whenver-we-invoke-a-pager.patch
|
||||||
|
Patch0907: 0907-test-login-always-test-sd_pid_get_owner_uid-moderniz.patch
|
||||||
|
Patch0908: 0908-pager-make-pager-secure-when-under-euid-is-changed-o.patch
|
||||||
|
Patch0909: 0909-ci-trigger-differential-shellcheck-workflow-on-push.patch
|
||||||
|
Patch0910: 0910-ci-codeql-master-main.patch
|
||||||
|
Patch0911: 0911-test-ignore-ENOMEDIUM-error-from-sd_pid_get_cgroup.patch
|
||||||
|
|
||||||
%ifarch %{ix86} x86_64 aarch64
|
%ifarch %{ix86} x86_64 aarch64
|
||||||
%global have_gnu_efi 1
|
%global have_gnu_efi 1
|
||||||
@ -1584,6 +1591,18 @@ fi
|
|||||||
%files tests -f .file-list-tests
|
%files tests -f .file-list-tests
|
||||||
|
|
||||||
%changelog
|
%changelog
|
||||||
|
* Tue Apr 18 2023 systemd maintenance team <systemd-maint@redhat.com> - 239-75
|
||||||
|
- journald-server: always create state file in signal handler (#2176892)
|
||||||
|
- journald-server: move relinquish code into function (#2176892)
|
||||||
|
- journald-server: always touch state file in signal handler (#2176892)
|
||||||
|
- test: make TEST-35-LOGIN stable again (#2179309)
|
||||||
|
- pager: set $LESSSECURE whenver we invoke a pager (#2175624)
|
||||||
|
- test-login: always test sd_pid_get_owner_uid(), modernize (#2175624)
|
||||||
|
- pager: make pager secure when under euid is changed or explicitly requested (#2175624)
|
||||||
|
- ci: trigger differential-shellcheck workflow on push (#2179309)
|
||||||
|
- ci: codeql `master` -> `main` (#2179309)
|
||||||
|
- test: ignore ENOMEDIUM error from sd_pid_get_cgroup() (#2175622)
|
||||||
|
|
||||||
* Tue Mar 14 2023 systemd maintenance team <systemd-maint@redhat.com> - 239-74
|
* Tue Mar 14 2023 systemd maintenance team <systemd-maint@redhat.com> - 239-74
|
||||||
- journald-server: always create state file in signal handler (#2174645)
|
- journald-server: always create state file in signal handler (#2174645)
|
||||||
- journald-server: move relinquish code into function (#2174645)
|
- journald-server: move relinquish code into function (#2174645)
|
||||||
|
Loading…
Reference in New Issue
Block a user