Skip to content

Lack of passwd/group file entries when run as arbitrarily assigned user ID. #552

@GrahamDumpleton

Description

@GrahamDumpleton

What docker image you are using?

All are affected by this issue.

What complete docker command do you run to launch the container (omitting sensitive values)?

Two commands to consider.

$ docker run -it -u 1000000 --group-add 100 jupyter/minimal-notebook:latest bash

and:

$ docker run -it -u 1000000 --group-add 100 --group-add 1000000 jupyter/minimal-notebook:latest bash

The examples are where images are run as arbitrarily assigned user ID. This scenario can arise in container deployment platforms which enforce a security model where images can't run as root or even the user the image specifies. This is the case with Kubernetes (and OpenShift), where Role Base Access Control (RBAC) and Security Context Constraints (SCC) are enabled to enforce a secure multitenant deployment environment.

Note that the images will not actualy work out of the box this way because the group they run as will be GID 0. To compensate for this, you need to add GID 100 as supplemental group for the container. A platform might also itself add the assigned user ID as a supplemental group as well.

What steps do you take once the container is running to reproduce the issue?

Once shell is running the container, run the commands:

id
whoami
groups

In the first case the result will be:

I have no name!@3dffcb336b17:~$ id
uid=1000000 gid=0(root) groups=0(root),100(users)
I have no name!@3dffcb336b17:~$ whoami
whoami: cannot find name for user ID 1000000
I have no name!@3dffcb336b17:~$ groups
root users

In the second it will be:

I have no name!@bf6a70260f15:~$ id
uid=1000000 gid=0(root) groups=0(root),100(users),1000000
I have no name!@bf6a70260f15:~$ whoami
whoami: cannot find name for user ID 1000000
I have no name!@bf6a70260f15:~$ groups
root users groups: cannot find name for group ID 1000000
1000000

What do you expect to happen?

No errors.

What actually happens?

Errors.

The reason this is a problem is some Python packages out there aren't tolerant of the user they are running as not having passwd and group file entries. An example of typical exception that might occur is:

Traceback (most recent call last):
  File "/opt/app-root/bin/jupyterhub", line 3, in <module>
    from jupyterhub.app import main
  File "/opt/app-root/lib/python3.6/site-packages/jupyterhub/app.py", line 118, in <module>
    class NewToken(Application):
  File "/opt/app-root/lib/python3.6/site-packages/jupyterhub/app.py", line 134, in NewToken
    name = Unicode(getuser())
  File "/opt/rh/rh-python36/root/usr/lib64/python3.6/getpass.py", line 169, in getuser
    return pwd.getpwuid(os.getuid())[0]
KeyError: 'getpwuid(): uid not found: 1000930000'

Solution

A solution to this problem is to make /etc/passwd and /etc/group files writable and when the container is run, add appropriate entries to the files so valid results are returned. That is, so get something like:

$ id
uid=1000070000(jovyan) gid=0(root) groups=0(root),100(users),1000070000(jovyan)
$ whoami
jovyan
$ groups
root users jovyan

This can be done through a script such as:

NB_UID=`id -u`
NB_GID=`id -g`

if [ $NB_GID -eq 0 -a $NB_UID -ge 100000 ]; then
    cat /etc/passwd | sed -e "s/^jovyan:/nayvoj:/" > /tmp/passwd
    echo "jovyan:x:$NB_UID:$NB_GID:,,,:/home/jovyan:/bin/bash" >> /tmp/passwd
    cat /tmp/passwd > /etc/passwd
    rm /tmp/passwd

    id -G | grep -q -w $NB_UID; STATUS=$?
    if [ $STATUS -eq 0 ]; then
        echo "jovyan:x:$NB_UID:" >> /etc/group
    fi
fi

so that the /etc/passwd file ends up being:

nayvoj:x:1000:100::/home/jovyan:/bin/bash
jovyan:x:1000070000:0:,,,:/home/jovyan:/bin/bash

and the /etc/group file being:

jovyan:x:1000070000:

The system C libraries in the container will consult the modified files and yield the desired results.

A PR is coming with a working fix for this.

Note that making /etc/passwd and /etc/group files writable has been reviewed by some security minded folks in Red Hat and no risk was seen in having them writable in the context of a container run under docker or other OCI spec runtime. The ability to make changes does not introduce any way of code being able to escalate privileges.

Metadata

Metadata

Assignees

No one assigned

    Labels

    type:EnhancementA proposed enhancement to the docker images

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions