This is a complete zram-config utility for swap, directories, and logs to reduce SD, NAND and eMMC block wear. Furthermore zram allows near RAM speed access to working directories, and prevents frequent writing to persistent storage. Even more importantly, data stored in zram can be compressed to conserve memory.
A table located at /etc/ztab
is used to configure any number and type of zram devices.
Using the table an OverlayFS mount is used to mount the newly created zram device as the upper filesystem of the OverlayFS.
OverlayFS is used so that files do not need to be copied from persistent storage to RAM on startup.
In theory this should allow for faster boots and larger directories as no complete directory copy is needed.
A modified version of kmxz/overlayfs-tools is used to implement the OverlayFS sync logic.
This tool is primarily developed and tested against Raspberry Pi OS. Any Debian derivative should also work out of the box, however there is no guarantee. Experimental Alpine support has also been added, other distributions may work but once again, there is no guarantee.
sudo apt-get install git
git clone https://github.com/ecdye/zram-config
sudo ./zram-config/install.bash
On Debian, use sudo systemctl {start|stop} zram-config.service
to start or stop zram-config.
On Alpine, use sudo rc-service zram-config {start|stop}
.
This will ensure that any changes are properly synced to the persistent storage before system poweroff.
Run sudo zram-config sync
to sync any changes in the zram filesystems managed by zram-config to persistent storage.
If you have concerns about losing data due to sudden power loss you could use this to ensure that changes are synced to disk periodically.
A default sync service that will sync files to disk every night can be installed by running the following.
sudo /path/to/zram-config/install.bash sync
Note that this sync service is not installed by default, you must install it separately.
sudo /path/to/zram-config/update.bash
To make changes to the code or checkout a specific branch/tag and prevent it from updating/resetting all changes run the following instead.
sudo /path/to/zram-config/update.bash custom
sudo /usr/local/share/zram-config/uninstall.bash
All configuration is done in the /etc/ztab
file.
Use #
to comment out any line, add new drives with the first column providing the drive type and then drive details separated by tab characters.
All algorithms in /proc/crypto
are supported but only lzo-rle
, lzo
, lz4
, and zstd
have zramctl text strings; lzo-rle
is the fastest with zstd
having much better text compression.
mem_limit
is the compressed memory limit and will set a hard memory limit for the system admin.
Set to 0 to disable the mem_limit
.
disk_size
is the maximum size of the uncompressed memory.
It should be set to roughly 150% of mem_limit
depending on the algorithm and how compressible the input files are.
Don't make it much higher than the compression algorithm (and the additional zram overhead) is capable of because there is a ~0.1% memory overhead when empty.
swap_priority
will set zram over alternative swap devices.
page-cluster
0 means tuning to singular pages rather than the default 3 which caches 8 for HDD tuning, which can lower latency.
swappiness
150 because the improved performance of zram allows more usage without any adverse affects from the default of 60.
It can be raised up to 200 which will improve performance in high memory pressure situations.
target_dir
is the directory you wish to hold in zram, and the original will be moved to a bind mount bind_dir
and is synchronized on start, stop, and write commands.
bind_dir
is the directory where the original directory will be mounted for sync purposes.
Usually in /opt
or /var
, name optional.
oldlog_dir
will enable log-rotation to an off device directory while retaining only live logs in zram.
Usually in /opt
or /var
, name optional.
If you need multiple zram swaps or zram directories, just create another entry in /etc/ztab
.
To do this simply add the new entries to the /etc/ztab
, if you need to edit an active zram device you must stop zram with sudo systemctl stop zram-config.service
on Debian or sudo rc-service zram-config stop
on Alpine and then edit any entries you need to.
Once finished, start zram using sudo systemctl start zram-config.service
or sudo rc-service zram-config start
which will only add the new entries if zram is already running.
# swap alg mem_limit disk_size swap_priority page-cluster swappiness
swap lzo-rle 250M 750M 75 0 150
# dir alg mem_limit disk_size target_dir bind_dir
#dir lzo-rle 50M 150M /home/pi /opt/zram/pi.bind
# log alg mem_limit disk_size target_dir bind_dir oldlog_dir
log lzo-rle 50M 150M /var/log /opt/zram/log.bind /opt/zram/oldlog
Run zramctl
in your preferred shell and if you see and output similar to below, yes it is working.
Please note that if the zramctl
command is missing, you will need to install the util-linux
package to have a convenient way to view the zram status.
pi@raspberrypi:~$ zramctl
NAME ALGORITHM DISKSIZE DATA COMPR TOTAL STREAMS MOUNTPOINT
/dev/zram1 lzo-rle 150M 16.9M 373.2K 692K 4 /opt/zram/zram1
/dev/zram0 lzo-rle 750M 4K 87B 12K 4 [SWAP]
To view more information on zram usage take a look at the following commands and their corresponding output.
pi@raspberrypi:~$ df
Filesystem 1K-blocks Used Available Use% Mounted on
/dev/root 3833792 1368488 2275172 38% /
devtmpfs 437356 0 437356 0% /dev
tmpfs 471980 0 471980 0% /dev/shm
tmpfs 188792 440 188352 1% /run
tmpfs 5120 0 5120 0% /run/lock
/dev/mmcblk0p1 258095 49436 208660 20% /boot
/dev/zram1 132240 18440 103048 16% /opt/zram/zram1
overlay1 132240 18440 103048 16% /var/log
tmpfs 94396 0 94396 0% /run/user/1000
pi@raspberrypi:~$ free -h
total used free shared buff/cache available
Mem: 921Mi 46Mi 750Mi 0.0Ki 124Mi 819Mi
Swap: 849Mi 0B 849Mi
pi@raspberrypi:~$ swapon
NAME TYPE SIZE USED PRIO
/var/swap file 100M 0B -2
/dev/zram0 partition 750M 0B 75
When running zram on a directory that has services accessing it, they will need to be stopped before starting or stopping zram.
For example, in the log zram device zram-config stops the services that run by default in the /var/log
directory before starting or stopping.
If your system has other services that write to /var/log
that are not stopped zram may fail to properly sync files and remove the zram device when stopping, and will probably outright fail to start when initializing a zram device.
This issue is not limited to logs, if you are running zram on another directoy that is written to by a service you will run into the same issue.
For an example on how this project internally takes care of this issue see the serviceConfiguration
function in zram-config.
A more in depth version of this function is used in the openHAB
branch that can be referenced as well.
When running zram swap on Linux kernel versions older than 5.8 swappiness has a maximum value of 100. If you observe issues runnning on older kernel versions try setting the default value of 150 back to 100.
The Raspberry Pi 4 8GB model can exhibit issues with zram due to a Linux kernel bug. This bug has been fixed as of Raspberry Pi Kernel version 1.20210527. See raspberrypi/linux@cef3970381 for more details about the issue.
By default zram-config should support most regular filesystems, as long as the tools are installed and available on the host system. In some cases, with niche filesystems some manual editing of the code may be required to enable support.
Pull requests adding support for filesystems that don't work automatically are welcome.
LZO-RLE offers the best performance and is probably the best choice, and from kernel 5.1 and onward it is the default.
If you are not running at least kernel 5.1 then LZO-RLE may not be supported by your system and you may need to change /etc/ztab
accordingly.
You might have text based low impact directories such as /var/log
or /var/cache
where a highly effective text compressor such as zstd is optimal, with effective compression that can be up to 200% of what LZO may achieve especially with text.
With /tmp
and /run
, zram is unnecessary because they are RAM mounted as tmpfs
and, if memory gets short, then the zram swap will provide extra.
It is only under intense loads that the slight overhead of zram compression becomes noticeable.
This chart from facebook/zstd provides a good benchmark for the performance of the different compressors.
https://www.kernel.org/doc/Documentation/blockdev/zram.txt
https://www.kernel.org/doc/Documentation/filesystems/overlayfs.txt