Fix for Debian Buster System Freeze

The Problem

After the release of Debian 10 Buster, I installed it on my Dell Inspiron 3558 laptop which comes with onboard Intel HD Graphics. I am using Xfce desktop environment instead of the default Gnome desktop. After the installation, I would intermittently face the problem where the whole desktop would suddenly just freeze and stop responding to the mouse and the keyboard. Even after hours of waiting the system would never come back to the normal state and the only solution was to hard reboot the whole system. It seemed really weird as prior to installing Debian 10, I had Debian 9 running on it for more than a year and I never had any such issues.

The Solution

This issue was very difficult to reproduce as it did not necessarily follow any pattern and was really unpredictable. After researching on the Internet for days, I finally found out a solution that fixed the issue. As per the official Debian documentation on video drivers, the use of X.org xf86-video-intel driver is discouraged in favour of the newer builtin modesetting driver especially if your hardware is newer than or from 2007. This was the default setting that came with the default Debian Xfce installation. And this was what was causing the freeze. To fix it and use the old xf86-video-intel driver instead, here is what I did.

Edit the file /etc/X11/xorg.conf and update it with the following content. If the file does not exist, create a new one.


Section "Device"
    Identifier "Intel Graphics"
    Driver "intel"
    Option "AccelMethod" "SNA"
    Option "TearFree" "true"
EndSection

That’s it. I have been having this setting for 3 months now and I never had any freezing issue after that.

 

Run Alpine Linux as a Docker Container

If you have never heard of Alpine Linux before, it’s a distribution of Linux, a very lightweight one . In fact it’s so small, an empty container of Alpine Linux can be run with less than 8 MB of memory. And that’s one of the reasons why it’s extensively used in containers. Docker Hub has an official image of Alpine Linux. So it’s fairly easy to run Alpine Linux as a docker container or build one on top of it.

Download the image

To download the alpine image from Docker Hub, run the below command, assuming you already have Docker installed in your system. I am using Alpine version 3.9 which is the latest at the time of writing the post. This link has a list of available tags and versions.

docker pull alpine:3.9

Run the image in interactive mode

To run the alpine image in interactive mode, run the following command:

docker run -it --rm --name alpine alpine:3.9

This should launch an alpine container and land you at a shell prompt. The “-it” flags tells Docker that the image should be run in interactive mode and a tty should be allocated. “–rm” flag ensures that the container is removed as soon as you exit the shell and come out of the interactive mode.

To check the version of Alpine Linux while inside the shell, run

cat /etc/alpine-release

Build your own Docker image

While it can be fun to run it in interactive mode, it’s not very useful. To make something useful with docker, you need to create your custom image. In this post, I will create a custom docker image with Alpine Linux that will run a simple HTTP server and I will access the server from the host. Here are the steps.

Create the Dockerfile

Create a file with name Dockerfile and paste the following content.

FROM alpine
MAINTAINER Subhadip Ghosh
RUN apk update
RUN apk add python3
RUN echo "Hello from Alpine Linux" >index.html
ENTRYPOINT ["/usr/bin/python3", "-m", "http.server"]
EXPOSE 8000

Create the Docker Image

Run the following command to create the Docker image. Make sure you are in the same directory as the Dockerfile.

docker build -t alpine-python-server:latest .

Execute the following command to verify that an image has been created with the name “alpine-python-server”.

docker images

Run the image

To run the image that was created in the previous step, execute the following command:

docker run -d -p 8000:8000 --name test-server alpine-python-server

This command does the following things:
– Creates a container from the “test-server” image created in the previous step.
– “-d” tells docker to run the container in detached mode ie in the back ground.
– Maps port 8000 of the container with port 8000 of the host so that you can open a web browser in your host system and point to http://localhost:8000 to visit the web-server running inside the container.
– I named our container as “test-server” for ease of reference.

Visit the web-server from host

Since we have mapped the container port on which the web-server is running to the same port on host, if you visit the URL http://localhost:8000 from any web-browser from your host system, you should see something like this:

 

 

 

 

Run MySQL as Docker Container on Debian

Event though Debian is considered as one of the most stable Linux distributions out there, part of it’s stability comes from the fact that a large portion of it’s package base consists of well-tested but outdated packages. This should be a blessing most of the times but if you are a developer like me, some times you may need a latest or specific version of a package. In this case, I needed the latest version of the mysql-server package. Although official apt repository is available from MySQL to install the latest version of it on Debian, to be able to run something in containers has it’s own advantages including having the ability to run multiple versions of the same package simultaneously and can be easily cleaned up after using.

While one could use my earlier post on creating LXC containers on Debian and run MySQL inside it, it’s a lot easier to use the official MySQL docker image from Docker Hub. If you are yet to install Docker, you can follow this official documentation from Docker to install the community edition of it on Debian. Post installation of Docker, follow the below steps to run MySQL as a Docker container. To be able to connect to the docker instance of MySQL from the MySQL client or MySQL workbench available in the Debian repository, I will be using a few additional tweaks.

  1. Download the required version of MySQL docker image from the Docker Hub. I am using MySQL version 8 which is the latest version of MySQL at the time of writing the post. Replace 8 with the required tag in your case. A full list of supported tags for MySQL docker image can be found at this link.
    docker pull mysql:8
  2. Run the docker image.
    docker run --name test-mysql -e MYSQL_ROOT_PASSWORD=test -d -p 3306:3306 mysql:8 --default_authentication_plugin=mysql_native_password

    A few things to note:
    – The name of the docker instance in this case is “test-mysql”. It can be any arbitrary name.
    – “test” value has been passed as the MYSQL_ROOT_PASSWORD environmental variable while starting the container. This value will be used as the MySQL root password by the container. In absence of this value, it will generate a random root password every time you start the container and print in the log.
    – “-d” option is to run the container in the background as a detached instance.
    – The 3306 port, which is the default port of MySQL is mapped with the 3306 port of the host. This is helpful if you want to connect to the MySQL docker instance on localhost.
    – The “default_authentication_plugin” has been set as “mysql_native_password”. This is required if you want to connect to the MySQL docker instance from the MySQL client or the Workbench available in the Debian repository, which are old and does not support the new default authentication methods introduced in MySQL 8.

  3. The container should take a few seconds to initialize itself. After which, you can use the following command to connect to it.
    mysql --protocol=tcp -u root -ptest

    If you don’t have MySQL client installed in your Debian host, use the following command to install it.

    sudo apt install -y mysql-client
  4. If you want to connect to MySQL from within the container itself, use the following command
    docker exec -it test-mysql mysql -u root -ptest

That’s it. This should give you enough information to start and run MySQL as a Docker container on your Debian host. For additional information and configuration options, visit the following listed pages

Fix for incorrect rendering of Indic fonts in Firefox on Debian

Debian Stretch, the current stable release of Debian now comes with Firefox ESR 60. One strange issue I have noticed with the out of the box configuration of Firefox on Debian is that it does not correctly render the Indic fonts on the websites. Most notable issue is that it breaks the connected letters while showing. Here’s how I fixed it.

  1. Install the fonts-indic package.
    sudo apt install fonts-indic
  2. Now open Firefox and go to Preferences > General > Language and Appearance > Fonts & Colors and click on Advanced. Select the language you want to set fonts for from the “Fonts for” dropdown and select fonts with your specific language support for Serif and Sans-serif fonts, click Ok.

    Here’s how my settings looks like:

    Screenshot_2019-02-18_19-17-52

How to fix Eclipse IDE flickering issue on Debian

I am using Eclipse IDE (version 2018-12 at the time of writing) on Debian 9 Xfce and the issue with it is that the Eclipse editor windows would flicker around the edges. Sometimes so much so that it’s impossible to type inside it. Here’s how I fixed it:

First check the value of GTK_IM_MODULE in your environment by executing

echo $GTK_IM_MODULE

In my case the output was “xim”. But Eclipse expect it to be “ibus”. So enter the following command in a terminal session to set it to the value.

export GTK_IM_MODULE="ibus"

Now if you launch Eclipse from the same terminal session, you should not experience any flickering issue. If you launch eclipse from a desktop menu entry, then edit the .desktop file and put the following string in the beginning of the Exec command:

env GTK_IM_MODULE=ibus

Format USB drive after installing Debian from it

If you have used an USB drive to write iso images to before installing Debian or recent versions of Ubuntu, here are the steps to reclaim it after installation is over.

  1. Open a terminal and list the available device names using the following command:
    lsblk

    which should show you an output like the one below:

  2. Identify the device name of your USB drive. Extreme caution should be taken while at it because wrong device names can potentially wipe your entire hard disk. In this case, the USB drive that we want to format is sdb.
  3. Writing the iso image to the USB drive has made it a read-only device. To change it back, the partition table needs to broken. Issue the below command after replacing sdb with the device name identified in the previous step:
    sudo dd if=/dev/zero of=/dev/sdb bs=1M && sync

    This step might take some time to complete depending upon the size of the USB drive. So be patient. When it is over, you should see an output like the below:

  4. Next you need to create a new partition. First enter the following command after replacing sdb with your device name:
    sudo fdisk /dev/sdb

    You should see a prompt like below


    Enter n to create a new partition, press enter to go with the default options until the next Command prompt comes, then enter w to write the changes to disk.

  5. Enter the following command to check if the device partition settings have been refreshed. If not, unplug and replug the USB drive.
    lsblk

  6. Enter the following command to format the partition to FAT after replacing sdb with your device name and <label> with your label of choice.
    sudo mkfs.vfat /dev/sdb1 -n <label>

And now your USB drive should become usable again.

Creating an unpriviledged lxc container on Debian Stretch

After a few earlier failed attempts, today I was successfully able to create an unprivileged LXC container on Debian Stretch for the first time. I had experience of using LXC’s more user friendly cousin LXD before I moved to Debian but unfortunately LXD is not available on Debian yet. While LXC is more low level compared to LXD, if you just need a basic container, it’s still pretty solid. The Debian wiki on LXC container is fairly straight forward and easy to follow, but still for someone who is a novice to both Debian and LXC, it is very easy to get lost. So I am writing this post so that it can be a good place to start if you need a very basic setup.

LXC containers can be of two types depending on the level of access they have to their host system:

  1. Privileged containers will have root access to your system.
  2. Unprivileged containers will not have root access and is more secure by nature but requires a bit more configurations before you can start using them. In this guide, I will be showing how to configure and create one.

Before I start with the steps, I want to talk a little bit about my system configuration. The installed version of Debian is Stretch and the architecture is amd64. It has two users – root and test which is a non-sudo user. This guide will assume that you will modify the commands as per your system specific configuration instead of blindly copying and running.

  1. Installed the required packages as root.
    # apt install lxc libvirt0 libpam-cgroup libpam-cgfs bridge-utils cgroupfs-mount
  2. Create networking related configurations: I will be using a virtual interface to create a network bridge that will make use of of the lxc-net package which comes as part of lxc 2.0. This bridge will be shared by the container but will not be accessible from outside of the host.
    1. Create /etc/default/lxc-net with the following line:
      USE_LXC_BRIDGE="true"
    2. Run the following command as root:
      # service lxc-net restart
  3. Configuring the host system: The following steps configures the host system for creation of an unprivileged lxc container.
    1. Run the following command which should return everything as ‘enabled’ in green. If not, restart your system.
      $ lxc-checkconfig
    2. Run the following as root:
      # sh -c 'echo "kernel.unprivileged_userns_clone=1" > /etc/sysctl.d/80-lxc-userns.conf'
      # sysctl --system
    3. Run the following command as the unprivileged user to get the subuids and subguids of the current user:
      $ cat /etc/s*id|grep $USER

      In my case, it produced a output like the following:

      test:100000:65536
      test:100000:65536

      But it can be different in your case. Note the first number ie 100000.

    4. Run the following commands as root after replacing ‘test’ with your username. The first number in the range is the number we noted in the previous step, the last number should be obtained after adding 65536 to the first number:
      # usermod --add-subuids 100000-165536 test
      # usermod --add-subgids 100000-165536 test
    5. Run the following command as root to change permission of some of the directories after replacing test with your username:
      # cd /home/test
      # setfacl -m u:100000:x . .local .local/share
    6. Run the following command as root to configure the virtual network interface for your user after replacing test with your username:
      # echo "test veth lxcbr0 10"| tee -i /etc/lxc/lxc-usernet
  4. Configure LXC for your user by performing the following steps as your user.
    1. Create the lxc config folder:
      $ mkdir -p .config/lxc
    2. Configure the default template for all the future unprivileged containers after replacing 100000 with the number noted in the “Configuring the host system” step:
      $ echo \
      'lxc.include = /etc/lxc/default.conf
      # Subuids and subgids mapping
      lxc.id_map = u 0 100000 65536
      lxc.id_map = g 0 100000 65536
      # "Secure" mounting
      lxc.mount.auto = proc:mixed sys:ro cgroup:mixed
      
      # Network configuration
      lxc.network.type = veth
      lxc.network.link = lxcbr0
      lxc.network.flags = up
      lxc.network.hwaddr = 00:FF:xx:xx:xx:xx'>.config/lxc/default.conf 
  5. Reboot the system.
  6. Creating the unprivileged container: Now we are at the end of the guide and hopefully with all the right configurations to create our first unprivileged container. Run the following command as your user to create an ubuntu xenial container:
    $ lxc-create --name ubuntu -t download

    Give the following inputs when prompted:

    Distribution: ubuntu
    Release: bionic
    Architecture: amd64
  7. Start the container by running the following command:
    $ lxc-start --name ubuntu --logfile $HOME/lxc_ubuntu.log --logpriority DEBUG

    The extra log options will be helpful in debugging if something goes wrong but can be ignored from next time onward.

  8. To access the newly created container, run the following command:
    $ lxc-attach --name ubuntu

If you have followed all the steps correctly, hopefully you are now running an unprivileged container on your Debian Stretch. Please consider reading the article mentioned in Further Reading section to understand each steps used in this guide in details.

Further Reading:

  1. LXC – Debian wiki

Assigning volume up/down shortcut keys for secondary speaker in Linux

I have a wireless Bluetooth speaker that I use with my laptop running Debian 9 with Xfce. My laptop also has a primary speaker. So when I connect my Bluetooth speaker to my laptop, my laptop is actually connected to both the primary and secondary speaker at the same time. The laptop volume up/down keys will still be mapped to the primary speaker and if I wish to control the volume of the secondary speaker, I needed to open the Volume Control window from the Panel volume plugin, which was a pain if you had to do it every time.

Here’s what I did to simplify it. Debian Linux and most other major Linux distributions use pulse audio to manage all audios and there’s a command line utility that comes installed by default to manage pulse audio. It’s called pactl. When you connect a speaker to your computer, it creates an audio sink for it to manage it. To get a list of audio sinks that your computer has access to, run the following command in Terminal:

pactl list sinks

And from the output, look for the speaker you need to manage and the corresponding “Name” string. In my case, it looks like “bluez_sink.<hardware-address>.a2dp_sink” where <hardware-address> is the address by which the computer identifies the particular hardware device. The good thing about this address string is that, it remains unchanged even if you remove it and then connect it back.

Once you determine the sink name of your audio device, you can do a bunch of operation from the command line on it including setting the volume, increasing/decreasing the volume or mute it. Example: the following command will increase the sink volume by 5%

pactl set-sink-volume <sink-name> +5%

and to decrease it by 5%

pactl set-sink-volume <sink-name> -5%

Replace <sink-name> with the name you copied from the previous step.

And then you can assign keyboard shortcuts to do those operations, so that you can perform them without opening a Terminal. To do that in Xfce, go to Settings > Keyboard > Application Shortcuts and then Add a new shortcut. For other desktop environments, follow the desktop environment specific instructions.

Installing the latest Libreoffice on Debian stable

One of the few software that I like to keep always updated to the latest version on my system is Libreoffice, because of the compatibility improvements with the other office suite each new version brings. And while Debian Stable provides a solid and stable base system, the libreoffice package becomes outdated with time. A lot of the guides on updating Libreoffice in Debian on the Internet speak about installing the latest binaries from the Libreoffice website. But the main shortcoming with this approach is that updating to the next version is again a manual task. I prefer to install it from the Debian backports repository (libreoffice version in stretch-backports is at par with testing repository). Following are the simple steps to install the latest LIbreoffice on Debian Stretch (steps will be slightly different if you’re on a different version of Debian). 1. Add the Stretch backports repository to apt sources if you have not done already by adding the following line to /etc/apt/sources.list file.
deb http://ftp.debian.org/debian stretch-backports main contrib
And update repository information.
sudo apt update
2. Uninstall the older libreoffice packages and dependencies.
sudo apt purge libreoffice*
sudo apt autoremove
3. Install the latest libreoffice and a couple of other additional packages from the backport repository
sudo apt install -t stretch-backports libreoffice libreoffice-gnome libreoffice-help-en-us
And that should be all. Open Libreoffice and check the version from Libreoffice > Help > About Libreoffice which should reflect the latest version. A couple of things to note here:
  1. For Xfce and other gtk based desktop environments, libreoffice-gnome should work fine. If you are using KDE, you should install libreoffice-kde instead.
  2. If you want to access the built-in Libreoffice help in some other language than US English, replace the libreoffice-help-en-us package with the help package for your language of choice.
I hope it helps.