Skip to content

[Question] Preload library enhancements for performance and security #431

@nephros

Description

@nephros

SailfishOS VERSION N/A

HARDWAREN/A

PATCHMANAGER VERSION 3.0 and later

QUESTION

Executive summary: Are there any benefits to expanding the "path blacklist" in Patchmanager's preload library?

So the current mode of operation of Patchmanager is something like this:

  1. A Patch is "activated"
  2. For each file the patch manipulates, a copy of the original file is put into a cache dir in /tmp, and the changes are applied there instead of on the original file.
  3. A patched application is launched.
  4. Through library preloading, the libpreloadpatchmanager.so library is injected into the launching binary.
  5. The library:
    1. intercepts calls to open(), analyzes which files the call was meant to open
    2. asks the patchmanager daemon (via socket) whether a patched version exists
    3. if yes, redirects the open call to that file instead of the original
    4. otherwise opens the original file

Now, this is done for all binaries launched, and it's done for all calls to open().

This of course has some impact on performance, (and raises security concerns, but lets put that aside for the moment).

What we also have is some safeguards built into the library, lists of paths and file names where it will not intercept calls:

I believe these can be expanded to improve both security and performance.

I would propose expanding the lists to include these categories of paths:

  1. firmware and related paths in / (such as /odm /vendor /apex and some others), patches have no business messing with those. Most of them are mounted read-only, but I think it would be possible to make them "writable" by constructing a clever patch.
  2. paths to files which are very commonly opened. This means things like:
  • /etc/ld.so.preload
  • /etc/ld.so.cache
  • /etc/localtime
  • /usr/lib/locale/locale-archive
  • /usr/share/locale/locale.alias
  • /usr/lib/libselinux.so.1
  • /lib/libc.so.6
  • /lib/libpthread.so.0
  • /lib/libdl.so.2
  • /lib/librt.so.1
  • ... and possibly some more like wayland and Qt libraries.
  1. while we're at it, try to fix some of the security considerations, like
  • /etc/pki (certificates)
  • /usr/lib/security (PAM)
  • /etc/sudoers
  • /etc/passwd
  • /etc/passwd-
  • /etc/group
  • /etc/group-
  • /etc/shadow
  • /etc/shadow-
  1. Maybe some other lists created by analyzing some commonly running, system- or performance-critical binaries, or those that tend to open a lot of files, and adding their most-opened files to the list. E.g. udev, everything systemd, any of the other daemons.

Further considerations

  1. Stability

libpreloadpatchmanager.so is currently a simple and time-tested piece of software, and is deployed in a manner very sensitive to bugs.
Changes should be done with great care, and certainly not because some nephros has a hunch there might be some microseconds gained in performance.

  1. Performance

The lists are parsed like this: https://github.com/sailfishos-patches/patchmanager/blob/master/src/preload/src/preloadpatchmanager.c#L121

If the lists become very long, that could have a negative impact all of its own. It is hard to judge (for me) whether these would offset any gains from not doing a round trip to the PM daemon, and not intercepting any libc calls.
(Preliminary research on optimizing strcmp calls comes back with "don't do that. You're not smarter than libc developers.")

  1. Gains

It is not proven at all that performance or security would be enhanced at all!

Hence the opening of this issue so these points can be discussed and analyzed.

Metadata

Metadata

Assignees

No one assigned

    Labels

    #questionsomeone asked something

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions