In the house
In this new series of articles, I’ll show you how to install all sorts of things in the comfort of your house. Yes, you’ve heard that right: the hardware will be located inside of your house. We’ll be installing software on things that we can actually see, touch and sometimes smell… How exciting is that? It’s like we’re back to 2003! Zero cloud, amigo.
For the first installment of this series, I’ll talk about the most popular SBC (single-board computer) in the market today: the Raspberry Pi. Every time I’m setting up a new RPi, I need to go back to my notes and review the whole process again and again and again and again. So, I decided to just write it down once and for all and share it with you. Here it is.
The overall process is quite simple: download an operating system compatible with the RPi (I’ll be using Raspbian Stretch Lite); flash the OS image into an SD card; have fun!
- an RPi (duh!);
- an SD card (or mini SD card, depending on your RPi model) of at least 4 GB;
- an SD card reader/writer.
- basic GNU toolset. I’ll assume you’re running a *nix OS on your personal computer;
Flash OS into SD card
Prepare SD card
Before plugging the SD card into your personal computer, use
dmesg to list the peripherals currently attached to the machine:
watch "dmesg | grep sd | tail -10"
Leave that command running and insert the SD card into the SD card reader/writer’s slot. Once you do that, you should notice the terminal’s screen display some different output. In my case, the output shows that the newly attached SD card is mapped to the
Every 2.0s: dmesg | grep sd | tail -10 Sun Jul 08 14:06:23 2018 [ 2991.442774] sd 5:0:0:0: [sdb] 7744512 512-byte logical blocks: (3.97 GB/3.69 GiB) [ 2991.443797] sd 5:0:0:0: [sdb] Write Protect is off [ 2991.443803] sd 5:0:0:0: [sdb] Mode Sense: 03 00 00 00 [ 2991.444879] sd 5:0:0:0: [sdb] No Caching mode page found [ 2991.444886] sd 5:0:0:0: [sdb] Assuming drive cache: write through [ 2991.449914] sdb: sdb1 sdb2 [ 2991.453579] sd 5:0:0:0: [sdb] Attached SCSI removable disk [ 2991.984276] FAT-fs (sdb1): Volume was not properly unmounted. Some data may be corrupt. Please run fsck. [ 2992.033111] EXT4-fs (sdb2): recovery complete [ 2992.033121] EXT4-fs (sdb2): mounted filesystem with ordered data mode. Opts: (null)
You can hit
CTRL+c to exit the command.
Linux will usually mount the SD card as soon as we plug it in, but we won’t leave it mounted like that, because we want to override its contents in a safe way. To unmount it, first find the local partition(s) it’s mounted to:
$ df -h | grep sdb /dev/sdb1 63M 21M 43M 33% /media/space-ghost/boot /dev/sdb2 3.6G 978M 2.5G 29% /media/space-ghost/292637e1-4ce7-46df-2a00-ad787c2517bb
To unmount those partitions, use the command
umount on each of their associated mount points (replace
sudo umount -l /dev/sdb1 sudo umount -l /dev/sdb2
df -h | grep sdb should now return an empty result.
Download OS image
The following commands will download Raspbian Stretch Lite (~350 MB archived as a zip file) from the official website and unzip it into your
wget https://downloads.raspberrypi.org/raspbian_lite_latest -O ~/Downloads/rpi.zip unzip ~/Downloads/rpi.zip -d ~/Downloads
.img file will be placed in the
~/Downloads directory. For the Raspbian Stretch Lite OS, that file is approximately 1.8 GB, so my 4 GB SD card should be more than enough for the new OS installation.
Flash OS image into SD card
This step will rely entirely on the
dd command. Don’t let this cute reduplication deceive you—
dd will regretlessly override everything you have in your SD card. Make sure the output parameter (
of) is pointing to your SD card’s device (example:
/dev/sdb). You don’t want to wipe out your computer’s hard drive, do you? This is the command’s blueprint:
dd bs=<bytes-per-instruction> if=<full-path-to-os-image> of=<sd-card-device-name> status=<stderr-information-level>
In my case, I want to write 4 MB at a time—too fast is too scary—and output the progress of the command to
STDERR. Note that
if (input file) and
of (output file or device) will entirely depend on where the OS image was placed in your computer and where your SD card is mounted, respectively.
sudo dd bs=4M if=~/Downloads/2018-06-27-raspbian-stretch-lite.img of=/dev/sdb status=progress
This is the result I get when running the command with the
1858076672 bytes (1.9 GB, 1.7 GiB) copied, 154.072 s, 12.1 MB/s 444+0 records in 444+0 records out 1862270976 bytes (1.9 GB, 1.7 GiB) copied, 198.527 s, 9.4 MB/s
Same amount of records in and out—that looks like success to me. The OS part is done, but… (There’s always a but.)
Enable the SSH server
If you were to plug the SD card into the RPi now, turn it on, connect it to an ethernet cable and try to access it from another computer in the LAN, you wouldn’t be able to access it. That’s because all ports are closed by default. If you don’t believe me,
nmap will convince you. Assuming your RPi’s IP address in the LAN is
192.168.0.19, try this from your local computer:
$ nmap -PN 192.168.0.19 Starting Nmap 7.01 ( https://nmap.org ) at 2018-07-08 14:56 EDT Nmap scan report for 192.168.0.19 Host is up (0.013s latency). All 1000 scanned ports on 192.168.0.19 are closed Nmap done: 1 IP address (1 host up) scanned in 0.22 seconds
The RPi is up and its networking stack is functioning as expected, but all ports are closed. By the way, that’s by design. According to the official documentation, “As of the November 2016 release, Raspbian has the SSH server disabled by default.”
So, unless you want to connect a monitor and a keyboard to a headless RPi (shame on you!), you’ll have to enable the SSH server. “HOW AM I SUPPOSED TO ENABLE THE SSH SERVER IF I NEED SSH FOR THAT?!” Yeah, yeah, I hear you—it’s a chicken and egg situation. The folks behind Raspbian were kind enough to add a bootloader instruction that starts the SSH service every time the RPi is turned on. All we need to do is find the boot partition in the SD card and place an empty file called
ssh in there. Let’s do that now.
Remove the SD card from your computer and repeat the process described in the beginning of this article. This is the sequence we want to play this time:
- remove SD card from slot;
watch "dmesg | grep sd | tail -10";
- plug SD card back in;
- take note of its mount points with
df -h | grep sdb. (They’ll probably be the same.)
As you may remember, the last step (
df -h) will output two entries, the first one being the boot partition. I know that because its associated path contains the word boot in it:
$ df -h | grep sdb /dev/sdb1 63M 21M 43M 33% /media/space-ghost/boot /dev/sdb2 3.6G 978M 2.5G 29% /media/space-ghost/202638e1-4ce4-45df-9a00-ad725c2537bb
All that’s left to do is create the dummy ssh file inside the directory associated with that partition:
sudo touch /media/space-ghost/boot/ssh
No need to
chown—nada. Just leave the file there; unmount the two partitions as shown earlier; and remove the SD card from the slot. Now for the fun part.
Turn it on
Plug the SD card into the RPi and turn it on—don’t forget the Ethernet cable. Give a few minutes and try to SSH into it (username is
pi and password is
raspberry). To find the RPi’s IP in the LAN, you can resort to our good friend
nmap again. Assuming your router is configured to use the
192.168.0.* address range, you can try this from your local computer:
nmap -sP 192.168.0.1/24
The RPi’s IP address should be somewhere in the middle of the output from that command. The full SSH command will look something like this:
Raspbian comes with a configuration tool called raspi-config, which allows us to tweak values for all sorts of system-level functionalities. While these steps are not mandatory, I highly recommend that you follow them. To access the configuration tool, just run
sudo raspi-config from the terminal.
Change the system timezone
To change the OS timezone, scroll down to menu item 4 (Localisation Options), select option I2 (Change Timezone) and follow the instructions.
As mentioned before, Raspbian Stretch Lite will take up approximately 1.8 GB of the SD card, which means that the remaining space won’t be used by the operating system. If you plan on installing extra software on the RPi or even keeping the OS updated with the latest system packages, it’s a good idea to expand its root filesystem so that you can use the SD card to its full capacity and avoid out of space issues. To do that, scroll down to menu item 7 (Advanced Options) and select option A1 (Expand Filesystem). Just follow the instructions and restart Raspbian. On the next system reboot, the OS will have access to the entire space in the SD card.
After the reboot, you may want to update the system with the usual sequence:
sudo apt update sudo apt upgrade
In cases where the RPi should be accessible from the Internet (or if you don’t trust the people who frequent your house…), I recommend you change the default user’s password and only accept SSH connections through an encrypted key.
To change the default user’s password, go to raspi-config’s option 1 (Change User Password) and follow the instructions.
To secure the SSH connection, start by adding your public SSH key to the RPi’s default user (
pi). Assuming you already have SSH keys set up for your local user, you can try something like this from your personal computer’s terminal (replace the IP address with your RPi’s IP address):
That’s right: you do not need to create a new user on the RPi to match the username on your personal computer—as long as the private key on your computer matches the public one on the RPi, SSH will let you in.
You can then—and only then!—disable password authentication. Back to the RPi’s terminal, run the following commands:
sudo sed -i.bak 's/^#PasswordAuthentication\s*yes$/PasswordAuthentication no/' /etc/ssh/sshd_config sudo systemctl restart sshd
Note that the first command (
sed) will make a backup copy (
/etc/ssh/sshd_config.bak) of the SSH server’s config file. Keep it there for future reference.
On Raspbian, the RPi’s hostname is set to raspberrypi by default. In the event that you add other RPis to your LAN, customizing this value will avoid hostname conflicts and let you easily identify those devices. This will not only simplify your life but also let you use port-forwarding rules and network protocols that rely on hostnames to function properly.
To change your RPi’s hostname, go to item 2 (Network Options), select option N1 (Hostname) and enter a valid hostname.
Create an OS backup
Now that you have your RPi in the state you want it to be (SSH is configured, timezone is set up etc.), consider making a backup of the whole system. This way, in case the SD card gets corrupted or you just want to replicate that setup onto another RPi, all you need to do is grab the backup
.img file and replay it on a new SD card. That would take you even less then 20 minutes!
In order to achieve this, we will once more resort to the
dd command. This time around, we want to copy the contents of the SD card into an image file that we’ll save in our local computer. So, turn off the RPi; remove the SD card; and then execute the following steps:
watch "dmesg | grep sd | tail -10";
- plug SD card into computer;
- take note of its device name (eg.:
ddto copy the SD card’s contents into a local
sudo dd bs=4M if=/dev/sdb of=~/my-headless-raspbian-backup.img status=progress
That’s it. You now have a full backup of your SD card.
Now that you have an RPi set up and running, the sky is the limit—you can implement all sorts of DIY projects on it, from network firewalls to Kubernetes clusters. Those will come in future installments of this series.