Script 'mail_helper' called by obssrc
Hello community,
here is the log from the commit of package shadowsocks-rust for
openSUSE:Factory checked in at 2026-05-27 16:13:55
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/shadowsocks-rust (Old)
and /work/SRC/openSUSE:Factory/.shadowsocks-rust.new.1937 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "shadowsocks-rust"
Wed May 27 16:13:55 2026 rev:20 rq:1354964 version:1.24.0
Changes:
--------
--- /work/SRC/openSUSE:Factory/shadowsocks-rust/shadowsocks-rust.changes
2026-05-05 17:59:09.241160906 +0200
+++
/work/SRC/openSUSE:Factory/.shadowsocks-rust.new.1937/shadowsocks-rust.changes
2026-05-27 16:14:20.462464588 +0200
@@ -1,0 +2,17 @@
+Mon May 18 13:18:23 UTC 2026 - Hillwood Yang <[email protected]>
+
+- Comprehensive systemd service hardening (bnc#1212862 and boo#1263916)
+ * Add CAP_DAC_READ_SEARCH to AmbientCapabilities/CapabilityBoundingSet
+ to allow reading certificates from restricted dynamic paths.
+ * Ensures v2ray-plugin can access Let's Encrypt keys reliably.
+ * Restrict root powers using CapabilityBoundingSet (minimal privileges).
+ * Isolate filesystem via ProtectSystem=full and ProtectHome=true.
+ * Whitelist binary and config access with ReadOnlyPaths.
+ * Disable kernel/device modifications (ProtectKernel*, PrivateDevices).
+ * Introduce SELinux and AppArmor as optional security hardening schemes,
+ and add shadowsocks-libev-selinux and shadowsocks-libev-apparmory
+ subpackages.
+- Integrate shadowsocks-sysuser for proper non-privileged user handling
+ (boo#1264355).
+
+-------------------------------------------------------------------
New:
----
shadowsocks-rust.apparmor
shadowsocks-rust.fc
shadowsocks-rust.te
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ shadowsocks-rust.spec ++++++
--- /var/tmp/diff_new_pack.605ld1/_old 2026-05-27 16:14:23.450587693 +0200
+++ /var/tmp/diff_new_pack.605ld1/_new 2026-05-27 16:14:23.454587857 +0200
@@ -16,6 +16,8 @@
#
+%global selinuxtype targeted
+
Name: shadowsocks-rust
Version: 1.24.0
Release: 0
@@ -29,12 +31,22 @@
Source3: %{name}-client.service
Source4: %{name}-server.service
Source5: %{name}-manager.service
+Source6: %{name}.apparmor
+Source7: %{name}.fc
+Source8: %{name}.te
# PATCH-FIX-UPSTREAM https://github.com/AlephAlpha/build-time/pull/5
Patch0: reproducible.patch
+BuildRequires: apparmor-abstractions
+BuildRequires: apparmor-rpm-macros
BuildRequires: cargo
BuildRequires: cargo-packaging
+BuildRequires: libapparmor-devel
+BuildRequires: selinux-policy-devel
+BuildRequires: selinux-policy-targeted
+BuildRequires: shadowsocks-common-selinux
BuildRequires: systemd-rpm-macros
BuildRequires: pkgconfig(openssl)
+Requires(pre): shadowsocks-sysuser
Requires(pre): shadow
Recommends: shadowsocks-v2ray-plugin
# ExcludeArch: ppc ppc64 ppc64le s390 s390x
@@ -46,6 +58,26 @@
shadowsocks is a lightweight secured SOCKS5 proxy for embedded devices and
low-end boxes.
+%package apparmor
+Summary: Apparmor profile for %{name}
+BuildArch: noarch
+Requires: %{name} = %{version}-%{release}
+Supplements: (shadowsocks-rust and apparmor-abstractions)
+
+%description apparmor
+This package adds the Apparmor profile to %{name}
+
+%package selinux
+Summary: Selinux support for %{name}
+BuildArch: noarch
+Requires: %{name} = %{version}-%{release}
+Requires: selinux-policy-targeted
+Requires: shadowsocks-common-selinux
+Supplements: (shadowsocks-rust and selinux-policy-targeted)
+
+%description selinux
+This package adds SELinux enforcement to %{name}.
+
%prep
%autosetup -p1 -a1 -n %{name}-%{version}
mkdir .cargo
@@ -57,10 +89,21 @@
EOF
%build
+cp %{SOURCE7} shadowsocks_rust.fc
+cp %{SOURCE8} shadowsocks_rust.te
+make -f %{_datadir}/selinux/devel/Makefile shadowsocks_rust.pp
+
cargo auditable build -j16 --offline --release
%install
%cargo_install
+
+install -d %{buildroot}%{_sysconfdir}/apparmor.d
+install -m 0644 %{SOURCE6} %{buildroot}%{_sysconfdir}/apparmor.d/%{name}
+
+install -d %{buildroot}%{_datadir}/selinux/packages/targeted
+install -m 0644 shadowsocks_rust.pp
%{buildroot}%{_datadir}/selinux/packages/targeted/shadowsocks_rust.pp
+
install -d %{buildroot}%{_sysconfdir}/shadowsocks/
install -m 0644 %{SOURCE2} %{buildroot}%{_sysconfdir}/shadowsocks/
@@ -78,18 +121,11 @@
%service_add_pre %{name}-client.service
%service_add_pre %{name}-server.service
%service_add_pre %{name}-manager.service
-getent group shadowsocks >/dev/null || %{_sbindir}/groupadd --system
shadowsocks
-getent passwd shadowsocks >/dev/null || %{_sbindir}/useradd --system -c
"shadowsocks User" \
- -d %{_localstatedir}/shadowsocks -m -g shadowsocks -s
%{_sbindir}/nologin \
- shadowsocks
%post
%service_add_post %{name}-client.service
%service_add_post %{name}-server.service
%service_add_post %{name}-manager.service
-chown root:shadowsocks %{_sysconfdir}/shadowsocks -R
-chmod 750 %{_sysconfdir}/shadowsocks
-chmod 640 %{_sysconfdir}/shadowsocks/*
%preun
%service_del_preun %{name}-client.service
@@ -101,13 +137,44 @@
%service_del_postun %{name}-server.service
%service_del_postun %{name}-manager.service
+%post apparmor
+if [ -d %{_sysconfdir}/apparmor.d ] && [ -d /sys/kernel/security/apparmor ];
then
+ %apparmor_reload %{_sysconfdir}/apparmor.d/%{name}
+fi
+
+%preun apparmor
+if [ $1 -eq 0 ]; then
+ if [ -d %{_sysconfdir}/apparmor.d ] && [ -d /sys/kernel/security/apparmor
]; then
+ %apparmor_reload %{_sysconfdir}/apparmor.d/%{name}
+ fi
+fi
+
+%pre selinux
+%selinux_relabel_pre -s %{selinuxtype}
+
+%post selinux
+%selinux_modules_install -s %{selinuxtype}
%{_datadir}/selinux/packages/%{selinuxtype}/shadowsocks_rust.pp
+%selinux_relabel_post -s %{selinuxtype}
+
+%preun selinux
+if [ $1 -eq 0 ]; then
+ %selinux_modules_uninstall -s %{selinuxtype} shadowsocks_rust
+fi
+
+%posttrans selinux
+%selinux_relabel_post -s %{selinuxtype}
+
%files
%doc README.md
%license LICENSE
%{_bindir}/ss*
%{_sbindir}/rc%{name}-*
%{_unitdir}/%{name}-*.service
-%dir %{_sysconfdir}/shadowsocks
-# %config(noreplace) %attr(660,%{name},root) %{_sysconfdir}/shadowsocks
-%config %{_sysconfdir}/shadowsocks/%{name}.json
+%attr(640,root,shadowsocks) %config(noreplace)
%{_sysconfdir}/shadowsocks/%{name}.json
+
+%files apparmor
+%config %{_sysconfdir}/apparmor.d/%{name}
+
+%files selinux
+%{_datadir}/selinux/packages/targeted/shadowsocks_rust.pp
++++++ shadowsocks-rust-server.service ++++++
--- /var/tmp/diff_new_pack.605ld1/_old 2026-05-27 16:14:24.014610929 +0200
+++ /var/tmp/diff_new_pack.605ld1/_new 2026-05-27 16:14:24.046612248 +0200
@@ -6,6 +6,10 @@
[Service]
# added automatically, for details please see
# https://en.opensuse.org/openSUSE:Security_Features#Systemd_hardening_effort
+AmbientCapabilities=CAP_NET_BIND_SERVICE CAP_DAC_READ_SEARCH
+CapabilityBoundingSet=CAP_NET_BIND_SERVICE CAP_DAC_READ_SEARCH
+PermissionsStartOnly=false
+ReadOnlyPaths=/etc/shadowsocks/ /etc/letsencrypt/ /usr/bin/ssserver
/usr/bin/v2ray-plugin /usr/bin/xray-plugin
ProtectSystem=full
ProtectHome=true
PrivateDevices=true
++++++ shadowsocks-rust.apparmor ++++++
#include <tunables/global>
/usr/bin/ss-server {
# Inherit basic permissions (e.g., loading shared libraries)
#include <abstractions/base>
#include <abstractions/nameservice>
# Allow reading configuration files
/etc/shadowsocks/*.json r,
# Allow reading certificate paths (Recursive read + path traversal/search)
/etc/letsencrypt/** r,
# Network operations
network inet stream,
network inet6 stream,
network inet dgram,
network inet6 dgram,
# Explicitly deny access to sensitive paths
# (Blocked even if CAP_DAC_READ_SEARCH is present)
deny /etc/shadow r,
deny /etc/gshadow r,
deny /root/** r,
deny /home/** r,
# Allow execution of plugins (e.g., v2ray-plugin)
/usr/bin/v2ray-plugin ix,
/usr/bin/xray-plugin ix,
}
(No newline at EOF)
++++++ shadowsocks-rust.fc ++++++
/usr/bin/ssserver -- system_u:object_r:shadowsocks_rust_exec_t:s0
(No newline at EOF)
++++++ shadowsocks-rust.te ++++++
policy_module(shadowsocks_rust, 1.0)
require {
type etc_t;
type cert_t;
type node_t;
# type var_run_t;
type systemd_socket_proxyd_t;
type shadowsocks_config_t;
attribute initrc_domain;
type bin_t;
type shell_exec_t;
type lo_node_t;
type inaddr_any_node_t;
attribute port_type;
type random_device_t;
type sysfs_t;
type cgroup_t;
type sysctl_net_t;
class chr_file { read getattr open };
class unix_dgram_socket { create connect sendto };
class capability { sys_resource };
class file { read open getattr write create unlink entrypoint map execute
ioctl lock };
class fifo_file { getattr read write ioctl };
class dir { search getattr write add_name remove_name read };
class lnk_file { read getattr };
class process { transition sigchld signull };
class tcp_socket { create bind node_bind name_bind listen accept connect
setopt getopt getattr setattr read write ioctl };
class udp_socket { create bind node_bind name_bind getattr setattr read
write connect setopt getopt listen accept };
class unix_stream_socket { connectto };
}
# ===================================================================
# Define shadowsocks-rust SPECIFIC domains
# ===================================================================
type shadowsocks_rust_t;
type shadowsocks_rust_exec_t;
init_daemon_domain(shadowsocks_rust_t, shadowsocks_rust_exec_t)
# ===================================================================
# File and Directory Access Rules
# ===================================================================
allow shadowsocks_rust_t cert_t:dir { search getattr };
allow shadowsocks_rust_t cert_t:file { read open getattr };
allow shadowsocks_rust_t cert_t:lnk_file { read getattr };
allow shadowsocks_rust_t etc_t:dir search;
allow shadowsocks_rust_t shadowsocks_config_t:dir { read search getattr };
allow shadowsocks_rust_t shadowsocks_config_t:file { read open getattr };
# files_pid_filetrans(shadowsocks_rust_t, var_run_t, dir)
# files_pid_filetrans(shadowsocks_rust_t, var_run_t, file)
# allow shadowsocks_rust_t var_run_t:dir { search getattr write add_name
remove_name };
# allow shadowsocks_rust_t var_run_t:file { read open getattr write create
unlink };
# ===================================================================
# System Initializations (Random, Logging, Sysfs)
# ===================================================================
allow shadowsocks_rust_t random_device_t:chr_file { read getattr open };
allow shadowsocks_rust_t self:unix_dgram_socket { create connect sendto };
allow shadowsocks_rust_t sysfs_t:file { read open getattr };
allow shadowsocks_rust_t cgroup_t:dir search;
allow shadowsocks_rust_t sysctl_net_t:dir search;
# ===================================================================
# Network Communication Rules (TCP & UDP)
# ===================================================================
allow shadowsocks_rust_t port_type:tcp_socket { name_bind connect };
allow shadowsocks_rust_t port_type:udp_socket { name_bind };
allow shadowsocks_rust_t { node_t lo_node_t inaddr_any_node_t }:tcp_socket {
node_bind };
allow shadowsocks_rust_t self:tcp_socket { create bind listen accept connect
setopt getopt getattr setattr read write ioctl };
allow shadowsocks_rust_t { node_t lo_node_t inaddr_any_node_t }:udp_socket {
node_bind };
allow shadowsocks_rust_t self:udp_socket { create bind getattr setattr read
write connect setopt getopt listen accept };
# ===================================================================
# Core Kernel Capabilities
# ===================================================================
allow shadowsocks_rust_t self:capability { sys_resource };
# ===================================================================
# Plugin Execution Rules (SIP003 Plugins like v2ray-plugin)
# ===================================================================
allow shadowsocks_rust_t bin_t:dir { search getattr };
allow shadowsocks_rust_t bin_t:lnk_file { read getattr };
allow shadowsocks_rust_t bin_t:file { read open getattr execute
execute_no_trans map };
allow shadowsocks_rust_t shell_exec_t:file { read open getattr execute
execute_no_trans map };
allow shadowsocks_rust_t self:fifo_file { read write getattr ioctl };
# ===================================================================
# DNS Name Resolution
# ===================================================================
sysnet_dns_name_resolve(shadowsocks_rust_t)
(No newline at EOF)