Skip to content

Commit

Permalink
I ♥ systemd
Browse files Browse the repository at this point in the history
This commit resolves many long-standing problems:

* Issue #25 (RESTRICTED setting) is resolved. Bots are still not fully
  secure, but now they are more secure that they've even been given
  that RESTRICTED setting is entirely useless
* Issue #52 (predictable filenames) is no longer blocked
* Issue #55 (sandboxable) is probably no longer relevant
* Issue #118 (ramfs for /tmp) now needs an update
* Issue #144 (bots leaving stuff behind) is resolved because every bot
  has its own /tmp
* Issue #183 (source ip issue) possibly has a systemd solution for it
* Issue #197 is tackled a little bit also because now there's a memory
  limit for every bot (3G for now, we can probably make it smaller)
* Issue #238 (e.g. forkbombs) is basically resolved, but needs a bit more work
* Moreover, there's now a watchdog that makes sure that bots come back
  online if something bad happens

Not that all of this wasn't possible without systemd, it's just that
it is so much easier now. Feel free to hate me as much as you want.
  • Loading branch information
AlexDaniel committed Sep 29, 2017
1 parent 3c015b2 commit 845db2e
Show file tree
Hide file tree
Showing 3 changed files with 89 additions and 11 deletions.
28 changes: 17 additions & 11 deletions lib/Whateverable.pm6
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,15 @@ multi method irc-to-me($) {
I cannot recognize this command. See wiki for some examples: ~ self.get-wiki-link
}

multi method irc-all($) {
# TODO https://github.com/zoffixznet/perl6-IRC-Client/issues/50
use NativeCall;
sub sd_notify(int32, str --> int32) is native(systemd) {*};
sd_notify 0, WATCHDOG=1; # this may be called too often, see TODO above
$.NEXT
}


method get-wiki-link { WIKI ~ self.^name }

method get-short-commit($original-commit) { # TODO not an actual solution tbh
Expand Down Expand Up @@ -285,10 +294,13 @@ method get-similar($tag-or-hash, @other?, :$repo=$RAKUDO) {
}

sub run-smth($full-commit-hash, $code, :$backend=rakudo-moar) is export {
my $build-path = { BUILDS-LOCATION}/$backend/$full-commit-hash;
my $archive-path = {ARCHIVES-LOCATION}/$backend/$full-commit-hash.zst;
my $archive-link = {ARCHIVES-LOCATION}/$backend/$full-commit-hash;
my $build-prepath = {BUILDS-LOCATION}/$backend/;
my $build-path = $build-prepath/$full-commit-hash;
my $archive-path = {ARCHIVES-LOCATION}/$backend/$full-commit-hash.zst;
my $archive-link = {ARCHIVES-LOCATION}/$backend/$full-commit-hash;

mkdir $build-prepath; # create all parent directories just in case
# (may be needed for isolated /tmp)
# lock on the destination directory to make
# sure that other bots will not get in our way.
while run(:err(Nil), mkdir, --, $build-path).exitcode ≠ 0 {
Expand All @@ -299,13 +311,7 @@ sub run-smth($full-commit-hash, $code, :$backend=‘rakudo-moar’) is export {
kill getppid, 10; # SIGUSR1
}
say $build-path is locked. Waiting…;
sleep 0.5;
# Uh, wait! Does it mean that at the same time we can use only one
# specific build? Yes, and you will have to wait until another bot
# deletes the directory so that you can extract it back again…
# There are some ways to make it work, but don't bother. Instead,
# we should be doing everything in separate isolated containers (soon),
# so this problem will fade away.
sleep 0.5 # should never happen if setup correctly
}
if $archive-path.IO ~~ :e {
my $proc = run :out, :bin, pzstd, -dqc, --, $archive-path;
Expand All @@ -326,7 +332,7 @@ sub run-snippet($full-commit-hash, $file, :$backend=‘rakudo-moar’, :@args=Em
$path/bin/perl6.IO !~~ :e
?? %(output => Commit exists, but a perl6 executable could not be built for it,
exit-code => -1, signal => -1, time => -1,)
!! get-output $path/bin/perl6, --setting=RESTRICTED, |@args,
!! get-output $path/bin/perl6, |@args,
--, $file, :$stdin, :$timeout, :$ENV
}
}
Expand Down
27 changes: 27 additions & 0 deletions services/whateverable-all.service
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
# Some settings don't work from user systemd, so you have to install
# this file under root. See https://github.com/systemd/systemd/issues/3944

[Unit]
Description=All Whateverable Bots
After=network-online.target
Wants=whateverable@Bisectable.service
Wants=whateverable@Committable.service
Wants=whateverable@Benchable.service
Wants=whateverable@Evalable.service
Wants=whateverable@Statisfiable.service
Wants=whateverable@Unicodable.service
Wants=whateverable@Bloatable.service
Wants=whateverable@Quotable.service
Wants=whateverable@Greppable.service
Wants=whateverable@Coverable.service
Wants=whateverable@Releasable.service
Wants=whateverable@Nativecallable.service
Wants=whateverable@Squashable.service

[Service]
Type=oneshot
ExecStart=/bin/true
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target
45 changes: 45 additions & 0 deletions services/whateverable@.service
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
# Some settings don't work from user systemd, so you have to install
# this file under root. See https://github.com/systemd/systemd/issues/3944

[Unit]
Description=Whateverable bot %i
PartOf=whateverable-all.service

[Service]
Type=simple
User=bisectable
ExecStart=/home/bisectable/.rakudobrew/bin/perl6 /home/bisectable/git/whateverable/bin/%i.p6
Environment=PERL6LIB=/home/bisectable/git/whateverable/lib
#Environment=DEBUGGABLE=1
WorkingDirectory=/home/bisectable/git/whateverable

NoNewPrivileges=yes
ProtectSystem=strict
ProtectHome=read-only
ProtectKernelTunables=yes
ProtectKernelModules=yes
ProtectControlGroups=yes
RestrictRealtime=yes
PrivateTmp=yes
PrivateDevices=yes
PrivateUsers=yes
ReadWritePaths=/home/bisectable/git/whateverable/.precomp
ReadWritePaths=/home/bisectable/git/whateverable/sandbox
ReadWritePaths=/home/bisectable/git/whateverable/data
ReadOnlyPaths=/home/bisectable/git/whateverable/data/builds

MemoryMax=3G
TasksMax=40

Restart=always
RestartSec=2
# WatchdogSec is set approximately to ping timeout
# TODO ... or not. There should be at least one non-ping message in 15 minutes
WatchdogSec=900
# TODO is exec the right option here?
NotifyAccess=exec

# TODO SystemCallFilter

[Install]
# WantedBy=multi-user.target

0 comments on commit 845db2e

Please sign in to comment.