Repository navigation
Add option to docker run to set umask in container #19189
Description
Proposal
docker run currently has a --user option for setting the UID and GID for the command to be run inside the container. I'm proposing adding a --umask option that also sets the umask of the containerized process.
Implementation
I think this should be straightforward to add. The actual setting of the umask would happen in libcontainer.setupUser(), right after the call to system.Setuid().
This would also require adding a Umask system call wrapper in libcontainer.system (e.g. in syscall_linux_64.go)
libcontainer Spec
Interestingly, the libcontainer SPEC says:
The umask is set back to 0022 after the filesystem setup has been completed.
and indeed, it is, in libpackage.setupRootfs().
However, the spec never indicates that umask was ever changed beforehand. Since it was not changed outside of the filesystem setup, it seems like an odd place for the umask to be set to 0022 for the execution of the container. It seems like setting this where I suggested, in libcontainer.setupUser() makes more sense.
Use case
I apologize for the verbosity here, but this is a somewhat complex problem.
I have a utility called Scuba which aids in using Docker to containerize build environments (e.g. with cross-compilers, etc). Scuba wraps up the invocation of docker run to make running one-off command lines, like make, easier to do inside a docker container. The goal is that users forget they're using Docker at all.
The most challenging problem has been setting up the call to docker run such that artifacts created during the build look like they were created directly on the host. This means:
Owner UID/GID
This was the hardest part. Doing nothing, you end up with files in the build directory owned by root which is unacceptable. Using --user to set the UID/GID of the containerized process works okay, except you end up with a user who has no entry in /etc/passwd which causes lots of problems. See JonathonReinhart/scuba#11.
There are various issues open (see #7198 and #18825). My latest solution for Scuba (JonathonReinhart/scuba#24) is to inject /etc/passwd, /etc/group and /etc/shadow files into the container which include entries for the invoking user.
Permissions
The umask of the containerized process is different than that of the host (JonathonReinhart/scuba#14). This causes files to have different permissions when created using Scuba than if created natively.
Initially, to solve the uid/gid problem, I had created a script called .scubainit which created the user/group and set the umask before using su to run the user command. (JonathonReinhart/scuba#13), but this caused problems because the user command was no longer PID 1 (JonathonReinhart/scuba#22).
So in fixing that (JonathonReinhart/scuba#24), I lost the ability to set the umask in the container.
Activity
[-]Set umask in container[/-][+]Add option to `docker run` to set umask in container[/+]vidarl commentedon Feb 12, 2016
I second this!
For instance, on debian the umask is set by login ( or ssh or whatever that initiates the user session ) via PAM. I believe most distros use a similar approach.
The problem with docker containers is that we have no login process to set this up, we "simply" spawns a new process in a given namespace.
This is why the debian way of changing umask via /etc/pam.d/common-session won't work when we are dealing with docker containers
Because of this I think it should also be possible to set the umask in the Dockerfile, not only via
--umaskoption todocker runJonathon, I haven't look deeply into your particular use-case ( and the various issues you are referring to ) but might it work for you to do this in your Dockerfile:
The key here is the
-iargument which instructs bash to act as it has been invoked as an interactive shell. This causes bash to read initialization file ( bashrc files etc)Edit : ha ha, I was a bit too quick.. You need to use the
-iargument, not the-l. My bad...JonathonReinhart commentedon Feb 12, 2016
@vidarl Long story short, my use case doesn't have Dockerfiles. Scbua's goal is to just run a containerized process, but setting things up so files created in the container look as if they were created by the host user. I'm able to do this, with the exception of the file permissions (because of the umask).
GordonTheTurtle commentedon Jul 22, 2016
USER POLL
The best way to get notified of updates is to use the Subscribe button on this page.
Please don't use "+1" or "I have this too" comments on issues. We automatically
collect those comments to keep the thread short.
The people listed below have upvoted this issue by leaving a +1 comment:
@edburns
ScreamingDev commentedon Apr 1, 2017
Setting it in bashrc does not seem to work well. Running PHP via
docker-compose exec -T php-fpm php check-umask.phpshows that this has no effect at all. Not even if I switch to a user that has it in the ~.bashrc file.thaJeztah commentedon Apr 1, 2017
/cc @mlaventure @tonistiigi @crosbymichael
mlaventure commentedon Apr 7, 2017
I'm not opposed to the change, but this is a feature request for http://github.com/opencontainers/runc 👼
I would recommend, duplicating that issue there.
If/When implemented in
runc, then it can be added todocker.kevinlul commentedon Sep 8, 2021
This seems to have been added to the spec and implemented in
runclast year?jscoys commentedon Nov 12, 2021
6 years it was asked, any news? Still not possible natively in docker to specify the umask along UID & GID?
davidnewhall commentedon Jun 7, 2023
I would like to know how to set umask in a container
FROM scratchwith only a single binary in it. It has no bash, it has noumaskcommand. Just a compiled go app that runs fine, but with the wrong umask.