packagekit/docs/security.txt
Richard Hughes a6c552f5bf yum: Remove the yum backend
This has been broken since December 2013, and unmaintained for a much longer
time than that.
2014-09-02 13:17:48 +01:00

111 lines
5.8 KiB
Plaintext

Security and PackageKit
This document is a brief overview of security policies and notes about security
in the PackageKit project. It has been written by the PackageKit authors, and
should not be treated as independent analysis. This document has been written as
packagekitd is a system activated daemon running as the root user (uid 0), which
means the package management system is run as root also. The daemon receives
untrusted input from the client, which means the daemon is security sensitive.
First, a high level overview, in this case using the hif backend as an example:
gpk-update-icon gpk-application
| ___/
[D-Bus] __[D-Bus]__/
| /
packagekitd -- [D-Bus] -- polkitd-1
|
thread using libhif (using librepo, hawkey, etc)
packagekitd does not expose itself remotely over XMLRPC or other remote
interface, and so a remote denial of service or exploit is impossible without a
serious exploit of other services such as D-Bus. It advertises a simple interface
that can be queried by clients in unprivileged and privileged modes.
The privileged modes are controlled using PolicyKit, and policy and the
authentication mechanism is deferred to the polkitd-1 service.
When a privileged method is executed, the daemon checks with polkitd-1 daemon
for whether the client is authorized for the action it wants to perform.
This may involve the user authenticating that they are either the user (by
typing their password) or that they are an administrative user (by typing the
root password or the password of a user designated as an administrative user).
The authorization check can take some time, but the daemon can process other
requests whilst waiting for user input. Please see the the PolicyKit-1 man page
for more information.
The packagekitd daemon is started using D-Bus system activation, which means it
is started without any environment (no PATH, etc) and therefore is impossible to
exploit by preloading other libraries. It is also running as uid 0, and so
requires root privileges to inject code into it.
A typical transaction would be for the client to request a TID (transaction ID)
to which the server responds by creating a transaction instance and exposing
this on the system bus. The client then connects to this interface, and executes
the chosen method. This method will emit signals such as ::Package(), then
::Finished() and then after a number of seconds ::Destroy() which will remove
the interface from the bus.
There is a concern that a session service can be written to automatically
authenticate methods, and replace the native client, but this is not possible.
When authenticating, polkitd-1 passes a cookie to the authentication agent. If
the user enters the right password, the authentication agent calls
AuthenticationAgentResponse on the Authority with the cookie for the
authentication request. If the caller of AuthenticationAgentResponse is not
uid 0, then it is ignored.
The authentication setuid root polkit-agent-helper-1 only decides to invoke this
method if the user actually successfully authenticated. This of course relies on
polkit-agent-helper-1 being a secure program. This is easy to verify since
this is just over 300 lines of code and only depends on PAM (which is supposed
to be secure) up until we have decided that the user successfully authenticated.
Only when that is done, we initialize other libraries to send the message.
Possible attack vectors:
* A client could cause a local DoS (denial of service) by repeatedly calling
CreateTransaction without then calling a method to use this TID. This is mitigated by
timing out Tid request after a present number of seconds, and the effect can be
limited with a config variable (SimultaneousTransactionsForUid).
* Local DoS by repeatedly calling non-privileged methods such as Resolve and
SearchName. This could be mitigated by limiting the number of requests per
second for a certain seat, although no code has been written to do this at
present.
* A privileged method could be requested and then ignored or hidden by the
window manager. This is mitigated by not blocking the daemon when processing
authentication, and timing-out the authentication after a number of seconds if
authentication credentials are not supplied.
* Passing untrusted input to the backend which could be used to crash and
exploit the underlying package system. This is mitigated by rejecting invalid
input to methods, and testing filenames for existence before they are passed
to the backend.
* Issuing a large amount of data to a method to cause a local denial of
service, for instance calling Resolve with millions of parameters. This is
mitigated in the daemon by checking for a sane number of requests
(MaximumPackagesToProcess) for each method, and also limiting the total length
of the data.
* The HTTP and FTP proxies that are sent by the session may contain embedded
usernames and passwords. Whilst these are sent in plain text over the system
D-Bus (FIXME?), the database is not be readable by users (mode 0640).
* The matching of UID and session to proxies assumes that the user cannot
modify the login UID, and cannot spoof a session in ConsoleKit. If a user were
able to change the apparent UID, then this would allow them to use proxy
settings set from another user.
This is manifested when a graphical application is run using sudo (which you
should never do, but I digress) and different proxy settings may be used from
the user settings. It also allows applications run using sudo to use the proxy
specified by root, which may be different.
* We save the UID and session to a database to get the proxy state for each
transaction. If the user is able to create a large number of different sessions
then this will add many entries to the database. Some rate-limiting could be
added to ConsoleKit or PackageKit to solve this, but has not been done at this
time.