Skip to the content.

24 Jan 2022

Не уверен, что мой способ оптимальный по надёжности или расходам, но для истории запишу его здесь, включая особенности и подводные камни.

P.S. Время от времени пробую сделать с малинкой что-нибудь новое и дополняю статью. P.P.S. В январе 2025 года я купил пятую малинку, про неё тоже буду писать здесь.

Установка ОС

Есть готовая штука - raspberry pi imager, в которой можно выбрать желаемую ОС и залить её на sd-карту. В случае с малинкой на 8 гб оперативной памяти стоит обратить внимание на битность ОС. Якобы видеодрайвера в 64битной ОС работают плохо, но в дальнейшем мне они и не нужны. Я выбрал 64-битную версию Ubuntu server. Из imager можно перейти в продвинутые настройки (ctrl+shift+X) и там указать имя пользоватетя, пароль от wifi, ssh ключ, имя в доменной зоне .local.

Можно установить ОС, не подключая монитор/клавиатуру/мышь. Лучше (и на мой взгляд проще) подключить сеть через кабель к роутеру. В малинке гигабитный порт, для нужд домашнего хранилища самое то. В идеале она будет доступна по имени типа pi.local, но неплохо бы иметь доступ на роутер на случай если что-то пойдёт не так.

Либо можно просканировать локальную сеть и так узнать адрес:

sudo nmap -sn 192.168.1.0/24

Если команда подвисла и ничего не происходит, то возможно надо сканировать адерс *.0.0

При самом первом запуске ОС грузится несколько минут, а я поначалу думал что что-то делаю не так. Вся дальнейшая работа и настройка делается через ssh

Внешний жёсткий диск

Я купил внешний жёсткий диск на 4Тб: HDD WD Elements Desktop WDBWLG0040HBK-EESN. Из особенностей - у него есть отдельный провод для питания от розетки и он не должен тащить энергию из малинки. Из минусов - в розетку придётся втыкать два девайса. У малинки синие разъёмы - usb 3.0, диск лучше втыкать в них.

Дальше начинаются приключения: raspberry pi imager при установке ОС размечает сд-карточку в MBR. Можно вместо карточки подключить жёсткий диск, но MBR позволит использовать только первые 2 Тб диска. А ещё хочется отказаться от sd карточки. Почему-то полностью переселить ОС на диск c GPT разметкой у меня не получилось, ОС не грузилась. В качестве полумеры я оставил загрузочный раздел на sd карточке и раздел с ОС перенёс на диск. Количество записей на карточку будет минимальным, и в случае потери я смогу вставить новую карточку памяти с загрузчиком и работать дальше.

Самое странное, что в сдругим жёстким диском toshiba на 2 гб с gpt внезапно загрузиться получилось. Я потратил около дня, но так и не понял, почему с одного диска грузится, а с другого - нет.

Можно взять раздел с ОС прямо с сд карточки (зря что ли на неё ОС ставили и настраивали) и скопировать на диск. Дальше понадобится узнать айдишники для разделов.

sudo blkid

Примерное описание тут: https://linuxtut.com/en/7af17f1272ca0c558d47/

Эти айдишники надо будет обновить в двух местах:

  1. В загрузчике boot/cmdline.txt указывает, откуда грузить ОС.
  2. В самой ОС в еtc/fstab монтируются и загрузчик, и раздел с ОС

Как я потом узнал - не обязательно использовать PARTUUID, можно вместо него указать PARTLABEL. Название раздела можно сделать любое, и мне это показалось более удобным. Но надо проследить, чтобы не было двух разделов с одинаковым названием.

В малинке целых 2 usb порта версии 3.0, поэтому можно включить рядышком второй диск и сделать софтовый RAID1. На двух дисках будут лежать идентичные копии данных, чтение теоретически может ускориться в два раза, запись будет со скоростью самого медленного и некоторыми приколами дисков с черепичной записью. К сожалению, о современных дисках производители эту информацию не особо публикуют, в одной “модели” может оказаться как одно, так и другое, и я RAID делать не стал. В планах организовать резервное копирование с домашнего ПК на малинку - тогда отказ одного из дисков или устройств не будет фатальным.

Применение

  1. sshfs для доступа из Линукса для тех, кто не осилил нормальную настройку самбы. (это я)
  2. Написать и хостить игрушечный веб-сервер для доступа к файлам из локальной сети.
  3. Samba для доступа к папкам из локальной сети не только из линукса
  4. QBittorrent с возможностью управлять им из браузера
  5. 24/7 крутить своего телеграм бота. (это тоже я)
  6. Хранить git-репозитории
  7. Подключить второй массив и организовать raid
  8. Настроить резервное копирование с помощью rsync и cron
  9. Раздобыть вторую малинку и организовать загрузку по сети, вообще без sd- карты
  10. Добавить пассивное охлаждение
  11. Настроить LUKS шифрование для дисков

Скорость копирования по проводу через sshfs получилась 44-47 мегабайт в секунду. Почти полгигабита! У меня есть подозрение, что сеть на малинке быстрее, а это тормозит жёсткий диск или роутер, но пруфов не будет.

Красивое имя в локальной сети: pi.local

Существует специальная доменная зона .local.

Можно поставить сервис, который будет окружающим устройствам в локальной сети сообщать об “имени” малинки.

Наверно, самый простой способ это сделать, это в расширенных настройках raspberry pi imager задать его операционной системе в момент установки.

Позже на пятой малинке и raspberry pi os я выяснил, что можно просто отредактировать /etc/hostsname и /etc/hosts. Но для истории оставлю менее удобный способ, которым я сделал это раньше:

sudo apt install avahi-daemon

По-дефолту работать не будет, надо поправить настройки и перезапустить сервис:

nano /etc/avahi/avahi-daemon.conf
sudo systemctl restart avahi-daemon.service

Из настроек нас интересуют

host-name=pi
domain-name=local

Автозапуск бота и торрентов

Ниже будет упрощённый пересказ того, что я узнал по этой ссылке: https://obu4alka.ru/ustanovka-qbittorrent-na-ubuntu-server-20-04-lts.html Ещё можно посмотреть тут: https://www.shubhamdipt.com/blog/how-to-create-a-systemd-service-in-linux/

Кстати, qbittorrent в браузере выглядит практически так же, как и приложение. И ещё он качает/раздаёт круглые сутки, так что можно оживить полузабытые раздачи.

В ubuntu есть systemd, которая запускает сервисы при старте ОС. Чтобы бот и торрент тоже запускались, сделаем текстовые файлики:

etc/systemd/system/qbittorrent-nox.service
[Unit]
Description=qBittorrent Command Line Client
After=network.target

[Service]
Type=forking
User=qbittorrent-nox
Group=qbittorrent-nox
UMask=007
ExecStart=/usr/bin/qbittorrent-nox -d --webui-port=8080
Restart=on-failure

[Install]
WantedBy=multi-user.target

и ещё один для моего бота:

[Unit]
Description = Runs my bot

Wants=network-online.target
After=network-online.target nss-lookup.target

[Service]
Type=simple
ExecStart=/home/ubuntu/bot/run.sh

[Install]
WantedBy=multi-user.target

В случае qbittorrent я создал отдельного пользователя, но если честно не особо понял смысл. Ну да, так вроде безопаснее. А потом самба не cможет открыть файл, т.к. у неё нет прав на чтение и вас ждут красота и изучение того как в линуксе работают пользователи, группы и разрешения.

дальше есть набор команд

sudo systemctl daemon-reload // чтобы увидело наши изменения в файле
sudo systemctl start qbittorrent-nox.service // запуск
sudo systemctl status example.service // посмотреть статус если вдруг не работает
sudo systemctl enable example.service // добавить в автозагрузку

В настройках qbittorrent (прямо в веб-интерфейсе) есть смысл поменять дефолтную папку для хранения торрентов, а так же залезть во вкладку webUI и убрать там галочку “Use UPnP / NAT-PMP to forward the port from my router”, чтобы запретить вход в веб-интерфейс из сети снаружи роутера. Ещё там есть опция “Bypass authentication for clients on localhost”, её наоборот удобнее включить для доступа из локальной сети без пароля.

Самба

В windows 10 отключили старую версию протокола smb, который позволял заходить без авторизации. Но с самбой всё как-то криво складывается, я сделал readonly шару и забил, потому что из линукса достаточно sshfs.

Для того, чтобы самба переходила по символьным ссылкам, придётся ещё какие-то опции указывать. Их тут нет. /etc/samba/smb.conf

[share]
  path = /mnt/data/share/
  read only = yes
  guest ok = yes
  guest only = yes

sshfs

Очень удобный вариант, можно удалённую папку примонтировать как папку у себя. Я даже alias завёл:

alias mount-pi8="sshfs -o reconnect,ServerAliveInterval=15,ServerAliveCountMax=3 ubuntu@192.168.1.120:/ /home/me/Desktop/pi8"
alias umount-pi8="umount /home/me/Desktop/pi8"

Единственное - несмотря на параметры, оно как-то криво работает при покидании домашней сети. Ноутбук был не рад, пришлось перезагружать. По тем же причинам в автозапуск такое ставить не надо. Руками каждый раз монтировать - чуточку лень. Возможно, я всё-таки донастрою самбу или ещё что-то.

В остальном - шикарно, скорость работы близка к скорости жёсткого диска (возможно, не современного, а десятилетней давности, но всё же).

На четвёртой малинке скорость копирования достигала где-то 50 мегабайт секунду и кажется что ограничением была скорость шифрования ssh. На пятой я смог увидеть 115 мегабайт в секунду и это близко к пределу гигабитной сети.

Игрушечный веб-сервер для доступа к файлам из локальной сети

Сделал просто потому, что мне хотелось написать свой сервер. Код тут: https://github.com/Kright/files-web-server. Не важно что за устройство - ПК, айфон, телефон с андроидом - лишь бы они были подключены к локальной сети и умели запускать браузер. Сервер отображает какие-то папки в какие-то пути в браузере, например, по 192.168.0.xx:/photo открывается папка с фотками. Что забавно, некоторые файлы типа mp4 можно воспроизводить прямо на лету - они прямо в браузере открываются как видео с проигрывателем.

Я не знаток веб-технологий, генерирую максимально простые html-странички:

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>${currentDir.getName}</title>
  </head>
  <body>
    <div>
    $parentLink
    $links
    </div>
  </body>
</html>

Хранение git-репозиториев

Я не стал использовать что-то типа gitlab и пошёл по максимально простому пути. В git сервер и клиент равноправны, на клиенте хранится своя копия данных. Между ними нет большой разницы, и я под сервером подразумеваю круглосуточно работающий ПК, и предполагаю что клиент запускается время от времени и закидывает на сервер свои изменения.

Адресов для скачивания/заливания репозитория может быть несколько. Обычно он один и называется origin. Но никто не запретит добавить несколько адресов, выкачать ветку с одного и потом её влить по другому адресу. И даже в совершенно другой репозиторий так можно, лишь бы имена веток не пересекались. Гибкость впечатляет, хоть про неё и не все знают.

Если есть ssh доступ к серверу, то добавить туда репозиторий очень просто:

На сервере: создать папку, в ней вызвать

git init --bare

На клиенте:

git remote add pi8 ssh://user@ip/path-to-repo
git push pi8 master

В идеале ещё можно создать отдельного пользователя для git и т.п., но для локального домашнего применения не вижу смысла.

Подробнее можно прочитать тут: https://git-scm.com/book/en/v2/Git-on-the-Server-Setting-Up-the-Server

RAID массив

В итоге я отказался от этой идеи. С помощью mdadm можно сделать raid1 массив, в котором данные будут лежать в двух копиях. Одна на одном диске и другая на другом. Т.к. диски обычно неравных размеров, лучше вместо указания дисков (типа /dev/sda) использовать разделы: например /dev/sda1. Само собой, разделы должны быть на разных дисках. В случае отказа одного из дисков массив с данными продолжит работать как ни в чём ни бывало, пока не откажет второй диск. В общем, за статусом raid массива надо будет следить (и мне кажется, это неудобно).

Вдобавок, я сделал раздел с raid только для важных данных, и при отказе основного диска ОС похерится и малинка всё равно не запустится. Я подумал над этим безобразием и решил вместо этого сделать бэкапы.

Бэкапы

В отличие от raid массива, у бэкапов есть очень полезное свойство - при случайном удалении файлов их можно будет восстановить.

Я подумал над возможными вариантами:

На мой взгляд, с rsync самый удобный вариант - я смогу вставить диск с бэкапами в любой комп и вытащить данные обратно.

Я вдохновлялся вот этой статьёй: https://linuxconfig.org/how-to-create-incremental-backups-using-rsync-on-linux, но сделал немножко по-другому:

readonly DATETIME="$(date '+%Y-%m-%d_%H:%M:%S')"
readonly LOG_FILE="/mnt/backup/logs/backup_safedata_${DATETIME}.txt"

printf "\n\nstart at ${DATETIME}\n" >> $LOG_FILE

rsync -av --delete /mnt/safedata --link-dest ../latest --exclude "lost+found" /mnt/backup/safedata/${DATETIME} >> $LOG_FILE

df >> $LOG_FILE
echo "finished at $(date '+%Y-%m-%d_%H:%M:%S')" >> $LOG_FILE

cd /mnt/backup/safedata
rm latest
ln -s ${DATETIME} latest

python3 -c '
import os
import shutil
listdir = os.listdir(".")
files = sorted([f for f in listdir if f.startswith("20")])
to_preserve = set(files[-31:])
monthly = {f[:7]: f for f in reversed(files)}
to_preserve.update(monthly.values())
for f in sorted(to_preserve):
	print(f"keep '{f}'")
for f in set(files) - to_preserve:
    print(f"remove '{f}'")
    shutil.rmtree(f)
' >> $LOG_FILE

latest - мягкая ссылка на последний бэкап. В –link-dest путь должен быть абсолютный или относительный для папки с бэкапом, поэтому надо выскочить на директорию вверх: ../latest

если ссылки нет, то rsync всё ещё работает.

Логи я решил каждый раз писать в отдельный файл, так как иначе при добавлении большого количества файлов он превращается в многомегабайтный лог и в нём сложно найти, что в какой день происходило. Папка для логов сама не создастся, надо добавить её вручную

скрипт на питоне хранит последние 30 версий бэкапа и первую версию каждого месяца, остальные удаляет.

Для отладки есть полезные опции –dry-run для запуска без реальных изменений, а так же можно опцию –verbose указать дважды и получить более подробный вывод: -vv

Опция -a раскрывается в кучу настроек, которые пытаются перетащить время, пользователя файла, права доступа и т.п. Я попробовал запускать rsync между компом и малинкой и несмотря на –link-dest создавались копии файлов. Я потратил кучу времени на то, чтобы понять, что все эти опции мешают и в итоге между машинами копировал с опциями -rl –size-only

В этом случае время игнорируется, а файл с тем же размером считается не требующим копирования. Можно ещё указать –checksum, но тогда и передающая и принимающая стороны будут считать md5 чексуммы для файлов одинакового размера, что потребует их полного прочтения. Я решил забить и ограничиться проверкой размера.

Eщё заслуживает внимания опция -t: с ней будет выставляться правильное время последнего изменения файлов (тогда всё будет работать ок и без –size-only). Но если предыдущий бэкап время не сохранил, то инкрементальным он не будет, файлы будут считаться разными.

Пример опций, которые я для использовал: -rltogp

C помощью cron можно будет настроить бэкапы на каждый день или каждую неделю:

crontab -e

и там написать

20 4 * * * /mnt/backup/backup.sh

Чтобы каждую ночь в 4:20 делать бэкап.

Загрузка по сети*

*Задание со звёздочкой, будут приключения.

Заливать образ на флешку, вставлять в малинку, ждать пока загрузится - не самое весёлое занятие. После того, как перевая малинка стала работающим 24/7 полноценным сервером, я раздобыл вторую и решил попробовать загрузку по сети.

Глобально это состоит из двух шагов:

  1. включить на клиентской малинке загрузку по сети
  2. настроить на сервере dhcp и nfs, чтобы они работали

Из принципиальных ограничений - клиентская малинка должна быть подключена к сети по проводу, а не через wifi.

Список команд и т.п. несложный, но в процессе я нашёл кучу подводных камней, и настройка заняла у меня целый вечер.

https://www.raspberrypi.com/documentation/computers/remote-access.html#network-boot-your-raspberry-pi

Вот ссылка на документацию, но делать надо далеко не всё, что в ней написано.

Настройка клиента

На 4B, загрузку включать надо, причём процесс отличается от предыдущих версий.

Во-первых, понадобится поставить именно raspbian os. В принципе, можно обойтись и без подключения мышки-клавиатуры, если в rpi Imager нажать ctrl+shift+x (или какое-то ещё неочевидное сочетание клавиш), оказаться в настройках и там указать ключ для ssh. Экран я советую всё-таки подключить, он потом пригодится.

Запускаем штуку для настройки (прям из консоли)

sudo raspi-config

В ней в менюшках надо выбрать Advanced Options, Boot Order, Network Boot и в ней выбрать загрузку по сети (что странно - с загрузкой по сети вариант ровно один - малинка попытается загрузиться с sd карты, если не получится - то по сети).

Чтобы изменения применились, придётся перезагрузиться.

И потом командой

vcgencmd bootloader_config

можно посмотреть, что в BOOT_ORDER. В идеале там должно быть 0xf21. Тут можно посмотреть подробнее, что же число значит:

https://www.raspberrypi.com/documentation/computers/raspberry-pi.html#raspberry-pi-4-bootloader-configuration

Я так понял, они справа налево идут.

После этого малинку можно выключить, выдернуть из неё sd-карту и снова включить. Выше я советовал включить экран - малинка на нём покажет текстом свой ip адрес и потихоньку растущее количество неудачных попыток загрузки по сети.

Настройка сервера

Дальше инструкции с официального сайта следовать не обязательно.

Во-первых, можно просто взять и на на домашнем роутере во вкладочке с настройками DHCP указать статические ip адреса для сервера (давно уже так сделал) и для клиента (сделал сейчас).

Во вторых, у меня клиент - raspbian os, а сервер ubuntu. На сайте происходит кунг-фу по включению той же самой sd-карты в сервер, загрузке с неё и дальнейшей модификации для того, чтобы клиент и сервер различались. Спасибо, но я воздержусь.

Итак, можно смело листать сайт до инструкции

sudo apt install tcpdump dnsmasq sudo systemctl enable dnsmasq sudo tcpdump -i eth0 port bootpc

Но dnsmasq ставить пока не надо.

С помощью tcpdump можно убедиться, что малинка при загрузке действительно посылает запросы всем в локальной сети.

С dnsmasq меня ждал сюрприз. Это в одном лице и dns сервер, и нужные нам dhcp и tftp сервера. В ubuntu уже есть свой dns-резолвер, systemd-resolved, и он, как нетрудно догадаться, тоже dns сервер, который слушает порт 53 и не даёт слушать его другим.

После установки dnsmasq полезет на 53 порт и не сможет - тот уже занят. Всё что надо сделать - залезть в /etc/dnsmasq.conf и указать там port=0, чтобы dns-составляющая не запускалась и не мешалась.

https://askubuntu.com/questions/191226/dnsmasq-failed-to-create-listening-socket-for-port-53-address-already-in-use

Я вместо этого воспользовался первым нагугленным советом и отключил systemd-resolved. В итоге dns работать перестал, я узнал, что команде sudo без dns работается плохо и потом возвращал всё обратно.

так вот, в dnsmasq.conf должно в итоге быть

port=0
dhcp-range=192.168.1.255,proxy
log-dhcp
enable-tftp
tftp-root=/tftpboot
pxe-service=0,"Raspberry Pi Boot"

tftp-root - путь к папке с загрузчиком на сервере

как скопировать системный раздел на сервер

В оригинальной статье они обходятся одной sd-картой, но я по понятным причинам включил sd-карту в ноутбук и задумался, как же скопировать её на сервер. Суть проблемы в том, что

rsync from to

не может скопировать файлы, принадлежащие root и запрещённые другим для чтения. А поскольку мы копируем системный раздел, там такие файлы будут.

Можно написать так:

sudo rsync from to

Тогда получится скопировать файлы с владельцем root, но не получится их записать по двум причинам:

  1. у рута своя папка .ssh и там может не быть ключа для ssh
  2. на системе, куда копируем, rsync работает не из под-рута

Красота и удобство. Указать root@ip:/path у меня тоже не получилось. Первая проблема решается копированием ~/.ssh/id_rsa, вторая - хитрой опцией. Для хитрой опции требуется, чтобы на другой машине команда sudo не спрашивала пароль. Рабочая команда выглядит так:

sudo rsync --progress -ax -e "ssh" --rsync-path="sudo rsync" rootfs/ ubuntu@192.168.1.142:/nfs/client1

Таким незамысловатым образом можно скопировать загрузчик в /nfs/nfsboot, а системный раздел в /nfs/client1

Идею и команду взял отсюда: https://superuser.com/questions/605425/rsync-root-files-between-systems-without-specifying-password

После этого надо будет в nfsboot/cmdline.txt заменить указание на root: у меня получилось так:

console=serial0,115200 console=tty1 root=/dev/nfs nfsroot=192.168.1.142:/nfs/client1,vers=4.1,proto=tcp rw ip=dhcp rootwait

и поправить etc/fstab

192.168.1.142:/nfs/tftpboot	/boot	nfs	defaults,vers=4.1,proto=tcp 0 0

То, что есть только boot без корневой системы - нормально, так и должно быть

Кроме того, надо ещё включить rpcbind, настроить nfs-kernel-server и в /etc/exports указать пути для nfs:

/nfs/client1 *(rw,sync,no_subtree_check,no_root_squash)
/nfs/tftpboot *(rw,sync,no_subtree_check,no_root_squash)

В результате малинка без SD-карты загружается по сети из файлов в папке. При желании ту папку можно будет копировать, хранить несколько разных версий ОС и т.п.

Пассивное охлаждение

Температуру можно узнать так:

vcgencmd measure_temp

У меня она была 64 градуса (с нагрузкой из описанного выше софта), после - 57. Я купил корпус Qumo Aluminum RS001, который заодно является радиатором. Охлаждение пассивное, вентилятора нет и ломаться нечему. И шуметь тоже. Сам корпус, кажется, сделан из аллюминия. Смотрится красиво и солидно. В комплекте шли два маленьких кусочка термопрокладки, болтики и шестигранный ключик - в общём, всё необходимое.

Эффектом немного разочарован, думал будет градусов 10-15 разницы, а получилось около 7. Сам корпус ощутимо горячий во всех местах

LUKS шифрование раздела

Опциональная часть, надо чётко понимать, нужно ли шифрование. Цель - чтобы содержимое диска было невозможно прочитать при включении в посторонний пк.

Если пароль от раздела будет храниться где-то на малинке, то затея бессмысленная. Я планирую заходить на малинку по ssh и руками подключать зашифрованный раздел. Кроме того - для самой малинки, пока она работает, пароль известен. Если сама малинка скомпроментирована - то злоумышленник и имеет доступ к диску, и может утащить к себе пароль.

Шифрование спасает только от сценария, когда постороний забирает диск и пытается прочитать с него данные. Всё, ничего больше.

Я где-то видел, чтобы на малине как-то хитро шифровали прям диск с системой, но я так извращаться не буду. В малинке негде хранить пароль, и я хочу, чтобы она могла сама включиться без моего участия. Шифрую только отдельный раздел с данными.

Итак, если шифрование всё-таки нужно, начнём:

Скорее всего, cryptsetup уже установлен, если нет, ставим:

sudo apt install cryptsetup

Особенности малинки - нет хардварной поддержки aes, скорость шифровки и дешифровки будет медленная, советуют вместо него использовать adiantum.

Проверить скорость шифрования (без записи на диск, всё в RAM):

cryptsetup benchmark
# Tests are approximate using memory only (no storage IO).
PBKDF2-sha1       386643 iterations per second for 256-bit key
PBKDF2-sha256     630912 iterations per second for 256-bit key
PBKDF2-sha512     510007 iterations per second for 256-bit key
PBKDF2-ripemd160  324034 iterations per second for 256-bit key
PBKDF2-whirlpool  142935 iterations per second for 256-bit key
argon2i       4 iterations, 333516 memory, 4 parallel threads (CPUs) for 256-bit key (requested 2000 ms time)
argon2id      4 iterations, 335222 memory, 4 parallel threads (CPUs) for 256-bit key (requested 2000 ms time)
#     Algorithm |       Key |      Encryption |      Decryption
        aes-cbc        128b        85.6 MiB/s        98.5 MiB/s
    serpent-cbc        128b        42.7 MiB/s        44.4 MiB/s
    twofish-cbc        128b        63.3 MiB/s        69.1 MiB/s
        aes-cbc        256b        76.0 MiB/s        77.5 MiB/s
    serpent-cbc        256b        43.8 MiB/s        44.4 MiB/s
    twofish-cbc        256b        68.1 MiB/s        69.2 MiB/s
        aes-xts        256b        84.4 MiB/s       101.8 MiB/s
    serpent-xts        256b        43.1 MiB/s        44.8 MiB/s
    twofish-xts        256b        67.9 MiB/s        70.7 MiB/s
        aes-xts        512b        78.6 MiB/s        79.8 MiB/s
    serpent-xts        512b        44.9 MiB/s        44.7 MiB/s
    twofish-xts        512b        70.5 MiB/s        70.6 MiB/s

и то же самое на пятой малинке (похоже, что поддержка aes появилась):

cryptsetup benchmark
# Tests are approximate using memory only (no storage IO).
PBKDF2-sha1       654541 iterations per second for 256-bit key
PBKDF2-sha256    1220693 iterations per second for 256-bit key
PBKDF2-sha512     458293 iterations per second for 256-bit key
PBKDF2-ripemd160  397790 iterations per second for 256-bit key
PBKDF2-whirlpool  139884 iterations per second for 256-bit key
argon2i       4 iterations, 584872 memory, 4 parallel threads (CPUs) for 256-bit key (requested 2000 ms time)
argon2id      4 iterations, 587760 memory, 4 parallel threads (CPUs) for 256-bit key (requested 2000 ms time)
#     Algorithm |       Key |      Encryption |      Decryption
        aes-cbc        128b      1130.0 MiB/s      2060.3 MiB/s
    serpent-cbc        128b               N/A               N/A
    twofish-cbc        128b       121.3 MiB/s       128.5 MiB/s
        aes-cbc        256b       907.5 MiB/s      1689.2 MiB/s
    serpent-cbc        256b               N/A               N/A
    twofish-cbc        256b       122.5 MiB/s       128.5 MiB/s
        aes-xts        256b      1644.9 MiB/s      1646.3 MiB/s
    serpent-xts        256b               N/A               N/A
    twofish-xts        256b       125.3 MiB/s       129.7 MiB/s
        aes-xts        512b      1428.7 MiB/s      1430.4 MiB/s
    serpent-xts        512b               N/A               N/A
    twofish-xts        512b       127.0 MiB/s       129.6 MiB/s

И померять aes-adiantum, который должен быть быстрее, малина 4:

cryptsetup benchmark -c xchacha12,aes-adiantum
# Tests are approximate using memory only (no storage IO).
#            Algorithm |       Key |      Encryption |      Decryption
xchacha12,aes-adiantum        256b       188.1 MiB/s       189.2 MiB/s
cryptsetup benchmark -c xchacha20,aes-adiantum
# Tests are approximate using memory only (no storage IO).
#            Algorithm |       Key |      Encryption |      Decryption
xchacha20,aes-adiantum        256b       161.0 MiB/s       162.2 MiB/s

малина 5 в два с лишним раза быстрее:

cryptsetup benchmark -c xchacha20,aes-adiantum
# Tests are approximate using memory only (no storage IO).
#            Algorithm |       Key |      Encryption |      Decryption
xchacha20,aes-adiantum        256b       378.8 MiB/s       401.1 MiB/s

Ссылки, которыми я руководствовался:

https://gist.github.com/palopezv/792b9f0100484186c3f74cbee7b07630

https://wiki.davidl.me/index.php?title=LUKS&mobileaction=toggle_view_desktop

Я выбрал xchacha20, т.к. разница в скорости не критичная, а оно вроде как надёжнее.

xchacha20 отличается в xchacha12 количеством раундов шифрования - 20 вместо 12.

Где почитать: https://www.reddit.com/r/cryptography/comments/p3dflu/fulldiskencryption_xchacha12_vs_xchacha20/

Создадим раздел:

sudo cryptsetup luksFormat --type=luks2 --sector-size=4096 -c xchacha20,aes-adiantum-plain64 -s 256 -h sha512 --use-urandom /dev/sdXX

Тут вместо sdXX написать реальный раздел как он показывается в lsblk

Дальше был забавный момент - после всего программа требует написать YES большими буковками. Просто чтобы убедиться, что человек внимательно посмотрел на команду и случайно не похерит нужный раздел.

Дальше надо подключить раздел и отформатировать

sudo cryptsetup open /dev/sdXX NAME
sudo mkfs.ext4 /dev/mapper/NAME

Примонтировать раздел:

# Open the encrypted drive
sudo cryptsetup open /dev/sdXX NAME
# Mount your partition
mount -t ext4 /dev/mapper/NAME MOUNT_LOCATION

Размонтировать:

# Unmount your partition
umount MOUNT_LOCATION
# Close the decrypted drive
cryptsetup close NAME

BTRFS

кроме ext4 можно попробовать BTRFS. Это довольно современная фаловая система с интересными возможностями типа Copy-on-Write, сжатием и т.п.

Я про неё пока мало знаю. Ссылки: Arch wiki, wikipedia

Cоздание отличается не сильно:

sudo mkfs.btrfs -L LABEL /dev/mapper/NAME

В btrfs есть штука под названием subvolume сделать снапшот можно командой:

sudo btrfs subvolume snapshot /mnt/disk/ /mnt/disk/@snapshot-1

Посмотреть доступные subvolume:

sudo btrfs subvolume list /mnt/disk

Удалить:

sudo btrfs subvolume delete /mnt/disk/@snapshot-1

Но почему-то в доступных subvolume у меня вообще нет дефолтного, его не показывает. Хотя вот такая команда что-то возвращает:

sudo btrfs subvolume get-default /mnt/disk

Ещё момент: если создавать снапшот как папку внутри диска с данными, то следующий снапшот будет содержать ещё и предыдущую папку со снапшотом (но правда пустую). Ещё btrfs поддерживает создание снапшотов на btrfs на другом диске (и даже на сервере), но я не пробовал.

Raspberry pi 5

Вышла пятая версия, добавлю информацию сюда же.

Отличия:

Последнее меня особо порадовало. По-умолчанию в raspbian в firefox стоит плагин, который просит у ютуба видео с кодеком 264 вместо VP9 и среди опций выше 1080р ничего нет. Но я ради интереса отключил этот плагин, позапускал 1440р и 4к - и оно всё работает! На глаз кажется что не идеально плавно, но это сильно круче чем было у четвёртой малинки. Насколько помню, там даже на 1080р были проблемы.

Корпус Argon NEO 5 NVME и SSD

Для охлаждения я купил корпус с вентилятором, который вдобавок позволяет поставить M.2 любого размера. Из минусов - процесс сборки довольно замороченный и разбирать-собирать малинку придётся несколько раз. Например, для того чтобы вытащить карточку памяти.

Вентилятор на корпусе крохотный и вообще не слышный. Ещё что интересно - он зачастую вообще останавливается и температура малинки при этом небольшая.

Кроме того, я умудрился подключить шину pcie не той стороной (контакты на креплении должны быть со стороны неподвижной штуки) и долго пытался понять, почему же не видно диск.

Я выбрал диск Kingston, потому что где-то нашёл инфу что они у них в пике потребляют меньше пяти ватт, в отличие от самсунгов (там вроде до 7.9 ватт).

Для включения pcie gen3 надо добавить следующую строчку в boot/firmware/config.txt, у меня всё заработало без проблем.

dtparam=pciex1_gen=3

При подключении через провод можно вообще отключить вайфай (а то иначе может получиться, что интернет зачем-то идёт через него

dtoverlay=disable-wifi

Если загрузиться с карточки памяти и иметь подключенный ssd, то можно прям на него поставить систему из rapsberry pi imager.

Raspberry Pi OS vs Ubuntu

Я попробовал первую, но остался недоволен и видимо вернусь обратно на Ubuntu Server. Почему - да просто потому, что по дефолту в rapsbian доступна только семнадцатая версия java и вдобавок она 32-битная. Я попытался поставить 64-битную 21-ую, почитал в интернете про аналогичные проблемы у людей с малинками и решил переставить систему. Да, убунта дольше запускается и тяжеловеснее, но зато другая слишком уж опорота своей легковенсостью - например, мой телеграм бот просто не запускался из-за того что дефолтное значение Xmx было слишком маленьким.

Выводы

Если хочется только домашнее хранилище - проще и дешевле подключить диск напрямую к роутеру (некоторые роутеры так умеют). Но мне хотелось иметь полноценный сервер, хоть и маленький. Своей цели я достиг и очень доволен.