Administration

Running Logitech Media Server in a chroot on Debian Wheezy

Posted on

Oh no, another chroot-tutorial! This time Logitech Media Server gets jailed. If you only have it running locally it’s not necessary to imprison it, but if you have it running on a public IP it is. Big software with plugins and open ports just creates this chroot-urge deep inside of me. It’s quick and easy, read on!

So, what do I want?

  • A minimal Debian at /var/local/squeezebox
  • A Logitech Media Server chrooted to that directory running as a certain user
  • Both the minimal Debian and the Media Server should be easily upgradeable through apt and dpkg

Installation

Install “cdebootstrap” and run these commands as root:

cdebootstrap -f minimal --include apt,apt-rdepends wheezy /var/local/squeezebox

Afterwards there’ll be a minimal Debian in /var/local/squeezebox.

Fetch the latest Media Server Debian package here and put it into our new chroot.

Then, start a chrooted bash by running this:

chroot /var/local/squeezebox /bin/bash -l

Then, we’ll do some setting up:

# To avoid some errors
export LANG=C.UTF-8
 
# Install the deb, there'll be unresolved dependencies!
dpkg -i logitechmediaserver_7.7.3_all.deb
 
# Make sure we're getting security updates
echo "deb http://security.debian.org wheezy/updates main" >> /etc/apt/sources.list
 
# Fetch available packages
apt-get update
 
# Make sure everything required by logitechmediaserver is pulled in
apt-get -f install

In the next step we’ll change the UID and GID of the user “squeezeboxserver” to the “real” UID:GID we want the server to be running as. In my case, it should be seb:seb (1000:1000 on my system).

Then (still in the chrooted shell):

# First, remember the original UID, it was 101 on my system
id -u squeezeboxserver

# The user is in group nogroup, let's put it into a dedicated group
addgroup squeezeboxserver
usermod -g squeezeboxserver squeezeboxserver

# Now change it to the ids it should be running as
usermod -u 1000 squeezeboxserver
groupmod -g 1000 squeezeboxserver

# Re-own its files to this uid:gid. Change 101 to whatever the command in line 2 spat out 
find / -uid 101 -exec chown squeezeboxserver:squeezeboxserver {} \;

As a precaution, let’s remove the suid-bit from all binaries that have it. The following command is meant to be run in the chrooted shell, be careful!

find / -perm +6000 -type f -exec chmod -s {} \;

Removing “unneeded” packages

This step is not recommended, it’s just an “academic exercise”. I just keep it here as reference. Go to the next step.

It removes all the packages that aren’t required for operation and this will break updating at some point. I was curious how to go about it and this is the result. Again, be careful, this is meant to be run in the chrooted shell!

# Get a list of packages required for the packages mentioned on the command line
apt-rdepends coreutils bash findutils sed apt dpkg libpam-runtime logitechmediaserver 2>/dev/null | grep -v '^ ' | sort | uniq > debs-needed
 
# Get a list of installed packages
dpkg-query -W -f='${Package}\n' | sort | uniq > debs-installed
 
# Remove those packages which are in debs-installed but not in debs-needed, possibly removing essential packages
dpkg -P --force-remove-essential `comm -23 debs-installed debs-needed`
 
apt-get clean

Starting the server

We’re going to start the server as the specific user directly, no root-privileges are ever needed. The following commands are run outside the chroot (hit Ctrl-D if you’re still in the chrooted shell).

There’s just one more thing to take care of, chowning the run-directory for the start-stop-daemon’s PID-file:

chown -R seb:seb /var/local/squeezebox/run/

Then we can start the server by running this as root:

chroot --userspec=1000:1000 --groups=1000 /var/local/squeezebox /etc/init.d/logitechmediaserver start

I prefer dropping the user-privileges at this stage. It’s probably safe without the userspec/groups-stuff because the start-script will drop its rights through start-stop-daemon anyway, but better safe than sorry.

Chroot’s man-page claims that names instead of numeric ids can be used, but it doesn’t seem to work. There’s one more catch: Without the –groups-parameter, the resulting proc will still have 0 in its groups! Bug or feature?

That should be all. If you want the server to be started at boot-time, a simple script like

#!/bin/sh
chroot --userspec=1000:1000 --groups=1000 /var/local/squeezebox /etc/init.d/logitechmediaserver $1

in /etc/init.d/ of the “real” filesystem should do the job.

For upgrading, simply launch a chrooted bash as shown above and use dpkg and apt-get as always.

That’s all for today!