pi

Bought a pi Zero 2W model to configure as my server for the arduino devices to be used in the farm at Thenkodipakkam .

Initially installed and used Debian based Raspberry Pi OS. Later on 2024-08-21 tried to install Alpine Linux in it. Went back to pi OS as on 2024-08-22.

Since the project at the farm was getting delayed, installed and ran pihole on Alpine Linux diskless mode from jul'25 to jul'26. On 2026-07-01, reinstalled the OS in sys mode and configured overlayfs the next day. Currently the pi is running only pihole.

pihole

Installed and configured pihole from testing repository in mid-July 2025 in diskless mode. Converted this installation to overlaytmpfs due to this bug↗ .

For pihole unbound is used as DNS server here.

The above changes have been committed using and should not cause issue when rebooting.

The following has to be done after every reboot.

$ doas apk update
$ doas apk add pihole@testing
$ doas addgroup pihole $USER
$ doas service pihole start

system state before installing pihole


prabu@pizero2w ~> df -m
Filesystem     1M-blocks   Used Available Use% Mounted on
tmpfs                225     77       148  35% /

prabu@pizero2w ~> free -m
              total        used        free      shared  buff/cache   available
Mem:            449         157         110          77         182         205

Top applications based on memory usage - output of smem
unbound 114780 kB
wpa_supplicant 6412 kB
fish 6324 kB

Top applications based on memory usage - output of smem after disabling stevenblack host file
unbound 25412 kB
wpa_supplicant 6412 kB
fish 6324 kB

prabu@pizero2w ~> free -m
              total        used        free      shared  buff/cache   available
Mem:            449          69         198          77         182         292

system state after installing and running pihole


prabu@pizero2w ~> free -m
              total        used        free      shared  buff/cache   available
Mem:            449          65         138         130         247         244

prabu@pizero2w ~> df -m
Filesystem     1M-blocks   Used Available Use% Mounted on
tmpfs                225    119       107  53% /

Top applications based on memory usage - output of smem
unbound 15876 kB
pihole-FTL 10332 kB
fish 6708 kB
wpa_supplicant 6412 kB

lbu & mem Usage

every lbu usage takes quite good amount of available memory

pizero2W:~$ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
devtmpfs              10     0        10   0% /dev
shm                  209     3       207   1% /dev/shm
/dev/mmcblk0       61106   153     60953   1% /media/mmcblk0
tmpfs                209   102       107  49% /
tmpfs                 84     1        84   1% /run
/dev/loop0            51    51         0 100% /.modloop
pizero2W:~$ free -m
              total        used        free      shared  buff/cache   available
Mem:            417          56         147         104         213         246
Swap:             0           0           0
pizero2W:~$ ls -lh /var/lib/pihole/
total 7.2M
drwxr-x--- 2 pihole pihole   80 Jan  1  1970 config_backups
-rw-r--r-- 1 pihole pihole 5.5K Sep 23 18:05 dnsmasq.conf
-rw-rw-r-- 1 pihole pihole 6.1M Nov  6 21:05 gravity.db
drwxr-xr-x 2 pihole pihole   80 Jan  1  1970 gravity_backups
-rw-rw-r-- 1 pihole pihole 100K Nov  6 21:05 gravity_old.db
drwxr-xr-x 2 pihole pihole   60 Jan  1  1970 hosts
drwxrwxr-x 2 pihole pihole  100 Jan  1  1970 listsCache
-rw-r----- 1 pihole pihole 348K Sep 23 18:04 pihole-FTL.db
-rw-r----- 1 pihole pihole  32K Sep 23 18:04 pihole-FTL.db-shm
-rw-r----- 1 pihole pihole 592K Nov  6 21:55 pihole-FTL.db-wal
pizero2W:~$ doas lbu st
doas (prabu@pizero2W) password:
U var/lib/pihole/pihole-FTL.db-wal
U home/prabu/.ash_history
pizero2W:~$ doas lbu ci
pizero2W:~$ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
devtmpfs              10     0        10   0% /dev
shm                  209     3       207   1% /dev/shm
/dev/mmcblk0       61106   156     60950   1% /media/mmcblk0
tmpfs                209   134        75  65% /
tmpfs                 84     1        84   1% /run
/dev/loop0            51    51         0 100% /.modloop

pizero2W:/tmp$ doas du -d 1 -h
3.8M	./lbu-2662-1762446369-GvY8iSeP01
3.8M	./lbu-2622-1762446336-DkeX8ov563
25M	./lbu-2622-1762446335-eYxIL8L7go
0	./.X11-unix
0	./.ICE-unix
33M	.
pizero2W:/tmp$ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
devtmpfs              10     0        10   0% /dev
shm                  209     3       207   1% /dev/shm
/dev/mmcblk0       61106   156     60950   1% /media/mmcblk0
tmpfs                209   134        75  65% /
tmpfs                 84     1        84   1% /run
/dev/loop0            51    51         0 100% /.modloop
pizero2W:/tmp$ doas reboot
pizero2W:~$ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
devtmpfs              10     0        10   0% /dev
shm                  209     3       207   1% /dev/shm
/dev/mmcblk0       61106   156     60950   1% /media/mmcblk0
tmpfs                209   102       108  49% /
tmpfs                 84     1        84   1% /run
/dev/loop0            51    51         0 100% /.modloop
pizero2W:~$ df -m /tmp/
Filesystem     1M-blocks  Used Available Use% Mounted on
tmpfs                209   102       108  49% /
pizero2W:~$ du -d 1 -h /tmp/
0	/tmp/.X11-unix
0	/tmp/.ICE-unix
0	/tmp/

System disk with overlaytmpfs

To set up the OS in the System Disk Mode, just follow the setup-alpine script. During Disk install stage, followed the below instructions:

No disks available. Try boot media /media/mmcblk0? (y/n) [n], change the default option and type y.

Which disk(s) would you like to use? (or ‘?’ for help or ’none’) [none], type device name mmcblk0 as per displayed information.

overlaytmpfs↗ has to be enabled after the OS reboots. Edit the below file as follows:

pizero2W:~$ cat /boot/cmdline.txt
root=UUID=7a1ecfc8-0f84-4c2c-b380-fbe85fcd7ef4 modules=sd-mod,usb-storage,ext4 quiet rootfstype=ext4 overlaytmpfs=yes overlaytmpfsflags=size=96M

The performance metrics with overlaytmpfs active when running pihole is given below.

pizero2W:~$ free -m
              total        used        free      shared  buff/cache   available
Mem:            416          50         312           8          54         348
Swap:             0           0           0
pizero2W:~$ uptime
 10:34:56 up 17 min,  0 users,  load average: 0.00, 0.00, 0.00
pizero2W:~$ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
devtmpfs              10     0        10   0% /dev
shm                  208     3       206   1% /dev/shm
/dev/mmcblk0p2     59555   132     56367   1% /media/root-ro
root-tmpfs            96     7        90   7% /media/root-rw
overlayfs             96     7        90   7% /
tmpfs                 84     1        83   1% /run
/dev/mmcblk0p1       300    42       259  14% /boot
tmpfs                208     0       208   0% /tmp
pizero2W:~$ rc-status
Runlevel: default
 unbound                                                                                                                    [  started  ]
 sshd                                                                                                                       [  started  ]
 pihole                                                                                                         [  started 01:50:28 (0) ]
 ntpd                                                                                                                       [  started  ]
 crond                                                                                                                      [  started  ]
Dynamic Runlevel: hotplugged
Dynamic Runlevel: needed/wanted
 sysfs                                                                                                                      [  started  ]
 fsck                                                                                                                       [  started  ]
 root                                                                                                                       [  started  ]
 localmount                                                                                                                 [  started  ]
Dynamic Runlevel: manual

Identifying changes

To identify all changes that have been made in the system i.e overlaytmpfs mode, issue the below command:

doas find /media/root-rw/root -type f

This might list a lot of files. Identify the file(s) that you actually want to save.

Making permanent changes

In overlaytmpfs mode, all runtime writes go to the temporary RW upper layer (tmpfs) and are lost on reboot. The lower layer - actual SD card partition - stays mounted read-only throughout normal operation and is never written to via /.

For major changes like package installation and update, toggle-overlay script can be used.

To persist a change in a single file permanent, it must be copied directly to the lower layer’s mountpoint. This is a separate write from the overlay and does not happen automatically:

Remount the lower layer read-write:

doas mount -o remount,rw /media/root-ro

If any changes are already made in the upper layer i,e live system, copy the specific file(s) to the corresponding path under /media/root-ro:

doas cp -a /etc/pihole/pihole.toml /media/root-ro/etc/pihole/pihole.toml

Remount the lower layer back to read-only:

doas mount -o remount,ro /media/root-ro

Keep the RW window as short as possible: remaining in rw longer than necessary increases exposure to accidental writes and, in the event of a crash or power loss during that window, filesystem inconsistency.

Toggle script for overlay

A toggle-overlay script is placed in /usr/local/bin so it can be used to switch to normal mode for updating packages or for other system maintenance.

#!/bin/sh
# /usr/local/bin/toggle-overlay
# Switch root boot mode between overlaytmpfs and normal RW, for next boot.
# usage: toggle-overlay              -> show current status (default)
#        toggle-overlay normal       -> switch to normal RW mode for next boot
#        toggle-overlay overlay      -> switch to overlaytmpfs mode for next boot

set -e

CMDLINE=/boot/cmdline.txt
BACKUP=/boot/cmdline.txt.overlay-backup
DEFAULT_FLAGS="overlaytmpfs=yes overlaytmpfsflags=size=96M"

show_status() {
        if grep -q "overlaytmpfs=yes" "$CMDLINE"; then
                echo "Next boot: overlaytmpfs mode"
        else
                echo "Next boot: normal RW mode"
        fi
        if mount | grep -q "on / type overlay"; then
                echo "Current session: overlaytmpfs mode"
        else
                echo "Current session: normal RW mode"
        fi
}

to_normal() {
        if ! grep -q "overlaytmpfs=yes" "$CMDLINE"; then
                echo "Already set to normal RW mode for next boot."
                return
        fi
        cp "$CMDLINE" "$BACKUP"
        sed -i 's/ overlaytmpfs=yes overlaytmpfsflags=[^ ]*//' "$CMDLINE"
        echo "Switched to normal RW mode for next boot."
        echo "Backup saved: $BACKUP"
}

to_overlay() {
        if grep -q "overlaytmpfs=yes" "$CMDLINE"; then
                echo "Already set to overlaytmpfs mode for next boot."
                return
        fi
        if [ -f "$BACKUP" ]; then
                cp "$BACKUP" "$CMDLINE"
                echo "Restored overlaytmpfs mode from backup for next boot."
        else
                sed -i "s|\$| $DEFAULT_FLAGS|" "$CMDLINE"
                echo "Appended default overlay flags for next boot (no backup found)."
        fi
}

case "$1" in
        "") show_status ;;
        normal) to_normal; show_status ;;
        overlay) to_overlay; show_status ;;
        *)
                echo "usage: $(basename "$0") [normal|overlay]"
                exit 1
                ;;
esac

Use serial access

prabu@pizero2W ~> doas mount -o remount,rw /media/mmcblk0/
prabu@pizero2W ~> cat /media/mmcblk0/usercfg.txt
dtoverlay=dwc2,dr_mode=peripheral
prabu@pizero2W ~ [1]> cat /media/mmcblk0/cmdline.txt
modules=loop,squashfs,sd-mod,usb-storage quiet console=tty1
prabu@pizero2W ~> doas vi /media/mmcblk0/cmdline.txt
prabu@pizero2W ~> cat /media/mmcblk0/cmdline.txt
modules=loop,squashfs,sd-mod,usb-storage,g_serial quiet console=ttyGS0,115200 console=tty1
prabu@pizero2W ~> cat /media/mmcblk0/cmdline.txt
modules=loop,squashfs,sd-mod,usb-storage,g_serial console=ttyGS0,115200 console=tty1

cutdown bootloader

Cutdown bootloader package installed on the system mode Alpine Linux as follows:

prabu@pizero2W ~> doas apk add raspberrypi-bootloader-cutdown
doas (prabu@pizero2W) password:
(1/1) Installing raspberrypi-bootloader-cutdown (1.20260619-r0)
Executing raspberrypi-bootloader-common-1.20260619-r0.trigger
* Configured kernel vmlinuz-rpi / initramfs-rpi
OK: 162.8 MiB in 119 packages

Installing the bootloader on a diskless installation earlier produced the below error message. The bootloader files were extracted and copied manually.

prabu@pizero2W /m/mmcblk0> doas apk add raspberrypi-bootloader-cutdown
doas (prabu@pizero2W) password:
(1/2) Installing raspberrypi-bootloader-common (1.20250820-r0)
(2/2) Installing raspberrypi-bootloader-cutdown (1.20250820-r0)
busybox-1.37.0-r24.trigger: Executing script...
raspberrypi-bootloader-common-1.20250820-r0.trigger: Executing script...
raspberrypi-bootloader-common-1.20250820-r0.trigger: /usr/sbin/update-raspberrypi-bootloader: WARNING: no kernel found
OK: 81 MiB in 101 packages

Once the cutdown bootloader files are installed to /boot folder, proceed to add gpu_mem=16 to /boot/config.txt as follows:

tail -n 2 /boot/config.txt
gpu_mem=16
include usercfg.txt

The setting gpu_mem=16 can be used only after installing cutdown bootloader. This results in the total usable memory size to increase from 416M to 464M for overlaytmpfs installation .

pizero2W:~$ free -m
              total        used        free      shared  buff/cache   available
Mem:            464          57         354           8          53         388
Swap:             0           0           0
prabu@pizero2W ~> cat /proc/cmdline
coherent_pool=1M 8250.nr_uarts=0 snd_bcm2835.enable_headphones=0 cgroup_disable=memory bcm2708_fb.fbwidth=656 bcm2708_fb.fbheight=416 bcm2708_fb.fbdepth=16 bcm2708_fb.fbswap=1 smsc95xx.macaddr=B8:27:EB:36:89:06 vc_mem.mem_base=0x1fa00000 vc_mem.mem_size=0x20000000  root=UUID=7a1ecfc8-0f84-4c2c-b380-fbe85fcd7ef4 modules=sd-mod,usb-storage,ext4 quiet rootfstype=ext4 overlaytmpfs=yes overlaytmpfsflags=size=96M

Headless Alpine

The below documentation was created in 2024-08-21.

Downloaded the OS alpine-rpi-3.20.2-aarch64.tar.gz for pi Zero 2W: Dowloaded the headless.apkvol.tar.gz and 3 sample files from:

https://github.com/macmpi/alpine-linux-headless-bootstrap↗

For v3.24, i just downloaded the headless.apkvol.tar.gz file and created a wpa_supplicant.conf as explained in alpine wiki↗ .

The following steps has to be done to prepare the SD card first on any windows/linux PC. I placed the SD card in a usb memory card reader and used it.

mkdir /mnt/pi
mount /dev/sda1 /mnt/pi

Go into the first partition (fat16) and issue the below command:

cd /mnt/pi
tar xvf ~prabu/Downloads/alpine-rpi-3.20.2-aarch64.tar.gz

After extracting the tar file to the SD card, create and edit the usercfg.txt file as follows:

touch usercfg.txt
cat usercfg.txt
enable_uart=1
gpu_mem=32

Now, copy the above 3 files in addition to headless.apkovl.tar.gz to the root of sdcard. The headless should be in the tar.gz format and it need not be modified.

Now eject the SD card and insert it into the pi and power it on. Once logged in, the below login screen appears:

  Alpine Linux headless bootstrap v1.2 by macmpi
...

Now proceed with the next stage of installation. Since next step requires more packages tried adding apkrepos and the inbuilt wget from buysbox generated below error, but the issue got resolved after installing wget.


alpine-headless:~# setup-apkrepos
200D7DA87F000000:error:0A000086:SSL routines:tls_post_process_server_certificate:certificate verify failed:ssl/statem/statem_clnt.c:2091:
ssl_client: SSL_connect
wget: error getting response: Connection reset by peer
20AD2EA77F000000:error:0A000086:SSL routines:tls_post_process_server_certificate:certificate verify failed:ssl/statem/statem_clnt.c:2091:
ssl_client: SSL_connect
alpine-headless:~# apk add wget
alpine-headless:~# lbu commit

With the above step and a reboot, the pi is usable, but works in diskless mode.

Headless Raspberry Pi OS

To get the headless option have to pre-configure wifi, ssh and user account using Pi Imager.

Performance Tracking

On 2024-08-22 after basic OS installation

prabu@pizero1:~ $ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
udev                  73     0        73   0% /dev
tmpfs                 42     1        41   3% /run
/dev/mmcblk0p2     59628  2020     54563   4% /
tmpfs                209     1       209   1% /dev/shm
tmpfs                  5     1         5   1% /run/lock
/dev/mmcblk0p1       510    64       447  13% /boot/firmware
tmpfs                 42     0        42   0% /run/user/1000
prabu@pizero1:~ $ free -m
               total        used        free      shared  buff/cache   available
Mem:             417         110         166           0         192         306
Swap:            199          25         174

On 2024-08-22 after system update

Added following new packages automatically: raspi-utils-core raspi-utils-dt raspi-utils-eeprom raspi-utils-otp raspinfo


prabu@pizero1:~ $ apt list --installed |wc -l
598
prabu@pizero1:~ $ free -m
               total        used        free      shared  buff/cache   available
Mem:             417         127         125           0         215         289
Swap:            199           0         199
prabu@pizero1:~ $ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
udev                  73     0        73   0% /dev
tmpfs                 42     1        41   3% /run
/dev/mmcblk0p2     59628  2036     54546   4% /
tmpfs                209     0       209   0% /dev/shm
tmpfs                  5     1         5   1% /run/lock
/dev/mmcblk0p1       510    64       447  13% /boot/firmware
tmpfs                 42     0        42   0% /run/user/1000

On 2024-08-22 after adding Mosquitto

prabu@pizero1:~ $ apt list --installed |wc -l
603
prabu@pizero1:~ $ free -m
               total        used        free      shared  buff/cache   available
Mem:             417         133         175           0         159         283
Swap:            199           3         196
prabu@pizero1:~ $ df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
udev                  73     0        73   0% /dev
tmpfs                 42     1        41   3% /run
/dev/mmcblk0p2     59628  2038     54544   4% /
tmpfs                209     0       209   0% /dev/shm
tmpfs                  5     1         5   1% /run/lock
/dev/mmcblk0p1       510    64       447  13% /boot/firmware
tmpfs                 42     0        42   0% /run/user/1000

On 2024-08-22 after installing python-paho library based script:

prabu@pizero1 ~> apt list --installed |wc -l
612
prabu@pizero1 ~> df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
udev                  73     0        73   0% /dev
tmpfs                 42     1        41   3% /run
/dev/mmcblk0p2     59628  2074     54509   4% /
tmpfs                209     0       209   0% /dev/shm
tmpfs                  5     1         5   1% /run/lock
/dev/mmcblk0p1       510    64       447  13% /boot/firmware
tmpfs                 42     0        42   0% /run/user/1000
prabu@pizero1 ~> free -m
               total        used        free      shared  buff/cache   available
Mem:             417         125         129           0         213         291
Swap:            199          31         168

On 2024-08-23 after installing Motion

prabu@pizero1 ~ [1]> apt list --installed |wc -l
773
prabu@pizero1 ~> df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
udev                  73     0        73   0% /dev
tmpfs                 42     1        41   3% /run
/dev/mmcblk0p2     59628  2480     54102   5% /
tmpfs                209     1       209   1% /dev/shm
tmpfs                  5     1         5   1% /run/lock
/dev/mmcblk0p1       510    64       447  13% /boot/firmware
tmpfs                 42     0        42   0% /run/user/1000
prabu@pizero1 ~> free -m
               total        used        free      shared  buff/cache   available
Mem:             417         138         140           0         189         278
Swap:            199          39         160

on 2024-08-23 after successfully running motion with extra packages

prabu@pizero1 ~> apt list --installed |wc -l
859
prabu@pizero1 ~> df -m
Filesystem     1M-blocks  Used Available Use% Mounted on
udev                  73     0        73   0% /dev
tmpfs                 42     1        41   3% /run
/dev/mmcblk0p2     59628  2974     53608   6% /
tmpfs                209     1       209   1% /dev/shm
tmpfs                  5     1         5   1% /run/lock
/dev/mmcblk0p1       510    64       447  13% /boot/firmware
tmpfs                 42     0        42   0% /run/user/1000
prabu@pizero1 ~> free -m
               total        used        free      shared  buff/cache   available
Mem:             417         192         157           0         124         224
Swap:            199          49         150

Using pi

pi camera

$libcamera-hello
prabu@pizero1:~ $ libcamera-hello
[5:53:55.355012758] [2138]  INFO Camera camera_manager.cpp:313 libcamera v0.3.0+65-6ddd79b5
[5:53:55.425653823] [2141]  WARN RPiSdn sdn.cpp:40 Using legacy SDN tuning - please consider moving SDN inside rpi.denoise
[5:53:55.431520539] [2141]  INFO RPI vc4.cpp:446 Registered camera /base/soc/i2c0mux/i2c@1/ov5647@36 to Unicam device /dev/media0 and ISP device /dev/media1
[5:53:55.431666997] [2141]  INFO RPI pipeline_base.cpp:1104 Using configuration file '/usr/share/libcamera/pipeline/rpi/vc4/rpi_apps.yaml'
Preview window unavailable
Mode selection for 1296:972:12:P
    SGBRG10_CSI2P,640x480/0 - Score: 3296
    SGBRG10_CSI2P,1296x972/0 - Score: 1000
    SGBRG10_CSI2P,1920x1080/0 - Score: 1349.67
    SGBRG10_CSI2P,2592x1944/0 - Score: 1567
Stream configuration adjusted
[5:53:55.434788767] [2138]  INFO Camera camera.cpp:1183 configuring streams: (0) 1296x972-YUV420 (1) 1296x972-SGBRG10_CSI2P
[5:53:55.435402361] [2141]  INFO RPI vc4.cpp:621 Sensor: /base/soc/i2c0mux/i2c@1/ov5647@36 - Selected sensor format: 1296x972-SGBRG10_1X10 - Selected unicam format: 1296x972-pGAA

stream video

On the pi:

$ rpicam-vid -t 0 --inline --listen -o tcp://0.0.0.0:8554

On the client:


$ mpv http://192.168.1.197:8554
 (+) Video --vid=1 (h264 640x480 25.000fps)
VO: [gpu] 640x480 yuv420p

mqtt broker

The MQTT protocol is a machine-to-machine (M2M)/“Internet of Things” connectivity protocol. Designed as an extremely lightweight publish/subscribe messaging transport, it is useful for connections with remote locations where a small code footprint is required and/or network bandwidth is at a premium.

Installation

Installed the broker and clients


prabu@pizero1:~ $ sudo apt install mosquitto mosquitto-clients
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
The following additional packages will be installed:
  libcjson1 libdlt2 libmosquitto1
The following NEW packages will be installed:
  libcjson1 libdlt2 libmosquitto1 mosquitto mosquitto-clients
0 upgraded, 5 newly installed, 0 to remove and 0 not upgraded.
Need to get 655 kB of archives.
After this operation, 1,977 kB of additional disk space will be used.
...
Created symlink /etc/systemd/system/multi-user.target.wants/mosquitto.service → /lib/systemd/system/mosquitto.service.


prabu@pizero1:~ $ systemctl status mosquitto.service
● mosquitto.service - Mosquitto MQTT Broker
Loaded: loaded (/lib/systemd/system/mosquitto.service; enabled; preset: enabled)
     ....
861 /usr/sbin/mosquitto -c /etc/mosquitto/mosquitto.conf

mqtt user

Created mqtt user esp32 with same password, and modified config file:

prabu@pizero1:~ $ sudo mosquitto_passwd -c /etc/mosquitto/passwd esp32
prabu@pizero1:~ $ cat /etc/mosquitto/mosquitto.conf
# Place your local configuration in /etc/mosquitto/conf.d/
#
# A full description of the configuration file is at
# /usr/share/doc/mosquitto/examples/mosquitto.conf.example
per_listener_settings true
pid_file /run/mosquitto/mosquitto.pid

persistence true
persistence_location /var/lib/mosquitto/

log_dest file /var/log/mosquitto/mosquitto.log

include_dir /etc/mosquitto/conf.d

listener 1883
allow_anonymous false
password_file /etc/mosquitto/passwd

testing

Tested with sub and pub on the Alpine Linux :

prabu@homepc2 /d/d/p/l/pizero> mosquitto_sub -h 192.168.1.197 -u esp32 -P esp32 -t "pi/#"
get_status
prabu@homepc2 ~> mosquitto_pub -h 192.168.1.197 -u esp32 -P esp32 -t "pi/control" -m "get_status"

On issuing the mosquitto_pub command, saw the message on mosquitto_sub window.

mqtt-paho

The Paho Python Client provides a client class with support for MQTT v5.0, MQTT v3.1.1, and v3.1 on Python 3.7+. It also provides some helper functions to make publishing one off messages to an MQTT server very straightforward. https://github.com/eclipse/paho.mqtt.python↗

The current implementation consists of two files:

The python script that makes use of Paho python client to respond to mqtt pub requests. The script must be an executable file. The following two python packages were installed for this script:

prabu@pizero1 ~> sudo apt install python3-paho-mqtt python3-psutil
prabu@pizero1 ~/backup> ls -l /usr/local/bin/
-rwxr-xr-x 1   root root 4936 Aug 22 20:22 mqtt_paho_client.py*

MQTT Paho Service file:


prabu@pizero1 ~/backup> cat etc/systemd/system/mqtt_paho.service
[Unit]
Description=MQTT Paho Service
After=network.target

[Service]
User=prabu
# Replace with the directory containing your script
WorkingDirectory=/usr/local/bin
ExecStart=/usr/bin/python /usr/local/bin/mqtt_paho_client.py
Restart=on-failure

[Install]
WantedBy=multi-user.target⏎

Based on the above mqtt_paho_client.py code, when mqtt client publishes the get_status message , all the subscribed mqtt clients receive the below reply:


prabu@homepc2 ~> mosquitto_pub -h 192.168.1.197 -u esp32 -P esp32 -t "pi/control" -m "get_status"
prabu@homepc2 ~> mosquitto_sub -h 192.168.1.197 -u esp32 -P esp32 -t "pi/#"
Current status of pizero1 at 20:36:16
CPU Usage: 0.2%
Memory Usage: 28.5%
CPU Temp: 45.1'C
Disk Usage: 3.7%
Uptime: 3:33:00
Network: 192.168.1.197
Processes: 139
Load Average: 1m 0.18, 5m 0.20, 15m 0.13

motion

The latest released version on motion website is 4.7 and then there is also 4.6. 4.7 is not yet available for aarch64 platform of bookworm.

prabu@pizero1 ~ [1]> sudo apt list motion Listing... Done
motion/stable 4.5.1-2 arm64
prabu@pizero1 ~ [1]> sudo apt install motion
0 upgraded, 161 newly installed, 0 to remove and 0 not upgraded.
Need to get 133 MB of archives.
After this operation, 422 MB of additional disk space will be used.

At the end of installation, found the below messages: Fixed them and checked the service status:


Setting up motion (4.5.1-2) ...
Adding group `motion' (GID 112) ...
Done.
adduser: Warning: The home dir /var/lib/motion you specified already exists.
Adding system user `motion' (UID 107) ...
Adding new user `motion' (UID 107) with group `motion' ...
adduser: The home directory `/var/lib/motion' already exists.  Not touching this directory.
adduser: Warning: The home directory `/var/lib/motion' does not belong to the user you are currently creating.
Adding user `motion' to group `video' ...
Done.
Created symlink /etc/systemd/system/multi-user.target.wants/motion.service → /lib/systemd/system/motion.service.
Setting up ffmpeg (8:5.1.6-0+deb12u1+rpt1) ...
Processing triggers for man-db (2.11.2-2) ...

Broadcast message from systemd-journald@pizero1 (Fri 2024-08-23 14:50:55 IST):

motion[6672]: [0:motion] [EMG] [ALL] motion_startup: Exit motion, cannot create log file /var/log/motion/motion.log: Permission denied

prabu@pizero1 ~> systemctl status motion
○ motion.service - Motion detection video capture daemon
     Loaded: loaded (/lib/systemd/system/motion.service; enabled; preset: enabled)
     Active: inactive (dead) since Fri 2024-08-23 14:50:55 IST; 1min 32s ago
   Duration: 3.951s
       Docs: man:motion(1)
    Process: 6672 ExecStart=/usr/bin/motion (code=exited, status=0/SUCCESS)
   Main PID: 6672 (code=exited, status=0/SUCCESS)
        CPU: 1.063s

Aug 23 14:50:51 pizero1 systemd[1]: Started motion.service - Motion detection video capture daemon.
Aug 23 14:50:55 pizero1 motion[6672]: [0:motion] [NTC] [ALL] conf_load: Processing thread 0 - config file /etc/motion/moti>
Aug 23 14:50:55 pizero1 motion[6672]: [0:motion] [NTC] [ALL] conf_load: Processing thread 0 - config file /etc/motion/moti>
Aug 23 14:50:55 pizero1 motion[6672]: [0:motion] [ERR] [ALL] mycreate_path: Problem creating directory /var/log/motion: Pe>
Aug 23 14:50:55 pizero1 motion[6672]: [0:motion] [EMG] [ALL] motion_startup: Exit motion, cannot create log file /var/log/>
Aug 23 14:50:55 pizero1 motion[6672]: [0:motion] [ERR] [ALL] mycreate_path: Problem creating directory /var/log/motion: Pe>
Aug 23 14:50:55 pizero1 motion[6672]: [0:motion] [EMG] [ALL] motion_startup: Exit motion, cannot create log file /var/log/>
Aug 23 14:50:55 pizero1 systemd[1]: motion.service: Deactivated successfully.
Aug 23 14:50:55 pizero1 systemd[1]: motion.service: Consumed 1.063s CPU time.
prabu@pizero1 ~ [3]> sudo mkdir /var/log/motion
prabu@pizero1 ~> sudo chown motion:motion /var/log/motion/
prabu@pizero1 ~> systemctl status motion
● motion.service - Motion detection video capture daemon
     Loaded: loaded (/lib/systemd/system/motion.service; enabled; preset: enabled)
     Active: active (running) since Fri 2024-08-23 14:53:43 IST; 2s ago
       Docs: man:motion(1)
   Main PID: 6880 (motion)
      Tasks: 1 (limit: 174)
        CPU: 818ms
     CGroup: /system.slice/motion.service
             └─6880 /usr/bin/motion

Aug 23 14:53:43 pizero1 systemd[1]: Started motion.service - Motion detection video capture daemon.
drwxr-s---  2 motion    adm  4096 Aug 23 14:50 motion/
prabu@pizero1 ~> sudo groups motion
motion : motion video
prabu@pizero1 ~> cat /etc/group |grep adm
adm:x:4:prabu
prabu@pizero1 ~> sudo chown motion:motion /var/lib/motion

Restored the earlier working configuration of motion and camera files. Took backup. Still camera did not work


prabu@pizero1 ~ [1]> sudo cp /etc/motion/motion.conf /etc/motion/motion.conf.default
prabu@pizero1 ~> sudo cp backup/etc/motion/motion.conf /etc/motion/
prabu@pizero1 ~> sudo cp backup/etc/motion/camera1.conf /etc/motion/

From https://motion-project.github.io/4.5.1/motion_config.html#basic_setup_picam↗

In the Raspbian version based upon Debian release of ‘bullseye’ (and presumably later releases), Raspbian allows access to the PI camera via an application called libcamera. libcamera provides access to the camera as a v4l2 device but this interface is only available when using a special application. Users must run Motion using the command “libcamerify motion” and then specify /dev/video0 in the Motion configuration file.

Error: Cant find libcamerify. libcamera-tools needs to be installed to solve the above error. https://github.com/Motion-Project/motion/discussions/1620↗

prabu@pizero1 ~> sudo apt install libcamera-tools

Also executed the below command from motion website documentation:

After updating the file /lib/systemd/system/motion.service, and restarting the service, noticed that systemctl status displayed the below error message:

ERROR: ld.so: object ‘/usr/lib/aarch64-linux-gnu/libcamera/v4l2-compat.so’ from LD_PRELOAD cannot be preloaded (cannot open shared object file): ignored.

As per https://forums.raspberrypi.com/viewtopic.php?t=358211↗ installed another package.

prabu@pizero1 ~> sudo apt install libcamera-v4l2

After the above packages are installed, picam started working.

git in Pi Zero

Installed git and configured bare repository to track the configuration changes.

Issued all the below commands after installing git:


git init --bare $HOME/.systemfiles
alias sysconfig='git --git-dir=$HOME/.systemfiles --work-tree=/'
echo "alias sysconfig='git --git-dir=/home/prabu/.systemfiles --work-tree=/'" >> ~/.config/fish/config.fish
source ~/.config/fish/config.fish
git config  --global user.email kprabuanand@gmail.com
git config --global user.name "Prabu Anand Kalivaradhan"
sysconfig commit -m "config file from previous setup"
sysconfig config status.showUntrackedFiles no
cat .systemfiles/config
[core]
    repositoryformatversion = 0
    filemode = true
    bare = true
[status]
    showUntrackedFiles = no
prabu@pizero1 ~> sysconfig config status.showUntrackedFiles no

sysconfig remote add origin https://github.com/prabusw/pizero2W.git↗ was a mistake sysconfig remote set-url origin git+ssh://git@github.com/prabusw/pizero2W.git https://gist.github.com/ddeveloperr/1859fd395e7cb5832c59↗

nginx

samba

samba has been configured on the pi zero2W on a diskless Alpine Linux .


© Prabu Anand K 2020-2026