Install Rocky Linux on Raspberry Pi for Remote Access

3 ways to get it ready to be remotely accessed in the first boot

image

This guide demonstrates three ways of providing a Raspberry Pi with a fresh new Rocky Linux installation ready to be accessed via SSH, without ever plugging a screen or a keyboard into the device to do the initial setup.

You don’t need to be an experienced Linux user to follow this guide! It is just required that you are a curious person with basic command-line interface skills such as executing commands with sudo privileges and editing text files.

This blog post describes the step by step on how to achieve that:

Step 1. Install Rocky Linux

Step 2. Find or configure the IP address

  • Case A. Find the IP address (…or…)

  • Case B. Configure a static IP address using a helper (…or…)

  • Case C. Configure a static IP address manually by creating a script

Step 3. SSH into the Raspberry Pi

Requirements:

(At the time of this writing I am using a Raspberry Pi 4b as the device, and Rocky Linux v8.5.)


The Shortcut!

If you just want to get it done as quick as possible, this is the shortcut:


Step 1. Install Rocky Linux

You could perform a quick install by simply downloading the Raspberry Pi(aarch64) image and flashing it into the MicroSD card using Balena Etcher, or you can perform the installation manually as described below:

Identify the MicroSD card

  • Do not plug it into your computer and run the command:

    lsblk

  • Take note of the output, then plug the MicroSD card into your computer and run lsblk again. Sample output:

    NAME   MAJ:MIN RM   SIZE RO TYPE MOUNTPOINT
    sda      8:0    0 223,6G  0 disk 
    ├─sda1   8:1    0   600M  0 part /boot/efi
    ├─sda2   8:2    0     1G  0 part /boot
    └─sda3   8:3    0   222G  0 part /home
    sdb      8:16   0 465,8G  0 disk 
    └─sdb1   8:17   0 465,8G  0 part 
    sdc      8:32   0 465,8G  0 disk 
    └─sdc1   8:33   0 465,8G  0 part 
    sdd      8:48   1  59,5G  0 disk 
    └─sdd1   8:49   1  59,5G  0 part /run/media/rossijonas/67E7-60D4
    zram0  252:0    0     4G  0 disk [SWAP]
    
  • Notice that sdd is the 64gb MicroSD card (in this case), and it has one partion sdd1 mounted.

    From now on, you may copy/paste the commands, but remember to replace sdd by the MicroSD disk name you found.

  • Unmount the partition(s):

    sudo umount /dev/sdd1

    or

    sudo umount /dev/sdd?* (If the device has more than one partition mounted.)

Install Rocky Linux Image Into the MicroSD Card

  • Download the Rocky Linux’s Raspberry Pi(aarch64) image.

  • Switch into a root shell:

    su -

  • Use xzcat to flash the Rocky Linux image into the MicroSD card (as suggested in Rocky Linux for Raspberri Pi Readme file):

    xzcat /home/rossijonas/Downloads/RockyRpi_8.5_20211116.img.xz > /dev/sdd

    It may take a few minutes but once the task is finished Rocky Linux is installed on the MicroSD card.

Verify the partitions installed

  • Run sudo umount /dev/sdd?* just to make sure the MicroSD card is unmounted.

  • Remove and re-insert the MicroSD card into your computer.

  • Run lsblk to verify the presence of the new partitions. Sample output:

    NAME   MAJ:MIN RM   SIZE RO TYPE MOUNTPOINT
    sda      8:0    0 223,6G  0 disk 
    ├─sda1   8:1    0   600M  0 part /boot/efi
    ├─sda2   8:2    0     1G  0 part /boot
    └─sda3   8:3    0   222G  0 part /home
    sdb      8:16   0 465,8G  0 disk 
    └─sdb1   8:17   0 465,8G  0 part 
    sdc      8:32   0 465,8G  0 disk 
    └─sdc1   8:33   0 465,8G  0 part 
    sdd      8:48   1  59,5G  0 disk 
    ├─sdd1   8:49   1   286M  0 part /run/media/rossijonas/B682-A2DB
    ├─sdd2   8:50   1   488M  0 part 
    └─sdd3   8:51   1   2.8G  0 part /run/media/rossijonas/__
    zram0  252:0    0     4G  0 disk [SWAP]
    

    From the Rocky Linux’s RaspberryPi(aarch64) image’s Readme file:

    - Partition layout: 300 MB /boot , 512 MB swap, ~2800 MB rootfs. Able to fit on a 4 GB or larger sd card.

    Observing the output of the lsblk command, it shows that the sdd3 is the rootfs partition and it is now mounted at the /run/media/rossijonas/__ directory on my computer. This is the main partition where Rocky Linux is installed in the MicroSD card.


Step 2. Find or configure the IP address

The Rocky Linux OS has the sshd service already set up to start since the first boot, and the Rocky Linux image for Raspberry Pi comes with a pre-configured user and password so, to SSH into the device after the first boot, the only part missing is the device’s IP address.

If the device is connected to your home network, it may be easy to find the automatic IP address assigned to the device, but if it is connected into a network with many devices, or to a network where network scans are not allowed, it may be a good idea to pre-configure a static IP address inside the Rocky Linux installation then the IP address is known to you since the device’s first boot.

Let’s start by checking the local network addresses.

  • Back where we left at “Step 1.", the MicroSD card is still connected into your computer so, for now, leave that as it is.

  • Identify the local network name:

    nmcli c s

    Sample output:

    NAME                UUID                                  TYPE      DEVICE      
    pvpn-killswitch     4ac5372f-a5ce-4f2a-8c0e-581e922e36b5  dummy     pvpnksintrf0
    Wired connection 1  1af840be-ec88-32d1-a8f3-9977148fc769  ethernet  eno1        
    

    The desired connection is named Wired connection 1 since it is the ethernet typed connection.

  • Verify the IP, Gateway, and DNS addresses of your computer on the subnet it is connected:

    nmcli c s "Wired connection 1" | grep -i -e ipv4 -e ip4

    Sample output:

    ipv4.method:                            auto
    ipv4.dns:                               --
    ipv4.dns-search:                        --
    ipv4.dns-options:                       --
    ipv4.dns-priority:                      0
    ipv4.addresses:                         --
    ipv4.gateway:                           --
    ipv4.routes:                            --
    ipv4.route-metric:                      -1
    ipv4.route-table:                       0 (unspec)
    ipv4.routing-rules:                     --
    ipv4.ignore-auto-routes:                no
    ipv4.ignore-auto-dns:                   no
    ipv4.dhcp-client-id:                    --
    ipv4.dhcp-iaid:                         --
    ipv4.dhcp-timeout:                      0 (default)
    ipv4.dhcp-send-hostname:                yes
    ipv4.dhcp-hostname:                     --
    ipv4.dhcp-fqdn:                         --
    ipv4.dhcp-hostname-flags:               0x0 (none)
    ipv4.never-default:                     no
    ipv4.may-fail:                          yes
    ipv4.required-timeout:                  -1 (default)
    ipv4.dad-timeout:                       -1 (default)
    ipv4.dhcp-vendor-class-identifier:      --
    ipv4.dhcp-reject-servers:               --
    IP4.ADDRESS[1]:                         192.168.0.129/24
    IP4.GATEWAY:                            192.168.0.1
    IP4.ROUTE[1]:                           dst = 0.0.0.0/0, nh = 192.168.0.1, mt = 100
    IP4.ROUTE[2]:                           dst = 185.159.158.182/32, nh = 192.168.0.1, mt
     = 100
     IP4.ROUTE[3]:                           dst = 192.168.0.0/24, nh = 0.0.0.0, mt = 100
     IP4.DNS[1]:                             192.168.0.1
    

    The output displays the field that has addresses assigned, that means, currently in use.

Case A. Find the IP address

Assuming the device is connected to a home network, where there are few devices connected, and it is allowed to perform a network scan, find the device’s IP address so you can SSH into the device.

  • Since you are already aware of your computer’s current IP address in the local network 192.168.0.129/24 (in this example), let’s scan the local subnet to identify IPs currently in use in this address range:

    nmap -sn 192.168.0.0/24

    Sample output:

    Starting Nmap 7.80 ( https://nmap.org ) at 2021-06-22 10:01 -03
    Nmap scan report for _gateway (192.168.0.1)
    Host is up (0.00036s latency).
    Nmap scan report for 192.168.0.128
    Host is up (0.0053s latency).
    Nmap scan report for fd2lm (192.168.0.129)
    Host is up (0.000038s latency).
    Nmap scan report for 192.168.0.145
    Host is up (0.0053s latency).
    Nmap done: 256 IP addresses (4 hosts up) scanned in 3.26 seconds
    

    Verify what IPs are in use and take note.

  • Remove the MicroSD card from your computer, place it inside the Raspberry Pi and connect the power and network cables to the device.

  • Perform another subnet scan (nmap -sn 192.168.0.0/24) and verify the new IP address present in the output, which should be the Raspberry Pi IP address:

    Sample output:

    Starting Nmap 7.80 ( https://nmap.org ) at 2021-06-22 10:01 -03
    Nmap scan report for _gateway (192.168.0.1)
    Host is up (0.00036s latency).
    Nmap scan report for 192.168.0.128
    Host is up (0.0053s latency).
    Nmap scan report for fd2lm (192.168.0.129)
    Host is up (0.000038s latency).
    Nmap scan report for 192.168.0.145
    Host is up (0.0053s latency).
    Nmap scan report for 192.168.0.146
    Host is up (0.0051s latency).
    Nmap done: 256 IP addresses (5 hosts up) scanned in 3.37 seconds
    

    There is a new IP address in the list 192.168.0.146. This is the address you are looking for. You are ready to jump to the "Step 3. SSH into the Raspberry Pi”.

Case B. Configure a static IP address using a helper

  • Assuming you have the MicroSD card connected to your computer, and the partitions are mounted locally, use the lsblk to identify where the rootfs partition is mounted, as described at the end of "Step 1.".

  • Take note of the IP, Gateway, and DNS addresses collected from your computer previously, that will serve as the reference to assign the adresses required for the Raspberry Pi connection.

  • Use the helper https://github.com/rossijonas/rocky-rpi-headless to set up the static IP connection (assigning IP, Gateway, and DNS addresses), following the “How to use” instructions.

    (I chose not to paste the instructions here since the repository’s instructions may change and should be the most accurate resource always!)

Case C. Configure a static IP address manually by creating a script

  • Assuming you have the MicroSD card connected to your computer, and the partitions are mounted locally, use the lsblk to identify where the rootfs partition is mounted, as described at the end of "Step 1.".

  • Change directory to the rootfs partition mounted on your computer, example:

    cd /run/media/rossijonas/__

  • Edit the etc/rc.d/rc.local file using sudo privileges (ex.: sudo vim etc/rc.d/rc.local) and add the following lines:

    # Provide the desired addresses here
    RPI_IP=192.168.1.127/24  # <- change to the desired IP address/mask
    RPI_GW=192.168.1.1       # <- change to the desired Gateway address
    RPI_DNS=192.168.1.1      # <- change to the desired DNS address
      
    # Default connection name, no need to change unless, after the first run,
    # the logs show a different connection name.
    RPI_CONN_NAME=Wired\ connection\ 1
      
    # Define static IP
    nmcli c down "$RPI_CONN_NAME"
    nmcli c m "$RPI_CONN_NAME" ipv4.method manual ipv4.address "$RPI_IP" ipv4.gateway "$RPI_GW" ipv4.dns "$RPI_DNS"
    systemctl restart NetworkManager
    nmcli c up "$RPI_CONN_NAME"                                               
    
    # Make sure sshd is running
    systemctl enable --now sshd
    
    # Make sure firewalld allows ssh service
    firewall-cmd --add-service ssh --permanent
    firewall-cmd --reload
    

    The IP, Gateway, and DNS addresses from the example must be replaced by the desired addresses as observed in your local computer previously, but remember to assign a different IP address (example 192.168.0.146/24) than your computer’s.

  • Make the etc/rc.d/rc.local script executable:

    sudo chmod +x etc/rc.d/rc.local

  • Leave the directory (cd) and unmount the MicroSD card’s partitions (sudo umount /dev/sdd?*).

  • Remove the MicroSD card from your computer, place it inside the Raspberry Pi and connect the power and network cables to the device.


Step 3. SSH into the Raspberry Pi

Access the device

Regardless of the case applied in the last step, you end up with the Raspberry Pi device running, and its IP address is known.

Now it’s time to SSH into the device:

  • Try to SSH into the found IP address using the rocky user and rockylinux password (provided by the standard Rocky Linux for Raspberry Pi installation):

    ssh rocky@192.168.0.146

    Accept the host fingerprint, insert the standard password rockylinux and it’s done! 🎉

    You will be prompted by the device’s shell, for example:

     
    [rocky@localhost ~]$ 
    
    

    ⚠️ Attention:

    If you get an error like this:

    @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
    @    WARNING: REMOTE HOST IDENTIFICATION HAS CHANGED!     @
    @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
    IT IS POSSIBLE THAT SOMEONE IS DOING SOMETHING NASTY!
    (...)
    

    That means that there was already another system using the static IP assigned for the Raspberry Pi, and there is a fingerprint on your local machine associated with this remote.

    If that error happens, edit the file ~/.ssh/known_hosts removing the line that starts with the IP address assigned to the Raspberry Pi.

Post-installation steps

Enable full utilization of the MicroSD card’s memory

Since the rootfs partition is formatted primarily occupying ~2.8GB of the MicroSD card’s memory, and most of the MicroSD cards provide at least 4GB of memory, it is recommended to grow the partition using all of the memory still available in the MicroSD card:

sudo rootfs-expand

After that, the rootfs filesystem will be expanded and you be able to update the system and install more software.

Clean up scripts that won’t be used anymore

Remove the scripts added.

  • In case you performed the “Case B.” or “Case C."

    Edit the /etc/rc.d/rc.local file using sudo privileges (ex.: sudo vim /etc/rc.d/rc.local) and remove all lines added previously since the desired configuration is already applied and you don’t need the configuration re-applied on every boot.

  • In case you performed the “Case B." also,

    Remove the rocky-rpi-headless.sh script:

    sudo rm /home/rocky/rocky-rpi-headless.sh

Finally, extra step, show off 😎!

Install neofetch and print the system’s information for your social media!

  • Install the EPEL repository: sudo dnf install epel-release -y

  • Install neofetch: sudo dnf install neofetch -y.

  • Run neofetch command! It will print the system information on the terminal, just like the header image from this post.

  • Print or take a picture of the screen.

  • Tweet the picture saying: “Thanks @rossijonas”


Conclusion

You learned how to install Rocky Linux on a Raspberry Pi device and how to access it remotely without ever connecting a keyboard or a screen.

Following this guide, you may have scanned your local network for devices connected or you may have used or created scripts to configure a static IP address so, it was a fun opportunity to learn a new skill or to refresh your knowledge.



Footnotes:

  • Follow me on Twitter to get more posts like this and other quick tips in your feed.
  • If you have any doubts or tips about this article, I’d appreciate knowing and discussing it via email.
  • Do you have any other Linux tips? Would you like to publish that in this blog? Please send an email to all drops.
  • As English is not my native language, I apologize for the errors. Corrections are welcome.
  • Contact: contact [@] alldrops [.] info.

Read more on linux drops: