Reminder: enable ZRAM on your Linux system to optimize RAM usage (and potentially save money)

ZRAM zstd compression ram sticks

With the price of RAM getting out of control, it might be a good idea to remind Linux users to enable ZRAM so they can get better performance without upgrading memory, or save money on their next single board computer by selecting a board with the right amount of memory.

I had already written about the subject when I enabled ZRAM on a ODROID-XU4Q in 2018 using zram-config, and did the same on my Ubuntu laptop at the time. In recent days, I found Firefox crashing often due to running out of memory on my system with 16GB of RAM, and the Linux 7.0 release reminded me about ZRAM, since there were some related changes. So I decided to check the current swap configuration on my Ubuntu 24.04 laptop:


lzo doesn’t look like a recent compression algorithm, and I think I’ve seen Zstandard compression used on other systems before. However, the zram-config utility appears to be an older solution, and it’s now been replaced with zram-tools. So I decided to replace it. If you haven’t already enabled ZRAM with zram-config, you don’t need to do that, but in my case, I had to disable swap and purge the package:


Once done, I installed zram-tools:


and edited the /etc/default/zramswap file as follows:


To be on the safe side, you may want to check zstd if supported by your kernel:


I then restarted the service with the new parameters:


Finally, let’s check if everything is enabled as expected:


It looks good. The swapfile on my NVMe SSD is not used anymore, but I’ll try to use my system that way, and only re-enable it in case the system runs out of memory.

Ubuntu zram laptop

Finally, I wanted to make sure it was enabled on my Raspberry Pi 5 with 2GB of RAM, and I forgot that it’s indeed enabled by default on Raspberry Pi OS:


Raspberry Pi ZRAM

Note the config for rpi-swap is in a different location: /etc/rpi/swap.conf, and follows a different format:


More details about this specific implementation can be found on GitHub. If you are using a different operating system on any SBC, you may want to check ZRAM (or  zswap) is enabled.

Share this:

Support CNX Software! Donate via cryptocurrencies, become a Patron on Patreon, or purchase goods on Amazon or Aliexpress. We also use affiliate links in articles to earn commissions if you make a purchase after clicking on those links.

Radxa Dragon Q8B Edge AI SBC with Snapdragon 8cx Gen3 SoC
Subscribe
Notify of
guest
The comment form collects your name, email and content to allow us keep track of the comments placed on the website. Please read and accept our website Terms and Privacy Policy to post a comment.
49 Comments
oldest
newest
tkaiser
tkaiser
6 months ago

> More details about this specific implementation can be found on GitHub

That’s funny. They started with their zram implementation for RPi in 2025, that’s only seven years after me making zram the default on Armbian.

Oh, and they’re using zram+file. Might take those Raspberry Pi Ltd. employees another seven years to realize what zswap is (which I would prefer on systems with reliable flash storage).

back2future
back2future
6 months ago

[ What’s Your experience with ‘zswap’? Could it be used in parallel to ‘zram’, each being activated with different computing demand? Is it standard being compiled with most available Kernels? What else for to be careful with ‘zswap’? (thx) ]

tkaiser
tkaiser
6 months ago

Never use both together (for reasons and all other details check the ‘zswap-vs-zram-when-to-use-what.html’ link below).

I would use zram only in situations where you want to avoid swap hitting storage at all (the typical ‘SBC with crappy SD card’ situation). Otherwise use zswap.

back2future
back2future
6 months ago

[ i see, thanks for the summary. From my POV, ‘zram’ is more visible/adjustable (maybe it’s only about habits also, and zswap has to be built-in, no kernel module?), but has the difficulty with ‘cold pages’, means longer time unused memory accesses, accumulating in compressed memory. Not for production environments, but being a work around, having several zram{0..3} devices, it’s possible with swapoff/swapon toggling through the devices for removing ‘cold pages’ (with Kernels that have sufficient swapoff capability, at ~x00MB/s, guess Kernels >5.x?) … official method would be(?): echo 3600 > /sys/block/zram0/idle # 1h echo idle > /sys/block/zram0/writeback … another… Read more »

tkaiser
tkaiser
6 months ago

Just looked up in our internal documentation. We’ve switched few years a VM running a crappy commercial software stack from zram (10GB assigned memory) to zswap (5GB now enough):

It was as easy as adding ‘zswap.enabled=1 zswap.compressor=zstd zswap.zpool=z3fold’ to kernel cmdline in /etc/default/grub. And then a simple ‘echo -e “zstd\nzstd_compress\nz3fold” >> /etc/initramfs-tools/modules’ followed by an update-grub and ‘update-initramfs -u’. And then ofc creating/using a swap partition on a fast SSD pool.

back2future
back2future
6 months ago

[ Do You recommend ‘vm.swappiness’ > 60 for RAM limited systems? (thx) ]

Val
Val
6 months ago

I’d recommend 120 or more with zram, that would evict more anonymous pages into zram instead of dropping file cache.

back2future
back2future
6 months ago

[ Thanks for the suggestion. (and an (useful) upper limit at ~140-160, without cpu constraint systems?, above that, it ‘can increase CPU usage due to compression’) Just for a reminder, with systems not (actively) utilizing zram that would be an useful number between around 10-40, therefore it’s a configuration setting that has to be adjusted for the ‘built-in’/inserted Kernel module being in use. (thx) ]

Al Sneed
Al Sneed
6 months ago

https://chrisdown.name/2026/03/24/zswap-vs-zram-when-to-use-what.html

>If in doubt, prefer to use zswap. Only use zram if you have a highly specific reason to.

Val
Val
6 months ago

There’s very little point in using zswap on SBC’s storage. You should avoid swapping anything to disk, because it would be very very slow due to typical MicroSD speeds and I/O.

RAM is so much faster, hence zram.

Vin
Vin
6 months ago

Yeah, this topic just seems so weird… I normally keep swap off altogether until I know that I’m needing to swap out old stuff for things like compiling/linking. When I’m done, I swapoff.
Adding an additional RAM consumer, even if compressed, seems non-sensical.
This is coming from an 8GB user. I couldn’t imagine any meaningful value with 2GB Some compiles, even single-job, can take a few GB.

rooted
rooted
6 months ago

Without zram oom situations kill background processes, with zram you have the ability to keep more processes online.

So is it really using more RAM.

Why do you think billions of Android devices use it?

Vin
Vin
6 months ago

If it’s using RAM (compressed or not), yes it’s using more RAM as opposed to kicking out to disk swap. RAM being used is RAM that’s not available to be used. I know that compiling vscode requires me not only to use swap, but I STILL have to close most open programs, and adjust the node compile command to fit my system constraints. I cannot fathom how adding ZRAM would remotely help me in this case. Again, even if compressed, that’s RAM that’s being occupied that would have to be swapped in/out ad nauseam, if not still causing an OOM… Read more »

tkaiser
tkaiser
6 months ago

> vscode

Thank you for reminding us all how using Microsoft cra^Wtools affects the brain 🙂

Vin
Vin
6 months ago

Truly appreciate the ad hominem there tkaiser. 👍

Vin
Vin
6 months ago

*IF* I were to throw a bone to ZRAM, I’d give it consideration if swap priorities work like giving ZRAM swap prio1 would shove as much as it can into ZRAM, then when more is needed, it kicks that ZRAM out to disk swap prio2.

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

If you really need convincing, here’s an example: ran an unmodified vanilla install on a low memory device, no programs open besides the terminal. Tried to compile some software and it ran out of memory, freezing the system to the point I had to do a hard reboot. Tried it again, this time with a hardware monitor program open alongside the terminal to see what was happening with RAM. Sure enough it would fill up and at that point the system would freeze. So I hard rebooted again, enabled zram with suitable values and guess what? Software compiled without filling… Read more »

Orzel
Orzel
6 months ago

I don’t understand this article.

zram (or zswap for that matters) are, iiuc, using RAM to optimize I/O (faster access to data, less I/O operations, less write to SSD, …). Which seems like a good deal….if you have RAM to spare.

I don’t see how it could benefit systems with low RAM, as the article seems to imply.

Orzel
Orzel
6 months ago

I see. I didn’t expect such a high compression ratio !

Val
Val
6 months ago

glibc’s memory allocator by default tuned for speed, which means many arenas, data alignment, conservative memory freeing, and all the other features designed mainly for beefy servers.

zram masks the unoptimized-for-size allocation patters (which is one of the two major reason for high RAM consumption, another is memory fragmentation) by just compressing the memory, and this is effective because there’s lots of zeroed space due to alignment and multiple arenas.

Another solution to reduce overall memory usage is use alternative allocator, such as jemalloc, or non-glibc distro.

Val
Val
6 months ago

You forgot about Multi-Gen LRU. Combined with zram, it makes wonders!
https://docs.kernel.org/admin-guide/mm/multigen_lru.html

Val
Val
6 months ago

I wrote a “Linux for old PC” article long ago, before MGLRU (before kernel 6.1), but most of the covered stuff still applies. In this article I describe how to tune the system to run lots of stuff (FF with 37 tabs, heavy software) on 2GB of RAM.

https://notes.valdikss.org.ru/linux-for-old-pc-from-2007/en/

rooted
rooted
6 months ago

I’ve never paid any attention to this but I’m going to give it a try on an old laptop I’ve got with only 8GB of RAM

Willy
Willy
6 months ago

> In recent days, I found Firefox crashing often due to running out of memory on my system with 16GB of RAM, Well, I’ve had 16GB on my work laptop since 2019 and never found how to fully use them. I even clone and build kernels under /dev/shm to avoid touching storage at all, and set my TMPDIR to /dev/shm. Regarding Firefox, mine runs with several hundred tabs (maybe 300 or so), it does indeed take lots of RAM but I never managed to make it crash on low memory condition. I’m actually the one killing it via “killall firefox-bin”… Read more »

Val
Val
6 months ago

MGLRU solves this issue, its min_ttl_ms option to be exact. Set it to 250 or more.

Val
Val
6 months ago

Simpler setup is:

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

should that be
– – – – 250
instead of
– – – – 100
?

Willy
Willy
6 months ago

Even then it shouldn’t be *that* heavy. A few coworkers have TB an I’ve heard that it can be heavy, though I don’t know how much. I’ve used its ancestor Netscape Communicator in 1997, it would fit fine on my fresh new 16MB (MB not GB) machine, though I really didn’t like it and switched to elm then mutt once attachments became common. Since then development practices have heavily changed, and the required RAM to do the same thing have multiplied by 1000 and the performance dropped…

rooted
rooted
6 months ago

Once sylpheed then claws came along the old ways mostly died off for me.

I can’t remember what year I started using Linux but I believe it was somewhere around the initial release of SuSE for sale as I couldn’t download what I needed due to dialup constraints.

Definitely around 1996 though. I still remember picking up the big box in Circuit City of all places.

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

Curious. Have you submitted an issue to the adblocker project repo (assuming a FOSS project?) about this? Would be pretty helpful if they could fix that leak.
Would you consider mentioning which adblocker it was?

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

Don’t forget OOM Killer

rooted
rooted
6 months ago

What about it, are you saying don’t forget to turn it off or tune it?

rooted
rooted
6 months ago

After reading that page it’s an exercise in what ifs and in little to no way applies to typical computing on home PCs and SBC devices.

I do appreciate you sharing the link however.

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

Sure, but the point about OOM Killer is an interesting one – and one I’ve heard before in the Linux community. Some might not like the idea of the OS responding like Android but I think I’d rather have a system that still remains responsive than regularly run into lockup situations where my only option is to hard reboot.

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

Unfortunately my reply to @rooted got hit by the spam filter for including a hyperlink (which is weird, seeing as someone else provided the same hyperlink above and therefore the fact their comment is visible demonstrates it didn’t get hit by the spam filter…) but basically in the guide “Debunking zswap and zram myths” by Chris Down, the author explains that if you’re going to enable zram you should combine that with an OOM Killer, like Fedora does.

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

Fair!

Upgrade pi-top [3]
Upgrade pi-top [3]
6 months ago

Priority is set to 100 by default but judging by years’ worth of testing/discussion across various online fora that’s way too low to the point of being practically useless and should probably be set to its maximum of 32767.

Also, isn’t the modern zram hotness zram-generator?

rooted
rooted
6 months ago

I was pushing zram (compcache) on Android back in 2009 and it’s used by default these days. I see no reason not to use it and zswap on most systems today.

hwertz
6 months ago

Just wanted to note, I turned off oom-killer personally. I don’t want random processes killed because I hit some memory pressure.

And min_ttl_ms doesn’t do what some think, it doesn’t try to keep most recently used stuff in RAM more or less depending on how it’s set (the memory management ALWAYS tries to do that.) It also just kills processes if it can’t keep LRU in memory. I set it to 0 because, again, I’d rather not have random processes killed.

Vin
Vin
6 months ago

^ This is the one here… Anecdotally, I encountered min_ttl_ms OOMing everything it could get it’s hands on just now. It started with my running du -hs on a large subtree (no ionice), and my drives were thrashing as I was using them at the same time. Suddenly programs started OOMing, starting with my browser or plasmashell. Looking at the log I saw mention of kswap0 being the OOM initiator. I thought it odd that plasmashell also OOMd when I use cgroup to make sure it doesn’t swap. Plasmashell automatically restarted, and I started to swapoff -a because memory was… Read more »

Vin
Vin
6 months ago

Just one more thing, some oddity occurred with RAM being used vs available.
My system was still showing 8G, but no usage was climbing much over 3G and there was A LOT of IO going on.
I got real scared that a module died, and don’t think I’ve ever encountered a module die on me and still run.
When I finally could reboot, I ran memtest which came back clean (forgot I only had 1 module anyway).
Things have been going fine so far now without min_ttl_ms (apart from the unrelated plasmashell Shmem leak).

back2future
back2future
6 months ago

[ Has anyone here experience with cgroups, version2 and possibly optimized settings for lowering memory pressure from programs/processes?
stat -fc %T /sys/fs/cgroup
(tmpfs (vers. 1) | cgroup2fs (vers. 2))
memory.high
memory.max
memory.low
memory.swap.max
systemd-run –user –scope -p MemoryMax=6G -p ManagedOOMMemoryPressure=kill firefox
(mainly above Kernel vers. (partly avail. 4.18) 5.8-5.10 ) (thx) ]

Vin
Vin
6 months ago

Yeah, even when I was “aware of” cgroup during the v1 period, I had only just started to get into it last year I guess.
My main use of it is for making sure kwin and plasmashell never swap out, so it remains performative.
I use systemctl --user edit <service> to automatically put me in an editor for the override config (which also shows the existing config), alongside values I find in man systemd.directives which shows EVERYTHING systemd has to offer and which man it’s in.

Boardcon Amlogic A311Y3 system-on-module with 8 TOPS AI performance