29 May 2026

feedPlanet Debian

Ravi Dwivedi: Budapest Travel

In September 2025, I attended the annual LibreOffice conference in Budapest, Hungary. This gave me an opportunity to explore the city, which I will cover in this post.

Let's start with the currency. Although Hungary is a part of the European Union (EU), it doesn't use the euro as its currency. Instead, it uses Hungarian forints (denoted by "Ft"). During my time in Hungary, 1 Indian rupee was equal to 4 Hungarian forints.

After reaching the Budapest airport, I bought a 15-day public transport pass. The public transport counter is after you pass customs and immigration. The pass allows unlimited use of public transport in the city. I had to show my passport and pay 5950 Ft to get the pass. The pass had my passport number mentioned on it. The public transport passes can also be bought at any of the tram stations as well.

This is the counter from where I bought my public transport pass.

This is the counter from where I bought my public transport pass.

Budapest pass.

My unlimited public transport pass for Budapest. I have redacted my passport number from it.

An automatic ticket machine

An automatic ticket machine at a tram station in Budapest.

Budapest is a union of two cities-Buda and Pest-lying on opposite sides of the Danube River. My hotel-Corvin Hotel-was on the Pest side.

Budapest had good public transport. The buses, metros, and trams complemented each other. For example, the airport didn't have metro or tram connectivity, but it was served by the bus. Most of the metro was on the Pest side, with only a couple of stations falling in Buda. However, both sides had an extensive network of trams.

Furthermore, the information about the public transport was easily accessible. For instance, the map of tram stops inside the trams also included the bus routes one could get after alighting at those stops.

From the airport, I took a bus followed by taking a metro on the M3 line to reach within walking distance of my hotel.

An M3 line metro in Budapest.

An M3 line metro in Budapest.

During the conference I would take the tram to the conference venue. The trams were modern and fast. They also had a smiley face at the front, which gave them a friendly look. It seemed like the trams were happily doing their job. The city also had a good pedestrian infrastructure along with separate cycling tracks.

A tram in Budapest.

A tram in Budapest having a smiley face at the front.

In the bathroom of my hotel room, there was a poster mentioning that the tap water was safe to drink.

On the 6th of September, I went on a sightseeing tour of Budapest with Dione. Our friend Attila, who was a local (from Hungary), joined us. We went to the central market from our hotel to the metro.

If you read my post on Vienna, I mentioned how the metros there don't have AFC gates but ticket validators instead. Budapest's metro also has the same system. If you buy individual tickets, you need to validate them using the validators on the station before boarding the metro. If you are using a public transport pass like I was, then you do not need to validate, and you can board the metro directly.

A ticket validator at a metro station in Budapest.

A ticket validator at a metro station in Budapest.

Attila showed us around. I bought a fridge magnet and paprika powder. I wanted a spicy one, but I didn't get that. Instead, I got the sweet version. It doesn't taste sweet, and it is mainly used for food coloring at home. I like the paprika powder and use it frequently in my omelets and other dishes.

Central Market.

Central market.

A building with a tram in front of it.

The building right behind the tram is the central market building.

At 12 noon, he had to join the The Document Foundation (TDF) sightseeing group, so we parted ways. The Hungarian parliament building is a tourist attraction. We were on the Pest side of Budapest, and the parliament was also on the Pest side, while other tourist attractions were on the Buda side.

So, Dione and I hopped on a tram and went to the parliament. There is a tram station just outside where we got off. The parliament is the icon of Budapest. One can buy tickets and go inside. However, we didn't have a lot of time, so we clicked pictures outside.

Hungarian Parliament building.

Hungarian Parliament building.

After spending some time there, we took a tram to the Chain Bridge. As I mentioned earlier, Budapest has two parts-Buda and Pest-separated by the Danube River. To go from one of the sides to the other requires crossing a bridge. Although Budapest has many bridges linking the two sides, the main one is the Chain Bridge.

We walked on the chain bridge to get to the other side. The bridge gave a good view of the Danube River. It also had a statue of a lion. We could see Buda Castle from the bridge.

Chain Bridge.

A shot of Chain Bridge.

A lion statue

The lion statue on the Chain Bridge.

After reaching the other side of the bridge (the Buda side), we sat on a bench for some time and then planned on where to go next. We decided to go to Fisherman's Bastion, which is another tourist attraction.

We used the OSMAnd~ app to figure out which bus to take and hopped on one. Soon we reached Fisherman's Bastion, where we found a flight of stairs that led upwards. Upon climbing the stairs, we got a panoramic view of the city. It also gave us a good view of the Hungarian parliament across the river. Going further upstairs, we found a statue of Stephen I of Hungary. He was the first king of Hungary, which he became in the year 1000.

A view of Hungarian parliament from Fisherman's bastion

A view of Hungarian parliament from Fisherman's bastion.

I found Fisherman's Bastion to be the best tourist attraction in the city. As mentioned earlier, it offers a panoramic view of the city, which I liked, and it is also beautiful. If you find yourself in Budapest, I would highly recommend that you visit it.

Fisherman's Bastion.

Fisherman's Bastion.

A green colored statue of King Stephen

Statue of Stephen I of Hungary at Fisherman's Bastion.

Next, we went downstairs and returned to where the bus dropped us. From here on, we walked in random streets to see the residential and non-touristy side of Budapest. It was not so random as we walked towards Batthyány tér metro station. Upon reaching the metro station, we found a café where we had coffee.

A metro station

Batthyány tér metro station.

For lunch, we decided to go to Rákóczi tér metro station after reading on the internet about the food options there. Upon exiting the metro station, we found a market inside a building that had a lot of shops, but most of them were closed.

After roaming around inside a bit, we found an Italian place open and decided to eat there. The name of this place was Matteos. We ordered an eggplant parmigiana, a lasagna artichoke, and a classic tiramisu. It wasn't very tasty but filled us up for the day.

The Italian place we had our lunch at.

A picture of Matteos, where we had our lunch.

Budapest has four metro lines, and we had been to three of them, so we decided to try the remaining line, which was the M1 line. It is the oldest line in the city and has a different vibe than the modern lines. This line was opened in 1896, one of the oldest subway systems in the world.

We took the M1 line and got down at the last stop, Mexikói út. The coaches were much smaller than the other metro lines, and the seating was pretty different too. Upon going outside, we found out there wasn't much to do here. At this point, I checked the map and realized that Heroes' Square is just a couple of metro stations away. Heroes' Square is a tourist attraction in Budapest. It is a historically significant place in Budapest.

M1 line station and tracks.

M1 line station and tracks. It is the oldest metro transit of Budapest and one of the oldest in the world. It started operations in 1896.

Here, our unlimited public transport pass was handy because if it was paid per trip, we would think of the stop as a "wasted" one because we would have to buy a ticket again, but in this case we could just hop on again without any regrets.

A metro train entering a station.

An M1 line metro train entering the station.

So we took the M1 line again and deboarded at Hősök tere station, followed by walking to the square. After roaming around for a while, we saw a trolleybus and decided to ride on that.

Heroes' Square

Heroes' Square.

A trolleybus

This is the trolleybus we took in Budapest.

A trolleybus is an electric bus that is powered by overhead electric cables. It is like a tram but runs on roads instead of tracks. We got down at Dózsa György út metro station. Then we took a metro to our hotel.

Before going to the hotel, we went to a place to eat something. We had coffee and lángos. Lángos is a deep-fried Hungarian dish, which looks exactly like the Indian flatbread bhatura. I found it tasty, but since it was deep-fried, that was almost a given.

A deep friend dish called Lángos.

Lángos - adish which looks like Indian flatbread bhatura.

The next day we went to Vienna-the capital of Austria-which I have already posted about. Check it out here.

I had a good time in Budapest, and it is a beautiful city with good public transport and some amazing sites to visit. That's it for now, and see you next time!

Credits: Thanks Dione and Badri for proofreading.

29 May 2026 2:26pm GMT

Russell Coker: Zswap

Zswap vs Zram

Last year I blogged about using Zram for VMs [1]. That setup is still working well for VMs and for phones and laptops with no swap device.

I have just read Chris Down's insightful blog post about Zswap vs Zram [2] which convinced me to setup Zswap on some systems. I have had some of the problems that were described in his blog post when trying to run Zram on workstation and server systems.

One limitation of zswap is that it doesn't allow specifying the compression level. For zram I can put the following in /etc/systemd/zram-generator.conf to set the zstd compression level (this works well on my Thinkpad X1 Carbon Gen6):

[zram0]
compression-algorithm=zstd(level=10)

For the BTRFS filesystem I can put "compress=zstd:13" in the mount options to specify the compression level. They really should support different compression levels in zswap. The ideal compression level depends on the speed of the CPU and new CPUs keep getting faster.

Setup

The documentation says to use something like the following on the kernel command-line to enable zswap:

zswap.enabled=1 zswap.compressor=zstd zswap.max_pool_percent=20 zswap.shrinker_enabled=1

The max_pool_percent=20 setting is the default which means to use up to 20% of system RAM for compressed data. I've seen documentation sugesting up to 50% which seems a little excessive.

Note that a lot of documentation says to use zswap.zpool=z3fold, but z3fold is going to be removed and zsmalloc (the default) is recommended [3].

There is documentation about changing the compression algorithm via command line parameters, on Debian only lzo is linked in to the kernel and zstd (my preferred option) is a module so the kernel command line can't be used to set zstd, but the following command works:

echo zstd > /sys/module/zswap/parameters/compressor

The shrinker_enabled option is to allow the kernel to evict cold pages without waiting for memory pressure.

You can enable zswap without rebooting by running commands like the following. You could even put them in /etc/rc.local or something, but I think putting it in the kernel command line is a good idea as it makes it obvious to the next sysadmin what is happening.

echo 1 > /sys/module/zswap/parameters/enabled
echo zstd > /sys/module/zswap/parameters/compressor
echo 1 > /sys/module/zswap/parameters/shrinker_enabled

Monitoring

The following command is documented as a way of finding out what zswap is doing:

# grep -r . /sys/kernel/debug/zswap/
/sys/kernel/debug/zswap/stored_pages:262541
/sys/kernel/debug/zswap/pool_total_size:455266304
/sys/kernel/debug/zswap/written_back_pages:384
/sys/kernel/debug/zswap/reject_compress_poor:0
/sys/kernel/debug/zswap/reject_compress_fail:160911
/sys/kernel/debug/zswap/reject_kmemcache_fail:0
/sys/kernel/debug/zswap/reject_alloc_fail:0
/sys/kernel/debug/zswap/reject_reclaim_fail:0
/sys/kernel/debug/zswap/pool_limit_hit:0

The following command gives the zswap compression level which gives a result of 2.36 for this example:

echo "scale=2; " $(</sys/kernel/debug/zswap/stored_pages) " * $(getconf PAGESIZE) /" $(</sys/kernel/debug/zswap/pool_total_size) | bc

This table documents my current understanding of the debug values. The difference between reject_compress_fail and reject_compress_poor isn't clear in a lot of the documentation, even reading the source didn't make it easy to understand.

File Meaning (LC is lifetime count)
pool_limit_hit LC pool limit hit and pages are forced to the swap partition
pool_total_size RAM used for zswap data
reject_alloc_fail LC can't allocate memory because max_pool_percent has been reached
reject_compress_fail LC of pages with a compression algorithm failure so go straight to swap partition
reject_compress_poor LC of pages that can't compress so go straight to swap partition
reject_kmemcache_fail LC kernel malloc failure (serious problem?)
reject_reclaim_fail LC failure to move a page from compressed RAM to disk - serious problem!
stored_pages Swapped pages stored by zswap
written_back_pages LC of pages written back to swap partition from zswap

All of this is not nearly as easy to understand as the following command for zram:

# zramctl 
NAME       ALGORITHM DISKSIZE  DATA COMPR TOTAL STREAMS MOUNTPOINT
/dev/zram0 zstd          7.7G  2.1G  375M  386M       4 [SWAP]

Debian Wiki

The Debian Wiki page about Zswap is very brief [4] and needs more description about this, I think a lot of Debian users will use zram instead of zswap because setting up zram is just a single apt command. I'm not planning to immediately add to that wiki page because I'm not an expert on this, I would appreciate comments on this blog post from others who have got zswap working. I will update the wiki if others report matching experiences to mine.

Conclusion

I'm now using zswap on a few systems including my main home workstation which had performed poorly with zram and a swap device in the past. If that goes well I'll put it on other systems.

I wrote the following shell script to display zswap stats, consider it GPL if you want to use it:

#!/bin/bash

if [ ! -f /sys/kernel/debug/zswap/stored_pages ]; then
  echo "ZSwap not enabled"
  exit 0
fi
PAGES=$(</sys/kernel/debug/zswap/stored_pages)
PAGESIZE=$(getconf PAGESIZE)
RAM=$(echo "$PAGESIZE * " $(getconf _PHYS_PAGES) | bc)
POOL=$(</sys/kernel/debug/zswap/pool_total_size)
if [ "$POOL" == "0" ]; then
  echo "ZSwap not used yet"
  exit 0
fi
COMP=$(</sys/module/zswap/parameters/compressor)
echo -n "$COMP compression ratio: "
echo "scale=2; $PAGES * $PAGESIZE / $POOL" | bc
echo -n "RAM%: "
echo "100 * $POOL / $RAM" | bc

29 May 2026 11:59am GMT

28 May 2026

feedPlanet Debian

Jonathan Dowland: nvim-µwiki

In January 2025, as a pre-requisite for something else, I published a minimal neovim plugin called nvim-µwiki. It's essentially just the features from vimwiki that I regularly use, which is a small fraction them. I forgot to blog about it. I recently dusted it off and cleaned it up. You can find it here, along with a longer list of its features and how to configure it: https://github.com/jmtd/nvim-microwiki

I had a couple of design goals. I didn't want to define a new filetype, so this is designed to work with the existing markdown one. I'm using neovim, so I wanted to leverage some of its features: this plugin is written in Lua, rather than vimscript. I use the parse trees provided by TreeSitter to navigate the structure of a document. I also decided to "plug into" the existing tag stack navigation, rather than define another dimension of navigation (along with buffers, etc.) to track: Following a wiki-link pushes onto the tag stack, just as if you followed a tag.

This was my first serious bit of Lua programming, as well as my first dive into neovim (or even vim) internals. Lua is quite reasonable. Most of the vim and neovim architecture is reasonable. The emerging conventions about structuring neovim plugins are mostly reasonable. TreeSitter is, well, interesting, but the devil is very much in the details. Somehow all together the experience for me was largely just frustrating, and I didn't really enjoy writing it.

28 May 2026 8:48am GMT