Setting Up A Raspberry Pi

There are many guides to setting up a Raspberry Pi available on the web. This one is geared toward projects at ITP. It assumes you’re interested in working with the Pi mainly through the command line interface, and don’t want to have to set up a monitor and keyboard every time you use your Pi. It also assumes you want to connect to the internet safely. It also explains how to install node.js as your initial programming environment.

This tutorial was written primarily with the Raspberry Pi 3 and the Pi Zero W in mind. The Pi 4 has superseded the 3 as the latest model with the greatest processing capability, and the Zero W is the least expensive networked model. All have built-in WiFi and Bluetooth, which are important to many projects. Together, these two models cover most of what an ITP student might need from a Pi. This tutorial should work for other models as well, but it’s been tested on these two.

The parts you’ll need are:

The steps you need to take are:

Installing the Operating System on an SD Card

You need an operating system for your Pi. There are many different Linux distributions that will run on the Pi. The official distribution from Raspberrypi.org is called Raspbian. It’s a variant of the Debian distribution of Linux, and comes in two versions: the full version and the Lite version. The Lite version can always be upgraded by adding software packages, so it’s a good place to start. The full version takes more space and contains additional software you may not need. Either will work.

Download the Raspberry Pi Imager from the raspberrypi.org site. Install the application once it’s downloaded. On the first screeen, click Choose OS. You’ll see a list of distributions you can use. The Raspbian Lite image is listed under “Raspberry Pi OS (Other)”as “Raspberry Pi OS Lite (32-bit)” Choose that. Then insert an SD card in your computer and click “Choose SD card.” Choose the SD card that you just inserted. Then click “write.” Installing Raspbian Lite will take about three minutes; the full Raspbian will take about ten minutes. When it’s done, you have a boot disk.

The two most convenient ways to access the Pi without a keyboard or monitor are through the serial port console or through WiFi and ssh. In order to access through the serial port, you need a USB-to-serial adapter. This is usually more reliable, as it doesn’t depend on network access, but it does require the adapter. In order to access through WiFi and ssh, you need to configure the Pi to connect to the network that your personal computer is on.

There are a couple of files you need to know about in order to enable SSH access through either the serial port or through WiFi. They are the config.txt file, a file you will create called ssh, and the wpa_supplicant.conf file, which holds your WiFi network credentials. You can create and edit all of these on your boot disk before you power up the Pi. Once the boot disk is created, remove and re-insert it into your computer and open the config.txt file in a text editor.

Enabling Serial Port Access

As of Rasbpian’s 2017-04-10 release, the Pi’s serial terminal is not enabled by default. To access the Pi via a serial terminal, you’ll need to modify the config.txt file on your boot disk. Open the file, and add the following line at the end:

enable_uart=1

UART stands for Universal Asynchronous Receiver-Transmitter; in other words, an asynchrnous serial port. That’s all you need to do to enable the serial port. See below for how to connect to the hardware.

Making a New User

You can create a new user by creating a new file in your boot drive called userconf.txt. Add this file in the boot partition of the SD card; this is the part of the SD card which can be seen when it is mounted in a Windows or MacOS computer.

This file should contain a single line of text, consisting of username:password. That is, your username, followed immediately by a colon, followed immediately by an encrypted representation of the password you want to use. NEVER put an unencrypted password in this file.

To encrypt your password, type the following on the command line of a POSIX computer (MacOS, Linus, Unix, or on Windows WSL):

 echo 'mypassword' | openssl passwd -1 -stdin

This will produce what looks like a string of random characters. It’s an encrypted version of your password. Copy it into the username:password line in the userconf.txt file. Make sure you don’t add an extra blank line to this file.

Note: Windows users may need to install openssl first. To do this, Launch Windows Subsystem for Linux (WSL) then type:

sudo apt-get install openssl

This will prompt you for your admin password, then will download the ssl application and install it in WSL for you.

Powering and Connecting to Your Pi

Insert the card into a Raspberry Pi. Connect your Pi to a 5V DC power adapter via the USB micro connection marked PWR IN. Use a power adapter that can supply at least 2A of current.

Connecting Via Serial Port

By enabling the UART above, you configured the Pi to provide a command line console via the serial port. Connect the adapter to the Pi’s I/O pins as shown below. The USB-to-serial adapter’s receive pin (RX) goes to the Pi’s transmit pin (TX) and vice versa. Connect the ground of the adapter to the ground of the Pi as well. Then connect the USB-to-serial adapter to your computer. Install any needed adapters for your USB-to-serial adapter and you should then see it show up as a serial port in whatever serial terminal application you normally use. The screen program on the MacOS and Linux command line will work best. CoolTerm works well for this on MacOS, Windows, and Linux as well.

To connect to the serial port via screen on MacOS, first you need to know the name of your serial port. Plug the adapter in, open the Terminal application, and list the ports in the /dev directory like so:

Note: From here on, whenever you see $ in front of a line, you can assume it’s the command prompt, and you don’t need to type the $, just the rest of the line.

$ ls /dev/cu.*

You’ll likely get a port name like /dev/cu.usbserial-14430 or /dev/cu.SLABtoUART. Once you know the name of your port, open screen at 115200 bits per second like so:

$ screen <portname> 115200
Diagram showing USB-to-serial adapter connected to a Raspberry Pi through their respective transmit (TX) and receive (RX) pins. The adapter's ground pin is also connected to the Pi's ground pin.
Figure 1. USB-to-serial connection to a Raspberry Pi. Click to enlarge.
Diagram identifying each of the I/O pin connections for the Raspberry Pi.
Figure 2. I/O pin connections for the Raspberry Pi. Click to enlarge.

Once you’ve opened a serial connection at 115200 bps, and press the spacebar a few times. You’ll get a login prompt like so:

Raspbian GNU/Linux 8 raspberrypi ttyAMA0
raspberrypi login:

Now you’re ready to log in.

Logging In To The Command Line Interface

The default login for the Raspbian OS is pi, and the default password is raspberry. If you didn’t create a username and password of your own, you can use this. Use these to log into your Pi. When you’re logged in, you’ll get a prompt like this:

The programs included with the Debian GNU/Linux system are free software;
the exact distribution terms for each program are described in the
individual files in /usr/share/doc/*/copyright.

Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent
permitted by applicable law.
Last login: Wed May 31 22:24:04 2017 


pi@rasbperrypi: ~ $

Configuring Your System

Once you are logged in, you need to configure the operating system for general use. This includes changing the default password and administrative user, changing the default hostname, setting the interfacing options, and expanding the filesystem on the SD card. To start, type:

$ sudo raspi-config

Note: most of the commands you’ll use on the pi will be run though sudo, the superuser do command. Sudo enables users to use administrative commands, making sure they’re a part of the system’s administrative users group, also called sudo. The system will ask for your password whenever you use sudo.

You’ll get a menu which you can scroll through with the arrow keys and select items with the enter key, as shown below.

Screenshot of the raspi-config main menu during installation.
raspi-config main menu. Click to enlarge.

Here are the most important things to take care of:

First choose System Options.

  • In this menu, you should Change Password if you’re still using the default pi/raspberry combination, and follow the prompts to change your password. If you made your own username with the userconfig.txt file, there’s no need to do this.
  • You can also Change Hostname, and change the name of your system from raspberrypi to something meaningful to you.
  • You can also set the SSID of your wireless network and the password, or follow the steps below if you’re using an enterprise network.

Next choose Interfacing Options.

  • If you didn’t make an ssh file on your SD card before booting, enable ssh. This will allow you to log in remotely via ssh.
  • If you plan to use a camera, or the I2C or SPI buses to communicate with external hardware, enable those options.

Finally choose Advanced Options, and expand the filesystem. This will make more room on your SD card for the system. This will finish by asking you to reboot your Pi. Choose Yes to reboot.

From now on, if you’re using the ethernet-over-USB option or logging into your Pi over a network using ssh (which we’ll get to shortly), you’ll need to log into your-username@your-pi-name.local (change your-pi-name to the name you chose).

Changing Defaults To Increase Security

Anyone who’s used a Pi knows the default username (pi) and password (raspberry) and the default device name (raspberrypi), so it’s a good idea to  change these to make your Pi harder to find and harder to break into. For more advice on security hardening your Pi, see these tips.

First, if you didn’t use the userconfig.txt file above to make a custom user, you should add a new user. Change username below to a name you want to use:

$ sudo adduser username

This will ask you twice for a password for the new user and ask you to fill in some identifying details. You can skip any question by hitting enter. Next, add your new user to the sudo group so it can act as a superuser:

$ sudo adduser username sudo

To access some of the Pi’s hardware, you may need to add your new username to some other groups, as follows:

pi       User-specific group. A group is automatically created for 
         each new user; you can ignore this.
adm      Allows access to log files in /var/log and using xconsole
dialout  Allows access to serial ports/modem reconfiguration, etc.
cdrom    Enables access to optical drives.
sudo     Enables sudo access for the user.
audio    Allows access to audio devices like microphones and soundcards
video    Allows access to a video devices, e.g. framebuffer, videocard, webcam
plugdev  Enables access to external storage devices
games    Many games are SETGID to games so they can write their high score files.
users    A Pi-specific group enabling access to 
         /opt/vc/src/hello_pi/ directory and contained files.
input    Appears to give access to the /dev/input/mice folder and nothing else.
netdev   Enables access to network interfaces
gpio     Pi-specific group for GPIO pin access.
i2c      Pi-specific group for I2C access. 
         Generated after installing i2c-tools.
spi      Pi-specific group for the SPI bus.

You can do this group by group with:

$ sudo adduser username groupname

or you can add many at a time like so:

sudo usermod -a -G adm,dialout,cdrom,sudo,audio,video,plugdev,games,users,input,netdev,gpio,i2c,spi username

For security reasons it’s a good idea to add as few groups as you actually need. So if your project only uses GPIO and SPI, for example, add those groups and not the others.

When you’ve added your new user and given it permissions, log out by typing logout or exit, then log back in as the user you just created:

$ssh username@your-pi-name.local

Now make sure the root account is disabled by locking it like so:

$ sudo passwd -l root

If you need to unlock it later you can do so by typing:

$ sudo passwd -u root

Next delete the default  pi user like so:

$ sudo deluser --remove-home pi

You’ll get a message: Warning: group `pi’ has no more members. Don’t worry. When you delete the pi account, the system will delete the corresponding pi group automatically. Now that the default pi user is gone, there’s less chance that someone will guess your username and gain access to your Pi.

Configuring After Changing Users

Note that many software packages install per user, rather than system-wide, so it’s a good idea to make sure you’ve got the user configuration you want before you install firewalls, development software, or other tools you plan to use. You don’t want the nasty surprise of installing software as one user only to find it gone when you change users.


Connecting To the Network via WiFi

The Pi Zero W and the Pi 3 and Pi 4 and later models all have built-in WiFi and the drivers are included in the Raspbian distributions. To check that yours is working, type

$ iwconfig wlan0

If you get a response that begins like this:

wlan0 IEEE 802.11bgn Nickname:

Then you know the radio is there and working. If not, your Pi’s wifi might need to be unblocked. This is often the case with 5GHz radios like the Pi 3 B+, as the allowable frequencies are different from country to country, so the manufacturer sometimes ships units with the wifi disabled.  If so, try this:

$ sudo rfkill unblock wifi

Now try this command to see nearby WiFi hotspots:

$ iwlist wlan0 scan | less

You will get a list of WiFi hotspots nearby and their credentials. It’s piped through  the less utility to paginate it. You should see a list of all nearby WiFi access points, with their details. You can see the listings page by page using the spacebar, and close the list by typing q.

Getting the MAC address of the Pi’s WiFi Radio

You might also need the MAC address of your Pi in order to connect to an institutional network. For example, you can’t connect a Pi at ITP until you’ve registered its MAC address at computer.registration.nyu.edu. To get the MAC address of your Pi’s WiFi, type the following once you’re logged in:

$ ifconfig wlan0 | grep ether

You’ll get a response like this:

ether b8:27:eb:aa:bb:cc txqueuelen 1000 (Ethernet)

Take that MAC address and register it with your institution. Then modify the wpa_supplicant.conf file to connect to the institution’s network as explained below.

Network Configuration by Editing wpa_supplicant.conf

If you didn’t set the network name and password using the raspi-config tool, you can do it like so: Create a file called wpa_supplicant.conf that stores your wifi configuration. It belongs in the /etc/wpa_supplicant directory. To create or edit it, type:

$ sudo nano /etc/wpa_supplicant/wpa_supplicant.conf

You should see something like this:

ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev
update_config=1
country=GB

network={
        ssid="your_network_name"
        psk="your_password"
}

You never want to store your password in plaintext, so you should generate an encrypted version (called a hash) of your password like so:

$ wpa_passphrase your_network_name your_password

This will generate a response like this:

network={
 ssid="your_network_name"
 #psk="your_password"
 psk=6a24edfec4d204601b6e1f409630702...
}

Delete the line with your password in plaintext, then use this in place of the network={...} block in the wpa_supplicant.conf file and you should be good to go. The wpa_supplicant.conf file can contain network blocks for multiple networks, so if you want to add your home network as well, you can. On startup, the Pi will go through the list and try to connect to each one in turn, stopping when it succeeds. So if you have two networks available in one location, then make sure to put the default one first.

Configuring For An Enterprise Network

If you’re connecting to an enterprise network like the one at NYU, your network configuration is a bit more complex. If you don’t need to do this, skip to the next section.

Many enterprise networks use the Protected Extensible Authorization Protocol, or PEAP, to manage multiple user logins. Here’s the wpa_supplicant.conf file for a PEAP network using MSCHAPv2, a common authentication protocol used with PEAP:

ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev
update_config=1
country=US

network={
  ssid="network_name"
  key_mgmt=WPA-EAP
  eap=PEAP
  proto=WPA2
  phase2="auth=MSCHAPV2"
  anonymous_identity="your_username"
  identity="your_username"
  password=your_password
}

Put your network name in for the ssid and your username for the anonymous_identity and the identity. Again, notice that the username and password are stored in cleartext. To make a hash for the password this time, do the following:

$ echo -n your_password | iconv -t utf16le | openssl md4

You’ll get a reply like this:

(stdin)= dad3329614566332455803ad3b...

Replace your_password in the wpa_config.conf with this hash like so:

  password=hash:dad3329614566332455803ad3b...

Once that’s set, you’ve enabled your Raspberry Pi to access the network configuration you set up, and you’ve saved the configuration to disk. The WiFi radio should start scanning for networks. You can check that you’re connected using ifconfig wlan0 and iwconfig wlan0 as you did before.

Connecting Via WiFi and ssh

To connect via WiFi and ssh instead of serial, you need to have created the ssh file and the wpa_supplicant.conf file mentioned above. Your Pi should connect to the network that you configured it for after it boots up. This might take a minute or two. When the Pi is booted up, make sure your personal computer is on the same WiFi network, then open the command line interface on your personal computer and type:

ssh username@your-pi-name.local

Alternately, you can use the IP address of your Pi if you know it, instead of raspberrypi.local. You should get a response like this:

username@your-pi-name.local's password:

Enter your password and you’ll be logged in.

Testing Your Network Connection with curl

You can test your network connection by making a web request. The command line program curl is a good way to do this. Type:

$ curl http://www.example.com

You should get a response that includes a lot of HTML,
ending with the following:

<body>
 <div>
 <h1>Example Domain</h1>
 nts. You may use this
 domain in examples without prior coordination or asking
 for permission.</p>
 <p><a href="http://www.iana.org/domains/example">More
 information...</a></p>
 </div>
 </body>
 </html>

If you got this result, your Raspberry Pi is now connected to the internet.

Deleting Your History File

At this point you have entered some sensitive information on the command line (like your passwords) and it gets saved in a file called .bash_history. To see this file, type:

$ sudo less ~/.bash_history

You can scroll through and see everything you’ve typed. This is useful, because you can just hit the up arrow on the command line to repeat older commands, but it’s also a security risk. You may notice the line where you typed in your password, for example. You can open this file with the nano text editor and delete any line with cmd-k. To save and close the file, type cmd-x, then y to confirm the change.

Updating the Operating System

Next you should upgrade the operating system to make sure you have the latest patches for all the software in it. Make sure you’re connected to the internet, because you’re going to update the list of installed software packages and upgrade them from the Raspbian package repository. You’ll use APT, the advanced packaging tool, to do this, via its apt-get utility. Each of these commands will take a long time. Type:

$ sudo apt update

You should get this message at the end:

Reading package lists... Done

If you get an error, check your network connection. The most likely error is that it didn’t get all the updates because it didn’t have a network connection. If it says you don’t have enough disk space, make sure you expanded the filesystem using raspi-config earlier. When you’ve updated the package lists, Type:

$ sudo apt upgrade

This will upgrade any installed software packages. This will take even longer than the update, and will ask you to confirm that you want to upgrade all the software. Type y to do so. Once this is complete, you’ll have the latest versions of all the tools in your Raspbian distribution.

Configuring a Firewall

If you’re connecting to the internet, it’s wise to set up a firewall to control incoming and outgoing network connections. Understanding network ports and connections is a topic larger than this tutorial can cover. For now, we’ll assume you know that networked devices connect to each other on ports, that ports are numbered and can be incoming or outgoing, and that network traffic can use a number of transport protocols, most commonly TCP and UDP.

The firewall rules explained here will block access to all incoming traffic except that on port 22, which is the standard port for ssh connections;  ports 80, 443, which are the standard ports HTTP traffic; and port 8080, which is a common port for node.js servers. Based on this example, you should be able to add or delete ports to your firewall configuration when you need them.

For more on ufw, see

First you need to install ufw. Assuming you’ve updated your package manager, start by installing ufw:

$ sudo apt install ufw

Once it’s installed, you can set defaults to allow outgoing traffic and deny incoming:

$ sudo ufw default allow outgoing
$ sudo ufw default deny incoming

This would disconnect your ssh connection if you enabled it now, so you might want to enable ssh connections before you enable the firewall. The following line will enable TCP connections on port 22, the default ssh port:

$ sudo ufw allow ssh

If you’re planning to run an HTTP server, or an HTTPS server, you’ll need to enable them as well. You can specify not only the application (http, https), but also the transport protocol, like so:

$ sudo ufw allow http/tcp
$ sudo ufw allow https/tcp

More specific rules ensure that someone won’t try a sneaky attack like flooding UDP packets through your open HTTP ports. If you’re planning to do custom server development, you might want to enable the ports you’ll use for that as well. These settings are typical for node.js development. 

$ sudo ufw allow 8080/tcp
$ sudo ufw allow 8081/tcp

Port 8081 is used by the p5.serialserver, which is common at ITP.

If you plan to use VNC to connect to the Pi desktop remotely, you’ll need to enable port 5900 as well.

Once you’ve configured your firewall, you enable it like so:

$ sudo ufw enable

You should reboot once you do this, to check that everything is in order. Once enabled, you can get a status report from ufw like so:

$ sudo ufw status

You should get a reply like this:

Status: active

To                         Action      From
--                         ------      ----
22/tcp                     ALLOW       Anywhere                  
80/tcp                     ALLOW       Anywhere                  
443/tcp                    ALLOW       Anywhere                  
8080/tcp                   ALLOW       Anywhere                  
8081/tcp                   ALLOW       Anywhere                  
22/tcp (v6)                ALLOW       Anywhere (v6)             
80/tcp (v6)                ALLOW       Anywhere (v6)             
443/tcp (v6)               ALLOW       Anywhere (v6)             
8080/tcp (v6)              ALLOW       Anywhere (v6)             
8081/tcp (v6)              ALLOW       Anywhere (v6)  

Now you’ve got a reasonably secure setup for a networked device.

Updating your Programming Environment

Now that you’ve got the operating system installed and upgraded and the network connections in place, the next step is to make sure you have the right programming tools in place. At ITP, node.js is a popular development environment for networked applications. You’ll also want to install git, since it’s used frequently for software version management. If you don’t want to use node.js, the section below about git and the package manager may still be useful.

Note: make sure you’ve created a unique user before you install custom software like this. Also, many open source software packages (like node.js) compile after download, so do your software config on the fastest Pi you can. You can always transfer your SD card to a slower Pi.

To check if any software tool is already installed, you can use the which command like so:

$ which git

You’ll get a reply like so:

/usr/bin/git

If you get no reply, then the software is not installed. You can check if the software is listed in the package repository like so:

$ sudo apt-cache show packageName

Replace packageName with the name of the package you’re looking for. If it’s there, you’ll get all the details on it, and you can install it using apt-get, like you’ll do for git next.  Install git like so:

$ sudo apt install git

This will automatically install the version of git that’s listed in the Raspbian package list.

Upgrading node.js

In this section, you’ll remove the installed version of node.js from the Rasbpian distribution and upgrade  to a more modern version. First, remove all node and npm files already on your Pi. These instructions come from this gitHub repo. Note that node.js stopped support for the processor on the Pi Zero as of version 12.0.0, so you’ll use an older version:

$ wget -O - https://raw.githubusercontent.com/sdesalas/node-pi-zero/master/install-node-v16.3.0.sh | bash

Check the version of node.js that you installed like so:

$ node --version

You should get this reply:

v16.3.0

Now you’ve got a working, reasonably secure Pi, and a programming environment with which to program it. Congratulations! Finally, reboot or shutdown:

$ sudo reboot

or

$ sudo poweroff

Back Up Your Custom Installation

At this point you may want to make a copy of the SD card using Etcher as you did at the beginning. Then you’ll have a customized image on which you can build other things. Since you’ll likely customize your system further for each application, it’s helpful to have a base installation from which to start. The ApplePiBaker app makes it easy for MacOS users to do backups simply.

Remote File Access

Remote file editing can be a pain on a Pi. If you’re using Visual Studio Code, here’s a set of instructions for the remote VSCode plugin that works well on the Pi. They have to be on the same network, but it can make editing much easier. Here’s the summary version:

  • Install Visual Studio Code on your personal computer and run it
  • Click the Extensions icon in the right side toolbar and search for Remote VSCode. Install it and relaunch VS Code.
  • On your Pi, install rmate like so:
$ sudo wget -O /usr/local/bin/rmate https://raw.github.com/aurora/rmate/master/rmate

$ sudo chmod a+x /usr/local/bin/rmate
  • In VS Code, Open the command palette (CTRL+P for Windows, CMD+P for MacOS) and type
>Remote: Start Server
  • This will start the VSCode live share server.
  • Get your Pi’s IP address.
  • Now open the terminal pane in VS code (CTRL+` for MacOS and Windows) and type (replace PI_IP_ADDR with the Pi’s IP address):
$ ssh -R 52698:localhost:52698 PI_IP_ADDR
  • This will log your computer into your Pi. You can then use rmate to open and edit files. For example, if there’s a file called myFile.txt, you can edit it by typing
$ rmate myFile.txt
  • The file will open in VSCode, and you can edit and save, and it’ll automatically get saved on the Pi. Simple!