I had a bout of insomnia last night and decided to play with Docker. For the uninitiated, Docker is a like chroot on steroids. It allows for applications to be force to run within a specific context, disallowing them to break out of that context (where context can be CPU allocation, hardware allocation, filesystem scoping, etc.). I didn’t find any single article that shed much light on the topic of Steam and Docker, yet there is clearly *some* progress in that realm. So, here is what I did to get it basically working.
After installing Docker (apt-get install docker.io
), I found that there was someone who already did a bunch of the groundwork for a steam container (docker search steam
). So I used that as a starting point in my own Dockerfile:
FROM tianon/steam
Next, I needed to include the nVidia drivers (since that’s the GPU in my system) in the container and give the container access to the GPU:
RUN sudo apt-get update && sudo apt-get install -yq kmod mesa-utils
ADD NVIDIA-Linux-x86_64-340.32.run /tmp/NVIDIA-DRIVER.run
RUN sudo sh /tmp/NVIDIA-DRIVER.run -a -N --ui=none --no-kernel-module
RUN sudo rm /tmp/NVIDIA-DRIVER.run
I copied the rest of what tianon/steam had in his dockerfile to finish it off. Here is the end result:
FROM tianon/steam
# my system has nvidia, so yours should too!
RUN sudo apt-get update && sudo apt-get install -yq kmod mesa-utils
ADD NVIDIA-Linux-x86_64-340.32.run /tmp/NVIDIA-DRIVER.run
RUN sudo sh /tmp/NVIDIA-DRIVER.run -a -N --ui=none --no-kernel-module
RUN sudo rm /tmp/NVIDIA-DRIVER.run
USER steam
ENV HOME /home/steam
VOLUME /home/steam
CMD ["steam"]
Now that I have my Dockerfile to build my own container with my GPU drivers, I needed to enable the lxc driver for docker (from what I understand, this is another part of allowing docker containers access to the hardware). On Debian Sid (09/12/2014), this was a matter of simply modifying /etc/default/docker.io
and uncommenting the “DOCKER_OPTS” and adding “-e lxc”. Here’s the result of that file after modification:
# Docker Upstart and SysVinit configuration file
# Customize location of Docker binary (especially for development testing).
#DOCKER="/usr/local/bin/docker"
# Use DOCKER_OPTS to modify the daemon startup options.
DOCKER_OPTS="--dns 8.8.8.8 --dns 8.8.4.4 -e lxc"
# If you need Docker to use an HTTP proxy, it can also be specified here.
#export http_proxy="http://127.0.0.1:3128/"
# This is also a handy place to tweak where Docker's temporary files go.
#export TMPDIR="/mnt/bigdrive/docker-tmp"
Then, restart the docker.io service (sudo /etc/init.d/docker.io restart
). Now that all the critical service stuff is in place, I created a docker container with that Dockerfile from earlier with the following command (hint: you need to be in the directory of the Dockerfile):
docker build -t mine .
“mine” is a horrible name. Use something less horrible (do as I say, not as I do). The one last piece was to properly kick off the container by mapping/binding devices to it. I created a script for this, ’cause I’m lazy. Here’s my script:
docker run --name=steam_mine \
-v /dev/dri:/dev/dri \
-v /tmp/.X11-unix:/tmp/.X11-unix -v /dev/shm:/dev/shm \
-v /run/user/${UID}/pulse:/run/user/${UID}/pulse \
-v /etc/machine-id:/etc/machine-id \
-v ${HOME}/Downloads:/tmp/Downloads \
--privileged=true \
-e DISPLAY=${DISPLAY} mine
Now, simply running the script would launch the container and I was greeted with the familiar steam installer (for linux). But sound is missing for some reason (I’ll deal with that later). I tested Super Meat Boy and Dota 2, both of which worked great. Performance was not noticeably different than running it outside of Docker (no hard data here other than it felt the same, no perceivable difference in framerate/loading time/etc.).
There is something very interesting that this allows for when bundled with steam in-home streaming. If you have a friend coming over, they can bring over a raspberry pi with a monitor/keyboard and use that to game on and get the same performance as a high-end gaming rig by streaming their game off of your computer. I’m sure there is some performance hits, but nothing that a little extra money can’t fix. I remember having LAN parties and packing up my tower/keyboard/mouse/CRT monitor. Now, a simple low-end laptop can provide a high-end gaming experience using Steam in Docker and in-home streaming. Interesting times ahead…
Awesome. How (more precisely) did you ‘stream game’ from your computer to a raspi? This is an awesome post for containerized steam application. I’m looking into building off of a dedicated steam server image, and have some hoops to jump through since the game I want to run dedicated has a ton of GUI configuration before launching the server… I want to try to containerize before I take on a dedicated server.