Skip to content

Commit 826b686

Browse files
BrainDamageBrainDamage
authored andcommitted
hardened and made more reliable monitor.service file:
since the service depends on bluetooth daemon, start after it ( After= ) since the daemon fails to work properly without bluetooth, don't start it if blueetooth fails ( Requires= ) shut down the service when bluetooth fails ( BindsTo= ) since the daemon isn't necessary for networking, don't install it network target set restart mode on-failure so that if the user accidentally sets a one-shot setting manually in the service, it doesn't keep re-launching it don't fork the process in the background so that systemd can track the pids of all the programs spawned and kill them if they hang to ensure a proper shutdown split re-writable file with environment to a separate optional file $service_config_path which equals to "/etc/default/monitor", the daemon file shouldn't re-write it's own service file for both security and bug prevention since the daemon runs with ultimate priviledges and it's networked, removing the unnecessary ones can prevent system disruption in the case of a bug or a flyby scripted attack: LockPersonality ensures kenel personality(2) is enforced NoNewPrivileges fixes process privileges as the one set in the srvice PrivateMounts makes any mount point created by the service private to the service itself ProtectClock prevents the system clock to be altered by the service ProtectControlGroups prevents the system to access the kernel control groups ( and override the security settings ) ProteectKernelLogs prevents the access to the kernel logs ProtectKernelModules prevents load/unload kernel modules; bluetooth modules will be loadeed as necessary anyway from the bluetooth.service ProtectKernelTunables denies accceess to the kernel runtime config ProtectHostname prevents hostname changes from the service ProtectHome prevents writing files to the home dir of the user ProtectProc=invisible makes the service be able to see only its own process tree and no further ProtectSystem=strict makes the whole filesystem read-only except for the paths specified in ReadWritePaths RestrictNamespaces denies altering the process namespace, useful to prevent bypassing protections RestrictAddressFamilies limits the types of sockets that can be read/written by the procss RestrictSUIDSGID prevents setting SUID and GID bits on files RestrictRealtime prevents acquiring realtime scheduling priority SystemCallArchitectures ensures that only native binaries are used ( eg only 64 bit in a mixed 32-64 bit environment; 32 bit ISA is often full of security pitholes ) SystemCallFilter=~@mount denies access to the mount functionality to prevent bypassing most of the security settings ReadWritePaths=/sys/class/bluetooth allows raw access to the bluetoot devices ReadWritePaths=$base_directory allows the service to overwrite itself / its config ( dangerous, but fixing it is not in the scope of this patch ) ReadWritePaths=$service_config_path allows the sevice to overwrite the execution args of the daemon daemon-reload is not necessary to reload the environment file, so it's only executed for service installation all the features used are documented in systemd.exec(5) systemd.unit(5) systemd.service(5)
1 parent ec0496b commit 826b686

File tree

1 file changed

+46
-13
lines changed

1 file changed

+46
-13
lines changed

support/init

Lines changed: 46 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818

1919
#FIND DEPENDENCY PATHS, ELSE MANUALLY SET
2020
service_path="/etc/systemd/system/monitor.service"
21+
service_config_path="/etc/default/monitor"
2122
mosquitto_pub_path=$(which mosquitto_pub)
2223
mosquitto_sub_path=$(which mosquitto_sub)
2324
hcidump_path=$(which hcidump)
@@ -203,14 +204,11 @@ fi
203204
#----------------------------------------------------------------------------------------
204205
# CHECK MONITOR.SERVICE (IF APPLICABLE)
205206
#
206-
# CREDITS & CONTRIBUTIONS: x99percent
207+
# CREDITS & CONTRIBUTIONS: x99percent, BrainDamage
207208
# ----------------------------------------------------------------------------------------
208209

209-
#FILTER THE ARGV FROM THE PARENT SCRIPT TO REMOVE ONE-TIME USE VARIABLES
210-
FILTERED_ARGS=$(printf '%s\n' "$(IFS=' '; echo "${RUNTIME_ARGS[*]}")" | sed 's/ \?-d//gi;s/ \?-V//gi;s/ \?-F//gi;s/ \?-u//gi;s/&//g;s/ */ /gi')
211-
212-
#CHECK FOR CORRECT SERVICE;
213-
if [ "$should_install" == "y" ] || [ "$PREF_UPDATE_SERVICE" == true ] ; then
210+
#CHECK FOR CORRECT SERVICE;
211+
if [ "$should_install" == "y" ]; then
214212
#REMOVE ALL INSTANCES
215213
if [ -f "$service_path" ]; then
216214
rm "$service_path" 2>&1 >/dev/null
@@ -222,26 +220,61 @@ if [ "$should_install" == "y" ] || [ "$PREF_UPDATE_SERVICE" == true ] ; then
222220
printf "%s\n" "[Unit]
223221
Description=Monitor Service
224222
After=network.target
223+
After=bluetooth.service
224+
BindsTo=bluetooth.service
225+
Requires=bluetooth.service
225226
226227
[Service]
227228
User=root
228-
ExecStart=/bin/bash $base_directory/$(basename $0) $FILTERED_ARGS &
229+
ExecStart=/bin/bash $base_directory/$(basename $0) \${MONITOR_ARGS}
229230
WorkingDirectory=$base_directory
230-
Restart=always
231+
EnvironmentFile=-$service_config_path
232+
Restart=on-failure
231233
RestartSec=10
232234
233-
[Install]
234-
WantedBy=multi-user.target network.target" > "$service_path"
235+
LockPersonality=True
236+
NoNewPrivileges=True
237+
PrivateMounts=True
238+
ProtectClock=True
239+
ProtectControlGroups=True
240+
ProtectKernelLogs=True
241+
ProtectKernelModules=True
242+
ProtectKernelTunables=True
243+
ProtectHostname=True
244+
ProtectHome=True
245+
ProtectProc=invisible
246+
ProtectSystem=strict
247+
RestrictNamespaces=True
248+
RestrictAddressFamilies=AF_UNIX AF_INET AF_INET6 AF_BLUETOOTH
249+
RestrictSUIDSGID=True
250+
RestrictRealtime=True
251+
SystemCallArchitectures=native
252+
SystemCallFilter=~@mount
253+
254+
ReadWritePaths=/sys/class/bluetooth
255+
ReadWritePaths=$base_directory
256+
ReadWritePaths=$service_config_path
235257
236-
#PRINT RESULTS
237-
[ "$PREF_UPDATE_SERVICE" == true ] && printf "%s\n" "> monitor.service updated with arguments: $FILTERED_ARGS"
258+
[Install]
259+
WantedBy=multi-user.target" > "$service_path"
238260

239261
sleep 3
240262

241263
#RELOAD DAEMON AND ENABLE SERVICE
242264
systemctl daemon-reload
243265
systemctl enable monitor.service
244-
fi
266+
fi
267+
268+
#FILTER THE ARGV FROM THE PARENT SCRIPT TO REMOVE ONE-TIME USE VARIABLES
269+
FILTERED_ARGS=$(printf '%s\n' "$(IFS=' '; echo "${RUNTIME_ARGS[*]}")" | sed 's/ \?-d//gi;s/ \?-V//gi;s/ \?-F//gi;s/ \?-u//gi;s/&//g;s/ */ /gi')
270+
271+
if [ "$should_install" == "y" ] || [ "$PREF_UPDATE_SERVICE" == true ]; then
272+
printf "%s\n" "MONITOR_ARGS=$FILTERED_ARGS" > "$service_path"
273+
274+
#PRINT RESULTS
275+
[ "$PREF_UPDATE_SERVICE" == true ] && printf "%s\n" "> monitor.service updated with arguments: $FILTERED_ARGS"
276+
fi
277+
245278

246279
#----------------------------------------------------------------------------------------
247280
# BEFORE WE ECHO PREFERENCES, EXIT IF WE NEED TO

0 commit comments

Comments
 (0)