All of lore.kernel.org
 help / color / mirror / Atom feed
* Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
@ 2022-05-02 21:55 Nirav Shah
  2022-05-02 22:33 ` Patrick Williams
  2022-05-09 20:08 ` Ed Tanous
  0 siblings, 2 replies; 10+ messages in thread
From: Nirav Shah @ 2022-05-02 21:55 UTC (permalink / raw)
  To: openbmc, nirav.j2.shah, nirav.j2.shah


[-- Attachment #1.1: Type: text/plain, Size: 3781 bytes --]

Hello,

I am new to OpenBMC (and BMC ), so apologies if I am posting this in the 
wrong place. I have been looking at this 
<https://github.com/openbmc/openbmc/issues/3383> issue.Here is my 
summary of the problem statement, please do comment and let me know if I 
got this right.

 1. The biggest challenge is the use of system bus and non root access
    to the system bus.
 2. As previously suggested an ACL based approach can work. (whether it
    is using a D-Bus ACL configuration file or SELinux)
 3. However, it does require an exact configuration to cover all
    security scenarios (for MAC) and IMO “may” make debugging efforts
    harder.

Coming from a desktop background (which additionally uses D-BUS 
session/user bus for user isolation), I was investigating if having a 
session bus would help. For OpenBMC, the idea would be to allow non root 
application to communicate with each other and with root** applications 
on a single session bus to begin with. This can be further augmented 
using ACL based approaches if needed. I have a small POC, which tests 
this on OpenBMC with D-Bus broker

To run the demo

  * As root, copy files dbus_session.service and dbus_session.socket to
    /etc/systemd/system/
  * useradd nirav //or change the .service and .socket file to your user
  * systemctl daemon-reload
  * systemctl start dbus_session
  * ps | grep dbus //will show an additional dbus-broker running
  * compile dbus_server.c and dbus_client.c using yocto sdk or write a
    receipe
  * ssh as root, export
    DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/bus1 and ./dbus_server
  * ssh as nirav, export
    DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/bus1 and ./dbus_client

With the POC I was able to …..

 1. Show dbus_broker_launch “–scope user” works on OpenBMC (A session
    busses can be created using the right system unit files and launcher
    provided by D-Bus broker)
     1. Since I am new to D-Bus broker and systemd I had to confirm this.
 2. Show DBUS_SESSION_BUS_ADDRESS is the only env variable required by
    root to access the session bus of another user. There is a
    limitation here, discussed below.

As far as the actual solution, idea would be to have a configuration 
file to specify which D-Bus interfaces can be on the session bus. An opt 
in model which does not need any modification to existing and future 
OpenBMC daemons/applications would be the goal but there are limitations …..

  * For root**, to access another user’s session bus, its needs to
    setuid/setgid to the corresponding user.

      o This is because D-Bus actively blocks any user even uid 0 from
        accessing another’s session bus. It would be a simple patch to
        make an exception for root. But still something that needs to be
        maintained.
  * My POC was not using sdbus/plus. At the very least, modification
    will be needed to sdbusplus, sdbus, phosphor-dbus and possibly to
    object mapper. Not sure if more applications need to change.
  * Supporting multiple session D-Buses will be really complicated for a
    lot of reasons. So even if session bus is a reasonable idea (which I
    need feedback on), I would not jump into having a session bus per
    usecase from the get-go.

I am happy to start with a design document on git hub and also make some 
code changes, but I had a few questions.

 1. Your views on, if this a workable idea?
 2. I am hoping I can isolate all the changes to sdbusplus, sdbus,
    phosphor-dbus and object mapper. What else might need to change?
 3. If I can make all these changes, I was thinking of starting with
    BMCWeb as non root but since BMCWeb interfaces with a lot of daemons
    that would be a big step. Any better ideas?



Thanks,

Nirav.

-- 
Nirav Shah

[-- Attachment #1.2: Type: text/html, Size: 80901 bytes --]

[-- Attachment #2: dbus_client.c --]
[-- Type: text/plain, Size: 3765 bytes --]

/*
 *
 *     add-client.c: client program, takes two numbers as input,
 *                   sends to server for addition,
 *                   gets result from server,
 *                   prints the result on the screen
 *
 */

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <stdbool.h>
#include <ctype.h>

#include <dbus/dbus.h>


const char *const INTERFACE_NAME = "org.nirav.dbus_example";
const char *const SERVER_BUS_NAME = "org.nirav.add_server";
const char *const CLIENT_BUS_NAME = "org.nirav.add_client";
const char *const SERVER_OBJECT_PATH_NAME = "/org/nirav/adder";
const char *const CLIENT_OBJECT_PATH_NAME = "/org/nirav/add_client";
const char *const METHOD_NAME = "add_numbers";

DBusError dbus_error;
void print_dbus_error (char *str);

int main (int argc, char **argv)
{
    DBusConnection *conn;
    int ret;
    char input [80];

    dbus_error_init (&dbus_error);

    conn = dbus_bus_get (DBUS_BUS_SESSION, &dbus_error);

    if (dbus_error_is_set (&dbus_error))
        print_dbus_error ("dbus_bus_get");

    if (!conn)
        exit (1);

    printf ("Please type two numbers: ");
    while (fgets (input, 78, stdin) != NULL) {

        // Get a well known name
        while (1) {
            ret = dbus_bus_request_name (conn, CLIENT_BUS_NAME, 0, &dbus_error);

            if (ret == DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER)
               break;

            if (ret == DBUS_REQUEST_NAME_REPLY_IN_QUEUE) {
               fprintf (stderr, "Waiting for the bus ... \n");
               sleep (1);
               continue;
            }
            if (dbus_error_is_set (&dbus_error))
               print_dbus_error ("dbus_bus_get");
        }

        DBusMessage *request;

        if ((request = dbus_message_new_method_call (SERVER_BUS_NAME, SERVER_OBJECT_PATH_NAME,
                           INTERFACE_NAME, METHOD_NAME)) == NULL) {
            fprintf (stderr, "Error in dbus_message_new_method_call\n");
            exit (1);
        }

        DBusMessageIter iter;
        dbus_message_iter_init_append (request, &iter);
        char *ptr = input;
        if (!dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &ptr)) {
            fprintf (stderr, "Error in dbus_message_iter_append_basic\n");
            exit (1);
        }
        DBusPendingCall *pending_return;
        if (!dbus_connection_send_with_reply (conn, request, &pending_return, -1)) {
            fprintf (stderr, "Error in dbus_connection_send_with_reply\n");
            exit (1);
        }

        if (pending_return == NULL) {
            fprintf (stderr, "pending return is NULL");
            exit (1);
        }

        dbus_connection_flush (conn);

        dbus_message_unref (request);

        dbus_pending_call_block (pending_return);

        DBusMessage *reply;
        if ((reply = dbus_pending_call_steal_reply (pending_return)) == NULL) {
            fprintf (stderr, "Error in dbus_pending_call_steal_reply");
            exit (1);
        }

        dbus_pending_call_unref	(pending_return);

        char *s;
        if (dbus_message_get_args (reply, &dbus_error, DBUS_TYPE_STRING, &s, DBUS_TYPE_INVALID)) {
            printf ("%s\n", s);
        }
        else
        {
             fprintf (stderr, "Did not get arguments in reply\n");
             exit (1);
        }
        dbus_message_unref (reply);

        if (dbus_bus_release_name (conn, CLIENT_BUS_NAME, &dbus_error) == -1) {
             fprintf (stderr, "Error in dbus_bus_release_name\n");
             exit (1);
        }

        printf ("Please type two numbers: ");
    }

    return 0;
}

void print_dbus_error (char *str)
{
    fprintf (stderr, "%s: %s\n", str, dbus_error.message);
    dbus_error_free (&dbus_error);
}

[-- Attachment #3: dbus_session.service --]
[-- Type: text/plain, Size: 384 bytes --]

[Unit]
Description=D-Bus User Message Bus
Documentation=man:dbus-daemon(1)
Requires=dbus_session.socket

[Service]
Type=notify
User=nirav
Group=nirav
NotifyAccess=main
ExecStart=/usr/bin/dbus-broker-launch --scope user --audit
ExecReload=/usr/bin/dbus-send --print-reply --session --type=method_call --dest=org.freedesktop.DBus / org.freedesktop.DBus.ReloadConfig
Slice=session.slice

[-- Attachment #4: dbus_session.socket --]
[-- Type: text/plain, Size: 202 bytes --]

[Unit]
Description=D-Bus User Message Bus Socket

[Socket]
ListenStream=%t/user/bus1
User=nirav
Group=nirav
ExecStartPost=-/bin/systemctl set-environment DBUS_SESSION_BUS_ADDRESS=unix:path=%t/user/bus1

[-- Attachment #5: dbus_server.c --]
[-- Type: text/plain, Size: 6628 bytes --]

#define _GNU_SOURCE /* See feature_test_macros(7) */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>
#include <unistd.h>
#include <ctype.h>
#include <dbus/dbus.h>
#include <errno.h>

const char *const INTERFACE_NAME = "org.nirav.dbus_example";
const char *const SERVER_BUS_NAME = "org.nirav.add_server";
const char *const OBJECT_PATH_NAME = "/org/nirav/adder";
const char *const METHOD_NAME = "add_numbers";

/* Remember the effective and real UIDs. */
static uid_t ruid = 1007;
const char *version = "0.1";

/* Restore the effective UID to its original value. */

void
do_setuid (void)
{
  int status;
#ifdef _POSIX_SAVED_IDS

#if 0
status = setresuid (ruid, euid, 1062);

 if (status < 0) {
    if (errno == EPERM)
       printf("Permission denied to sudo\n");
    else
       printf ("Couldn't set uid.i%d\n", errno);
}
status = setresgid (1062, 1062, 1062);
#else
   status = setuid(ruid);
//   status = setresgid(1007, 1007, 1007);
#endif

#else
  status = setreuid (euid, ruid);
#endif
  if (status < 0) {
    if (errno == EPERM)
       printf("Permission denied to sudo\n");
    else
       printf ("Couldn't set uid.i%d\n", errno);
    exit (status);
  }
}




DBusError dbus_error;
void print_dbus_error (char *str);
bool isinteger (char *ptr);

int main (int argc, char **argv)
{
    DBusConnection *conn;
    int ret;

        uid_t lruid = 0, leuid=0, lsuid=0;
        uid_t lrgid = 0, legid=0, lsgid=0;
        if (0 == getresuid(&lruid, &leuid, &lsuid))
             printf("ruid=%d, euid=%d, suid=%d\n", lruid, leuid, lsuid);
        if (0 == getresgid(&lrgid, &legid, &lsgid))
             printf("rgid=%d, egid=%d, sgid=%d\n", lrgid, legid, lsgid);
#if 0
       printf("try to setuid\n");
       /* Remember the real and effective user IDs.  */
        do_setuid();

        if (0 == getresuid(&lruid, &leuid, &lsuid))
             printf("New ruid=%d, euid=%d, suid=%d\n", lruid, leuid, lsuid);
        if (0 == getresgid(&lrgid, &legid, &lsgid))
             printf("New rgid=%d, egid=%d, sgid=%d\n", lrgid, legid, lsgid);

        lruid = getuid ();
        leuid = geteuid ();
        fprintf(stderr, "new ruid=%d, new_euid=%d\n", lruid, leuid);
#endif
        printf("starting1\n");



    dbus_error_init (&dbus_error);

    conn = dbus_bus_get (DBUS_BUS_SESSION, &dbus_error);

    if (dbus_error_is_set (&dbus_error))
        print_dbus_error ("dbus_bus_get");

    if (!conn)
        exit (1);

    // Get a well known name
    ret = dbus_bus_request_name (conn, SERVER_BUS_NAME, DBUS_NAME_FLAG_DO_NOT_QUEUE, &dbus_error);

    if (dbus_error_is_set (&dbus_error))
        print_dbus_error ("dbus_bus_get");

    if (ret != DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER) {
        fprintf (stderr, "Dbus: not primary owner, ret = %d\n", ret);
        exit (1);
    }

    // Handle request from clients
    while (1) {
        // Block for msg from client
        if (!dbus_connection_read_write_dispatch (conn, -1)) {
            fprintf (stderr, "Not connected now.\n");
            exit (1);
        }

        DBusMessage *message;

        if ((message = dbus_connection_pop_message (conn)) == NULL) {
            fprintf (stderr, "Did not get message\n");
            continue;
        }

        if (dbus_message_is_method_call (message, INTERFACE_NAME, METHOD_NAME)) {
            char *s;
            char *str1 = NULL, *str2 = NULL;
            const char space [4] = " \n\t";
            long i, j;
            bool error = false;

            if (dbus_message_get_args (message, &dbus_error, DBUS_TYPE_STRING, &s, DBUS_TYPE_INVALID)) {
                printf ("%s", s);
                // Validate received message
                str1 = strtok (s, space);
                if (str1)
                    str2 = strtok (NULL, space);

                if (!str1 || !str2)
                    error = true;

                if (!error) {
                    if (isinteger (str1))
                        i = atol (str1);
                    else
                        error = true;
                }
                if (!error) {
                    if (isinteger (str2))
                        j = atol (str2);
                    else
                        error = true;
                }

                if (!error) {
                    // send reply
                    DBusMessage *reply;
                    char answer [40];

                    sprintf (answer, "Sum is %ld", i + j);
                    if ((reply = dbus_message_new_method_return (message)) == NULL) {
                        fprintf (stderr, "Error in dbus_message_new_method_return\n");
                        exit (1);
                    }

                    DBusMessageIter iter;
                    dbus_message_iter_init_append (reply, &iter);
                    char *ptr = answer;
                    if (!dbus_message_iter_append_basic (&iter, DBUS_TYPE_STRING, &ptr)) {
                        fprintf (stderr, "Error in dbus_message_iter_append_basic\n");
                        exit (1);
                    }

                    if (!dbus_connection_send (conn, reply, NULL)) {
                        fprintf (stderr, "Error in dbus_connection_send\n");
                        exit (1);
                    }

                    dbus_connection_flush (conn);

                    dbus_message_unref (reply);
                }
                else // There was an error
                {
                    DBusMessage *dbus_error_msg;
                    char error_msg [] = "Error in input";
                    if ((dbus_error_msg = dbus_message_new_error (message, DBUS_ERROR_FAILED, error_msg)) == NULL) {
                         fprintf (stderr, "Error in dbus_message_new_error\n");
                         exit (1);
                    }

                    if (!dbus_connection_send (conn, dbus_error_msg, NULL)) {
                        fprintf (stderr, "Error in dbus_connection_send\n");
                        exit (1);
                    }

                    dbus_connection_flush (conn);

                    dbus_message_unref (dbus_error_msg);
                }
            }
            else
            {
                print_dbus_error ("Error getting message");
            }
        }
    }

    return 0;
}


bool isinteger (char *ptr)
{

    if (*ptr == '+' || *ptr == '-')
        ptr++;

    while (*ptr) {
        if (!isdigit ((int) *ptr++))
            return false;
    }

    return true;
}

void print_dbus_error (char *str)
{
    fprintf (stderr, "%s: %s\n", str, dbus_error.message);
    dbus_error_free (&dbus_error);
}

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-02 21:55 Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus Nirav Shah
@ 2022-05-02 22:33 ` Patrick Williams
  2022-05-03  6:00   ` Nirav Shah
  2022-05-09 20:08 ` Ed Tanous
  1 sibling, 1 reply; 10+ messages in thread
From: Patrick Williams @ 2022-05-02 22:33 UTC (permalink / raw)
  To: Nirav Shah; +Cc: openbmc, nirav.j2.shah

[-- Attachment #1: Type: text/plain, Size: 4148 bytes --]

On Mon, May 02, 2022 at 02:55:39PM -0700, Nirav Shah wrote:
> Hello,
> 
> I am new to OpenBMC (and BMC ), so apologies if I am posting this in the 
> wrong place. I have been looking at this 
> <https://github.com/openbmc/openbmc/issues/3383> issue.Here is my 
> summary of the problem statement, please do comment and let me know if I 
> got this right.
> 
>  1. The biggest challenge is the use of system bus and non root access
>     to the system bus.
>  2. As previously suggested an ACL based approach can work. (whether it
>     is using a D-Bus ACL configuration file or SELinux)
>  3. However, it does require an exact configuration to cover all
>     security scenarios (for MAC) and IMO “may” make debugging efforts
>     harder.

I don't really think the issue is session bus vs system bus.  There
isn't really a significant difference between the two.  Just moving
everything to a session bus doesn't solve any security concerns.

> Coming from a desktop background (which additionally uses D-BUS 
> session/user bus for user isolation), I was investigating if having a 
> session bus would help. For OpenBMC, the idea would be to allow non root 
> application to communicate with each other and with root** applications 
> on a single session bus to begin with. This can be further augmented 
> using ACL based approaches if needed. I have a small POC, which tests 
> this on OpenBMC with D-Bus broker

What does moving everything to a session bus improve from a security
perspective?  I can't think of much.

I think the primary concern is that external-facing applications, like
IPMI and Redfish:

    1. Are the biggest attack vector for being compromised.
    2. Once compromised could do anything they wanted on the system,
       including on the DBus.

Moving everything from the system to session doesn't really improve
either of these aspects.

From an ACL perspective there is similarly a large surface area of dbus
interfaces that these (especially Redfish) need in order to do their
primary job.  The ACLs likely need to be written at an method/property
level within the DBus interfaces and this is, frankly, a lot of work.  I
suspect the 'best' answer is to put decorators into the
phosphor-dbus-interface YAML to be able to generate the appropriate
ACL configs.


> I am happy to start with a design document on git hub and also make some 
> code changes, but I had a few questions.

Code contributions go through Gerrit.

>  1. Your views on, if this a workable idea?

If you try to move all openbmc applications to the session bus, most of
them will work just fine.  A few of them will need secondary access to
the system bus because they operate on upstream components
(org.freedesktop interfaces) that only live on the system bus.  Anything
that initiates systemd service operations would certainly be affected.

>  2. I am hoping I can isolate all the changes to sdbusplus, sdbus,
>     phosphor-dbus and object mapper. What else might need to change?

sdbusplus already has functions to request the system-bus or the
session-bus (just like sdbus itself does).  Some applications are
currently written explicitly requesting the system-bus and some are
written requesting the 'default' bus, which is system for root and
session for non-root.  I was mentioning elsewhere recently that this
inconsistency is a poor situation for unit-testing as it is.

>  3. If I can make all these changes, I was thinking of starting with
>     BMCWeb as non root but since BMCWeb interfaces with a lot of daemons
>     that would be a big step. Any better ideas?

If the only goal is to run bmcweb as non-root, this could probably be
achieved without any change at a DBus level.  Use the systemd magic to
run the bmcweb service as a non-root user and add an ACL so that user can
access everything on system DBus.  This at least limits the bmcweb
process from accessing kernel APIs and limit the surface area to just
the available DBus interfaces.  We can then figure out how to further
limit the DBus APIs after that.

-- 
Patrick Williams

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-02 22:33 ` Patrick Williams
@ 2022-05-03  6:00   ` Nirav Shah
  2022-05-03 12:02     ` Patrick Williams
  0 siblings, 1 reply; 10+ messages in thread
From: Nirav Shah @ 2022-05-03  6:00 UTC (permalink / raw)
  To: Patrick Williams; +Cc: openbmc, nirav.j2.shah

[-- Attachment #1: Type: text/plain, Size: 7816 bytes --]

Hello,

<<<< Moving everything from the system to session /bus/ doesn't really 
improve either of these aspects.

I agree i am not proposing a complete transition to session bus. The 
proposal is to move the interactions to and from as you defined it 
"external facing application" and anything that does _*NOT*_ really need 
root access to the session bus by running them as non-root. Applications 
that "may" need root access (may be because the hardware interface 
requires root privilege) will continue to use the system bus for 
communicating with other root application and session bus for 
communication with non root applications.

<<<< if the only goal is to run bmcweb as non-root, this could probably 
be achieved without any change at a DBus level. Use the systemd magic to 
run the bmcweb service as a non-root user and add an ACL so that user 
can access everything on system DBus. This at least limits the bmcweb 
process from accessing kernel APIs and limit the surface area to just 
the available DBus interfaces. We can then figure out how to further 
limit the DBus APIs after that.

I agree that BMCWeb can run as non root today and still be on the system 
bus. Also agree, this is better than running BMCWeb as root. However, 
"We can then figure out how to further limit the DBus APIs after that" 
is what I want to address. How does having a session bus help solve 
this? This for me is complicated to put down in an email. If my 
explanation below sounds too high level, I would agree with that too.

Essentially today we have 2 possible ways in OpenBMC to implement ACL on 
D-BUS.

1. Using D-Bus configuration file, by default full access is enabled 
(e.g. if a root application crashes a non root application can take over 
the interface while the root application is being restarted). To block 
all possible accesses that could be exploited exception rules need to be 
program. This is what is called discretionary access control. This might 
be fine if we have an exhaustive list of all the possible exploits but 
we rarely do.

2. Using SELinux, apparmor or some sort of a mandatory access control 
system, where unless specifically configured, by default access is 
blocked to everything. In my experience, biggest problem here is a 
separate debug build with special privileges is almost always required. 
This becomes a challenge with on field debug and also when there are 
timing issues. Also, corner conditions where the unit test was not done 
could easily lead to "access denied" failures.

Using a session bus allows for flexible combination of these 2 
approaches with ...

1. By default, blocking "all" non root access to system bus unless 
specifically configured for an interface/method/signal. (MAC approach)

2. By default, allow "all" non root access to the session bus unless 
specifically blocked (DAC approach).

This is the approach I have seen in most of the Linux Distros for 
desktop. I understand OpenBMC does not have the same use cases as 
desktop but in this case it could be lot similar. Does this change your 
mind?

<<<< sdbusplus already has functions to request the system-bus or the 
session-bus (just like sdbus itself does). Some applications 
arecurrently written explicitly requesting the system-bus and some are 
written requesting the 'default' bus, which is system for root and 
session for non-root. I was mentioning elsewhere recently that this 
inconsistency is a poor situation for unit-testing as it is.

Thank you for this information.

<<<< Code contributions go through Gerrit.

Understood, thank you!

Thanks,

Nirav.



On 5/2/2022 3:33 PM, Patrick Williams wrote:
> On Mon, May 02, 2022 at 02:55:39PM -0700, Nirav Shah wrote:
>> Hello,
>>
>> I am new to OpenBMC (and BMC ), so apologies if I am posting this in the
>> wrong place. I have been looking at this
>> <https://github.com/openbmc/openbmc/issues/3383>  issue.Here is my
>> summary of the problem statement, please do comment and let me know if I
>> got this right.
>>
>>   1. The biggest challenge is the use of system bus and non root access
>>      to the system bus.
>>   2. As previously suggested an ACL based approach can work. (whether it
>>      is using a D-Bus ACL configuration file or SELinux)
>>   3. However, it does require an exact configuration to cover all
>>      security scenarios (for MAC) and IMO “may” make debugging efforts
>>      harder.
> I don't really think the issue is session bus vs system bus.  There
> isn't really a significant difference between the two.  Just moving
> everything to a session bus doesn't solve any security concerns.
>
>> Coming from a desktop background (which additionally uses D-BUS
>> session/user bus for user isolation), I was investigating if having a
>> session bus would help. For OpenBMC, the idea would be to allow non root
>> application to communicate with each other and with root** applications
>> on a single session bus to begin with. This can be further augmented
>> using ACL based approaches if needed. I have a small POC, which tests
>> this on OpenBMC with D-Bus broker
> What does moving everything to a session bus improve from a security
> perspective?  I can't think of much.
>
> I think the primary concern is that external-facing applications, like
> IPMI and Redfish:
>
>      1. Are the biggest attack vector for being compromised.
>      2. Once compromised could do anything they wanted on the system,
>         including on the DBus.
>
> Moving everything from the system to session doesn't really improve
> either of these aspects.
>
>  From an ACL perspective there is similarly a large surface area of dbus
> interfaces that these (especially Redfish) need in order to do their
> primary job.  The ACLs likely need to be written at an method/property
> level within the DBus interfaces and this is, frankly, a lot of work.  I
> suspect the 'best' answer is to put decorators into the
> phosphor-dbus-interface YAML to be able to generate the appropriate
> ACL configs.
>
>
>> I am happy to start with a design document on git hub and also make some
>> code changes, but I had a few questions.
> Code contributions go through Gerrit.
>
>>   1. Your views on, if this a workable idea?
> If you try to move all openbmc applications to the session bus, most of
> them will work just fine.  A few of them will need secondary access to
> the system bus because they operate on upstream components
> (org.freedesktop interfaces) that only live on the system bus.  Anything
> that initiates systemd service operations would certainly be affected.
>
>>   2. I am hoping I can isolate all the changes to sdbusplus, sdbus,
>>      phosphor-dbus and object mapper. What else might need to change?
> sdbusplus already has functions to request the system-bus or the
> session-bus (just like sdbus itself does).  Some applications are
> currently written explicitly requesting the system-bus and some are
> written requesting the 'default' bus, which is system for root and
> session for non-root.  I was mentioning elsewhere recently that this
> inconsistency is a poor situation for unit-testing as it is.
>
>>   3. If I can make all these changes, I was thinking of starting with
>>      BMCWeb as non root but since BMCWeb interfaces with a lot of daemons
>>      that would be a big step. Any better ideas?
> If the only goal is to run bmcweb as non-root, this could probably be
> achieved without any change at a DBus level.  Use the systemd magic to
> run the bmcweb service as a non-root user and add an ACL so that user can
> access everything on system DBus.  This at least limits the bmcweb
> process from accessing kernel APIs and limit the surface area to just
> the available DBus interfaces.  We can then figure out how to further
> limit the DBus APIs after that.
>
-- 
Nirav Shah

[-- Attachment #2: Type: text/html, Size: 9652 bytes --]

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-03  6:00   ` Nirav Shah
@ 2022-05-03 12:02     ` Patrick Williams
  2022-05-03 19:48       ` Bills, Jason M
  2022-05-03 23:46       ` Andrew Jeffery
  0 siblings, 2 replies; 10+ messages in thread
From: Patrick Williams @ 2022-05-03 12:02 UTC (permalink / raw)
  To: Nirav Shah; +Cc: openbmc, nirav.j2.shah

[-- Attachment #1: Type: text/plain, Size: 2597 bytes --]

On Mon, May 02, 2022 at 11:00:01PM -0700, Nirav Shah wrote:
> Hello,
> 
> <<<< Moving everything from the system to session /bus/ doesn't really 
> improve either of these aspects.
> 
> I agree i am not proposing a complete transition to session bus. The 
> proposal is to move the interactions to and from as you defined it 
> "external facing application" and anything that does _*NOT*_ really need 
> root access to the session bus by running them as non-root. Applications 
> that "may" need root access (may be because the hardware interface 
> requires root privilege) will continue to use the system bus for 
> communicating with other root application and session bus for 
> communication with non root applications.

To be honest, this sounds even more complex than just using the session
bus for almost everything.

> I agree that BMCWeb can run as non root today and still be on the system 
> bus. Also agree, this is better than running BMCWeb as root. However, 
> "We can then figure out how to further limit the DBus APIs after that" 
> is what I want to address. How does having a session bus help solve 
> this? This for me is complicated to put down in an email. If my 
> explanation below sounds too high level, I would agree with that too.
...
> This is the approach I have seen in most of the Linux Distros for 
> desktop. I understand OpenBMC does not have the same use cases as 
> desktop but in this case it could be lot similar. Does this change your 
> mind?

Not really. :)  Yes, "too high level" is probably the simplest statement
here.

Let me switch this discussion around a bit.  Please name me 4 daemons,
which currently reside on the system bus, and that bmcweb does not and
should not ever access.  

I think you'll find it hard to enumerate because our architecture is
purposefully very flat.  I know the codebase fairly well and have thought
about it for a bit and can only come up with one: kcsbridge (or btbridge).
Perhaps you could expand to a few of the systemd daemons (org.freedesktop)
where we've created an abstraction (xyz.openbmc_project), but I actually see
present day code in bmcweb which interacts with the ones I was thinking of
there.

So, effectively everything would need to be moved to the session bus
_and_ we'd still need a mechanism for bmcweb to access some of the
system bus end-points (via restricted ACLs), but effectively that is
still every single dbus endpoint.  This proposed move didn't actually
accomplish anything from a security standpoint in practice.

-- 
Patrick Williams

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 833 bytes --]

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-03 12:02     ` Patrick Williams
@ 2022-05-03 19:48       ` Bills, Jason M
  2022-05-09 20:10         ` Ed Tanous
  2022-05-03 23:46       ` Andrew Jeffery
  1 sibling, 1 reply; 10+ messages in thread
From: Bills, Jason M @ 2022-05-03 19:48 UTC (permalink / raw)
  To: openbmc



On 5/3/2022 6:02 AM, Patrick Williams wrote:
> On Mon, May 02, 2022 at 11:00:01PM -0700, Nirav Shah wrote:
>> Hello,
>>
>> <<<< Moving everything from the system to session /bus/ doesn't really
>> improve either of these aspects.
>>
>> I agree i am not proposing a complete transition to session bus. The
>> proposal is to move the interactions to and from as you defined it
>> "external facing application" and anything that does _*NOT*_ really need
>> root access to the session bus by running them as non-root. Applications
>> that "may" need root access (may be because the hardware interface
>> requires root privilege) will continue to use the system bus for
>> communicating with other root application and session bus for
>> communication with non root applications.
> 
> To be honest, this sounds even more complex than just using the session
> bus for almost everything.
> 
>> I agree that BMCWeb can run as non root today and still be on the system
>> bus. Also agree, this is better than running BMCWeb as root. However,
>> "We can then figure out how to further limit the DBus APIs after that"
>> is what I want to address. How does having a session bus help solve
>> this? This for me is complicated to put down in an email. If my
>> explanation below sounds too high level, I would agree with that too.
> ...
>> This is the approach I have seen in most of the Linux Distros for
>> desktop. I understand OpenBMC does not have the same use cases as
>> desktop but in this case it could be lot similar. Does this change your
>> mind?
> 
> Not really. :)  Yes, "too high level" is probably the simplest statement
> here.
> 
> Let me switch this discussion around a bit.  Please name me 4 daemons,
> which currently reside on the system bus, and that bmcweb does not and
> should not ever access.
One possible example that maybe isn't in place yet is MCTP.  If we end 
up exposing an MCTP interface over D-Bus, is there risk that this could 
be used maliciously since a compromised application running as root has 
direct access to the MCTP interface?

If the direct MCTP interface is on the system bus and the filtered MCTP 
interface is on the session bus, then a compromised non-root application 
would still be blocked from accessing the direct MCTP interface.

> 
> I think you'll find it hard to enumerate because our architecture is
> purposefully very flat.  I know the codebase fairly well and have thought
> about it for a bit and can only come up with one: kcsbridge (or btbridge).
> Perhaps you could expand to a few of the systemd daemons (org.freedesktop)
> where we've created an abstraction (xyz.openbmc_project), but I actually see
> present day code in bmcweb which interacts with the ones I was thinking of
> there.
> 
> So, effectively everything would need to be moved to the session bus
> _and_ we'd still need a mechanism for bmcweb to access some of the
> system bus end-points (via restricted ACLs), but effectively that is
> still every single dbus endpoint.  This proposed move didn't actually
> accomplish anything from a security standpoint in practice.
> 

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-03 12:02     ` Patrick Williams
  2022-05-03 19:48       ` Bills, Jason M
@ 2022-05-03 23:46       ` Andrew Jeffery
  2022-05-09 20:10         ` Ed Tanous
  1 sibling, 1 reply; 10+ messages in thread
From: Andrew Jeffery @ 2022-05-03 23:46 UTC (permalink / raw)
  To: Patrick Williams, Nirav Shah; +Cc: openbmc, nirav.j2.shah



On Tue, 3 May 2022, at 21:32, Patrick Williams wrote:
> I think you'll find it hard to enumerate because our architecture is
> purposefully very flat.  I know the codebase fairly well and have thought
> about it for a bit and can only come up with one: kcsbridge (or btbridge).

IMO both kcsbridged and btbridged should be deleted and the 
functionality folded into phosphor-host-ipmid. The split that we have 
there is not useful or efficient.

In terms of what Patrick spoke about, that means even fewer examples.

Andrew

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-02 21:55 Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus Nirav Shah
  2022-05-02 22:33 ` Patrick Williams
@ 2022-05-09 20:08 ` Ed Tanous
  2022-05-12 16:11   ` Joseph Reynolds
  1 sibling, 1 reply; 10+ messages in thread
From: Ed Tanous @ 2022-05-09 20:08 UTC (permalink / raw)
  To: nirav.j2.shah; +Cc: openbmc, nirav.j2.shah

On Mon, May 2, 2022 at 2:58 PM Nirav Shah <nirav.j2.shah@linux.intel.com> wrote:
>
> Hello,
>
>
>
> I am new to OpenBMC (and BMC ),

Welcome!  Glad to have you.

> so apologies if I am posting this in the wrong place. I have been looking at this issue.  Here is my summary of the problem statement, please do comment and let me know if I got this right.
>
> The biggest challenge is the use of system bus and non root access to the system bus.

This statement could be phrased a little more precisely.  The biggest
challenge is that:
1. bmcweb (and all user-facing daemons) run as root.
2. There is no way to define an ACL such that a user-facing daemon
would not have access to something.
4. User-facing daemons enforce their own authorization systems,
instead of relying on something out of process, which makes them more
vulnerable than is ideal.

> As previously suggested an ACL based approach can work. (whether it is using a D-Bus ACL configuration file or SELinux)
> However, it does require an exact configuration to cover all security scenarios (for MAC) and IMO “may” make debugging efforts harder.
>
> Coming from a desktop background (which additionally uses D-BUS session/user bus for user isolation), I was investigating if having a session bus would help. For OpenBMC, the idea would be to allow non root application to communicate with each other and with root** applications on a single session bus to begin with. This can be further augmented using ACL based approaches if needed. I have a small POC, which tests this on OpenBMC with D-Bus broker

I think the thing you haven't touched on here is that in the way linux
generally uses these, session busses are spun up per-user session,
which provides some level of abstraction and segmentation between
various users.  it'd be interesting to talk through that as an
architecture, and how it maps, but as Patrick points out elsewhere,
simply moving nearly everything onto a shared session bus doesn't
really do much to solve the security concerns.

An architecture that would be interesting would be:

1. On creation of a session, bmcweb registers the session with linux,
and gives the session that users permissions levels, similar to how a
"normal distro" session manager would act.
2. ACLs would define specifically (at dbus level) what that user was
allowed to do.  Ideally we could drive some of these from
PrivilegeRegistry.
3. When user requests come in, bmcweb would route the requests to the
appropriate session bus for that user.

And in theory, at the end, we could remove the permissions code from
bmcweb, because we'd be relying on linux permissions, which are
arguably better.

>
> To run the demo
>
> As root, copy files dbus_session.service and dbus_session.socket to /etc/systemd/system/
> useradd nirav //or change the .service and .socket file to your user
> systemctl daemon-reload
> systemctl start dbus_session
> ps | grep dbus //will show an additional dbus-broker running
> compile dbus_server.c and dbus_client.c using yocto sdk or write a receipe
> ssh as root, export DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/bus1 and ./dbus_server
> ssh as nirav, export DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/bus1 and ./dbus_client
>
> With the POC I was able to …..
>
> Show dbus_broker_launch “–scope user” works on OpenBMC (A session busses can be created using the right system unit files and launcher provided by D-Bus broker)
>
> Since I am new to D-Bus broker and systemd I had to confirm this.
>
> Show DBUS_SESSION_BUS_ADDRESS is the only env variable required by root to access the session bus of another user. There is a limitation here, discussed below.
>
> As far as the actual solution, idea would be to have a configuration file to specify which D-Bus interfaces can be on the session bus. An opt in model which does not need any modification to existing and future OpenBMC daemons/applications would be the goal but there are limitations …..
>
> For root**, to access another user’s session bus, its needs to setuid/setgid to the corresponding user.
>
> This is because D-Bus actively blocks any user even uid 0 from accessing another’s session bus. It would be a simple patch to make an exception for root. But still something that needs to be maintained.

This is something that would need to be looked at in more depth technically.

>
> My POC was not using sdbus/plus. At the very least, modification will be needed to sdbusplus, sdbus, phosphor-dbus and possibly to object mapper. Not sure if more applications need to change.
> Supporting multiple session D-Buses will be really complicated for a lot of reasons. So even if session bus is a reasonable idea (which I need feedback on), I would not jump into having a session bus per usecase from the get-go.
>
> I am happy to start with a design document on git hub and also make some code changes, but I had a few questions.
>
> Your views on, if this a workable idea?

I have very similar concerns with Patrick;  With that said, if these
are minor additions to existing daemons that are optional, I'd be in
support of some amount of experimentation in this regard to find an
acceptable solution, but I don't think the above gets us to what we
need.

> I am hoping I can isolate all the changes to sdbusplus, sdbus, phosphor-dbus and object mapper. What else might need to change?

I'm fairly certain every daemon needs some changes to define the
appropriate ACLs.  Essentially we need to distribute BMCWEBs privilege
registry mapping to dbus, so individual daemons can put in ACLs that
define whether their APIs are Admin, Operator, user, or read-only
privilege level.

> If I can make all these changes, I was thinking of starting with BMCWeb as non root but since BMCWeb interfaces with a lot of daemons that would be a big step. Any better ideas?

Keep in mind, bmcweb also accesses things that:
1. Aren't openbmc dbus daemons (primarily systemd)
2. Supports accessing data through unix sockets (KVM, serial port,
virtual media, ect).
3. Supports accessing system data through the filesystem (EventLog,
HostLog, ect).
4. Has data that it needs to persist (sessions, guids, ect) in
bmcweb_persistent_data.json.

If you want to run bmcweb as non-root on any non-trivial system, you'd
have to find solutions for those use cases as well.  WIth that said,
if you want to focus on the dbus aspects first, happy to work through
that piecemeal, but it will mean that we will have to support both
configs (bmcweb as root, and bmcweb as non-root) for some amount of
time, so keep that in mind when you write your patches.

>
>
>
> Thanks,
>
> Nirav.
>
>
>
>
>
>
>
> --
> Nirav Shah

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-03 19:48       ` Bills, Jason M
@ 2022-05-09 20:10         ` Ed Tanous
  0 siblings, 0 replies; 10+ messages in thread
From: Ed Tanous @ 2022-05-09 20:10 UTC (permalink / raw)
  To: Bills, Jason M; +Cc: openbmc

On Tue, May 3, 2022 at 12:49 PM Bills, Jason M
<jason.m.bills@linux.intel.com> wrote:
>
>
>
> On 5/3/2022 6:02 AM, Patrick Williams wrote:
> > On Mon, May 02, 2022 at 11:00:01PM -0700, Nirav Shah wrote:
> >> Hello,
> >>
> >> <<<< Moving everything from the system to session /bus/ doesn't really
> >> improve either of these aspects.
> >>
> >> I agree i am not proposing a complete transition to session bus. The
> >> proposal is to move the interactions to and from as you defined it
> >> "external facing application" and anything that does _*NOT*_ really need
> >> root access to the session bus by running them as non-root. Applications
> >> that "may" need root access (may be because the hardware interface
> >> requires root privilege) will continue to use the system bus for
> >> communicating with other root application and session bus for
> >> communication with non root applications.
> >
> > To be honest, this sounds even more complex than just using the session
> > bus for almost everything.
> >
> >> I agree that BMCWeb can run as non root today and still be on the system
> >> bus. Also agree, this is better than running BMCWeb as root. However,
> >> "We can then figure out how to further limit the DBus APIs after that"
> >> is what I want to address. How does having a session bus help solve
> >> this? This for me is complicated to put down in an email. If my
> >> explanation below sounds too high level, I would agree with that too.
> > ...
> >> This is the approach I have seen in most of the Linux Distros for
> >> desktop. I understand OpenBMC does not have the same use cases as
> >> desktop but in this case it could be lot similar. Does this change your
> >> mind?
> >
> > Not really. :)  Yes, "too high level" is probably the simplest statement
> > here.
> >
> > Let me switch this discussion around a bit.  Please name me 4 daemons,
> > which currently reside on the system bus, and that bmcweb does not and
> > should not ever access.
> One possible example that maybe isn't in place yet is MCTP.  If we end
> up exposing an MCTP interface over D-Bus, is there risk that this could
> be used maliciously since a compromised application running as root has
> direct access to the MCTP interface?
>
> If the direct MCTP interface is on the system bus and the filtered MCTP
> interface is on the session bus, then a compromised non-root application
> would still be blocked from accessing the direct MCTP interface.
>

+1 IPMB would be similar to this, although I suspect that we really
don't want to put raw MCTP on dbus like we did with IPMB.  Arguably
even in the IPMB case there were likely better paths, and now that the
shared IPMB state is in the kernel, needing to pass arbitrary ipmb
messages over dbus is probably not something we'd do if we did it
again.

> >
> > I think you'll find it hard to enumerate because our architecture is
> > purposefully very flat.  I know the codebase fairly well and have thought
> > about it for a bit and can only come up with one: kcsbridge (or btbridge).
> > Perhaps you could expand to a few of the systemd daemons (org.freedesktop)
> > where we've created an abstraction (xyz.openbmc_project), but I actually see
> > present day code in bmcweb which interacts with the ones I was thinking of
> > there.
> >
> > So, effectively everything would need to be moved to the session bus
> > _and_ we'd still need a mechanism for bmcweb to access some of the
> > system bus end-points (via restricted ACLs), but effectively that is
> > still every single dbus endpoint.  This proposed move didn't actually
> > accomplish anything from a security standpoint in practice.
> >

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-03 23:46       ` Andrew Jeffery
@ 2022-05-09 20:10         ` Ed Tanous
  0 siblings, 0 replies; 10+ messages in thread
From: Ed Tanous @ 2022-05-09 20:10 UTC (permalink / raw)
  To: Andrew Jeffery; +Cc: openbmc, Nirav Shah, nirav.j2.shah

On Tue, May 3, 2022 at 4:47 PM Andrew Jeffery <andrew@aj.id.au> wrote:
>
>
>
> On Tue, 3 May 2022, at 21:32, Patrick Williams wrote:
> > I think you'll find it hard to enumerate because our architecture is
> > purposefully very flat.  I know the codebase fairly well and have thought
> > about it for a bit and can only come up with one: kcsbridge (or btbridge).
>
> IMO both kcsbridged and btbridged should be deleted and the
> functionality folded into phosphor-host-ipmid. The split that we have
> there is not useful or efficient.

+1

>
> In terms of what Patrick spoke about, that means even fewer examples.
>
> Andrew

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus.
  2022-05-09 20:08 ` Ed Tanous
@ 2022-05-12 16:11   ` Joseph Reynolds
  0 siblings, 0 replies; 10+ messages in thread
From: Joseph Reynolds @ 2022-05-12 16:11 UTC (permalink / raw)
  To: Ed Tanous, nirav.j2.shah; +Cc: openbmc, nirav.j2.shah

On 5/9/22 3:08 PM, Ed Tanous wrote:
> On Mon, May 2, 2022 at 2:58 PM Nirav Shah <nirav.j2.shah@linux.intel.com> wrote:
>> Hello,
>>
>>
>>
>> I am new to OpenBMC (and BMC ),
> Welcome!  Glad to have you.
>
>> so apologies if I am posting this in the wrong place. I have been looking at this issue.  Here is my summary of the problem statement, please do comment and let me know if I got this right.
>>
>> The biggest challenge is the use of system bus and non root access to the system bus.
> This statement could be phrased a little more precisely.  The biggest
> challenge is that:
> 1. bmcweb (and all user-facing daemons) run as root.
> 2. There is no way to define an ACL such that a user-facing daemon
> would not have access to something.
> 4. User-facing daemons enforce their own authorization systems,
> instead of relying on something out of process, which makes them more
> vulnerable than is ideal.
>
>> As previously suggested an ACL based approach can work. (whether it is using a D-Bus ACL configuration file or SELinux)
>> However, it does require an exact configuration to cover all security scenarios (for MAC) and IMO “may” make debugging efforts harder.
>>
>> Coming from a desktop background (which additionally uses D-BUS session/user bus for user isolation), I was investigating if having a session bus would help. For OpenBMC, the idea would be to allow non root application to communicate with each other and with root** applications on a single session bus to begin with. This can be further augmented using ACL based approaches if needed. I have a small POC, which tests this on OpenBMC with D-Bus broker
> I think the thing you haven't touched on here is that in the way linux
> generally uses these, session busses are spun up per-user session,
> which provides some level of abstraction and segmentation between
> various users.  it'd be interesting to talk through that as an
> architecture, and how it maps, but as Patrick points out elsewhere,
> simply moving nearly everything onto a shared session bus doesn't
> really do much to solve the security concerns.
>
> An architecture that would be interesting would be:
>
> 1. On creation of a session, bmcweb registers the session with linux,
> and gives the session that users permissions levels, similar to how a
> "normal distro" session manager would act.
> 2. ACLs would define specifically (at dbus level) what that user was
> allowed to do.  Ideally we could drive some of these from
> PrivilegeRegistry.
> 3. When user requests come in, bmcweb would route the requests to the
> appropriate session bus for that user.
>
> And in theory, at the end, we could remove the permissions code from
> bmcweb, because we'd be relying on linux permissions, which are
> arguably better.

In the 2022-05-11 Security Working Group meeting, I advocated that we 
document a model for how some of the BMC's network-facing services use 
D-Bus interfaces.
The model would be organized by interface, similar to 
https://github.com/openbmc/docs/blob/master/security/network-security-considerations.md 
so it could be incrorporated into a larger threat model.
The model should be adequate to show, for example, how bmcweb and the 
ipmi (ipmitool) network-facing services invoke D-Bus APIs to perform 
user management functions, and how access should be limited to admin users.

This model could be used, for example, to help describe that only bmcweb 
and ipmi should have access to user-management APIs.  Or it could be 
used to help describe the user authority needed to invoke each of the 
user-management APIs.  Or whatever authorization mechanism the projects 
decides to have.

Joseph

Ref:
Security Working Group meeting: 
https://docs.google.com/document/d/1b7x9BaxsfcukQDqbvZsU2ehMq4xoJRQvLxxsDUWmAOI
>
>> To run the demo
>>
>> As root, copy files dbus_session.service and dbus_session.socket to /etc/systemd/system/
>> useradd nirav //or change the .service and .socket file to your user
>> systemctl daemon-reload
>> systemctl start dbus_session
>> ps | grep dbus //will show an additional dbus-broker running
>> compile dbus_server.c and dbus_client.c using yocto sdk or write a receipe
>> ssh as root, export DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/bus1 and ./dbus_server
>> ssh as nirav, export DBUS_SESSION_BUS_ADDRESS=unix:path=/run/user/bus1 and ./dbus_client
>>
>> With the POC I was able to …..
>>
>> Show dbus_broker_launch “–scope user” works on OpenBMC (A session busses can be created using the right system unit files and launcher provided by D-Bus broker)
>>
>> Since I am new to D-Bus broker and systemd I had to confirm this.
>>
>> Show DBUS_SESSION_BUS_ADDRESS is the only env variable required by root to access the session bus of another user. There is a limitation here, discussed below.
>>
>> As far as the actual solution, idea would be to have a configuration file to specify which D-Bus interfaces can be on the session bus. An opt in model which does not need any modification to existing and future OpenBMC daemons/applications would be the goal but there are limitations …..
>>
>> For root**, to access another user’s session bus, its needs to setuid/setgid to the corresponding user.
>>
>> This is because D-Bus actively blocks any user even uid 0 from accessing another’s session bus. It would be a simple patch to make an exception for root. But still something that needs to be maintained.
> This is something that would need to be looked at in more depth technically.
>
>> My POC was not using sdbus/plus. At the very least, modification will be needed to sdbusplus, sdbus, phosphor-dbus and possibly to object mapper. Not sure if more applications need to change.
>> Supporting multiple session D-Buses will be really complicated for a lot of reasons. So even if session bus is a reasonable idea (which I need feedback on), I would not jump into having a session bus per usecase from the get-go.
>>
>> I am happy to start with a design document on git hub and also make some code changes, but I had a few questions.
>>
>> Your views on, if this a workable idea?
> I have very similar concerns with Patrick;  With that said, if these
> are minor additions to existing daemons that are optional, I'd be in
> support of some amount of experimentation in this regard to find an
> acceptable solution, but I don't think the above gets us to what we
> need.
>
>> I am hoping I can isolate all the changes to sdbusplus, sdbus, phosphor-dbus and object mapper. What else might need to change?
> I'm fairly certain every daemon needs some changes to define the
> appropriate ACLs.  Essentially we need to distribute BMCWEBs privilege
> registry mapping to dbus, so individual daemons can put in ACLs that
> define whether their APIs are Admin, Operator, user, or read-only
> privilege level.
>
>> If I can make all these changes, I was thinking of starting with BMCWeb as non root but since BMCWeb interfaces with a lot of daemons that would be a big step. Any better ideas?
> Keep in mind, bmcweb also accesses things that:
> 1. Aren't openbmc dbus daemons (primarily systemd)
> 2. Supports accessing data through unix sockets (KVM, serial port,
> virtual media, ect).
> 3. Supports accessing system data through the filesystem (EventLog,
> HostLog, ect).
> 4. Has data that it needs to persist (sessions, guids, ect) in
> bmcweb_persistent_data.json.
>
> If you want to run bmcweb as non-root on any non-trivial system, you'd
> have to find solutions for those use cases as well.  WIth that said,
> if you want to focus on the dbus aspects first, happy to work through
> that piecemeal, but it will mean that we will have to support both
> configs (bmcweb as root, and bmcweb as non-root) for some amount of
> time, so keep that in mind when you write your patches.
>
>>
>>
>> Thanks,
>>
>> Nirav.
>>
>>
>>
>>
>>
>>
>>
>> --
>> Nirav Shah


^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2022-05-12 16:12 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-05-02 21:55 Running OpenBMC Daemons/Applications as non root using D-Bus Session/User Bus Nirav Shah
2022-05-02 22:33 ` Patrick Williams
2022-05-03  6:00   ` Nirav Shah
2022-05-03 12:02     ` Patrick Williams
2022-05-03 19:48       ` Bills, Jason M
2022-05-09 20:10         ` Ed Tanous
2022-05-03 23:46       ` Andrew Jeffery
2022-05-09 20:10         ` Ed Tanous
2022-05-09 20:08 ` Ed Tanous
2022-05-12 16:11   ` Joseph Reynolds

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.