Skip to content
Snippets Groups Projects
Commit 959fd338 authored by Simon McVittie's avatar Simon McVittie
Browse files

wrap: Take out a lock on the container's runtime for the duration


If we upgrade from runtime 0.20191024.0 to 0.20191108.0 while an app
or game is still running under runtime 0.20191024.0, then deleting
the app or game's shared libraries out from under it will probably
break it.

Flatpak solves this problem with a read/write lock on the file
`files/.ref` - for runtimes this is `/usr/.ref` in the container.
Each instance of `flatpak run` takes a read-lock on that file. Any
number of processes can hold a read-lock at the same time.
Before a package-manager-style operation like `flatpak uninstall`
does anything destructive to a runtime, it takes a write-lock, which
only succeeds if there are currently no read- or write-locks.
Depending on the operation, the lock is either taken directly or by
asking bubblewrap to do it.

We'll use the same scheme. Different families of locking APIs interact
unpredictably, so it's important that we use the same locking API as
bubblewrap, namely POSIX byte-range (record) advisory locks via
fcntl F_SETLK. In particular, this means flock(1) and flock(2) are
not going to help us: they use POSIX file-level advisory locks.

One difference between our locking and flatpak's is that we support
runtimes that are not "merged /usr". In this case, we could either
take a lock on files/.ref (/.ref in the container) or on files/usr/.ref
(/usr/.ref in the container). I've chosen to do the former here, so that
it's always files/.ref. It doesn't matter, as long as we're consistent.

(For apps the lock file is `/app/.ref` and for extensions it's
`$mountpoint/.ref`, but pressure-vessel doesn't have an equivalent of
Flatpak apps or extensions yet.)

This version is only a partial solution. We can't use bwrap --lock-file
or bwrap --sync-fd without also using --unshare-pid, which breaks
gameoverlayrenderer.so; so we do the next best thing, by leaking the
lock fd to the bubblewrap process, which will leak it to the game's
main process. This won't work if the game forks background processes,
but it's good enough for a straightforward execve() chain.

Signed-off-by: default avatarSimon McVittie <smcv@collabora.com>
parent 8b531350
No related branches found
No related tags found
No related merge requests found
Loading
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment